templatesPath = __DIR__ . '/../../templates'; } /** * 生成PHP代码文件 */ public function generatePhpFiles(string $packageName, string $namespace, string $id, string $description, string $targetPath, SymfonyStyle $io): bool { try { $basePath = $this->getBasePath($packageName, $targetPath); // 准备模板变量 $variables = [ 'namespace' => $namespace, 'name' => $packageName, 'id' => $id, 'description' => $description ]; // 获取所有需要生成的PHP文件模板 $templateFiles = $this->getTemplateFiles(); $io->section('生成PHP代码文件:'); foreach ($templateFiles as $templateFile) { if (!$this->generateFileFromTemplate($templateFile, $basePath, $variables, $io)) { return false; } } $io->success('PHP代码文件生成完成!'); return true; } catch (\Exception $e) { $io->error('生成PHP代码文件时发生错误: ' . $e->getMessage()); return false; } } /** * 获取扩展基础路径 */ private function getBasePath(string $packageName, ?string $targetPath = null): string { if ($targetPath !== null) { return $targetPath; } // 默认路径 $vendorDir = dirname(__DIR__, 5); return $vendorDir . '/runtime/extension/' . $packageName; } /** * 获取所有模板文件 */ private function getTemplateFiles(): array { $templates = []; $this->scanTemplateDirectory($this->templatesPath, '', $templates); return $templates; } /** * 递归扫描模板目录 */ private function scanTemplateDirectory(string $directory, string $relativePath, array &$templates): void { if (!is_dir($directory)) { return; } $items = scandir($directory); foreach ($items as $item) { if ($item === '.' || $item === '..') { continue; } $fullPath = $directory . '/' . $item; $currentRelativePath = $relativePath ? $relativePath . '/' . $item : $item; if (is_dir($fullPath)) { // 检查是否为排除的目录 if ($this->isExcludedTemplate($currentRelativePath)) { continue; } // 递归扫描子目录 $this->scanTemplateDirectory($fullPath, $currentRelativePath, $templates); } elseif (is_file($fullPath) && str_ends_with($item, '.php.tpl.php')) { // 检查是否为排除的模板文件 if ($this->isExcludedTemplate($currentRelativePath)) { continue; } // 添加模板文件 $templates[] = [ 'template' => $currentRelativePath, 'target' => str_replace('.tpl.php', '', $currentRelativePath), 'fullPath' => $fullPath ]; } } } /** * 从模板生成文件 */ private function generateFileFromTemplate(array $templateInfo, string $basePath, array $variables, SymfonyStyle $io): bool { $templatePath = $templateInfo['fullPath']; $targetPath = $basePath . '/' . $templateInfo['target']; // 确保目标目录存在 $targetDir = dirname($targetPath); if (!is_dir($targetDir)) { if (!mkdir($targetDir, 0755, true)) { $io->error("无法创建目录: $targetDir"); return false; } } // 如果文件已存在,询问是否覆盖 if (file_exists($targetPath)) { if (!$io->confirm("文件已存在: {$templateInfo['target']},是否覆盖?", false)) { $io->text("跳过文件: {$templateInfo['target']}"); return true; } } // 提取变量到当前作用域 // 命名空间双斜杆需要改为单斜杠 $namespace = str_replace('\\\\', '\\', $variables['namespace']); $name = $variables['name']; $id = $variables['id']; $description = $variables['description']; // 生成文件内容 ob_start(); include $templatePath; $content = ob_get_clean(); // 写入文件 if (file_put_contents($targetPath, $content) !== false) { $io->text("✓ 生成文件: {$templateInfo['target']}"); return true; } else { $io->error("✗ 无法写入文件: {$templateInfo['target']}"); return false; } } /** * 获取模板文件列表(用于预览) */ public function getTemplateList(): array { return $this->getTemplateFiles(); } /** * 检查模板是否在排除列表中 */ private function isExcludedTemplate(string $templatePath): bool { foreach ($this->excludedTemplates as $excludedPattern) { // 支持精确匹配和前缀匹配 if ($templatePath === $excludedPattern || str_starts_with($templatePath, $excludedPattern)) { return true; } } return false; } /** * 设置排除的模板列表 */ public function setExcludedTemplates(array $excludedTemplates): self { $this->excludedTemplates = $excludedTemplates; return $this; } /** * 添加排除的模板 */ public function addExcludedTemplate(string $templatePath): self { if (!in_array($templatePath, $this->excludedTemplates)) { $this->excludedTemplates[] = $templatePath; } return $this; } /** * 移除排除的模板 */ public function removeExcludedTemplate(string $templatePath): self { $this->excludedTemplates = array_filter( $this->excludedTemplates, fn($excluded) => $excluded !== $templatePath ); return $this; } /** * 获取当前排除的模板列表 */ public function getExcludedTemplates(): array { return $this->excludedTemplates; } }