[Example 4.1: Using `CSVNormalizer` and `CSVDenormalizer`](./ex4_1.js) ([input](./data/ex4_1-in.csv), [output](./data/ex4_1-out.csv))
[Example 4.2: Using `CSVNormalizer` and `CSVDenormalizer` with `CSVTransformer`](./ex4_2.js) ([input](./data/ex4_2-in.csv), [output](./data/ex4_2-out.csv))
+
+[Example 4.3: Using `CSVNormalizer.toObject()`](./ex4_3.js) ([input](./data/ex4_3-in.csv), [output](./data/ex4_3-out.csv))
--- /dev/null
+a,b,c,🏴☠️,😂\r
+111,222,333,444,555\r
+111,222,333,444,555\r
+111,222,333,444,555\r
--- /dev/null
+a,b,c,🏴☠️,😂\r
+intercepted: 111,intercepted: 222,intercepted: 333,intercepted: 444,intercepted: 555\r
+intercepted: 111,intercepted: 222,intercepted: 333,intercepted: 444,intercepted: 555\r
+intercepted: 111,intercepted: 222,intercepted: 333,intercepted: 444,intercepted: 555\r
--- /dev/null
+// ## Example 4.3: Using `CSVNormalizer.toObject()`
+//
+// Use the static method `CSVNormalizer.toObject()` if you just want to read the values of `CSVNormalizerField`.
+// For more advanced usage, such as keeping the underlying `row` object in sync with changes to the value, see
+// `CSVNormalizer.toFieldMap()`.
+
+import { CSVReader, CSVWriter, CSVNormalizer, CSVDenormalizer, CSVTransformer } from '../src/index.js';
+/** @import { CSVNormalizerHeader, CSVNormalizerField } from '../src/index.js'; */
+
+/** @type {Array<CSVNormalizerHeader>} */
+const headers = [
+ { name: 'a' },
+ { name: 'b' },
+ { name: 'c' },
+ { name: '🏴☠️' },
+ { name: '😂' }
+];
+
+/**
+ * @param {Array<CSVNormalizerField>} row
+ * @returns {Array<CSVNormalizerField>}
+ */
+function transform(row) {
+ const obj = CSVNormalizer.toObject(row);
+ const { a, b, c } = obj; // Destructuring works
+ const pirate = obj['🏴☠️']; // Access by field name works
+ const laughing = obj['😂'];
+ const out = [ // Manually construct a new output row
+ { name: 'a', value: `intercepted: ${a}` },
+ { name: 'b', value: `intercepted: ${b}` },
+ { name: 'c', value: `intercepted: ${c}` },
+ { name: '🏴☠️', value: `intercepted: ${pirate}` },
+ { name: '😂', value: `intercepted: ${laughing}` },
+ ];
+ return out;
+}
+
+await new CSVReader(new URL('./data/ex4_3-in.csv', import.meta.url))
+ .pipeThrough(new CSVNormalizer(headers))
+ .pipeThrough(new CSVTransformer(transform))
+ .pipeThrough(new CSVDenormalizer())
+ .pipeTo(new CSVWriter(new URL('./data/ex4_3-out.csv', import.meta.url)));
console.warn(`Could not fix date: "${original}". Passing through as a string.`);
return original;
}
+
+ /**
+ * Create a simple object that maps each `CSVNormalizerField` `name` to its `value`. Useful if you just want to read all the
+ * values in a normalized CSV row.
+ *
+ * The `displayName` and `emptyField` values of a field are lost in the resulting object.
+ * @param {Array<CSVNormalizerField>} row A normalized CSV row.
+ * @returns {Record<string,any>} An object where each key is a field `name` and the value is the field's `value`.
+ */
+ static toObject(row) {
+ const object = {};
+ for (const field of row) {
+ object[field.name] = field.value;
+ }
+ return object;
+ }
}
/**
}
});
+suite('CSVNormalizer.toObject', { concurrency: true }, () => {
+ test('converts simple fields', { concurrency: true }, async () => {
+ const row = [
+ { name: 'a', value: 1 },
+ { name: 'b', value: 2 },
+ { name: 'c', value: 3 }
+ ];
+ const obj = CSVNormalizer.toObject(row);
+ deepStrictEqual(obj.a, 1);
+ deepStrictEqual(obj.b, 2);
+ deepStrictEqual(obj.c, 3);
+ });
+ test('converts complex field names', { concurrency: true }, async () => {
+ const row = [
+ { name: '🏴☠️', value: 1 }
+ ];
+ const obj = CSVNormalizer.toObject(row);
+ deepStrictEqual(obj['🏴☠️'], 1);
+ });
+ test('converts complex field values', { concurrency: true }, async () => {
+ const row = [
+ { name: 'a', value: { 'b': [1n] } }
+ ];
+ const obj = CSVNormalizer.toObject(row);
+ deepStrictEqual(obj.a.b[0], 1n);
+ });
+});
+
suite('CSVNormalizer', { concurrency: true }, () => {
test('can remove extra columns in CSV', { concurrency: true }, async () => {
await createCSVMockStream([