forked from sheetjs/docs.sheetjs.com
		
	Command-Line testing grid
This commit is contained in:
		
							parent
							
								
									945e5f02eb
								
							
						
					
					
						commit
						1a80a55e76
					
				
							
								
								
									
										14
									
								
								docz/data/cli.js
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										14
									
								
								docz/data/cli.js
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,14 @@ | ||||
| import { read, utils } from 'xlsx'; | ||||
| import url from './cli.xls'; | ||||
| import React, { useEffect, useState } from 'react'; | ||||
| 
 | ||||
| const FrameworkData = () => { | ||||
|   const [fw, setFW] = useState(""); | ||||
| 
 | ||||
|   useEffect(() => { (async() => { | ||||
|     const wb = read(await (await fetch(url)).arrayBuffer(), { dense: true }); | ||||
|     setFW(utils.sheet_to_html(wb.Sheets["Frameworks"])); | ||||
|   })(); }, []); | ||||
|   return ( <div dangerouslySetInnerHTML={{__html: fw}}/> ); | ||||
| }; | ||||
| export default FrameworkData; | ||||
							
								
								
									
										124
									
								
								docz/data/cli.xls
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										124
									
								
								docz/data/cli.xls
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,124 @@ | ||||
| <?xml version="1.0"?> | ||||
| <?mso-application progid="Excel.Sheet"?> | ||||
| <Workbook xmlns="urn:schemas-microsoft-com:office:spreadsheet" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet" xmlns:html="http://www.w3.org/TR/REC-html40"> | ||||
|  <ExcelWorkbook xmlns="urn:schemas-microsoft-com:office:excel"> | ||||
|   <WindowHeight>10620</WindowHeight> | ||||
|   <WindowWidth>11020</WindowWidth> | ||||
|   <WindowTopX>2260</WindowTopX> | ||||
|   <WindowTopY>19600</WindowTopY> | ||||
|   <ActiveSheet>1</ActiveSheet> | ||||
|   <ProtectStructure>False</ProtectStructure> | ||||
|   <ProtectWindows>False</ProtectWindows> | ||||
|  </ExcelWorkbook> | ||||
|  <Styles> | ||||
|   <Style ss:ID="Default" ss:Name="Normal"> | ||||
|    <Alignment ss:Vertical="Bottom"/> | ||||
|    <Borders/> | ||||
|    <Font ss:FontName="Calibri" x:Family="Swiss" ss:Size="12" ss:Color="#000000"/> | ||||
|    <Interior/> | ||||
|    <NumberFormat/> | ||||
|    <Protection/> | ||||
|   </Style> | ||||
|   <Style ss:ID="s16"> | ||||
|    <Font ss:FontName="Calibri" x:Family="Swiss" ss:Size="12" ss:Color="#1C1E21"/> | ||||
|   </Style> | ||||
|   <Style ss:ID="s17"> | ||||
|    <Font ss:FontName="Calibri" x:Family="Swiss" ss:Size="12" ss:Color="#000000" ss:Bold="1"/> | ||||
|   </Style> | ||||
|   <Style ss:ID="s19"> | ||||
|    <Alignment ss:Horizontal="Center" ss:Vertical="Bottom"/> | ||||
|    <Font ss:FontName="Calibri" x:Family="Swiss" ss:Size="12" ss:Color="#000000" ss:Bold="1"/> | ||||
|   </Style> | ||||
|   <Style ss:ID="s20"> | ||||
|    <Font ss:FontName="Calibri" x:Family="Swiss" ss:Size="12" ss:Color="#467886" ss:Underline="Single"/> | ||||
|   </Style> | ||||
|  </Styles> | ||||
|  <Worksheet ss:Name="Frameworks"> | ||||
|   <Table ss:ExpandedColumnCount="7" ss:ExpandedRowCount="10" x:FullColumns="1" x:FullRows="1" ss:DefaultColumnWidth="65" ss:DefaultRowHeight="16"> | ||||
|    <Column ss:Index="2" ss:Width="24"/> | ||||
|    <Column ss:Width="31"/> | ||||
|    <Column ss:Width="24"/> | ||||
|    <Column ss:Width="31"/> | ||||
|    <Column ss:Width="24"/> | ||||
|    <Column ss:Width="31"/> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:MergeAcross="1" ss:StyleID="s19"><Data ss:Type="String">MacOS</Data></Cell> | ||||
|     <Cell ss:MergeAcross="1" ss:StyleID="s19"><Data ss:Type="String">Windows</Data></Cell> | ||||
|     <Cell ss:MergeAcross="1" ss:StyleID="s19"><Data ss:Type="String">Linux</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">Framework</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">x64</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">ARM</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">x64</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">ARM</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">x64</Data></Cell> | ||||
|     <Cell ss:StyleID="s17"><Data ss:Type="String">ARM</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/nexe"><Data ss:Type="String">nexe</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/boxednode"><Data ss:Type="String">boxednode</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/pkg"><Data ss:Type="String">pkg</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/nodesea#complete-example"><Data ss:Type="String">NodeJS SEA</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/bunsea#complete-example"><Data ss:Type="String">Bun SEA</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String"></Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/cli/denosea#complete-example"><Data ss:Type="String">Deno SEA</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|    </Row> | ||||
|    <Row> | ||||
|     <Cell ss:StyleID="s20" ss:HRef="/docs/demos/engines/v8#snapshots"><Data ss:Type="String">V8 Engine</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|     <Cell ss:StyleID="s16"><Data ss:Type="String">✔</Data></Cell> | ||||
|    </Row> | ||||
|   </Table> | ||||
|  </Worksheet> | ||||
| </Workbook> | ||||
							
								
								
									
										187
									
								
								docz/docs/03-demos/20-cli/03-nexe.md
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										187
									
								
								docz/docs/03-demos/20-cli/03-nexe.md
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,187 @@ | ||||
| --- | ||||
| title: Spreadsheet Tools with Nexe | ||||
| sidebar_label: nexe | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| sidebar_custom_props: | ||||
|   summary: Prebuilt NodeJS packages | ||||
| --- | ||||
| 
 | ||||
| import current from '/version.js'; | ||||
| import Tabs from '@theme/Tabs'; | ||||
| import TabItem from '@theme/TabItem'; | ||||
| import CodeBlock from '@theme/CodeBlock'; | ||||
| 
 | ||||
| export const r = {style: {color:"red"}}; | ||||
| export const B = {style: {fontWeight:"bold"}}; | ||||
| 
 | ||||
| `nexe`[^1] is a tool for generating command-line tools that embed scripts. | ||||
| 
 | ||||
| [SheetJS](https://sheetjs.com) is a JavaScript library for reading and writing | ||||
| data from spreadsheets. | ||||
| 
 | ||||
| This demo uses `nexe` and SheetJS to create a standalone CLI tool for parsing | ||||
| spreadsheets and converting to other formats. | ||||
| 
 | ||||
| :::info pass | ||||
| 
 | ||||
| The latest prebuilt package matches NodeJS version `14.15.3`. | ||||
| 
 | ||||
| `nexe` can build the required packages for newer NodeJS versions. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | Version      | NodeJS    | Source    | Date       | | ||||
| |:-------------|:-------------|:----------|:----------|:-----------| | ||||
| | `darwin-x64` | `4.0.0-rc.6` | `14.15.3` | Pre-built | 2024-05-28 | | ||||
| | `darwin-arm` | `4.0.0-rc.6` | `18.20.3` | Compiled  | 2024-05-25 | | ||||
| | `win10-x64`  | `4.0.0-rc.4` | `14.15.3` | Pre-built | 2024-04-18 | | ||||
| | `win11-arm`  | `4.0.0-rc.6` | `20.10.0` | Compiled  | 2024-05-28 | | ||||
| | `linux-x64`  | `4.0.0-rc.4` | `14.15.3` | Pre-built | 2024-03-21 | | ||||
| | `linux-arm`  | `4.0.0-rc.6` | `18.20.3` | Compiled  | 2024-05-26 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ## Integration Details | ||||
| 
 | ||||
| The [SheetJS NodeJS module](/docs/getting-started/installation/nodejs) can be | ||||
| required from scripts. `nexe` will automatically handle packaging. | ||||
| 
 | ||||
| ### Script Requirements | ||||
| 
 | ||||
| Scripts that exclusively use SheetJS libraries and NodeJS built-in modules can | ||||
| be bundled using `nexe`. | ||||
| 
 | ||||
| The demo script [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) runs in NodeJS. It | ||||
| is a simple command-line tool for reading and writing spreadsheets. | ||||
| 
 | ||||
| ## Complete Example | ||||
| 
 | ||||
| 0) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 1) Download [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| 2) Install the dependencies: | ||||
| 
 | ||||
