initial commit.

This commit is contained in:
2022-06-06 02:04:50 -04:00
commit 62de970149
1557 changed files with 256441 additions and 0 deletions

60
node_modules/json2csv/lib/JSON2CSVAsyncParser.js generated vendored Normal file
View File

@@ -0,0 +1,60 @@
'use strict';
const { Transform } = require('stream');
const JSON2CSVTransform = require('./JSON2CSVTransform');
const { fastJoin } = require('./utils');
class JSON2CSVAsyncParser {
constructor(opts, transformOpts) {
this.input = new Transform(transformOpts);
this.input._read = () => {};
this.transform = new JSON2CSVTransform(opts, transformOpts);
this.processor = this.input.pipe(this.transform);
}
fromInput(input) {
if (this._input) {
throw new Error('Async parser already has an input.');
}
this._input = input;
this.input = this._input.pipe(this.processor);
return this;
}
throughTransform(transform) {
if (this._output) {
throw new Error('Can\'t add transforms once an output has been added.');
}
this.processor = this.processor.pipe(transform);
return this;
}
toOutput(output) {
if (this._output) {
throw new Error('Async parser already has an output.');
}
this._output = output;
this.processor = this.processor.pipe(output);
return this;
}
promise(returnCSV = true) {
return new Promise((resolve, reject) => {
if (!returnCSV) {
this.processor
.on('finish', () => resolve())
.on('error', err => reject(err));
return;
}
let csvBuffer = [];
this.processor
.on('data', chunk => csvBuffer.push(chunk.toString()))
.on('finish', () => resolve(fastJoin(csvBuffer, '')))
.on('error', err => reject(err));
});
}
}
module.exports = JSON2CSVAsyncParser

188
node_modules/json2csv/lib/JSON2CSVBase.js generated vendored Normal file
View File

