Batu Lab NotesPractical developer guides

Create a CSV required-column contract for a one-off import

By Batu · English technical notes

Also published in our Blogger archive.

Quick answer

Put the mandatory labels for a one-off CSV import in a small, versioned contract, then obtain the candidate header with the same parser that will read the file. A literal Python list can prove a membership algorithm, but it cannot establish that a CSV header was parsed with the file’s quoting and delimiter rules.

Example

The example keeps id and email in an ordered contract and parses the first record from actual CSV text with csv.reader. The header may be ordered differently, so the membership check succeeds. The output exposes the contract version and a deterministic empty missing list; changing the fixture to omit email makes the asserted normal case fail, which is the point of the preflight.

import csv
import io
import json

contract = {"version": 1, "required": ["id", "email"]}
csv_text = "email,id,note\na@example.test,1,first import\n"
headers = next(csv.reader(io.StringIO(csv_text, newline="")))
missing = [name for name in contract["required"] if name not in headers]

assert headers == ["email", "id", "note"]
assert missing == []
print(json.dumps({"version": contract["version"], "missing": missing}))

Expected stdout:

{"version": 1, "missing": []}

Reading the result

The contract’s list order is useful to reviewers, but required-column presence is intentionally order-independent here. Do not use this result to authorize a positional mapper: a consumer that depends on column order must compare the header sequence too. Likewise, duplicate headers need a separate position-aware check before turning the parsed names into a mapping.

JSON is used only to show a compact report shape. The example does not write a contract file, infer aliases such as contact_email, or validate values in the data records. Those decisions belong to the import’s explicit versioned schema.

Sources

- Python csv.reader documentation

Prepared with AI assistance. The example uses synthetic data; its stated limits apply.