| <Tabs groupId="pm"> | ||||
|   <TabItem value="npm" label="npm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="pnpm" label="pnpm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="yarn" label="Yarn" default> | ||||
| <CodeBlock language="bash">{`\ | ||||
| yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 3) Create the standalone program: | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe -t 14.15.3 xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| <details open> | ||||
|   <summary><b>Building from source (click to hide)</b></summary> | ||||
| 
 | ||||
| When the demo was tested on ARM targets, the Nexe pre-built packages were | ||||
| missing. For unsupported NodeJS versions, packages must be built from source: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --python=$(which python3) --make="-j8" | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| On Windows x64, the `--build` flag suffices: | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --make="-j8" | ||||
| ``` | ||||
| 
 | ||||
| On Windows ARM, the target `windows-arm64-20.10.0` must be specified: | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --make="-j8" --target=windows-arm64-20.10.0 | ||||
| ``` | ||||
| 
 | ||||
| **`vcbuild.bat` issues** | ||||
| 
 | ||||
| The Windows ARM build may fail with a `vcbuild.bat` error: | ||||
| 
 | ||||
| ``` | ||||
| Error: vcbuild.bat nosign release arm64 exited with code: 1 | ||||
| ``` | ||||
| 
 | ||||
| Pass the `-v` flag for more details. In the most recent test, the error stemmed | ||||
| from a Python version mismatch: | ||||
| 
 | ||||
| ``` | ||||
| Node.js configure: found Python 2.7.18 | ||||
| Please use python3.11 or python3.10 or python3.9 or python3.8 or python3.7 or python3.6 | ||||
| ``` | ||||
| 
 | ||||
| The resolved version of Python can be found with | ||||
| 
 | ||||
| ```cmd | ||||
| where python | ||||
| ``` | ||||
| 
 | ||||
| In the most recent test, a Python 2 version appeared first. This was fixed by | ||||
| finding the Python 3 location and prepending it to `PATH`: | ||||
| 
 | ||||
| ```cmd | ||||
| set PATH="C:\correct\path\to\python\three";%PATH% | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| </details> | ||||
| 
 | ||||
| This generates `xlsx-cli` or `xlsx-cli.exe` depending on platform. | ||||
| 
 | ||||
| 5) Run the generated program, passing `pres.numbers` as the argument: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| ./xlsx-cli pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```powershell | ||||
| .\xlsx-cli.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 
 | ||||
| [^1]: The project does not have a website. The [source repository](https://github.com/nexe/nexe) is publicly available. | ||||
| [^2]: The NodeJS website hosts [prebuilt installers](https://nodejs.org/en/download/prebuilt-installer). | ||||
							
								
								
									
										169
									
								
								docz/docs/03-demos/20-cli/05-pkg.md
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										169
									
								
								docz/docs/03-demos/20-cli/05-pkg.md
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,169 @@ | ||||
| --- | ||||
| title: Packing Sheets with pkg | ||||
| sidebar_label: pkg | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| sidebar_custom_props: | ||||
|   summary: Prebuilt NodeJS packages | ||||
| --- | ||||
| 
 | ||||
| import current from '/version.js'; | ||||
| import Tabs from '@theme/Tabs'; | ||||
| import TabItem from '@theme/TabItem'; | ||||
| import CodeBlock from '@theme/CodeBlock'; | ||||
| 
 | ||||
| export const r = {style: {color:"red"}}; | ||||
| export const B = {style: {fontWeight:"bold"}}; | ||||
| 
 | ||||
| `pkg`[^1] is a tool for generating command-line tools that embed scripts. | ||||
| 
 | ||||
| [SheetJS](https://sheetjs.com) is a JavaScript library for reading and writing | ||||
| data from spreadsheets. | ||||
| 
 | ||||
| This demo uses `pkg` and SheetJS to create a standalone CLI tool for parsing | ||||
| spreadsheets and converting to other formats. | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| With the official release of [NodeJS SEA](/docs/demos/cli/nodesea), Vercel opted | ||||
| to deprecate `pkg`. It is still useful for deploying apps embedding NodeJS v18 | ||||
| or earlier since those versions do not support NodeJS SEA. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | Version | NodeJS   | Date       | | ||||
| |:-------------|:--------|:---------|:-----------| | ||||
| | `darwin-x64` | `5.8.1` | `18.5.0` | 2024-05-28 | | ||||
| | `darwin-arm` | `5.8.1` | `18.5.0` | 2024-05-25 | | ||||
| | `win10-x64`  | `5.8.1` | `18.5.0` | 2024-04-18 | | ||||
| | `win11-arm`  | `5.8.1` | `18.5.0` | 2024-05-28 | | ||||
| | `linux-x64`  | `5.8.1` | `18.5.0` | 2024-03-21 | | ||||
| | `linux-arm`  | `5.8.1` | `18.5.0` | 2024-05-26 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ## Integration Details | ||||
| 
 | ||||
| The [SheetJS NodeJS module](/docs/getting-started/installation/nodejs) can be | ||||
| required from scripts. `pkg` will automatically handle packaging. | ||||
| 
 | ||||
| ### Script Requirements | ||||
| 
 | ||||
| Scripts that exclusively use SheetJS libraries and NodeJS built-in modules can | ||||
| be bundled using `pkg`. | ||||
| 
 | ||||
| The demo script [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) runs in NodeJS. It | ||||
| is a simple command-line tool for reading and writing spreadsheets. | ||||
| 
 | ||||
| ### Limitations | ||||
| 
 | ||||
| :::danger pass | ||||
| 
 | ||||
| When this demo was last tested, `pkg` failed with an error referencing `node20`: | ||||
| 
 | ||||
| ``` | ||||
| > Targets not specified. Assuming: | ||||
|   node20-linux-arm64, node20-macos-arm64, node20-win-arm64 | ||||
| > Error! No available node version satisfies 'node20' | ||||
| ``` | ||||
| 
 | ||||
| **`pkg` does not support NodeJS 20 or 22!** | ||||
| 
 | ||||
| The local NodeJS version must be rolled back to version 18. | ||||
| 
 | ||||
| If `nvm` or `nvm-windows` was used to install NodeJS: | ||||
| 
 | ||||
| ```bash | ||||
| nvm install 18 | ||||
| nvm use 18 | ||||
| ``` | ||||
| 
 | ||||
| Otherwise, on macOS and Linux, `n` can manage the global installation: | ||||
| 
 | ||||
| ```bash | ||||
| sudo npm i -g n | ||||
| sudo n 18 | ||||
| ``` | ||||
| 
 | ||||
| On Windows, it is recommended to use a prebuilt installer[^2] | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 
 | ||||
| ## Complete Example | ||||
| 
 | ||||
| 0) Downgrade NodeJS to major version 18 or earlier. | ||||
| 
 | ||||
| 1) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 2) Download [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| 3) Install the dependencies: | ||||
| 
 | ||||
| <Tabs groupId="pm"> | ||||
|   <TabItem value="npm" label="npm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="pnpm" label="pnpm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="yarn" label="Yarn" default> | ||||
| <CodeBlock language="bash">{`\ | ||||
| yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 4) Create the standalone program: | ||||
| 
 | ||||
| ```bash | ||||
| npx pkg xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| This generates `xlsx-cli-linux`, `xlsx-cli-macos`, and `xlsx-cli-win.exe` . | ||||
| 
 | ||||
| 5) Run the generated program, passing `pres.numbers` as the argument: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="linux" label="Linux"> | ||||
| 
 | ||||
| ```bash | ||||
| ./xlsx-cli-linux pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="macos" label="macOS"> | ||||
| 
 | ||||
| ```bash | ||||
| ./xlsx-cli-macos pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```powershell | ||||
| .\xlsx-cli-win.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 
 | ||||
