/excelCompare Excel Spreadsheets
Compute a diff between two spreadsheets. Supports both multipart/form-data file uploads and JSON with base64-encoded data URLs. Accepts .xlsx, .xls, and .csv files. Columns are matched using headers and content, allowing renamed columns to remain paired.
Parameters
Diffchecker-VersionheaderstringAPI version to serve the request with. Defaults to the newest version, currently 1, when omitted. An unsupported version is rejected with 400 UNSUPPORTED_API_VERSION. See Versioning and Deprecation in the getting started guide.
Values: 1
Default: 1
emailquerystringYour email address. Required if not using an API key.
input_typequerystringrequiredSpecifies the request content-type.
- form: multipart/form-data
- json: application/json
Values: json, form
diff_levelquerystringSpecifies whether you want to diff values by their formulas or standard values. Default is standard.
Values: standard, formulas
Default: standard
ignore_whitespacequerystringWhether to ignore leading and trailing whitespace in the diff. Default is false.
Values: true, false
Default: false
ignore_case_changesquerystringWhether to ignore case changes in the diff. Default is false.
Values: true, false
Default: false
hide_unchanged_rowsquerystringWhether to hide unchanged rows in the diff. Default is false.
Values: true, false
Default: false
hide_unchanged_columnsquerystringWhether to hide unchanged columns in the diff. Default is false.
Values: true, false
Default: false
Request Bodyrequired
left_spreadsheetstring (binary)requiredLeft spreadsheet file. File extension must be .xlsx, .xls, or .csv.
right_spreadsheetstring (binary)requiredRight spreadsheet file. File extension must be .xlsx, .xls, or .csv.
left_sheet_namestringThe sheet name from the left spreadsheet to diff. If not provided, the first sheet will be used.
right_sheet_namestringThe sheet name from the right spreadsheet to diff. If not provided, the first sheet will be used.
left_header_rowintegerThe row number to use as the header from the left spreadsheet. If not provided, the first row will be used.
right_header_rowintegerThe row number to use as the header from the right spreadsheet. If not provided, the first row will be used.
Responses
Every response includes the X-Credits-Used header. In JSON responses, the same value is also available in the creditsUsed field.
Diff computed successfully.
application/json
creditsUsedintegerrequiredCredits charged for the diff request.
tableobject[][][]requiredThe diff results for each cell. Cells are organized by rows, with each row containing cells in column order (left to right). Each cell is represented by an array of one or two objects. If the cell value changed, there will be two objects (one removed, one inserted). Each object contains the type of change and the value. Cells equal under ignore options retain the original right-side value. A cell where a row present on one side meets a column present only on the other exists on neither side; it has an empty value and its row's type.
rowsobject[]requiredRow-level diff metadata. Row numbers are one-based relative to the selected header (row 1); null means absent. Filtering preserves source coordinates.
typestringEnum: equal, removed, inserted, modified, moved
originalinteger | nullnewinteger | nullcolumnsobject[]requiredColumn-level diff metadata. Column numbers are one-based source positions; null means absent. Filtering preserves source coordinates.
typestringEnum: equal, removed, inserted, modified, moved
originalinteger | nullnewinteger | nullstatsobjectrequiredChange counts cover the full comparison; row and column counts describe the visible output.
movedintegerNumber of moved rows plus moved columns.
insertedintegerInserted or modified data cells plus inserted or renamed column headers.
removedintegerDeleted or modified data cells plus deleted or renamed column headers.
rowsintegerTotal rows in the output, including the header when present.
columnsintegerTotal columns in the output.
Example
{
"creditsUsed": 1,
"table": [
[
[
{
"value": "Bird",
"type": "equal"
}
],
[
{
"value": "Population",
"type": "equal"
}
]
],
[
[
{
"value": "Kagu",
"type": "equal"
}
],
[
{
"value": "1,000",
"type": "equal"
}
]
],
[
[
{
"value": "Dodo",
"type": "removed"
}
],
[
{
"value": "0",
"type": "removed"
}
]
],
[
[
{
"value": "Kiwi",
"type": "equal"
}
],
[
{
"value": "120,000",
"type": "removed"
},
{
"value": "70,000",
"type": "inserted"
}
]
]
],
"rows": [
{
"type": "equal",
"original": 1,
"new": 1
},
{
"type": "equal",
"original": 2,
"new": 2
},
{
"type": "removed",
"original": 3,
"new": null
},
{
"type": "modified",
"original": 4,
"new": 3
}
],
"columns": [
{
"type": "equal",
"original": 1,
"new": 1
},
{
"type": "modified",
"original": 2,
"new": 2
}
],
"stats": {
"moved": 0,
"inserted": 1,
"removed": 2,
"rows": 4,
"columns": 2
}
}Example Request
curl -X POST \
"https://api.diffchecker.com/public/excel?email=your@email.com&input_type=json&diff_level=standard&ignore_whitespace=false&ignore_case_changes=false&hide_unchanged_rows=false&hide_unchanged_columns=false" \
-H "Content-Type: application/json" \
-d '{
"left_spreadsheet": "{left_spreadsheet}",
"right_spreadsheet": "{right_spreadsheet}",
"left_sheet_name": "{left_sheet_name}",
"right_sheet_name": "{right_sheet_name}",
"left_header_row": "{left_header_row}",
"right_header_row": "{right_header_row}"
}'Try It
Understanding the Output
The response contains four sections: table, rows, columns, and stats. Below is a walkthrough using an example comparing bird populations.
The Kagu population remained the same, the Dodo was removed because it is extinct, and the Kiwi population declined.
| 1 | 1 | Bird | Population |
|---|---|---|---|
| 2 | 2 | Kagu | 1,000 |
| 3 | Dodo | 0 | |
| 4 | 3 | Kiwi | 120,00070,000 |
Rows
{
"rows": [
{
"type": "equal",
"original": 1,
"new": 1
},
{
"type": "equal",
"original": 2,
"new": 2
},
{
"type": "removed",
"original": 3,
"new": null
},
{
"type": "modified",
"original": 4,
"new": 3
}
]
}Each entry describes a row's change between the original and new spreadsheet.
originalRow number in the left (original) spreadsheet.newRow number in the right (new) spreadsheet.typeThe kind of change: equal, removed, inserted, or modified.In our example, the first two rows are unchanged. Row 3 (Dodo) was removed, and row 4 (Kiwi) was modified — shifting up from position 4 to 3.
Columns
{
"columns": [
{
"type": "equal",
"original": 1,
"new": 1
},
{
"type": "modified",
"original": 2,
"new": 2
}
]
}Same structure as rows, but describes column-level changes.
originalColumn number in the left spreadsheet.newColumn number in the right spreadsheet.typeThe kind of change: equal, removed, inserted, or modified.Column 1 (“Bird”) is unchanged. Column 2 (“Population”) is modified because the Kiwi's population value changed.
Table
{
"table": [
[
[
{
"value": "Bird",
"type": "equal"
}
],
[
{
"value": "Population",
"type": "equal"
}
]
],
[
[
{
"value": "Kagu",
"type": "equal"
}
],
[
{
"value": "1,000",
"type": "equal"
}
]
],
[
[
{
"value": "Dodo",
"type": "removed"
}
],
[
{
"value": "0",
"type": "removed"
}
]
],
[
[
{
"value": "Kiwi",
"type": "equal"
}
],
[
{
"value": "120,000",
"type": "removed"
},
{
"value": "70,000",
"type": "inserted"
}
]
]
]
}Cell-level diff results organized by rows, with each row containing cells in column order (left to right).
Each cell is an array of one or two objects. Two objects appear when a value changed — one for the removed value and one for the inserted value.
typeThe change for this value: equal, removed, or inserted.valueThe cell content.Every cell is equal except the Dodo's row (removed) and the Kiwi's population cell, which has both a removed value (120,000) and an inserted value (70,000).
Stats
{
"stats": {
"moved": 0,
"inserted": 1,
"removed": 2,
"rows": 4,
"columns": 2
}
}Summary statistics for the entire diff.
movedCells that moved position.insertedCells that were added.removedCells that were deleted.rowsTotal rows in the output.columnsTotal columns in the output.One insertion (Kiwi's new population) and two removals (Dodo's row and Kiwi's old population).