jtcsv 3.0.0 → 3.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (258) hide show
  1. package/README.md +205 -146
  2. package/bin/jtcsv.ts +280 -202
  3. package/browser.d.ts +142 -0
  4. package/dist/benchmark.js +446 -0
  5. package/dist/benchmark.js.map +1 -0
  6. package/dist/bin/jtcsv.js +1940 -0
  7. package/dist/bin/jtcsv.js.map +1 -0
  8. package/dist/csv-to-json.js +1262 -0
  9. package/dist/csv-to-json.js.map +1 -0
  10. package/dist/errors.js +291 -0
  11. package/dist/errors.js.map +1 -0
  12. package/dist/eslint.config.js +147 -0
  13. package/dist/eslint.config.js.map +1 -0
  14. package/dist/index-core.js +95 -0
  15. package/dist/index-core.js.map +1 -0
  16. package/dist/index.js +93 -0
  17. package/dist/index.js.map +1 -0
  18. package/dist/json-save.js +229 -0
  19. package/dist/json-save.js.map +1 -0
  20. package/dist/json-to-csv.js +576 -0
  21. package/dist/json-to-csv.js.map +1 -0
  22. package/dist/jtcsv-core.cjs.js +336 -7
  23. package/dist/jtcsv-core.cjs.js.map +1 -1
  24. package/dist/jtcsv-core.esm.js +336 -7
  25. package/dist/jtcsv-core.esm.js.map +1 -1
  26. package/dist/jtcsv-core.umd.js +336 -7
  27. package/dist/jtcsv-core.umd.js.map +1 -1
  28. package/dist/jtcsv-full.cjs.js +336 -7
  29. package/dist/jtcsv-full.cjs.js.map +1 -1
  30. package/dist/jtcsv-full.esm.js +336 -7
  31. package/dist/jtcsv-full.esm.js.map +1 -1
  32. package/dist/jtcsv-full.umd.js +336 -7
  33. package/dist/jtcsv-full.umd.js.map +1 -1
  34. package/dist/jtcsv-workers.esm.js +9 -0
  35. package/dist/jtcsv-workers.esm.js.map +1 -1
  36. package/dist/jtcsv-workers.umd.js +9 -0
  37. package/dist/jtcsv-workers.umd.js.map +1 -1
  38. package/dist/jtcsv.cjs.js +1998 -2092
  39. package/dist/jtcsv.cjs.js.map +1 -1
  40. package/dist/jtcsv.esm.js +1994 -2092
  41. package/dist/jtcsv.esm.js.map +1 -1
  42. package/dist/jtcsv.umd.js +2157 -2251
  43. package/dist/jtcsv.umd.js.map +1 -1
  44. package/dist/plugins/express-middleware/index.js +350 -0
  45. package/dist/plugins/express-middleware/index.js.map +1 -0
  46. package/dist/plugins/fastify-plugin/index.js +315 -0
  47. package/dist/plugins/fastify-plugin/index.js.map +1 -0
  48. package/dist/plugins/hono/index.js +111 -0
  49. package/dist/plugins/hono/index.js.map +1 -0
  50. package/dist/plugins/nestjs/index.js +112 -0
  51. package/dist/plugins/nestjs/index.js.map +1 -0
  52. package/dist/plugins/nuxt/index.js +53 -0
  53. package/dist/plugins/nuxt/index.js.map +1 -0
  54. package/dist/plugins/remix/index.js +133 -0
  55. package/dist/plugins/remix/index.js.map +1 -0
  56. package/dist/plugins/sveltekit/index.js +155 -0
  57. package/dist/plugins/sveltekit/index.js.map +1 -0
  58. package/dist/plugins/trpc/index.js +136 -0
  59. package/dist/plugins/trpc/index.js.map +1 -0
  60. package/dist/run-demo.js +49 -0
  61. package/dist/run-demo.js.map +1 -0
  62. package/dist/src/browser/browser-functions.js +193 -0
  63. package/dist/src/browser/browser-functions.js.map +1 -0
  64. package/dist/src/browser/core.js +123 -0
  65. package/dist/src/browser/core.js.map +1 -0
  66. package/dist/src/browser/csv-to-json-browser.js +353 -0
  67. package/dist/src/browser/csv-to-json-browser.js.map +1 -0
  68. package/dist/src/browser/errors-browser.js +219 -0
  69. package/dist/src/browser/errors-browser.js.map +1 -0
  70. package/dist/src/browser/extensions/plugins.js +106 -0
  71. package/dist/src/browser/extensions/plugins.js.map +1 -0
  72. package/dist/src/browser/extensions/workers.js +66 -0
  73. package/dist/src/browser/extensions/workers.js.map +1 -0
  74. package/dist/src/browser/index.js +140 -0
  75. package/dist/src/browser/index.js.map +1 -0
  76. package/dist/src/browser/json-to-csv-browser.js +225 -0
  77. package/dist/src/browser/json-to-csv-browser.js.map +1 -0
  78. package/dist/src/browser/streams.js +340 -0
  79. package/dist/src/browser/streams.js.map +1 -0
  80. package/dist/src/browser/workers/csv-parser.worker.js +264 -0
  81. package/dist/src/browser/workers/csv-parser.worker.js.map +1 -0
  82. package/dist/src/browser/workers/worker-pool.js +338 -0
  83. package/dist/src/browser/workers/worker-pool.js.map +1 -0
  84. package/dist/src/core/delimiter-cache.js +196 -0
  85. package/dist/src/core/delimiter-cache.js.map +1 -0
  86. package/dist/src/core/node-optimizations.js +279 -0
  87. package/dist/src/core/node-optimizations.js.map +1 -0
  88. package/dist/src/core/plugin-system.js +399 -0
  89. package/dist/src/core/plugin-system.js.map +1 -0
  90. package/dist/src/core/transform-hooks.js +348 -0
  91. package/dist/src/core/transform-hooks.js.map +1 -0
  92. package/dist/src/engines/fast-path-engine-new.js +262 -0
  93. package/dist/src/engines/fast-path-engine-new.js.map +1 -0
  94. package/dist/src/engines/fast-path-engine.js +671 -0
  95. package/dist/src/engines/fast-path-engine.js.map +1 -0
  96. package/dist/src/errors.js +18 -0
  97. package/dist/src/errors.js.map +1 -0
  98. package/dist/src/formats/ndjson-parser.js +332 -0
  99. package/dist/src/formats/ndjson-parser.js.map +1 -0
  100. package/dist/src/formats/tsv-parser.js +230 -0
  101. package/dist/src/formats/tsv-parser.js.map +1 -0
  102. package/dist/src/index-with-plugins.js +259 -0
  103. package/dist/src/index-with-plugins.js.map +1 -0
  104. package/dist/src/types/index.js +3 -0
  105. package/dist/src/types/index.js.map +1 -0
  106. package/dist/src/utils/bom-utils.js +267 -0
  107. package/dist/src/utils/bom-utils.js.map +1 -0
  108. package/dist/src/utils/encoding-support.js +77 -0
  109. package/dist/src/utils/encoding-support.js.map +1 -0
  110. package/dist/src/utils/schema-validator.js +609 -0
  111. package/dist/src/utils/schema-validator.js.map +1 -0
  112. package/dist/src/utils/transform-loader.js +281 -0
  113. package/dist/src/utils/transform-loader.js.map +1 -0
  114. package/dist/src/utils/validators.js +40 -0
  115. package/dist/src/utils/validators.js.map +1 -0
  116. package/dist/src/utils/zod-adapter.js +144 -0
  117. package/dist/src/utils/zod-adapter.js.map +1 -0
  118. package/{src → dist/src}/web-server/index.js +251 -286
  119. package/dist/src/web-server/index.js.map +1 -0
  120. package/dist/src/workers/csv-multithreaded.js +211 -0
  121. package/dist/src/workers/csv-multithreaded.js.map +1 -0
  122. package/dist/src/workers/csv-parser.worker.js +179 -0
  123. package/dist/src/workers/csv-parser.worker.js.map +1 -0
  124. package/dist/src/workers/worker-pool.js +228 -0
  125. package/dist/src/workers/worker-pool.js.map +1 -0
  126. package/dist/stream-csv-to-json.js +665 -0
  127. package/dist/stream-csv-to-json.js.map +1 -0
  128. package/dist/stream-json-to-csv.js +389 -0
  129. package/dist/stream-json-to-csv.js.map +1 -0
  130. package/examples/advanced/conditional-transformations.ts +2 -2
  131. package/examples/advanced/performance-optimization.ts +2 -2
  132. package/examples/cli-advanced-usage.md +2 -0
  133. package/examples/cli-tool.ts +1 -1
  134. package/examples/large-dataset-example.ts +2 -2
  135. package/examples/simple-usage.ts +2 -2
  136. package/examples/streaming-example.ts +1 -1
  137. package/index.d.ts +186 -15
  138. package/package.json +43 -108
  139. package/plugins.d.ts +37 -0
  140. package/schema.d.ts +103 -0
  141. package/src/browser/csv-to-json-browser.ts +233 -3
  142. package/src/browser/errors-browser.ts +45 -28
  143. package/src/browser/json-to-csv-browser.ts +81 -5
  144. package/src/browser/streams.ts +73 -6
  145. package/src/core/delimiter-cache.ts +21 -11
  146. package/src/core/plugin-system.ts +343 -155
  147. package/src/core/transform-hooks.ts +20 -12
  148. package/src/engines/fast-path-engine.ts +48 -32
  149. package/src/errors.ts +1 -72
  150. package/src/formats/ndjson-parser.ts +6 -0
  151. package/src/formats/tsv-parser.ts +6 -0
  152. package/src/types/index.ts +21 -1
  153. package/src/utils/validators.ts +35 -0
  154. package/src/web-server/index.ts +1 -1
  155. package/bin/jtcsv.js +0 -2532
  156. package/csv-to-json.js +0 -711
  157. package/errors.js +0 -394
  158. package/examples/advanced/conditional-transformations.js +0 -446
  159. package/examples/advanced/csv-parser.worker.js +0 -89
  160. package/examples/advanced/nested-objects-example.js +0 -306
  161. package/examples/advanced/performance-optimization.js +0 -504
  162. package/examples/advanced/run-demo-server.js +0 -116
  163. package/examples/cli-batch-processing.js +0 -38
  164. package/examples/cli-tool.js +0 -183
  165. package/examples/error-handling.js +0 -338
  166. package/examples/express-api.js +0 -164
  167. package/examples/large-dataset-example.js +0 -182
  168. package/examples/ndjson-processing.js +0 -434
  169. package/examples/plugin-excel-exporter.js +0 -406
  170. package/examples/schema-validation.js +0 -640
  171. package/examples/simple-usage.js +0 -282
  172. package/examples/streaming-example.js +0 -418
  173. package/examples/web-workers-advanced.js +0 -28
  174. package/index.js +0 -82
  175. package/json-save.js +0 -255
  176. package/json-to-csv.js +0 -668
  177. package/plugins/README.md +0 -91
  178. package/plugins/express-middleware/README.md +0 -83
  179. package/plugins/express-middleware/example.js +0 -135
  180. package/plugins/express-middleware/example.ts +0 -135
  181. package/plugins/express-middleware/index.d.ts +0 -114
  182. package/plugins/express-middleware/index.js +0 -512
  183. package/plugins/express-middleware/index.ts +0 -557
  184. package/plugins/express-middleware/package.json +0 -52
  185. package/plugins/fastify-plugin/index.js +0 -404
  186. package/plugins/fastify-plugin/index.ts +0 -443
  187. package/plugins/fastify-plugin/package.json +0 -55
  188. package/plugins/hono/README.md +0 -28
  189. package/plugins/hono/index.d.ts +0 -12
  190. package/plugins/hono/index.js +0 -36
  191. package/plugins/hono/index.ts +0 -226
  192. package/plugins/hono/package.json +0 -35
  193. package/plugins/nestjs/README.md +0 -35
  194. package/plugins/nestjs/index.d.ts +0 -25
  195. package/plugins/nestjs/index.js +0 -77
  196. package/plugins/nestjs/index.ts +0 -201
  197. package/plugins/nestjs/package.json +0 -37
  198. package/plugins/nextjs-api/README.md +0 -57
  199. package/plugins/nextjs-api/examples/ConverterComponent.jsx +0 -386
  200. package/plugins/nextjs-api/examples/ConverterComponent.tsx +0 -386
  201. package/plugins/nextjs-api/examples/api-convert.js +0 -67
  202. package/plugins/nextjs-api/examples/api-convert.ts +0 -67
  203. package/plugins/nextjs-api/index.js +0 -387
  204. package/plugins/nextjs-api/index.tsx +0 -339
  205. package/plugins/nextjs-api/package.json +0 -63
  206. package/plugins/nextjs-api/route.js +0 -370
  207. package/plugins/nextjs-api/route.ts +0 -370
  208. package/plugins/nuxt/README.md +0 -24
  209. package/plugins/nuxt/index.js +0 -21
  210. package/plugins/nuxt/index.ts +0 -94
  211. package/plugins/nuxt/package.json +0 -35
  212. package/plugins/nuxt/runtime/composables/useJtcsv.js +0 -6
  213. package/plugins/nuxt/runtime/composables/useJtcsv.ts +0 -100
  214. package/plugins/nuxt/runtime/plugin.js +0 -6
  215. package/plugins/nuxt/runtime/plugin.ts +0 -71
  216. package/plugins/remix/README.md +0 -26
  217. package/plugins/remix/index.d.ts +0 -16
  218. package/plugins/remix/index.js +0 -62
  219. package/plugins/remix/index.ts +0 -260
  220. package/plugins/remix/package.json +0 -35
  221. package/plugins/sveltekit/README.md +0 -28
  222. package/plugins/sveltekit/index.d.ts +0 -17
  223. package/plugins/sveltekit/index.js +0 -54
  224. package/plugins/sveltekit/index.ts +0 -301
  225. package/plugins/sveltekit/package.json +0 -33
  226. package/plugins/trpc/README.md +0 -25
  227. package/plugins/trpc/index.d.ts +0 -7
  228. package/plugins/trpc/index.js +0 -32
  229. package/plugins/trpc/index.ts +0 -267
  230. package/plugins/trpc/package.json +0 -34
  231. package/src/browser/browser-functions.js +0 -219
  232. package/src/browser/core.js +0 -92
  233. package/src/browser/csv-to-json-browser.js +0 -722
  234. package/src/browser/errors-browser.js +0 -212
  235. package/src/browser/extensions/plugins.js +0 -92
  236. package/src/browser/extensions/workers.js +0 -39
  237. package/src/browser/index.js +0 -113
  238. package/src/browser/json-to-csv-browser.js +0 -319
  239. package/src/browser/streams.js +0 -403
  240. package/src/browser/workers/csv-parser.worker.js +0 -377
  241. package/src/browser/workers/worker-pool.js +0 -527
  242. package/src/core/delimiter-cache.js +0 -200
  243. package/src/core/node-optimizations.js +0 -408
  244. package/src/core/plugin-system.js +0 -494
  245. package/src/core/transform-hooks.js +0 -350
  246. package/src/engines/fast-path-engine-new.js +0 -338
  247. package/src/engines/fast-path-engine.js +0 -844
  248. package/src/errors.js +0 -26
  249. package/src/formats/ndjson-parser.js +0 -467
  250. package/src/formats/tsv-parser.js +0 -339
  251. package/src/index-with-plugins.js +0 -378
  252. package/src/utils/bom-utils.js +0 -259
  253. package/src/utils/encoding-support.js +0 -124
  254. package/src/utils/schema-validator.js +0 -594
  255. package/src/utils/transform-loader.js +0 -205
  256. package/src/utils/zod-adapter.js +0 -170
  257. package/stream-csv-to-json.js +0 -560
  258. package/stream-json-to-csv.js +0 -465