| [^1]: The project does not have a website. The [source repository](https://github.com/vercel/pkg) is publicly available. | ||||
| [^2]: The NodeJS website hosts [prebuilt installers](https://nodejs.org/en/download/prebuilt-installer). | ||||
							
								
								
									
										214
									
								
								docz/docs/03-demos/20-cli/08-boxednode.md
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										214
									
								
								docz/docs/03-demos/20-cli/08-boxednode.md
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,214 @@ | ||||
| --- | ||||
| title: Sheets in a Box with boxednode | ||||
| sidebar_label: boxednode | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| sidebar_custom_props: | ||||
|   summary: NodeJS binaries with scripts, built from source | ||||
| --- | ||||
| 
 | ||||
| import current from '/version.js'; | ||||
| import Tabs from '@theme/Tabs'; | ||||
| import TabItem from '@theme/TabItem'; | ||||
| import CodeBlock from '@theme/CodeBlock'; | ||||
| 
 | ||||
| export const r = {style: {color:"red"}}; | ||||
| export const B = {style: {fontWeight:"bold"}}; | ||||
| 
 | ||||
| `boxednode`[^1] is a tool for generating command-line tools that embed scripts. | ||||
| It automates the process of building NodeJS from source. | ||||
| 
 | ||||
| [SheetJS](https://sheetjs.com) is a JavaScript library for reading and writing | ||||
| data from spreadsheets. | ||||
| 
 | ||||
| This demo uses `boxednode` and SheetJS to create a standalone CLI tool for | ||||
| parsing spreadsheets and converting to other formats. | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | Version | NodeJS    | Date       | | ||||
| |:-------------|:--------|:----------|:-----------| | ||||
| | `darwin-x64` | `2.4.0` | `22.2.0`  | 2024-05-28 | | ||||
| | `darwin-arm` | `2.4.3` | `22.2.0`  | 2024-05-25 | | ||||
| | `win10-x64`  | `2.4.2` | `16.20.2` | 2024-04-18 | | ||||
| | `linux-x64`  | `2.4.0` | `21.7.1`  | 2024-03-21 | | ||||
| | `linux-arm`  | `2.4.3` | `20.13.1` | 2024-05-26 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ## Integration Details | ||||
| 
 | ||||
| The [SheetJS NodeJS module](/docs/getting-started/installation/nodejs) can be | ||||
| required from scripts. `boxednode` will automatically handle packaging. | ||||
| 
 | ||||
| ### Script Requirements | ||||
| 
 | ||||
| Scripts that exclusively use SheetJS libraries and NodeJS built-in modules can | ||||
| be bundled using `boxednode` | ||||
| 
 | ||||
| The demo script [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) runs in NodeJS. It | ||||
| is a simple command-line tool for reading and writing spreadsheets. | ||||
| 
 | ||||
| ## Complete Example | ||||
| 
 | ||||
| 0) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 1) Download [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| 2) Install the dependencies: | ||||
| 
 | ||||
| <Tabs groupId="pm"> | ||||
|   <TabItem value="npm" label="npm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="pnpm" label="pnpm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="yarn" label="Yarn" default> | ||||
| <CodeBlock language="bash">{`\ | ||||
| yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 3) Create the standalone program: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli | ||||
| ``` | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When this demo was last tested in `linux-arm`, the build failed with an error: | ||||
| 
 | ||||
| <pre> | ||||
| ../deps/v8/src/base/small-vector.h:  In instantiation of <span {...B}>‘class v8::base::SmallVector<std::pair<const v8::internal::compiler::turboshaft::PhiOp*, const v8::internal::compiler::turboshaft::OpIndex>, 16>’</span>: | ||||
| <span {...B}>../deps/v8/src/compiler/turboshaft/loop-unrolling-reducer.h:444:11:</span>   required from here | ||||
| <span {...B}>../deps/v8/src/base/macros.h:206:55:</span> <span style={{...r.style,...B.style}}>error:</span> static assertion failed: T should be trivially copyable | ||||
| {"  206 |"}   static_assert(::v8::base::is_trivially_copyable<T>::<span style={{...r.style,...B.style}}>value</span>, \\ | ||||
| {"      |"}                                                       ^~~~~ | ||||
| </pre> | ||||
| 
 | ||||
| This affects NodeJS `22.2.0`, but does not affect `20.13.1`. It affects the | ||||
| [V8 JavaScript Engine](/docs/demos/engines/v8#build-v8). | ||||
| 
 | ||||
| The `-n` flag controls the target NodeJS version. For this demo, the following | ||||
| command uses NodeJS `20.13.1`: | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli -n 20.13.1 | ||||
| ``` | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli.exe -n 16.20.2 | ||||
| ``` | ||||
| 
 | ||||
| :::info pass | ||||
| 
 | ||||
| The Windows 10 build requires Visual Studio with "Desktop development with C++" | ||||
| workload, Python 3.11, and NASM[^2]. | ||||
| 
 | ||||
| **The build command must be run in "x64 Native Tools Command Prompt"** | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When the demo was last tested, the build failed: | ||||
| 
 | ||||
| ``` | ||||
| Not an executable Python program | ||||
| Could not find Python. | ||||
| ``` | ||||
| 
 | ||||
| By default, Windows aliases `python` to a Microsoft Store installer. If the | ||||
| official installer was used, the alias should be disabled manually: | ||||
| 
 | ||||
| 1) Open Start menu and type "app alias". Click "Manage app execution aliases". | ||||
| 
 | ||||
| 2) Disable the App Installer for all items with `python` in the name. | ||||
| 
 | ||||
| Using Python 3.12, the build fails with an error: | ||||
| 
 | ||||
| ``` | ||||
| Please use python3.11 or python3.10 or python3.9 or python3.8 or python3.7 or python3.6. | ||||
| ``` | ||||
| 
 | ||||
| In the most recent test, Python 3.11.8 was installed from the official site. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When the demo was last tested on Windows, the build failed: | ||||
| 
 | ||||
| ``` | ||||
| error MSB8020: The build tools for Visual Studio 2019 (Platform Toolset = 'v142') cannot be found. To build using the v142 build tools, please install Visual Studio 2019 build tools. | ||||
| ``` | ||||
| 
 | ||||
| This error was fixed by installing the `v142` build tools through the Visual | ||||
| Studio installer. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| In the most recent Windows test against NodeJS `20.8.0`, the build failed due | ||||
| to an issue in the OpenSSL dependency: | ||||
| 
 | ||||
| ``` | ||||
| ...\node-v20.8.0\deps\openssl\openssl\crypto\cversion.c(75,33): error C2153: integer literals must have at least one digit [...\node-v20.8.0\deps\openssl\openssl.vcxproj] | ||||
| ``` | ||||
| 
 | ||||
| SheetJS libraries are compatible with NodeJS versions dating back to `v0.8`. The | ||||
| workaround is to select NodeJS `v16.20.2` using the `-n` flag. This version was | ||||
| was chosen since NodeJS `v18` upgraded the OpenSSL dependency. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 4) Run the generated program, passing `pres.numbers` as the argument: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| ./xlsx-cli pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```powershell | ||||
| .\xlsx-cli.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| [^1]: The project does not have a website. The [source repository](https://github.com/mongodb-js/boxednode) is publicly available. | ||||
| [^2]: Downloads can be found [at the main NASM project website](https://www.nasm.us/) | ||||
| @ -158,7 +158,7 @@ This demo was tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | NodeJS    | Date       | | ||||
| |:-------------|:----------|:-----------| | ||||
| | `darwin-x64` | `20.11.1` | 2024-03-17 | | ||||
| | `darwin-x64` | `22.2.0`  | 2024-05-28 | | ||||
| | `win10-x64`  | `20.12.0` | 2024-03-26 | | ||||
| | `win11-x64`  | `20.13.1` | 2024-05-22 | | ||||
| | `linux-x64`  | `20.11.1` | 2024-03-18 | | ||||
| @ -237,7 +237,7 @@ node sheet2csv.js pres.numbers | ||||
| 
 | ||||
| The script should display CSV contents from the first sheet: | ||||
| 
 | ||||
| ``` | ||||
| ```text title="Expected Output" | ||||
| Name,Index | ||||
| Bill Clinton,42 | ||||
| GeorgeW Bush,43 | ||||
							
								
								
									
										131
									
								
								docz/docs/03-demos/20-cli/12-bunsea.md
									
									
									
									
									
										Normal file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										131
									
								
								docz/docs/03-demos/20-cli/12-bunsea.md
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,131 @@ | ||||
| --- | ||||
| title: BunJS SEA | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| sidebar_custom_props: | ||||
|   summary: BunJS Single-file Executables | ||||
| --- | ||||
| 
 | ||||
| import current from '/version.js'; | ||||
| import CodeBlock from '@theme/CodeBlock'; | ||||
| 
 | ||||
| [BunJS](https://bun.sh/docs/bundler/executables) is a JavaScript runtime with | ||||
| support for compiling scripts into self-contained executables. | ||||
| 
 | ||||
| [SheetJS](https://sheetjs.com) is a JavaScript library for reading and writing | ||||
| data from spreadsheets. | ||||
| 
 | ||||
| This demo uses the Bun compiler and SheetJS to create a standalone CLI tool for | ||||
| parsing spreadsheets and generating CSV rows. | ||||
| 
 | ||||
| :::info pass | ||||
| 
 | ||||
| It is strongly recommended to install BunJS on systems using SheetJS libraries | ||||
| in command-line tools. This workaround should only be considered if a standalone | ||||
| binary is considered desirable. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution BunJS support is considered experimental. | ||||
| 
 | ||||
| Great open source software grows with user tests and reports. Any issues should | ||||
| be reported to the BunJS project for further diagnosis. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ## Integration Details | ||||
| 
 | ||||
| The [SheetJS BunJS module](/docs/getting-started/installation/bun) can be | ||||
| imported from BunJS scripts. | ||||
| 
 | ||||
| `bun build --compile` generates a standalone executable that includes the BunJS | ||||
| runtime, user JS code and supporting scripts and assets | ||||
| 
 | ||||
| ### Script Requirements | ||||
| 
 | ||||
| Scripts that exclusively use SheetJS libraries and BunJS built-in modules can be | ||||
| bundled using BunJS. The module should be required directly: | ||||
| 
 | ||||
| <CodeBlock language="ts">{`\ | ||||
| const XLSX = require("xlsx");`} | ||||
| </CodeBlock> | ||||
| 
 | ||||
| For example, the following script accepts one command line argument, parses the | ||||
| specified file using the SheetJS `readFile` method[^1], generates CSV text from | ||||
| the first worksheet using `sheet_to_csv`[^2], and prints to terminal: | ||||
| 
 | ||||
| <CodeBlock language="ts" title="sheet2csv.ts">{`\ | ||||
| const XLSX = require("xlsx"); | ||||
| \n\ | ||||
| /* process.argv[2] is the first argument to the script */ | ||||
| const filename = process.argv[2]; | ||||
| \n\ | ||||
| /* read file */ | ||||
| const wb = XLSX.readFile(filename); | ||||
| \n\ | ||||
| /* generate CSV of first sheet */ | ||||
| const ws = wb.Sheets[wb.SheetNames[0]]; | ||||
| const csv = XLSX.utils.sheet_to_csv(ws); | ||||
| \n\ | ||||
| /* print to terminal */ | ||||
| console.log(csv);`} | ||||
| </CodeBlock> | ||||
| 
 | ||||
| ## Complete Example | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was last tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | BunJS    | Date       | | ||||
| |:-------------|:---------|:-----------| | ||||
| | `darwin-x64` | `1.1.10` | 2024-05-28 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 0) Install or update BunJS.[^3] | ||||
| 
 | ||||
| 1) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 2) Save the [contents of the `sheet2csv.ts` code block](#script-requirements) | ||||
| to `sheet2csv.ts` in the project folder. | ||||
| 
 | ||||
| 3) Install the SheetJS dependency: | ||||
| 
 | ||||
| <CodeBlock language="bash">{`\ | ||||
| bun install https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz`} | ||||
| </CodeBlock> | ||||
| 
 | ||||
| 4) Test the script with `bun run`: | ||||
| 
 | ||||
| ```bash | ||||
| bun run sheet2csv.ts pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| The script should display CSV contents from the first sheet: | ||||
| 
 | ||||
| ```text title="Expected Output" | ||||
| Name,Index | ||||
| Bill Clinton,42 | ||||
| GeorgeW Bush,43 | ||||
| Barack Obama,44 | ||||
| Donald Trump,45 | ||||
| Joseph Biden,46 | ||||
| ``` | ||||
| 
 | ||||
| 5) Compile and run `sheet2csv`: | ||||
| 
 | ||||
