systemjs
This commit is contained in:
parent
9612e25631
commit
a1f9f5e4d9
@ -771,6 +771,194 @@ Click on "Click here to export" to generate a file.
|
||||
|
||||
</details>
|
||||
|
||||
## SystemJS
|
||||
|
||||
With configuration, SystemJS supports both browser and NodeJS deployments.
|
||||
|
||||
:::caution
|
||||
|
||||
This demo was written against SystemJS 0.19, the most popular SystemJS version.
|
||||
used with Angular applications. In the years since the release, Angular and
|
||||
other tools using SystemJS have switched to Webpack.
|
||||
|
||||
:::
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="browser" label="Browser">
|
||||
|
||||
SystemJS fails by default because the library does not export anything in the
|
||||
web browser. The `meta` configuration option can be used to expose `XLSX`:
|
||||
|
||||
```js
|
||||
SystemJS.config({
|
||||
meta: {
|
||||
'xlsx': {
|
||||
exports: 'XLSX' // <-- tell SystemJS to expose the XLSX variable
|
||||
}
|
||||
},
|
||||
map: {
|
||||
'xlsx': 'https://cdn.sheetjs.com/xlsx-latest/package/dist/xlsx.full.min.js',
|
||||
'fs': '', // <--|
|
||||
'crypto': '', // <--| suppress native node modules
|
||||
'stream': '' // <--|
|
||||
}
|
||||
});
|
||||
SystemJS.import('main.js'); // load `main.js`
|
||||
```
|
||||
|
||||
The `main.js` script can freely `require("xlsx")`.
|
||||
|
||||
:::caution Web Workers
|
||||
|
||||
Web Workers can load the SystemJS library with `importScripts`, but the imported
|
||||
code cannot assign the original worker's `onmessage` callback. The recommended
|
||||
approach is to expose a global from the required script, For example, supposing
|
||||
the shared name is `_cb`, the primary worker script would call the callback:
|
||||
|
||||
```js title="worker.js"
|
||||
/* main worker script */
|
||||
importScripts('system.js');
|
||||
|
||||
SystemJS.config({ /* ... browser config ... */ });
|
||||
|
||||
onmessage = function(evt) {
|
||||
SystemJS.import('workermain.js').then(function() { _cb(evt); });
|
||||
};
|
||||
```
|
||||
|
||||
The worker script would define and expose the function:
|
||||
|
||||
```js title="workermain.js"
|
||||
/* Loaded with SystemJS import */
|
||||
var XLSX = require('xlsx');
|
||||
|
||||
_cb = function(evt) { /* ... do work here ... */ };
|
||||
```
|
||||
|
||||
:::
|
||||
|
||||
</TabItem>
|
||||
<TabItem value="nodejs" label="NodeJS">
|
||||
|
||||
:::caution
|
||||
|
||||
While SystemJS works in NodeJS, the built-in `require` should be preferred.
|
||||
|
||||
:::
|
||||
|
||||
The NodeJS module entrypoint is `xlsx/xlsx.js` and should be mapped:
|
||||
|
||||
```js
|
||||
SystemJS.config({
|
||||
map: {
|
||||
"xlsx": "./node_modules/xlsx/xlsx.js"
|
||||
}
|
||||
});
|
||||
```
|
||||
|
||||
The standalone scripts require a hint that the script assigns a global:
|
||||
|
||||
```js
|
||||
SystemJS.config({
|
||||
meta: {
|
||||
"standalone": { format: "global" }
|
||||
},
|
||||
map: {
|
||||
"standalone": "xlsx.full.min.js"
|
||||
}
|
||||
});
|
||||
```
|
||||
</TabItem>
|
||||
</Tabs>
|
||||
|
||||
<details><summary><b>Complete Example</b> (click to show)</summary>
|
||||
|
||||
<Tabs>
|
||||
<TabItem value="browser" label="Browser">
|
||||
|
||||
The [Live demo](pathname:///systemjs/systemjs.html) loads SystemJS from the
|
||||
CDN, uses it to load the standalone script from the SheetJS CDN and emulate
|
||||
a `require` implementation when loading [`main.js`](pathname:///systemjs/main.js)
|
||||
|
||||
"View Source" works on the main HTML page and the `main.js` script.
|
||||
|
||||
</TabItem>
|
||||
<TabItem value="nodejs" label="NodeJS">
|
||||
|
||||
1) Install the dependencies:
|
||||
|
||||
<pre><code parentName="pre" {...{"className": "language-bash"}}>{`\
|
||||
$ npm i --save https://cdn.sheetjs.com/xlsx-${current}/xlsx-${current}.tgz systemjs@0.19`}
|
||||
</code></pre>
|
||||
|
||||
2) Save the following script to `SheetJSystem.js`:
|
||||
|
||||
```js title="SheetJSystem.js"
|
||||
const SystemJS = require('systemjs');
|
||||
|
||||
// highlight-start
|
||||
SystemJS.config({
|
||||
map: {
|
||||
'xlsx': 'node_modules/xlsx/xlsx.js',
|
||||
'fs': '@node/fs',
|
||||
'crypto': '@node/crypto',
|
||||
'stream': '@node/stream'
|
||||
}
|
||||
});
|
||||
// highlight-end
|
||||
|
||||
SystemJS.import('xlsx').then(async function(XLSX) {
|
||||
|
||||
/* fetch JSON data and parse */
|
||||
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.xlsx */
|
||||
XLSX.writeFile(workbook, "Presidents.xlsx");
|
||||
|
||||
});
|
||||
```
|
||||
|
||||
3) Run in NodeJS:
|
||||
|
||||
```bash
|
||||
node SheetJSystem.js
|
||||
```
|
||||
|
||||
If the demo worked, `Presidents.xlsx` will be created.
|
||||
|
||||
:::note
|
||||
|
||||
As it uses `fetch`, this demo requires Node 18.
|
||||
|
||||
:::
|
||||
|
||||
</TabItem>
|
||||
</Tabs>
|
||||
|
||||
</details>
|
||||
|
||||
## Vite
|
||||
|
||||
:::caution
|
||||
|
129
docz/static/systemjs/main.js
Normal file
129
docz/static/systemjs/main.js
Normal file
@ -0,0 +1,129 @@
|
||||
/* sheetjs (C) 2013-present SheetJS -- http://sheetjs.com */
|
||||
/*jshint browser:true */
|
||||
/*global XLSX */
|
||||
var XLSX = require('xlsx');
|
||||
|
||||
var global_wb;
|
||||
|
||||
var process_wb = (function() {
|
||||
var OUT = document.getElementById('out');
|
||||
var HTMLOUT = document.getElementById('htmlout');
|
||||
|
||||
var get_format = (function() {
|
||||
var radios = document.getElementsByName( "format" );
|
||||
return function() {
|
||||
for(var i = 0; i < radios.length; ++i) if(radios[i].checked || radios.length === 1) return radios[i].value;
|
||||
};
|
||||
})();
|
||||
|
||||
var to_json = function to_json(workbook) {
|
||||
var result = {};
|
||||
workbook.SheetNames.forEach(function(sheetName) {
|
||||
var roa = XLSX.utils.sheet_to_json(workbook.Sheets[sheetName]);
|
||||
if(roa.length) result[sheetName] = roa;
|
||||
});
|
||||
return JSON.stringify(result, 2, 2);
|
||||
};
|
||||
|
||||
var to_csv = function to_csv(workbook) {
|
||||
var result = [];
|
||||
workbook.SheetNames.forEach(function(sheetName) {
|
||||
var csv = XLSX.utils.sheet_to_csv(workbook.Sheets[sheetName]);
|
||||
if(csv.length){
|
||||
result.push("SHEET: " + sheetName);
|
||||
result.push("");
|
||||
result.push(csv);
|
||||
}
|
||||
});
|
||||
return result.join("\n");
|
||||
};
|
||||
|
||||
var to_fmla = function to_fmla(workbook) {
|
||||
var result = [];
|
||||
workbook.SheetNames.forEach(function(sheetName) {
|
||||
var formulae = XLSX.utils.get_formulae(workbook.Sheets[sheetName]);
|
||||
if(formulae.length){
|
||||
result.push("SHEET: " + sheetName);
|
||||
result.push("");
|
||||
result.push(formulae.join("\n"));
|
||||
}
|
||||
});
|
||||
return result.join("\n");
|
||||
};
|
||||
|
||||
var to_html = function to_html(workbook) {
|
||||
HTMLOUT.innerHTML = "";
|
||||
workbook.SheetNames.forEach(function(sheetName) {
|
||||
var htmlstr = XLSX.write(workbook, {sheet:sheetName, type:'string', bookType:'html'});
|
||||
HTMLOUT.innerHTML += htmlstr;
|
||||
});
|
||||
return "";
|
||||
};
|
||||
|
||||
return function process_wb(wb) {
|
||||
global_wb = wb;
|
||||
var output = "";
|
||||
switch(get_format()) {
|
||||
case "form": output = to_fmla(wb); break;
|
||||
case "html": output = to_html(wb); break;
|
||||
case "json": output = to_json(wb); break;
|
||||
default: output = to_csv(wb);
|
||||
}
|
||||
if(OUT.innerText === undefined) OUT.textContent = output;
|
||||
else OUT.innerText = output;
|
||||
if(typeof console !== 'undefined') console.log("output", new Date());
|
||||
};
|
||||
})();
|
||||
|
||||
var setfmt = window.setfmt = function setfmt() { if(global_wb) process_wb(global_wb); };
|
||||
|
||||
var b64it = window.b64it = (function() {
|
||||
var tarea = document.getElementById('b64data');
|
||||
return function b64it() {
|
||||
if(typeof console !== 'undefined') console.log("onload", new Date());
|
||||
var wb = XLSX.read(tarea.value, {type:'base64', WTF:false});
|
||||
process_wb(wb);
|
||||
};
|
||||
})();
|
||||
|
||||
var do_file = (function() {
|
||||
return function do_file(files) {
|
||||
var f = files[0];
|
||||
var reader = new FileReader();
|
||||
reader.onload = function(e) {
|
||||
if(typeof console !== 'undefined') console.log("onload", new Date());
|
||||
var data = e.target.result;
|
||||
data = new Uint8Array(data);
|
||||
process_wb(XLSX.read(data, {type: 'array'}));
|
||||
};
|
||||
reader.readAsArrayBuffer(f);
|
||||
};
|
||||
})();
|
||||
|
||||
(function() {
|
||||
var drop = document.getElementById('drop');
|
||||
if(!drop.addEventListener) return;
|
||||
|
||||
function handleDrop(e) {
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
do_file(e.dataTransfer.files);
|
||||
}
|
||||
|
||||
function handleDragover(e) {
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
e.dataTransfer.dropEffect = 'copy';
|
||||
}
|
||||
|
||||
drop.addEventListener('dragenter', handleDragover, false);
|
||||
drop.addEventListener('dragover', handleDragover, false);
|
||||
drop.addEventListener('drop', handleDrop, false);
|
||||
})();
|
||||
|
||||
(function() {
|
||||
var xlf = document.getElementById('xlf');
|
||||
if(!xlf.addEventListener) return;
|
||||
function handleFile(e) { do_file(e.target.files); }
|
||||
xlf.addEventListener('change', handleFile, false);
|
||||
})();
|
77
docz/static/systemjs/systemjs.html
Normal file
77
docz/static/systemjs/systemjs.html
Normal file
@ -0,0 +1,77 @@
|
||||
<!DOCTYPE html>
|
||||
<!-- sheetjs (C) 2013-present SheetJS http://sheetjs.com -->
|
||||
<!-- vim: set ts=2: -->
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
|
||||
<title>SheetJS Live Demo</title>
|
||||
<style>
|
||||
#drop{
|
||||
border:2px dashed #bbb;
|
||||
-moz-border-radius:5px;
|
||||
-webkit-border-radius:5px;
|
||||
border-radius:5px;
|
||||
padding:25px;
|
||||
text-align:center;
|
||||
font:20pt bold,"Vollkorn";color:#bbb
|
||||
}
|
||||
#b64data{
|
||||
width:100%;
|
||||
}
|
||||
a { text-decoration: none }
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<pre>
|
||||
<b><a href="http://sheetjs.com">SheetJS Data Preview Live Demo</a></b>
|
||||
(Base64 text works back to IE6; drag and drop works back to IE10)
|
||||
|
||||
<a href="https://github.com/SheetJS/js-xlsx">Source Code Repo</a>
|
||||
<a href="https://github.com/SheetJS/js-xlsx/issues">Issues? Something look weird? Click here and report an issue</a>
|
||||
Output Format: <select name="format" onchange="setfmt()">
|
||||
<option value="csv" selected> CSV</option>
|
||||
<option value="json"> JSON</option>
|
||||
<option value="form"> FORMULAE</option>
|
||||
<option value="html"> HTML</option>
|
||||
</select><br />
|
||||
<div id="drop">Drop a spreadsheet file here to see sheet data</div>
|
||||
<input type="file" name="xlfile" id="xlf" /> ... or click here to select a file
|
||||
|
||||
<textarea id="b64data">... or paste a base64-encoding here</textarea>
|
||||
<input type="button" id="dotext" value="Click here to process the base64 text" onclick="b64it();"/><br />
|
||||
<b>Advanced Demo Options:</b>
|
||||
</pre>
|
||||
<pre id="out"></pre>
|
||||
<div id="htmlout"></div>
|
||||
<br />
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.20.16/system.js"></script>
|
||||
<script>
|
||||
SystemJS.config({
|
||||
meta: {
|
||||
'xlsx': {
|
||||
exports: 'XLSX'
|
||||
}
|
||||
},
|
||||
map: {
|
||||
'xlsx': 'https://cdn.sheetjs.com/xlsx-latest/package/dist/xlsx.full.min.js',
|
||||
'fs': '',
|
||||
'crypto': '',
|
||||
'stream': ''
|
||||
}
|
||||
});
|
||||
SystemJS.import('main.js');
|
||||
</script>
|
||||
<script type="text/javascript">
|
||||
/* eslint no-use-before-define:0 */
|
||||
var _gaq = _gaq || [];
|
||||
_gaq.push(['_setAccount', 'UA-36810333-1']);
|
||||
_gaq.push(['_trackPageview']);
|
||||
|
||||
(function() {
|
||||
var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
|
||||
ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
|
||||
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
|
||||
})();
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
Loading…
Reference in New Issue
Block a user