Skip to main content
Glama
andr3medeiros

PDF Manipulation MCP Server

pdf_crop_page

Crop a specific page in a PDF by defining coordinates to remove unwanted margins or content, enabling precise document editing.

Instructions

Crop a page in a PDF.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
pdf_pathYes
page_numberYes
x0Yes
y0Yes
x1Yes
y1Yes
coordinate_modeNobbox

Implementation Reference

  • The main handler function for the 'pdf_crop_page' tool. Decorated with @mcp.tool() which registers it with the FastMCP server. Implements PDF page cropping using PyMuPDF by setting the cropbox on the specified page, with support for 'bbox' (bottom-left origin) and 'rect' (top-left origin) coordinate modes. Validates inputs and generates a timestamped output file.
    @mcp.tool()
    async def pdf_crop_page(
        pdf_path: str,
        page_number: int,
        x0: float,
        y0: float,
        x1: float,
        y1: float,
        coordinate_mode: str = "bbox"
    ) -> str:
        """Crop a page in a PDF."""
        if not os.path.exists(pdf_path):
            return f"Error: PDF file not found: {pdf_path}"
        
        if not validate_pdf_file(pdf_path):
            return f"Error: Invalid PDF file: {pdf_path}"
        
        if coordinate_mode not in ["bbox", "rect"]:
            return f"Error: Invalid coordinate_mode. Must be 'bbox' or 'rect'."
        
        try:
            # Open PDF document
            doc = fitz.open(pdf_path)
            
            # Validate page number
            if not validate_page_number(doc, page_number):
                doc.close()
                return f"Error: Invalid page number {page_number}. Document has {len(doc)} pages."
            
            # Get the page
            page = doc[page_number]
            
            # Convert coordinates based on mode
            if coordinate_mode == "rect":
                # Convert from x, y, width, height to x0, y0, x1, y1
                # Note: PDF coordinates have origin at bottom-left, so we need to adjust
                page_rect = page.rect
                actual_x0 = x0
                actual_y0 = page_rect.height - (y0 + y1)  # Convert from top-left to bottom-left origin
                actual_x1 = x0 + x1
                actual_y1 = page_rect.height - y0
            else:  # bbox mode
                actual_x0, actual_y0, actual_x1, actual_y1 = x0, y0, x1, y1
            
            # Validate crop coordinates
            page_rect = page.rect
            if (actual_x0 < 0 or actual_y0 < 0 or 
                actual_x1 > page_rect.width or actual_y1 > page_rect.height or
                actual_x0 >= actual_x1 or actual_y0 >= actual_y1):
                doc.close()
                return f"Error: Invalid crop coordinates. Page dimensions: {page_rect.width:.1f} x {page_rect.height:.1f}"
            
            # Set the crop box
            crop_rect = fitz.Rect(actual_x0, actual_y0, actual_x1, actual_y1)
            page.set_cropbox(crop_rect)
            
            # Generate output filename
            output_path = generate_output_filename(pdf_path)
            
            # Save the modified PDF
            doc.save(output_path)
            doc.close()
            
            return f"Successfully cropped page {page_number + 1}. Output saved to: {output_path}"
            
        except Exception as e:
            return f"Error cropping page: {str(e)}"

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/andr3medeiros/pdf-manipulation-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server