| ```bash | ||||
| bun build ./sheet2csv.ts --compile --outfile sheet2csv | ||||
| ./sheet2csv pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| The program should display the same CSV contents as the script (from step 2) | ||||
| 
 | ||||
| [^1]: See [`readFile` in "Reading Files"](/docs/api/parse-options) | ||||
| [^2]: See [`sheet_to_csv` in "CSV and Text"](/docs/api/utilities/csv#delimiter-separated-output) | ||||
| [^3]: See ["Installation"](https://bun.sh/docs/installation) in the BunJS documentation for instructions. | ||||
| @ -1,5 +1,5 @@ | ||||
| --- | ||||
| title: Deno Compiler | ||||
| title: Deno SEA | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| sidebar_custom_props: | ||||
| @ -69,7 +69,7 @@ const wb = XLSX.readFile(filename); | ||||
| \n\ | ||||
| /* generate CSV of first sheet */ | ||||
| const ws = wb.Sheets[wb.SheetNames[0]]; | ||||
| const csv = utils.sheet_to_csv(ws); | ||||
| const csv = XLSX.utils.sheet_to_csv(ws); | ||||
| \n\ | ||||
| /* print to terminal */ | ||||
| console.log(csv);`} | ||||
| @ -99,7 +99,7 @@ This demo was last tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | Deno     | Date       | | ||||
| |:-------------|:---------|:-----------| | ||||
| | `darwin-x64` | `1.43.1` | 2024-05-08 | | ||||
| | `darwin-x64` | `1.43.6` | 2024-05-28 | | ||||
| | `darwin-arm` | `1.43.6` | 2024-05-23 | | ||||
| | `win10-x64`  | `1.41.3` | 2024-03-24 | | ||||
| | `win11-x64`  | `1.43.6` | 2024-05-25 | | ||||
| @ -125,7 +125,7 @@ deno run -r --allow-read https://docs.sheetjs.com/cli/sheet2csv.ts pres.numbers | ||||
| 
 | ||||
| The script should display CSV contents from the first sheet: | ||||
| 
 | ||||
| ``` | ||||
| ```text title="Expected Output" | ||||
| Name,Index | ||||
| Bill Clinton,42 | ||||
| GeorgeW Bush,43 | ||||
| @ -1,5 +1,7 @@ | ||||
| --- | ||||
| title: Command-Line Tools | ||||
| title: Sheets on the Command Line | ||||
| sidebar_label: Command-Line Tools | ||||
| hide_table_of_contents: true | ||||
| pagination_prev: demos/desktop/index | ||||
| pagination_next: demos/data/index | ||||
| --- | ||||
| @ -9,6 +11,7 @@ import Tabs from '@theme/Tabs'; | ||||
| import TabItem from '@theme/TabItem'; | ||||
| import CodeBlock from '@theme/CodeBlock'; | ||||
| import {useCurrentSidebarCategory} from '@docusaurus/theme-common'; | ||||
| import FrameworkData from '/data/cli.js' | ||||
| 
 | ||||
| export const r = {style: {color:"red"}}; | ||||
| export const B = {style: {fontWeight:"bold"}}; | ||||
| @ -45,10 +48,16 @@ Demos for common standalone CLI tools are included in separate pages: | ||||
|   </li>); | ||||
| })}</ul> | ||||
| 
 | ||||
| #### Platform Support | ||||
| 
 | ||||
| The following frameworks have been tested on the following platforms: | ||||
| 
 | ||||
| <FrameworkData/> | ||||
| 
 | ||||
| :::tip pass | ||||
| 
 | ||||
