Zovo Spreadsheet Checker MCP
This MCP server validates spreadsheet data by detecting errors such as invalid dates, emails, duplicates, and format inconsistencies. It supports custom rules for required columns, unique values, and numeric ranges, returning a detailed issue list and an Excel copy with highlighted problems.
Endpoint and access
No sign-in to connect and list tools. Individual tools may still need a vendor account, credentials, or permissions; check the documented prerequisites.
https://sheet-validate.zovo.one/mcpWhat its tools do
2 tools, grouped by the hints the server advertises. Hints are self-declared, not verified behavior.
Read-only (2)
Checks and signals
Each line is separate evidence, not a trust score.
- Passed Endpoint answered the live check ·
- Availability 1 of 1 checks passed in 30 days
What you can do with it
- Check a spreadsheet for errors before importing it into a CRM
- Find duplicates in an Excel file and identify impossible dates
- Validate CSV data with specific status and age constraints
Source and maintenance
Protocol and capabilities
- Server
- sheet-validate 1.0.0
- MCP protocol negotiated in check
- 2025-11-25
- Tools
- 2 advertised
- Resources
- 1 advertised
- Resource templates
- 1 advertised
- Prompts
- Not advertised
{
"tools": {
"listChanged": true
},
"resources": {
"listChanged": true
}
}Server-provided instructions
Untrusted server output shown for inspection. It is not Koskamo guidance and is excluded from knowledge search.
Tools
2 advertised
check_spreadsheet — Check spreadsheet for errors
Use this when the user wants to check a spreadsheet for errors or validate data before importing or sending it: "check spreadsheet for errors", "data validation excel", "find duplicates in excel", "check this csv for errors", "find invalid dates", "are there bad emails in this list". Attach a CSV, TSV or .xlsx file or paste the table. With no rules it detects column types from the values and checks impossible, ambiguous and mixed-format dates, invalid emails and email typos, phone digit counts, duplicate IDs and duplicate rows, blank cells in mostly filled columns, text in number columns, numbers stored as text, mixed decimal marks, leading/trailing spaces, IDs that lost leading zeros or became 1.2E+15, formula errors and row totals that do not add up. Optional rules: required_columns, unique_columns, allowed_values, ranges, total_rules. Returns each issue with row, column and cell value, counts per check, a column health score, an Excel copy with problem cells highlighted plus an Issues sheet, and an issues CSV. Does not edit or clean the data, does not verify that mailboxes or phone lines exist, and does not compare two files (use a comparison tool for that).
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"properties": {
"file": {
"type": "object",
"required": [
"download_url",
"file_id"
],
"properties": {
"file_id": {
"type": "string",
"description": "ChatGPT file id, e.g. file_abc123."
},
"file_name": {
"type": "string",
"description": "Original file name if known, e.g. statement.pdf."
},
"mime_type": {
"type": "string",
"description": "Media type if known, e.g. application/pdf."
},
"download_url": {
"type": "string",
"description": "Temporary download link for the file, supplied by ChatGPT."
}
},
"description": "The spreadsheet to check: CSV, TSV or Excel .xlsx, e.g. customers.xlsx."
},
"sheet": {
"anyOf": [
{
"type": "string",
"maxLength": 100
},
{
"type": "number"
}
],
"description": "Sheet name or number in an Excel workbook, e.g. Orders or 2. Default: the first sheet with data."
},
"table": {
"anyOf": [
{
"type": "string",
"maxLength": 400000
},
{
"type": "array",
"items": {
"type": "array",
"items": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "number"
},
{
"type": "boolean"
},
{
"type": "null"
}
]
},
"maxItems": 200
},
"maxItems": 5000
},
{
"type": "array",
"items": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "number"
},
{
"type": "boolean"
},
{
"type": "null"
}
]
}
},
"maxItems": 5000
}
],
"description": "Only when no file is attached: the table pasted as CSV, tab-separated or a Markdown table with its header row, e.g. \"id,date,email\\n1,2026-02-30,ana@example.com\". A list of rows also works."
},
"ranges": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"anyOf": [
{
"type": "string",
"maxLength": 100
},
{
"type": "number"
},
{
"type": "object",
"properties": {
"max": {
"type": [
"number",
"string"
]
},
"min": {
"type": [
"number",
"string"
]
}
}
}
]
}
}
],
"description": "Numeric limits per column, e.g. {\"Age\":\"0-120\",\"Discount\":{\"min\":0,\"max\":50}} or \"Age: 0-120; Qty: >= 1\"."
},
"date_order": {
"type": "string",
"maxLength": 30,
"description": "Day/month order for dates like 03/04/2026: auto (default), MDY (US, month first) or DMY (day first)."
},
"header_row": {
"anyOf": [
{
"type": "number"
},
{
"type": "string",
"maxLength": 10
}
],
"description": "Only if the headings were detected wrongly: the row number of the header, e.g. 3."
},
"skip_checks": {
"anyOf": [
{
"type": "string",
"maxLength": 4000
},
{
"type": "array",
"items": {
"type": "string",
"maxLength": 200
},
"maxItems": 200
}
],
"description": "Checks to turn off, e.g. [\"extra_spaces\"]. Options: impossible_date, mixed_date_order, ambiguous_date, mixed_date_format, implausible_date, not_a_date, invalid_email, email_typo, invalid_phone, duplicate_id, duplicate_row, blank_required, not_a_number, number_as_text, mixed_decimal, extra_spaces, lost_leading_zeros, scientific_notation, total_mismatch, formula_error, inconsistent_spelling, extra_cell, impossible_time, not_allowed, out_of_range."
},
"total_rules": {
"anyOf": [
{
"type": "string",
"maxLength": 4000
},
{
"type": "array",
"items": {
"type": "string",
"maxLength": 200
},
"maxItems": 200
}
],
"description": "Totals that must add up, e.g. \"Total = Q1 + Q2 + Q3 + Q4\" or \"Amount = Qty * Price\". Default: total columns are detected and checked automatically."
},
"allowed_values": {
"anyOf": [
{
"type": "string",
"maxLength": 4000
},
{
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "array",
"items": {
"anyOf": [
{
"type": "string",
"maxLength": 200
},
{
"type": "number"
}
]
},
"maxItems": 500
}
]
}
}
],
"description": "Allowed values per column, e.g. {\"Status\":[\"Open\",\"Closed\"]} or \"Status: Open, Closed; Region: North, South\"."
},
"unique_columns": {
"anyOf": [
{
"type": "string",
"maxLength": 4000
},
{
"type": "array",
"items": {
"type": "string",
"maxLength": 200
},
"maxItems": 200
}
],
"description": "Columns whose values must not repeat, e.g. \"Order ID\". Default: the ID column is detected from its header and values."
},
"required_columns": {
"anyOf": [
{
"type": "string",
"maxLength": 4000
},
{
"type": "array",
"items": {
"type": "string",
"maxLength": 200
},
"maxItems": 200
}
],
"description": "Columns that must never be blank, e.g. [\"Email\",\"Order ID\"] or \"Email, Order ID\". Default: columns that are almost fully filled are treated as required (blanks reported as warnings)."
}
}
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"kind",
"file",
"summary",
"checks",
"columns",
"issues_preview",
"totals_checked",
"rules_applied",
"notes",
"downloads",
"copy"
],
"properties": {
"copy": {
"type": "string"
},
"file": {
"type": "object",
"required": [
"name",
"data_rows",
"columns",
"header_row"
],
"properties": {
"name": {
"type": "string"
},
"sheet": {
"type": "string"
},
"columns": {
"type": "number"
},
"data_rows": {
"type": "number"
},
"header_row": {
"type": [
"number",
"null"
]
},
"other_sheets": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
},
"kind": {
"type": "string"
},
"notes": {
"type": "array",
"items": {
"type": "string"
}
},
"checks": {
"type": "array",
"items": {
"type": "object",
"required": [
"check",
"label",
"severity",
"count"
],
"properties": {
"check": {
"type": "string"
},
"count": {
"type": "number"
},
"label": {
"type": "string"
},
"severity": {
"type": "string"
}
},
"additionalProperties": false
}
},
"columns": {
"type": "array",
"items": {
"type": "object",
"required": [
"letter",
"name",
"type",
"health",
"issues",
"blank",
"key",
"required"
],
"properties": {
"key": {
"type": "boolean"
},
"name": {
"type": "string"
},
"type": {
"type": "string"
},
"blank": {
"type": "number"
},
"health": {
"type": "number"
},
"issues": {
"type": "number"
},
"letter": {
"type": "string"
},
"required": {
"type": "boolean"
}
},
"additionalProperties": false
}
},
"summary": {
"type": "object",
"required": [
"issues",
"errors",
"warnings",
"rows_with_issues",
"clean_rows",
"health_score"
],
"properties": {
"errors": {
"type": "number"
},
"issues": {
"type": "number"
},
"warnings": {
"type": "number"
},
"clean_rows": {
"type": "number"
},
"health_score": {
"type": "number"
},
"rows_with_issues": {
"type": "number"
}
},
"additionalProperties": false
},
"downloads": {
"type": "object",
"required": [
"xlsx",
"csv"
],
"properties": {
"csv": {
"type": "string"
},
"xlsx": {
"type": "string"
}
},
"additionalProperties": false
},
"rules_applied": {
"type": "array",
"items": {
"type": "string"
}
},
"issues_preview": {
"type": "array",
"items": {
"type": "object",
"required": [
"row",
"column",
"cell",
"value",
"check",
"severity",
"problem"
],
"properties": {
"row": {
"type": "number"
},
"cell": {
"type": "string"
},
"check": {
"type": "string"
},
"value": {
"type": "string"
},
"column": {
"type": "string"
},
"problem": {
"type": "string"
},
"severity": {
"type": "string"
}
},
"additionalProperties": false
}
},
"totals_checked": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
}{
"title": "Check spreadsheet for errors",
"readOnlyHint": true,
"openWorldHint": false,
"destructiveHint": false
}list_spreadsheet_columns — List spreadsheet columns
Use this when the user wants to see what is in a spreadsheet before validating it, or asks which columns, types or values it has: "what columns are in this file", "profile this csv", "which column is the ID", "suggest validation rules". Attach a CSV, TSV or .xlsx file or paste the table. Returns each column's letter, name, detected type (date, email, phone, ID, ZIP, number, money, percent, text), filled and blank counts, unique values, examples, min/max for numbers, short value lists, and suggested rules to pass to check_spreadsheet. Does not report errors (use check_spreadsheet) and does not change the file.
{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"properties": {
"file": {
"type": "object",
"required": [
"download_url",
"file_id"
],
"properties": {
"file_id": {
"type": "string",
"description": "ChatGPT file id, e.g. file_abc123."
},
"file_name": {
"type": "string",
"description": "Original file name if known, e.g. statement.pdf."
},
"mime_type": {
"type": "string",
"description": "Media type if known, e.g. application/pdf."
},
"download_url": {
"type": "string",
"description": "Temporary download link for the file, supplied by ChatGPT."
}
},
"description": "The spreadsheet to check: CSV, TSV or Excel .xlsx, e.g. customers.xlsx."
},
"sheet": {
"anyOf": [
{
"type": "string",
"maxLength": 100
},
{
"type": "number"
}
],
"description": "Sheet name or number in an Excel workbook, e.g. Orders or 2. Default: the first sheet with data."
},
"table": {
"anyOf": [
{
"type": "string",
"maxLength": 400000
},
{
"type": "array",
"items": {
"type": "array",
"items": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "number"
},
{
"type": "boolean"
},
{
"type": "null"
}
]
},
"maxItems": 200
},
"maxItems": 5000
},
{
"type": "array",
"items": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"anyOf": [
{
"type": "string",
"maxLength": 2000
},
{
"type": "number"
},
{
"type": "boolean"
},
{
"type": "null"
}
]
}
},
"maxItems": 5000
}
],
"description": "Only when no file is attached: the table pasted as CSV, tab-separated or a Markdown table with its header row, e.g. \"id,date,email\\n1,2026-02-30,ana@example.com\". A list of rows also works."
},
"header_row": {
"anyOf": [
{
"type": "number"
},
{
"type": "string",
"maxLength": 10
}
],
"description": "Only if the headings were detected wrongly: the row number of the header, e.g. 3."
}
}
}{
"type": "object",
"$schema": "http://json-schema.org/draft-07/schema#",
"required": [
"kind",
"file",
"columns",
"suggested_rules",
"notes"
],
"properties": {
"file": {
"type": "object",
"required": [
"name",
"data_rows",
"columns",
"header_row"
],
"properties": {
"name": {
"type": "string"
},
"sheet": {
"type": "string"
},
"columns": {
"type": "number"
},
"data_rows": {
"type": "number"
},
"header_row": {
"type": [
"number",
"null"
]
},
"other_sheets": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
},
"kind": {
"type": "string"
},
"notes": {
"type": "array",
"items": {
"type": "string"
}
},
"columns": {
"type": "array",
"items": {
"type": "object",
"required": [
"letter",
"name",
"type",
"filled",
"blank",
"unique",
"examples",
"key"
],
"properties": {
"key": {
"type": "boolean"
},
"max": {
"type": "number"
},
"min": {
"type": "number"
},
"name": {
"type": "string"
},
"type": {
"type": "string"
},
"blank": {
"type": "number"
},
"filled": {
"type": "number"
},
"letter": {
"type": "string"
},
"unique": {
"type": "number"
},
"values": {
"type": "array",
"items": {
"type": "string"
}
},
"examples": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
}
},
"suggested_rules": {
"type": "object",
"required": [
"required_columns",
"unique_columns",
"allowed_values",
"ranges"
],
"properties": {
"ranges": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "string"
}
},
"allowed_values": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "array",
"items": {
"type": "string"
}
}
},
"unique_columns": {
"type": "array",
"items": {
"type": "string"
}
},
"required_columns": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
}
},
"additionalProperties": false
}{
"title": "List spreadsheet columns",
"readOnlyHint": true,
"openWorldHint": false,
"destructiveHint": false
}Prompts
Not advertised
Resources
1 advertised
sheet-validate-widget — Zovo Spreadsheet Checker view
Interactive view for Zovo Spreadsheet Checker.
ui://widget/sheet-validate-v1-1.0.0-5449021f2b2bb33f36a4aeff7cc4f8e4dec2a442758df0576a22a0245c9ea8ec.htmlsheet-validate-widget-legacy — Zovo Spreadsheet Checker view (previous versions)
ui://widget/sheet-validate-{version}.html30-day availability
Aggregated from read-only remote checks; this is not a tool-execution or security guarantee.
- Successful checks
- 1 of 1 (100%)
- Average latency
- 366 ms
- 95th percentile latency
- 366 ms
Maintenance history
Public check and source-refresh events. Editorial and ownership records remain private.
- · probe · passed · 366 ms · metadata changed · 2 tool(s), 1 resource(s), 1 resource template(s)
Connect from your client
Each snippet registers the same endpoint; pick the client you use.
Claude Code
claude mcp add --transport http zovo-spreadsheet-checker-mcp https://sheet-validate.zovo.one/mcpCodex
codex mcp add zovo-spreadsheet-checker-mcp --url https://sheet-validate.zovo.one/mcpCursor
{
"mcpServers": {
"zovo-spreadsheet-checker-mcp": {
"url": "https://sheet-validate.zovo.one/mcp"
}
}
}Cline
{
"mcpServers": {
"zovo-spreadsheet-checker-mcp": {
"type": "streamableHttp",
"url": "https://sheet-validate.zovo.one/mcp",
"disabled": false
}
}
}VS Code
{
"servers": {
"zovo-spreadsheet-checker-mcp": {
"type": "http",
"url": "https://sheet-validate.zovo.one/mcp"
}
}
}Gemini CLI
gemini mcp add --transport http zovo-spreadsheet-checker-mcp https://sheet-validate.zovo.one/mcpClaude Desktop
https://sheet-validate.zovo.one/mcpWindsurf
{
"mcpServers": {
"zovo-spreadsheet-checker-mcp": {
"serverUrl": "https://sheet-validate.zovo.one/mcp"
}
}
}Let your agent find its tools
Find servers like Zovo Spreadsheet Checker MCP from your agent. Add Koskamo once to search the index for endpoints, access requirements, and client setup. Public discovery needs no key.