@@ -0,0 +1,188 @@
'use strict';
const os = require('os');
const lodashGet = require('lodash.get');
const { getProp, fastJoin, flattenReducer } = require('./utils');
class JSON2CSVBase {
constructor(opts) {
this.opts = this.preprocessOpts(opts);
}
/**
* Check passing opts and set defaults.
*
* @param {Json2CsvOptions} opts Options object containing fields,
* delimiter, default value, quote mark, header, etc.
*/
preprocessOpts(opts) {
const processedOpts = Object.assign({}, opts);
processedOpts.transforms = !Array.isArray(processedOpts.transforms)
? (processedOpts.transforms ? [processedOpts.transforms] : [])
: processedOpts.transforms
processedOpts.delimiter = processedOpts.delimiter || ',';
processedOpts.eol = processedOpts.eol || os.EOL;
processedOpts.quote = typeof processedOpts.quote === 'string'
? processedOpts.quote
: '"';
processedOpts.escapedQuote = typeof processedOpts.escapedQuote === 'string'
? processedOpts.escapedQuote
: `${processedOpts.quote}${processedOpts.quote}`;
processedOpts.header = processedOpts.header !== false;
processedOpts.includeEmptyRows = processedOpts.includeEmptyRows || false;
processedOpts.withBOM = processedOpts.withBOM || false;
return processedOpts;
}
/**
* Check and normalize the fields configuration.
*
* @param {(string|object)[]} fields Fields configuration provided by the user
* or inferred from the data
* @returns {object[]} preprocessed FieldsInfo array
*/
preprocessFieldsInfo(fields) {
return fields.map((fieldInfo) => {
if (typeof fieldInfo === 'string') {
return {
label: fieldInfo,
value: (fieldInfo.includes('.') || fieldInfo.includes('['))
? row => lodashGet(row, fieldInfo, this.opts.defaultValue)
: row => getProp(row, fieldInfo, this.opts.defaultValue),
};
}
if (typeof fieldInfo === 'object') {
const defaultValue = 'default' in fieldInfo
? fieldInfo.default
: this.opts.defaultValue;
if (typeof fieldInfo.value === 'string') {
return {
label: fieldInfo.label || fieldInfo.value,
value: (fieldInfo.value.includes('.') || fieldInfo.value.includes('['))
? row => lodashGet(row, fieldInfo.value, defaultValue)
: row => getProp(row, fieldInfo.value, defaultValue),
};
}
if (typeof fieldInfo.value === 'function') {
const label = fieldInfo.label || fieldInfo.value.name || '';
const field = { label, default: defaultValue };
return {
label,
value(row) {
const value = fieldInfo.value(row, field);
return (value === null || value === undefined)
? defaultValue
: value;
},
}
}
}
throw new Error('Invalid field info option. ' + JSON.stringify(fieldInfo));
});
}
/**
* Create the title row with all the provided fields as column headings
*
* @returns {String} titles as a string
*/
getHeader() {
return fastJoin(
this.opts.fields.map(fieldInfo => this.processValue(fieldInfo.label)),
this.opts.delimiter
);
}
/**
* Preprocess each object according to the given transforms (unwind, flatten, etc.).
* @param {Object} row JSON object to be converted in a CSV row
*/
preprocessRow(row) {
return this.opts.transforms.reduce((rows, transform) =>
rows.map(row => transform(row)).reduce(flattenReducer, []),
[row]
);
}
/**
* Create the content of a specific CSV row
*
* @param {Object} row JSON object to be converted in a CSV row
* @returns {String} CSV string (row)
*/
processRow(row) {
if (!row) {
return undefined;
}
const processedRow = this.opts.fields.map(fieldInfo => this.processCell(row, fieldInfo));
if (!this.opts.includeEmptyRows && processedRow.every(field => field === undefined)) {
return undefined;
}
return fastJoin(
processedRow,
this.opts.delimiter
);
}
/**
* Create the content of a specfic CSV row cell
*
* @param {Object} row JSON object representing the CSV row that the cell belongs to
* @param {FieldInfo} fieldInfo Details of the field to process to be a CSV cell
* @returns {String} CSV string (cell)
*/
processCell(row, fieldInfo) {
return this.processValue(fieldInfo.value(row));
}
/**
* Create the content of a specfic CSV row cell
*
* @param {Any} value Value to be included in a CSV cell
* @returns {String} Value stringified and processed
*/
processValue(value) {
if (value === null || value === undefined) {
return undefined;
}
const valueType = typeof value;
if (valueType !== 'boolean' && valueType !== 'number' && valueType !== 'string') {
value = JSON.stringify(value);
if (value === undefined) {
return undefined;
}
if (value[0] === '"') {
value = value.replace(/^"(.+)"$/,'$1');
}
}
if (typeof value === 'string') {
if (this.opts.excelStrings) {
if(value.includes(this.opts.quote)) {
value = value.replace(new RegExp(this.opts.quote, 'g'), `${this.opts.escapedQuote}${this.opts.escapedQuote}`);
}
value = `"=""${value}"""`;
} else {
if(value.includes(this.opts.quote)) {
value = value.replace(new RegExp(this.opts.quote, 'g'), this.opts.escapedQuote);
}
value = `${this.opts.quote}${value}${this.opts.quote}`;
}
}
return value;
}
}
module.exports = JSON2CSVBase;

81
node_modules/json2csv/lib/JSON2CSVParser.js generated vendored Normal file
View File

@@ -0,0 +1,81 @@
'use strict';
const JSON2CSVBase = require('./JSON2CSVBase');
const { fastJoin, flattenReducer } = require('./utils');
class JSON2CSVParser extends JSON2CSVBase {
constructor(opts) {
super(opts);
if (this.opts.fields) {
this.opts.fields = this.preprocessFieldsInfo(this.opts.fields);
}
}
/**
* Main function that converts json to csv.
*
* @param {Array|Object} data Array of JSON objects to be converted to CSV
* @returns {String} The CSV formated data as a string
*/
parse(data) {
const processedData = this.preprocessData(data);
if (!this.opts.fields) {
this.opts.fields = processedData
.reduce((fields, item) => {
Object.keys(item).forEach((field) => {
if (!fields.includes(field)) {
fields.push(field)
}
});
return fields
}, []);
this.opts.fields = this.preprocessFieldsInfo(this.opts.fields);
}
const header = this.opts.header ? this.getHeader() : '';
const rows = this.processData(processedData);
const csv = (this.opts.withBOM ? '\ufeff' : '')
+ header
+ ((header && rows) ? this.opts.eol : '')
+ rows;
return csv;
}
/**
* Preprocess the data according to the give opts (unwind, flatten, etc.)
and calculate the fields and field names if they are not provided.
*
* @param {Array|Object} data Array or object to be converted to CSV
*/
preprocessData(data) {
const processedData = Array.isArray(data) ? data : [data];
if (!this.opts.fields && (processedData.length === 0 || typeof processedData[0] !== 'object')) {
throw new Error('Data should not be empty or the "fields" option should be included');
}
if (this.opts.transforms.length === 0) return processedData;
return processedData
.map(row => this.preprocessRow(row))
.reduce(flattenReducer, []);
}
/**
* Create the content row by row below the header
*
* @param {Array} data Array of JSON objects to be converted to CSV
* @returns {String} CSV string (body)
*/
processData(data) {
return fastJoin(
data.map(row => this.processRow(row)).filter(row => row), // Filter empty rows
this.opts.eol
);
}
}
module.exports = JSON2CSVParser;