| The [`xlsx-cli`](https://cdn.sheetjs.com/xlsx-cli/) NodeJS script is available | ||||
| as a package on the SheetJS CDN. It is an easy-to-use command-line tool for | ||||
| as a package on the SheetJS CDN. It is a straightforward command-line tool for | ||||
| translating files between supported spreadsheet file formats. | ||||
| 
 | ||||
| ::: | ||||
| @ -65,457 +74,33 @@ server-side scripting platform cannot be installed on the target computer. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ## NodeJS | ||||
| #### NodeJS | ||||
| 
 | ||||
| There are a few popular tools for compiling NodeJS scripts to CLI programs. | ||||
| This demo has been organized by framework: | ||||
| 
 | ||||
| The demo script presents a friendly command line interface including flags: | ||||
| - [`boxednode`](/docs/demos/cli/boxednode) | ||||
| - [`nexe`](/docs/demos/cli/nexe) | ||||
| - [`pkg`](/docs/demos/cli/pkg) | ||||
| 
 | ||||
| ```bash | ||||
| $ ./xlsx-cli -h | ||||
| Usage: xlsx-cli [options] <file> [sheetname] | ||||
| #### V8 | ||||
| 
 | ||||
| Options: | ||||
|   -V, --version            output the version number | ||||
|   -f, --file <file>        use specified workbook | ||||
|   -s, --sheet <sheet>      print specified sheet (default first sheet) | ||||
| ... | ||||
| ``` | ||||
| **[The exposition has been moved to the "V8" demo.](/docs/demos/engines/v8#snapshots)** | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| #### BunJS | ||||
| 
 | ||||
| This demo was tested in the following deployments: | ||||
| 
 | ||||
| <Tabs groupId="njs"> | ||||
|   <TabItem value="nexe" label="Nexe"> | ||||
| 
 | ||||
| | Architecture | Version      | NodeJS    | Source    | Date       | | ||||
| |:-------------|:-------------|:----------|:----------|:-----------| | ||||
| | `darwin-x64` | `4.0.0-rc.4` | `14.15.3` | Pre-built | 2024-03-15 | | ||||
| | `darwin-arm` | `4.0.0-rc.6` | `18.20.3` | Compiled  | 2024-05-25 | | ||||
| | `win10-x64`  | `4.0.0-rc.4` | `14.15.3` | Pre-built | 2024-04-18 | | ||||
| | `win11-arm`  | `4.0.0-rc.6` | `20.10.0` | Compiled  | 2024-05-28 | | ||||
| | `linux-x64`  | `4.0.0-rc.4` | `14.15.3` | Pre-built | 2024-03-21 | | ||||
| | `linux-arm`  | `4.0.0-rc.6` | `18.20.3` | Compiled  | 2024-05-26 | | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="pkg" label="pkg"> | ||||
| 
 | ||||
| | Architecture | Version | NodeJS   | Date       | | ||||
| |:-------------|:--------|:---------|:-----------| | ||||
| | `darwin-x64` | `5.8.1` | `18.5.0` | 2024-03-15 | | ||||
| | `darwin-arm` | `5.8.1` | `18.5.0` | 2024-05-25 | | ||||
| | `win10-x64`  | `5.8.1` | `18.5.0` | 2024-04-18 | | ||||
| | `win11-arm`  | `5.8.1` | `18.5.0` | 2024-05-28 | | ||||
| | `linux-x64`  | `5.8.1` | `18.5.0` | 2024-03-21 | | ||||
| | `linux-arm`  | `5.8.1` | `18.5.0` | 2024-05-26 | | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="boxednode" label="boxednode"> | ||||
| 
 | ||||
| | Architecture | Version | NodeJS    | Date       | | ||||
| |:-------------|:--------|:----------|:-----------| | ||||
| | `darwin-x64` | `2.4.0` | `21.7.1`  | 2024-03-15 | | ||||
| | `darwin-arm` | `2.4.3` | `22.2.0`  | 2024-05-25 | | ||||
| | `win10-x64`  | `2.4.2` | `16.20.2` | 2024-04-18 | | ||||
| | `linux-x64`  | `2.4.0` | `21.7.1`  | 2024-03-21 | | ||||
| | `linux-arm`  | `2.4.3` | `20.13.1` | 2024-05-26 | | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 0) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 1) Download [`xlsx-cli.js`](pathname:///cli/xlsx-cli.js) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| 2) Install the dependencies: | ||||
| 
 | ||||
| <Tabs groupId="pm"> | ||||
|   <TabItem value="npm" label="npm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="pnpm" label="pnpm"> | ||||
| <CodeBlock language="bash">{`\ | ||||
| pnpm install --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
|   <TabItem value="yarn" label="Yarn" default> | ||||
| <CodeBlock language="bash">{`\ | ||||
| yarn add https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz exit-on-epipe commander@2`} | ||||
| </CodeBlock> | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 3) Follow tooling steps: | ||||
| 
 | ||||
| <Tabs groupId="njs"> | ||||
|   <TabItem value="nexe" label="Nexe"> | ||||
| 
 | ||||
| Run `nexe` and manually specify NodeJS version 14.15.3 | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe -t 14.15.3 xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| This generates `xlsx-cli` or `xlsx-cli.exe` depending on platform. | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When the demo was tested on ARM targets, the Nexe pre-built packages were | ||||
| missing.  The package must be built from source: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --python=$(which python3) --make="-j8" | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --make="-j8" | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| On Windows ARM, the target `windows-arm64-20.10.0` must be specified: | ||||
| 
 | ||||
| ```bash | ||||
| npx nexe xlsx-cli.js --build --make="-j8" --target=windows-arm64-20.10.0 | ||||
| ``` | ||||
| 
 | ||||
| The Windows build may fail with a `vcbuild.bat` error: | ||||
| 
 | ||||
| ``` | ||||
| Error: vcbuild.bat nosign release arm64 exited with code: 1 | ||||
| ``` | ||||
| 
 | ||||
| Pass the `-v` flag for more details. In the most recent test, the error stemmed | ||||
| from a Python version mismatch: | ||||
| 
 | ||||
| ``` | ||||
| Node.js configure: found Python 2.7.18 | ||||
| Please use python3.11 or python3.10 or python3.9 or python3.8 or python3.7 or python3.6 | ||||
| ``` | ||||
| 
 | ||||
| The resolved version of Python can be found with | ||||
| 
 | ||||
| ```cmd | ||||
| where python | ||||
| ``` | ||||
| 
 | ||||
| In the most recent test, a Python 2 version appeared first. This was fixed by | ||||
| finding the Python 3 location and prepending it to `PATH`: | ||||
| 
 | ||||
| ```cmd | ||||
| set PATH="C:\correct\path\to\python\three";%PATH% | ||||
| ``` | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="pkg" label="pkg"> | ||||
| 
 | ||||
| :::danger pass | ||||
| 
 | ||||
| When this demo was last tested, `pkg` failed with an error referencing `node20`: | ||||
| 
 | ||||
| ``` | ||||
| > Targets not specified. Assuming: | ||||
|   node20-linux-arm64, node20-macos-arm64, node20-win-arm64 | ||||
| > Error! No available node version satisfies 'node20' | ||||
| ``` | ||||
| 
 | ||||
| **`pkg` does not support NodeJS 20!** | ||||
| 
 | ||||
| The local NodeJS version must be rolled back to version 18. | ||||
| 
 | ||||
| If `n` is installed: | ||||
| 
 | ||||
| ```bash | ||||
| sudo n 18 | ||||
| ``` | ||||
| 
 | ||||
| If `nvm` was used to install NodeJS: | ||||
| 
 | ||||
| ```bash | ||||
| nvm install 18 | ||||
| nvm use 18 | ||||
| ``` | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| Run `pkg`: | ||||
| 
 | ||||
| ```bash | ||||
| npx pkg xlsx-cli.js | ||||
| ``` | ||||
| 
 | ||||
| This generates `xlsx-cli-linux`, `xlsx-cli-macos`, and `xlsx-cli-win.exe` . | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="boxednode" label="boxednode"> | ||||
| 
 | ||||
| Run `boxednode`: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli | ||||
| ``` | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When this demo was last tested in `linux-arm`, the build failed with an error: | ||||
| 
 | ||||
| <pre> | ||||
| ../deps/v8/src/base/small-vector.h:  In instantiation of <span {...B}>‘class v8::base::SmallVector<std::pair<const v8::internal::compiler::turboshaft::PhiOp*, const v8::internal::compiler::turboshaft::OpIndex>, 16>’</span>: | ||||
| <span {...B}>../deps/v8/src/compiler/turboshaft/loop-unrolling-reducer.h:444:11:</span>   required from here | ||||
| <span {...B}>../deps/v8/src/base/macros.h:206:55:</span> <span style={{...r.style,...B.style}}>error:</span> static assertion failed: T should be trivially copyable | ||||
| {"  206 |"}   static_assert(::v8::base::is_trivially_copyable<T>::<span style={{...r.style,...B.style}}>value</span>, \\ | ||||
| {"      |"}                                                       ^~~~~ | ||||
| </pre> | ||||
| 
 | ||||
| This affects NodeJS `22.2.0`, but does not affect `20.13.1`. It affects the | ||||
| [V8 JavaScript Engine](https://docs.sheetjs.com/docs/demos/engines/v8#build-v8) | ||||
| and cannot easily be patched using `boxednode`. | ||||
| 
 | ||||
| The `-n` flag controls the target NodeJS version. For this demo, the following | ||||
| command uses NodeJS `20.13.1`: | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli -n 20.13.1 | ||||
| ``` | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```bash | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli.exe -n 16.20.2 | ||||
| ``` | ||||
| 
 | ||||
| :::info pass | ||||
| 
 | ||||
| The Windows 10 build requires Visual Studio with "Desktop development with C++" | ||||
| workload, Python 3.11, and NASM[^1]. | ||||
| 
 | ||||
| **The build command must be run in "x64 Native Tools Command Prompt"** | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When the demo was last tested, the build failed: | ||||
| 
 | ||||
| ``` | ||||
| Not an executable Python program | ||||
| Could not find Python. | ||||
| ``` | ||||
| 
 | ||||
| By default, Windows aliases `python` to a Microsoft Store installer. If the | ||||
| official installer was used, the alias should be disabled manually: | ||||
| 
 | ||||
| 1) Open Start menu and type "app alias". Click "Manage app execution aliases". | ||||
| 
 | ||||
| 2) Disable the App Installer for all items with `python` in the name. | ||||
| 
 | ||||
| Using Python 3.12, the build fails with an error: | ||||
| 
 | ||||
| ``` | ||||
| Please use python3.11 or python3.10 or python3.9 or python3.8 or python3.7 or python3.6. | ||||
| ``` | ||||
| 
 | ||||
| In the most recent test, Python 3.11.8 was installed from the official site. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| When the demo was last tested on Windows, the build failed: | ||||
| 
 | ||||
| ``` | ||||
| error MSB8020: The build tools for Visual Studio 2019 (Platform Toolset = 'v142') cannot be found. To build using the v142 build tools, please install Visual Studio 2019 build tools. | ||||
| ``` | ||||
| 
 | ||||
| This error was fixed by installing the `v142` build tools through the Visual | ||||
| Studio installer. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| In the most recent Windows test against NodeJS `20.8.0`, the build failed due | ||||
| to an issue in the OpenSSL dependency: | ||||
| 
 | ||||
| ``` | ||||
| ...\node-v20.8.0\deps\openssl\openssl\crypto\cversion.c(75,33): error C2153: integer literals must have at least one digit [...\node-v20.8.0\deps\openssl\openssl.vcxproj] | ||||
| ``` | ||||
| 
 | ||||
| SheetJS libraries are compatible with NodeJS versions dating back to `v0.8`. The | ||||
| workaround is to select NodeJS `v16.20.2` using the `-n` flag. This version was | ||||
| was chosen since NodeJS `v18` upgraded the OpenSSL dependency. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| 
 | ||||
| 4) Run the generated program, passing `pres.numbers` as the argument. For | ||||
| example, `nexe` generates `xlsx-cli` in macOS so the command is: | ||||
| 
 | ||||
| ```bash | ||||
| ./xlsx-cli pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| `nexe` generates `xlsx-cli.exe` in Windows, so the command is: | ||||
| 
 | ||||
| ```powershell | ||||
| .\xlsx-cli.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| ## V8 | ||||
| 
 | ||||
| The [V8](/docs/demos/engines/v8) demo covers standalone programs that embed the | ||||
| V8 engine. This demo uses the Rust integration to generate a command line tool. | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was last tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | V8 Version    | Crate    | Date       | | ||||
| |:-------------|:--------------|:---------|:-----------| | ||||
| | `darwin-x64` | `12.3.219.9`  | `0.88.0` | 2024-03-15 | | ||||
| | `darwin-arm` | `12.6.228.3`  | `0.92.0` | 2024-05-23 | | ||||
| | `win10-x64`  | `12.3.219.9`  | `0.88.0` | 2024-03-24 | | ||||
| | `win11-x64`  | `12.6.228.3`  | `0.92.0` | 2024-05-23 | | ||||
| | `linux-x64`  | `12.3.219.9`  | `0.88.0` | 2024-03-18 | | ||||
| | `linux-arm`  | `12.6.228.3`  | `0.92.0` | 2024-05-26 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 0) Make a new folder for the project: | ||||
| 
 | ||||
| ```bash | ||||
| mkdir sheetjs2csv | ||||
| cd sheetjs2csv | ||||
| ``` | ||||
| 
 | ||||
| 1) Download the following scripts: | ||||
| 
 | ||||
| - [`Cargo.toml`](pathname:///cli/Cargo.toml) | ||||
| - [`snapshot.rs`](pathname:///cli/snapshot.rs) | ||||
| - [`sheet2csv.rs`](pathname:///cli/sheet2csv.rs) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o Cargo.toml https://docs.sheetjs.com/cli/Cargo.toml | ||||
| curl -o snapshot.rs https://docs.sheetjs.com/cli/snapshot.rs | ||||
| curl -o sheet2csv.rs https://docs.sheetjs.com/cli/sheet2csv.rs | ||||
| ``` | ||||
| 
 | ||||
| 2) Download the SheetJS Standalone script and move to the project directory: | ||||
| 
 | ||||
| <ul> | ||||
| <li><a href={`https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js`}>xlsx.full.min.js</a></li> | ||||
| </ul> | ||||
| 
 | ||||
| <CodeBlock language="bash">{`\ | ||||
| curl -o xlsx.full.min.js https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js`} | ||||
| </CodeBlock> | ||||
| 
 | ||||
| 3) Build the V8 snapshot: | ||||
| 
 | ||||
| ```bash | ||||
| cargo build --bin snapshot | ||||
| cargo run --bin snapshot | ||||
| ``` | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| With some versions of the `v8` crate, the Linux AArch64 build failed with an error: | ||||
| 
 | ||||
| ``` | ||||
| error[E0080]: evaluation of constant value failed | ||||
| 
 | ||||
|      | | ||||
| 1715 |   assert!(size_of::<TypeId>() == size_of::<u64>()); | ||||
|      |   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the evaluated program panicked at 'assertion failed: size_of::<TypeId>() == size_of::<u64>()' | ||||
| ``` | ||||
| 
 | ||||
| Versions `0.75.1` and `0.82.0` are known to work. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 
 | ||||
| 4) Build `sheet2csv` (`sheet2csv.exe` in Windows): | ||||
| 
 | ||||
| ```bash | ||||
| cargo build --release --bin sheet2csv | ||||
| ``` | ||||
| 
 | ||||
| 5) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 6) Test the application: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| mv target/release/sheet2csv . | ||||
| ./sheet2csv pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```bash | ||||
| mv target/release/sheet2csv.exe . | ||||
| .\sheet2csv.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
| **[The exposition has been moved to a separate page.](/docs/demos/cli/bunsea)** | ||||
| 
 | ||||
| #### Deno | ||||
| 
 | ||||
| **[The exposition has been moved to a separate page.](/docs/demos/cli/deno)** | ||||
| **[The exposition has been moved to a separate page.](/docs/demos/cli/denosea)** | ||||
| 
 | ||||
| ## Dedicated Engines | ||||
| #### Dedicated Engines | ||||
| 
 | ||||
| The following demos for JS engines produce standalone programs: | ||||
| 
 | ||||
| - [V8](/docs/demos/engines/v8) | ||||
| - [Duktape](/docs/demos/engines/duktape) | ||||
| - [ChakraCore](/docs/demos/engines/chakra) | ||||
| - [QuickJS](/docs/demos/engines/quickjs) | ||||
| - [Goja](/docs/demos/engines/goja) | ||||
| - [JavaScriptCore](/docs/demos/engines/jsc) | ||||
| 
 | ||||
| [^1]: Downloads can be found [at the main NASM project website](https://www.nasm.us/) | ||||
| @ -19,9 +19,7 @@ data from spreadsheets. | ||||
| 
 | ||||
| The ["Complete Example"](#complete-example) section includes a complete | ||||
| command-line tool for reading data from spreadsheets and exporting to Excel XLSB | ||||
| workbooks. | ||||
| 
 | ||||
| The ["Bindings"](#bindings) section covers bindings for other ecosystems. | ||||
| workbooks. ["Bindings"](#bindings) covers bindings for other ecosystems. | ||||
| 
 | ||||
| ## Integration Details | ||||
| 
 | ||||
|  | ||||
| @ -1,7 +1,7 @@ | ||||
| --- | ||||
| title: Blazing Fast Data Processing with V8 | ||||
| sidebar_label: C++ + V8 | ||||
| description: Process structured data in C++ or Rust programs. Seamlessly integrate spreadsheets by paring V8 and SheetJS. Modernize  workflows while preserving Excel compatibility. | ||||
| description: Process structured data in C++ or Rust programs. Seamlessly integrate spreadsheets by pairing V8 and SheetJS. Modernize workflows while maintaining Excel compatibility. | ||||
| pagination_prev: demos/bigdata/index | ||||
| pagination_next: solutions/input | ||||
| --- | ||||
| @ -30,6 +30,18 @@ covers V8 engine bindings for other programming languages. | ||||
| The [SheetJS Standalone scripts](/docs/getting-started/installation/standalone) | ||||
| can be parsed and evaluated in a V8 context. | ||||
| 
 | ||||
| :::note pass | ||||
| 
 | ||||
| This section describes a flow where the script is parsed and evaluated every | ||||
| time the program is run. | ||||
| 
 | ||||
| Using V8 snapshots, SheetJS libraries can be parsed and evaluated beforehand. | ||||
| This greatly improves program startup time. | ||||
| 
 | ||||
| The ["Snapshots"](#snapshots) section includes a complete example. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| ### Initialize V8 | ||||
| 
 | ||||
| The official V8 `hello-world` example covers initialization and cleanup. For the | ||||
| @ -890,7 +902,7 @@ Pulling data from an `ArrayBuffer` back into Rust involves an unsafe operation: | ||||
| ```rust | ||||
| /* assuming JS code returns an ArrayBuffer, copy result to a Vec<u8> */ | ||||
| fn eval_code_ab(scope: &mut v8::HandleScope, code: &str) -> Vec<u8> { | ||||
|   let source = v8::String::new(scope, &code).unwrap(); | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result: v8::Local<v8::ArrayBuffer> = script.run(scope).unwrap().try_into().unwrap(); | ||||
|   /* In C++, `Data` returns a pointer. Collecting data into Vec<u8> is unsafe */ | ||||
| @ -907,7 +919,7 @@ This demo was last tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | V8 Crate | Date       | | ||||
| |:-------------|:---------|:-----------| | ||||
| | `darwin-x64` | `0.89.0` | 2024-04-04 | | ||||
| | `darwin-x64` | `0.92.0` | 2024-05-28 | | ||||
| | `darwin-arm` | `0.92.0` | 2024-05-25 | | ||||
| | `win10-x64`  | `0.89.0` | 2024-03-24 | | ||||
| | `linux-x64`  | `0.91.0` | 2024-04-25 | | ||||
| @ -957,3 +969,125 @@ cargo run pres.numbers | ||||
| 
 | ||||
| If the program succeeded, the CSV contents will be printed to console and the | ||||
| file `sheetjsw.xlsb` will be created.  That file can be opened with Excel. | ||||
| 
 | ||||
| ## Snapshots | ||||
| 
 | ||||
| At a high level, V8 snapshots are raw dumps of the V8 engine state. It is much | ||||
| more efficient for programs to load snapshots than to evaluate code. | ||||
| 
 | ||||
| ### Snapshot Demo | ||||
| 
 | ||||
| There are two parts to this demo: | ||||
| 
 | ||||
| A) The [`snapshot`](pathname:///cli/snapshot.rs) command creates a snapshot with | ||||
| the [SheetJS standalone script](/docs/getting-started/installation/standalone) | ||||
| and [supplementary NUMBERS script](/docs/api/write-options#writing-options). It | ||||
| will dump the snapshot to `snapshot.bin` | ||||
| 
 | ||||
| B) The [`sheet2csv`](pathname:///cli/sheet2csv.rs) tool embeds `snapshot.bin`. | ||||
| The tool will parse a specified file, print CSV contents of a named worksheet, | ||||
| and export the workbook to NUMBERS. | ||||
| 
 | ||||
| :::note Tested Deployments | ||||
| 
 | ||||
| This demo was last tested in the following deployments: | ||||
| 
 | ||||
| | Architecture | V8 Version    | Crate    | Date       | | ||||
| |:-------------|:--------------|:---------|:-----------| | ||||
| | `darwin-x64` | `12.6.228.3`  | `0.92.0` | 2024-05-28 | | ||||
| | `darwin-arm` | `12.6.228.3`  | `0.92.0` | 2024-05-23 | | ||||
| | `win10-x64`  | `12.3.219.9`  | `0.88.0` | 2024-03-24 | | ||||
| | `win11-x64`  | `12.6.228.3`  | `0.92.0` | 2024-05-23 | | ||||
| | `linux-x64`  | `12.3.219.9`  | `0.88.0` | 2024-03-18 | | ||||
| | `linux-arm`  | `12.6.228.3`  | `0.92.0` | 2024-05-26 | | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 0) Make a new folder for the project: | ||||
| 
 | ||||
| ```bash | ||||
| mkdir sheetjs2csv | ||||
| cd sheetjs2csv | ||||
| ``` | ||||
| 
 | ||||
| 1) Download the following scripts: | ||||
| 
 | ||||
