move_category
Relocate a category to a different parent location within a knowledge base to reorganize content structure.
Instructions
Move a category to a different parent location
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| source_path | Yes | Current category path (e.g., 'personal/work-notes') | |
| destination_path | Yes | New parent path (e.g., 'work/archived') |
Implementation Reference
- src/knowledge_base_mcp/server.py:389-406 (handler)MCP tool handler that extracts source_path and destination_path from arguments and delegates to storage.move_category, handling errors and returning TextContent.async def handle_move_category(arguments: dict) -> list[TextContent]: """Handle move_category tool call.""" try: source_path = arguments["source_path"] destination_path = arguments["destination_path"] result = storage.move_category( source_path=source_path, destination_path=destination_path, create_destination=True ) return [TextContent(type="text", text=result)] except (CategoryNotFoundError, CategoryExistsError, StorageError) as e: return [TextContent(type="text", text=str(e))] except Exception as e: return [TextContent(type="text", text=f"❌ Error: {str(e)}")]
- src/knowledge_base_mcp/server.py:106-123 (registration)Registration of the move_category tool in the list_tools handler, defining its name, description, and input schema.Tool( name="move_category", description="Move a category to a different parent location", inputSchema={ "type": "object", "properties": { "source_path": { "type": "string", "description": "Current category path (e.g., 'personal/work-notes')", }, "destination_path": { "type": "string", "description": "New parent path (e.g., 'work/archived')", }, }, "required": ["source_path", "destination_path"], }, ),
- Input schema definition for the move_category tool, specifying required source_path and destination_path parameters.inputSchema={ "type": "object", "properties": { "source_path": { "type": "string", "description": "Current category path (e.g., 'personal/work-notes')", }, "destination_path": { "type": "string", "description": "New parent path (e.g., 'work/archived')", }, }, "required": ["source_path", "destination_path"], },
- Core storage method that performs the actual category move operation, including path normalization, cycle detection, existence checks, and filesystem shutil.move.def move_category( self, source_path: str, destination_path: str, create_destination: bool = True ) -> str: """ Move a category to a new location. Args: source_path: Current category path destination_path: New parent path (or full new path) create_destination: If True, create destination if it doesn't exist Returns: Success message with new path Raises: CategoryNotFoundError: If source doesn't exist StorageError: If move would create circular reference or fails """ source_normalized = normalize_path(source_path) dest_normalized = normalize_path(destination_path) if not source_normalized: raise InvalidPathError("Source path cannot be empty") if not self._category_exists(source_normalized): raise CategoryNotFoundError( f"❌ Error: Category '{source_normalized}' not found" ) # Check for circular reference if would_create_cycle(source_normalized, dest_normalized): raise StorageError( f"❌ Error: Cannot move '{source_normalized}' to '{dest_normalized}' " "(would create circular reference)" ) # Determine final destination source_name = get_category_name(source_normalized) final_dest = join_path(dest_normalized, source_name) # Check if destination parent exists if dest_normalized and not self._category_exists(dest_normalized): if create_destination: self.create_category(dest_normalized, create_parents=True) else: raise CategoryNotFoundError( f"❌ Error: Destination '{dest_normalized}' does not exist\n" f"💡 Tip: Use create_destination=True to create it" ) # Check if final destination already exists if self._category_exists(final_dest): raise CategoryExistsError( f"❌ Error: Category '{final_dest}' already exists" ) # Perform move source_cat_path = self._get_category_path(source_normalized) final_dest_path = self._get_category_path(final_dest) try: shutil.move(str(source_cat_path), str(final_dest_path)) except Exception as e: raise StorageError(f"Failed to move category: {e}") return f"✓ Category moved: '{source_normalized}' → '{final_dest}'"