203
node_modules/json2csv/lib/JSON2CSVTransform.js generated vendored Normal file
View File

@@ -0,0 +1,203 @@
'use strict';
const { Transform } = require('stream');
const Parser = require('jsonparse');
const JSON2CSVBase = require('./JSON2CSVBase');
class JSON2CSVTransform extends Transform {
constructor(opts, transformOpts) {
super(transformOpts);
// Inherit methods from JSON2CSVBase since extends doesn't
// allow multiple inheritance and manually preprocess opts
Object.getOwnPropertyNames(JSON2CSVBase.prototype)
.forEach(key => (this[key] = JSON2CSVBase.prototype[key]));
this.opts = this.preprocessOpts(opts);
this._data = '';
this._hasWritten = false;
if (this._readableState.objectMode) {
this.initObjectModeParse();
} else if (this.opts.ndjson) {
this.initNDJSONParse();
} else {
this.initJSONParser();
}
if (this.opts.withBOM) {
this.push('\ufeff');
}
if (this.opts.fields) {
this.opts.fields = this.preprocessFieldsInfo(this.opts.fields);
this.pushHeader();
}
}
/**
* Init the transform with a parser to process data in object mode.
* It receives JSON objects one by one and send them to `pushLine for processing.
*/
initObjectModeParse() {
const transform = this;
this.parser = {
write(line) {
transform.pushLine(line);
},
getPendingData() {
return undefined;
}
};
}
/**
* Init the transform with a parser to process NDJSON data.
* It maintains a buffer of received data, parses each line
* as JSON and send it to `pushLine for processing.
*/
initNDJSONParse() {
const transform = this;
this.parser = {
_data: '',
write(chunk) {
this._data += chunk.toString();
const lines = this._data
.split('\n')
.map(line => line.trim())
.filter(line => line !== '');
let pendingData = false;
lines
.forEach((line, i) => {
try {
transform.pushLine(JSON.parse(line));
} catch(e) {
if (i === lines.length - 1) {
pendingData = true;
} else {
e.message = `Invalid JSON (${line})`
transform.emit('error', e);
}
}
});
this._data = pendingData
? this._data.slice(this._data.lastIndexOf('\n'))
: '';
},
getPendingData() {
return this._data;
}
};
}
/**
* Init the transform with a parser to process JSON data.
* It maintains a buffer of received data, parses each as JSON
* item if the data is an array or the data itself otherwise
* and send it to `pushLine` for processing.
*/
initJSONParser() {
const transform = this;
this.parser = new Parser();
this.parser.onValue = function (value) {
if (this.stack.length !== this.depthToEmit) return;
transform.pushLine(value);
}
this.parser._onToken = this.parser.onToken;
this.parser.onToken = function (token, value) {
transform.parser._onToken(token, value);
if (this.stack.length === 0
&& !transform.opts.fields
&& this.mode !== Parser.C.ARRAY
&& this.mode !== Parser.C.OBJECT) {
this.onError(new Error('Data should not be empty or the "fields" option should be included'));
}
if (this.stack.length === 1) {
if(this.depthToEmit === undefined) {
// If Array emit its content, else emit itself
this.depthToEmit = (this.mode === Parser.C.ARRAY) ? 1 : 0;
}
if (this.depthToEmit !== 0 && this.stack.length === 1) {
// No need to store the whole root array in memory
this.value = undefined;
}
}
}
this.parser.getPendingData = function () {
return this.value;
}
this.parser.onError = function (err) {
if(err.message.includes('Unexpected')) {
err.message = `Invalid JSON (${err.message})`;
}
transform.emit('error', err);
}
}
/**
* Main function that send data to the parse to be processed.
*
* @param {Buffer} chunk Incoming data
* @param {String} encoding Encoding of the incoming data. Defaults to 'utf8'
* @param {Function} done Called when the proceesing of the supplied chunk is done
*/
_transform(chunk, encoding, done) {
this.parser.write(chunk);
done();
}
_flush(done) {
if (this.parser.getPendingData()) {
done(new Error('Invalid data received from stdin', this.parser.getPendingData()));
}
done();
}
/**
* Generate the csv header and pushes it downstream.
*/
pushHeader() {
if (this.opts.header) {
const header = this.getHeader();
this.emit('header', header);
this.push(header);
this._hasWritten = true;
}
}
/**
* Transforms an incoming json data to csv and pushes it downstream.
*
* @param {Object} data JSON object to be converted in a CSV row
*/
pushLine(data) {
const processedData = this.preprocessRow(data);
if (!this._hasWritten) {
this.opts.fields = this.opts.fields || this.preprocessFieldsInfo(Object.keys(processedData[0]));
this.pushHeader();
}
processedData.forEach(row => {
const line = this.processRow(row, this.opts);
if (line === undefined) return;
this.emit('line', line);
this.push(this._hasWritten ? this.opts.eol + line : line);
this._hasWritten = true;
});
}
}
module.exports = JSON2CSVTransform;