| - [`Cargo.toml`](pathname:///cli/Cargo.toml) | ||||
| - [`snapshot.rs`](pathname:///cli/snapshot.rs) | ||||
| - [`sheet2csv.rs`](pathname:///cli/sheet2csv.rs) | ||||
| 
 | ||||
| ```bash | ||||
| curl -o Cargo.toml https://docs.sheetjs.com/cli/Cargo.toml | ||||
| curl -o snapshot.rs https://docs.sheetjs.com/cli/snapshot.rs | ||||
| curl -o sheet2csv.rs https://docs.sheetjs.com/cli/sheet2csv.rs | ||||
| ``` | ||||
| 
 | ||||
| 2) Download the SheetJS Standalone script and NUMBERS supplementary script. Move | ||||
| both scripts to the project directory: | ||||
| 
 | ||||
| <ul> | ||||
| <li><a href={`https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js`}>xlsx.full.min.js</a></li> | ||||
| <li><a href={`https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.zahl.js`}>xlsx.zahl.js</a></li> | ||||
| </ul> | ||||
| 
 | ||||
| <CodeBlock language="bash">{`\ | ||||
| curl -o xlsx.full.min.js https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.full.min.js | ||||
| curl -o xlsx.zahl.js https://cdn.sheetjs.com/xlsx-${current}/package/dist/xlsx.zahl.js`} | ||||
| </CodeBlock> | ||||
| 
 | ||||
| 3) Build the V8 snapshot: | ||||
| 
 | ||||
| ```bash | ||||
| cargo build --bin snapshot | ||||
| cargo run --bin snapshot | ||||
| ``` | ||||
| 
 | ||||
| :::caution pass | ||||
| 
 | ||||
| In some tests, the Linux AArch64 build failed with an error: | ||||
| 
 | ||||
| ``` | ||||
| error[E0080]: evaluation of constant value failed | ||||
| 
 | ||||
|      | | ||||
| 1715 |   assert!(size_of::<TypeId>() == size_of::<u64>()); | ||||
|      |   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the evaluated program panicked at 'assertion failed: size_of::<TypeId>() == size_of::<u64>()' | ||||
| ``` | ||||
| 
 | ||||
| Versions `0.75.1`, `0.82.0`, and `0.92.0` are known to work. | ||||
| 
 | ||||
| ::: | ||||
| 
 | ||||
| 
 | ||||
| 4) Build `sheet2csv` (`sheet2csv.exe` in Windows): | ||||
| 
 | ||||
