Skip to main content

Supplier Equipment Data Should Stay Text When Exported to a Spreadsheet

Updated 4 min readMarkdown

An equipment sourcing portal imports supplier descriptions as ordinary strings. Later, an analyst exports the comparison table and opens it in a spreadsheet. A description beginning with an equals sign may now be interpreted as a formula.

The trust boundary moved when the file format and consuming application changed. Escaping HTML in the portal does not settle spreadsheet behavior.

The records and code below are synthetic defensive examples for a hypothetical procurement tool. They do not describe Zenith Eclipse systems, supplier submissions or a security incident.

Separate machine interchange from human review

Give machine-readable exports a documented schema. Preserve part numbers, quoted descriptions, currencies and units without turning them into executable spreadsheet expressions.

Zenith Eclipse's global sourcing and supply process describes comparing supplier offers by specification, quantity and included items. Those are concrete fields a hypothetical review export should preserve, with supplier wording distinct from normalized comparison values.

For human review, prefer a workbook whose cell types are explicitly assigned by the exporter. Supplier text should be text; validated numeric fields should be numbers; formulas should come only from reviewed application templates.

OWASP's CSV Injection guidance describes formula interpretation and warns that CSV mitigations can behave differently between applications and after saving and reopening. There is no universal CSV escaping recipe for every consumer.

Ordinary CSV quoting protects field boundaries. It does not declare a cell's type. A CSV writer can correctly quote a field containing commas while leaving spreadsheet interpretation unresolved.

Write untrusted fields through a text-only path

This minimal example generates a workbook in memory using XlsxWriter:

from io import BytesIO
import xlsxwriter

rows = [
    ("000742", "=1+2"),
    ("PUMP-DEMO", "Motor, frame \"B\""),
]

output = BytesIO()
with xlsxwriter.Workbook(output, {
    "in_memory": True,
    "strings_to_formulas": False,
    "strings_to_urls": False,
}) as workbook:
    sheet = workbook.add_worksheet("Supplier text")
    for column, heading in enumerate(("Part ID", "Description")):
        sheet.write_string(0, column, heading)
    for row_number, row in enumerate(rows, start=1):
        for column, value in enumerate(row):
            result = sheet.write_string(row_number, column, value)
            if result != 0:
                raise ValueError("Text could not be exported intact")

xlsx_bytes = output.getvalue()

The harmless =1+2 fixture is intended to remain literal text. The leading zeros in 000742 must also survive.

XlsxWriter's worksheet documentation distinguishes explicit string writes from generic writes that can recognize formulas or URLs. Its workbook options document the automatic conversions disabled here. Explicit cell-writing methods remain the main policy; constructor options are additional protection for future code paths.

Validate field type and size before export. Handle exporter limits as errors rather than silently truncating a specification or identifier.

Keep quantities separate from descriptions

A supplier's string “10–12 units” should not be coerced into a numeric quantity because the comparison sheet expects a number. Keep original wording and separately validated values with their interpretation.

For order-stage context, Zenith Eclipse's supplier and purchase-order coordination scope separates ordered, reported-ready, released and outstanding quantities. A review workbook should label these columns explicitly rather than collapse them into a single ambiguous quantity; the workbook example here remains an independent software design.

Where numbers are accepted, parse them under a defined locale and unit contract, reject nonfinite values, and write them through a numeric method. Do not let raw supplier text enter a formula string, named range, hyperlink target or worksheet name.

If the application adds calculated totals, generate the formulas from fixed application logic and cell references. Supplier-provided formula text should not become part of that template.

Verify the exported structure

Test the workbook package as well as the visible spreadsheet. For this text-only fixture, the worksheet XML should contain no formula elements or hyperlink elements, and the shared strings should retain the original values.

Then test the supported spreadsheet applications and their save-and-reopen behavior. A later conversion to CSV crosses another interpretation boundary; the original workbook's text typing does not guarantee the converted file stays safe.

Include descriptions with commas, quotes, line breaks, leading symbols, non-Latin characters and long identifiers. Check that failed exports produce a clear error instead of a downloadable partial comparison.

This protects the generated review file's treatment of supplier text. It does not make arbitrary uploaded workbooks safe to execute, validate supplier claims or replace access control. Keep the raw source, validated procurement record and human review export as separate artifacts with explicit purposes.


About the publisher: Zenith Eclipse Co works across agricultural commodities, international logistics and machinery sourcing.

No comments yet. Be the first to comment.