@json-eval-rs/react-native 0.0.28

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.
@@ -0,0 +1,786 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.multiply = exports.default = exports.JSONEval = void 0;
7
+ exports.useJSONEval = useJSONEval;
8
+ var _react = _interopRequireDefault(require("react"));
9
+ var _reactNative = require("react-native");
10
+ function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
11
+ const LINKING_ERROR = `The package '@json-eval-rs/react-native' doesn't seem to be linked. Make sure: \n\n` + _reactNative.Platform.select({
12
+ ios: "- You have run 'pod install'\n",
13
+ default: ''
14
+ }) + '- You rebuilt the app after installing the package\n' + '- You are not using Expo managed workflow\n';
15
+ const JsonEvalRs = _reactNative.NativeModules.JsonEvalRs ? _reactNative.NativeModules.JsonEvalRs : new Proxy({}, {
16
+ get() {
17
+ throw new Error(LINKING_ERROR);
18
+ }
19
+ });
20
+
21
+ /**
22
+ * Validation error for a specific field
23
+ */
24
+
25
+ /**
26
+ * Result of validation operation
27
+ */
28
+
29
+ /**
30
+ * Dependent field change from evaluateDependents
31
+ */
32
+
33
+ /**
34
+ * Options for creating a JSONEval instance
35
+ */
36
+
37
+ /**
38
+ * Options for evaluation
39
+ */
40
+
41
+ /**
42
+ * Options for validation with path filtering
43
+ */
44
+
45
+ /**
46
+ * Cache statistics
47
+ */
48
+
49
+ /**
50
+ * Options for evaluating dependents
51
+ */
52
+
53
+ /**
54
+ * Options for evaluating a subform
55
+ */
56
+
57
+ /**
58
+ * Options for validating a subform
59
+ */
60
+
61
+ /**
62
+ * Options for evaluating dependents in a subform
63
+ */
64
+
65
+ /**
66
+ * Options for resolving layout in a subform
67
+ */
68
+
69
+ /**
70
+ * Options for getting evaluated schema from a subform
71
+ */
72
+
73
+ /**
74
+ * Options for getting schema value from a subform
75
+ */
76
+
77
+ /**
78
+ * Options for getting evaluated schema by path from a subform
79
+ */
80
+
81
+ /**
82
+ * Options for getting evaluated schema by multiple paths from a subform
83
+ */
84
+
85
+ /**
86
+ * Options for getting schema by path from a subform
87
+ */
88
+
89
+ /**
90
+ * Options for getting schema by multiple paths from a subform
91
+ */
92
+
93
+ /**
94
+ * High-performance JSON Logic evaluator with schema validation for React Native
95
+ *
96
+ * ## Zero-Copy Architecture
97
+ *
98
+ * This binding is optimized for minimal memory copies:
99
+ * - **Rust FFI Layer**: Returns raw pointers (zero-copy)
100
+ * - **C++ Bridge**: Uses direct pointer access with single-copy string construction
101
+ * - **Native Platform**: Minimizes intermediate conversions
102
+ * - **JS Bridge**: React Native's architecture requires serialization (unavoidable)
103
+ *
104
+ * While true zero-copy across JS/Native boundary is not possible due to React Native's
105
+ * architecture, we minimize copies within the native layer to maximize performance.
106
+ *
107
+ * @example
108
+ * ```typescript
109
+ * import { JSONEval } from '@json-eval-rs/react-native';
110
+ *
111
+ * const schema = {
112
+ * type: 'object',
113
+ * properties: {
114
+ * user: {
115
+ * type: 'object',
116
+ * properties: {
117
+ * name: {
118
+ * type: 'string',
119
+ * rules: {
120
+ * required: { value: true, message: 'Name is required' }
121
+ * }
122
+ * }
123
+ * }
124
+ * }
125
+ * }
126
+ * };
127
+ *
128
+ * const eval = new JSONEval({ schema });
129
+ *
130
+ * const data = { user: { name: 'John' } };
131
+ * const result = await eval.evaluate({ data });
132
+ * console.log(result);
133
+ *
134
+ * const validation = await eval.validate({ data });
135
+ * if (validation.hasError) {
136
+ * console.error('Validation errors:', validation.errors);
137
+ * }
138
+ *
139
+ * await eval.dispose();
140
+ * ```
141
+ */
142
+ class JSONEval {
143
+ disposed = false;
144
+
145
+ /**
146
+ * Creates a new JSON evaluator instance from a cached ParsedSchema
147
+ * @param cacheKey - Cache key to lookup in the global ParsedSchemaCache
148
+ * @param context - Optional context data
149
+ * @param data - Optional initial data
150
+ * @returns New JSONEval instance
151
+ * @throws {Error} If schema not found in cache or creation fails
152
+ */
153
+ static fromCache(cacheKey, context, data) {
154
+ const contextStr = context ? typeof context === 'string' ? context : JSON.stringify(context) : null;
155
+ const dataStr = data ? typeof data === 'string' ? data : JSON.stringify(data) : null;
156
+ const handle = JsonEvalRs.createFromCache(cacheKey, contextStr, dataStr);
157
+ return new JSONEval({
158
+ schema: {},
159
+ _handle: handle
160
+ });
161
+ }
162
+
163
+ /**
164
+ * Creates a new JSON evaluator instance
165
+ * @param options - Configuration options with schema, context, and data
166
+ * @throws {Error} If creation fails
167
+ */
168
+ constructor(options) {
169
+ // If handle is provided (from static factory), use it directly
170
+ if (options._handle) {
171
+ this.handle = options._handle;
172
+ return;
173
+ }
174
+ const {
175
+ schema,
176
+ context,
177
+ data
178
+ } = options;
179
+ try {
180
+ const schemaStr = typeof schema === 'string' ? schema : JSON.stringify(schema);
181
+ const contextStr = context ? typeof context === 'string' ? context : JSON.stringify(context) : null;
182
+ const dataStr = data ? typeof data === 'string' ? data : JSON.stringify(data) : null;
183
+ this.handle = JsonEvalRs.create(schemaStr, contextStr, dataStr);
184
+ } catch (error) {
185
+ const errorMessage = error instanceof Error ? error.message : String(error);
186
+ throw new Error(`Failed to create JSONEval instance: ${errorMessage}`);
187
+ }
188
+ }
189
+ throwIfDisposed() {
190
+ if (this.disposed) {
191
+ throw new Error('JSONEval instance has been disposed');
192
+ }
193
+ }
194
+
195
+ /**
196
+ * Convert value to JSON string
197
+ * Performance note: If you have a pre-serialized JSON string, pass it directly
198
+ * instead of an object to avoid the JSON.stringify overhead
199
+ */
200
+ toJsonString(value) {
201
+ return typeof value === 'string' ? value : JSON.stringify(value);
202
+ }
203
+
204
+ /**
205
+ * Evaluate schema with provided data
206
+ * @param options - Evaluation options
207
+ * @returns Promise resolving to evaluated schema object
208
+ * @throws {Error} If evaluation fails
209
+ */
210
+ async evaluate(options) {
211
+ this.throwIfDisposed();
212
+ try {
213
+ const dataStr = this.toJsonString(options.data);
214
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
215
+ const resultStr = await JsonEvalRs.evaluate(this.handle, dataStr, contextStr);
216
+ return JSON.parse(resultStr);
217
+ } catch (error) {
218
+ const errorMessage = error instanceof Error ? error.message : String(error);
219
+ throw new Error(`Evaluation failed: ${errorMessage}`);
220
+ }
221
+ }
222
+
223
+ /**
224
+ * Validate data against schema rules
225
+ * @param options - Validation options
226
+ * @returns Promise resolving to ValidationResult
227
+ * @throws {Error} If validation operation fails
228
+ */
229
+ async validate(options) {
230
+ this.throwIfDisposed();
231
+ try {
232
+ const dataStr = this.toJsonString(options.data);
233
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
234
+ const resultStr = await JsonEvalRs.validate(this.handle, dataStr, contextStr);
235
+ return JSON.parse(resultStr);
236
+ } catch (error) {
237
+ const errorMessage = error instanceof Error ? error.message : String(error);
238
+ throw new Error(`Validation failed: ${errorMessage}`);
239
+ }
240
+ }
241
+
242
+ /**
243
+ * Re-evaluate fields that depend on a changed path
244
+ * @param options - Dependent evaluation options
245
+ * @returns Promise resolving to array of dependent field changes
246
+ * @throws {Error} If evaluation fails
247
+ */
248
+ async evaluateDependents(options) {
249
+ this.throwIfDisposed();
250
+ try {
251
+ const {
252
+ changedPaths,
253
+ data,
254
+ context,
255
+ reEvaluate = false
256
+ } = options;
257
+ const changedPathsJson = JSON.stringify(changedPaths);
258
+ const dataStr = data ? this.toJsonString(data) : null;
259
+ const contextStr = context ? this.toJsonString(context) : null;
260
+ const resultStr = await JsonEvalRs.evaluateDependents(this.handle, changedPathsJson, dataStr, contextStr, reEvaluate);
261
+ return JSON.parse(resultStr);
262
+ } catch (error) {
263
+ const errorMessage = error instanceof Error ? error.message : String(error);
264
+ throw new Error(`Dependent evaluation failed: ${errorMessage}`);
265
+ }
266
+ }
267
+
268
+ /**
269
+ * Get the evaluated schema with optional layout resolution
270
+ * @param skipLayout - Whether to skip layout resolution (default: false)
271
+ * @returns Promise resolving to evaluated schema object
272
+ * @throws {Error} If operation fails
273
+ */
274
+ async getEvaluatedSchema(skipLayout = false) {
275
+ this.throwIfDisposed();
276
+ const resultStr = await JsonEvalRs.getEvaluatedSchema(this.handle, skipLayout);
277
+ return JSON.parse(resultStr);
278
+ }
279
+
280
+ /**
281
+ * Get all schema values (evaluations ending with .value)
282
+ * @returns Promise resolving to map of path -> value
283
+ * @throws {Error} If operation fails
284
+ */
285
+ async getSchemaValue() {
286
+ this.throwIfDisposed();
287
+ const resultStr = await JsonEvalRs.getSchemaValue(this.handle);
288
+ return JSON.parse(resultStr);
289
+ }
290
+
291
+ /**
292
+ * Get the evaluated schema without $params field
293
+ * @param skipLayout - Whether to skip layout resolution (default: false)
294
+ * @returns Promise resolving to evaluated schema object
295
+ * @throws {Error} If operation fails
296
+ */
297
+ async getEvaluatedSchemaWithoutParams(skipLayout = false) {
298
+ this.throwIfDisposed();
299
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaWithoutParams(this.handle, skipLayout);
300
+ return JSON.parse(resultStr);
301
+ }
302
+
303
+ /**
304
+ * Get a value from the evaluated schema using dotted path notation
305
+ * @param path - Dotted path to the value (e.g., "properties.field.value")
306
+ * @param skipLayout - Whether to skip layout resolution
307
+ * @returns Promise resolving to the value at the path, or null if not found
308
+ * @throws {Error} If operation fails
309
+ */
310
+ async getEvaluatedSchemaByPath(path, skipLayout = false) {
311
+ this.throwIfDisposed();
312
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaByPath(this.handle, path, skipLayout);
313
+ return resultStr ? JSON.parse(resultStr) : null;
314
+ }
315
+
316
+ /**
317
+ * Get values from the evaluated schema using multiple dotted path notations
318
+ * Returns a merged object containing all requested paths (skips paths that are not found)
319
+ * @param paths - Array of dotted paths to retrieve
320
+ * @param skipLayout - Whether to skip layout resolution
321
+ * @returns Promise resolving to merged object containing all found paths
322
+ * @throws {Error} If operation fails
323
+ */
324
+ async getEvaluatedSchemaByPaths(paths, skipLayout = false) {
325
+ this.throwIfDisposed();
326
+ const pathsJson = JSON.stringify(paths);
327
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaByPaths(this.handle, pathsJson, skipLayout);
328
+ return JSON.parse(resultStr);
329
+ }
330
+
331
+ /**
332
+ * Get a value from the schema using dotted path notation
333
+ * @param path - Dotted path to the value (e.g., "properties.field.value")
334
+ * @returns Promise resolving to the value at the path, or null if not found
335
+ * @throws {Error} If operation fails
336
+ */
337
+ async getSchemaByPath(path) {
338
+ this.throwIfDisposed();
339
+ const resultStr = await JsonEvalRs.getSchemaByPath(this.handle, path);
340
+ return resultStr ? JSON.parse(resultStr) : null;
341
+ }
342
+
343
+ /**
344
+ * Get values from the schema using multiple dotted path notations
345
+ * Returns a merged object containing all requested paths (skips paths that are not found)
346
+ * @param paths - Array of dotted paths to retrieve
347
+ * @returns Promise resolving to merged object containing all found paths
348
+ * @throws {Error} If operation fails
349
+ */
350
+ async getSchemaByPaths(paths) {
351
+ this.throwIfDisposed();
352
+ const pathsJson = JSON.stringify(paths);
353
+ const resultStr = await JsonEvalRs.getSchemaByPaths(this.handle, pathsJson);
354
+ return JSON.parse(resultStr);
355
+ }
356
+
357
+ /**
358
+ * Reload schema with new data
359
+ * @param options - Configuration options with new schema, context, and data
360
+ * @throws {Error} If reload fails
361
+ */
362
+ async reloadSchema(options) {
363
+ this.throwIfDisposed();
364
+ try {
365
+ const {
366
+ schema,
367
+ context,
368
+ data
369
+ } = options;
370
+ const schemaStr = typeof schema === 'string' ? schema : JSON.stringify(schema);
371
+ const contextStr = context ? typeof context === 'string' ? context : JSON.stringify(context) : null;
372
+ const dataStr = data ? typeof data === 'string' ? data : JSON.stringify(data) : null;
373
+ await JsonEvalRs.reloadSchema(this.handle, schemaStr, contextStr, dataStr);
374
+ } catch (error) {
375
+ const errorMessage = error instanceof Error ? error.message : String(error);
376
+ throw new Error(`Failed to reload schema: ${errorMessage}`);
377
+ }
378
+ }
379
+
380
+ /**
381
+ * Reload schema from MessagePack bytes
382
+ * @param schemaMsgpack - MessagePack-encoded schema bytes (Uint8Array or number array)
383
+ * @param context - Optional context data
384
+ * @param data - Optional initial data
385
+ * @throws {Error} If reload fails
386
+ */
387
+ async reloadSchemaMsgpack(schemaMsgpack, context, data) {
388
+ this.throwIfDisposed();
389
+ try {
390
+ // Convert Uint8Array to number array if needed
391
+ const msgpackArray = schemaMsgpack instanceof Uint8Array ? Array.from(schemaMsgpack) : schemaMsgpack;
392
+ const contextStr = context ? typeof context === 'string' ? context : JSON.stringify(context) : null;
393
+ const dataStr = data ? typeof data === 'string' ? data : JSON.stringify(data) : null;
394
+ await JsonEvalRs.reloadSchemaMsgpack(this.handle, msgpackArray, contextStr, dataStr);
395
+ } catch (error) {
396
+ const errorMessage = error instanceof Error ? error.message : String(error);
397
+ throw new Error(`Failed to reload schema from MessagePack: ${errorMessage}`);
398
+ }
399
+ }
400
+
401
+ /**
402
+ * Reload schema from ParsedSchemaCache using a cache key
403
+ * @param cacheKey - Cache key to lookup in the global ParsedSchemaCache
404
+ * @param context - Optional context data
405
+ * @param data - Optional initial data
406
+ * @throws {Error} If reload fails or schema not found in cache
407
+ */
408
+ async reloadSchemaFromCache(cacheKey, context, data) {
409
+ this.throwIfDisposed();
410
+ try {
411
+ const contextStr = context ? typeof context === 'string' ? context : JSON.stringify(context) : null;
412
+ const dataStr = data ? typeof data === 'string' ? data : JSON.stringify(data) : null;
413
+ await JsonEvalRs.reloadSchemaFromCache(this.handle, cacheKey, contextStr, dataStr);
414
+ } catch (error) {
415
+ const errorMessage = error instanceof Error ? error.message : String(error);
416
+ throw new Error(`Failed to reload schema from cache: ${errorMessage}`);
417
+ }
418
+ }
419
+
420
+ /**
421
+ * Get cache statistics
422
+ * @returns Promise resolving to cache statistics
423
+ * @throws {Error} If operation fails
424
+ */
425
+ async cacheStats() {
426
+ this.throwIfDisposed();
427
+ const resultStr = await JsonEvalRs.cacheStats(this.handle);
428
+ return JSON.parse(resultStr);
429
+ }
430
+
431
+ /**
432
+ * Clear the evaluation cache
433
+ * @returns Promise that resolves when cache is cleared
434
+ * @throws {Error} If operation fails
435
+ */
436
+ async clearCache() {
437
+ this.throwIfDisposed();
438
+ await JsonEvalRs.clearCache(this.handle);
439
+ }
440
+
441
+ /**
442
+ * Get the number of cached entries
443
+ * @returns Promise resolving to number of cached entries
444
+ * @throws {Error} If operation fails
445
+ */
446
+ async cacheLen() {
447
+ this.throwIfDisposed();
448
+ return await JsonEvalRs.cacheLen(this.handle);
449
+ }
450
+
451
+ /**
452
+ * Enable evaluation caching
453
+ * Useful for reusing JSONEval instances with different data
454
+ * @returns Promise that resolves when cache is enabled
455
+ * @throws {Error} If operation fails
456
+ */
457
+ async enableCache() {
458
+ this.throwIfDisposed();
459
+ await JsonEvalRs.enableCache(this.handle);
460
+ }
461
+
462
+ /**
463
+ * Disable evaluation caching
464
+ * Useful for web API usage where each request creates a new JSONEval instance
465
+ * Improves performance by skipping cache operations that have no benefit for single-use instances
466
+ * @returns Promise that resolves when cache is disabled
467
+ * @throws {Error} If operation fails
468
+ */
469
+ async disableCache() {
470
+ this.throwIfDisposed();
471
+ await JsonEvalRs.disableCache(this.handle);
472
+ }
473
+
474
+ /**
475
+ * Check if evaluation caching is enabled
476
+ * @returns Boolean indicating if caching is enabled
477
+ * @throws {Error} If operation fails
478
+ */
479
+ isCacheEnabled() {
480
+ this.throwIfDisposed();
481
+ return JsonEvalRs.isCacheEnabled(this.handle);
482
+ }
483
+
484
+ /**
485
+ * Resolve layout with optional evaluation
486
+ * @param evaluate - If true, runs evaluation before resolving layout (default: false)
487
+ * @returns Promise that resolves when layout resolution is complete
488
+ * @throws {Error} If operation fails
489
+ */
490
+ async resolveLayout(evaluate = false) {
491
+ this.throwIfDisposed();
492
+ await JsonEvalRs.resolveLayout(this.handle, evaluate);
493
+ }
494
+
495
+ /**
496
+ * Compile and run JSON logic from a JSON logic string
497
+ * @param logicStr - JSON logic expression as a string or object
498
+ * @param data - Optional JSON data string or object (null to use existing data)
499
+ * @param context - Optional context data string or object (null to use existing context)
500
+ * @returns Promise resolving to the result of the evaluation
501
+ * @throws {Error} If compilation or evaluation fails
502
+ */
503
+ async compileAndRunLogic(logicStr, data, context) {
504
+ this.throwIfDisposed();
505
+ const logic = this.toJsonString(logicStr);
506
+ const dataStr = data ? this.toJsonString(data) : null;
507
+ const contextStr = context ? this.toJsonString(context) : null;
508
+ const resultStr = await JsonEvalRs.compileAndRunLogic(this.handle, logic, dataStr, contextStr);
509
+ return JSON.parse(resultStr);
510
+ }
511
+
512
+ /**
513
+ * Compile JSON logic and return a global ID
514
+ * @param logicStr - JSON logic expression as a string or object
515
+ * @returns Promise resolving to the compiled logic ID
516
+ * @throws {Error} If compilation fails
517
+ */
518
+ async compileLogic(logicStr) {
519
+ this.throwIfDisposed();
520
+ const logic = this.toJsonString(logicStr);
521
+ return await JsonEvalRs.compileLogic(this.handle, logic);
522
+ }
523
+
524
+ /**
525
+ * Run pre-compiled logic by ID
526
+ * @param logicId - Compiled logic ID from compileLogic
527
+ * @param data - Optional JSON data string or object (null to use existing data)
528
+ * @param context - Optional context data string or object (null to use existing context)
529
+ * @returns Promise resolving to the result of the evaluation
530
+ * @throws {Error} If execution fails
531
+ */
532
+ async runLogic(logicId, data, context) {
533
+ this.throwIfDisposed();
534
+ const dataStr = data ? this.toJsonString(data) : null;
535
+ const contextStr = context ? this.toJsonString(context) : null;
536
+ const resultStr = await JsonEvalRs.runLogic(this.handle, logicId, dataStr, contextStr);
537
+ return JSON.parse(resultStr);
538
+ }
539
+
540
+ /**
541
+ * Validate data against schema rules with optional path filtering
542
+ * @param options - Validation options with optional path filtering
543
+ * @returns Promise resolving to ValidationResult
544
+ * @throws {Error} If validation operation fails
545
+ */
546
+ async validatePaths(options) {
547
+ this.throwIfDisposed();
548
+ const dataStr = this.toJsonString(options.data);
549
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
550
+ const paths = options.paths || null;
551
+ const resultStr = await JsonEvalRs.validatePaths(this.handle, dataStr, contextStr, paths);
552
+ return JSON.parse(resultStr);
553
+ }
554
+
555
+ // ============================================================================
556
+ // Subform Methods
557
+ // ============================================================================
558
+
559
+ /**
560
+ * Evaluate a subform with data
561
+ * @param options - Evaluation options including subform path and data
562
+ * @returns Promise that resolves when evaluation is complete
563
+ * @throws {Error} If evaluation fails
564
+ */
565
+ async evaluateSubform(options) {
566
+ this.throwIfDisposed();
567
+ const dataStr = this.toJsonString(options.data);
568
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
569
+ return JsonEvalRs.evaluateSubform(this.handle, options.subformPath, dataStr, contextStr);
570
+ }
571
+
572
+ /**
573
+ * Validate subform data against its schema rules
574
+ * @param options - Validation options including subform path and data
575
+ * @returns Promise resolving to ValidationResult
576
+ * @throws {Error} If validation fails
577
+ */
578
+ async validateSubform(options) {
579
+ this.throwIfDisposed();
580
+ const dataStr = this.toJsonString(options.data);
581
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
582
+ const resultStr = await JsonEvalRs.validateSubform(this.handle, options.subformPath, dataStr, contextStr);
583
+ return JSON.parse(resultStr);
584
+ }
585
+
586
+ /**
587
+ * Evaluate dependents in a subform when fields change
588
+ * @param options - Options including subform path, changed paths array, and optional data
589
+ * @returns Promise resolving to dependent evaluation results
590
+ * @throws {Error} If evaluation fails
591
+ */
592
+ async evaluateDependentsSubform(options) {
593
+ this.throwIfDisposed();
594
+ const dataStr = options.data ? this.toJsonString(options.data) : null;
595
+ const contextStr = options.context ? this.toJsonString(options.context) : null;
596
+
597
+ // For now, pass the first path since native bridge expects single path (wraps internally)
598
+ const changedPath = options.changedPaths[0] || '';
599
+ const resultStr = await JsonEvalRs.evaluateDependentsSubform(this.handle, options.subformPath, changedPath, dataStr, contextStr);
600
+ return JSON.parse(resultStr);
601
+ }
602
+
603
+ /**
604
+ * Resolve layout for subform
605
+ * @param options - Options including subform path and evaluate flag
606
+ * @returns Promise that resolves when layout is resolved
607
+ * @throws {Error} If layout resolution fails
608
+ */
609
+ async resolveLayoutSubform(options) {
610
+ this.throwIfDisposed();
611
+ return JsonEvalRs.resolveLayoutSubform(this.handle, options.subformPath, options.evaluate || false);
612
+ }
613
+
614
+ /**
615
+ * Get evaluated schema from subform
616
+ * @param options - Options including subform path and resolveLayout flag
617
+ * @returns Promise resolving to evaluated schema
618
+ * @throws {Error} If operation fails
619
+ */
620
+ async getEvaluatedSchemaSubform(options) {
621
+ this.throwIfDisposed();
622
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaSubform(this.handle, options.subformPath, options.resolveLayout || false);
623
+ return JSON.parse(resultStr);
624
+ }
625
+
626
+ /**
627
+ * Get schema value from subform (all .value fields)
628
+ * @param options - Options including subform path
629
+ * @returns Promise resolving to schema values
630
+ * @throws {Error} If operation fails
631
+ */
632
+ async getSchemaValueSubform(options) {
633
+ this.throwIfDisposed();
634
+ const resultStr = await JsonEvalRs.getSchemaValueSubform(this.handle, options.subformPath);
635
+ return JSON.parse(resultStr);
636
+ }
637
+
638
+ /**
639
+ * Get evaluated schema without $params from subform
640
+ * @param options - Options including subform path and resolveLayout flag
641
+ * @returns Promise resolving to evaluated schema without $params
642
+ * @throws {Error} If operation fails
643
+ */
644
+ async getEvaluatedSchemaWithoutParamsSubform(options) {
645
+ this.throwIfDisposed();
646
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaWithoutParamsSubform(this.handle, options.subformPath, options.resolveLayout || false);
647
+ return JSON.parse(resultStr);
648
+ }
649
+
650
+ /**
651
+ * Get evaluated schema by specific path from subform
652
+ * @param options - Options including subform path, schema path, and skipLayout flag
653
+ * @returns Promise resolving to value at path or null if not found
654
+ * @throws {Error} If operation fails
655
+ */
656
+ async getEvaluatedSchemaByPathSubform(options) {
657
+ this.throwIfDisposed();
658
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaByPathSubform(this.handle, options.subformPath, options.schemaPath, options.skipLayout || false);
659
+ return resultStr ? JSON.parse(resultStr) : null;
660
+ }
661
+
662
+ /**
663
+ * Get evaluated schema by multiple paths from subform
664
+ * Returns a merged object containing all requested paths (skips paths that are not found)
665
+ * @param options - Options including subform path, array of schema paths, and skipLayout flag
666
+ * @returns Promise resolving to merged object containing all found paths
667
+ * @throws {Error} If operation fails
668
+ */
669
+ async getEvaluatedSchemaByPathsSubform(options) {
670
+ this.throwIfDisposed();
671
+ const pathsJson = JSON.stringify(options.schemaPaths);
672
+ const resultStr = await JsonEvalRs.getEvaluatedSchemaByPathsSubform(this.handle, options.subformPath, pathsJson, options.skipLayout || false);
673
+ return JSON.parse(resultStr);
674
+ }
675
+
676
+ /**
677
+ * Get list of available subform paths
678
+ * @returns Promise resolving to array of subform paths
679
+ * @throws {Error} If operation fails
680
+ */
681
+ async getSubformPaths() {
682
+ this.throwIfDisposed();
683
+ const resultStr = await JsonEvalRs.getSubformPaths(this.handle);
684
+ return JSON.parse(resultStr);
685
+ }
686
+
687
+ /**
688
+ * Get schema value by specific path from subform
689
+ * @param options - Options including subform path and schema path
690
+ * @returns Promise resolving to value at path or null if not found
691
+ * @throws {Error} If operation fails
692
+ */
693
+ async getSchemaByPathSubform(options) {
694
+ this.throwIfDisposed();
695
+ const resultStr = await JsonEvalRs.getSchemaByPathSubform(this.handle, options.subformPath, options.schemaPath);
696
+ return resultStr ? JSON.parse(resultStr) : null;
697
+ }
698
+
699
+ /**
700
+ * Get schema values by multiple paths from subform
701
+ * Returns a merged object containing all requested paths (skips paths that are not found)
702
+ * @param options - Options including subform path and array of schema paths
703
+ * @returns Promise resolving to merged object containing all found paths
704
+ * @throws {Error} If operation fails
705
+ */
706
+ async getSchemaByPathsSubform(options) {
707
+ this.throwIfDisposed();
708
+ const pathsJson = JSON.stringify(options.schemaPaths);
709
+ const resultStr = await JsonEvalRs.getSchemaByPathsSubform(this.handle, options.subformPath, pathsJson);
710
+ return JSON.parse(resultStr);
711
+ }
712
+
713
+ /**
714
+ * Check if a subform exists at the given path
715
+ * @param subformPath - Path to check
716
+ * @returns Promise resolving to true if subform exists, false otherwise
717
+ * @throws {Error} If operation fails
718
+ */
719
+ async hasSubform(subformPath) {
720
+ this.throwIfDisposed();
721
+ return JsonEvalRs.hasSubform(this.handle, subformPath);
722
+ }
723
+
724
+ /**
725
+ * Dispose of the native resources
726
+ * Must be called when done using the instance
727
+ * @returns Promise that resolves when disposal is complete
728
+ */
729
+ async dispose() {
730
+ if (this.disposed) return;
731
+ await JsonEvalRs.dispose(this.handle);
732
+ this.disposed = true;
733
+ }
734
+
735
+ /**
736
+ * Get the library version
737
+ * @returns Promise resolving to version string
738
+ */
739
+ static async version() {
740
+ return JsonEvalRs.version();
741
+ }
742
+ }
743
+
744
+ /**
745
+ * Hook for using JSONEval in React components with automatic cleanup
746
+ * @param options - Configuration options
747
+ * @returns JSONEval instance or null if not yet initialized
748
+ *
749
+ * @example
750
+ * ```typescript
751
+ * import { useJSONEval } from '@json-eval-rs/react-native';
752
+ *
753
+ * function MyComponent() {
754
+ * const eval = useJSONEval({ schema: mySchema });
755
+ *
756
+ * const handleValidate = async () => {
757
+ * if (!eval) return;
758
+ * const result = await eval.validate({ data: myData });
759
+ * console.log(result);
760
+ * };
761
+ *
762
+ * return <Button onPress={handleValidate} title="Validate" />;
763
+ * }
764
+ * ```
765
+ */
766
+ exports.JSONEval = JSONEval;
767
+ function useJSONEval(options) {
768
+ const [evalInstance, setEvalInstance] = _react.default.useState(null);
769
+ _react.default.useEffect(() => {
770
+ const instance = new JSONEval(options);
771
+ setEvalInstance(instance);
772
+ return () => {
773
+ instance.dispose().catch(console.error);
774
+ };
775
+ // eslint-disable-next-line react-hooks/exhaustive-deps
776
+ }, []);
777
+ return evalInstance;
778
+ }
779
+
780
+ // Default export
781
+ var _default = exports.default = JSONEval; // For backwards compatibility
782
+ const multiply = (a, b) => {
783
+ return JsonEvalRs.multiply(a, b);
784
+ };
785
+ exports.multiply = multiply;
786
+ //# sourceMappingURL=index.js.map