mcp-code-indexer 1.1.1__tar.gz → 1.1.3__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. {mcp_code_indexer-1.1.1/src/mcp_code_indexer.egg-info → mcp_code_indexer-1.1.3}/PKG-INFO +1 -1
  2. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/pyproject.toml +1 -1
  3. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/server/mcp_server.py +46 -30
  4. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3/src/mcp_code_indexer.egg-info}/PKG-INFO +1 -1
  5. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/LICENSE +0 -0
  6. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/MANIFEST.in +0 -0
  7. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/README.md +0 -0
  8. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/docs/api-reference.md +0 -0
  9. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/docs/architecture.md +0 -0
  10. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/docs/configuration.md +0 -0
  11. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/docs/contributing.md +0 -0
  12. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/migrations/001_initial.sql +0 -0
  13. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/migrations/002_performance_indexes.sql +0 -0
  14. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/requirements.txt +0 -0
  15. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/setup.cfg +0 -0
  16. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/setup.py +0 -0
  17. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/__init__.py +0 -0
  18. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/database/__init__.py +0 -0
  19. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/database/database.py +0 -0
  20. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/database/models.py +0 -0
  21. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/error_handler.py +0 -0
  22. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/file_scanner.py +0 -0
  23. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/logging_config.py +0 -0
  24. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/main.py +0 -0
  25. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/merge_handler.py +0 -0
  26. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/middleware/__init__.py +0 -0
  27. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/middleware/error_middleware.py +0 -0
  28. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/server/__init__.py +0 -0
  29. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/tiktoken_cache/9b5ad71b2ce5302211f9c61530b329a4922fc6a4 +0 -0
  30. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/token_counter.py +0 -0
  31. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer/tools/__init__.py +0 -0
  32. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer.egg-info/SOURCES.txt +0 -0
  33. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer.egg-info/dependency_links.txt +0 -0
  34. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer.egg-info/entry_points.txt +0 -0
  35. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer.egg-info/requires.txt +0 -0
  36. {mcp_code_indexer-1.1.1 → mcp_code_indexer-1.1.3}/src/mcp_code_indexer.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: mcp-code-indexer
3
- Version: 1.1.1
3
+ Version: 1.1.3
4
4
  Summary: MCP server that tracks file descriptions across codebases, enabling AI agents to efficiently navigate and understand code through searchable summaries and token-aware overviews.
5
5
  Author: MCP Code Indexer Contributors
6
6
  Maintainer: MCP Code Indexer Contributors
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "mcp-code-indexer"
7
- version = "1.1.1"
7
+ version = "1.1.3"
8
8
  description = "MCP server that tracks file descriptions across codebases, enabling AI agents to efficiently navigate and understand code through searchable summaries and token-aware overviews."
9
9
  readme = "README.md"
10
10
  license = {text = "MIT"}
@@ -159,7 +159,8 @@ class MCPCodeIndexServer:
159
159
  "folderPath": {"type": "string", "description": "Absolute path to the project folder on disk"},
160
160
  "branch": {"type": "string", "description": "Git branch name"},
161
161
  "remoteOrigin": {"type": ["string", "null"], "description": "Git remote origin URL if available"},
162
- "upstreamOrigin": {"type": ["string", "null"], "description": "Upstream repository URL if this is a fork"}
162
+ "upstreamOrigin": {"type": ["string", "null"], "description": "Upstream repository URL if this is a fork"},
163
+ "tokenLimit": {"type": "integer", "description": "Optional token limit override (defaults to server configuration)"}
163
164
  },
164
165
  "required": ["projectName", "folderPath", "branch"]
165
166
  }
@@ -473,19 +474,28 @@ class MCPCodeIndexServer:
473
474
  await self.db_manager.update_project(project)
474
475
  logger.debug(f"Updated project metadata for {project.name}")
475
476
 
