@naturalcycles/nodejs-lib
Version:
Standard library for Node.js
44 lines (43 loc) • 1.35 kB
JavaScript
// Inspired by: https://gist.github.com/Jezternz/c8e9fafc2c114e079829974e3764db75
import { _assert } from '@naturalcycles/js-lib/error/assert.js';
// export class CSVReader {
// constructor (cfg: CSVReaderConfig) {
// this.cfg = {
// delimiter: ',',
// includeHeader: true,
// ...cfg,
// }
// }
//
// public cfg: Required<CSVReaderConfig>
// }
export function csvStringParse(str, cfg = {}) {
const { firstRowIsHeader = true, columns } = cfg;
const arr = csvStringToArray(str);
let header = columns;
if (firstRowIsHeader) {
const firstRow = arr.shift();
header ||= firstRow;
}
_assert(header, `firstRowIsHeader or columns is required`);
return arr.map(row => {
// oxlint-disable-next-line unicorn/no-array-reduce
return header.reduce((obj, col, i) => {
;
obj[col] = row[i];
return obj;
}, {});
});
}
export function csvStringToArray(str) {
const objPattern = /(,|\r?\n|\r|^)(?:"([^"]*(?:""[^"]*)*)"|([^,\r\n]*))/gi;
let matches;
const arr = [[]];
while ((matches = objPattern.exec(str))) {
if (matches[1].length && matches[1] !== ',') {
arr.push([]);
}
arr[arr.length - 1].push(matches[2] ? matches[2].replaceAll('""', '"') : matches[3]);
}
return arr;
}