44
node_modules/json2csv/lib/json2csv.js generated vendored Normal file
View File

@@ -0,0 +1,44 @@
'use strict';
const { Readable } = require('stream');
const JSON2CSVParser = require('./JSON2CSVParser');
const JSON2CSVAsyncParser = require('./JSON2CSVAsyncParser');
const JSON2CSVTransform = require('./JSON2CSVTransform');
const flatten = require('./transforms/flatten');
const unwind = require('./transforms/unwind');
module.exports.Parser = JSON2CSVParser;
module.exports.AsyncParser = JSON2CSVAsyncParser;
module.exports.Transform = JSON2CSVTransform;
// Convenience method to keep the API similar to version 3.X
module.exports.parse = (data, opts) => new JSON2CSVParser(opts).parse(data);
module.exports.parseAsync = (data, opts, transformOpts) => {
try {
if (!(data instanceof Readable)) {
transformOpts = Object.assign({}, transformOpts, { objectMode: true });
}
const asyncParser = new JSON2CSVAsyncParser(opts, transformOpts);
const promise = asyncParser.promise();
if (Array.isArray(data)) {
data.forEach(item => asyncParser.input.push(item));
asyncParser.input.push(null);
} else if (data instanceof Readable) {
asyncParser.fromInput(data);
} else {
asyncParser.input.push(data);
asyncParser.input.push(null);
}
return promise;
} catch (err) {
return Promise.reject(err);
}
};
module.exports.transforms = {
flatten,
unwind,
};

37
node_modules/json2csv/lib/transforms/flatten.js generated vendored Normal file
View File

@@ -0,0 +1,37 @@
/**
* Performs the flattening of a data row recursively
*
* @param {String} separator Separator to be used as the flattened field name
* @returns {Object => Object} Flattened object
*/
function flatten({ objects = true, arrays = false, separator = '.' } = {}) {
function step (obj, flatDataRow, currentPath) {
Object.keys(obj).forEach((key) => {
const newPath = currentPath ? `${currentPath}${separator}${key}` : key;
const value = obj[key];
if (objects
&& typeof value === 'object'
&& value !== null
&& !Array.isArray(value)
&& Object.prototype.toString.call(value.toJSON) !== '[object Function]'
&& Object.keys(value).length) {
step(value, flatDataRow, newPath);
return;
}
if (arrays && Array.isArray(value)) {
step(value, flatDataRow, newPath);
return;
}
flatDataRow[newPath] = value;
});
return flatDataRow;
}
return dataRow => step(dataRow, {});
}
module.exports = flatten;

