templates = [ 'controller' => $this->getControllerTemplate(), 'method' => $this->getMethodTemplate(), 'api_controller' => $this->getApiControllerTemplate(), 'resource_controller' => $this->getResourceControllerTemplate() ]; } public function generate(string $name, array $options = []): bool { if (!$this->validateName($name)) { return false; } $className = $this->getClassName($name) . 'Controller'; $type = $options['type'] ?? 'basic'; $resource = $options['resource'] ?? null; $api = $options['api'] ?? false; $methods = $options['methods'] ?? []; $subNamespace = 'Controller'; if ($api) { $subNamespace .= '\\Api'; } $path = $this->getNamespacePath($subNamespace); $namespace = $this->getFullNamespace($subNamespace); if (!$this->createDirectory($path)) { return false; } $content = $this->generateController($className, $namespace, $type, $resource, $methods, $options); $filePath = $path . '/' . $className . '.php'; if (!$this->createFile($filePath, $content)) { return false; } $this->showMessage('success', "Controller '{$className}' generated successfully!"); // 生成路由提示 $this->showRouteHint($className, $resource, $api); return true; } private function generateController(string $className, string $namespace, string $type, ?string $resource, array $methods, array $options): string { switch ($type) { case 'api': return $this->generateApiController($className, $namespace, $resource, $methods, $options); case 'resource': return $this->generateResourceController($className, $namespace, $resource, $options); default: return $this->generateBasicController($className, $namespace, $methods, $options); } } private function generateBasicController(string $className, string $namespace, array $methods, array $options): string { $useStatements = []; $classMethods = ''; if (empty($methods)) { $methods = ['index']; } foreach ($methods as $method) { $classMethods .= $this->generateMethod($method, $options); if (in_array($method, ['request', 'response'])) { $useStatements[] = 'use Fendx\\Web\\Request\\Request;'; $useStatements[] = 'use Fendx\\Web\\Response\\Response;'; } } $useStatements = array_unique($useStatements); $useBlock = empty($useStatements) ? '' : implode("\n", $useStatements) . "\n\n"; return $this->renderTemplate('controller', [ 'namespace' => $namespace, 'use_block' => $useBlock, 'class_name' => $className, 'methods' => $classMethods ]); } private function generateApiController(string $className, string $namespace, ?string $resource, array $methods, array $options): string { $useStatements = [ 'use Fendx\\Core\\Annotation\\Controller;', 'use Fendx\\Web\\Annotation\\GetRoute;', 'use Fendx\\Web\\Annotation\\PostRoute;', 'use Fendx\\Web\\Annotation\\PutRoute;', 'use Fendx\\Web\\Annotation\\DeleteRoute;', 'use Fendx\\Web\\Request\\Request;', 'use Fendx\\Web\\Response\\Response;' ]; $classMethods = ''; $resourceName = $resource ?: strtolower(str_replace('Controller', '', $className)); if (empty($methods)) { $methods = ['index', 'show', 'store', 'update', 'destroy']; } foreach ($methods as $method) { $classMethods .= $this->generateApiMethod($method, $resourceName, $options); } return $this->renderTemplate('api_controller', [ 'namespace' => $namespace, 'use_block' => implode("\n", $useStatements) . "\n\n", 'class_name' => $className, 'resource_name' => $resourceName, 'methods' => $classMethods ]); } private function generateResourceController(string $className, string $namespace, ?string $resource, array $options): string { $useStatements = [ 'use Fendx\\Core\\Annotation\\Controller;', 'use Fendx\\Web\\Annotation\\GetRoute;', 'use Fendx\\Web\\Annotation\\PostRoute;', 'use Fendx\\Web\\Annotation\\PutRoute;', 'use Fendx\\Web\\Annotation\\DeleteRoute;', 'use Fendx\\Web\\Request\\Request;', 'use Fendx\\Web\\Response\\Response;' ]; $resourceName = $resource ?: strtolower(str_replace('Controller', '', $className)); $modelClass = $this->getClassName($resourceName); $modelNamespace = $this->getFullNamespace('Model'); $classMethods = $this->generateResourceMethods($resourceName, $modelClass, $modelNamespace, $options); return $this->renderTemplate('resource_controller', [ 'namespace' => $namespace, 'use_block' => implode("\n", $useStatements) . "\n\n", 'class_name' => $className, 'resource_name' => $resourceName, 'model_class' => $modelClass, 'model_namespace' => $modelNamespace, 'methods' => $classMethods ]); } private function generateMethod(string $method, array $options): string { $methodName = $method; $parameters = ''; $body = ''; $docBlock = ''; switch ($method) { case 'index': $docBlock = $this->generateDocBlock([], 'array'); $body = ' // TODO: Implement index method' . "\n" . ' return [];'; break; case 'show': $docBlock = $this->generateDocBlock(['id' => 'int'], 'array'); $parameters = 'int $id'; $body = ' // TODO: Implement show method' . "\n" . ' return [];'; break; case 'create': $docBlock = $this->generateDocBlock([], 'array'); $body = ' // TODO: Implement create method' . "\n" . ' return [];'; break; case 'store': $docBlock = $this->generateDocBlock(['request' => 'Request'], 'array'); $parameters = 'Request $request'; $useStatements[] = 'use Fendx\\Web\\Request\\Request;'; $body = ' // TODO: Implement store method' . "\n" . ' return [];'; break; case 'edit': $docBlock = $this->generateDocBlock(['id' => 'int'], 'array'); $parameters = 'int $id'; $body = ' // TODO: Implement edit method' . "\n" . ' return [];'; break; case 'update': $docBlock = $this->generateDocBlock(['id' => 'int', 'request' => 'Request'], 'array'); $parameters = 'int $id, Request $request'; $useStatements[] = 'use Fendx\\Web\\Request\\Request;'; $body = ' // TODO: Implement update method' . "\n" . ' return [];'; break; case 'destroy': $docBlock = $this->generateDocBlock(['id' => 'int'], 'bool'); $parameters = 'int $id'; $body = ' // TODO: Implement destroy method' . "\n" . ' return true;'; break; default: $docBlock = $this->generateDocBlock([], 'mixed'); $body = ' // TODO: Implement ' . $method . ' method' . "\n" . ' return null;'; } return $this->renderTemplate('method', [ 'doc_block' => $docBlock, 'method_name' => $methodName, 'parameters' => $parameters, 'body' => $body ]); } private function generateApiMethod(string $method, string $resourceName, array $options): string { $methodName = $method; $route = ''; $parameters = ''; $body = ''; $httpMethod = ''; switch ($method) { case 'index': $route = "/{$resourceName}"; $httpMethod = 'GetRoute'; $docBlock = $this->generateDocBlock([], 'array'); $body = ' $data = []; // TODO: Fetch data from database' . "\n" . ' return Response::success($data);'; break; case 'show': $route = "/{$resourceName}/{id}"; $httpMethod = 'GetRoute'; $parameters = 'int $id'; $docBlock = $this->generateDocBlock(['id' => 'int'], 'array'); $body = ' $data = []; // TODO: Fetch item by id' . "\n" . ' return Response::success($data);'; break; case 'store': $route = "/{$resourceName}"; $httpMethod = 'PostRoute'; $parameters = 'Request $request'; $docBlock = $this->generateDocBlock(['request' => 'Request'], 'array'); $body = ' $data = $request->all();' . "\n" . ' // TODO: Store data to database' . "\n" . ' return Response::success($data, \'Resource created successfully\');'; break; case 'update': $route = "/{$resourceName}/{id}"; $httpMethod = 'PutRoute'; $parameters = 'int $id, Request $request'; $docBlock = $this->generateDocBlock(['id' => 'int', 'request' => 'Request'], 'array'); $body = ' $data = $request->all();' . "\n" . ' // TODO: Update item by id' . "\n" . ' return Response::success($data, \'Resource updated successfully\');'; break; case 'destroy': $route = "/{$resourceName}/{id}"; $httpMethod = 'DeleteRoute'; $parameters = 'int $id'; $docBlock = $this->generateDocBlock(['id' => 'int'], 'array'); $body = ' // TODO: Delete item by id' . "\n" . ' return Response::success(null, \'Resource deleted successfully\');'; break; default: return ''; } return <<all(); \$item = {$modelClass}::create(\$data); return Response::success(\$item, '{$modelClass} created successfully'); } PHP; // Update method $methods .= <<all(); \$item->update(\$data); return Response::success(\$item, '{$modelClass} updated successfully'); } PHP; // Destroy method $methods .= <<delete(); return Response::success(null, '{$modelClass} deleted successfully'); } PHP; return $methods; } private function showRouteHint(string $className, ?string $resource, bool $api): void { $controllerName = str_replace('Controller', '', $className); $this->output->writeln(''); $this->output->writeln('Route registration hint:'); if ($api) { $this->output->writeln("Add this to your routes configuration:"); $this->output->writeln("\$router->mount('/api', function(\$router) {"); $this->output->writeln(" \$router->registerController(new {$this->getFullNamespace('Controller\\Api')}\\{$className}());"); $this->output->writeln("});"); } else { $this->output->writeln("Add this to your routes configuration:"); $this->output->writeln("\$router->registerController(new {$this->getFullNamespace('Controller')}\\{$className}());"); } } private function getControllerTemplate(): string { return <<