read_excel
Extract structured data from Excel files by specifying file paths, sheet names, and row ranges for data analysis and processing.
Instructions
Read an Excel file and return its contents as structured data
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| filePath | Yes | Path to the Excel file to read | |
| sheetName | No | Name of the sheet to read (optional) | |
| startRow | No | Starting row index (optional) | |
| maxRows | No | Maximum number of rows to read (optional) |
Implementation Reference
- src/index.ts:93-167 (handler)Core handler function that reads and parses the Excel file, computes chunks based on estimated size, and returns structured data including sheets, rows, and columns.private readExcelFile(args: ReadExcelArgs): ExcelData { const { filePath, sheetName, startRow = 0, maxRows } = args; if (!existsSync(filePath)) { throw new McpError( ErrorCode.InvalidRequest, `File not found: ${filePath}` ); } try { // Read file as buffer first const data = readFileSync(filePath); const workbook = XLSX.read(data, { type: 'buffer', cellDates: true, cellNF: false, cellText: false, dateNF: 'yyyy-mm-dd' }); const fileName = filePath.split(/[\\/]/).pop() || ''; const selectedSheetName = sheetName || workbook.SheetNames[0]; const worksheet = workbook.Sheets[selectedSheetName]; const allData = XLSX.utils.sheet_to_json(worksheet, { raw: true, dateNF: 'yyyy-mm-dd' }) as Record<string, any>[]; const totalRows = allData.length; const columns = totalRows > 0 ? Object.keys(allData[0] as object) : []; const totalColumns = columns.length; // Calculate chunk size based on data size let effectiveMaxRows = maxRows; if (!effectiveMaxRows) { const initialChunk = allData.slice(0, 100); // Sample first 100 rows if (initialChunk.length > 0) { effectiveMaxRows = calculateChunkSize(initialChunk, MAX_RESPONSE_SIZE); } else { effectiveMaxRows = 100; // Default if no data } } const endRow = Math.min(startRow + effectiveMaxRows, totalRows); const chunkData = allData.slice(startRow, endRow); const hasMore = endRow < totalRows; const nextChunk = hasMore ? { rowStart: endRow, columns } : undefined; return { fileName, totalSheets: workbook.SheetNames.length, currentSheet: { name: selectedSheetName, totalRows, totalColumns, chunk: { rowStart: startRow, rowEnd: endRow, columns, data: chunkData }, hasMore, nextChunk } }; } catch (error) { throw new McpError( ErrorCode.InternalError, `Error reading Excel file: ${error instanceof Error ? error.message : String(error)}` ); } }
- src/index.ts:38-43 (schema)TypeScript interface defining the input arguments for the read_excel tool.interface ReadExcelArgs { filePath: string; sheetName?: string; startRow?: number; maxRows?: number; }
- src/index.ts:170-199 (registration)Registration of the read_excel tool in the ListToolsRequestSchema handler, including name, description, and input schema.this.server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: [ { name: 'read_excel', description: 'Read an Excel file and return its contents as structured data', inputSchema: { type: 'object', properties: { filePath: { type: 'string', description: 'Path to the Excel file to read', }, sheetName: { type: 'string', description: 'Name of the sheet to read (optional)', }, startRow: { type: 'number', description: 'Starting row index (optional)', }, maxRows: { type: 'number', description: 'Maximum number of rows to read (optional)', }, }, required: ['filePath'], }, }, ], }));
- src/index.ts:201-235 (registration)Dispatch handler for CallToolRequestSchema that validates arguments, calls the readExcelFile handler, and returns the result for the read_excel tool.this.server.setRequestHandler(CallToolRequestSchema, async (request) => { if (request.params.name !== 'read_excel') { throw new McpError( ErrorCode.MethodNotFound, `Unknown tool: ${request.params.name}` ); } if (!isValidReadExcelArgs(request.params.arguments)) { throw new McpError( ErrorCode.InvalidParams, 'Invalid read_excel arguments' ); } try { const data = this.readExcelFile(request.params.arguments); return { content: [ { type: 'text', text: JSON.stringify(data, null, 2), }, ], }; } catch (error) { if (error instanceof McpError) { throw error; } throw new McpError( ErrorCode.InternalError, `Unexpected error: ${error instanceof Error ? error.message : String(error)}` ); } });
- src/index.ts:47-53 (helper)Type guard and validator function for ReadExcelArgs input.const isValidReadExcelArgs = (args: any): args is ReadExcelArgs => typeof args === 'object' && args !== null && typeof args.filePath === 'string' && (args.sheetName === undefined || typeof args.sheetName === 'string') && (args.startRow === undefined || typeof args.startRow === 'number') && (args.maxRows === undefined || typeof args.maxRows === 'number');