476
- async def _find_best_branch(self, project_id: str, requested_branch: str) -> Optional[str]:
477
+ async def _resolve_branch(self, project_id: str, requested_branch: str) -> str:
477
478
  """
478
- Find the best available branch for a project when the requested branch has no files.
479
- Returns the branch with the most files, or None if no branches have files.
479
+ Resolve the actual branch to use for operations.
480
+
481
+ For new projects or branches with no existing files, uses the requested branch.
482
+ For existing projects, tries to find a consistent branch to avoid data fragmentation.
483
+
484
+ Returns the resolved branch name.
480
485
  """
481
486
  try:
482
487
  # Get all branches and their file counts for this project
483
488
  branch_counts = await self.db_manager.get_branch_file_counts(project_id)
484
489
 
490
+ # If no existing data, use the requested branch
485
491
  if not branch_counts:
486
- return None
492
+ return requested_branch
493
+
494
+ # If requested branch has files, use it
495
+ if requested_branch in branch_counts and branch_counts[requested_branch] > 0:
496
+ return requested_branch
487
497
 
488
- # First try common branch name variations
498
+ # Try common branch name variations to find existing data
489
499
  common_variations = {
490
500
  'main': ['master', 'develop', 'development', 'dev'],
491
501
  'master': ['main', 'develop', 'development', 'dev'],
@@ -498,23 +508,31 @@ class MCPCodeIndexServer:
498
508
  if requested_branch.lower() in common_variations:
499
509
  for variation in common_variations[requested_branch.lower()]:
500
510
  if variation in branch_counts and branch_counts[variation] > 0:
511
+ logger.info(f"Resolved branch '{requested_branch}' to existing branch '{variation}' with {branch_counts[variation]} files")
501
512
  return variation
502
513
 
503
- # Fall back to the branch with the most files
514
+ # If no variations found, check if we should use the main data branch
515
+ # (to avoid fragmenting data across multiple branches)
504
516
  best_branch = max(branch_counts.items(), key=lambda x: x[1])
505
- return best_branch[0] if best_branch[1] > 0 else None
517
+ if best_branch[1] > 10: # Only if there's substantial existing data
518
+ logger.info(f"Using primary branch '{best_branch[0]}' instead of '{requested_branch}' to avoid data fragmentation")
519
+ return best_branch[0]
520
+
521
+ # Fall back to requested branch for new/small projects
522
+ return requested_branch
506
523
 
507
524
  except Exception as e:
508
- logger.warning(f"Error finding best branch: {e}")
509
- return None
525
+ logger.warning(f"Error resolving branch: {e}")
526
+ return requested_branch
510
527
 
511
528
  async def _handle_get_file_description(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
512
529
  """Handle get_file_description tool calls."""
513
530
  project_id = await self._get_or_create_project_id(arguments)
531
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
514
532
 
515
533
  file_desc = await self.db_manager.get_file_description(
516
534
  project_id=project_id,
517
- branch=arguments["branch"],
535
+ branch=resolved_branch,
518
536
  file_path=arguments["filePath"]
519
537
  )
520
538
 
@@ -535,10 +553,11 @@ class MCPCodeIndexServer:
535
553
  async def _handle_update_file_description(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
536
554
  """Handle update_file_description tool calls."""
537
555
  project_id = await self._get_or_create_project_id(arguments)
556
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
538
557
 
539
558
  file_desc = FileDescription(
540
559
  project_id=project_id,
541
- branch=arguments["branch"],
560
+ branch=resolved_branch,
542
561
  file_path=arguments["filePath"],
543
562
  description=arguments["description"],
544
563
  file_hash=arguments.get("fileHash"),
@@ -558,46 +577,40 @@ class MCPCodeIndexServer:
558
577
  async def _handle_check_codebase_size(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
559
578
  """Handle check_codebase_size tool calls."""
560
579
  project_id = await self._get_or_create_project_id(arguments)
561
- requested_branch = arguments["branch"]
580
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
562
581
 
563
582
  # Get file descriptions for this project/branch
564
583
  file_descriptions = await self.db_manager.get_all_file_descriptions(
565
584
  project_id=project_id,
566
- branch=requested_branch
585
+ branch=resolved_branch
567
586
  )
568
587
 
569
- # If no files found for requested branch, try to find the best available branch
570
- if not file_descriptions:
571
- available_branch = await self._find_best_branch(project_id, requested_branch)
572
- if available_branch and available_branch != requested_branch:
573
- file_descriptions = await self.db_manager.get_all_file_descriptions(
574
- project_id=project_id,
575
- branch=available_branch
576
- )
577
- logger.info(f"No files found for branch '{requested_branch}', using '{available_branch}' instead")
588
+ # Use provided token limit or fall back to server default
589
+ token_limit = arguments.get("tokenLimit", self.token_limit)
578
590
 
579
591
  # Calculate total tokens
580
592
  total_tokens = self.token_counter.calculate_codebase_tokens(file_descriptions)
581
- is_large = self.token_counter.is_large_codebase(total_tokens)
582
- recommendation = self.token_counter.get_recommendation(total_tokens)
593
+ is_large = total_tokens > token_limit
594
+ recommendation = "use_search" if is_large else "use_overview"
583
595
 
584
596
  return {
585
597
  "totalTokens": total_tokens,
586
598
  "isLarge": is_large,
587
599
  "recommendation": recommendation,
588
- "tokenLimit": self.token_counter.token_limit,
600
+ "tokenLimit": token_limit,
589
601
  "totalFiles": len(file_descriptions)
590
602
  }
591
603
 
592
604
  async def _handle_find_missing_descriptions(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
593
605
  """Handle find_missing_descriptions tool calls."""
594
606
  project_id = await self._get_or_create_project_id(arguments)
607
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
595
608
  folder_path = Path(arguments["folderPath"])
596
609
 
597
610
  # Get existing file descriptions
598
611
  existing_descriptions = await self.db_manager.get_all_file_descriptions(
599
612
  project_id=project_id,
600
- branch=arguments["branch"]
613
+ branch=resolved_branch
601
614
  )
602
615
  existing_paths = {desc.file_path for desc in existing_descriptions}
603
616
 
@@ -631,12 +644,13 @@ class MCPCodeIndexServer:
631
644
  async def _handle_search_descriptions(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
632
645
  """Handle search_descriptions tool calls."""
633
646
  project_id = await self._get_or_create_project_id(arguments)
647
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
634
648
  max_results = arguments.get("maxResults", 20)
635
649
 
636
650
  # Perform search
637
651
  search_results = await self.db_manager.search_file_descriptions(
638
652
  project_id=project_id,
639
- branch=arguments["branch"],
653
+ branch=resolved_branch,
640
654
  query=arguments["query"],
641
655
  max_results=max_results
642
656
  )
@@ -660,11 +674,12 @@ class MCPCodeIndexServer:
660
674
  async def _handle_get_codebase_overview(self, arguments: Dict[str, Any]) -> Dict[str, Any]:
661
675
  """Handle get_codebase_overview tool calls."""
662
676
  project_id = await self._get_or_create_project_id(arguments)
677
+ resolved_branch = await self._resolve_branch(project_id, arguments["branch"])
663
678
 
664
679
  # Get all file descriptions
665
680
  file_descriptions = await self.db_manager.get_all_file_descriptions(
666
681
  project_id=project_id,
667
- branch=arguments["branch"]
682
+ branch=resolved_branch
668
683
  )
669
684
 
670
685
  # Calculate total tokens
@@ -687,7 +702,8 @@ class MCPCodeIndexServer:
687
702
 
688
703
  return {
689
704
  "projectName": arguments["projectName"],
690
- "branch": arguments["branch"],
705
+ "branch": resolved_branch,
706
+ "requestedBranch": arguments["branch"] if arguments["branch"] != resolved_branch else None,
691
707
  "totalFiles": len(file_descriptions),
692
708
  "totalTokens": total_tokens,
693
709
  "isLarge": is_large,
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: mcp-code-indexer
3
- Version: 1.1.1
3
+ Version: 1.1.3
4
4
  Summary: MCP server that tracks file descriptions across codebases, enabling AI agents to efficiently navigate and understand code through searchable summaries and token-aware overviews.
5
5
  Author: MCP Code Indexer Contributors
6
6
  Maintainer: MCP Code Indexer Contributors