| ```bash | ||||
| cargo build --release --bin sheet2csv | ||||
| ``` | ||||
| 
 | ||||
| 5) Download the test file https://docs.sheetjs.com/pres.numbers: | ||||
| 
 | ||||
| ```bash | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| ``` | ||||
| 
 | ||||
| 6) Test the application: | ||||
| 
 | ||||
| <Tabs groupId="os"> | ||||
|   <TabItem value="unix" label="Linux/MacOS"> | ||||
| 
 | ||||
| ```bash | ||||
| mv target/release/sheet2csv . | ||||
| ./sheet2csv pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
|   <TabItem value="win" label="Windows"> | ||||
| 
 | ||||
| ```bash | ||||
| mv target/release/sheet2csv.exe . | ||||
| .\sheet2csv.exe pres.numbers | ||||
| ``` | ||||
| 
 | ||||
|   </TabItem> | ||||
| </Tabs> | ||||
|  | ||||
| @ -1,16 +1,24 @@ | ||||
| /* run code, get result as a Rust String */ | ||||
| fn eval_code(scope: &mut v8::HandleScope, code: &str) -> std::string::String { | ||||
|   let source = v8::String::new(scope, &code).unwrap(); | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result = script.run(scope).unwrap(); | ||||
|   return result.to_string(scope).unwrap().to_rust_string_lossy(scope); | ||||
| } | ||||
| 
 | ||||
| /* assuming JS code returns an ArrayBuffer, copy result to a Vec<u8> */ | ||||
| fn eval_code_ab(scope: &mut v8::HandleScope, code: &str) -> Vec<u8> { | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result: v8::Local<v8::ArrayBuffer> = script.run(scope).unwrap().try_into().unwrap(); | ||||
|   unsafe { return std::slice::from_raw_parts_mut(result.data().unwrap().cast::<u8>().as_ptr(), result.byte_length()).to_vec(); } | ||||
| } | ||||
| 
 | ||||
| fn main() { | ||||
|   /* parse arguments */ | ||||
|   let mut iter = std::env::args(); | ||||
|   let path: String = iter.nth(1).expect("must specify a file name"); | ||||
|   let sheetname: String = match iter.nth(0) { | ||||
|   let sheetname: String = match iter.next() { | ||||
|     Some(v) => format!("'{}'", v), | ||||
|     None => "wb.SheetNames[0]".to_string() | ||||
|   }; | ||||
| @ -29,14 +37,24 @@ fn main() { | ||||
|   let context_scope = &mut v8::ContextScope::new(handle_scope, context); | ||||
| 
 | ||||
|   /* read file */ | ||||
|   let data: Vec<u8> = std::fs::read(path.clone()).unwrap(); | ||||
|   let back: v8::UniqueRef<v8::BackingStore> = v8::ArrayBuffer::new_backing_store_from_vec(data); | ||||
|   let shared = back.make_shared(); | ||||
|   let ab: v8::Local<v8::ArrayBuffer> = v8::ArrayBuffer::with_backing_store(context_scope, &shared); | ||||
|   let key = v8::String::new(context_scope, "buf").unwrap(); | ||||
|   context.global(context_scope).set(context_scope, key.into(), ab.into()); | ||||
|   { | ||||
|     let data: Vec<u8> = std::fs::read(path.clone()).unwrap(); | ||||
|     let back: v8::UniqueRef<v8::BackingStore> = v8::ArrayBuffer::new_backing_store_from_vec(data); | ||||
|     let shared = back.make_shared(); | ||||
|     let ab: v8::Local<v8::ArrayBuffer> = v8::ArrayBuffer::with_backing_store(context_scope, &shared); | ||||
|     let key = v8::String::new(context_scope, "buf").unwrap(); | ||||
|     context.global(context_scope).set(context_scope, key.into(), ab.into()); | ||||
|   } | ||||
| 
 | ||||
|   /* print CSV of specified sheet */ | ||||
|   let result = eval_code(context_scope, &mut format!("var wb = XLSX.read(buf, {{dense: true}}); XLSX.utils.sheet_to_csv(wb.Sheets[{}])", sheetname)); | ||||
|   println!("{}", result); | ||||
|   { | ||||
|     let result = eval_code(context_scope, &format!("var wb = XLSX.read(buf, {{dense: true}}); XLSX.utils.sheet_to_csv(wb.Sheets[{}])", sheetname)); | ||||
|     println!("{}", result); | ||||
|   } | ||||
| 
 | ||||
|   /* write sheetjsw.numbers */ | ||||
|   { | ||||
|     let result = eval_code_ab(context_scope, "XLSX.write(wb, {type:'array', bookType:'numbers', numbers: XLSX_ZAHL_PAYLOAD})"); | ||||
|     std::fs::write("sheetjsw.numbers", result).unwrap(); | ||||
|   } | ||||
| } | ||||
|  | ||||
| @ -1,38 +1,42 @@ | ||||
| /* run code, get result as a Rust String */ | ||||
| fn eval_code(scope: &mut v8::HandleScope, code: &str) -> std::string::String { | ||||
|   let source = v8::String::new(scope, &code).unwrap(); | ||||
| /*! sheetjs (C) SheetJS -- https://sheetjs.com */ | ||||
| /* run code and ignore result */ | ||||
| fn eval_code(scope: &mut v8::HandleScope, code: &str) { | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result = script.run(scope).unwrap(); | ||||
|   return result.to_string(scope).unwrap().to_rust_string_lossy(scope); | ||||
|   let _ = script.run(scope); | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| fn main() { | ||||
|   create_snapshot(); | ||||
| } | ||||
| 
 | ||||
| fn create_snapshot() { | ||||
|   /* initialize */ | ||||
|   let platform = v8::new_default_platform(0, false).make_shared(); | ||||
|   v8::V8::initialize_platform(platform); | ||||
|   v8::V8::initialize(); | ||||
| 
 | ||||
|   let startup_data = { | ||||
|     let mut isolate = v8::Isolate::snapshot_creator(None); | ||||
|     { | ||||
|       let handle_scope = &mut v8::HandleScope::new(&mut isolate); | ||||
|       let context = v8::Context::new(handle_scope); | ||||
|       let context_scope = &mut v8::ContextScope::new(handle_scope, context); | ||||
|   /* use SnapshotCreator */ | ||||
|   let mut isolate = v8::Isolate::snapshot_creator(None); | ||||
| 
 | ||||
|       /* load library */ | ||||
|       { | ||||
|         let script = std::fs::read_to_string("./xlsx.full.min.js").expect("Error reading xlsx.full.min.js"); | ||||
|         let _result = eval_code(context_scope, &script); | ||||
|       } | ||||
|       context_scope.set_default_context(context); | ||||
|   /* scope enforces the lifetime of the `&mut isolate` in `handle_scope` */ | ||||
|   { | ||||
|     /* same steps as normal flow */ | ||||
|     let handle_scope = &mut v8::HandleScope::new(&mut isolate); | ||||
|     let context = v8::Context::new(handle_scope); | ||||
|     let context_scope = &mut v8::ContextScope::new(handle_scope, context); | ||||
| 
 | ||||
|     /* instructs the snapshot creator to dump the new context */ | ||||
|     context_scope.set_default_context(context); | ||||
| 
 | ||||
|     /* load scripts */ | ||||
|     let scripts = vec!["./xlsx.full.min.js", "./xlsx.zahl.js"]; | ||||
|     for path in &scripts { | ||||
|       let script = std::fs::read_to_string(path).unwrap_or_else(|_| panic!("Error reading {}", path)); | ||||
|       eval_code(context_scope, &script); | ||||
|     } | ||||
|     isolate.create_blob(v8::FunctionCodeHandling::Clear).unwrap() | ||||
|   }; | ||||
| 
 | ||||
|   /* create snapshot */ | ||||
|   let startup_data = isolate.create_blob(v8::FunctionCodeHandling::Clear).unwrap(); | ||||
| 
 | ||||
|   /* write to snapshot.bin */ | ||||
|   let blob: Vec<u8> = startup_data.to_vec(); | ||||
|   std::fs::write("snapshot.bin", blob).unwrap(); | ||||
| } | ||||
|  | ||||
| @ -1,7 +1,7 @@ | ||||
| /*! sheetjs (C) SheetJS -- https://sheetjs.com */ | ||||
| /* run code, get result as a Rust String */ | ||||
| fn eval_code(scope: &mut v8::HandleScope, code: &str) -> std::string::String { | ||||
|   let source = v8::String::new(scope, &code).unwrap(); | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result = script.run(scope).unwrap(); | ||||
|   return result.to_string(scope).unwrap().to_rust_string_lossy(scope); | ||||
| @ -9,13 +9,17 @@ fn eval_code(scope: &mut v8::HandleScope, code: &str) -> std::string::String { | ||||
| 
 | ||||
| /* assuming JS code returns an ArrayBuffer, copy result to a Vec<u8> */ | ||||
| fn eval_code_ab(scope: &mut v8::HandleScope, code: &str) -> Vec<u8> { | ||||
|   let source = v8::String::new(scope, &code).unwrap(); | ||||
|   let source = v8::String::new(scope, code).unwrap(); | ||||
|   let script = v8::Script::compile(scope, source, None).unwrap(); | ||||
|   let result: v8::Local<v8::ArrayBuffer> = script.run(scope).unwrap().try_into().unwrap(); | ||||
|   unsafe { return std::slice::from_raw_parts_mut(result.data().unwrap().cast::<u8>().as_ptr(), result.byte_length()).to_vec(); } | ||||
| } | ||||
| 
 | ||||
| fn main() { | ||||
|   /* parse arguments */ | ||||
|   let mut iter = std::env::args(); | ||||
|   let path: String = iter.nth(1).expect("must specify a file name"); | ||||
| 
 | ||||
|   /* initialize */ | ||||
|   let platform = v8::new_default_platform(0, false).make_shared(); | ||||
|   v8::V8::initialize_platform(platform); | ||||
| @ -40,7 +44,6 @@ fn main() { | ||||
| 
 | ||||
|   /* read file */ | ||||
|   { | ||||
|     let path: String = std::env::args().collect::<Vec<_>>().into_iter().nth(1).unwrap().to_string(); | ||||
|     let data: Vec<u8> = std::fs::read(path.clone()).unwrap(); | ||||
|     let back: v8::UniqueRef<v8::BackingStore> = v8::ArrayBuffer::new_backing_store_from_vec(data); | ||||
|     let shared = back.make_shared(); | ||||
|  | ||||
							
								
								
									
										18
									
								
								tests/cli-boxednode.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										18
									
								
								tests/cli-boxednode.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,18 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/boxednode | ||||
| cd /tmp | ||||
| rm -rf sheetjs-boxednode | ||||
| mkdir sheetjs-boxednode | ||||
| cd sheetjs-boxednode | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| 
 | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz exit-on-epipe commander@2 | ||||
| 
 | ||||
| ## NOTE: these steps are for darwin-x64 | ||||
| 
 | ||||
| npx boxednode@2.4.3 -s xlsx-cli.js -t xlsx-cli | ||||
| 
 | ||||
| ./xlsx-cli pres.numbers | ||||
							
								
								
									
										35
									
								
								tests/cli-bunsea.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										35
									
								
								tests/cli-bunsea.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,35 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/bunsea | ||||
| cd /tmp | ||||
| rm -rf sheetjs-bunsea | ||||
| mkdir sheetjs-bunsea | ||||
| cd sheetjs-bunsea | ||||
| 
 | ||||
| bun --version | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| cat >sheet2csv.ts <<EOF | ||||
| const XLSX = require("xlsx"); | ||||
| 
 | ||||
| /* process.argv[2] is the first argument to the script */ | ||||
| const filename = process.argv[2]; | ||||
| 
 | ||||
| /* read file */ | ||||
| const wb = XLSX.readFile(filename); | ||||
| 
 | ||||
| /* generate CSV of first sheet */ | ||||
| const ws = wb.Sheets[wb.SheetNames[0]]; | ||||
| const csv = XLSX.utils.sheet_to_csv(ws); | ||||
| 
 | ||||
| /* print to terminal */ | ||||
| console.log(csv); | ||||
| EOF | ||||
| 
 | ||||
| bun install https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz | ||||
| 
 | ||||
| bun run sheet2csv.ts pres.numbers | ||||
| 
 | ||||
| bun build ./sheet2csv.ts --compile --outfile sheet2csv | ||||
| ./sheet2csv pres.numbers | ||||
| 
 | ||||
							
								
								
									
										16
									
								
								tests/cli-denosea.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										16
									
								
								tests/cli-denosea.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,16 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/denosea | ||||
| cd /tmp | ||||
| rm -rf sheetjs-cli-deno | ||||
| mkdir -p sheetjs-cli-deno | ||||
| cd sheetjs-cli-deno | ||||
| 
 | ||||
| deno --version | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| deno run -r --allow-read https://docs.sheetjs.com/cli/sheet2csv.ts pres.numbers | ||||
| 
 | ||||
| deno compile -r --allow-read https://docs.sheetjs.com/cli/sheet2csv.ts | ||||
| ./sheet2csv pres.numbers | ||||
| 
 | ||||
							
								
								
									
										18
									
								
								tests/cli-nexe.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										18
									
								
								tests/cli-nexe.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,18 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/nexe | ||||
| cd /tmp | ||||
| rm -rf sheetjs-nexe | ||||
| mkdir sheetjs-nexe | ||||
| cd sheetjs-nexe | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| 
 | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz exit-on-epipe commander@2 | ||||
| 
 | ||||
| ## NOTE: these steps are for darwin-x64 | ||||
| 
 | ||||
| npx nexe -t 14.15.3 xlsx-cli.js | ||||
| 
 | ||||
| ./xlsx-cli pres.numbers | ||||
							
								
								
									
										65
									
								
								tests/cli-nodesea.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										65
									
								
								tests/cli-nodesea.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,65 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/nodesea | ||||
| cd /tmp | ||||
| rm -rf sheetjs-sea | ||||
| mkdir sheetjs-sea | ||||
| cd sheetjs-sea | ||||
| 
 | ||||
| node --version | ||||
| 
 | ||||
| npm init -y | ||||
| 
 | ||||
| cat >sheet2csv.js <<EOF | ||||
| // For NodeJS SEA, the CommonJS \`require\` must be used | ||||
| const { createRequire } = require('node:module'); | ||||
| require = createRequire(__filename); | ||||
| const { readFile, utils } = require("xlsx"); | ||||
| 
 | ||||
| // argv[2] is the first argument to the script | ||||
| const filename = process.argv[2]; | ||||
| 
 | ||||
| // read file | ||||
| const wb = readFile(filename); | ||||
| 
 | ||||
| // generate CSV of first sheet | ||||
| const ws = wb.Sheets[wb.SheetNames[0]]; | ||||
| const csv = utils.sheet_to_csv(ws); | ||||
| 
 | ||||
| // print to terminal | ||||
| console.log(csv); | ||||
| EOF | ||||
| 
 | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz | ||||
| 
 | ||||
| ### Script Test | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| node sheet2csv.js pres.numbers | ||||
| 
 | ||||
| ### SEA Bundle | ||||
| 
 | ||||
| cat >sheet2csv.json <<EOF | ||||
| { | ||||
|   "main": "sheet2csv.js", | ||||
|   "output": "sheet2csv.blob" | ||||
| } | ||||
| EOF | ||||
| 
 | ||||
| node --experimental-sea-config sheet2csv.json | ||||
| 
 | ||||
| ## NOTE: these steps are for darwin-x64 | ||||
| 
 | ||||
| cp `which node` sheet2csv | ||||
| 
 | ||||
| codesign --remove-signature ./sheet2csv | ||||
| 
 | ||||
| npx -y postject --sentinel-fuse NODE_SEA_FUSE_fce680ab2cc467b6e072b8b5df1996b2 --macho-segment-name NODE_SEA sheet2csv NODE_SEA_BLOB sheet2csv.blob | ||||
| 
 | ||||
| codesign -s - ./sheet2csv | ||||
| 
 | ||||
| ./sheet2csv pres.numbers | ||||
| 
 | ||||
| codesign -dv ./sheet2csv | ||||
| 
 | ||||
| 
 | ||||
							
								
								
									
										20
									
								
								tests/cli-pkg.sh
									
									
									
									
									
										Executable file
									
								
							
							
								
								
								
								
								
									
									
								
							
						
						
									
										20
									
								
								tests/cli-pkg.sh
									
									
									
									
									
										Executable file
									
								
							| @ -0,0 +1,20 @@ | ||||
| #!/bin/bash | ||||
| # https://docs.sheetjs.com/docs/demos/cli/pkg | ||||
| cd /tmp | ||||
| rm -rf sheetjs-pkg | ||||
| mkdir sheetjs-pkg | ||||
| cd sheetjs-pkg | ||||
| 
 | ||||
| curl -o pres.numbers https://docs.sheetjs.com/pres.numbers | ||||
| 
 | ||||
| curl -o xlsx-cli.js https://docs.sheetjs.com/cli/xlsx-cli.js | ||||
| 
 | ||||
| npm i --save https://cdn.sheetjs.com/xlsx-0.20.2/xlsx-0.20.2.tgz exit-on-epipe commander@2 | ||||
| 
 | ||||
| ## NOTE: must downgrade to node 18 | ||||
| 
 | ||||
| npx pkg xlsx-cli.js | ||||
| 
 | ||||
| ## NOTE: these steps are for darwin-x64 | ||||
| 
 | ||||
| ./xlsx-cli-macos pres.numbers | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user