@@ -1,640 +0,0 @@
1
- /**
2
- * Schema Validation Examples for jtcsv
3
- *
4
- * jtcsv supports JSON Schema validation for ensuring
5
- * data integrity during CSV/JSON conversions.
6
- */
7
-
8
- const {
9
- jsonToCsv,
10
- csvToJson,
11
- ValidationError
12
- } = require('jtcsv');
13
-
14
- // =============================================================================
15
- // Example 1: Basic Schema Validation
16
- // =============================================================================
17
-
18
- function basicSchemaValidation() {
19
- console.log('\n=== Basic Schema Validation ===\n');
20
-
21
- // Define schema for user data
22
- const userSchema = {
23
- type: 'object',
24
- required: ['name', 'email'],
25
- properties: {
26
- name: {
27
- type: 'string',
28
- minLength: 1,
29
- maxLength: 100
30
- },
31
- email: {
32
- type: 'string',
33
- pattern: '^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$'
34
- },
35
- age: {
36
- type: 'number',
37
- minimum: 0,
38
- maximum: 150
39
- }
40
- }
41
- };
42
-
43
- // Valid data
44
- const validUsers = [
45
- { name: 'John Doe', email: 'john@example.com', age: 30 },
46
- { name: 'Jane Smith', email: 'jane@test.org', age: 25 }
47
- ];
48
-
49
- try {
50
- const csv = jsonToCsv(validUsers, { schema: userSchema });
51
- console.log('Valid data converted successfully:');
52
- console.log(csv);
53
- } catch (error) {
54
- console.log('Unexpected error:', error.message);
55
- }
56
-
57
- // Invalid data
58
- const invalidUsers = [
59
- { name: '', email: 'john@example.com', age: 30 }, // Empty name
60
- { name: 'Jane', email: 'invalid-email', age: -5 } // Bad email, negative age
61
- ];
62
-
63
- try {
64
- jsonToCsv(invalidUsers, { schema: userSchema });
65
- } catch (error) {
66
- if (error instanceof ValidationError) {
67
- console.log('\nValidation failed (expected):');
68
- console.log('Error:', error.message);
69
- }
70
- }
71
- }
72
-
73
- // =============================================================================
74
- // Example 2: Complex Nested Schema
75
- // =============================================================================
76
-
77
- function nestedSchemaValidation() {
78
- console.log('\n=== Nested Schema Validation ===\n');
79
-
80
- const orderSchema = {
81
- type: 'object',
82
- required: ['orderId', 'customer', 'total'],
83
- properties: {
84
- orderId: {
85
- type: 'string',
86
- pattern: '^ORD-[0-9]{6}$' // Format: ORD-123456
87
- },
88
- customer: {
89
- type: 'object',
90
- required: ['name', 'email'],
91
- properties: {
92
- name: { type: 'string', minLength: 1 },
93
- email: { type: 'string' }
94
- }
95
- },
96
- items: {
97
- type: 'array',
98
- minItems: 1,
99
- items: {
100
- type: 'object',
101
- required: ['sku', 'quantity'],
102
- properties: {
103
- sku: { type: 'string' },
104
- quantity: { type: 'number', minimum: 1 }
105
- }
106
- }
107
- },
108
- total: {
109
- type: 'number',
110
- minimum: 0
111
- },
112
- status: {
113
- type: 'string',
114
- enum: ['pending', 'processing', 'shipped', 'delivered']
115
- }
116
- }
117
- };
118
-
119
- const orders = [
120
- {
121
- orderId: 'ORD-123456',
122
- customer: { name: 'John Doe', email: 'john@example.com' },
123
- items: [
124
- { sku: 'PROD-001', quantity: 2 },
125
- { sku: 'PROD-002', quantity: 1 }
126
- ],
127
- total: 149.99,
128
- status: 'processing'
129
- }
130
- ];
131
-
132
- try {
133
- const csv = jsonToCsv(orders, {
134
- schema: orderSchema,
135
- delimiter: ','
136
- });
137
- console.log('Order with nested data converted:');
138
- console.log(csv);
139
- } catch (error) {
140
- console.log('Error:', error.message);
141
- }
142
- }
143
-
144
- // =============================================================================
145
- // Example 3: Schema with Custom Formats
146
- // =============================================================================
147
-
148
- function customFormatSchema() {
149
- console.log('\n=== Custom Format Schema ===\n');
150
-
151
- const eventSchema = {
152
- type: 'object',
153
- required: ['eventId', 'timestamp', 'eventType'],
154
- properties: {
155
- eventId: {
156
- type: 'string',
157
- pattern: '^EVT-[A-Z0-9]{8}$' // EVT-XXXXXXXX
158
- },
159
- timestamp: {
160
- type: 'string',
161
- pattern: '^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}(\\.\\d{3})?Z$' // ISO 8601
162
- },
163
- eventType: {
164
- type: 'string',
165
- enum: ['click', 'view', 'purchase', 'signup', 'login', 'logout']
166
- },
167
- userId: {
168
- type: 'string',
169
- pattern: '^USR-\\d{6}$' // Optional but must match if present
170
- },
171
- metadata: {
172
- type: 'object' // Allow any object structure
173
- }
174
- }
175
- };
176
-
177
- const events = [
178
- {
179
- eventId: 'EVT-A1B2C3D4',
180
- timestamp: '2024-01-15T10:30:00.123Z',
181
- eventType: 'purchase',
182
- userId: 'USR-000123',
183
- metadata: { productId: 'PRD-001', amount: 99.99 }
184
- },
185
- {
186
- eventId: 'EVT-E5F6G7H8',
187
- timestamp: '2024-01-15T10:31:00Z',
188
- eventType: 'view',
189
- metadata: { page: '/products', duration: 45 }
190
- }
191
- ];
192
-
193
- try {
194
- const csv = jsonToCsv(events, { schema: eventSchema });
195
- console.log('Events validated and converted:');
196
- console.log(csv);
197
- } catch (error) {
198
- console.log('Error:', error.message);
199
- }
200
- }
201
-
202
- // =============================================================================
203
- // Example 4: Array Validation
204
- // =============================================================================
205
-
206
- function arraySchemaValidation() {
207
- console.log('\n=== Array Schema Validation ===\n');
208
-
209
- const surveySchema = {
210
- type: 'object',
211
- required: ['respondentId', 'answers'],
212
- properties: {
213
- respondentId: {
214
- type: 'number',
215
- minimum: 1
216
- },
217
- answers: {
218
- type: 'array',
219
- minItems: 5,
220
- maxItems: 10,
221
- items: {
222
- type: 'number',
223
- minimum: 1,
224
- maximum: 5 // Rating 1-5
225
- }
226
- },
227
- comments: {
228
- type: 'string',
229
- maxLength: 500
230
- }
231
- }
232
- };
233
-
234
- const surveyResponses = [
235
- {
236
- respondentId: 1,
237
- answers: [5, 4, 3, 5, 4],
238
- comments: 'Great experience!'
239
- },
240
- {
241
- respondentId: 2,
242
- answers: [3, 3, 4, 4, 5, 4],
243
- comments: ''
244
- }
245
- ];
246
-
247
- try {
248
- const csv = jsonToCsv(surveyResponses, { schema: surveySchema });
249
- console.log('Survey responses validated:');
250
- console.log(csv);
251
- } catch (error) {
252
- console.log('Error:', error.message);
253
- }
254
-
255
- // Test with invalid data
256
- console.log('\nTesting invalid survey data:');
257
- const invalidSurvey = [
258
- {
259
- respondentId: 1,
260
- answers: [5, 4, 6, 5, 4], // 6 is out of range (max 5)
261
- comments: 'Test'
262
- }
263
- ];
264
-
265
- try {
266
- jsonToCsv(invalidSurvey, { schema: surveySchema });
267
- } catch (error) {
268
- console.log('Validation error (expected):', error.message);
269
- }
270
- }
271
-
272
- // =============================================================================
273
- // Example 5: Conditional Schema (oneOf/anyOf)
274
- // =============================================================================
275
-
276
- function conditionalSchema() {
277
- console.log('\n=== Conditional Schema ===\n');
278
-
279
- // Schema where payment method determines required fields
280
- const paymentSchema = {
281
- type: 'object',
282
- required: ['paymentId', 'method', 'amount'],
283
- properties: {
284
- paymentId: { type: 'string' },
285
- method: {
286
- type: 'string',
287
- enum: ['credit_card', 'bank_transfer', 'crypto']
288
- },
289
- amount: {
290
- type: 'number',
291
- minimum: 0.01
292
- },
293
- // Credit card fields
294
- cardLast4: {
295
- type: 'string',
296
- pattern: '^\\d{4}$'
297
- },
298
- // Bank transfer fields
299
- bankAccount: {
300
- type: 'string'
301
- },
302
- // Crypto fields
303
- walletAddress: {
304
- type: 'string',
305
- pattern: '^0x[a-fA-F0-9]{40}$'
306
- }
307
- }
308
- };
309
-
310
- const payments = [
311
- {
312
- paymentId: 'PAY-001',
313
- method: 'credit_card',
314
- amount: 99.99,
315
- cardLast4: '1234'
316
- },
317
- {
318
- paymentId: 'PAY-002',
319
- method: 'bank_transfer',
320
- amount: 500.00,
321
- bankAccount: 'GB82WEST12345698765432'
322
- },
323
- {
324
- paymentId: 'PAY-003',
325
- method: 'crypto',
326
- amount: 250.00,
327
- walletAddress: '0x742d35Cc6634C0532925a3b844Bc9e7595f8e21d'
328
- }
329
- ];
330
-
331
- try {
332
- const csv = jsonToCsv(payments, { schema: paymentSchema });
333
- console.log('Payments validated:');
334
- console.log(csv);
335
- } catch (error) {
336
- console.log('Error:', error.message);
337
- }
338
- }
339
-
340
- // =============================================================================
341
- // Example 6: Schema for Type Coercion Hints
342
- // =============================================================================
343
-
344
- function typeCoercionSchema() {
345
- console.log('\n=== Schema for Type Hints ===\n');
346
-
347
- // Schema that helps with proper type handling
348
- const productSchema = {
349
- type: 'object',
350
- properties: {
351
- sku: { type: 'string' },
352
- name: { type: 'string' },
353
- price: { type: 'number' },
354
- quantity: { type: 'integer' },
355
- isAvailable: { type: 'boolean' },
356
- tags: {
357
- type: 'array',
358
- items: { type: 'string' }
359
- },
360
- dimensions: {
361
- type: 'object',
362
- properties: {
363
- width: { type: 'number' },
364
- height: { type: 'number' },
365
- depth: { type: 'number' }
366
- }
367
- }
368
- }
369
- };
370
-
371
- const products = [
372
- {
373
- sku: 'LAPTOP-001',
374
- name: 'Pro Laptop 15"',
375
- price: 1299.99,
376
- quantity: 50,
377
- isAvailable: true,
378
- tags: ['electronics', 'computers', 'portable'],
379
- dimensions: { width: 35.5, height: 1.8, depth: 24.0 }
380
- }
381
- ];
382
-
383
- const csv = jsonToCsv(products, {
384
- schema: productSchema,
385
- delimiter: ','
386
- });
387
- console.log('Product with type hints:');
388
- console.log(csv);
389
- }
390
-
391
- // =============================================================================
392
- // Example 7: Validation Error Details
393
- // =============================================================================
394
-
395
- function validationErrorDetails() {
396
- console.log('\n=== Validation Error Details ===\n');
397
-
398
- const strictSchema = {
399
- type: 'object',
400
- additionalProperties: false, // No extra fields allowed
401
- required: ['id', 'name', 'email', 'role'],
402
- properties: {
403
- id: {
404
- type: 'integer',
405
- minimum: 1
406
- },
407
- name: {
408
- type: 'string',
409
- minLength: 2,
410
- maxLength: 50
411
- },
412
- email: {
413
- type: 'string',
414
- pattern: '^[^@]+@[^@]+\\.[^@]+$'
415
- },
416
- role: {
417
- type: 'string',
418
- enum: ['admin', 'user', 'guest']
419
- }
420
- }
421
- };
422
-
423
- // Data with multiple validation errors
424
- const invalidData = [
425
- {
426
- id: 0, // Error: minimum is 1
427
- name: 'A', // Error: minLength is 2
428
- email: 'invalid', // Error: doesn't match pattern
429
- role: 'superuser', // Error: not in enum
430
- extra: 'field' // Error: additionalProperties false
431
- }
432
- ];
433
-
434
- try {
435
- jsonToCsv(invalidData, { schema: strictSchema });
436
- } catch (error) {
437
- if (error instanceof ValidationError) {
438
- console.log('Multiple validation errors detected:');
439
- console.log('Message:', error.message);
440
- console.log('Code:', error.code);
441
- }
442
- }
443
- }
444
-
445
- // =============================================================================
446
- // Example 8: Schema Validation with CSV Input
447
- // =============================================================================
448
-
449
- function schemaValidationOnCsvInput() {
450
- console.log('\n=== Schema Validation on CSV Input ===\n');
451
-
452
- const csv = `id,name,score,passed
453
- 1,Alice,95,true
454
- 2,Bob,87,true
455
- 3,Charlie,45,false
456
- 4,Diana,invalid,true`; // 'invalid' should be a number
457
-
458
- // First parse CSV
459
- const data = csvToJson(csv, {
460
- parseNumbers: true,
461
- parseBooleans: true
462
- });
463
-
464
- console.log('Parsed data:');
465
- data.forEach(row => {
466
- console.log(` ${row.name}: score=${row.score} (${typeof row.score})`);
467
- });
468
-
469
- // Now validate
470
- const scoreSchema = {
471
- type: 'object',
472
- properties: {
473
- id: { type: 'number' },
474
- name: { type: 'string' },
475
- score: { type: 'number', minimum: 0, maximum: 100 },
476
- passed: { type: 'boolean' }
477
- }
478
- };
479
-
480
- // Validate each row
481
- console.log('\nValidation results:');
482
- data.forEach((row, i) => {
483
- const isValid = typeof row.score === 'number' &&
484
- row.score >= 0 && row.score <= 100;
485
- console.log(` Row ${i + 1} (${row.name}): ${isValid ? 'Valid' : 'Invalid'}`);
486
- });
487
- }
488
-
489
- // =============================================================================
490
- // Example 9: Reusable Schema Definitions
491
- // =============================================================================
492
-
493
- function reusableSchemaDefinitions() {
494
- console.log('\n=== Reusable Schema Definitions ===\n');
495
-
496
- // Common field definitions
497
- const commonFields = {
498
- id: { type: 'integer', minimum: 1 },
499
- createdAt: { type: 'string' },
500
- updatedAt: { type: 'string' }
501
- };
502
-
503
- const addressSchema = {
504
- type: 'object',
505
- required: ['street', 'city', 'country'],
506
- properties: {
507
- street: { type: 'string' },
508
- city: { type: 'string' },
509
- postalCode: { type: 'string' },
510
- country: { type: 'string', minLength: 2, maxLength: 2 } // ISO country code
511
- }
512
- };
513
-
514
- // Customer schema using common fields
515
- const customerSchema = {
516
- type: 'object',
517
- required: ['id', 'name', 'email'],
518
- properties: {
519
- ...commonFields,
520
- name: { type: 'string', minLength: 1 },
521
- email: { type: 'string' },
522
- phone: { type: 'string' },
523
- billingAddress: addressSchema,
524
- shippingAddress: addressSchema
525
- }
526
- };
527
-
528
- const customers = [
529
- {
530
- id: 1,
531
- name: 'John Doe',
532
- email: 'john@example.com',
533
- phone: '+1-555-1234',
534
- billingAddress: {
535
- street: '123 Main St',
536
- city: 'New York',
537
- postalCode: '10001',
538
- country: 'US'
539
- },
540
- shippingAddress: {
541
- street: '456 Oak Ave',
542
- city: 'Brooklyn',
543
- postalCode: '11201',
544
- country: 'US'
545
- },
546
- createdAt: '2024-01-15T10:00:00Z',
547
- updatedAt: '2024-01-15T10:00:00Z'
548
- }
549
- ];
550
-
551
- try {
552
- const csv = jsonToCsv(customers, { schema: customerSchema });
553
- console.log('Customer data validated with reusable schema:');
554
- console.log(csv);
555
- } catch (error) {
556
- console.log('Error:', error.message);
557
- }
558
- }
559
-
560
- // =============================================================================
561
- // Example 10: Schema Factory Pattern
562
- // =============================================================================
563
-
564
- function schemaFactoryPattern() {
565
- console.log('\n=== Schema Factory Pattern ===\n');
566
-
567
- // Schema factory for different entity types
568
- const createEntitySchema = (entityType, customProperties = {}) => ({
569
- type: 'object',
570
- required: ['id', 'type', 'name'],
571
- properties: {
572
- id: { type: 'integer', minimum: 1 },
573
- type: { type: 'string', enum: [entityType] },
574
- name: { type: 'string', minLength: 1 },
575
- description: { type: 'string' },
576
- active: { type: 'boolean' },
577
- metadata: { type: 'object' },
578
- ...customProperties
579
- }
580
- });
581
-
582
- // Create specific schemas
583
- const productSchema = createEntitySchema('product', {
584
- price: { type: 'number', minimum: 0 },
585
- sku: { type: 'string', pattern: '^[A-Z]{3}-\\d{4}$' },
586
- category: { type: 'string' }
587
- });
588
-
589
- const serviceSchema = createEntitySchema('service', {
590
- hourlyRate: { type: 'number', minimum: 0 },
591
- duration: { type: 'integer', minimum: 1 },
592
- availability: { type: 'string', enum: ['available', 'busy', 'unavailable'] }
593
- });
594
-
595
- console.log('Product schema created:', Object.keys(productSchema.properties));
596
- console.log('Service schema created:', Object.keys(serviceSchema.properties));
597
-
598
- // Validate data
599
- const product = {
600
- id: 1,
601
- type: 'product',
602
- name: 'Widget Pro',
603
- price: 29.99,
604
- sku: 'WGT-0001',
605
- category: 'widgets',
606
- active: true
607
- };
608
-
609
- try {
610
- const csv = jsonToCsv([product], { schema: productSchema });
611
- console.log('\nProduct validated successfully');
612
- } catch (error) {
613
- console.log('Error:', error.message);
614
- }
615
- }
616
-
617
- // =============================================================================
618
- // Run All Examples
619
- // =============================================================================
620
-
621
- async function main() {
622
- console.log('jtcsv Schema Validation Examples');
623
- console.log('='.repeat(60));
624
-
625
- basicSchemaValidation();
626
- nestedSchemaValidation();
627
- customFormatSchema();
628
- arraySchemaValidation();
629
- conditionalSchema();
630
- typeCoercionSchema();
631
- validationErrorDetails();
632
- schemaValidationOnCsvInput();
633
- reusableSchemaDefinitions();
634
- schemaFactoryPattern();
635
-
636
- console.log('\n' + '='.repeat(60));
637
- console.log('All schema validation examples completed.');
638
- }
639
-
640
- main().catch(console.error);