content: package com.example.demo.service;
  
  import com.example.demo.model.ProjectContext;
  import com.example.demo.model.ProjectStructure;
  import com.example.demo.model.ProjectType;
  import com.fasterxml.jackson.databind.JsonNode;
  import com.fasterxml.jackson.databind.ObjectMapper;
  import org.slf4j.Logger;
  import org.slf4j.LoggerFactory;
  import org.springframework.beans.factory.annotation.Autowired;
  import org.springframework.stereotype.Service;
  
  import java.io.IOException;
  import java.nio.file.Files;
  import java.nio.file.Path;
  import java.util.ArrayList;
  import java.util.List;
  import java.util.stream.Stream;
  
  /**
   * 项目发现和分析服务
   * 负责分析项目结构、依赖关系和配置信息
   */
  @Service
  public class ProjectDiscoveryService {
      
      private static final Logger logger = LoggerFactory.getLogger(ProjectDiscoveryService.class);
      
      @Autowired
      private ProjectTypeDetector projectTypeDetector;
      
      private final ObjectMapper objectMapper = new ObjectMapper();
      
      /**
       * 分析项目结构
       * @param projectRoot 项目根目录
       * @return 项目结构信息
       */
      public ProjectStructure analyzeProjectStructure(Path projectRoot) {
          logger.debug("Analyzing project structure for: {}", projectRoot);
          
          ProjectType projectType = projectTypeDetector.detectProjectType(projectRoot);
          ProjectStructure structure = new ProjectStructure(projectRoot, projectType);
          
          try {
              analyzeDirectoryStructure(projectRoot, structure, 0, 3); // 最大深度3层
              structure.markImportantDirectories();
              
              logger.info("Project structure analysis completed for: {}", projectRoot);
              return structure;
              
          } catch (IOException e) {
              logger.error("Error analyzing project structure for: " + projectRoot, e);
              return structure; // 返回部分分析结果
          }
      }
      
      /**
       * 递归分析目录结构
       */
      private void analyzeDirectoryStructure(Path currentPath, ProjectStructure structure, 
                                           int currentDepth, int maxDepth) throws IOException {
          if (currentDepth > maxDepth) {
              return;
          }
          
          try (Stream<Path> paths = Files.list(currentPath)) {
              paths.forEach(path -> {
                  try {
                      if (Files.isDirectory(path)) {
                          String dirName = path.getFileName().toString();
                          String relativePath = structure.getProjectRoot().relativize(path).toString();
                          
                          // 跳过常见的忽略目录
                          if (shouldIgnoreDirectory(dirName)) {
                              return;
                          }
                          
                          ProjectStructure.DirectoryInfo dirInfo = 
                              new ProjectStructure.DirectoryInfo(dirName, relativePath);
                          
                          // 分析目录中的文件
                          analyzeDirectoryFiles(path, dirInfo);
                          structure.addDirectory(dirInfo);
                          
                          // 递归分析子目录
                          if (currentDepth < maxDepth) {
                              analyzeDirectoryStructure(path, structure, currentDepth + 1, maxDepth);
                          }
                          
                      } else if (Files.isRegularFile(path)) {
                          // 处理根目录下的文件
                          String fileName = path.getFileName().toString();
                          String extension = getFileExtension(fileName);
                          
                          structure.addFileType(extension, 1);
                          structure.setTotalFiles(structure.getTotalFiles() + 1);
                          
                          // 检查是否为关键文件
                          if (isKeyFile(fileName, structure.getProjectType())) {
                              structure.addKeyFile(fileName);
                          }
                          
                          // 累计文件大小
                          try {
                              structure.setTotalSize(structure.getTotalSize() + Files.size(path));
                          } catch (IOException e) {
                              logger.warn("Could not get size for file: {}", path);
                          }
                      }
                  } catch (Exception e) {
                      logger.warn("Error processing path: " + path, e);
                  }
              });
          }
      }
      
      /**
       * 分析目录中的文件
       */
      private void analyzeDirectoryFiles(Path directory, ProjectStructure.DirectoryInfo dirInfo) {
          try (Stream<Path> files = Files.list(directory)) {
              files.filter(Files::isRegularFile)
                   .forEach(file -> {
                       String fileName = file.getFileName().toString();
                       dirInfo.addFile(fileName);
                   });
          } catch (IOException e) {
              logger.warn("Error analyzing files in directory: {}", directory);
          }
      }
      
      /**
       * 分析项目依赖
       */
      public List<ProjectContext.DependencyInfo> analyzeDependencies(Path projectRoot) {
          logger.debug("Analyzing dependencies for: {}", projectRoot);
          
          List<ProjectContext.DependencyInfo> dependencies = new ArrayList<>();
          ProjectType projectType = projectTypeDetector.detectProjectType(projectRoot);
          
          try {
              switch (projectType) {
                  case JAVA_MAVEN:
                  case SPRING_BOOT:
                      dependencies.addAll(analyzeMavenDependencies(projectRoot));
                      break;
                  case NODE_JS:
                  case REACT:
                  case VUE:
                  case ANGULAR:
                  case NEXT_JS:
                      dependencies.addAll(analyzeNpmDependencies(projectRoot));
                      break;
                  case PYTHON:
                  case DJANGO:
                  case FLASK:
                  case FASTAPI:
                      dependencies.addAll(analyzePythonDependencies(projectRoot));
                      break;
                  default:
                      logger.info("Dependency analysis not supported for project type: {}", projectType);
              }
          } catch (Exception e) {
              logger.error("Error analyzing dependencies for: " + projectRoot, e);
          }
          
          logger.info("Found {} dependencies for project: {}", dependencies.size(), projectRoot);
          return dependencies;
      }
      
      /**
       * 分析Maven依赖
       */
      private List<ProjectContext.DependencyInfo> analyzeMavenDependencies(Path projectRoot) {
          List<ProjectContext.DependencyInfo> dependencies = new ArrayList<>();
          Path pomFile = projectRoot.resolve("pom.xml");
          
          if (!Files.exists(pomFile)) {
              return dependencies;
          }
          
          try {
              String pomContent = Files.readString(pomFile);
              // 简单的XML解析 - 在实际项目中应该使用专门的XML解析器
              if (pomContent.contains("spring-boot-starter-web")) {
                  dependencies.add(new ProjectContext.DependencyInfo(
                      "spring-boot-starter-web", "auto", "compile"));
              }
              if (pomContent.contains("spring-boot-starter-data-jpa")) {
                  dependencies.add(new ProjectContext.DependencyInfo(
                      "spring-boot-starter-data-jpa", "auto", "compile"));
              }
              if (pomContent.contains("spring-boot-starter-test")) {
                  dependencies.add(new ProjectContext.DependencyInfo(
                      "spring-boot-starter-test", "auto", "test"));
              }
              // 可以添加更多依赖检测逻辑
              
          } catch (IOException e) {
              logger.warn("Error reading pom.xml", e);
          }
          
          return dependencies;
      }
      
      /**
       * 分析NPM依赖
       */
      private List<ProjectContext.DependencyInfo> analyzeNpmDependencies(Path projectRoot) {
          List<ProjectContext.DependencyInfo> dependencies = new ArrayList<>();
          Path packageJsonPath = projectRoot.resolve("package.json");
          
          if (!Files.exists(packageJsonPath)) {
              return dependencies;
          }
          
          try {
              String content = Files.readString(packageJsonPath);
              JsonNode packageJson = objectMapper.readTree(content);
              
              // 分析生产依赖
              JsonNode deps = packageJson.get("dependencies");
              if (deps != null) {
                  deps.fields().forEachRemaining(entry -> {
                      dependencies.add(new ProjectContext.DependencyInfo(
                          entry.getKey(), entry.getValue().asText(), "production"));
                  });
              }
              
              // 分析开发依赖
              JsonNode devDeps = packageJson.get("devDependencies");
              if (devDeps != null) {
                  devDeps.fields().forEachRemaining(entry -> {
                      ProjectContext.DependencyInfo depInfo = new ProjectContext.DependencyInfo(
                          entry.getKey(), entry.getValue().asText(), "development");
                      depInfo.setDirectDependency(true);
                      dependencies.add(depInfo);
                  });
              }
              
          } catch (IOException e) {
              logger.warn("Error reading package.json", e);
          }
          
          return dependencies;
      }
      
      /**
       * 分析Python依赖
       */
      private List<ProjectContext.DependencyInfo> analyzePythonDependencies(Path projectRoot) {
          List<ProjectContext.DependencyInfo> dependencies = new ArrayList<>();
          Path requirementsFile = projectRoot.resolve("requirements.txt");
          
          if (Files.exists(requirementsFile)) {
              try {
                  List<String> lines = Files.readAllLines(requirementsFile);
                  for (String line : lines) {
                      line = line.trim();
                      if (!line.isEmpty() && !line.startsWith("#")) {
                          String[] parts = line.split("==|>=|<=|>|<");
                          String name = parts[0].trim();
                          String version = parts.length > 1 ? parts[1].trim() : "latest";
                          dependencies.add(new ProjectContext.DependencyInfo(name, version, "runtime"));
                      }
                  }
              } catch (IOException e) {
                  logger.warn("Error reading requirements.txt", e);
              }
          }
          
          return dependencies;
      }
      
      /**
       * 查找配置文件
       */
      public List<ProjectContext.ConfigFile> findConfigurationFiles(Path projectRoot) {
          logger.debug("Finding configuration files for: {}", projectRoot);
          
          List<ProjectContext.ConfigFile> configFiles = new ArrayList<>();
          ProjectType projectType = projectTypeDetector.detectProjectType(projectRoot);
          
          try {
              // 通用配置文件
              addConfigFileIfExists(configFiles, projectRoot, "application.properties", "properties");
              addConfigFileIfExists(configFiles, projectRoot, "application.yml", "yaml");
              addConfigFileIfExists(configFiles, projectRoot, "application.yaml", "yaml");
              addConfigFileIfExists(configFiles, projectRoot, "config.json", "json");
              
              // 项目类型特定的配置文件
              switch (projectType) {
                  case JAVA_MAVEN:
                  case SPRING_BOOT:
                      addConfigFileIfExists(configFiles, projectRoot, "pom.xml", "xml");
                      break;
                  case NODE_JS:
                  case REACT:
                  case VUE:
                  case ANGULAR:
                  case NEXT_JS:
                      addConfigFileIfExists(configFiles, projectRoot, "package.json", "json");
                      addConfigFileIfExists(configFiles, projectRoot, "webpack.config.js", "javascript");
                      break;
                  case PYTHON:
                  case DJANGO:
                  case FLASK:
                  case FASTAPI:
                      addConfigFileIfExists(configFiles, projectRoot, "requirements.txt", "text");
                      addConfigFileIfExists(configFiles, projectRoot, "setup.py", "python");
                      break;
              }
              
          } catch (Exception e) {
              logger.error("Error finding configuration files for: " + projectRoot, e);
          }
          
          logger.info("Found {} configuration files for project: {}", configFiles.size(), projectRoot);
          return configFiles;
      }
      
      /**
       * 添加配置文件（如果存在）
       */
      private void addConfigFileIfExists(List<ProjectContext.ConfigFile> configFiles, 
                                       Path projectRoot, String fileName, String fileType) {
          Path configPath = projectRoot.resolve(fileName);
          if (Files.exists(configPath)) {
              String relativePath = projectRoot.relativize(configPath).toString();
              ProjectContext.ConfigFile configFile = 
                  new ProjectContext.ConfigFile(fileName, relativePath, fileType);
              
              // 标记主要配置文件
              if (fileName.equals("pom.xml") || fileName.equals("package.json") || 
                  fileName.startsWith("application.")) {
                  configFile.setMainConfig(true);
              }
              
              configFiles.add(configFile);
          }
      }
      
      /**
       * 检查是否应该忽略目录
       */
      private boolean shouldIgnoreDirectory(String dirName) {
          return dirName.equals(".git") || dirName.equals(".svn") || 
                 dirName.equals("node_modules") || dirName.equals("target") ||
                 dirName.equals("build") || dirName.equals("dist") ||
                 dirName.equals("__pycache__") || dirName.equals(".idea") ||
                 dirName.equals(".vscode") || dirName.startsWith(".");
      }
      
      /**
       * 获取文件扩展名
       */
      private String getFileExtension(String fileName) {
          int lastDot = fileName.lastIndexOf('.');
          return lastDot > 0 ? fileName.substring(lastDot) : "";
      }
      
      /**
       * 检查是否为关键文件
       */
      private boolean isKeyFile(String fileName, ProjectType projectType) {
          // 通用关键文件
          if (fileName.equals("README.md") || fileName.equals("LICENSE") || 
              fileName.equals("Dockerfile") || fileName.equals(".gitignore")) {
              return true;
          }
          
          // 项目类型特定的关键文件
          if (projectType != null) {
              String keyFile = projectType.getKeyFile();
              if (keyFile != null && !keyFile.isEmpty()) {
                  return fileName.equals(keyFile) || fileName.matches(keyFile);
              }
          }
          
          return false;
      }
  }
  