docusaurus
This commit is contained in:
parent
34f4c09cac
commit
6449ecc35e
@ -5,6 +5,7 @@ js-xlsx
|
||||
xls
|
||||
xlsb
|
||||
xlsx
|
||||
docs.sheetjs.com
|
||||
|
||||
# Excel-related terms
|
||||
A1-style
|
||||
@ -48,6 +49,7 @@ NPM
|
||||
Nuxt
|
||||
PhantomJS
|
||||
Photoshop
|
||||
ReactJS
|
||||
Redis
|
||||
RequireJS
|
||||
Rollup
|
||||
@ -58,6 +60,7 @@ VueJS
|
||||
WebKit
|
||||
WebSQL
|
||||
WK_
|
||||
axios
|
||||
iOS
|
||||
iWork
|
||||
nodejs
|
||||
|
8
Makefile
8
Makefile
@ -1,3 +1,9 @@
|
||||
.PHONY: build
|
||||
build:
|
||||
cd docz; pnpm build; cd ..
|
||||
rm -rf docs
|
||||
mv docz/build/ docs
|
||||
|
||||
.PHONY: index
|
||||
index: readme ## Rebuild site
|
||||
sed -i .bak 's/](d/](https:\/\/github.com\/SheetJS\/SheetJS\/tree\/master\/d/g' README.md
|
||||
@ -21,7 +27,7 @@ formats.png legend.png: %.png: misc/%.svg
|
||||
node misc/coarsify.js misc/$*.svg misc/$*.svg.svg
|
||||
npx svgexport misc/$*.svg.svg $@ 0.5x
|
||||
|
||||
MDLINT=README.md
|
||||
MDLINT=README.md $(wildcard docz/*.md*) $(wildcard docz/docs/*.md*) $(wildcard docz/docs/*/*.md*)
|
||||
.PHONY: mdlint
|
||||
mdlint: $(MDLINT) ## Check markdown documents
|
||||
npx alex $^
|
||||
|
20
docz/.gitignore
vendored
Normal file
20
docz/.gitignore
vendored
Normal file
@ -0,0 +1,20 @@
|
||||
# Dependencies
|
||||
/node_modules
|
||||
|
||||
# Production
|
||||
/build
|
||||
|
||||
# Generated files
|
||||
.docusaurus
|
||||
.cache-loader
|
||||
|
||||
# Misc
|
||||
.DS_Store
|
||||
.env.local
|
||||
.env.development.local
|
||||
.env.test.local
|
||||
.env.production.local
|
||||
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
3
docz/README.md
Normal file
3
docz/README.md
Normal file
@ -0,0 +1,3 @@
|
||||
# docs.sheetjs.com
|
||||
|
||||
<https://docs.sheetjs.com/>
|
3
docz/babel.config.js
Normal file
3
docz/babel.config.js
Normal file
@ -0,0 +1,3 @@
|
||||
module.exports = {
|
||||
presets: [require.resolve('@docusaurus/core/lib/babel/preset')],
|
||||
};
|
12
docz/blog/2019-05-28-first-blog-post.md
Normal file
12
docz/blog/2019-05-28-first-blog-post.md
Normal file
@ -0,0 +1,12 @@
|
||||
---
|
||||
slug: first-blog-post
|
||||
title: First Blog Post
|
||||
authors:
|
||||
name: Gao Wei
|
||||
title: Docusaurus Core Team
|
||||
url: https://github.com/wgao19
|
||||
image_url: https://github.com/wgao19.png
|
||||
tags: [hola, docusaurus]
|
||||
---
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
44
docz/blog/2019-05-29-long-blog-post.md
Normal file
44
docz/blog/2019-05-29-long-blog-post.md
Normal file
@ -0,0 +1,44 @@
|
||||
---
|
||||
slug: long-blog-post
|
||||
title: Long Blog Post
|
||||
authors: endi
|
||||
tags: [hello, docusaurus]
|
||||
---
|
||||
|
||||
This is the summary of a very long blog post,
|
||||
|
||||
Use a `<!--` `truncate` `-->` comment to limit blog post size in the list view.
|
||||
|
||||
<!--truncate-->
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet
|
20
docz/blog/2021-08-01-mdx-blog-post.mdx
Normal file
20
docz/blog/2021-08-01-mdx-blog-post.mdx
Normal file
@ -0,0 +1,20 @@
|
||||
---
|
||||
slug: mdx-blog-post
|
||||
title: MDX Blog Post
|
||||
authors: [slorber]
|
||||
tags: [docusaurus]
|
||||
---
|
||||
|
||||
Blog posts support [Docusaurus Markdown features](https://docusaurus.io/docs/markdown-features), such as [MDX](https://mdxjs.com/).
|
||||
|
||||
:::tip
|
||||
|
||||
Use the power of React to create interactive blog posts.
|
||||
|
||||
```js
|
||||
<button onClick={() => alert('button clicked!')}>Click me!</button>
|
||||
```
|
||||
|
||||
<button onClick={() => alert('button clicked!')}>Click me!</button>
|
||||
|
||||
:::
|
BIN
docz/blog/2021-08-26-welcome/docusaurus-plushie-banner.jpeg
Normal file
BIN
docz/blog/2021-08-26-welcome/docusaurus-plushie-banner.jpeg
Normal file
Binary file not shown.
After Width: | Height: | Size: 94 KiB |
25
docz/blog/2021-08-26-welcome/index.md
Normal file
25
docz/blog/2021-08-26-welcome/index.md
Normal file
@ -0,0 +1,25 @@
|
||||
---
|
||||
slug: welcome
|
||||
title: Welcome
|
||||
authors: [slorber, yangshun]
|
||||
tags: [facebook, hello, docusaurus]
|
||||
---
|
||||
|
||||
[Docusaurus blogging features](https://docusaurus.io/docs/blog) are powered by the [blog plugin](https://docusaurus.io/docs/api/plugins/@docusaurus/plugin-content-blog).
|
||||
|
||||
Simply add Markdown files (or folders) to the `blog` directory.
|
||||
|
||||
Regular blog authors can be added to `authors.yml`.
|
||||
|
||||
The blog post date can be extracted from filenames, such as:
|
||||
|
||||
- `2019-05-30-welcome.md`
|
||||
- `2019-05-30-welcome/index.md`
|
||||
|
||||
A blog post folder can be convenient to co-locate blog post images:
|
||||
|
||||
![Docusaurus Plushie](./docusaurus-plushie-banner.jpeg)
|
||||
|
||||
The blog supports tags as well!
|
||||
|
||||
**And if you don't want a blog**: just delete this directory, and use `blog: false` in your Docusaurus config.
|
17
docz/blog/authors.yml
Normal file
17
docz/blog/authors.yml
Normal file
@ -0,0 +1,17 @@
|
||||
endi:
|
||||
name: Endilie Yacop Sucipto
|
||||
title: Maintainer of Docusaurus
|
||||
url: https://github.com/endiliey
|
||||
image_url: https://github.com/endiliey.png
|
||||
|
||||
yangshun:
|
||||
name: Yangshun Tay
|
||||
title: Front End Engineer @ Facebook
|
||||
url: https://github.com/yangshun
|
||||
image_url: https://github.com/yangshun.png
|
||||
|
||||
slorber:
|
||||
name: Sébastien Lorber
|
||||
title: Docusaurus maintainer
|
||||
url: https://sebastienlorber.com
|
||||
image_url: https://github.com/slorber.png
|
112
docz/docs/02-installation/01-standalone.mdx
Normal file
112
docz/docs/02-installation/01-standalone.mdx
Normal file
@ -0,0 +1,112 @@
|
||||
---
|
||||
sidebar_position: 1
|
||||
sidebar_custom_props:
|
||||
summary: Classic pages with simple <script> tags
|
||||
---
|
||||
|
||||
import current from '/version.js';
|
||||
|
||||
# Standalone Browser Scripts
|
||||
|
||||
Each standalone release script is available at <https://cdn.sheetjs.com/>.
|
||||
|
||||
<div>The current version is {current} and can be referenced as follows:</div>
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-html"}}>{`\
|
||||
<!-- use version ${current} -->
|
||||
<script lang="javascript" src="https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js"></script>`}
|
||||
</code></pre>
|
||||
|
||||
The `latest` tag references the latest version and updates with each release:
|
||||
|
||||
```html
|
||||
<!-- use the latest version -->
|
||||
<script lang="javascript" src="https://cdn.sheetjs.com/xlsx-latest/package/dist/xlsx.full.min.js"></script>
|
||||
```
|
||||
|
||||
**For production use, scripts should be downloaded and added to a public folder
|
||||
alongside other scripts.**
|
||||
|
||||
<details>
|
||||
<summary><b>Download using Bower</b> (click to show)</summary>
|
||||
|
||||
[Bower](https://bower.io/) plays nice with the CDN tarballs:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ npx bower install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
|
||||
Bower will place the standalone scripts in `bower_components/js-xlsx/dist/`
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Browser builds</b> (click to show)</summary>
|
||||
|
||||
The complete single-file version is generated at `dist/xlsx.full.min.js`
|
||||
|
||||
`dist/xlsx.core.min.js` omits codepage library (no support for XLS encodings)
|
||||
|
||||
A slimmer build is generated at `dist/xlsx.mini.min.js`. Compared to full build:
|
||||
- codepage library skipped (no support for XLS encodings)
|
||||
- no support for XLSB / XLS / Lotus 1-2-3 / SpreadsheetML 2003 / Numbers
|
||||
- node stream utils removed
|
||||
|
||||
These scripts are also available on the CDN:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-html"}}>{`\
|
||||
<!-- use xlsx.mini.min.js from version ${current} -->
|
||||
<script lang="javascript" src="https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.mini.min.js"></script>`}
|
||||
</code></pre>
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Internet Explorer and ECMAScript 3 Compatibility</b> (click to show)</summary>
|
||||
|
||||
For broad compatibility with JavaScript engines, the library is written using
|
||||
ECMAScript 3 language dialect as well as some ES5 features like `Array#forEach`.
|
||||
Older browsers require shims to provide missing functions.
|
||||
|
||||
To use the shim, add the shim before the script tag that loads `xlsx.js`:
|
||||
|
||||
```html
|
||||
<!-- add the shim first -->
|
||||
<script type="text/javascript" src="shim.min.js"></script>
|
||||
<!-- after the shim is referenced, add the library -->
|
||||
<script type="text/javascript" src="xlsx.full.min.js"></script>
|
||||
```
|
||||
|
||||
Due to SSL certificate compatibility issues, it is highly recommended to save
|
||||
the Standalone and Shim scripts from <https://cdn.sheetjs.com/> and add to a
|
||||
public directory in the site.
|
||||
|
||||
The script also includes `IE_LoadFile` and `IE_SaveFile` for loading and saving
|
||||
files in Internet Explorer versions 6-9. The `xlsx.extendscript.js` script
|
||||
bundles the shim in a format suitable for Photoshop and other Adobe products.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>ECMAScript Module Imports in a SCRIPT TAG</b> (click to show)</summary>
|
||||
|
||||
The ECMAScript Module build is saved to `xlsx.mjs` and can be directly added to
|
||||
a page with a `script` tag using `type="module"`:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-html"}}>{`\
|
||||
<script type="module">
|
||||
import { read, writeFileXLSX } from "https://cdn.sheetjs.com/xlsx-${current}/package/xlsx.mjs";
|
||||
</script>`}
|
||||
</code></pre>
|
||||
|
||||
If XLS support is required, `cpexcel.full.js` must be manually imported:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-html"}}>{`\
|
||||
<script type="module">
|
||||
/* load the codepage support library for extended support with older formats */
|
||||
import { set_cptable } from "https://cdn.sheetjs.com/xlsx-${current}/package/xlsx.mjs";
|
||||
import * as cptable from 'https://cdn.sheetjs.com/xlsx-${current}/package/dist/cpexcel.full.mjs';
|
||||
set_cptable(cptable);
|
||||
</script>`}
|
||||
</code></pre>
|
||||
|
||||
</details>
|
54
docz/docs/02-installation/02-frameworks.md
Normal file
54
docz/docs/02-installation/02-frameworks.md
Normal file
@ -0,0 +1,54 @@
|
||||
---
|
||||
sidebar_position: 2
|
||||
sidebar_custom_props:
|
||||
summary: Angular, React, VueJS, Webpack, etc.
|
||||
---
|
||||
|
||||
import current from '/version.js';
|
||||
|
||||
# Frameworks and Bundlers
|
||||
|
||||
import Tabs from '@theme/Tabs';
|
||||
import TabItem from '@theme/TabItem';
|
||||
|
||||
Each standalone release package is available at <https://cdn.sheetjs.com/>. The
|
||||
NodeJS package is designed to be used with frameworks and bundlers. It is a
|
||||
proper ECMAScript Module release which can be optimized with developer tools.
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="npm" label="npm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ npm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="pnpm" label="pnpm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="yarn" label="Yarn" default>
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ yarn add --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
</Tabs>
|
||||
|
||||
Once installed, the library can be imported under the name `xlsx`:
|
||||
|
||||
```js
|
||||
import { read, writeFileXLSX } from "xlsx";
|
||||
```
|
||||
|
||||
<details>
|
||||
<summary><b>XLS Codepage support</b> (click to show)</summary>
|
||||
|
||||
If XLS support is required, `cpexcel.full.js` must be manually imported:
|
||||
|
||||
```js
|
||||
/* load the codepage support library for extended support with older formats */
|
||||
import { set_cptable } from "xlsx";
|
||||
import * as cptable from 'xlsx/dist/cpexcel.full.mjs';
|
||||
set_cptable(cptable);
|
||||
```
|
||||
|
||||
</details>
|
31
docz/docs/02-installation/03-deno.md
Normal file
31
docz/docs/02-installation/03-deno.md
Normal file
@ -0,0 +1,31 @@
|
||||
---
|
||||
sidebar_position: 3
|
||||
sidebar_custom_props:
|
||||
summary: Import ECMAScript Modules and TypeScript definitions
|
||||
---
|
||||
|
||||
import current from '/version.js';
|
||||
|
||||
# Deno
|
||||
|
||||
Each standalone release script is available at <https://cdn.sheetjs.com/>.
|
||||
|
||||
Using the URL imports, `deno run` will automatically download scripts and types:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-ts"}}>{`\
|
||||
// @deno-types="https://cdn.sheetjs.com/xlsx-${current}/package/types/index.d.ts"
|
||||
import * as XLSX from 'https://cdn.sheetjs.com/xlsx-${current}/package/xlsx.mjs';`}
|
||||
</code></pre>
|
||||
|
||||
<details>
|
||||
<summary><b>XLS Codepage support</b> (click to show)</summary>
|
||||
|
||||
If XLS support is required, `cpexcel.full.js` must be manually imported:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-ts"}}>{`\
|
||||
/* load the codepage support library for extended support with older formats */
|
||||
import * as cptable from 'https://cdn.sheetjs.com/xlsx-${current}/package/dist/cpexcel.full.mjs';
|
||||
XLSX.set_cptable(cptable);`}
|
||||
</code></pre>
|
||||
|
||||
</details>
|
104
docz/docs/02-installation/04-nodejs.md
Normal file
104
docz/docs/02-installation/04-nodejs.md
Normal file
@ -0,0 +1,104 @@
|
||||
---
|
||||
sidebar_position: 4
|
||||
sidebar_custom_props:
|
||||
summary: Server-side and other frameworks using NodeJS modules
|
||||
---
|
||||
|
||||
import current from '/version.js';
|
||||
|
||||
# NodeJS
|
||||
|
||||
import Tabs from '@theme/Tabs';
|
||||
import TabItem from '@theme/TabItem';
|
||||
|
||||
Tarballs are available on <https://cdn.sheetjs.com>.
|
||||
|
||||
<div>Each individual version can be referenced using a similar URL pattern.
|
||||
|
||||
<a href={`https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}>https://cdn.sheetjs.com/xlsx-{current}/xlsx-{current}.tgz</a> is the URL for {current}</div>
|
||||
|
||||
<https://cdn.sheetjs.com/xlsx-latest/xlsx-latest.tgz> is a link to the latest
|
||||
version and will refresh on each release.
|
||||
|
||||
## Installation
|
||||
|
||||
Tarballs can be directly installed using a package manager:
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="npm" label="npm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ npm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="pnpm" label="pnpm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="yarn" label="Yarn" default>
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ yarn add --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
</Tabs>
|
||||
|
||||
### Vendoring
|
||||
|
||||
For general stability, "vendoring" modules is the recommended approach:
|
||||
|
||||
<div>1) Download the tarball (<code parentName="pre">xlsx-{current}.tgz</code>) for the desired version. The current
|
||||
version is available at <a href={`https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`}>https://cdn.sheetjs.com/xlsx-{current}/xlsx-{current}.tgz</a></div><br/>
|
||||
|
||||
2) Create a `vendor` subdirectory at the root of your project and move the
|
||||
tarball to that folder. Add it to your project repository.
|
||||
|
||||
3) Install the tarball using a package manager:
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="npm" label="npm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ npm install --save file:vendor/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="pnpm" label="pnpm">
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ pnpm install --save file:vendor/xlsx-${current}.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
<TabItem value="yarn" label="Yarn" default>
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ yarn add --save file:vendor/xlsx-0.18.7.tgz`}
|
||||
</code></pre>
|
||||
</TabItem>
|
||||
</Tabs>
|
||||
|
||||
The package will be installed and accessible as `xlsx`.
|
||||
|
||||
## Usage
|
||||
|
||||
By default, the module supports `require` and it will automatically add support
|
||||
for streams and filesystem access:
|
||||
|
||||
```js
|
||||
var XLSX = require("xlsx");
|
||||
```
|
||||
|
||||
The module also ships with `xlsx.mjs` for use with `import`. The `mjs` version
|
||||
does not automatically load native node modules, so they must be added manually:
|
||||
|
||||
```js
|
||||
import * as XLSX from 'xlsx/xlsx.mjs';
|
||||
|
||||
/* load 'fs' for readFile and writeFile support */
|
||||
import * as fs from 'fs';
|
||||
XLSX.set_fs(fs);
|
||||
|
||||
/* load 'stream' for stream support */
|
||||
import { Readable } from 'stream';
|
||||
XLSX.stream.set_readable(Readable);
|
||||
|
||||
/* load the codepage support library for extended support with older formats */
|
||||
import * as cpexcel from 'xlsx/dist/cpexcel.full.mjs';
|
||||
XLSX.set_cptable(cpexcel);
|
||||
```
|
||||
|
21
docz/docs/02-installation/05-extendscript.md
Normal file
21
docz/docs/02-installation/05-extendscript.md
Normal file
@ -0,0 +1,21 @@
|
||||
---
|
||||
sidebar_position: 5
|
||||
sidebar_custom_props:
|
||||
summary: Photoshop, InDesign, and other Creative Cloud apps
|
||||
---
|
||||
|
||||
import current from '/version.js';
|
||||
|
||||
# ExtendScript
|
||||
|
||||
Each standalone release script is available at <https://cdn.sheetjs.com/>.
|
||||
|
||||
`xlsx.extendscript.js` is an ExtendScript build for Photoshop and InDesign.
|
||||
|
||||
<div><a href={`https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.extendscript.js`}>https://cdn.sheetjs.com/xlsx-{current}/package/dist/xlsx.extendscript.js</a> is the URL for {current}</div><br/>
|
||||
|
||||
After downloading the script, it can be directly referenced with `#include`:
|
||||
|
||||
```c
|
||||
#include "xlsx.extendscript.js"
|
||||
```
|
4
docz/docs/02-installation/_category_.json
Normal file
4
docz/docs/02-installation/_category_.json
Normal file
@ -0,0 +1,4 @@
|
||||
{
|
||||
"label": "Installation",
|
||||
"position": 2
|
||||
}
|
20
docz/docs/02-installation/index.md
Normal file
20
docz/docs/02-installation/index.md
Normal file
@ -0,0 +1,20 @@
|
||||
---
|
||||
hide_table_of_contents: true
|
||||
---
|
||||
|
||||
# Installation
|
||||
|
||||
import DocCardList from '@theme/DocCardList';
|
||||
import {useCurrentSidebarCategory} from '@docusaurus/theme-common';
|
||||
|
||||
<https://cdn.sheetjs.com> is the primary software distribution site. Please
|
||||
read the installation instructions for your use case:
|
||||
|
||||
<ul>{useCurrentSidebarCategory().items.map((item, index) => {
|
||||
const listyle = (item.customProps?.icon) ? {
|
||||
listStyleImage: `url("${item.customProps.icon}")`
|
||||
} : {};
|
||||
return (<li style={listyle} {...(item.customProps?.class ? {className: item.customProps.class}: {})}>
|
||||
<a href={item.href}>{item.label}</a>{item.customProps?.summary && (" - " + item.customProps.summary)}
|
||||
</li>);
|
||||
})}</ul>
|
375
docz/docs/03-example.mdx
Normal file
375
docz/docs/03-example.mdx
Normal file
@ -0,0 +1,375 @@
|
||||
---
|
||||
sidebar_position: 3
|
||||
---
|
||||
|
||||
# Complete Example
|
||||
|
||||
SheetJS presents a simple JS interface that works with "Array of Arrays" and
|
||||
"Array of JS Objects". The API functions are building blocks that should be
|
||||
combined with other JS APIs to solve problems.
|
||||
|
||||
The discussion focuses on the problem solving mindset. API details are covered
|
||||
in other parts of the documentation.
|
||||
|
||||
The goal of this example is to generate a XLSB workbook of US President names
|
||||
and birthdays. [Click here](#live-demo) to jump to the live demo
|
||||
|
||||
## Acquire Data
|
||||
|
||||
### Raw Data
|
||||
|
||||
[The raw data is available in JSON form](https://theunitedstates.io/congress-legislators/executive.json).
|
||||
For convenience, it has been [mirrored here](https://sheetjs.com/executive.json)
|
||||
|
||||
The data result is an Array of objects. This is the data for John Adams:
|
||||
|
||||
```js
|
||||
{
|
||||
"id": { /* (data omitted) */ },
|
||||
"name": {
|
||||
"first": "John", // <-- first name
|
||||
"last": "Adams" // <-- last name
|
||||
},
|
||||
"bio": {
|
||||
"birthday": "1735-10-19", // <-- birthday
|
||||
"gender": "M"
|
||||
},
|
||||
"terms": [
|
||||
{ "type": "viceprez", /* (other fields omitted) */ },
|
||||
{ "type": "viceprez", /* (other fields omitted) */ },
|
||||
{ "type": "prez", /* (other fields omitted) */ }
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
### Filtering for Presidents
|
||||
|
||||
The dataset includes Aaron Burr, a Vice President who was never President!
|
||||
|
||||
`Array#filter` creates a new array with the desired rows. A President served
|
||||
at least one term with `type` set to `"prez"`. To test if a particular row has
|
||||
at least one `"prez"` term, `Array#some` is another native JS function. The
|
||||
complete filter would be:
|
||||
|
||||
```js
|
||||
const prez = raw_data.filter(row => row.terms.some(term => term.type === "prez"));
|
||||
```
|
||||
|
||||
### Reshaping the Array
|
||||
|
||||
For this example, the name will be the first name combined with the last name
|
||||
(`row.name.first + " " + row.name.last`) and the birthday will be the subfield
|
||||
`row.bio.birthday`. Using `Array#map`, the dataset can be massaged in one call:
|
||||
|
||||
```js
|
||||
const rows = prez.map(row => ({
|
||||
name: row.name.first + " " + row.name.last,
|
||||
birthday: row.bio.birthday
|
||||
}));
|
||||
```
|
||||
|
||||
The result is an array of "simple" objects with no nesting:
|
||||
|
||||
```js
|
||||
[
|
||||
{ name: "George Washington", birthday: "1732-02-22" },
|
||||
{ name: "John Adams", birthday: "1735-10-19" },
|
||||
// ... one row per President
|
||||
]
|
||||
```
|
||||
|
||||
## Create a Workbook
|
||||
|
||||
With the cleaned dataset, `XLSX.utils.json_to_sheet` generates a worksheet:
|
||||
|
||||
```js
|
||||
const worksheet = XLSX.utils.json_to_sheet(rows);
|
||||
```
|
||||
|
||||
`XLSX.utils.book_new` creates a new workbook and `XLSX.utils.book_append_sheet`
|
||||
appends a worksheet to the workbook. The new worksheet will be called "Dates":
|
||||
|
||||
```js
|
||||
const workbook = XLSX.utils.book_new();
|
||||
XLSX.utils.book_append_sheet(workbook, worksheet, "Dates");
|
||||
```
|
||||
|
||||
## Clean up Workbook
|
||||
|
||||
The data is in the workbook and can be exported.
|
||||
|
||||
![Rough export](./img/rough.png)
|
||||
|
||||
There are multiple opportunities for improvement: the headers can be renamed and
|
||||
the column widths can be adjusted. [SheetJS Pro](https://sheetjs.com/pro) offers
|
||||
additional styling options like cell styling and frozen rows.
|
||||
|
||||
<details><summary><b>Changing Header Names</b> (click to show)</summary>
|
||||
|
||||
By default, `json_to_sheet` creates a worksheet with a header row. In this case,
|
||||
the headers come from the JS object keys: "name" and "birthday".
|
||||
|
||||
The headers are in cells A1 and B1. `XLSX.utils.sheet_add_aoa` can write text
|
||||
values to the existing worksheet starting at cell A1:
|
||||
|
||||
```js
|
||||
XLSX.utils.sheet_add_aoa(worksheet, [["Name", "Birthday"]], { origin: "A1" });
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details><summary><b>Changing Column Widths</b> (click to show)</summary>
|
||||
|
||||
Some of the names are longer than the default column width. Column widths are
|
||||
set by setting the `"!cols"` worksheet property.
|
||||
|
||||
The following line sets the width of column A to approximately 10 characters:
|
||||
|
||||
```js
|
||||
worksheet["!cols"] = [ { wch: 10 } ]; // set column A width to 10 characters
|
||||
```
|
||||
|
||||
One `Array#reduce` call over `rows` can calculate the maximum width:
|
||||
|
||||
```js
|
||||
const max_width = rows.reduce((w, r) => Math.max(w, r.name.length), 10);
|
||||
worksheet["!cols"] = [ { wch: max_width } ];
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
## Export a File
|
||||
|
||||
`XLSX.writeFile` creates a spreadsheet file and tries to write it to the system.
|
||||
In the browser, it will try to prompt the user to download the file. In NodeJS,
|
||||
it will write to the local directory.
|
||||
|
||||
```js
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
```
|
||||
|
||||
![Final export](./img/final.png)
|
||||
|
||||
|
||||
## Live Demo
|
||||
|
||||
```jsx live
|
||||
function Presidents() { return ( <button onClick={async () => {
|
||||
/* fetch JSON data and parse */
|
||||
const url = "https://sheetjs.com/executive.json";
|
||||
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.xlsb */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
}}><b>Click to Generate file!</b></button> ); }
|
||||
```
|
||||
|
||||
## Run the Demo Locally
|
||||
|
||||
import Tabs from '@theme/Tabs';
|
||||
import TabItem from '@theme/TabItem';
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="browser" label="Browser">
|
||||
|
||||
Save the following script to `snippet.html` and open the page. The page must be
|
||||
hosted (no `file:///` access).
|
||||
|
||||
<https://sheetjs.com/pres.html> is a hosted version of the page.
|
||||
|
||||
```html
|
||||
<body>
|
||||
<script src="https://cdn.sheetjs.com/xlsx-latest/package/dist/xlsx.full.min.js"></script>
|
||||
<script>
|
||||
(async() => {
|
||||
/* fetch JSON data and parse */
|
||||
const url = "https://sheetjs.com/executive.json";
|
||||
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.xlsb */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
})();
|
||||
</script>
|
||||
<body>
|
||||
```
|
||||
</TabItem>
|
||||
<TabItem value="nodejs" label="NodeJS">
|
||||
|
||||
Install the dependencies:
|
||||
|
||||
```bash
|
||||
$ npm i --save https://cdn.sheetjs.com/xlsx-latest/xlsx-latest.tgz
|
||||
```
|
||||
|
||||
Save the following script to `snippet.js` and run `node snippet.js`:
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
|
||||
(async() => {
|
||||
/* fetch JSON data and parse */
|
||||
const url = "https://sheetjs.com/executive.json";
|
||||
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.xlsb */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
})();
|
||||
```
|
||||
|
||||
Native `fetch` support was added in NodeJS 18. For older versions of NodeJS,
|
||||
the script will throw an error `fetch is not defined`. A third-party library
|
||||
like `axios` presents a similar API for fetching data:
|
||||
|
||||
<details><summary><b>Example using axios</b> (click to show)</summary>
|
||||
|
||||
Install the dependencies:
|
||||
|
||||
```bash
|
||||
$ npm i --save https://cdn.sheetjs.com/xlsx-latest/xlsx-latest.tgz
|
||||
```
|
||||
|
||||
The differences in the script are highlighted below.
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
// highlight-next-line
|
||||
const axios = require("axios");
|
||||
|
||||
(async() => {
|
||||
/* fetch JSON data and parse */
|
||||
const url = "https://sheetjs.com/executive.json";
|
||||
// highlight-next-line
|
||||
const raw_data = (await axios(url, {responseType: "json"})).data;
|
||||
|
||||
/* 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.xlsb */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
})();
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
</TabItem>
|
||||
<TabItem value="deno" label="Deno">
|
||||
|
||||
Save the following script to `snippet.ts` and run with
|
||||
`deno run --allow-net --allow-write snippet.ts`:
|
||||
|
||||
```js
|
||||
// @deno-types="https://cdn.sheetjs.com/xlsx-latest/package/types/index.d.ts"
|
||||
import * as XLSX from 'https://cdn.sheetjs.com/xlsx-latest/package/xlsx.mjs';
|
||||
|
||||
/* fetch JSON data and parse */
|
||||
const url = "https://sheetjs.com/executive.json";
|
||||
const raw_data = await (await fetch(url)).json();
|
||||
|
||||
/* filter for the Presidents */
|
||||
const prez = raw_data.filter((row: any) => row.terms.some((term: any) => term.type === "prez"));
|
||||
|
||||
/* flatten objects */
|
||||
const rows = prez.map((row: any) => ({
|
||||
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: number, r: any) => Math.max(w, r.name.length), 10);
|
||||
worksheet["!cols"] = [ { wch: max_width } ];
|
||||
|
||||
/* create an XLSX file and try to save to Presidents.xlsb */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsb");
|
||||
```
|
||||
|
||||
</TabItem>
|
||||
</Tabs>
|
67
docz/docs/04-getting-started/01-roadmap.md
Normal file
67
docz/docs/04-getting-started/01-roadmap.md
Normal file
@ -0,0 +1,67 @@
|
||||
---
|
||||
sidebar_position: 1
|
||||
---
|
||||
|
||||
# Roadmap
|
||||
|
||||
Most scenarios involving spreadsheets and data can be divided into 5 parts:
|
||||
|
||||
1) **Acquire Data**: Data may be stored anywhere: local or remote files,
|
||||
databases, HTML TABLE, or even generated programmatically in the web browser.
|
||||
|
||||
2) **Extract Data**: For spreadsheet files, this involves parsing raw bytes to
|
||||
read the cell data. For general JS data, this involves reshaping the data.
|
||||
|
||||
3) **Process Data**: From generating summary statistics to cleaning data
|
||||
records, this step is the heart of the problem.
|
||||
|
||||
4) **Package Data**: This can involve making a new spreadsheet or serializing
|
||||
with `JSON.stringify` or writing XML or simply flattening data for UI tools.
|
||||
|
||||
5) **Release Data**: Spreadsheet files can be uploaded to a server or written
|
||||
locally. Data can be presented to users in an HTML TABLE or data grid.
|
||||
|
||||
A common problem involves generating a valid spreadsheet export from data stored
|
||||
in an HTML table. In this example, an HTML TABLE on the page will be scraped,
|
||||
a row will be added to the bottom with the date of the report, and a new file
|
||||
will be generated and downloaded locally. `XLSX.writeFile` takes care of
|
||||
packaging the data and attempting a local download:
|
||||
|
||||
```js
|
||||
// Acquire Data (reference to the HTML table)
|
||||
var table_elt = document.getElementById("my-table-id");
|
||||
|
||||
// Extract Data (create a workbook object from the table)
|
||||
var workbook = XLSX.utils.table_to_book(table_elt);
|
||||
|
||||
// Process Data (add a new row)
|
||||
var ws = workbook.Sheets["Sheet1"];
|
||||
XLSX.utils.sheet_add_aoa(ws, [["Created "+new Date().toISOString()]], {origin:-1});
|
||||
|
||||
// Package and Release Data (`writeFile` tries to write and save an XLSB file)
|
||||
XLSX.writeFile(workbook, "Report.xlsb");
|
||||
```
|
||||
|
||||
This library tries to simplify steps 2 and 4 with functions to extract useful
|
||||
data from spreadsheet files (`read` / `readFile`) and generate new spreadsheet
|
||||
files from data (`write` / `writeFile`). Additional utility functions like
|
||||
`table_to_book` work with other common data sources like HTML tables.
|
||||
|
||||
This documentation and various demo projects cover a number of common scenarios
|
||||
and approaches for steps 1 and 5.
|
||||
|
||||
Utility functions help with step 3.
|
||||
|
||||
## Highlights
|
||||
|
||||
["Data Import"](../solutions/input) describes solutions for common data import
|
||||
scenarios.
|
||||
|
||||
["Data Export"](../solutions/output) describes solutions for common data export
|
||||
scenarios.
|
||||
|
||||
["Data Processing"](../solutions/processing) describes solutions for common
|
||||
workbook processing and manipulation scenarios.
|
||||
|
||||
["Utility Functions"](../api/utilities) details utility functions for
|
||||
translating JSON Arrays and other common JS structures into worksheet objects.
|
37
docz/docs/04-getting-started/02-zen.md
Normal file
37
docz/docs/04-getting-started/02-zen.md
Normal file
@ -0,0 +1,37 @@
|
||||
---
|
||||
sidebar_position: 2
|
||||
hide_table_of_contents: true
|
||||
---
|
||||
|
||||
# Zen of SheetJS
|
||||
|
||||
SheetJS design and development is guided by a few key principles.
|
||||
|
||||
### Data processing should fit in any workflow
|
||||
|
||||
The library does not impose a separate lifecycle. It fits nicely in websites
|
||||
and apps built using any framework. The plain JS data objects play nice with
|
||||
Web Workers and future APIs.
|
||||
|
||||
### JavaScript is a powerful language for data processing
|
||||
|
||||
The ["Common Spreadsheet Format"](../csf/general) is a simple object
|
||||
representation of the core concepts of a workbook. The various functions in the
|
||||
library provide low-level tools for working with the object.
|
||||
|
||||
For friendly JS processing, there are utility functions for converting parts of
|
||||
a worksheet to/from an Array of Arrays. The [Complete example](../03-example.mdx)
|
||||
combines powerful JS Array methods with a network request library to download
|
||||
data, select the information we want and create a workbook file:
|
||||
|
||||
### File formats are implementation details
|
||||
|
||||
The parser covers a wide gamut of common spreadsheet file formats to ensure that
|
||||
"HTML-saved-as-XLS" files work as well as actual XLS or XLSX files.
|
||||
|
||||
The writer supports a number of common output formats for broad compatibility
|
||||
with the data ecosystem.
|
||||
|
||||
To the greatest extent possible, data processing code should not have to worry
|
||||
about the specific file formats involved.
|
||||
|
50
docz/docs/04-getting-started/03-demos.md
Normal file
50
docz/docs/04-getting-started/03-demos.md
Normal file
@ -0,0 +1,50 @@
|
||||
---
|
||||
sidebar_position: 3
|
||||
hide_table_of_contents: true
|
||||
---
|
||||
|
||||
# Demo Projects
|
||||
|
||||
The demo projects include small runnable examples and short explainers.
|
||||
|
||||
### Frameworks and APIs
|
||||
|
||||
- [`Angular.JS`](https://github.com/SheetJS/SheetJS/tree/master/demos/angular/)
|
||||
- [`Angular 2+ and Ionic`](https://github.com/SheetJS/SheetJS/tree/master/demos/angular2/)
|
||||
- [`Knockout`](https://github.com/SheetJS/SheetJS/tree/master/demos/knockout/)
|
||||
- [`Meteor`](https://github.com/SheetJS/SheetJS/tree/master/demos/meteor/)
|
||||
- [`React, React Native and NextJS`](https://github.com/SheetJS/SheetJS/tree/master/demos/react/)
|
||||
- [`VueJS, WeeX, and NuxtJS`](https://github.com/SheetJS/SheetJS/tree/master/demos/vue/)
|
||||
- [`XMLHttpRequest and fetch`](https://github.com/SheetJS/SheetJS/tree/master/demos/xhr/)
|
||||
- [`NodeJS Server-Side Processing`](https://github.com/SheetJS/SheetJS/tree/master/demos/server/)
|
||||
- [`Databases and Key/Value Stores`](https://github.com/SheetJS/SheetJS/tree/master/demos/database/)
|
||||
- [`Typed Arrays and Math`](https://github.com/SheetJS/SheetJS/tree/master/demos/array/)
|
||||
|
||||
### Front-End UI Components
|
||||
|
||||
- [`canvas-datagrid`](https://github.com/SheetJS/SheetJS/tree/master/demos/datagrid/)
|
||||
- [`x-spreadsheet`](https://github.com/SheetJS/SheetJS/tree/master/demos/xspreadsheet/)
|
||||
- [`react-data-grid`](https://github.com/SheetJS/SheetJS/tree/master/demos/react/modify/)
|
||||
- [`vue3-table-light`](https://github.com/SheetJS/SheetJS/tree/master/demos/vue/modify/)
|
||||
|
||||
### Platforms and Integrations
|
||||
- [`Deno`](https://github.com/SheetJS/SheetJS/tree/master/demos/deno/)
|
||||
- [`Electron`](https://github.com/SheetJS/SheetJS/tree/master/demos/electron/)
|
||||
- [`NW.js`](https://github.com/SheetJS/SheetJS/tree/master/demos/nwjs/)
|
||||
- [`Chrome / Chromium Extension`](https://github.com/SheetJS/SheetJS/tree/master/demos/chrome/)
|
||||
- [`Google Sheet export`](https://github.com/SheetJS/SheetJS/tree/master/demos/google-sheet/)
|
||||
- [`ExtendScript for Adobe Apps`](https://github.com/SheetJS/SheetJS/tree/master/demos/extendscript/)
|
||||
- [`Headless Browsers`](https://github.com/SheetJS/SheetJS/tree/master/demos/headless/)
|
||||
- [`Other JavaScript Engines`](https://github.com/SheetJS/SheetJS/tree/master/demos/altjs/)
|
||||
- [`"serverless" functions`](https://github.com/SheetJS/SheetJS/tree/master/demos/function/)
|
||||
- [`Legacy Internet Explorer`](https://github.com/SheetJS/SheetJS/tree/master/demos/oldie/)
|
||||
|
||||
### Bundlers and Tooling
|
||||
- [`browserify`](https://github.com/SheetJS/SheetJS/tree/master/demos/browserify/)
|
||||
- [`fusebox`](https://github.com/SheetJS/SheetJS/tree/master/demos/fusebox/)
|
||||
- [`parcel`](https://github.com/SheetJS/SheetJS/tree/master/demos/parcel/)
|
||||
- [`requirejs`](https://github.com/SheetJS/SheetJS/tree/master/demos/requirejs/)
|
||||
- [`rollup`](https://github.com/SheetJS/SheetJS/tree/master/demos/rollup/)
|
||||
- [`systemjs`](https://github.com/SheetJS/SheetJS/tree/master/demos/systemjs/)
|
||||
- [`typescript`](https://github.com/SheetJS/SheetJS/tree/master/demos/typescript/)
|
||||
- [`webpack 2.x`](https://github.com/SheetJS/SheetJS/tree/master/demos/webpack/)
|
4
docz/docs/04-getting-started/_category_.json
Normal file
4
docz/docs/04-getting-started/_category_.json
Normal file
@ -0,0 +1,4 @@
|
||||
{
|
||||
"label": "Getting Started",
|
||||
"position": 4
|
||||
}
|
BIN
docz/docs/04-getting-started/img/docsVersionDropdown.png
Normal file
BIN
docz/docs/04-getting-started/img/docsVersionDropdown.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 25 KiB |
BIN
docz/docs/04-getting-started/img/localeDropdown.png
Normal file
BIN
docz/docs/04-getting-started/img/localeDropdown.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 27 KiB |
70
docz/docs/05-interface.md
Normal file
70
docz/docs/05-interface.md
Normal file
@ -0,0 +1,70 @@
|
||||
---
|
||||
sidebar_position: 5
|
||||
---
|
||||
|
||||
# Interface Summary
|
||||
|
||||
`XLSX` is the exposed variable in the browser and the exported node variable
|
||||
|
||||
`XLSX.version` is the version of the library (added by the build script).
|
||||
|
||||
`XLSX.SSF` is an embedded version of the [format library](https://github.com/SheetJS/ssf).
|
||||
|
||||
## Parsing functions
|
||||
|
||||
`XLSX.read(data, read_opts)` attempts to parse `data`.
|
||||
|
||||
`XLSX.readFile(filename, read_opts)` attempts to read `filename` and parse.
|
||||
|
||||
Parse options are described in the [Parsing Options](./api/parse-options) section.
|
||||
|
||||
## Writing functions
|
||||
|
||||
`XLSX.write(wb, write_opts)` attempts to write the workbook `wb`
|
||||
|
||||
`XLSX.writeFile(wb, filename, write_opts)` attempts to write `wb` to `filename`.
|
||||
In browser-based environments, it will attempt to force a client-side download.
|
||||
|
||||
`XLSX.writeFileAsync(filename, wb, o, cb)` attempts to write `wb` to `filename`.
|
||||
If `o` is omitted, the writer will use the third argument as the callback.
|
||||
|
||||
`XLSX.stream` contains a set of streaming write functions.
|
||||
|
||||
Write options are described in the [Writing Options](./api/write-options) section.
|
||||
|
||||
## Utilities
|
||||
|
||||
Utilities are available in the `XLSX.utils` object and are described in the
|
||||
[Utility Functions](./api/utilities) section:
|
||||
|
||||
**Constructing:**
|
||||
|
||||
- `book_new` creates an empty workbook
|
||||
- `book_append_sheet` adds a worksheet to a workbook
|
||||
|
||||
**Importing:**
|
||||
|
||||
- `aoa_to_sheet` converts an array of arrays of JS data to a worksheet.
|
||||
- `json_to_sheet` converts an array of JS objects to a worksheet.
|
||||
- `table_to_sheet` converts a DOM TABLE element to a worksheet.
|
||||
- `sheet_add_aoa` adds an array of arrays of JS data to an existing worksheet.
|
||||
- `sheet_add_json` adds an array of JS objects to an existing worksheet.
|
||||
|
||||
|
||||
**Exporting:**
|
||||
|
||||
- `sheet_to_json` converts a worksheet object to an array of JSON objects.
|
||||
- `sheet_to_csv` generates delimiter-separated-values output.
|
||||
- `sheet_to_txt` generates UTF16 formatted text.
|
||||
- `sheet_to_html` generates HTML output.
|
||||
- `sheet_to_formulae` generates a list of the formulae (with value fallbacks).
|
||||
|
||||
|
||||
**Cell and cell address manipulation:**
|
||||
|
||||
- `format_cell` generates the text value for a cell (using number formats).
|
||||
- `encode_row / decode_row` converts between 0-indexed rows and 1-indexed rows.
|
||||
- `encode_col / decode_col` converts between 0-indexed columns and column names.
|
||||
- `encode_cell / decode_cell` converts cell addresses.
|
||||
- `encode_range / decode_range` converts cell ranges.
|
||||
|
782
docz/docs/06-solutions/01-input.md
Normal file
782
docz/docs/06-solutions/01-input.md
Normal file
@ -0,0 +1,782 @@
|
||||
---
|
||||
sidebar_position: 1
|
||||
---
|
||||
|
||||
# Data Import
|
||||
|
||||
## Parsing Workbooks
|
||||
|
||||
#### API
|
||||
|
||||
_Extract data from spreadsheet bytes_
|
||||
|
||||
```js
|
||||
var workbook = XLSX.read(data, opts);
|
||||
```
|
||||
|
||||
The `read` method can extract data from spreadsheet bytes stored in a JS string,
|
||||
"binary string", NodeJS buffer or typed array (`Uint8Array` or `ArrayBuffer`).
|
||||
|
||||
|
||||
_Read spreadsheet bytes from a local file and extract data_
|
||||
|
||||
```js
|
||||
var workbook = XLSX.readFile(filename, opts);
|
||||
```
|
||||
|
||||
The `readFile` method attempts to read a spreadsheet file at the supplied path.
|
||||
Browsers generally do not allow reading files in this way (it is deemed a
|
||||
security risk), and attempts to read files in this way will throw an error.
|
||||
|
||||
The second `opts` argument is optional. ["Parsing Options"](../api/parse-options)
|
||||
covers the supported properties and behaviors.
|
||||
|
||||
#### Examples
|
||||
|
||||
Here are a few common scenarios (click on each subtitle to see the code):
|
||||
|
||||
<details>
|
||||
<summary><b>Local file in a NodeJS server</b> (click to show)</summary>
|
||||
|
||||
`readFile` uses `fs.readFileSync` under the hood:
|
||||
|
||||
```js
|
||||
var XLSX = require("xlsx");
|
||||
|
||||
var workbook = XLSX.readFile("test.xlsx");
|
||||
```
|
||||
|
||||
For Node ESM, the `readFile` helper is not enabled. Instead, `fs.readFileSync`
|
||||
should be used to read the file data as a `Buffer` for use with `XLSX.read`:
|
||||
|
||||
```js
|
||||
import { readFileSync } from "fs";
|
||||
import { read } from "xlsx/xlsx.mjs";
|
||||
|
||||
const buf = readFileSync("test.xlsx");
|
||||
/* buf is a Buffer */
|
||||
const workbook = read(buf);
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Local file in a Deno application</b> (click to show)</summary>
|
||||
|
||||
`readFile` uses `Deno.readFileSync` under the hood:
|
||||
|
||||
```js
|
||||
// @deno-types="https://deno.land/x/sheetjs/types/index.d.ts"
|
||||
import * as XLSX from 'https://deno.land/x/sheetjs/xlsx.mjs'
|
||||
|
||||
const workbook = XLSX.readFile("test.xlsx");
|
||||
```
|
||||
|
||||
Applications reading files must be invoked with the `--allow-read` flag. The
|
||||
[`deno` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/deno/) has more examples
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>User-submitted file in a web page ("Drag-and-Drop")</b> (click to show)</summary>
|
||||
|
||||
For modern websites targeting Chrome 76+, `File#arrayBuffer` is recommended:
|
||||
|
||||
```js
|
||||
// XLSX is a global from the standalone script
|
||||
|
||||
async function handleDropAsync(e) {
|
||||
e.stopPropagation(); e.preventDefault();
|
||||
const f = e.dataTransfer.files[0];
|
||||
/* f is a File */
|
||||
const data = await f.arrayBuffer();
|
||||
/* data is an ArrayBuffer */
|
||||
const workbook = XLSX.read(data);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
}
|
||||
drop_dom_element.addEventListener("drop", handleDropAsync, false);
|
||||
```
|
||||
|
||||
For maximal compatibility, the `FileReader` API should be used:
|
||||
|
||||
```js
|
||||
function handleDrop(e) {
|
||||
e.stopPropagation(); e.preventDefault();
|
||||
var f = e.dataTransfer.files[0];
|
||||
/* f is a File */
|
||||
var reader = new FileReader();
|
||||
reader.onload = function(e) {
|
||||
var data = e.target.result;
|
||||
/* reader.readAsArrayBuffer(file) -> data will be an ArrayBuffer */
|
||||
var workbook = XLSX.read(data);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
};
|
||||
reader.readAsArrayBuffer(f);
|
||||
}
|
||||
drop_dom_element.addEventListener("drop", handleDrop, false);
|
||||
```
|
||||
|
||||
<https://oss.sheetjs.com/sheetjs/> demonstrates the FileReader technique.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>User-submitted file with an HTML INPUT element</b> (click to show)</summary>
|
||||
|
||||
Starting with an HTML INPUT element with `type="file"`:
|
||||
|
||||
```html
|
||||
<input type="file" id="input_dom_element">
|
||||
```
|
||||
|
||||
For modern websites targeting Chrome 76+, `Blob#arrayBuffer` is recommended:
|
||||
|
||||
```js
|
||||
// XLSX is a global from the standalone script
|
||||
|
||||
async function handleFileAsync(e) {
|
||||
const file = e.target.files[0];
|
||||
const data = await file.arrayBuffer();
|
||||
/* data is an ArrayBuffer */
|
||||
const workbook = XLSX.read(data);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
}
|
||||
input_dom_element.addEventListener("change", handleFileAsync, false);
|
||||
```
|
||||
|
||||
For broader support (including IE10+), the `FileReader` approach is recommended:
|
||||
|
||||
```js
|
||||
function handleFile(e) {
|
||||
var file = e.target.files[0];
|
||||
var reader = new FileReader();
|
||||
reader.onload = function(e) {
|
||||
var data = e.target.result;
|
||||
/* reader.readAsArrayBuffer(file) -> data will be an ArrayBuffer */
|
||||
var workbook = XLSX.read(e.target.result);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
};
|
||||
reader.readAsArrayBuffer(file);
|
||||
}
|
||||
input_dom_element.addEventListener("change", handleFile, false);
|
||||
```
|
||||
|
||||
The [`oldie` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/oldie/) shows an IE-compatible fallback scenario.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Fetching a file in the web browser ("Ajax")</b> (click to show)</summary>
|
||||
|
||||
For modern websites targeting Chrome 42+, `fetch` is recommended:
|
||||
|
||||
```js
|
||||
// XLSX is a global from the standalone script
|
||||
|
||||
(async() => {
|
||||
const url = "http://oss.sheetjs.com/test_files/formula_stress_test.xlsx";
|
||||
const data = await (await fetch(url)).arrayBuffer();
|
||||
/* data is an ArrayBuffer */
|
||||
const workbook = XLSX.read(data);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
})();
|
||||
```
|
||||
|
||||
For broader support, the `XMLHttpRequest` approach is recommended:
|
||||
|
||||
```js
|
||||
var url = "http://oss.sheetjs.com/test_files/formula_stress_test.xlsx";
|
||||
|
||||
/* set up async GET request */
|
||||
var req = new XMLHttpRequest();
|
||||
req.open("GET", url, true);
|
||||
req.responseType = "arraybuffer";
|
||||
|
||||
req.onload = function(e) {
|
||||
var workbook = XLSX.read(req.response);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
};
|
||||
|
||||
req.send();
|
||||
```
|
||||
|
||||
The [`xhr` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/xhr/) includes a longer discussion and more examples.
|
||||
|
||||
<http://oss.sheetjs.com/sheetjs/ajax.html> shows fallback approaches for IE6+.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Local file in a PhotoShop or InDesign plugin</b> (click to show)</summary>
|
||||
|
||||
`readFile` wraps the `File` logic in Photoshop and other ExtendScript targets.
|
||||
The specified path should be an absolute path:
|
||||
|
||||
```js
|
||||
#include "xlsx.extendscript.js"
|
||||
|
||||
/* Read test.xlsx from the Documents folder */
|
||||
var workbook = XLSX.readFile(Folder.myDocuments + "/test.xlsx");
|
||||
```
|
||||
|
||||
The [`extendscript` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/extendscript/) includes a more complex example.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Local file in an Electron app</b> (click to show)</summary>
|
||||
|
||||
`readFile` can be used in the renderer process:
|
||||
|
||||
```js
|
||||
/* From the renderer process */
|
||||
var XLSX = require("xlsx");
|
||||
|
||||
var workbook = XLSX.readFile(path);
|
||||
```
|
||||
|
||||
Electron APIs have changed over time. The [`electron` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/electron/)
|
||||
shows a complete example and details the required version-specific settings.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Local file in a mobile app with React Native</b> (click to show)</summary>
|
||||
|
||||
The [`react` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/react) includes a sample React Native app.
|
||||
|
||||
Since React Native does not provide a way to read files from the filesystem, a
|
||||
third-party library must be used. The following libraries have been tested:
|
||||
|
||||
- [`react-native-file-access`](https://npm.im/react-native-file-access)
|
||||
|
||||
The `base64` encoding returns strings compatible with the `base64` type:
|
||||
|
||||
```js
|
||||
import XLSX from "xlsx";
|
||||
import { FileSystem } from "react-native-file-access";
|
||||
|
||||
const b64 = await FileSystem.readFile(path, "base64");
|
||||
/* b64 is a base64 string */
|
||||
const workbook = XLSX.read(b64, {type: "base64"});
|
||||
```
|
||||
|
||||
- [`react-native-fs`](https://npm.im/react-native-fs)
|
||||
|
||||
The `ascii` encoding returns binary strings compatible with the `binary` type:
|
||||
|
||||
```js
|
||||
import XLSX from "xlsx";
|
||||
import { readFile } from "react-native-fs";
|
||||
|
||||
const bstr = await readFile(path, "ascii");
|
||||
/* bstr is a binary string */
|
||||
const workbook = XLSX.read(bstr, {type: "binary"});
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>NodeJS Server File Uploads</b> (click to show)</summary>
|
||||
|
||||
`read` can accept a NodeJS buffer. `readFile` can read files generated by a
|
||||
HTTP POST request body parser like [`formidable`](https://npm.im/formidable):
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
const http = require("http");
|
||||
const formidable = require("formidable");
|
||||
|
||||
const server = http.createServer((req, res) => {
|
||||
const form = new formidable.IncomingForm();
|
||||
form.parse(req, (err, fields, files) => {
|
||||
/* grab the first file */
|
||||
const f = Object.entries(files)[0][1];
|
||||
const path = f.filepath;
|
||||
const workbook = XLSX.readFile(path);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
});
|
||||
}).listen(process.env.PORT || 7262);
|
||||
```
|
||||
|
||||
The [`server` demo](https://github.com/SheetJS/SheetJS/tree/master/demos/server) has more advanced examples.
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Download files in a NodeJS process</b> (click to show)</summary>
|
||||
|
||||
Node 17.5 and 18.0 have native support for fetch:
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
|
||||
const data = await (await fetch(url)).arrayBuffer();
|
||||
/* data is an ArrayBuffer */
|
||||
const workbook = XLSX.read(data);
|
||||
```
|
||||
|
||||
For broader compatibility, third-party modules are recommended.
|
||||
|
||||
[`request`](https://npm.im/request) requires a `null` encoding to yield Buffers:
|
||||
|
||||
```js
|
||||
var XLSX = require("xlsx");
|
||||
var request = require("request");
|
||||
|
||||
request({url: url, encoding: null}, function(err, resp, body) {
|
||||
var workbook = XLSX.read(body);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
});
|
||||
```
|
||||
|
||||
[`axios`](https://npm.im/axios) works the same way in browser and in NodeJS:
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
const axios = require("axios");
|
||||
|
||||
(async() => {
|
||||
const res = await axios.get(url, {responseType: "arraybuffer"});
|
||||
/* res.data is a Buffer */
|
||||
const workbook = XLSX.read(res.data);
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
})();
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Download files in an Electron app</b> (click to show)</summary>
|
||||
|
||||
The `net` module in the main process can make HTTP/HTTPS requests to external
|
||||
resources. Responses should be manually concatenated using `Buffer.concat`:
|
||||
|
||||
```js
|
||||
const XLSX = require("xlsx");
|
||||
const { net } = require("electron");
|
||||
|
||||
const req = net.request(url);
|
||||
req.on("response", (res) => {
|
||||
const bufs = []; // this array will collect all of the buffers
|
||||
res.on("data", (chunk) => { bufs.push(chunk); });
|
||||
res.on("end", () => {
|
||||
const workbook = XLSX.read(Buffer.concat(bufs));
|
||||
|
||||
/* DO SOMETHING WITH workbook HERE */
|
||||
});
|
||||
});
|
||||
req.end();
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>Readable Streams in NodeJS</b> (click to show)</summary>
|
||||
|
||||
When dealing with Readable Streams, the easiest approach is to buffer the stream
|
||||
and process the whole thing at the end:
|
||||
|
||||
```js
|
||||
var fs = require("fs");
|
||||
var XLSX = require("xlsx");
|
||||
|
||||
function process_RS(stream, cb) {
|
||||
var buffers = [];
|
||||
stream.on("data", function(data) { buffers.push(data); });
|
||||
stream.on("end", function() {
|
||||
var buffer = Buffer.concat(buffers);
|
||||
var workbook = XLSX.read(buffer, {type:"buffer"});
|
||||
|
||||
/* DO SOMETHING WITH workbook IN THE CALLBACK */
|
||||
cb(workbook);
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><b>ReadableStream in the browser</b> (click to show)</summary>
|
||||
|
||||
When dealing with `ReadableStream`, the easiest approach is to buffer the stream
|
||||
and process the whole thing at the end:
|
||||
|
||||
```js
|
||||
// XLSX is a global from the standalone script
|
||||
|
||||
async function process_RS(stream) {
|
||||
/* collect data */
|
||||
const buffers = [];
|
||||
const reader = stream.getReader();
|
||||
for(;;) {
|
||||
const res = await reader.read();
|
||||
if(res.value) buffers.push(res.value);
|
||||
if(res.done) break;
|
||||
}
|
||||
|
||||
/* concat */
|
||||
const out = new Uint8Array(buffers.reduce((acc, v) => acc + v.length, 0));
|
||||
|