63
node_modules/json2csv/lib/transforms/unwind.js generated vendored Normal file
View File

@@ -0,0 +1,63 @@
const lodashGet = require('lodash.get');
const { setProp, unsetProp, flattenReducer } = require('../utils');
function getUnwindablePaths(obj, currentPath) {
return Object.keys(obj).reduce((unwindablePaths, key) => {
const newPath = currentPath ? `${currentPath}.${key}` : key;
const value = obj[key];
if (typeof value === 'object'
&& value !== null
&& !Array.isArray(value)
&& Object.prototype.toString.call(value.toJSON) !== '[object Function]'
&& Object.keys(value).length) {
unwindablePaths = unwindablePaths.concat(getUnwindablePaths(value, newPath));
} else if (Array.isArray(value)) {
unwindablePaths.push(newPath);
unwindablePaths = unwindablePaths.concat(value
.map(arrObj => getUnwindablePaths(arrObj, newPath))
.reduce(flattenReducer, [])
.filter((item, index, arr) => arr.indexOf(item) !== index));
}
return unwindablePaths;
}, []);
}
/**
* Performs the unwind recursively in specified sequence
*
* @param {String[]} unwindPaths The paths as strings to be used to deconstruct the array
* @returns {Object => Array} Array of objects containing all rows after unwind of chosen paths
*/
function unwind({ paths = undefined, blankOut = false } = {}) {
function unwindReducer(rows, unwindPath) {
return rows
.map(row => {
const unwindArray = lodashGet(row, unwindPath);
if (!Array.isArray(unwindArray)) {
return row;
}
if (!unwindArray.length) {
return unsetProp(row, unwindPath);
}
return unwindArray.map((unwindRow, index) => {
const clonedRow = (blankOut && index > 0)
? {}
: row;
return setProp(clonedRow, unwindPath, unwindRow);
});
})
.reduce(flattenReducer, []);
}
paths = Array.isArray(paths) ? paths : (paths ? [paths] : undefined);
return dataRow => (paths || getUnwindablePaths(dataRow)).reduce(unwindReducer, [dataRow]);
}
module.exports = unwind;

72
node_modules/json2csv/lib/utils.js generated vendored Normal file
View File

@@ -0,0 +1,72 @@
'use strict';
function getProp(obj, path, defaultValue) {
return obj[path] === undefined ? defaultValue : obj[path];
}
function setProp(obj, path, value) {
const pathArray = Array.isArray(path) ? path : path.split('.');
const [key, ...restPath] = pathArray;
return {
...obj,
[key]: pathArray.length > 1 ? setProp(obj[key] || {}, restPath, value) : value
};
}
function unsetProp(obj, path) {
const pathArray = Array.isArray(path) ? path : path.split('.');
const [key, ...restPath] = pathArray;
if (typeof obj[key] !== 'object') {
// This will never be hit in the current code because unwind does the check before calling unsetProp
/* istanbul ignore next */
return obj;
}
if (pathArray.length === 1) {
return Object.keys(obj)
.filter(prop => prop !== key)
.reduce((acc, prop) => Object.assign(acc, { [prop]: obj[prop] }), {});
}
return Object.keys(obj)
.reduce((acc, prop) => ({
...acc,
[prop]: prop !== key ? obj[prop] : unsetProp(obj[key], restPath),
}), {});
}
function flattenReducer(acc, arr) {
try {
// This is faster but susceptible to `RangeError: Maximum call stack size exceeded`
acc.push(...arr);
return acc;
} catch (err) {
// Fallback to a slower but safer option
return acc.concat(arr);
}
}
function fastJoin(arr, separator) {
let isFirst = true;
return arr.reduce((acc, elem) => {
if (elem === null || elem === undefined) {
elem = '';
}
if (isFirst) {
isFirst = false;
return `${elem}`;
}
return `${acc}${separator}${elem}`;
}, '');
}
module.exports = {
getProp,
setProp,
unsetProp,
fastJoin,
flattenReducer
};