docs.sheetjs.com/docz/docs/03-demos/01-frontend/08-bundler.md

1612 lines
40 KiB
Markdown
Raw Normal View History

2022-07-17 03:47:27 +00:00
---
title: Bundlers
2023-01-10 00:31:37 +00:00
pagination_prev: demos/index
2023-02-28 11:40:44 +00:00
pagination_next: demos/grid/index
2023-01-09 05:08:30 +00:00
sidebar_position: 8
sidebar_custom_props:
skip: 1
2022-07-17 03:47:27 +00:00
---
import current from '/version.js';
import Tabs from '@theme/Tabs';
import TabItem from '@theme/TabItem';
2023-04-29 11:21:37 +00:00
import CodeBlock from '@theme/CodeBlock';
2022-07-17 03:47:27 +00:00
SheetJS predates ECMAScript modules and bundler tools like Webpack. As best
practices have evolved, stress testing SheetJS libraries have revealed bugs in
the respective bundlers. This demo collects various notes and provides basic
2022-07-20 08:58:29 +00:00
examples.
:::note
Issues should be reported to the respective bundler projects. Typically it is
considered a bundler bug if the tool cannot properly handle JS libraries.
:::
2022-07-22 03:26:52 +00:00
## Browserify
`browserify` is compatible with the library and should "just work" with the
`require` form in a main page or in a web worker:
```js
var XLSX = require("xlsx");
// ... use XLSX ...
```
2022-10-30 05:45:37 +00:00
[After installing the module](/docs/getting-started/installation/nodejs), bundling is easy:
2022-07-22 03:26:52 +00:00
```bash
browserify app.js > browserify.js
uglifyjs browserify.js > browserify.min.js
```
Web Worker scripts can be bundled using the same approach.
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against Browserify `17.0.0`
:::
2022-07-22 03:26:52 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-22 03:26:52 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-22 03:26:52 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-22 03:26:52 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-22 03:26:52 +00:00
</TabItem>
</Tabs>
2) Download the following files:
- [`app.js`](pathname:///browserify/app.js)
- [`index.html`](pathname:///browserify/index.html)
- [`xlsxworker.js`](pathname:///browserify/xlsxworker.js)
2023-05-09 08:08:01 +00:00
```bash
curl -LO https://docs.sheetjs.com/browserify/app.js
curl -LO https://docs.sheetjs.com/browserify/index.html
curl -LO https://docs.sheetjs.com/browserify/xlsxworker.js
```
2022-07-22 03:26:52 +00:00
3) Bundle the scripts:
```bash
npx browserify app.js > browserify.js
npx browserify xlsxworker.js > worker.js
```
4) Spin up a local web server:
```
2022-07-25 20:48:10 +00:00
npx http-server
2022-07-22 03:26:52 +00:00
```
2023-05-03 03:40:40 +00:00
5) Access the site `http://localhost:8080/` and use the file input element to
2022-07-22 03:26:52 +00:00
select a spreadsheet.
</details>
2022-07-20 08:58:29 +00:00
## Bun
`bun bun` is capable of optimizing imported libraries in `node_modules`. In
local testing, a bundled script can save tens of milliseconds per run.
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against Bun `0.5.9`
:::
2022-07-20 08:58:29 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-20 08:58:29 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
</Tabs>
2) Save the following script to `bun.js`:
```js title="bun.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import * as XLSX from 'xlsx';
2022-07-20 08:58:29 +00:00
// highlight-next-line
import * as fs from 'fs';
// highlight-next-line
XLSX.set_fs(fs);
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-20 08:58:29 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter((row) => row.terms.some((term) => term.type === "prez"));
/* flatten objects */
const rows = prez.map((row) => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = XLSX.utils.json_to_sheet(rows);
const workbook = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
XLSX.utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
XLSX.writeFile(workbook, "Presidents.xlsx");
```
3) Bundle the script with `bun bun`:
```bash
bun bun bun.js
```
This procedure will generate `node_modules.bun`.
4) Run the script
```bash
bun bun.js
```
</details>
2022-07-22 03:26:52 +00:00
2022-08-30 22:12:52 +00:00
## Dojo
2022-10-30 05:45:37 +00:00
Integration details are included [in the "AMD" installation](/docs/getting-started/installation/amd#dojo-toolkit)
2022-08-30 22:12:52 +00:00
2023-01-09 17:25:32 +00:00
Complete Examples are included [in the "Dojo" demo](/docs/demos/frontend/legacy#dojo-toolkit)
2022-08-30 22:12:52 +00:00
2022-08-25 08:22:28 +00:00
## esbuild
2022-07-20 08:58:29 +00:00
2023-04-14 08:13:40 +00:00
The `xlsx.mjs` source file uses a subset of ES6 that `esbuild` understands and
is able to transpile for older browsers.
2022-07-20 08:58:29 +00:00
Both the `node` and `browser` platforms work out of the box.
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against esbuild `0.17.18`
:::
2022-07-20 08:58:29 +00:00
<Tabs>
<TabItem value="browser" label="Browser">
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-20 08:58:29 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
</Tabs>
2) Save the following to `esbrowser.js`:
```js title="esbrowser.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-07-20 08:58:29 +00:00
(async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-20 08:58:29 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
2022-07-26 10:49:14 +00:00
writeFileXLSX(workbook, "Presidents.xlsx");
2022-07-20 08:58:29 +00:00
})();
```
3) Create a small HTML page that loads the script. Save to `index.html`:
```html title="index.html"
<body><script src="esb.browser.js"></script></body>
```
4) Create bundle:
```bash
2023-05-09 08:08:01 +00:00
npx esbuild@0.17.18 esbrowser.js --bundle --outfile=esb.browser.js
2022-07-20 08:58:29 +00:00
```
2023-05-03 03:40:40 +00:00
5) Start a local HTTP server, then go to `http://localhost:8080/`
2022-07-20 08:58:29 +00:00
```bash
npx http-server .
```
</TabItem>
<TabItem value="nodejs" label="NodeJS">
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-20 08:58:29 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-20 08:58:29 +00:00
</TabItem>
</Tabs>
2) Save the following to `esbnode.js`:
```js title="esbnode.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { set_fs, utils, version, writeFile } from 'xlsx';
2022-07-20 08:58:29 +00:00
// highlight-next-line
import * as fs from 'fs';
// highlight-next-line
set_fs(fs);
(async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-20 08:58:29 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
writeFile(workbook, "Presidents.xlsx");
})();
```
3) Create bundle:
```bash
2023-05-09 08:08:01 +00:00
npx esbuild@0.17.18 esbnode.js --bundle --platform=node --outfile=esb.node.js
2022-07-20 08:58:29 +00:00
```
4) Run the bundle:
```bash
node esb.node.js
```
</TabItem>
</Tabs>
</details>
2022-07-17 03:47:27 +00:00
2023-05-29 02:52:54 +00:00
:::note
Bundling raw data is supported using the `binary` loader. For more advanced
content workflows, [ViteJS](/docs/demos/static/vitejs) is the recommended tool.
:::
2022-07-17 03:47:27 +00:00
## Parcel
2022-08-25 08:22:28 +00:00
Parcel should play nice with SheetJS out of the box.
2022-07-17 03:47:27 +00:00
2022-07-20 08:58:29 +00:00
:::warning Parcel Bug
2022-10-19 10:05:59 +00:00
Errors of the form `Could not statically evaluate fs call` stem from a Parcel
bug. Upgrade to Parcel version 1.5.0 or later.
2022-07-17 03:47:27 +00:00
2022-07-20 08:58:29 +00:00
:::
2022-07-17 03:47:27 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against parcel `2.8.3`
:::
2022-10-30 05:45:37 +00:00
This demo follows the [Presidents Example](/docs/getting-started/example).
2022-07-17 03:47:27 +00:00
1) Save the following to `index.html`:
```html title="index.html"
<body>
<h3>SheetJS <span id="vers"></span> export demo</h3>
<button id="xport">Click to Export!</button>
<!-- the script tag must be marked as `type="module"` -->
<!-- highlight-next-line -->
<script type="module">
// ESM-style import from "xlsx"
// highlight-next-line
2022-07-26 10:49:14 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-07-17 03:47:27 +00:00
document.getElementById("vers").innerText = version;
document.getElementById("xport").onclick = async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-17 03:47:27 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
2022-07-26 10:49:14 +00:00
writeFileXLSX(workbook, "Presidents.xlsx");
2022-07-17 03:47:27 +00:00
};
</script>
<body>
```
2) Install the SheetJS node module:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-17 03:47:27 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-17 03:47:27 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-17 03:47:27 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-17 03:47:27 +00:00
</TabItem>
</Tabs>
3) Run the Parcel CLI tool:
```bash
2023-05-09 08:08:01 +00:00
npx -y parcel@2.8.3 index.html
2022-07-17 03:47:27 +00:00
```
4) Access the page listed in the output (typically `http://localhost:1234`) and
click the "Click to Export!" button to generate a file.
2022-07-25 20:48:10 +00:00
</details>
2022-07-28 05:36:09 +00:00
## RequireJS
2022-10-30 05:45:37 +00:00
[Standalone scripts](/docs/getting-started/installation/standalone) comply with AMD `define`
2022-07-28 05:36:09 +00:00
semantics, enabling use in RequireJS out of the box.
To enable use of the alias `xlsx`, the RequireJS config should set an alias in
the `paths` property:
```js
require.config({
baseUrl: ".",
name: "app",
paths: {
// highlight-next-line
xlsx: "xlsx.full.min"
}
});
// highlight-next-line
require(["xlsx"], function(XLSX) {
2022-08-04 03:00:20 +00:00
/* use XLSX here */
2022-07-28 05:36:09 +00:00
console.log(XLSX.version);
});
```
The [Live demo](pathname:///requirejs/requirejs.html) loads RequireJS from the
CDN, uses it to load the standalone script from the SheetJS CDN, and uses the
`XLSX` variable to create a button click handler that creates a workbook.
The `r.js` optimizer also supports the standalone scripts.
2023-05-09 08:08:01 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
:::note
This demo was last tested on 2023 May 07 against RequireJS `2.3.3`
:::
:::caution
The `r.js` optimizer does not support ES6 syntax including arrow functions and
the `async` keyword! The demo JS code uses traditional functions.
:::
0) Download the standalone build:
<CodeBlock language="bash">{`\
curl -LO https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js`}
</CodeBlock>
1) Save the following to `index.html`:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script src="http://requirejs.org/docs/release/2.3.3/comments/require.js"></script>
<script>
/* Wire up RequireJS */
require.config({
baseUrl: ".",
name: "SheetJSRequire",
paths: {
xlsx: "./xlsx.full.min"
}
});
</script>
<script src="SheetJSRequire.js"></script>
</body>
</html>
```
2) Save the following to `SheetJSRequire.js`:
```js title="SheetJSRequire.js"
require(["xlsx"], function(XLSX) {
document.getElementById("xport").addEventListener("click", function() {
/* fetch JSON data and parse */
var url = "https://sheetjs.com/data/executive.json";
fetch(url).then(function(res) { return res.json(); }).then(function(raw_data) {
/* filter for the Presidents */
var prez = raw_data.filter(function(row) { return row.terms.some(function(term) { return term.type === "prez"; }); });
/* flatten objects */
var rows = prez.map(function(row) { return {
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}; });
/* generate worksheet and workbook */
var worksheet = XLSX.utils.json_to_sheet(rows);
var workbook = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
XLSX.utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
var max_width = rows.reduce(function(w, r) { return Math.max(w, r.name.length); }, 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
XLSX.writeFileXLSX(workbook, "Presidents.xlsx");
});
});
});
```
3) Start a local HTTP server, then go to `http://localhost:8080/`
```bash
npx http-server .
```
Click on "Click here to export" to generate a file.
4) Create `build.js` configuration for the optimizer:
```js title="build.js"
({
baseUrl: ".",
name: "SheetJSRequire",
paths: {
xlsx: "./xlsx.full.min"
},
out: "SheetJSRequire.min.js"
});
```
5) Run the `r.js` optimizer to create `SheetJSRequire.min.js`:
```bash
npx -p requirejs@2.3.3 r.js -o build.js
```
6) Save the following to `optimized.html`:
```html title="optimized.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script src="http://requirejs.org/docs/release/2.3.3/comments/require.js"></script>
<script src="SheetJSRequire.min.js"></script>
</body>
</html>
```
7) Open `http://localhost:8080/optimized.html`
Click on "Click here to export" to generate a file.
</details>
2022-07-31 18:48:02 +00:00
## Rollup
Rollup requires `@rollup/plugin-node-resolve` to support NodeJS modules:
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against Rollup 3.21.5
:::
2022-07-31 18:48:02 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-31 18:48:02 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} rollup@3.21.5 @rollup/plugin-node-resolve
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} rollup@3.21.5 @rollup/plugin-node-resolve
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} rollup@3.21.5 @rollup/plugin-node-resolve
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
</Tabs>
2) Save the following to `index.js`:
```js title="index.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-07-31 18:48:02 +00:00
document.getElementById("xport").addEventListener("click", async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-31 18:48:02 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
writeFileXLSX(workbook, "Presidents.xlsx");
});
```
3) Bundle the script:
```bash
npx rollup index.js --plugin @rollup/plugin-node-resolve --file bundle.js --format iife
```
4) Create a small HTML page that loads the script. Save to `index.html`:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script type="module" src="./bundle.js"></script>
</body>
</html>
```
2023-05-03 03:40:40 +00:00
5) Start a local HTTP server, then go to `http://localhost:8080/`
2022-07-31 18:48:02 +00:00
```bash
npx http-server .
```
Click on "Click here to export" to generate a file.
</details>
2022-07-25 20:48:10 +00:00
## Snowpack
Snowpack works with no caveats.
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against Snowpack `3.8.8`
:::
2022-07-25 20:48:10 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-25 20:48:10 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-25 20:48:10 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-25 20:48:10 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-25 20:48:10 +00:00
</TabItem>
</Tabs>
2) Save the following to `index.js`:
```js title="index.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-07-25 20:48:10 +00:00
document.getElementById("xport").addEventListener("click", async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-25 20:48:10 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
2022-07-26 10:49:14 +00:00
writeFileXLSX(workbook, "Presidents.xlsx");
2022-07-25 20:48:10 +00:00
});
```
3) Create a small HTML page that loads the script. Save to `index.html`:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script type="module" src="./index.js"></script>
</body>
</html>
```
:::note
Unlike other bundlers, Snowpack requires a full page including `HEAD` element.
:::
4) Build for production:
```bash
2023-05-09 08:08:01 +00:00
npx snowpack@3.8.8 build
2022-07-25 20:48:10 +00:00
```
2023-05-03 03:40:40 +00:00
5) Start a local HTTP server, then go to `http://localhost:8080/`
2022-07-25 20:48:10 +00:00
```bash
npx http-server build/
```
Click on "Click here to export" to generate a file.
</details>
2022-07-26 10:49:14 +00:00
2022-07-31 09:22:30 +00:00
## SWC
SWC provides `spack` for bundling scripts.
2023-05-09 08:08:01 +00:00
:::warning
When this demo was last tested, there was a bug affecting 1.2.247 and 1.3 . It
is strongly recommended to use `@swc/core@1.2.245` until the bug is fixed.
:::
2022-07-31 09:22:30 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against SWC 1.2.246
:::
2022-07-31 09:22:30 +00:00
1) Install the dependencies using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-31 09:22:30 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} regenerator-runtime @swc/cli @swc/core@1.2.246
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 09:22:30 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} regenerator-runtime @swc/cli @swc/core@1.2.246
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 09:22:30 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} regenerator-runtime @swc/cli @swc/core@1.2.246
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 09:22:30 +00:00
</TabItem>
</Tabs>
:::note
The `regenerator-runtime` dependency is used for transpiling `fetch` and is not
required if the interface code does not use `fetch` or Promises.
:::
2) Save the following to `index.js`:
```js title="index.js"
import { utils, version, writeFileXLSX } from 'xlsx';
document.getElementById("xport").addEventListener("click", async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-31 09:22:30 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
writeFileXLSX(workbook, "Presidents.xlsx");
});
```
3) Create an `spack.config.js` config file:
```js title="spack.config.js"
const { config } = require('@swc/core/spack');
module.exports = ({
entry: {
'web': __dirname + '/index.js',
},
output: {
path: __dirname + '/lib'
},
module: {},
});
```
4) Build for production:
```bash
npx spack
```
This command will create the script `lib/web.js`
5) Create a small HTML page that loads the generated script:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script src="lib/web.js"></script>
</body>
</html>
```
2023-05-03 03:40:40 +00:00
6) Start a local HTTP server, then go to `http://localhost:8080/`
2022-07-31 09:22:30 +00:00
```bash
2023-05-09 08:08:01 +00:00
npx http-server
2022-07-31 09:22:30 +00:00
```
Click on "Click here to export" to generate a file.
</details>
2022-08-07 01:57:38 +00:00
## SystemJS
With configuration, SystemJS supports both browser and NodeJS deployments.
:::caution
2022-10-21 00:10:10 +00:00
This demo was written against SystemJS 0.19, the most popular SystemJS version
2022-08-07 01:57:38 +00:00
used with Angular applications. In the years since the release, Angular and
other tools using SystemJS have switched to Webpack.
:::
<Tabs>
<TabItem value="browser" label="Browser">
SystemJS fails by default because the library does not export anything in the
web browser. The `meta` configuration option can be used to expose `XLSX`:
2023-04-29 11:21:37 +00:00
<CodeBlock language="js">{`\
2022-08-07 01:57:38 +00:00
SystemJS.config({
meta: {
'xlsx': {
exports: 'XLSX' // <-- tell SystemJS to expose the XLSX variable
}
},
map: {
2023-04-29 11:21:37 +00:00
'xlsx': 'https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js',
2022-08-07 01:57:38 +00:00
'fs': '', // <--|
'crypto': '', // <--| suppress native node modules
'stream': '' // <--|
}
});
2023-04-29 11:21:37 +00:00
SystemJS.import('main.js'); // load \`main.js\``}
</CodeBlock>
2022-08-07 01:57:38 +00:00
The `main.js` script can freely `require("xlsx")`.
:::caution Web Workers
Web Workers can load the SystemJS library with `importScripts`, but the imported
code cannot assign the original worker's `onmessage` callback. The recommended
approach is to expose a global from the required script, For example, supposing
the shared name is `_cb`, the primary worker script would call the callback:
```js title="worker.js"
/* main worker script */
importScripts('system.js');
SystemJS.config({ /* ... browser config ... */ });
onmessage = function(evt) {
SystemJS.import('workermain.js').then(function() { _cb(evt); });
};
```
The worker script would define and expose the function:
```js title="workermain.js"
/* Loaded with SystemJS import */
var XLSX = require('xlsx');
_cb = function(evt) { /* ... do work here ... */ };
```
:::
</TabItem>
<TabItem value="nodejs" label="NodeJS">
:::caution
While SystemJS works in NodeJS, the built-in `require` should be preferred.
:::
2022-08-25 08:22:28 +00:00
The NodeJS module main script is `xlsx/xlsx.js` and should be mapped:
2022-08-07 01:57:38 +00:00
```js
SystemJS.config({
map: {
"xlsx": "./node_modules/xlsx/xlsx.js"
}
});
```
The standalone scripts require a hint that the script assigns a global:
```js
SystemJS.config({
meta: {
"standalone": { format: "global" }
},
map: {
"standalone": "xlsx.full.min.js"
}
});
```
</TabItem>
</Tabs>
<details><summary><b>Complete Example</b> (click to show)</summary>
<Tabs>
<TabItem value="browser" label="Browser">
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against SystemJS 0.20.16
:::
2022-08-07 01:57:38 +00:00
The [Live demo](pathname:///systemjs/systemjs.html) loads SystemJS from the
CDN, uses it to load the standalone script from the SheetJS CDN and emulate
a `require` implementation when loading [`main.js`](pathname:///systemjs/main.js)
"View Source" works on the main HTML page and the `main.js` script.
</TabItem>
<TabItem value="nodejs" label="NodeJS">
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against SystemJS 0.19.47
:::
2022-08-07 01:57:38 +00:00
1) Install the dependencies:
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2023-05-09 08:08:01 +00:00
npm init -y
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz systemjs@0.19.47`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-08-07 01:57:38 +00:00
2) Save the following script to `SheetJSystem.js`:
```js title="SheetJSystem.js"
const SystemJS = require('systemjs');
// highlight-start
SystemJS.config({
map: {
'xlsx': 'node_modules/xlsx/xlsx.js',
'fs': '@node/fs',
'crypto': '@node/crypto',
'stream': '@node/stream'
}
});
// highlight-end
SystemJS.import('xlsx').then(async function(XLSX) {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-08-07 01:57:38 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = XLSX.utils.json_to_sheet(rows);
const workbook = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
XLSX.utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
XLSX.writeFile(workbook, "Presidents.xlsx");
});
```
3) Run in NodeJS:
```bash
node SheetJSystem.js
```
If the demo worked, `Presidents.xlsx` will be created.
:::note
As it uses `fetch`, this demo requires Node 18.
:::
</TabItem>
</Tabs>
</details>
2022-07-26 10:49:14 +00:00
## Vite
2023-04-14 08:13:40 +00:00
ViteJS is compatible with SheetJS versions starting from 0.18.10.
2022-07-26 10:49:14 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against ViteJS `4.3.5`
:::
2022-07-26 10:49:14 +00:00
1) Create a new ViteJS project:
```
2023-05-09 08:08:01 +00:00
npm create vite@latest sheetjs-vite -- --template vue-ts
cd sheetjs-vite
2022-07-26 10:49:14 +00:00
npm i
```
2) Add the SheetJS dependency:
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-26 10:49:14 +00:00
3) Replace `src\components\HelloWorld.vue` with:
```html title="src\components\HelloWorld.vue"
<script setup lang="ts">
import { version, utils, writeFileXLSX } from 'xlsx';
interface President {
terms: { "type": "prez" | "viceprez"; }[];
name: { first: string; last: string; }
bio: { birthday: string; }
}
async function xport() {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-26 10:49:14 +00:00
const raw_data: President[] = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
writeFileXLSX(workbook, "Presidents.xlsx");
}
</script>
<template>
<button type="button" @click="xport">Export with SheetJS version {{ version }}</button>
</template>
```
4) Run `npm run dev` and test functionality by opening a web browser to
2023-05-09 08:08:01 +00:00
`http://localhost:5173/` and clicking the button
2022-07-26 10:49:14 +00:00
5) Run `npx vite build` and verify the generated pages work by running a local
web server in the `dist` folder:
```
npx http-server dist/
```
2023-05-09 08:08:01 +00:00
Access `http://localhost:8080` in your web browser and click the export button.
2022-07-26 10:49:14 +00:00
</details>
2022-10-18 22:33:42 +00:00
:::note
2023-01-15 03:36:13 +00:00
The [Vite section of the Content demo](/docs/demos/static/vitejs) covers asset
2022-10-31 00:58:49 +00:00
loaders. They are ideal for static sites pulling data from sheets at build time.
2022-10-18 22:33:42 +00:00
:::
2022-08-07 07:48:40 +00:00
## Webpack
The ECMAScript Module build has no `require` or `import` statements and does
not use `process` or any variable that Webpack could interpret as a NodeJS
feature. Various `package.json` fields have been added to appease various
Webpack versions starting from the `2.x` series.
:::note CommonJS and ESM
Webpack bundled the CommonJS build in older versions of the library. Version
`0.18.1` changed the NodeJS module package so that Webpack uses the ESM build.
The ESM build does not include the codepage support library for XLS reading.
2022-10-30 05:45:37 +00:00
[As described in the installation instructions](/docs/getting-started/installation/frameworks),
2022-08-07 07:48:40 +00:00
the codepage dependency should be imported explicitly:
```js
import * as XLSX from 'xlsx';
import * as cptable from 'xlsx/dist/cpexcel.full.mjs';
set_cptable(cptable);
```
:::
2023-04-14 08:13:40 +00:00
:::caution
Some older webpack projects will throw an error in the browser:
```
require is not defined (xlsx.mjs)
```
This was a bug in Webpack and affected projects built with `create-react-app`.
If upgrading Webpack is not feasible, explicitly import the standalone builds:
```js
import * as XLSX from 'xlsx/dist/xlsx.full.min.js';
```
:::
2022-08-07 07:48:40 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was tested against the following Webpack versions:
| Version | Date | Required Workarounds |
|:---------|:-----------|:------------------------------------|
| `2.7.0` | 2023-05-07 | Import `xlsx/dist/xlsx.full.min.js` |
| `3.12.0` | 2023-05-07 | Import `xlsx/dist/xlsx.full.min.js` |
| `4.46.0` | 2023-05-07 | Downgrade NodeJS (tested v16.20.0) |
| `5.82.0` | 2023-05-07 | |
:::
2022-08-07 07:48:40 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-08-07 07:48:40 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-08-07 07:48:40 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-08-07 07:48:40 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-08-07 07:48:40 +00:00
</TabItem>
</Tabs>
2) Save the following to `index.js`:
```js title="index.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
document.getElementById("xport").addEventListener("click", function() {
/* fetch JSON data and parse */
var url = "https://sheetjs.com/data/executive.json";
fetch(url).then(function(res) { return res.json(); }).then(function(raw_data) {
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* filter for the Presidents */
var prez = raw_data.filter(function(row) { return row.terms.some(function(term) { return term.type === "prez"; }); });
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* flatten objects */
var rows = prez.map(function(row) { return {
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}; });
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* generate worksheet and workbook */
var worksheet = utils.json_to_sheet(rows);
var workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* calculate column width */
var max_width = rows.reduce(function(w, r) { return Math.max(w, r.name.length); }, 10);
worksheet["!cols"] = [ { wch: max_width } ];
2022-08-07 07:48:40 +00:00
2023-05-09 08:08:01 +00:00
/* create an XLSX file and try to save to Presidents.xlsx */
writeFileXLSX(workbook, "Presidents.xlsx");
});
2022-08-07 07:48:40 +00:00
});
```
3) Create a small `webpack.config.js` script that writes to `index.min.js`:
```js title="webpack.config.js"
module.exports = {
/* entry point index.js */
entry: './index.js',
/* write to index.min.js */
output: { path:__dirname, filename: './index.min.js' }
}
```
4) Build for production. The command depends on the version of webpack:
<Tabs>
<TabItem value="23" label="2.x and 3.x">
2023-05-09 08:08:01 +00:00
:::note
In Webpack 2.x and 3.x, the import statement must use the standalone build:
```js title="index.js"
// highlight-next-line
import { utils, version, writeFileXLSX } from 'xlsx/dist/xlsx.full.min.js';
```
:::
This line must be changed before bundling.
2022-08-07 07:48:40 +00:00
**Webpack 2.x**
```bash
npx webpack@2.x -p
```
**Webpack 3.x**
```bash
npx webpack@3.x -p
```
:::caution
The minifier that ships with Webpack 2.x does not handle `async` functions. The
unminified code generated by Webpack will work for the purposes of the demo. It
is strongly recommended to upgrade to a newer version of Webpack. If that is
not feasible, the example should be replaced with a traditional Promise chain.
:::
</TabItem>
<TabItem value="4+" label="4.x, 5.x and beyond" default>
:::warning Pinning specific versions of webpack
The webpack tooling is not designed for switching between versions. A specific
version above 4.0 can be pinned by locally installing webpack and the CLI tool.
:::
**Webpack 4.x**
2023-05-09 08:08:01 +00:00
:::note
Webpack 4 is incompatible with Node 18+. When this demo was last tested, NodeJS
was locally downgraded to 16.20.0
:::
2022-08-07 07:48:40 +00:00
```bash
2023-05-09 08:08:01 +00:00
npm i --save webpack@4.x webpack-cli@4.x
2022-08-07 07:48:40 +00:00
npx webpack --mode=production
```
**Webpack 5.x**
```bash
2023-05-09 08:08:01 +00:00
npm i --save webpack@5.x webpack-cli@5.x
2022-08-07 07:48:40 +00:00
npx webpack --mode=production
```
**Webpack latest**
```bash
2023-05-07 13:58:36 +00:00
npm i --save webpack webpack-cli
2022-08-07 07:48:40 +00:00
npx webpack --mode=production
```
</TabItem>
</Tabs>
5) Create a small HTML page that loads the script. Save to `index.html`:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script src="./index.min.js"></script>
</body>
</html>
```
2023-05-03 03:40:40 +00:00
6) Start a local HTTP server and go to `http://localhost:8080/`
2022-08-07 07:48:40 +00:00
```bash
npx http-server .
```
Click on "Click here to export" to generate a file.
</details>
2023-05-25 01:36:15 +00:00
:::note
The [Webpack section of the Content demo](/docs/demos/static/webpack) covers asset
loaders. They are ideal for static sites pulling data from sheets at build time.
:::
2022-07-31 18:48:02 +00:00
## WMR
2023-05-09 08:08:01 +00:00
WMR works with no caveats.
2022-07-31 18:48:02 +00:00
<details><summary><b>Complete Example</b> (click to show)</summary>
2023-05-09 08:08:01 +00:00
:::note
This demo was last tested on 2023 May 07 against WMR `3.8.0`
:::
2022-07-31 18:48:02 +00:00
1) Install the tarball using a package manager:
2023-05-07 13:58:36 +00:00
<Tabs groupId="pm">
2022-07-31 18:48:02 +00:00
<TabItem value="npm" label="npm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
<TabItem value="pnpm" label="pnpm">
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
pnpm install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
<TabItem value="yarn" label="Yarn" default>
2023-05-07 13:58:36 +00:00
<CodeBlock language="bash">{`\
2022-08-07 07:48:40 +00:00
yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
2023-05-07 13:58:36 +00:00
</CodeBlock>
2022-07-31 18:48:02 +00:00
</TabItem>
</Tabs>
2) Save the following to `index.js`:
```js title="index.js"
// highlight-next-line
2023-01-09 05:08:30 +00:00
import { utils, version, writeFileXLSX } from 'xlsx';
2022-07-31 18:48:02 +00:00
document.getElementById("xport").addEventListener("click", async() => {
/* fetch JSON data and parse */
2022-08-21 19:43:30 +00:00
const url = "https://sheetjs.com/data/executive.json";
2022-07-31 18:48:02 +00:00
const raw_data = await (await fetch(url)).json();
/* filter for the Presidents */
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
/* flatten objects */
const rows = prez.map(row => ({
name: row.name.first + " " + row.name.last,
birthday: row.bio.birthday
}));
/* generate worksheet and workbook */
const worksheet = utils.json_to_sheet(rows);
const workbook = utils.book_new();
utils.book_append_sheet(workbook, worksheet, "Dates");
/* fix headers */
utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
/* calculate column width */
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
worksheet["!cols"] = [ { wch: max_width } ];
/* create an XLSX file and try to save to Presidents.xlsx */
writeFileXLSX(workbook, "Presidents.xlsx");
});
```
3) Create a small HTML page that loads the script. Save to `index.html`:
```html title="index.html"
<!DOCTYPE html>
<html lang="en">
<head></head>
<body>
<h1>SheetJS Presidents Demo</h1>
<button id="xport">Click here to export</button>
<script type="module" src="./index.js"></script>
</body>
</html>
```
4) Build for production:
```bash
2023-05-09 08:08:01 +00:00
npx wmr@3.8.0 build
2022-07-31 18:48:02 +00:00
```
2023-05-03 03:40:40 +00:00
5) Start a local HTTP server in `dist` folder and go to `http://localhost:8080/`
2022-07-31 18:48:02 +00:00
```bash
npx http-server dist/
```
Click on "Click here to export" to generate a file.
</details>