Skip to content
ABCrimson edited this page Mar 2, 2026 · 8 revisions

FAQ

General

What runtimes are supported?

modern-xlsx works in any environment with WASM support:

  • Node.js 25+ (uses node:fs for file operations)
  • Bun (full support)
  • Deno (full support)
  • Browsers (Chrome, Firefox, Safari, Edge — all modern versions)

Why Node.js 25+?

The TypeScript source uses modern features available in Node.js 25+. If you need older Node.js support, you can try building from source with appropriate transpilation, but this is not officially supported.

Does it support .xls files?

No. modern-xlsx only supports the OOXML .xlsx format (Office 2007+). The legacy .xls binary format is not supported.

Is it production-ready?

v0.1.0 is a fully functional initial release with 340+ tests covering reading, writing, styling, and round-trip fidelity. It handles real-world Excel files correctly, but as with any 0.x release, APIs may evolve.

Reading Files

How do I read a file in the browser?

const input = document.querySelector('input[type="file"]');
input.addEventListener('change', async (e) => {
  const file = e.target.files[0];
  const buffer = new Uint8Array(await file.arrayBuffer());
  const wb = await readBuffer(buffer);
  console.log(wb.sheetNames);
});

How do I access shared strings?

The reader resolves shared strings automatically. Cell values are returned as their actual text content — you don't need to look up SST indices manually.

Can I read password-protected files?

Not currently. Password-protected XLSX files use encryption that is not yet supported.

Writing Files

How do I download a file in the browser?

import { writeBlob } from 'modern-xlsx';

const blob = writeBlob(wb);
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = 'output.xlsx';
a.click();
URL.revokeObjectURL(url);

Can I write formulas?

Yes! Set the formula property on a cell:

ws.cell('C1').formula = 'SUM(A1:B1)';

The formula will be preserved in the file. Excel will calculate the result when the file is opened.

Can I set date values?

Use dateToSerial to convert a Date to an Excel serial number, then apply a date number format:

import { dateToSerial } from 'modern-xlsx';

ws.cell('A1').value = dateToSerial(new Date(2024, 0, 15));

const dateStyle = wb.createStyle()
  .numberFormat('yyyy-mm-dd')
  .build(wb.styles);
ws.cell('A1').styleIndex = dateStyle;

Styling

Why do I need wb.styles?

Styles in XLSX are shared across the workbook, not stored per-cell. The build(wb.styles) call adds the style definition to the workbook's shared style table and returns an index. Assigning that index to a cell is very efficient — it's just setting a number.

Can I apply a style to a range?

There's no built-in range styling, but you can loop:

const bold = wb.createStyle().font({ bold: true }).build(wb.styles);
for (let col = 0; col < 10; col++) {
  ws.cell(encodeCellRef(0, col)).styleIndex = bold;
}

Troubleshooting

"WASM not initialized" error

You forgot to call initWasm() before using the library:

import { initWasm } from 'modern-xlsx';
await initWasm(); // must be called first

File opens but looks wrong in Excel

Check that you're using the correct number format for dates. Raw serial numbers display as plain numbers unless you apply a date format style.

Large files are slow to write

Writing performance scales with cell count. For very large files (500K+ cells), consider:

  • Using aoaToSheet for batch cell creation
  • Splitting data across multiple sheets
  • Reducing the number of unique styles (each unique combination creates a new style entry)

Clone this wiki locally