diff --git a/.spelling b/.spelling
index cde96ad..3d415ba 100644
--- a/.spelling
+++ b/.spelling
@@ -130,6 +130,7 @@ DOM
DPI
DataGrid
Deno
+Dojo
Downloadify
Drash
Duktape
diff --git a/docz/docs/02-getting-started/01-installation/06-amd.md b/docz/docs/02-getting-started/01-installation/06-amd.md
index ddb8bf7..51cf7ac 100644
--- a/docz/docs/02-getting-started/01-installation/06-amd.md
+++ b/docz/docs/02-getting-started/01-installation/06-amd.md
@@ -93,3 +93,77 @@ require(['xlsx'], function(XLSX) {
// ... use XLSX here
});
```
+
+## Dojo Toolkit
+
+Dojo has changed module loading strategies over the years. These examples were
+tested with Dojo `1.10.4` and are not guaranteed to work with other versions.
+
+Live demos are included in ["Dojo Toolkit"](../../demos/legacy#dojo-toolkit)
+
+:::caution
+
+The standalone scripts add `window.XLSX`, so it is recommended to use `_XLSX`
+in the function arguments and access the library with `XLSX` in the callback:
+
+```js
+require(["xlsx"], function(
+ // highlight-next-line
+ _XLSX // !! NOTE: this is not XLSX! A different variable name must be used
+) {
+ // highlight-next-line
+ console.log(XLSX.version); // use XLSX in the callback
+})
+```
+
+:::
+
+#### Synchronous Loading
+
+When `async` is disabled, the scripts can be referenced directly in `require`
+calls.
+
+```html
+
+
+```
+
+#### Asynchronous Loading
+
+When `async` is enabled, Dojo will only understand the name `xlsx`. The config
+object can map package names to scripts:
+
+```html
+
+
+
+```
\ No newline at end of file
diff --git a/docz/docs/03-demos/05-database.md b/docz/docs/03-demos/05-database.md
index 8562193..9f23960 100644
--- a/docz/docs/03-demos/05-database.md
+++ b/docz/docs/03-demos/05-database.md
@@ -404,8 +404,8 @@ result.forEach(function(row) {
var query = db.prepareQuery("SELECT * FROM '" + row[0] + "' LIMIT 100000")
var aoa = query.all();
if(aoa.length > 0) {
- /* Create array of arrays */
- var data = [query.columns().map(x => x.name)].concat(aoa);
+ /* Create array of arrays */
+ var data = [query.columns().map(x => x.name)].concat(aoa);
/* Create Worksheet from the aoa */
var ws = XLSX.utils.aoa_to_sheet(data, {dense: true});
/* Add to Workbook */
diff --git a/docz/docs/03-demos/19-bundler.md b/docz/docs/03-demos/19-bundler.md
index 94bef84..e036a91 100644
--- a/docz/docs/03-demos/19-bundler.md
+++ b/docz/docs/03-demos/19-bundler.md
@@ -168,6 +168,13 @@ bun bun.js
+## Dojo
+
+Integration details are included [in the "AMD" installation](../getting-started/installation/amd#dojo-toolkit)
+
+Complete Examples are included [in the "Dojo" demo](./legacy#dojo-toolkit)
+
+
## esbuild
The `xlsx.mjs` source file are written in a subset of ES6 that `esbuild`
diff --git a/docz/docs/03-demos/26-excel.md b/docz/docs/03-demos/26-excelapi.md
similarity index 94%
rename from docz/docs/03-demos/26-excel.md
rename to docz/docs/03-demos/26-excelapi.md
index 1ea6ef5..081b22d 100644
--- a/docz/docs/03-demos/26-excel.md
+++ b/docz/docs/03-demos/26-excelapi.md
@@ -2,6 +2,13 @@
title: Excel JavaScript API
---
+:::info
+
+This demo focuses on the JavaScript API included with Excel. For reading and
+writing Excel files, [other demos](/docs/demos) cover a wide variety of use cases
+
+:::
+
Office 2016 introduced a JavaScript API for interacting with the application.
It offers solutions for custom functions as well as task panes.
diff --git a/docz/docs/03-demos/33-localfile.md b/docz/docs/03-demos/33-localfile.md
index 5f22e36..f6cc3a1 100644
--- a/docz/docs/03-demos/33-localfile.md
+++ b/docz/docs/03-demos/33-localfile.md
@@ -314,6 +314,18 @@ var wb = XLSX.readFile("sheetjs.numbers");
XLSX.writeFile(wb, "sheetjs.xlsx");
```
+### ExtendScript
+
+In Photoshop and other Adobe apps, `readFile` and `writeFile` use the `File`
+object under the hood:
+
+```js
+#include "xlsx.extendscript.js"
+
+var wb = XLSX.readFile("sheetjs.xlsx");
+XLSX.writeFile(wb, "sheetjs.csv");
+```
+
### Deno
`Deno.readFileSync` and `Deno.writeFileSync` are supported by `readFile` and
diff --git a/docz/docs/03-demos/44-legacy.md b/docz/docs/03-demos/44-legacy.md
index 9ace8ca..017aeee 100644
--- a/docz/docs/03-demos/44-legacy.md
+++ b/docz/docs/03-demos/44-legacy.md
@@ -301,6 +301,94 @@ XLSX.writeFile(wb, "sheetjs.xlsx");
+### Dojo Toolkit
+
+_Live Demos_
+
+- [Download and display data](pathname:///dojo/read.html)
+- [Fetch JSON and generate a workbook](pathname:///dojo/write.html)
+
+
+The ["AMD" instructions](../getting-started/installation/amd#dojo-toolkit)
+includes details for use with `require`.
+
+Integration in the demos (click to show)
+
+The demos use the async loading strategy with the SheetJS CDN:
+
+```html
+
+
+
+```
+
+
+
+The ["Dojo" section in "Bundlers"](./bundler#dojo) includes a complete example
+mirroring the [official example](../getting-started/example)
+
+Details (click to show)
+
+_Reading Data_
+
+When fetching spreadsheets with XHR, `handleAs: "arraybuffer"` yields an
+`ArrayBuffer` which can be passed to `XLSX.read`:
+
+```html
+
+
+```
+
+:::note
+
+The `X-Requested-With` header setting resolves some issues related to CORS.
+
+:::
+
+_Writing Data_
+
+`XLSX.writeFile` works as expected:
+
+```html
+
+```
+
+
+
+
### KnockoutJS
[KnockoutJS](https://en.wikipedia.org/wiki/Knockout_(web_framework)) was a
diff --git a/docz/docs/03-demos/45-git.md b/docz/docs/03-demos/45-git.md
index 2f20aef..77a4922 100644
--- a/docz/docs/03-demos/45-git.md
+++ b/docz/docs/03-demos/45-git.md
@@ -34,7 +34,7 @@ explores storing and comparing versions of structured CSV and JSON data. The
official ["Excel to CSV"](https://github.com/githubocto/flat-demo-xlsx) example
uses SheetJS under the hood to generate CSV data from an XLSX file.
-This demo covers implementation details elided in the official writeup.
+This demo covers implementation details elided in the official write-up.
## Flat Data
diff --git a/docz/docs/03-demos/index.md b/docz/docs/03-demos/index.md
index bbf864e..b41ccdc 100644
--- a/docz/docs/03-demos/index.md
+++ b/docz/docs/03-demos/index.md
@@ -25,6 +25,7 @@ run in the web browser, demos will include interactive examples.
- [`Svelte`](./svelte)
- [`VueJS`](./vue)
- [`Angular.JS`](./legacy#angularjs)
+- [`Dojo`](./legacy#dojo)
- [`Knockout`](./legacy#knockout)
### Front-End UI Components
@@ -50,7 +51,7 @@ run in the web browser, demos will include interactive examples.
- [`ExtendScript for Adobe Apps`](./extendscript)
- [`NetSuite SuiteScript`](./netsuite)
- [`SalesForce Lightning Web Components`](./salesforce)
-- [`Excel JavaScript API`](./excel)
+- [`Excel JavaScript API`](./excelapi)
- [`Headless Automation`](./headless)
- [`Other JavaScript Engines`](./engines)
- [`Azure Functions and Storage`](./azure)
diff --git a/docz/docs/06-solutions/05-output.md b/docz/docs/06-solutions/05-output.md
index f7ef496..5855b87 100644
--- a/docz/docs/06-solutions/05-output.md
+++ b/docz/docs/06-solutions/05-output.md
@@ -794,13 +794,40 @@ Readable Stream.
-In a CommonJS context, NodeJS Streams immediately work with SheetJS. This
-example reads a worksheet passed as an argument to the script, pulls the first
-worksheet, converts to CSV and writes to `out.csv`:
+:::note
+
+In a CommonJS context, NodeJS Streams and `fs` immediately work with SheetJS:
```js
-const XLSX = require("xlsx");
+const XLSX = require("xlsx"); // "just works"
+```
+In NodeJS ESM, the dependency must be loaded manually:
+
+```js
+import * as XLSX from 'xlsx';
+import { Readable } from 'stream';
+
+XLSX.stream.set_readable(Readable); // manually load stream helpers
+```
+
+Additionally, for file-related operations in NodeJS ESM, `fs` must be loaded:
+
+```js
+import * as XLSX from 'xlsx';
+import * as fs from 'fs';
+
+XLSX.set_fs(fs); // manually load fs helpers
+```
+
+**It is strongly encouraged to use CommonJS in NodeJS whenever possible.**
+
+:::
+
+This example reads a worksheet passed as an argument to the script, pulls the
+first worksheet, converts to CSV and writes to `out.csv`:
+
+```js
const workbook = XLSX.readFile(process.argv[2]);
const worksheet = workbook.Sheets[workbook.SheetNames[0]];
// highlight-next-line
diff --git a/docz/docs/07-csf/07-features/03-dates.md b/docz/docs/07-csf/07-features/03-dates.md
index 72368e4..b85b19b 100644
--- a/docz/docs/07-csf/07-features/03-dates.md
+++ b/docz/docs/07-csf/07-features/03-dates.md
@@ -91,7 +91,7 @@ The interpretation of date codes requires a shared understanding of date code
The workbook's epoch can be determined by examining the workbook's `wb.Workbook.WBProps.date1904` property:
```js
-if(!!(((wb.Workbook||{}).WBProps||{}).date1904)) {
+if(!(wb?.Workbook?.WBProps?.date1904)) {
/* uses 1904 date system */
} else {
/* uses 1900 date system */
diff --git a/docz/docusaurus.config.js b/docz/docusaurus.config.js
index 64d38bc..8971f06 100644
--- a/docz/docusaurus.config.js
+++ b/docz/docusaurus.config.js
@@ -163,6 +163,9 @@ const config = {
redirects: [
{ from: '/docs/example', to: '/docs/getting-started/example' },
{ from: '/docs/installation', to: '/docs/getting-started/' },
+ { from: '/docs/demos/excel', to: '/docs/demos/' },
+ { from: '/docs/getting-started/demos/', to: '/docs/demos/' },
+ { from: '/docs/getting-started/demos/excel', to: '/docs/demos/' },
]
}]
]
diff --git a/docz/static/dojo/read.html b/docz/static/dojo/read.html
new file mode 100644
index 0000000..db8d4a6
--- /dev/null
+++ b/docz/static/dojo/read.html
@@ -0,0 +1,34 @@
+
+
+SheetJS + Dojo Read Demo
+
+ SheetJS + Dojo Read Demo
+
+ (this HTML page is not minified -- feel free to view source!)
+ SheetJS CE Documentation
+ Table output:
+
+
+
+
+
+
\ No newline at end of file
diff --git a/docz/static/dojo/write.html b/docz/static/dojo/write.html
new file mode 100644
index 0000000..ce15876
--- /dev/null
+++ b/docz/static/dojo/write.html
@@ -0,0 +1,50 @@
+
+
+SheetJS + Dojo Write Demo
+
+ SheetJS + Dojo Write Demo
+
+ (this HTML page is not minified -- feel free to view source!)
+ SheetJS CE Documentation
+
+
+
+
+
\ No newline at end of file