@celigo/api-specs 0.2.196 → 0.2.197
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.
- package/dist/ai-agent.yml +14 -5
- package/dist/api.yml +2885 -151
- package/dist/asynchelper.yml +10 -2
- package/dist/export.yml +10 -2
- package/dist/import.yml +10 -2
- package/dist/tool.yml +10 -2
- package/package.json +1 -1
- package/schemas.json +850 -819
package/dist/api.yml
CHANGED
|
@@ -2596,57 +2596,2862 @@ components:
|
|
|
2596
2596
|
422 with its message. Any other `statusCode` is sent as returned.
|
|
2597
2597
|
items:
|
|
2598
2598
|
type: object
|
|
2599
|
+
properties:
|
|
2600
|
+
generate:
|
|
2601
|
+
type: string
|
|
2602
|
+
description: |
|
|
2603
|
+
**Purpose**
|
|
2604
|
+
Defines the target field name in the output object/record.
|
|
2605
|
+
|
|
2606
|
+
**Guidance**
|
|
2607
|
+
This is the PRIMARY FIELD that identifies the output property being created:
|
|
2608
|
+
|
|
2609
|
+
- For regular fields: Set to the exact property name (e.g., "firstName", "price", "isActive")
|
|
2610
|
+
- For object fields: Set to the object property name, then add child mappings in the 'mappings' array
|
|
2611
|
+
- For array fields: Set to the array property name, then configure 'buildArrayHelper'
|
|
2612
|
+
- One structural blank: the single top-level `objectarray` item of a `rows [ ]` mapping (the
|
|
2613
|
+
array output structure — see the array's description). A child-bearing wrapper and a source-only row that
|
|
2614
|
+
already exist in a saved document also stay unnamed when the tree is re-sent — filling in a
|
|
2615
|
+
name changes the output; it does not complete the row
|
|
2616
|
+
|
|
2617
|
+
IMPORTANT: Do NOT use dot notation (e.g., "customer.firstName") in this field. Instead, create proper
|
|
2618
|
+
hierarchical structure with nested mappings:
|
|
2619
|
+
```json
|
|
2620
|
+
{
|
|
2621
|
+
"generate": "customer",
|
|
2622
|
+
"dataType": "object",
|
|
2623
|
+
"status": "Active",
|
|
2624
|
+
"mappings": [
|
|
2625
|
+
{"generate": "firstName", "dataType": "string", "extract": "$.name.first", "status": "Active"}
|
|
2626
|
+
]
|
|
2627
|
+
}
|
|
2628
|
+
```
|
|
2629
|
+
|
|
2630
|
+
When parsing existing mappings, an empty `generate` on a row inside an `arrayarray` row's
|
|
2631
|
+
`buildArrayHelper` entry is that row's inner array (`arrayarray` fails at run time; see
|
|
2632
|
+
`dataType`); other unnamed rows are the wrappers and source-only rows described above; an
|
|
2633
|
+
empty `generate` on the ONLY top-level item, with `dataType: objectarray`, is the `rows [ ]` JSON
|
|
2634
|
+
structure — array output, bound as `rows` in templates — and is intentional, not a missing name.
|
|
2635
|
+
examples:
|
|
2636
|
+
- name
|
|
2637
|
+
- address
|
|
2638
|
+
- items
|
|
2639
|
+
dataType:
|
|
2640
|
+
type: string
|
|
2641
|
+
description: |
|
|
2642
|
+
**Purpose**
|
|
2643
|
+
Explicitly declares the data type of the output field, controlling how data is processed and structured.
|
|
2644
|
+
|
|
2645
|
+
**Guidance**
|
|
2646
|
+
This is a REQUIRED field that fundamentally determines mapping behavior:
|
|
2647
|
+
|
|
2648
|
+
**Simple Types (direct value mapping)**
|
|
2649
|
+
- `string`: Text values, converts other types to string representation
|
|
2650
|
+
- `number`: Numeric values. Converts a numeric string (`"24"` → `24`,
|
|
2651
|
+
`"007"` → `7`) and leaves the field out for an empty string; a value
|
|
2652
|
+
holding letters or a thousands separator (`"1,250.00"`) fails the
|
|
2653
|
+
record with `non_parsable_string` (`<generate>: String contains alpha
|
|
2654
|
+
characters`)
|
|
2655
|
+
- `boolean`: True/false values, converts truthy/falsy values
|
|
2656
|
+
|
|
2657
|
+
Dates are represented as strings — use `string` for date fields and
|
|
2658
|
+
drive the parsing/formatting through the `extractDateFormat` /
|
|
2659
|
+
`generateDateFormat` / `extractDateTimezone` / `generateDateTimezone`
|
|
2660
|
+
fields. There is no separate `date` enum value.
|
|
2661
|
+
|
|
2662
|
+
**Complex Types (require additional configuration)**
|
|
2663
|
+
- `object`: Creates a nested object from child mappings in the 'mappings' array, or
|
|
2664
|
+
copies a whole object with `extract` (one or the other, not both)
|
|
2665
|
+
|
|
2666
|
+
**Array Types**
|
|
2667
|
+
- `stringarray`: Array of strings
|
|
2668
|
+
- `numberarray`: Array of numbers
|
|
2669
|
+
- `booleanarray`: Array of booleans
|
|
2670
|
+
- `objectarray`: Array of objects (most common array type)
|
|
2671
|
+
|
|
2672
|
+
`arrayarray` is not a type the mapper recognizes: a save accepts it, but every record
|
|
2673
|
+
then fails with `Destination datatype is a required field.` Build an array of arrays
|
|
2674
|
+
in a script hook instead.
|
|
2675
|
+
|
|
2676
|
+
Array dataTypes are populated two ways: construct or iterate through
|
|
2677
|
+
`buildArrayHelper` entries, or set a constant with `hardCodedValue`. The
|
|
2678
|
+
row's own `extract` is never read on an array type: a primitive-array row
|
|
2679
|
+
that has only an `extract` (JSONPath, Handlebars or a literal) yields
|
|
2680
|
+
nothing, with no error, and an `objectarray` row without `buildArrayHelper`
|
|
2681
|
+
or `hardCodedValue` is refused with 422 ("buildArrayHelper" or
|
|
2682
|
+
"hardCodedValue" must be present for object array datatype.). To copy a
|
|
2683
|
+
source array through unchanged, use one entry that iterates it
|
|
2684
|
+
(`buildArrayHelper: [{"extract": "$.items[*]"}]`).
|
|
2685
|
+
|
|
2686
|
+
IMPORTANT: The dataType controls which additional fields are relevant:
|
|
2687
|
+
- For date-like string fields: extractDateFormat, generateDateFormat, etc. become relevant
|
|
2688
|
+
- For object types: 'mappings' array becomes relevant
|
|
2689
|
+
- For array types: `buildArrayHelper` or `hardCodedValue` (see above)
|
|
2690
|
+
|
|
2691
|
+
When analyzing existing mappings or generating new ones, always check dataType first
|
|
2692
|
+
to understand what additional fields should be present.
|
|
2693
|
+
x-celigo-ai-guidance:
|
|
2694
|
+
- |-
|
|
2695
|
+
Missing `dataType` is rejected at save with validation error
|
|
2696
|
+
`[mandatory_destination_datatype] Destination datatype is a
|
|
2697
|
+
required field.`
|
|
2698
|
+
- |-
|
|
2699
|
+
Give each row the type the destination field expects; `"string"` is
|
|
2700
|
+
not a safe default. It accepts any source value, but sends a numeric
|
|
2701
|
+
source as text (`"24"`), which a destination that checks JSON types
|
|
2702
|
+
refuses. Map numeric destination fields as `number`, which fails a
|
|
2703
|
+
record (`non_parsable_string`) only when the value holds letters or a
|
|
2704
|
+
thousands separator.
|
|
2705
|
+
enum:
|
|
2706
|
+
- string
|
|
2707
|
+
- number
|
|
2708
|
+
- boolean
|
|
2709
|
+
- object
|
|
2710
|
+
- stringarray
|
|
2711
|
+
- numberarray
|
|
2712
|
+
- booleanarray
|
|
2713
|
+
- objectarray
|
|
2714
|
+
x-enumDescriptions:
|
|
2715
|
+
string: Text values; converts other types to their string representation.
|
|
2716
|
+
number: Numeric values; converts numeric strings, and fails the record (`non_parsable_string`) on letters or a thousands separator.
|
|
2717
|
+
boolean: True/false values; converts truthy/falsy values.
|
|
2718
|
+
object: Nested object built from child `mappings`, or copied whole with `extract` (not both).
|
|
2719
|
+
stringarray: Array of string values.
|
|
2720
|
+
numberarray: Array of numeric values.
|
|
2721
|
+
booleanarray: Array of boolean values.
|
|
2722
|
+
objectarray: Array of objects, the most common array type.
|
|
2723
|
+
examples:
|
|
2724
|
+
- string
|
|
2725
|
+
- number
|
|
2726
|
+
- object
|
|
2727
|
+
- objectarray
|
|
2728
|
+
extract:
|
|
2729
|
+
type: string
|
|
2730
|
+
description: |
|
|
2731
|
+
**Purpose**
|
|
2732
|
+
Defines how to retrieve data from the input record to populate the output field.
|
|
2733
|
+
|
|
2734
|
+
**Guidance**
|
|
2735
|
+
This field supports THREE DISTINCT PATTERNS that are easily distinguished:
|
|
2736
|
+
|
|
2737
|
+
**1. json Path Syntax**
|
|
2738
|
+
- MUST start with '$' — the record root. An object record is addressed as
|
|
2739
|
+
'$.field'; a grouped (array) record as '$[0].field' / '$[*].field'
|
|
2740
|
+
- Used for precisely targeting data in structured JSON objects
|
|
2741
|
+
- Examples: '$.customer.firstName', '$.items[0].price', '$.addresses[*].street',
|
|
2742
|
+
'$[*].Tax' (every row of a grouped record)
|
|
2743
|
+
- Wildcards like [*] extract multiple values/objects
|
|
2744
|
+
- A key that contains a dot needs bracket notation: `$['P.O. Number']` (or
|
|
2745
|
+
`$["P.O. Number"]`, `$.[P.O. Number]`). `$.P.O. Number` is read as a nested
|
|
2746
|
+
path: it maps nothing and the record still succeeds. Spaces, hyphens and `#`
|
|
2747
|
+
need no brackets (`$.Ship To Name`, `$.Tracking #`)
|
|
2748
|
+
- Filter expressions such as `$.items[?(@.active)]` fail the record with
|
|
2749
|
+
"Eval [?(expr)] prevented in JSONPath expression."
|
|
2750
|
+
|
|
2751
|
+
```json
|
|
2752
|
+
"extract": "$.customer.addresses[*]" // Extracts all addresses
|
|
2753
|
+
```
|
|
2754
|
+
|
|
2755
|
+
**2. Handlebars Template Syntax**
|
|
2756
|
+
- Contains '{{' and '}}' pattern
|
|
2757
|
+
- Evaluated by the AFE 2.0 handlebars template engine
|
|
2758
|
+
- Can include logic, formatting, and computation
|
|
2759
|
+
- Access input record fields with {{record.fieldName}} notation; a grouped
|
|
2760
|
+
(array) record binds as `rows` instead — {{rows.0.fieldName}} / {{#each rows}}
|
|
2761
|
+
- Examples: "{{record.firstName}} {{record.lastName}}", "{{#if record.isActive}}Active{{else}}Inactive{{/if}}"
|
|
2762
|
+
- Valid on scalars and on `object` rows, where the rendered output must
|
|
2763
|
+
parse into an object. On an array row the template goes in a
|
|
2764
|
+
`buildArrayHelper` entry instead: on an `objectarray` row's own
|
|
2765
|
+
`extract` it is refused with 422 ("buildArrayHelper" or "hardCodedValue"
|
|
2766
|
+
must be present for object array datatype.), and on a primitive-array
|
|
2767
|
+
row's own `extract` it yields nothing (the field is left out) without an
|
|
2768
|
+
error
|
|
2769
|
+
|
|
2770
|
+
```json
|
|
2771
|
+
"extract": "{{record.price}} {{record.currency}}" // Combines two fields
|
|
2772
|
+
```
|
|
2773
|
+
|
|
2774
|
+
**3. Hard-Coded Value (literal string)**
|
|
2775
|
+
- Does NOT start with '$'
|
|
2776
|
+
- Does NOT contain handlebars '{{' syntax
|
|
2777
|
+
- System treats it as a literal string value
|
|
2778
|
+
- VERY COMMON for setting static/constant values
|
|
2779
|
+
- Examples: "Active", "USD", "Completed", "true"
|
|
2780
|
+
|
|
2781
|
+
```json
|
|
2782
|
+
"extract": "primary" // Sets field value to the literal string "primary"
|
|
2783
|
+
"extract": "true" // Sets field value to the literal string "true"
|
|
2784
|
+
"extract": "N/A" // Sets field value to the literal string "N/A"
|
|
2785
|
+
```
|
|
2786
|
+
|
|
2787
|
+
This third pattern is the simplest and most efficient way to set hard-coded values in your mappings.
|
|
2788
|
+
AI agents should use this pattern whenever a field needs a static value that doesn't come from
|
|
2789
|
+
the input record or require computation.
|
|
2790
|
+
|
|
2791
|
+
**Important implementation details**
|
|
2792
|
+
|
|
2793
|
+
- JSON path patterns ALWAYS execute from the TOP-LEVEL root of the input record
|
|
2794
|
+
- The system maintains this context even in deeply nested mappings
|
|
2795
|
+
- For object mappings without child mappings, extract should return a complete object
|
|
2796
|
+
- An `object` row takes `extract` (to copy a whole object) or child `mappings`, not
|
|
2797
|
+
both: a row with both fails with 422 (`"extract" should not be present if
|
|
2798
|
+
"mappings" field is present`). A `buildArrayHelper` entry is different: there
|
|
2799
|
+
`extract` and `mappings` work together.
|
|
2800
|
+
- The root is the record as it arrives: an object record roots at `$.field`; a
|
|
2801
|
+
grouped record (an array of rows — grouped exports, file key columns, NetSuite
|
|
2802
|
+
grouped saved searches) roots at the array, so its rows are addressed as
|
|
2803
|
+
`$[0].field` (one row) or `$[*].field` (every row). A root that contradicts the
|
|
2804
|
+
record's shape resolves to nothing without an error.
|
|
2805
|
+
|
|
2806
|
+
For most simple field-to-field mappings, prefer JSON path syntax for its clarity and performance.
|
|
2807
|
+
For hard-coded values, simply use the literal string as the extract value.
|
|
2808
|
+
x-celigo-ai-guidance:
|
|
2809
|
+
- |-
|
|
2810
|
+
## GROUPED (ARRAY) RECORDS
|
|
2811
|
+
Decide the JSONPath root from the record's shape before writing
|
|
2812
|
+
any extract. When the record is an array of rows, `$.field`,
|
|
2813
|
+
`$.properties.field` and `$.rows[*].field` all resolve to
|
|
2814
|
+
nothing — the processor still reports success and the request
|
|
2815
|
+
body ships as `{}`. Address rows as `$[0].field` (that row's
|
|
2816
|
+
value, typed) or `$[*].field` (every row: joined with commas
|
|
2817
|
+
into a `string` destination; rejected with
|
|
2818
|
+
`incompatible_destination_conversion` into a `number`
|
|
2819
|
+
destination). Column labels with spaces work as
|
|
2820
|
+
`$[*][Order Number]`, `$[*].[Order Number]`, or
|
|
2821
|
+
`$[*]['Order Number']`. For one destination element per row
|
|
2822
|
+
the two array kinds take different helper forms: a primitive
|
|
2823
|
+
array (`stringarray` / `numberarray`) uses `buildArrayHelper:
|
|
2824
|
+
[{"extract": "$[*].field"}]`; an `objectarray` uses
|
|
2825
|
+
`buildArrayHelper: [{"extract": "$[*]", "mappings": [...]}]`
|
|
2826
|
+
with the children addressing the row relatively (`$.field`,
|
|
2827
|
+
`{{rows.field}}`). An `extract` placed directly on the
|
|
2828
|
+
array-typed field yields nothing. Handlebars
|
|
2829
|
+
extracts bind the array record as `rows` (`{{rows.0.field}}`),
|
|
2830
|
+
an object record as `record`. The reverse holds too: `$[*]` on
|
|
2831
|
+
an object record iterates the object's values, not rows.
|
|
2832
|
+
- |-
|
|
2833
|
+
## SIZE LIMIT
|
|
2834
|
+
The platform's import save validator caps this field at **1024
|
|
2835
|
+
characters**. Saves with a longer `extract` are rejected
|
|
2836
|
+
with `[size_limit_exceeded] The maximum size of the field:
|
|
2837
|
+
mappings.<index>.extract in the Import document should be
|
|
2838
|
+
1024 characters`. This typically only matters for
|
|
2839
|
+
Handlebars templates that build complex strings inline -- if
|
|
2840
|
+
a template is approaching the cap, prefer one of:
|
|
2841
|
+
|
|
2842
|
+
- **Decompose into nested mappings** (set `dataType:
|
|
2843
|
+
"object"` and use child `mappings` -- each child gets
|
|
2844
|
+
its own 1024-char budget).
|
|
2845
|
+
- **Move the logic to a `preMap` hook** so the heavy
|
|
2846
|
+
transformation runs in script and the mapping just reads
|
|
2847
|
+
`record.<computed>`.
|
|
2848
|
+
- **Use a lookup** (`lookupName` + a small `lookups` entry)
|
|
2849
|
+
for value translation that would otherwise need a long
|
|
2850
|
+
`{{#if ...}}{{else if ...}}` chain.
|
|
2851
|
+
examples:
|
|
2852
|
+
- $.fullName
|
|
2853
|
+
- '{{record.fullName}}'
|
|
2854
|
+
- primary
|
|
2855
|
+
- $.lineItems[*].unitPrice
|
|
2856
|
+
extractDateFormat:
|
|
2857
|
+
type: string
|
|
2858
|
+
description: |
|
|
2859
|
+
Specifies the format pattern of the input date string to ensure proper parsing.
|
|
2860
|
+
|
|
2861
|
+
Used on string-typed mappings whose `extract` yields a date. Uses
|
|
2862
|
+
Moment.js-compatible formatting tokens to describe how the incoming date
|
|
2863
|
+
string is structured.
|
|
2864
|
+
examples:
|
|
2865
|
+
- YYYY-MM-DD
|
|
2866
|
+
- MM/DD/YYYY
|
|
2867
|
+
- DD-MMM-YYYY HH:mm:ss
|
|
2868
|
+
extractDateTimezone:
|
|
2869
|
+
type: string
|
|
2870
|
+
description: |
|
|
2871
|
+
Specifies the timezone of the input date string using Olson/IANA timezone identifiers.
|
|
2872
|
+
|
|
2873
|
+
Used on string-typed mappings whose `extract` yields a date; tells the system
|
|
2874
|
+
how to interpret timestamp values from the input system.
|
|
2875
|
+
examples:
|
|
2876
|
+
- UTC
|
|
2877
|
+
- America/New_York
|
|
2878
|
+
- Europe/London
|
|
2879
|
+
generateDateFormat:
|
|
2880
|
+
type: string
|
|
2881
|
+
description: |
|
|
2882
|
+
Specifies the output format pattern when generating a date string or converting
|
|
2883
|
+
from a Date type to String type.
|
|
2884
|
+
|
|
2885
|
+
Uses Moment.js-compatible formatting tokens to define the structure of the resulting
|
|
2886
|
+
date string.
|
|
2887
|
+
examples:
|
|
2888
|
+
- YYYY-MM-DD
|
|
2889
|
+
- MM/DD/YYYY
|
|
2890
|
+
- DD-MMM-YYYY HH:mm:ss
|
|
2891
|
+
generateDateTimezone:
|
|
2892
|
+
type: string
|
|
2893
|
+
description: |
|
|
2894
|
+
Specifies the timezone to apply when generating or converting timestamp values
|
|
2895
|
+
using Olson/IANA timezone identifiers.
|
|
2896
|
+
|
|
2897
|
+
Controls timezone conversion when producing date output.
|
|
2898
|
+
examples:
|
|
2899
|
+
- UTC
|
|
2900
|
+
- America/New_York
|
|
2901
|
+
- Europe/London
|
|
2902
|
+
default:
|
|
2903
|
+
type:
|
|
2904
|
+
- string
|
|
2905
|
+
- 'null'
|
|
2906
|
+
description: |
|
|
2907
|
+
Specifies a fallback value to use when extract returns empty/null or when conditional
|
|
2908
|
+
logic fails and no other mapping supplies a value.
|
|
2909
|
+
|
|
2910
|
+
Explicit JSON `null` is itself a valid fallback: the destination field is written as
|
|
2911
|
+
JSON null when the extract yields nothing (the Mapper UI's "Use null as default value"
|
|
2912
|
+
action). Omitting the key entirely means no fallback — the field is left out of the
|
|
2913
|
+
output when the extract is missing or an empty string (the UI's "Do nothing" action),
|
|
2914
|
+
while a null source is still written as null unless `conditional.when` is
|
|
2915
|
+
`extract_not_empty`. Failing the record instead is `conditional.when:
|
|
2916
|
+
fail_record_when_empty`, which excludes a default.
|
|
2917
|
+
x-celigo-ai-guidance:
|
|
2918
|
+
- |-
|
|
2919
|
+
`"default": null` and `"default": ""` are distinct saved values, not
|
|
2920
|
+
absent keys: null renders the destination field as JSON null and the
|
|
2921
|
+
empty string renders it as `""` when the extract yields nothing.
|
|
2922
|
+
Preserve them verbatim when editing or migrating a mapping — dropping
|
|
2923
|
+
the key changes runtime behavior from "use null/empty string as
|
|
2924
|
+
default value" to "do nothing" (a missing or `""` source is left out
|
|
2925
|
+
of the output, while a null source is written as null unless
|
|
2926
|
+
`conditional.when` is `extract_not_empty`).
|
|
2927
|
+
- |-
|
|
2928
|
+
The four "Action to take if source field has no value" choices map to:
|
|
2929
|
+
do nothing → no `default` key (add `conditional.when:
|
|
2930
|
+
extract_not_empty` to leave a null source out too; without it a null
|
|
2931
|
+
source is written as null); use null → `"default": null`; use empty string or
|
|
2932
|
+
a custom value → `"default": "<value>"`; cause the record to fail →
|
|
2933
|
+
`conditional.when: fail_record_when_empty` with no `default` key.
|
|
2934
|
+
examples:
|
|
2935
|
+
- N/A
|
|
2936
|
+
- '0'
|
|
2937
|
+
- 'false'
|
|
2938
|
+
lookupName:
|
|
2939
|
+
type: string
|
|
2940
|
+
description: |
|
|
2941
|
+
**Purpose**
|
|
2942
|
+
References a lookup table for transforming values during the mapping process.
|
|
2943
|
+
|
|
2944
|
+
**Usage**
|
|
2945
|
+
|
|
2946
|
+
The lookupName refers to a named lookup defined in the lookups array of the same resource.
|
|
2947
|
+
On an HTTP import that is `http.lookups`: a `lookups` array sent only at the top level
|
|
2948
|
+
is dropped on save. On an import, a name that matches no lookup fails every record
|
|
2949
|
+
with "Unable to find lookup in mapping configs - <name>", and a key the lookup
|
|
2950
|
+
doesn't hold follows the lookup's `allowFailures`: false fails the record; true, or
|
|
2951
|
+
the field left out, lets the record succeed with the lookup's `default`, or without
|
|
2952
|
+
the mapped field when there is none.
|
|
2953
|
+
|
|
2954
|
+
```json
|
|
2955
|
+
{
|
|
2956
|
+
"generate": "countryName",
|
|
2957
|
+
"dataType": "string",
|
|
2958
|
+
"extract": "$.countryCode",
|
|
2959
|
+
"lookupName": "countryCodeToName"
|
|
2960
|
+
}
|
|
2961
|
+
```
|
|
2962
|
+
|
|
2963
|
+
During processing, the system:
|
|
2964
|
+
1. Extracts the value from the input record (e.g., "US")
|
|
2965
|
+
2. Finds the lookup table with the specified name
|
|
2966
|
+
3. Uses the extracted value as a key in the lookup
|
|
2967
|
+
4. Returns the corresponding value (e.g., "United States")
|
|
2968
|
+
|
|
2969
|
+
**Benefits**
|
|
2970
|
+
|
|
2971
|
+
- **Standardization**: Ensures consistent value translation across mappings
|
|
2972
|
+
- **Centralization**: Define translations once and reference them in multiple places
|
|
2973
|
+
- **Maintainability**: Update all mappings by changing the lookup definition
|
|
2974
|
+
- **Readability**: Makes mappings more descriptive and self-documenting
|
|
2975
|
+
|
|
2976
|
+
The specific lookup capabilities depend on the context where mappings are used.
|
|
2977
|
+
examples:
|
|
2978
|
+
- countryCodeToName
|
|
2979
|
+
- statusMapping
|
|
2980
|
+
- departmentCodes
|
|
2981
|
+
hardCodedValue:
|
|
2982
|
+
type:
|
|
2983
|
+
- string
|
|
2984
|
+
- 'null'
|
|
2985
|
+
description: |
|
|
2986
|
+
Constant written to the destination instead of an extracted value. On a primitive
|
|
2987
|
+
array (`stringarray`, `numberarray`, `booleanarray`) the string is split on commas,
|
|
2988
|
+
verbatim and untrimmed, into elements of the array's type (`"A,B"` gives `["A", "B"]`).
|
|
2989
|
+
On an `object` it must be a JSON object string and on an `objectarray` a JSON array
|
|
2990
|
+
string (an object string becomes one element); the save parses it and refuses non-JSON
|
|
2991
|
+
or the wrong shape with 422, and an array row with a constant needs no `buildArrayHelper`.
|
|
2992
|
+
JSON `null` writes the destination field as null; it is what the mapper saves for its
|
|
2993
|
+
hard-coded "Use null as default value" choice.
|
|
2994
|
+
examples:
|
|
2995
|
+
- USD
|
|
2996
|
+
- A,B
|
|
2997
|
+
- '[{"code": "A"}, {"code": "B"}]'
|
|
2998
|
+
description:
|
|
2999
|
+
type: string
|
|
3000
|
+
description: |
|
|
3001
|
+
Optional free-text annotation that appears in the Mapper sidebar to provide context about
|
|
3002
|
+
the mapping's purpose for collaboration and documentation.
|
|
3003
|
+
|
|
3004
|
+
Has no functional impact on the mapping behavior.
|
|
3005
|
+
examples:
|
|
3006
|
+
- Maps customer name
|
|
3007
|
+
- Converts price to target currency
|
|
3008
|
+
- Formats date for target system
|
|
3009
|
+
sourceDataType:
|
|
3010
|
+
type: string
|
|
3011
|
+
description: |
|
|
3012
|
+
Declares the JSON type of the value produced by `extract`, before any
|
|
3013
|
+
conversion to `dataType`. Same enum as `dataType`. Set on leaf mappings
|
|
3014
|
+
only — parent mappings (with child `mappings` or `buildArrayHelper`)
|
|
3015
|
+
have no extracted value of their own; the children carry their own
|
|
3016
|
+
`sourceDataType`.
|
|
3017
|
+
|
|
3018
|
+
For date fields use `string` (JSON represents dates as strings); the
|
|
3019
|
+
parsing/formatting lives in `extractDateFormat` / `generateDateFormat` /
|
|
3020
|
+
`extractDateTimezone` / `generateDateTimezone`.
|
|
3021
|
+
enum:
|
|
3022
|
+
- string
|
|
3023
|
+
- number
|
|
3024
|
+
- boolean
|
|
3025
|
+
- object
|
|
3026
|
+
- stringarray
|
|
3027
|
+
- numberarray
|
|
3028
|
+
- booleanarray
|
|
3029
|
+
- objectarray
|
|
3030
|
+
- arrayarray
|
|
3031
|
+
x-enumDescriptions:
|
|
3032
|
+
string: Source value is a text string.
|
|
3033
|
+
number: Source value is numeric.
|
|
3034
|
+
boolean: Source value is true or false.
|
|
3035
|
+
object: Source value is a JSON object.
|
|
3036
|
+
stringarray: Source value is an array of strings.
|
|
3037
|
+
numberarray: Source value is an array of numbers.
|
|
3038
|
+
booleanarray: Source value is an array of booleans.
|
|
3039
|
+
objectarray: Source value is an array of objects.
|
|
3040
|
+
arrayarray: Source value is an array of arrays.
|
|
3041
|
+
examples:
|
|
3042
|
+
- string
|
|
3043
|
+
- number
|
|
3044
|
+
- boolean
|
|
3045
|
+
- object
|
|
3046
|
+
mappings:
|
|
3047
|
+
type: array
|
|
3048
|
+
description: |
|
|
3049
|
+
**Purpose**
|
|
3050
|
+
Enables recursive definition of nested object structures through child mapping objects.
|
|
3051
|
+
|
|
3052
|
+
**Guidance**
|
|
3053
|
+
This is the KEY FIELD that implements the recursive pattern at the core of this schema:
|
|
3054
|
+
|
|
3055
|
+
**When to Use**
|
|
3056
|
+
- REQUIRED when dataType = "object" (unless you are copying an entire object from the input record)
|
|
3057
|
+
- REQUIRED in buildArrayHelper.mappings when defining complex object array elements
|
|
3058
|
+
- NEVER used with simple types (string, number, boolean)
|
|
3059
|
+
|
|
3060
|
+
**Behavior**
|
|
3061
|
+
- Each mapping in this array becomes a property of the parent object
|
|
3062
|
+
- The full Mappings schema is repeated recursively at each level
|
|
3063
|
+
- Can be nested to any depth for complex hierarchical structures
|
|
3064
|
+
|
|
3065
|
+
**Context Handling**
|
|
3066
|
+
- Each level of nesting changes the mapping CONTEXT for 'generate'
|
|
3067
|
+
- The extraction CONTEXT always remains the original input record
|
|
3068
|
+
- This means child mappings can pull data from anywhere in the input record
|
|
3069
|
+
|
|
3070
|
+
**Common Patterns**
|
|
3071
|
+
|
|
3072
|
+
**Nested Objects**
|
|
3073
|
+
```json
|
|
3074
|
+
{
|
|
3075
|
+
"generate": "customer",
|
|
3076
|
+
"dataType": "object",
|
|
3077
|
+
"mappings": [
|
|
3078
|
+
{
|
|
3079
|
+
"generate": "contact",
|
|
3080
|
+
"dataType": "object",
|
|
3081
|
+
"mappings": [
|
|
3082
|
+
{"generate": "email", "dataType": "string", "extract": "$.customerEmail"}
|
|
3083
|
+
]
|
|
3084
|
+
}
|
|
3085
|
+
]
|
|
3086
|
+
}
|
|
3087
|
+
```
|
|
3088
|
+
|
|
3089
|
+
**Multiple Fields in Object**
|
|
3090
|
+
```json
|
|
3091
|
+
{
|
|
3092
|
+
"generate": "address",
|
|
3093
|
+
"dataType": "object",
|
|
3094
|
+
"mappings": [
|
|
3095
|
+
{"generate": "street", "dataType": "string", "extract": "$.address.line1"},
|
|
3096
|
+
{"generate": "city", "dataType": "string", "extract": "$.address.city"},
|
|
3097
|
+
{"generate": "country", "dataType": "string", "extract": "$.address.country"}
|
|
3098
|
+
]
|
|
3099
|
+
}
|
|
3100
|
+
```
|
|
3101
|
+
|
|
3102
|
+
IMPORTANT: When analyzing or generating mappings, ALWAYS check if parent.dataType = "object"
|
|
3103
|
+
or if you're inside buildArrayHelper.mappings for objectarray elements. These are the only
|
|
3104
|
+
valid contexts for the mappings array.
|
|
3105
|
+
items:
|
|
3106
|
+
$ref: '#/components/schemas/items'
|
|
3107
|
+
examples:
|
|
3108
|
+
- - generate: firstName
|
|
3109
|
+
extract: $.name.first
|
|
3110
|
+
dataType: string
|
|
3111
|
+
status: Active
|
|
3112
|
+
- generate: lastName
|
|
3113
|
+
extract: $.name.last
|
|
3114
|
+
dataType: string
|
|
3115
|
+
status: Active
|
|
3116
|
+
buildArrayHelper:
|
|
3117
|
+
type: array
|
|
3118
|
+
x-celigo-ai-guidance:
|
|
3119
|
+
- |-
|
|
3120
|
+
Entry-level `extract` accepts an iterating array path
|
|
3121
|
+
(`$.items[*]`), `"$"` (the record root), or omission — a
|
|
3122
|
+
constructed entry (child `mappings` with the extract omitted or
|
|
3123
|
+
`"$"`; the two spellings are equivalent) contributes exactly one
|
|
3124
|
+
element, and entries append in order. On a grouped (array)
|
|
3125
|
+
record the record itself is the array to iterate: `"$[*]"`
|
|
3126
|
+
yields one `objectarray` element per row (children address the
|
|
3127
|
+
row as `$.field`), and `"$[*].field"` yields one primitive-array
|
|
3128
|
+
value per row. Indexed or comma-joined
|
|
3129
|
+
entry extracts (`"$[0]"`, `"$[0],$[0]"`) are not valid: the
|
|
3130
|
+
processor renders the entire destination array as null with no
|
|
3131
|
+
validation error. To emit a fixed number of static elements, add
|
|
3132
|
+
that many sibling constructed entries — never index the extract.
|
|
3133
|
+
- |-
|
|
3134
|
+
An entry's `extract` can be a Handlebars template. On an
|
|
3135
|
+
`objectarray` it must render a JSON object (one element) or a JSON
|
|
3136
|
+
array (one element per item). On a primitive array each entry
|
|
3137
|
+
renders one element, so a serialized array becomes one string
|
|
3138
|
+
element. A bare literal entry extract is refused with 422 ("extract
|
|
3139
|
+
only supports json path or handlebars expression"); set a constant
|
|
3140
|
+
with the row's `hardCodedValue` instead.
|
|
3141
|
+
description: |
|
|
3142
|
+
**Purpose**
|
|
3143
|
+
Configures how to construct arrays in the output record, handling various array types and inputs.
|
|
3144
|
+
|
|
3145
|
+
**Guidance**
|
|
3146
|
+
This is the mechanism for building array data types:
|
|
3147
|
+
|
|
3148
|
+
**When to Use**
|
|
3149
|
+
- REQUIRED when dataType ends with "array" (stringarray, objectarray, etc.), unless the
|
|
3150
|
+
row sets `hardCodedValue`: an array row's own `extract` is never read (see `dataType`)
|
|
3151
|
+
- Each entry in this array contributes elements to the output array
|
|
3152
|
+
- Multiple entries allow combining data from different input arrays
|
|
3153
|
+
|
|
3154
|
+
**Array Type Handling**
|
|
3155
|
+
|
|
3156
|
+
**For Simple Arrays (stringarray, numberarray, booleanarray)**
|
|
3157
|
+
- Only the 'extract' field is used to pull values
|
|
3158
|
+
- JSON path with wildcards (e.g., $.items[*].name) returns multiple values;
|
|
3159
|
+
on a grouped (array) record the record itself is the array, so the
|
|
3160
|
+
path roots at it ($[*].name — one value per row)
|
|
3161
|
+
- Each result is converted to the appropriate primitive type
|
|
3162
|
+
```json
|
|
3163
|
+
{
|
|
3164
|
+
"generate": "productNames",
|
|
3165
|
+
"dataType": "stringarray",
|
|
3166
|
+
"buildArrayHelper": [
|
|
3167
|
+
{"extract": "$.products[*].name"}
|
|
3168
|
+
]
|
|
3169
|
+
}
|
|
3170
|
+
```
|
|
3171
|
+
|
|
3172
|
+
**For Object Arrays (objectarray) - three patterns**
|
|
3173
|
+
|
|
3174
|
+
1. Extract Only (existing objects):
|
|
3175
|
+
```json
|
|
3176
|
+
{
|
|
3177
|
+
"generate": "contacts",
|
|
3178
|
+
"dataType": "objectarray",
|
|
3179
|
+
"buildArrayHelper": [
|
|
3180
|
+
{"extract": "$.account.primaryContacts[*]"}, // Pull primary contact objects
|
|
3181
|
+
{"extract": "$.account.secondaryContacts[*]"}, // Pull secondary contact objects
|
|
3182
|
+
{"extract": "$.vendor.contactPersons[*]"}, // Pull vendor contact objects
|
|
3183
|
+
{"extract": "$.subsidiaries[*].mainContact"} // Pull main contact from each subsidiary
|
|
3184
|
+
]
|
|
3185
|
+
}
|
|
3186
|
+
```
|
|
3187
|
+
|
|
3188
|
+
2. Mappings Only (constructed object):
|
|
3189
|
+
```json
|
|
3190
|
+
{
|
|
3191
|
+
"generate": "contactInfo",
|
|
3192
|
+
"dataType": "objectarray",
|
|
3193
|
+
"buildArrayHelper": [
|
|
3194
|
+
{
|
|
3195
|
+
"mappings": [ // Creates one object in the array
|
|
3196
|
+
{"generate": "type", "dataType": "string", "extract": "primary"},
|
|
3197
|
+
{"generate": "email", "dataType": "string", "extract": "$.primaryEmail"}
|
|
3198
|
+
]
|
|
3199
|
+
},
|
|
3200
|
+
{
|
|
3201
|
+
"mappings": [ // Creates another object in the array
|
|
3202
|
+
{"generate": "type", "dataType": "string", "extract": "secondary"},
|
|
3203
|
+
{"generate": "email", "dataType": "string", "extract": "$.secondaryEmail"}
|
|
3204
|
+
]
|
|
3205
|
+
}
|
|
3206
|
+
]
|
|
3207
|
+
}
|
|
3208
|
+
```
|
|
3209
|
+
Each constructed entry contributes exactly one element, in entry
|
|
3210
|
+
order; writing the entry with `"extract": "$"` is equivalent to
|
|
3211
|
+
omitting the extract (both anchor the element at the record root).
|
|
3212
|
+
A fixed number of static elements is built from that many sibling
|
|
3213
|
+
constructed entries.
|
|
3214
|
+
|
|
3215
|
+
3. Extract AND Mappings (transform input arrays):
|
|
3216
|
+
```json
|
|
3217
|
+
{
|
|
3218
|
+
"generate": "lineItems",
|
|
3219
|
+
"dataType": "objectarray",
|
|
3220
|
+
"buildArrayHelper": [
|
|
3221
|
+
{
|
|
3222
|
+
"extract": "$.order.items[*]", // For each item in the array
|
|
3223
|
+
"mappings": [ // Transform to this structure using the composite object
|
|
3224
|
+
{"generate": "sku", "dataType": "string", "extract": "$.order.items.productId"}, // Notice: items is singular
|
|
3225
|
+
{"generate": "quantity", "dataType": "number", "extract": "$.order.items.qty"}, // Notice: items is singular
|
|
3226
|
+
{"generate": "orderNumber", "dataType": "string", "extract": "$.order.id"}, // Access parent data
|
|
3227
|
+
{"generate": "customerName", "dataType": "string", "extract": "$.customerName"} // Access root data
|
|
3228
|
+
]
|
|
3229
|
+
}
|
|
3230
|
+
]
|
|
3231
|
+
}
|
|
3232
|
+
```
|
|
3233
|
+
|
|
3234
|
+
**Arrays of Arrays**
|
|
3235
|
+
- The mapper has no working type for them: `arrayarray` saves, but every record
|
|
3236
|
+
fails with `Destination datatype is a required field.` Build an array of arrays
|
|
3237
|
+
in a script hook instead.
|
|
3238
|
+
|
|
3239
|
+
**Important details**
|
|
3240
|
+
|
|
3241
|
+
- When both extract and mappings are provided, the system creates special composite objects
|
|
3242
|
+
that maintain hierarchical context during processing
|
|
3243
|
+
- This enables accessing both the current array element AND its parent context
|
|
3244
|
+
- An ITERATING entry's extract MUST be a JSON path that iterates an array:
|
|
3245
|
+
'$.items[*]' when the array is a field of an object record, or '$[*]'
|
|
3246
|
+
(objectarray) / '$[*].field' (primitive arrays) when the record itself is a
|
|
3247
|
+
grouped array of rows. A CONSTRUCTED entry (child mappings building one
|
|
3248
|
+
element) instead omits extract or sets it to exactly "$" — never rewrite "$"
|
|
3249
|
+
into an indexed or comma-joined form ('$[0]', '$[0],$[0]'): those render the
|
|
3250
|
+
entire destination array as null without raising a validation error
|
|
3251
|
+
- Each array helper entry acts independently, potentially adding multiple elements
|
|
3252
|
+
|
|
3253
|
+
The buildArrayHelper is the most complex part of the mappings system - always analyze the
|
|
3254
|
+
dataType first to understand which pattern is appropriate.
|
|
3255
|
+
items:
|
|
3256
|
+
type: object
|
|
3257
|
+
properties:
|
|
3258
|
+
extract:
|
|
3259
|
+
type: string
|
|
3260
|
+
description: |
|
|
3261
|
+
JSON path expression that identifies the input array or values to extract.
|
|
3262
|
+
|
|
3263
|
+
For objectarray with mappings, this defines which input objects to iterate through.
|
|
3264
|
+
The JSON path must return either a single object or an array of objects.
|
|
3265
|
+
|
|
3266
|
+
For a CONSTRUCTED entry (child mappings building exactly one element from
|
|
3267
|
+
record-root fields and constants), omit this field or set it to exactly "$" —
|
|
3268
|
+
the two spellings are equivalent. Indexed or comma-joined forms ('$[0]',
|
|
3269
|
+
'$[0],$[0]') are not valid at the entry level: the processor renders the
|
|
3270
|
+
entire destination array as null without raising a validation error.
|
|
3271
|
+
|
|
3272
|
+
The system creates special composite objects during processing to maintain
|
|
3273
|
+
hierarchical relationships, allowing easy access to both the current array item
|
|
3274
|
+
and its parent contexts.
|
|
3275
|
+
|
|
3276
|
+
An iterating entry keeps the `[*]`: `$.line_items` without it yields one empty
|
|
3277
|
+
element per item, with no error. Child extracts drop the `[*]` but keep the
|
|
3278
|
+
array's path (`$.line_items.sku`); `$.line_items[*].sku` maps nothing, and an
|
|
3279
|
+
element-relative `$.sku` reads the record root instead of the element.
|
|
3280
|
+
examples:
|
|
3281
|
+
- $.items[*]
|
|
3282
|
+
- $.order.lineItems[*]
|
|
3283
|
+
- $.parents[*].children[*]
|
|
3284
|
+
- $
|
|
3285
|
+
name:
|
|
3286
|
+
type: string
|
|
3287
|
+
maxLength: 200
|
|
3288
|
+
description: |
|
|
3289
|
+
Display label for this source object in the mapper, so the sources of
|
|
3290
|
+
an object array can be told apart instead of all showing as `$`.
|
|
3291
|
+
Has no effect at runtime; stored only when non-empty.
|
|
3292
|
+
x-celigo-ai-guidance:
|
|
3293
|
+
- |-
|
|
3294
|
+
Carry an existing `name` through every edit — it is the user's label
|
|
3295
|
+
for the tab, and an entry sent without it loses the label. Duplicate
|
|
3296
|
+
names across entries are allowed. Set one only when the user names
|
|
3297
|
+
the source object; never invent labels.
|
|
3298
|
+
examples:
|
|
3299
|
+
- Billing address
|
|
3300
|
+
- Shipping address
|
|
3301
|
+
sourceDataType:
|
|
3302
|
+
type: string
|
|
3303
|
+
description: |
|
|
3304
|
+
Declares the JSON type of the input array being iterated, to ensure
|
|
3305
|
+
proper type handling during array construction. Same enum as `dataType`.
|
|
3306
|
+
enum:
|
|
3307
|
+
- string
|
|
3308
|
+
- number
|
|
3309
|
+
- boolean
|
|
3310
|
+
- object
|
|
3311
|
+
- stringarray
|
|
3312
|
+
- numberarray
|
|
3313
|
+
- booleanarray
|
|
3314
|
+
- objectarray
|
|
3315
|
+
- arrayarray
|
|
3316
|
+
x-enumDescriptions:
|
|
3317
|
+
string: Input array contains string elements.
|
|
3318
|
+
number: Input array contains numeric elements.
|
|
3319
|
+
boolean: Input array contains boolean elements.
|
|
3320
|
+
object: Input array contains object elements.
|
|
3321
|
+
stringarray: Input array contains arrays of strings.
|
|
3322
|
+
numberarray: Input array contains arrays of numbers.
|
|
3323
|
+
booleanarray: Input array contains arrays of booleans.
|
|
3324
|
+
objectarray: Input array contains arrays of objects.
|
|
3325
|
+
arrayarray: Input array contains arrays of arrays.
|
|
3326
|
+
examples:
|
|
3327
|
+
- string
|
|
3328
|
+
- number
|
|
3329
|
+
- boolean
|
|
3330
|
+
- object
|
|
3331
|
+
default:
|
|
3332
|
+
type:
|
|
3333
|
+
- string
|
|
3334
|
+
- 'null'
|
|
3335
|
+
description: |
|
|
3336
|
+
Specifies a fallback value when the extracted array element is empty or
|
|
3337
|
+
not found in the input data.
|
|
3338
|
+
|
|
3339
|
+
Explicit JSON `null` is itself a valid fallback (the element is written as
|
|
3340
|
+
JSON null); omitting the key means no fallback is applied.
|
|
3341
|
+
examples:
|
|
3342
|
+
- N/A
|
|
3343
|
+
- '0'
|
|
3344
|
+
- 'false'
|
|
3345
|
+
conditional:
|
|
3346
|
+
type: object
|
|
3347
|
+
description: |
|
|
3348
|
+
Defines conditional rules for including each array element in the result.
|
|
3349
|
+
x-celigo-ai-guidance:
|
|
3350
|
+
- |-
|
|
3351
|
+
Judged against this entry's own `extract` (the array source). The
|
|
3352
|
+
design scopes the UI's tab-level "Action to take if source field has
|
|
3353
|
+
no value" to copy-as-is tabs (no child `mappings`); the API accepts
|
|
3354
|
+
`fail_record_when_empty` on a mapped entry as well, and the mapper
|
|
3355
|
+
processor honors it there — the record fails when that array is
|
|
3356
|
+
missing or empty (`errors[]` entry `code: extract_empty`, `fatal:
|
|
3357
|
+
true`, message `<generate>: Source field has no value`; probed
|
|
3358
|
+
2026-10-09). Say so when writing it on a mapped entry: the user may
|
|
3359
|
+
not find the setting in the mapper's tab. To fail on an empty field
|
|
3360
|
+
inside each element, set the action on that child mapping instead.
|
|
3361
|
+
properties:
|
|
3362
|
+
when:
|
|
3363
|
+
type: string
|
|
3364
|
+
description: |
|
|
3365
|
+
Condition judged on the entry's extract — skip the elements the
|
|
3366
|
+
extract does not return, or fail the whole record when the source
|
|
3367
|
+
array is missing or empty.
|
|
3368
|
+
enum:
|
|
3369
|
+
- extract_not_empty
|
|
3370
|
+
- fail_record_when_empty
|
|
3371
|
+
x-enumDescriptions:
|
|
3372
|
+
extract_not_empty: Include an array element only when the extract returns a non-empty value for it
|
|
3373
|
+
fail_record_when_empty: Fail the record when the entry's source array is missing or empty
|
|
3374
|
+
examples:
|
|
3375
|
+
- extract_not_empty
|
|
3376
|
+
mappings:
|
|
3377
|
+
type: array
|
|
3378
|
+
description: |
|
|
3379
|
+
Contains recursive mapping definitions for complex array element transformations.
|
|
3380
|
+
|
|
3381
|
+
**Composite object mechanism**
|
|
3382
|
+
|
|
3383
|
+
When both 'extract' and 'mappings' are used together, the system implements a sophisticated
|
|
3384
|
+
"composite object" approach that is crucial for AI agents to understand:
|
|
3385
|
+
|
|
3386
|
+
1. The system starts with the complete input record
|
|
3387
|
+
|
|
3388
|
+
2. For each array element matched by the extract path, it creates a modified version of
|
|
3389
|
+
the input record where:
|
|
3390
|
+
- Array paths in the extract JSON path are REPLACED with single objects
|
|
3391
|
+
- Each array ([]) in the path is converted to a single object ({})
|
|
3392
|
+
- This preserves the hierarchical relationship between nested arrays
|
|
3393
|
+
|
|
3394
|
+
**Example**
|
|
3395
|
+
|
|
3396
|
+
Given an input record:
|
|
3397
|
+
```json
|
|
3398
|
+
{
|
|
3399
|
+
"customer": {
|
|
3400
|
+
"name": "John Doe",
|
|
3401
|
+
"orders": [
|
|
3402
|
+
{
|
|
3403
|
+
"id": "O-001",
|
|
3404
|
+
"items": [
|
|
3405
|
+
{"sku": "ABC", "qty": 2},
|
|
3406
|
+
{"sku": "XYZ", "qty": 1}
|
|
3407
|
+
]
|
|
3408
|
+
},
|
|
3409
|
+
{
|
|
3410
|
+
"id": "O-002",
|
|
3411
|
+
"items": [
|
|
3412
|
+
{"sku": "DEF", "qty": 3}
|
|
3413
|
+
]
|
|
3414
|
+
}
|
|
3415
|
+
]
|
|
3416
|
+
}
|
|
3417
|
+
}
|
|
3418
|
+
```
|
|
3419
|
+
|
|
3420
|
+
With extract path: `$.customer.orders[*].items[*]`
|
|
3421
|
+
|
|
3422
|
+
For each item, the system creates a composite object like:
|
|
3423
|
+
```json
|
|
3424
|
+
{
|
|
3425
|
+
"customer": {
|
|
3426
|
+
"name": "John Doe",
|
|
3427
|
+
"orders": { // Note: Array replaced with single object
|
|
3428
|
+
"id": "O-001",
|
|
3429
|
+
"items": { // Note: Array replaced with single object
|
|
3430
|
+
"sku": "ABC",
|
|
3431
|
+
"qty": 2
|
|
3432
|
+
}
|
|
3433
|
+
}
|
|
3434
|
+
}
|
|
3435
|
+
}
|
|
3436
|
+
```
|
|
3437
|
+
|
|
3438
|
+
Then in your mappings, you can access:
|
|
3439
|
+
- The current item: `$.customer.orders.items.sku`
|
|
3440
|
+
- The parent order: `$.customer.orders.id`
|
|
3441
|
+
- Top-level data: `$.customer.name`
|
|
3442
|
+
|
|
3443
|
+
This approach allows for precise mapping from deeply nested structures while maintaining
|
|
3444
|
+
access to all contextual parent data, without requiring complex array index management.
|
|
3445
|
+
|
|
3446
|
+
**Implementation guidance**
|
|
3447
|
+
|
|
3448
|
+
When implementing the composite object mechanism:
|
|
3449
|
+
|
|
3450
|
+
1. Analyze the extract path to identify all array patterns (`[*]` or `[number]`)
|
|
3451
|
+
2. For each array in the path, understand that it will be replaced with a single object
|
|
3452
|
+
3. In the mappings, use paths that reference these arrays as if they were objects
|
|
3453
|
+
4. Remember that every mapping still has access to the full input record context
|
|
3454
|
+
5. This mechanism is especially powerful when mapping hierarchical data like:
|
|
3455
|
+
- Order → Line Items → Taxes/Discounts
|
|
3456
|
+
- Customer → Addresses → Address Lines
|
|
3457
|
+
- Invoice → Line Items → Serial Numbers
|
|
3458
|
+
|
|
3459
|
+
The extract path effectively tells the system "iterate through these arrays",
|
|
3460
|
+
while the composite object mechanism ensures you can still access both the
|
|
3461
|
+
current array item AND its parent context during mapping.
|
|
3462
|
+
items:
|
|
3463
|
+
$ref: '#/components/schemas/items'
|
|
3464
|
+
examples:
|
|
3465
|
+
- - generate: itemName
|
|
3466
|
+
extract: $.name
|
|
3467
|
+
dataType: string
|
|
3468
|
+
status: Active
|
|
3469
|
+
- generate: itemPrice
|
|
3470
|
+
extract: $.price
|
|
3471
|
+
dataType: number
|
|
3472
|
+
status: Active
|
|
3473
|
+
if:
|
|
3474
|
+
properties:
|
|
3475
|
+
conditional:
|
|
3476
|
+
properties:
|
|
3477
|
+
when:
|
|
3478
|
+
const: fail_record_when_empty
|
|
3479
|
+
required:
|
|
3480
|
+
- when
|
|
3481
|
+
required:
|
|
3482
|
+
- conditional
|
|
3483
|
+
then:
|
|
3484
|
+
not:
|
|
3485
|
+
required:
|
|
3486
|
+
- default
|
|
3487
|
+
status:
|
|
3488
|
+
type: string
|
|
3489
|
+
description: |
|
|
3490
|
+
**Purpose**
|
|
3491
|
+
Controls whether the mapping is applied. Send it on every mapping entry.
|
|
3492
|
+
|
|
3493
|
+
**Guidance**
|
|
3494
|
+
Only `Active` rows run. `Draft` and `Inactive` rows keep their
|
|
3495
|
+
configuration, are saved with minimal validation, and are skipped at
|
|
3496
|
+
runtime and in preview; a non-Active parent skips its whole subtree
|
|
3497
|
+
whatever its children say. Imports (on save and in the mapper processor)
|
|
3498
|
+
and API response mappings reject a row missing this field (validation
|
|
3499
|
+
error: "Mapping object must have status field present."); a Tool's
|
|
3500
|
+
output mapping saves and runs one, which is why `required` doesn't
|
|
3501
|
+
list it.
|
|
3502
|
+
x-celigo-ai-guidance:
|
|
3503
|
+
- |-
|
|
3504
|
+
Emit `"Active"` for mappings that should run; `"Draft"` is also
|
|
3505
|
+
accepted and saves the mapping while bypassing the Active-only
|
|
3506
|
+
field validations. The value is case-sensitive. The API rejects:
|
|
3507
|
+
- Missing field: `[status_field_absent] Mapping object must have status field present.`
|
|
3508
|
+
- Wrong case (e.g. `"active"`): `[invalid_status_enums] active is not a valid enum for status field.`
|
|
3509
|
+
- |-
|
|
3510
|
+
`"Inactive"` is the user's "Set inactive" on a row: use it only when
|
|
3511
|
+
asked to disable or park a row, never to mean incomplete (that is
|
|
3512
|
+
`"Draft"`). Setting a parent `Inactive` means no `Active` row may
|
|
3513
|
+
remain under it — the save rejects an `Active` row under an
|
|
3514
|
+
`Inactive` parent (`[inactive_parent_active_child]` on `mappings`,
|
|
3515
|
+
no message text) and never cascades or promotes on its own; `Draft`
|
|
3516
|
+
descendants are kept as they are, and a `Draft` parent does not gate
|
|
3517
|
+
its children. The UI's Set inactive on a parent marks the parent and
|
|
3518
|
+
every child `Inactive`. Re-enabling a child
|
|
3519
|
+
means re-enabling its ancestors in the same payload. Edits that keep
|
|
3520
|
+
existing rows must carry their stored status forward — rewriting a
|
|
3521
|
+
`Draft` or `Inactive` row to `Active` turns a row the user parked
|
|
3522
|
+
back on.
|
|
3523
|
+
enum:
|
|
3524
|
+
- Active
|
|
3525
|
+
- Draft
|
|
3526
|
+
- Inactive
|
|
3527
|
+
x-enumDescriptions:
|
|
3528
|
+
Active: The mapping is enabled and applied during processing
|
|
3529
|
+
Draft: In-progress mapping; saved without the Active-only field validations and skipped at runtime
|
|
3530
|
+
Inactive: Disabled by the user; configuration kept, skipped at runtime and in preview
|
|
3531
|
+
examples:
|
|
3532
|
+
- Active
|
|
3533
|
+
conditional:
|
|
3534
|
+
type: object
|
|
3535
|
+
description: |
|
|
3536
|
+
**Purpose**
|
|
3537
|
+
Defines conditional processing rules for the entire mapping.
|
|
3538
|
+
|
|
3539
|
+
**Guidance**
|
|
3540
|
+
These conditions determine whether the mapping is applied based on record
|
|
3541
|
+
state or field content:
|
|
3542
|
+
|
|
3543
|
+
**When to Use**
|
|
3544
|
+
- When a mapping should only be applied in specific circumstances
|
|
3545
|
+
- To implement conditional logic without using complex handlebars expressions
|
|
3546
|
+
- For creating mappings that only run during create or update operations
|
|
3547
|
+
|
|
3548
|
+
**Available Conditions**
|
|
3549
|
+
|
|
3550
|
+
- `record_created`: Apply only when creating a new record
|
|
3551
|
+
Useful for setting initial values that should not be overwritten during updates
|
|
3552
|
+
|
|
3553
|
+
- `record_updated`: Apply only when updating an existing record
|
|
3554
|
+
Useful for transformation logic that should only run during updates
|
|
3555
|
+
|
|
3556
|
+
- `extract_not_empty`: Apply only when the extract field returns a value
|
|
3557
|
+
Useful for conditional mapping based on input data availability
|
|
3558
|
+
|
|
3559
|
+
- `fail_record_when_empty`: Fail the record when the extract field returns
|
|
3560
|
+
no value (the UI's "Cause record to fail" action when the source field
|
|
3561
|
+
has no value)
|
|
3562
|
+
|
|
3563
|
+
**Example**
|
|
3564
|
+
```json
|
|
3565
|
+
{
|
|
3566
|
+
"generate": "statusMessage",
|
|
3567
|
+
"dataType": "string",
|
|
3568
|
+
"status": "Active",
|
|
3569
|
+
"extract": "$.status.message",
|
|
3570
|
+
"conditional": {
|
|
3571
|
+
"when": "extract_not_empty" // Only map when status.message exists
|
|
3572
|
+
}
|
|
3573
|
+
}
|
|
3574
|
+
```
|
|
3575
|
+
x-celigo-ai-guidance:
|
|
3576
|
+
- |-
|
|
3577
|
+
`when` holds one value, and two different settings share it: the
|
|
3578
|
+
composite-import operation gate (`record_created` / `record_updated`,
|
|
3579
|
+
the UI's "Only perform mapping when") and the empty-source action
|
|
3580
|
+
(`extract_not_empty` / `fail_record_when_empty`, the UI's "Action to
|
|
3581
|
+
take if source field has no value"). A row cannot carry both — writing
|
|
3582
|
+
one replaces the other and the save succeeds, so a composite import
|
|
3583
|
+
row that needs both has to choose. Never author `fail_record_when_empty`
|
|
3584
|
+
on a row that already carries `record_created` or `record_updated`.
|
|
3585
|
+
properties:
|
|
3586
|
+
when:
|
|
3587
|
+
type: string
|
|
3588
|
+
description: |
|
|
3589
|
+
Condition that gates this mapping — either an operation gate on a
|
|
3590
|
+
composite (create-or-update) import or the action to take when the
|
|
3591
|
+
extract returns no value. Empty means null, undefined or an empty
|
|
3592
|
+
string; `0`, `false` and whitespace are values.
|
|
3593
|
+
x-celigo-ai-guidance:
|
|
3594
|
+
- |-
|
|
3595
|
+
`fail_record_when_empty` is the fourth "Action to take if source field
|
|
3596
|
+
has no value" and is mutually exclusive with the other three: send it
|
|
3597
|
+
with no `default` key. A `default`, a `lookupName` or a `hardCodedValue`
|
|
3598
|
+
on the same row — or a `default` on a `buildArrayHelper` entry — is
|
|
3599
|
+
rejected at save with `[unsupported_mapping] "<key>" and conditional.when
|
|
3600
|
+
"fail_record_when_empty" cannot be present in mapping simultaneously.`
|
|
3601
|
+
(the lookup variant adds `Use lookup "allowFailures" instead.`);
|
|
3602
|
+
lookups fail through `allowFailures: false`, and a hard-coded row
|
|
3603
|
+
always has a value. At runtime an empty extract fails the record with
|
|
3604
|
+
an `errors[]` entry `{code: "extract_empty", fatal: true, source:
|
|
3605
|
+
"mapping", message: "<generate>: Source field has no value"}`
|
|
3606
|
+
("Input field has no value" in a Transformation 2.0); `0` and `false`
|
|
3607
|
+
are values and map through.
|
|
3608
|
+
enum:
|
|
3609
|
+
- record_created
|
|
3610
|
+
- record_updated
|
|
3611
|
+
- extract_not_empty
|
|
3612
|
+
- fail_record_when_empty
|
|
3613
|
+
x-enumDescriptions:
|
|
3614
|
+
record_created: Apply this mapping only when creating a new record
|
|
3615
|
+
record_updated: Apply this mapping only when updating an existing record
|
|
3616
|
+
extract_not_empty: Apply this mapping only when the extract field returns a non-empty value
|
|
3617
|
+
fail_record_when_empty: Fail the record when the extract field returns no value
|
|
3618
|
+
examples:
|
|
3619
|
+
- record_created
|
|
3620
|
+
- record_updated
|
|
3621
|
+
- extract_not_empty
|
|
3622
|
+
- fail_record_when_empty
|
|
2599
3623
|
required:
|
|
2600
3624
|
- dataType
|
|
3625
|
+
if:
|
|
3626
|
+
properties:
|
|
3627
|
+
conditional:
|
|
3628
|
+
properties:
|
|
3629
|
+
when:
|
|
3630
|
+
const: fail_record_when_empty
|
|
3631
|
+
required:
|
|
3632
|
+
- when
|
|
3633
|
+
required:
|
|
3634
|
+
- conditional
|
|
3635
|
+
then:
|
|
3636
|
+
not:
|
|
3637
|
+
anyOf:
|
|
3638
|
+
- required:
|
|
3639
|
+
- default
|
|
3640
|
+
- required:
|
|
3641
|
+
- lookupName
|
|
3642
|
+
- required:
|
|
3643
|
+
- hardCodedValue
|
|
3644
|
+
Mappings:
|
|
3645
|
+
type: array
|
|
3646
|
+
description: |
|
|
3647
|
+
Array of field mapping configurations for transforming data from one format into another.
|
|
3648
|
+
|
|
3649
|
+
**Guidance**
|
|
3650
|
+
|
|
3651
|
+
This schema is designed around RECURSION as its core architectural principle. Understanding this recursive
|
|
3652
|
+
nature is essential for building effective mappings:
|
|
3653
|
+
|
|
3654
|
+
1. The schema is self-referential by design - a mapping can contain nested mappings of the same structure
|
|
3655
|
+
2. Complex data structures (nested objects and arrays of objects, to any depth) are ALL
|
|
3656
|
+
handled through this recursive pattern; an array of arrays is not (build one in a script hook)
|
|
3657
|
+
3. Each mapping handles one level of the data structure; deeper levels are handled by nested mappings
|
|
3658
|
+
|
|
3659
|
+
When generating mappings programmatically:
|
|
3660
|
+
- For simple fields (string, number, boolean): Create single mapping objects
|
|
3661
|
+
- For objects: Create a parent mapping with nested 'mappings' array containing child field mappings
|
|
3662
|
+
- For arrays: Use 'buildArrayHelper' with extract paths defining array inputs and
|
|
3663
|
+
recursive 'mappings' to define object structures
|
|
3664
|
+
|
|
3665
|
+
The system will process these nested structures recursively during runtime, ensuring proper construction
|
|
3666
|
+
of complex hierarchical data while maintaining excellent performance.
|
|
3667
|
+
|
|
3668
|
+
On save, a leaf row with neither a source (`extract`, `hardCodedValue`, `lookupName`) nor a
|
|
3669
|
+
destination (`generate`) is dropped silently, at every nesting level, and so is an object or
|
|
3670
|
+
object-array row left with no source, no destination and no remaining child `mappings` or
|
|
3671
|
+
`buildArrayHelper` entries; a row with only one of the two, and a source-less, destination-less
|
|
3672
|
+
wrapper that still has children, are kept.
|
|
3673
|
+
|
|
3674
|
+
The shape of the array is the mapper's **JSON structure**. Named top-level items produce an object
|
|
3675
|
+
record (`record { }`). Exactly one top-level item with `dataType: objectarray` and no `generate` is
|
|
3676
|
+
the `rows [ ]` structure: the mapped record is an array — usually one element per element of the
|
|
3677
|
+
source array that root's `buildArrayHelper` iterates — Handlebars templates such as `http.body`
|
|
3678
|
+
bind it as `rows` instead of `record`, and the mapping editor shows that row's destination disabled.
|
|
3679
|
+
x-celigo-ai-guidance:
|
|
3680
|
+
- |-
|
|
3681
|
+
Rows that exist in the saved document — including `Draft` and `Inactive` rows and
|
|
3682
|
+
rows with only a source or only a destination — are the user's state: an edit that
|
|
3683
|
+
re-sends the tree must carry them through unchanged unless the user asked to change
|
|
3684
|
+
them. Only a row with neither source nor destination — and, for an object or
|
|
3685
|
+
object-array row, no remaining children — can be left out; the save would drop it
|
|
3686
|
+
anyway. A wrapper with children but no `generate` is kept by the save, so keep it.
|
|
3687
|
+
- |-
|
|
3688
|
+
A single unnamed top-level `objectarray` item is the `rows [ ]` JSON structure, not a
|
|
3689
|
+
missing destination: keep it unnamed when editing (naming it turns the output into an
|
|
3690
|
+
object, and a template that iterates `rows` then renders nothing), and author that
|
|
3691
|
+
shape only when the request body must be an array or a template iterates `rows`.
|
|
3692
|
+
The editor's save check accepts the unnamed root only in the `rows [ ]` structure;
|
|
3693
|
+
any other row with a source and no `generate` fails with "One or more destination
|
|
3694
|
+
field values not entered".
|
|
3695
|
+
items:
|
|
3696
|
+
type: object
|
|
3697
|
+
properties:
|
|
3698
|
+
generate:
|
|
3699
|
+
type: string
|
|
3700
|
+
description: |
|
|
3701
|
+
**Purpose**
|
|
3702
|
+
Defines the target field name in the output object/record.
|
|
3703
|
+
|
|
3704
|
+
**Guidance**
|
|
3705
|
+
This is the PRIMARY FIELD that identifies the output property being created:
|
|
3706
|
+
|
|
3707
|
+
- For regular fields: Set to the exact property name (e.g., "firstName", "price", "isActive")
|
|
3708
|
+
- For object fields: Set to the object property name, then add child mappings in the 'mappings' array
|
|
3709
|
+
- For array fields: Set to the array property name, then configure 'buildArrayHelper'
|
|
3710
|
+
- One structural blank: the single top-level `objectarray` item of a `rows [ ]` mapping (the
|
|
3711
|
+
array output structure — see the array's description). A child-bearing wrapper and a source-only row that
|
|
3712
|
+
already exist in a saved document also stay unnamed when the tree is re-sent — filling in a
|
|
3713
|
+
name changes the output; it does not complete the row
|
|
3714
|
+
|
|
3715
|
+
IMPORTANT: Do NOT use dot notation (e.g., "customer.firstName") in this field. Instead, create proper
|
|
3716
|
+
hierarchical structure with nested mappings:
|
|
3717
|
+
```json
|
|
3718
|
+
{
|
|
3719
|
+
"generate": "customer",
|
|
3720
|
+
"dataType": "object",
|
|
3721
|
+
"status": "Active",
|
|
3722
|
+
"mappings": [
|
|
3723
|
+
{"generate": "firstName", "dataType": "string", "extract": "$.name.first", "status": "Active"}
|
|
3724
|
+
]
|
|
3725
|
+
}
|
|
3726
|
+
```
|
|
3727
|
+
|
|
3728
|
+
When parsing existing mappings, an empty `generate` on a row inside an `arrayarray` row's
|
|
3729
|
+
`buildArrayHelper` entry is that row's inner array (`arrayarray` fails at run time; see
|
|
3730
|
+
`dataType`); other unnamed rows are the wrappers and source-only rows described above; an
|
|
3731
|
+
empty `generate` on the ONLY top-level item, with `dataType: objectarray`, is the `rows [ ]` JSON
|
|
3732
|
+
structure — array output, bound as `rows` in templates — and is intentional, not a missing name.
|
|
3733
|
+
examples:
|
|
3734
|
+
- name
|
|
3735
|
+
- address
|
|
3736
|
+
- items
|
|
3737
|
+
dataType:
|
|
3738
|
+
type: string
|
|
3739
|
+
description: |
|
|
3740
|
+
**Purpose**
|
|
3741
|
+
Explicitly declares the data type of the output field, controlling how data is processed and structured.
|
|
3742
|
+
|
|
3743
|
+
**Guidance**
|
|
3744
|
+
This is a REQUIRED field that fundamentally determines mapping behavior:
|
|
3745
|
+
|
|
3746
|
+
**Simple Types (direct value mapping)**
|
|
3747
|
+
- `string`: Text values, converts other types to string representation
|
|
3748
|
+
- `number`: Numeric values. Converts a numeric string (`"24"` → `24`,
|
|
3749
|
+
`"007"` → `7`) and leaves the field out for an empty string; a value
|
|
3750
|
+
holding letters or a thousands separator (`"1,250.00"`) fails the
|
|
3751
|
+
record with `non_parsable_string` (`<generate>: String contains alpha
|
|
3752
|
+
characters`)
|
|
3753
|
+
- `boolean`: True/false values, converts truthy/falsy values
|
|
3754
|
+
|
|
3755
|
+
Dates are represented as strings — use `string` for date fields and
|
|
3756
|
+
drive the parsing/formatting through the `extractDateFormat` /
|
|
3757
|
+
`generateDateFormat` / `extractDateTimezone` / `generateDateTimezone`
|
|
3758
|
+
fields. There is no separate `date` enum value.
|
|
3759
|
+
|
|
3760
|
+
**Complex Types (require additional configuration)**
|
|
3761
|
+
- `object`: Creates a nested object from child mappings in the 'mappings' array, or
|
|
3762
|
+
copies a whole object with `extract` (one or the other, not both)
|
|
3763
|
+
|
|
3764
|
+
**Array Types**
|
|
3765
|
+
- `stringarray`: Array of strings
|
|
3766
|
+
- `numberarray`: Array of numbers
|
|
3767
|
+
- `booleanarray`: Array of booleans
|
|
3768
|
+
- `objectarray`: Array of objects (most common array type)
|
|
3769
|
+
|
|
3770
|
+
`arrayarray` is not a type the mapper recognizes: a save accepts it, but every record
|
|
3771
|
+
then fails with `Destination datatype is a required field.` Build an array of arrays
|
|
3772
|
+
in a script hook instead.
|
|
3773
|
+
|
|
3774
|
+
Array dataTypes are populated two ways: construct or iterate through
|
|
3775
|
+
`buildArrayHelper` entries, or set a constant with `hardCodedValue`. The
|
|
3776
|
+
row's own `extract` is never read on an array type: a primitive-array row
|
|
3777
|
+
that has only an `extract` (JSONPath, Handlebars or a literal) yields
|
|
3778
|
+
nothing, with no error, and an `objectarray` row without `buildArrayHelper`
|
|
3779
|
+
or `hardCodedValue` is refused with 422 ("buildArrayHelper" or
|
|
3780
|
+
"hardCodedValue" must be present for object array datatype.). To copy a
|
|
3781
|
+
source array through unchanged, use one entry that iterates it
|
|
3782
|
+
(`buildArrayHelper: [{"extract": "$.items[*]"}]`).
|
|
3783
|
+
|
|
3784
|
+
IMPORTANT: The dataType controls which additional fields are relevant:
|
|
3785
|
+
- For date-like string fields: extractDateFormat, generateDateFormat, etc. become relevant
|
|
3786
|
+
- For object types: 'mappings' array becomes relevant
|
|
3787
|
+
- For array types: `buildArrayHelper` or `hardCodedValue` (see above)
|
|
3788
|
+
|
|
3789
|
+
When analyzing existing mappings or generating new ones, always check dataType first
|
|
3790
|
+
to understand what additional fields should be present.
|
|
3791
|
+
x-celigo-ai-guidance:
|
|
3792
|
+
- |-
|
|
3793
|
+
Missing `dataType` is rejected at save with validation error
|
|
3794
|
+
`[mandatory_destination_datatype] Destination datatype is a
|
|
3795
|
+
required field.`
|
|
3796
|
+
- |-
|
|
3797
|
+
Give each row the type the destination field expects; `"string"` is
|
|
3798
|
+
not a safe default. It accepts any source value, but sends a numeric
|
|
3799
|
+
source as text (`"24"`), which a destination that checks JSON types
|
|
3800
|
+
refuses. Map numeric destination fields as `number`, which fails a
|
|
3801
|
+
record (`non_parsable_string`) only when the value holds letters or a
|
|
3802
|
+
thousands separator.
|
|
3803
|
+
enum:
|
|
3804
|
+
- string
|
|
3805
|
+
- number
|
|
3806
|
+
- boolean
|
|
3807
|
+
- object
|
|
3808
|
+
- stringarray
|
|
3809
|
+
- numberarray
|
|
3810
|
+
- booleanarray
|
|
3811
|
+
- objectarray
|
|
3812
|
+
x-enumDescriptions:
|
|
3813
|
+
string: Text values; converts other types to their string representation.
|
|
3814
|
+
number: Numeric values; converts numeric strings, and fails the record (`non_parsable_string`) on letters or a thousands separator.
|
|
3815
|
+
boolean: True/false values; converts truthy/falsy values.
|
|
3816
|
+
object: Nested object built from child `mappings`, or copied whole with `extract` (not both).
|
|
3817
|
+
stringarray: Array of string values.
|
|
3818
|
+
numberarray: Array of numeric values.
|
|
3819
|
+
booleanarray: Array of boolean values.
|
|
3820
|
+
objectarray: Array of objects, the most common array type.
|
|
3821
|
+
examples:
|
|
3822
|
+
- string
|
|
3823
|
+
- number
|
|
3824
|
+
- object
|
|
3825
|
+
- objectarray
|
|
3826
|
+
extract:
|
|
3827
|
+
type: string
|
|
3828
|
+
description: |
|
|
3829
|
+
**Purpose**
|
|
3830
|
+
Defines how to retrieve data from the input record to populate the output field.
|
|
3831
|
+
|
|
3832
|
+
**Guidance**
|
|
3833
|
+
This field supports THREE DISTINCT PATTERNS that are easily distinguished:
|
|
3834
|
+
|
|
3835
|
+
**1. json Path Syntax**
|
|
3836
|
+
- MUST start with '$' — the record root. An object record is addressed as
|
|
3837
|
+
'$.field'; a grouped (array) record as '$[0].field' / '$[*].field'
|
|
3838
|
+
- Used for precisely targeting data in structured JSON objects
|
|
3839
|
+
- Examples: '$.customer.firstName', '$.items[0].price', '$.addresses[*].street',
|
|
3840
|
+
'$[*].Tax' (every row of a grouped record)
|
|
3841
|
+
- Wildcards like [*] extract multiple values/objects
|
|
3842
|
+
- A key that contains a dot needs bracket notation: `$['P.O. Number']` (or
|
|
3843
|
+
`$["P.O. Number"]`, `$.[P.O. Number]`). `$.P.O. Number` is read as a nested
|
|
3844
|
+
path: it maps nothing and the record still succeeds. Spaces, hyphens and `#`
|
|
3845
|
+
need no brackets (`$.Ship To Name`, `$.Tracking #`)
|
|
3846
|
+
- Filter expressions such as `$.items[?(@.active)]` fail the record with
|
|
3847
|
+
"Eval [?(expr)] prevented in JSONPath expression."
|
|
3848
|
+
|
|
3849
|
+
```json
|
|
3850
|
+
"extract": "$.customer.addresses[*]" // Extracts all addresses
|
|
3851
|
+
```
|
|
3852
|
+
|
|
3853
|
+
**2. Handlebars Template Syntax**
|
|
3854
|
+
- Contains '{{' and '}}' pattern
|
|
3855
|
+
- Evaluated by the AFE 2.0 handlebars template engine
|
|
3856
|
+
- Can include logic, formatting, and computation
|
|
3857
|
+
- Access input record fields with {{record.fieldName}} notation; a grouped
|
|
3858
|
+
(array) record binds as `rows` instead — {{rows.0.fieldName}} / {{#each rows}}
|
|
3859
|
+
- Examples: "{{record.firstName}} {{record.lastName}}", "{{#if record.isActive}}Active{{else}}Inactive{{/if}}"
|
|
3860
|
+
- Valid on scalars and on `object` rows, where the rendered output must
|
|
3861
|
+
parse into an object. On an array row the template goes in a
|
|
3862
|
+
`buildArrayHelper` entry instead: on an `objectarray` row's own
|
|
3863
|
+
`extract` it is refused with 422 ("buildArrayHelper" or "hardCodedValue"
|
|
3864
|
+
must be present for object array datatype.), and on a primitive-array
|
|
3865
|
+
row's own `extract` it yields nothing (the field is left out) without an
|
|
3866
|
+
error
|
|
3867
|
+
|
|
3868
|
+
```json
|
|
3869
|
+
"extract": "{{record.price}} {{record.currency}}" // Combines two fields
|
|
3870
|
+
```
|
|
3871
|
+
|
|
3872
|
+
**3. Hard-Coded Value (literal string)**
|
|
3873
|
+
- Does NOT start with '$'
|
|
3874
|
+
- Does NOT contain handlebars '{{' syntax
|
|
3875
|
+
- System treats it as a literal string value
|
|
3876
|
+
- VERY COMMON for setting static/constant values
|
|
3877
|
+
- Examples: "Active", "USD", "Completed", "true"
|
|
3878
|
+
|
|
3879
|
+
```json
|
|
3880
|
+
"extract": "primary" // Sets field value to the literal string "primary"
|
|
3881
|
+
"extract": "true" // Sets field value to the literal string "true"
|
|
3882
|
+
"extract": "N/A" // Sets field value to the literal string "N/A"
|
|
3883
|
+
```
|
|
3884
|
+
|
|
3885
|
+
This third pattern is the simplest and most efficient way to set hard-coded values in your mappings.
|
|
3886
|
+
AI agents should use this pattern whenever a field needs a static value that doesn't come from
|
|
3887
|
+
the input record or require computation.
|
|
3888
|
+
|
|
3889
|
+
**Important implementation details**
|
|
3890
|
+
|
|
3891
|
+
- JSON path patterns ALWAYS execute from the TOP-LEVEL root of the input record
|
|
3892
|
+
- The system maintains this context even in deeply nested mappings
|
|
3893
|
+
- For object mappings without child mappings, extract should return a complete object
|
|
3894
|
+
- An `object` row takes `extract` (to copy a whole object) or child `mappings`, not
|
|
3895
|
+
both: a row with both fails with 422 (`"extract" should not be present if
|
|
3896
|
+
"mappings" field is present`). A `buildArrayHelper` entry is different: there
|
|
3897
|
+
`extract` and `mappings` work together.
|
|
3898
|
+
- The root is the record as it arrives: an object record roots at `$.field`; a
|
|
3899
|
+
grouped record (an array of rows — grouped exports, file key columns, NetSuite
|
|
3900
|
+
grouped saved searches) roots at the array, so its rows are addressed as
|
|
3901
|
+
`$[0].field` (one row) or `$[*].field` (every row). A root that contradicts the
|
|
3902
|
+
record's shape resolves to nothing without an error.
|
|
3903
|
+
|
|
3904
|
+
For most simple field-to-field mappings, prefer JSON path syntax for its clarity and performance.
|
|
3905
|
+
For hard-coded values, simply use the literal string as the extract value.
|
|
3906
|
+
x-celigo-ai-guidance:
|
|
3907
|
+
- |-
|
|
3908
|
+
## GROUPED (ARRAY) RECORDS
|
|
3909
|
+
Decide the JSONPath root from the record's shape before writing
|
|
3910
|
+
any extract. When the record is an array of rows, `$.field`,
|
|
3911
|
+
`$.properties.field` and `$.rows[*].field` all resolve to
|
|
3912
|
+
nothing — the processor still reports success and the request
|
|
3913
|
+
body ships as `{}`. Address rows as `$[0].field` (that row's
|
|
3914
|
+
value, typed) or `$[*].field` (every row: joined with commas
|
|
3915
|
+
into a `string` destination; rejected with
|
|
3916
|
+
`incompatible_destination_conversion` into a `number`
|
|
3917
|
+
destination). Column labels with spaces work as
|
|
3918
|
+
`$[*][Order Number]`, `$[*].[Order Number]`, or
|
|
3919
|
+
`$[*]['Order Number']`. For one destination element per row
|
|
3920
|
+
the two array kinds take different helper forms: a primitive
|
|
3921
|
+
array (`stringarray` / `numberarray`) uses `buildArrayHelper:
|
|
3922
|
+
[{"extract": "$[*].field"}]`; an `objectarray` uses
|
|
3923
|
+
`buildArrayHelper: [{"extract": "$[*]", "mappings": [...]}]`
|
|
3924
|
+
with the children addressing the row relatively (`$.field`,
|
|
3925
|
+
`{{rows.field}}`). An `extract` placed directly on the
|
|
3926
|
+
array-typed field yields nothing. Handlebars
|
|
3927
|
+
extracts bind the array record as `rows` (`{{rows.0.field}}`),
|
|
3928
|
+
an object record as `record`. The reverse holds too: `$[*]` on
|
|
3929
|
+
an object record iterates the object's values, not rows.
|
|
3930
|
+
- |-
|
|
3931
|
+
## SIZE LIMIT
|
|
3932
|
+
The platform's import save validator caps this field at **1024
|
|
3933
|
+
characters**. Saves with a longer `extract` are rejected
|
|
3934
|
+
with `[size_limit_exceeded] The maximum size of the field:
|
|
3935
|
+
mappings.<index>.extract in the Import document should be
|
|
3936
|
+
1024 characters`. This typically only matters for
|
|
3937
|
+
Handlebars templates that build complex strings inline -- if
|
|
3938
|
+
a template is approaching the cap, prefer one of:
|
|
3939
|
+
|
|
3940
|
+
- **Decompose into nested mappings** (set `dataType:
|
|
3941
|
+
"object"` and use child `mappings` -- each child gets
|
|
3942
|
+
its own 1024-char budget).
|
|
3943
|
+
- **Move the logic to a `preMap` hook** so the heavy
|
|
3944
|
+
transformation runs in script and the mapping just reads
|
|
3945
|
+
`record.<computed>`.
|
|
3946
|
+
- **Use a lookup** (`lookupName` + a small `lookups` entry)
|
|
3947
|
+
for value translation that would otherwise need a long
|
|
3948
|
+
`{{#if ...}}{{else if ...}}` chain.
|
|
3949
|
+
examples:
|
|
3950
|
+
- $.fullName
|
|
3951
|
+
- '{{record.fullName}}'
|
|
3952
|
+
- primary
|
|
3953
|
+
- $.lineItems[*].unitPrice
|
|
3954
|
+
extractDateFormat:
|
|
3955
|
+
type: string
|
|
3956
|
+
description: |
|
|
3957
|
+
Specifies the format pattern of the input date string to ensure proper parsing.
|
|
3958
|
+
|
|
3959
|
+
Used on string-typed mappings whose `extract` yields a date. Uses
|
|
3960
|
+
Moment.js-compatible formatting tokens to describe how the incoming date
|
|
3961
|
+
string is structured.
|
|
3962
|
+
examples:
|
|
3963
|
+
- YYYY-MM-DD
|
|
3964
|
+
- MM/DD/YYYY
|
|
3965
|
+
- DD-MMM-YYYY HH:mm:ss
|
|
3966
|
+
extractDateTimezone:
|
|
3967
|
+
type: string
|
|
3968
|
+
description: |
|
|
3969
|
+
Specifies the timezone of the input date string using Olson/IANA timezone identifiers.
|
|
3970
|
+
|
|
3971
|
+
Used on string-typed mappings whose `extract` yields a date; tells the system
|
|
3972
|
+
how to interpret timestamp values from the input system.
|
|
3973
|
+
examples:
|
|
3974
|
+
- UTC
|
|
3975
|
+
- America/New_York
|
|
3976
|
+
- Europe/London
|
|
3977
|
+
generateDateFormat:
|
|
3978
|
+
type: string
|
|
3979
|
+
description: |
|
|
3980
|
+
Specifies the output format pattern when generating a date string or converting
|
|
3981
|
+
from a Date type to String type.
|
|
3982
|
+
|
|
3983
|
+
Uses Moment.js-compatible formatting tokens to define the structure of the resulting
|
|
3984
|
+
date string.
|
|
3985
|
+
examples:
|
|
3986
|
+
- YYYY-MM-DD
|
|
3987
|
+
- MM/DD/YYYY
|
|
3988
|
+
- DD-MMM-YYYY HH:mm:ss
|
|
3989
|
+
generateDateTimezone:
|
|
3990
|
+
type: string
|
|
3991
|
+
description: |
|
|
3992
|
+
Specifies the timezone to apply when generating or converting timestamp values
|
|
3993
|
+
using Olson/IANA timezone identifiers.
|
|
3994
|
+
|
|
3995
|
+
Controls timezone conversion when producing date output.
|
|
3996
|
+
examples:
|
|
3997
|
+
- UTC
|
|
3998
|
+
- America/New_York
|
|
3999
|
+
- Europe/London
|
|
4000
|
+
default:
|
|
4001
|
+
type:
|
|
4002
|
+
- string
|
|
4003
|
+
- 'null'
|
|
4004
|
+
description: |
|
|
4005
|
+
Specifies a fallback value to use when extract returns empty/null or when conditional
|
|
4006
|
+
logic fails and no other mapping supplies a value.
|
|
4007
|
+
|
|
4008
|
+
Explicit JSON `null` is itself a valid fallback: the destination field is written as
|
|
4009
|
+
JSON null when the extract yields nothing (the Mapper UI's "Use null as default value"
|
|
4010
|
+
action). Omitting the key entirely means no fallback — the field is left out of the
|
|
4011
|
+
output when the extract is missing or an empty string (the UI's "Do nothing" action),
|
|
4012
|
+
while a null source is still written as null unless `conditional.when` is
|
|
4013
|
+
`extract_not_empty`. Failing the record instead is `conditional.when:
|
|
4014
|
+
fail_record_when_empty`, which excludes a default.
|
|
4015
|
+
x-celigo-ai-guidance:
|
|
4016
|
+
- |-
|
|
4017
|
+
`"default": null` and `"default": ""` are distinct saved values, not
|
|
4018
|
+
absent keys: null renders the destination field as JSON null and the
|
|
4019
|
+
empty string renders it as `""` when the extract yields nothing.
|
|
4020
|
+
Preserve them verbatim when editing or migrating a mapping — dropping
|
|
4021
|
+
the key changes runtime behavior from "use null/empty string as
|
|
4022
|
+
default value" to "do nothing" (a missing or `""` source is left out
|
|
4023
|
+
of the output, while a null source is written as null unless
|
|
4024
|
+
`conditional.when` is `extract_not_empty`).
|
|
4025
|
+
- |-
|
|
4026
|
+
The four "Action to take if source field has no value" choices map to:
|
|
4027
|
+
do nothing → no `default` key (add `conditional.when:
|
|
4028
|
+
extract_not_empty` to leave a null source out too; without it a null
|
|
4029
|
+
source is written as null); use null → `"default": null`; use empty string or
|
|
4030
|
+
a custom value → `"default": "<value>"`; cause the record to fail →
|
|
4031
|
+
`conditional.when: fail_record_when_empty` with no `default` key.
|
|
4032
|
+
examples:
|
|
4033
|
+
- N/A
|
|
4034
|
+
- '0'
|
|
4035
|
+
- 'false'
|
|
4036
|
+
lookupName:
|
|
4037
|
+
type: string
|
|
4038
|
+
description: |
|
|
4039
|
+
**Purpose**
|
|
4040
|
+
References a lookup table for transforming values during the mapping process.
|
|
4041
|
+
|
|
4042
|
+
**Usage**
|
|
4043
|
+
|
|
4044
|
+
The lookupName refers to a named lookup defined in the lookups array of the same resource.
|
|
4045
|
+
On an HTTP import that is `http.lookups`: a `lookups` array sent only at the top level
|
|
4046
|
+
is dropped on save. On an import, a name that matches no lookup fails every record
|
|
4047
|
+
with "Unable to find lookup in mapping configs - <name>", and a key the lookup
|
|
4048
|
+
doesn't hold follows the lookup's `allowFailures`: false fails the record; true, or
|
|
4049
|
+
the field left out, lets the record succeed with the lookup's `default`, or without
|
|
4050
|
+
the mapped field when there is none.
|
|
4051
|
+
|
|
4052
|
+
```json
|
|
4053
|
+
{
|
|
4054
|
+
"generate": "countryName",
|
|
4055
|
+
"dataType": "string",
|
|
4056
|
+
"extract": "$.countryCode",
|
|
4057
|
+
"lookupName": "countryCodeToName"
|
|
4058
|
+
}
|
|
4059
|
+
```
|
|
4060
|
+
|
|
4061
|
+
During processing, the system:
|
|
4062
|
+
1. Extracts the value from the input record (e.g., "US")
|
|
4063
|
+
2. Finds the lookup table with the specified name
|
|
4064
|
+
3. Uses the extracted value as a key in the lookup
|
|
4065
|
+
4. Returns the corresponding value (e.g., "United States")
|
|
4066
|
+
|
|
4067
|
+
**Benefits**
|
|
4068
|
+
|
|
4069
|
+
- **Standardization**: Ensures consistent value translation across mappings
|
|
4070
|
+
- **Centralization**: Define translations once and reference them in multiple places
|
|
4071
|
+
- **Maintainability**: Update all mappings by changing the lookup definition
|
|
4072
|
+
- **Readability**: Makes mappings more descriptive and self-documenting
|
|
4073
|
+
|
|
4074
|
+
The specific lookup capabilities depend on the context where mappings are used.
|
|
4075
|
+
examples:
|
|
4076
|
+
- countryCodeToName
|
|
4077
|
+
- statusMapping
|
|
4078
|
+
- departmentCodes
|
|
4079
|
+
hardCodedValue:
|
|
4080
|
+
type:
|
|
4081
|
+
- string
|
|
4082
|
+
- 'null'
|
|
4083
|
+
description: |
|
|
4084
|
+
Constant written to the destination instead of an extracted value. On a primitive
|
|
4085
|
+
array (`stringarray`, `numberarray`, `booleanarray`) the string is split on commas,
|
|
4086
|
+
verbatim and untrimmed, into elements of the array's type (`"A,B"` gives `["A", "B"]`).
|
|
4087
|
+
On an `object` it must be a JSON object string and on an `objectarray` a JSON array
|
|
4088
|
+
string (an object string becomes one element); the save parses it and refuses non-JSON
|
|
4089
|
+
or the wrong shape with 422, and an array row with a constant needs no `buildArrayHelper`.
|
|
4090
|
+
JSON `null` writes the destination field as null; it is what the mapper saves for its
|
|
4091
|
+
hard-coded "Use null as default value" choice.
|
|
4092
|
+
examples:
|
|
4093
|
+
- USD
|
|
4094
|
+
- A,B
|
|
4095
|
+
- '[{"code": "A"}, {"code": "B"}]'
|
|
4096
|
+
description:
|
|
4097
|
+
type: string
|
|
4098
|
+
description: |
|
|
4099
|
+
Optional free-text annotation that appears in the Mapper sidebar to provide context about
|
|
4100
|
+
the mapping's purpose for collaboration and documentation.
|
|
4101
|
+
|
|
4102
|
+
Has no functional impact on the mapping behavior.
|
|
4103
|
+
examples:
|
|
4104
|
+
- Maps customer name
|
|
4105
|
+
- Converts price to target currency
|
|
4106
|
+
- Formats date for target system
|
|
4107
|
+
sourceDataType:
|
|
4108
|
+
type: string
|
|
4109
|
+
description: |
|
|
4110
|
+
Declares the JSON type of the value produced by `extract`, before any
|
|
4111
|
+
conversion to `dataType`. Same enum as `dataType`. Set on leaf mappings
|
|
4112
|
+
only — parent mappings (with child `mappings` or `buildArrayHelper`)
|
|
4113
|
+
have no extracted value of their own; the children carry their own
|
|
4114
|
+
`sourceDataType`.
|
|
4115
|
+
|
|
4116
|
+
For date fields use `string` (JSON represents dates as strings); the
|
|
4117
|
+
parsing/formatting lives in `extractDateFormat` / `generateDateFormat` /
|
|
4118
|
+
`extractDateTimezone` / `generateDateTimezone`.
|
|
4119
|
+
enum:
|
|
4120
|
+
- string
|
|
4121
|
+
- number
|
|
4122
|
+
- boolean
|
|
4123
|
+
- object
|
|
4124
|
+
- stringarray
|
|
4125
|
+
- numberarray
|
|
4126
|
+
- booleanarray
|
|
4127
|
+
- objectarray
|
|
4128
|
+
- arrayarray
|
|
4129
|
+
x-enumDescriptions:
|
|
4130
|
+
string: Source value is a text string.
|
|
4131
|
+
number: Source value is numeric.
|
|
4132
|
+
boolean: Source value is true or false.
|
|
4133
|
+
object: Source value is a JSON object.
|
|
4134
|
+
stringarray: Source value is an array of strings.
|
|
4135
|
+
numberarray: Source value is an array of numbers.
|
|
4136
|
+
booleanarray: Source value is an array of booleans.
|
|
4137
|
+
objectarray: Source value is an array of objects.
|
|
4138
|
+
arrayarray: Source value is an array of arrays.
|
|
4139
|
+
examples:
|
|
4140
|
+
- string
|
|
4141
|
+
- number
|
|
4142
|
+
- boolean
|
|
4143
|
+
- object
|
|
4144
|
+
mappings:
|
|
4145
|
+
type: array
|
|
4146
|
+
description: |
|
|
4147
|
+
**Purpose**
|
|
4148
|
+
Enables recursive definition of nested object structures through child mapping objects.
|
|
4149
|
+
|
|
4150
|
+
**Guidance**
|
|
4151
|
+
This is the KEY FIELD that implements the recursive pattern at the core of this schema:
|
|
4152
|
+
|
|
4153
|
+
**When to Use**
|
|
4154
|
+
- REQUIRED when dataType = "object" (unless you are copying an entire object from the input record)
|
|
4155
|
+
- REQUIRED in buildArrayHelper.mappings when defining complex object array elements
|
|
4156
|
+
- NEVER used with simple types (string, number, boolean)
|
|
4157
|
+
|
|
4158
|
+
**Behavior**
|
|
4159
|
+
- Each mapping in this array becomes a property of the parent object
|
|
4160
|
+
- The full Mappings schema is repeated recursively at each level
|
|
4161
|
+
- Can be nested to any depth for complex hierarchical structures
|
|
4162
|
+
|
|
4163
|
+
**Context Handling**
|
|
4164
|
+
- Each level of nesting changes the mapping CONTEXT for 'generate'
|
|
4165
|
+
- The extraction CONTEXT always remains the original input record
|
|
4166
|
+
- This means child mappings can pull data from anywhere in the input record
|
|
4167
|
+
|
|
4168
|
+
**Common Patterns**
|
|
4169
|
+
|
|
4170
|
+
**Nested Objects**
|
|
4171
|
+
```json
|
|
4172
|
+
{
|
|
4173
|
+
"generate": "customer",
|
|
4174
|
+
"dataType": "object",
|
|
4175
|
+
"mappings": [
|
|
4176
|
+
{
|
|
4177
|
+
"generate": "contact",
|
|
4178
|
+
"dataType": "object",
|
|
4179
|
+
"mappings": [
|
|
4180
|
+
{"generate": "email", "dataType": "string", "extract": "$.customerEmail"}
|
|
4181
|
+
]
|
|
4182
|
+
}
|
|
4183
|
+
]
|
|
4184
|
+
}
|
|
4185
|
+
```
|
|
4186
|
+
|
|
4187
|
+
**Multiple Fields in Object**
|
|
4188
|
+
```json
|
|
4189
|
+
{
|
|
4190
|
+
"generate": "address",
|
|
4191
|
+
"dataType": "object",
|
|
4192
|
+
"mappings": [
|
|
4193
|
+
{"generate": "street", "dataType": "string", "extract": "$.address.line1"},
|
|
4194
|
+
{"generate": "city", "dataType": "string", "extract": "$.address.city"},
|
|
4195
|
+
{"generate": "country", "dataType": "string", "extract": "$.address.country"}
|
|
4196
|
+
]
|
|
4197
|
+
}
|
|
4198
|
+
```
|
|
4199
|
+
|
|
4200
|
+
IMPORTANT: When analyzing or generating mappings, ALWAYS check if parent.dataType = "object"
|
|
4201
|
+
or if you're inside buildArrayHelper.mappings for objectarray elements. These are the only
|
|
4202
|
+
valid contexts for the mappings array.
|
|
4203
|
+
items:
|
|
4204
|
+
$ref: '#/components/schemas/items'
|
|
4205
|
+
examples:
|
|
4206
|
+
- - generate: firstName
|
|
4207
|
+
extract: $.name.first
|
|
4208
|
+
dataType: string
|
|
4209
|
+
status: Active
|
|
4210
|
+
- generate: lastName
|
|
4211
|
+
extract: $.name.last
|
|
4212
|
+
dataType: string
|
|
4213
|
+
status: Active
|
|
4214
|
+
buildArrayHelper:
|
|
4215
|
+
type: array
|
|
4216
|
+
x-celigo-ai-guidance:
|
|
4217
|
+
- |-
|
|
4218
|
+
Entry-level `extract` accepts an iterating array path
|
|
4219
|
+
(`$.items[*]`), `"$"` (the record root), or omission — a
|
|
4220
|
+
constructed entry (child `mappings` with the extract omitted or
|
|
4221
|
+
`"$"`; the two spellings are equivalent) contributes exactly one
|
|
4222
|
+
element, and entries append in order. On a grouped (array)
|
|
4223
|
+
record the record itself is the array to iterate: `"$[*]"`
|
|
4224
|
+
yields one `objectarray` element per row (children address the
|
|
4225
|
+
row as `$.field`), and `"$[*].field"` yields one primitive-array
|
|
4226
|
+
value per row. Indexed or comma-joined
|
|
4227
|
+
entry extracts (`"$[0]"`, `"$[0],$[0]"`) are not valid: the
|
|
4228
|
+
processor renders the entire destination array as null with no
|
|
4229
|
+
validation error. To emit a fixed number of static elements, add
|
|
4230
|
+
that many sibling constructed entries — never index the extract.
|
|
4231
|
+
- |-
|
|
4232
|
+
An entry's `extract` can be a Handlebars template. On an
|
|
4233
|
+
`objectarray` it must render a JSON object (one element) or a JSON
|
|
4234
|
+
array (one element per item). On a primitive array each entry
|
|
4235
|
+
renders one element, so a serialized array becomes one string
|
|
4236
|
+
element. A bare literal entry extract is refused with 422 ("extract
|
|
4237
|
+
only supports json path or handlebars expression"); set a constant
|
|
4238
|
+
with the row's `hardCodedValue` instead.
|
|
4239
|
+
description: |
|
|
4240
|
+
**Purpose**
|
|
4241
|
+
Configures how to construct arrays in the output record, handling various array types and inputs.
|
|
4242
|
+
|
|
4243
|
+
**Guidance**
|
|
4244
|
+
This is the mechanism for building array data types:
|
|
4245
|
+
|
|
4246
|
+
**When to Use**
|
|
4247
|
+
- REQUIRED when dataType ends with "array" (stringarray, objectarray, etc.), unless the
|
|
4248
|
+
row sets `hardCodedValue`: an array row's own `extract` is never read (see `dataType`)
|
|
4249
|
+
- Each entry in this array contributes elements to the output array
|
|
4250
|
+
- Multiple entries allow combining data from different input arrays
|
|
4251
|
+
|
|
4252
|
+
**Array Type Handling**
|
|
4253
|
+
|
|
4254
|
+
**For Simple Arrays (stringarray, numberarray, booleanarray)**
|
|
4255
|
+
- Only the 'extract' field is used to pull values
|
|
4256
|
+
- JSON path with wildcards (e.g., $.items[*].name) returns multiple values;
|
|
4257
|
+
on a grouped (array) record the record itself is the array, so the
|
|
4258
|
+
path roots at it ($[*].name — one value per row)
|
|
4259
|
+
- Each result is converted to the appropriate primitive type
|
|
4260
|
+
```json
|
|
4261
|
+
{
|
|
4262
|
+
"generate": "productNames",
|
|
4263
|
+
"dataType": "stringarray",
|
|
4264
|
+
"buildArrayHelper": [
|
|
4265
|
+
{"extract": "$.products[*].name"}
|
|
4266
|
+
]
|
|
4267
|
+
}
|
|
4268
|
+
```
|
|
4269
|
+
|
|
4270
|
+
**For Object Arrays (objectarray) - three patterns**
|
|
4271
|
+
|
|
4272
|
+
1. Extract Only (existing objects):
|
|
4273
|
+
```json
|
|
4274
|
+
{
|
|
4275
|
+
"generate": "contacts",
|
|
4276
|
+
"dataType": "objectarray",
|
|
4277
|
+
"buildArrayHelper": [
|
|
4278
|
+
{"extract": "$.account.primaryContacts[*]"}, // Pull primary contact objects
|
|
4279
|
+
{"extract": "$.account.secondaryContacts[*]"}, // Pull secondary contact objects
|
|
4280
|
+
{"extract": "$.vendor.contactPersons[*]"}, // Pull vendor contact objects
|
|
4281
|
+
{"extract": "$.subsidiaries[*].mainContact"} // Pull main contact from each subsidiary
|
|
4282
|
+
]
|
|
4283
|
+
}
|
|
4284
|
+
```
|
|
4285
|
+
|
|
4286
|
+
2. Mappings Only (constructed object):
|
|
4287
|
+
```json
|
|
4288
|
+
{
|
|
4289
|
+
"generate": "contactInfo",
|
|
4290
|
+
"dataType": "objectarray",
|
|
4291
|
+
"buildArrayHelper": [
|
|
4292
|
+
{
|
|
4293
|
+
"mappings": [ // Creates one object in the array
|
|
4294
|
+
{"generate": "type", "dataType": "string", "extract": "primary"},
|
|
4295
|
+
{"generate": "email", "dataType": "string", "extract": "$.primaryEmail"}
|
|
4296
|
+
]
|
|
4297
|
+
},
|
|
4298
|
+
{
|
|
4299
|
+
"mappings": [ // Creates another object in the array
|
|
4300
|
+
{"generate": "type", "dataType": "string", "extract": "secondary"},
|
|
4301
|
+
{"generate": "email", "dataType": "string", "extract": "$.secondaryEmail"}
|
|
4302
|
+
]
|
|
4303
|
+
}
|
|
4304
|
+
]
|
|
4305
|
+
}
|
|
4306
|
+
```
|
|
4307
|
+
Each constructed entry contributes exactly one element, in entry
|
|
4308
|
+
order; writing the entry with `"extract": "$"` is equivalent to
|
|
4309
|
+
omitting the extract (both anchor the element at the record root).
|
|
4310
|
+
A fixed number of static elements is built from that many sibling
|
|
4311
|
+
constructed entries.
|
|
4312
|
+
|
|
4313
|
+
3. Extract AND Mappings (transform input arrays):
|
|
4314
|
+
```json
|
|
4315
|
+
{
|
|
4316
|
+
"generate": "lineItems",
|
|
4317
|
+
"dataType": "objectarray",
|
|
4318
|
+
"buildArrayHelper": [
|
|
4319
|
+
{
|
|
4320
|
+
"extract": "$.order.items[*]", // For each item in the array
|
|
4321
|
+
"mappings": [ // Transform to this structure using the composite object
|
|
4322
|
+
{"generate": "sku", "dataType": "string", "extract": "$.order.items.productId"}, // Notice: items is singular
|
|
4323
|
+
{"generate": "quantity", "dataType": "number", "extract": "$.order.items.qty"}, // Notice: items is singular
|
|
4324
|
+
{"generate": "orderNumber", "dataType": "string", "extract": "$.order.id"}, // Access parent data
|
|
4325
|
+
{"generate": "customerName", "dataType": "string", "extract": "$.customerName"} // Access root data
|
|
4326
|
+
]
|
|
4327
|
+
}
|
|
4328
|
+
]
|
|
4329
|
+
}
|
|
4330
|
+
```
|
|
4331
|
+
|
|
4332
|
+
**Arrays of Arrays**
|
|
4333
|
+
- The mapper has no working type for them: `arrayarray` saves, but every record
|
|
4334
|
+
fails with `Destination datatype is a required field.` Build an array of arrays
|
|
4335
|
+
in a script hook instead.
|
|
4336
|
+
|
|
4337
|
+
**Important details**
|
|
4338
|
+
|
|
4339
|
+
- When both extract and mappings are provided, the system creates special composite objects
|
|
4340
|
+
that maintain hierarchical context during processing
|
|
4341
|
+
- This enables accessing both the current array element AND its parent context
|
|
4342
|
+
- An ITERATING entry's extract MUST be a JSON path that iterates an array:
|
|
4343
|
+
'$.items[*]' when the array is a field of an object record, or '$[*]'
|
|
4344
|
+
(objectarray) / '$[*].field' (primitive arrays) when the record itself is a
|
|
4345
|
+
grouped array of rows. A CONSTRUCTED entry (child mappings building one
|
|
4346
|
+
element) instead omits extract or sets it to exactly "$" — never rewrite "$"
|
|
4347
|
+
into an indexed or comma-joined form ('$[0]', '$[0],$[0]'): those render the
|
|
4348
|
+
entire destination array as null without raising a validation error
|
|
4349
|
+
- Each array helper entry acts independently, potentially adding multiple elements
|
|
4350
|
+
|
|
4351
|
+
The buildArrayHelper is the most complex part of the mappings system - always analyze the
|
|
4352
|
+
dataType first to understand which pattern is appropriate.
|
|
4353
|
+
items:
|
|
4354
|
+
type: object
|
|
4355
|
+
properties:
|
|
4356
|
+
extract:
|
|
4357
|
+
type: string
|
|
4358
|
+
description: |
|
|
4359
|
+
JSON path expression that identifies the input array or values to extract.
|
|
4360
|
+
|
|
4361
|
+
For objectarray with mappings, this defines which input objects to iterate through.
|
|
4362
|
+
The JSON path must return either a single object or an array of objects.
|
|
4363
|
+
|
|
4364
|
+
For a CONSTRUCTED entry (child mappings building exactly one element from
|
|
4365
|
+
record-root fields and constants), omit this field or set it to exactly "$" —
|
|
4366
|
+
the two spellings are equivalent. Indexed or comma-joined forms ('$[0]',
|
|
4367
|
+
'$[0],$[0]') are not valid at the entry level: the processor renders the
|
|
4368
|
+
entire destination array as null without raising a validation error.
|
|
4369
|
+
|
|
4370
|
+
The system creates special composite objects during processing to maintain
|
|
4371
|
+
hierarchical relationships, allowing easy access to both the current array item
|
|
4372
|
+
and its parent contexts.
|
|
4373
|
+
|
|
4374
|
+
An iterating entry keeps the `[*]`: `$.line_items` without it yields one empty
|
|
4375
|
+
element per item, with no error. Child extracts drop the `[*]` but keep the
|
|
4376
|
+
array's path (`$.line_items.sku`); `$.line_items[*].sku` maps nothing, and an
|
|
4377
|
+
element-relative `$.sku` reads the record root instead of the element.
|
|
4378
|
+
examples:
|
|
4379
|
+
- $.items[*]
|
|
4380
|
+
- $.order.lineItems[*]
|
|
4381
|
+
- $.parents[*].children[*]
|
|
4382
|
+
- $
|
|
4383
|
+
name:
|
|
4384
|
+
type: string
|
|
4385
|
+
maxLength: 200
|
|
4386
|
+
description: |
|
|
4387
|
+
Display label for this source object in the mapper, so the sources of
|
|
4388
|
+
an object array can be told apart instead of all showing as `$`.
|
|
4389
|
+
Has no effect at runtime; stored only when non-empty.
|
|
4390
|
+
x-celigo-ai-guidance:
|
|
4391
|
+
- |-
|
|
4392
|
+
Carry an existing `name` through every edit — it is the user's label
|
|
4393
|
+
for the tab, and an entry sent without it loses the label. Duplicate
|
|
4394
|
+
names across entries are allowed. Set one only when the user names
|
|
4395
|
+
the source object; never invent labels.
|
|
4396
|
+
examples:
|
|
4397
|
+
- Billing address
|
|
4398
|
+
- Shipping address
|
|
4399
|
+
sourceDataType:
|
|
4400
|
+
type: string
|
|
4401
|
+
description: |
|
|
4402
|
+
Declares the JSON type of the input array being iterated, to ensure
|
|
4403
|
+
proper type handling during array construction. Same enum as `dataType`.
|
|
4404
|
+
enum:
|
|
4405
|
+
- string
|
|
4406
|
+
- number
|
|
4407
|
+
- boolean
|
|
4408
|
+
- object
|
|
4409
|
+
- stringarray
|
|
4410
|
+
- numberarray
|
|
4411
|
+
- booleanarray
|
|
4412
|
+
- objectarray
|
|
4413
|
+
- arrayarray
|
|
4414
|
+
x-enumDescriptions:
|
|
4415
|
+
string: Input array contains string elements.
|
|
4416
|
+
number: Input array contains numeric elements.
|
|
4417
|
+
boolean: Input array contains boolean elements.
|
|
4418
|
+
object: Input array contains object elements.
|
|
4419
|
+
stringarray: Input array contains arrays of strings.
|
|
4420
|
+
numberarray: Input array contains arrays of numbers.
|
|
4421
|
+
booleanarray: Input array contains arrays of booleans.
|
|
4422
|
+
objectarray: Input array contains arrays of objects.
|
|
4423
|
+
arrayarray: Input array contains arrays of arrays.
|
|
4424
|
+
examples:
|
|
4425
|
+
- string
|
|
4426
|
+
- number
|
|
4427
|
+
- boolean
|
|
4428
|
+
- object
|
|
4429
|
+
default:
|
|
4430
|
+
type:
|
|
4431
|
+
- string
|
|
4432
|
+
- 'null'
|
|
4433
|
+
description: |
|
|
4434
|
+
Specifies a fallback value when the extracted array element is empty or
|
|
4435
|
+
not found in the input data.
|
|
4436
|
+
|
|
4437
|
+
Explicit JSON `null` is itself a valid fallback (the element is written as
|
|
4438
|
+
JSON null); omitting the key means no fallback is applied.
|
|
4439
|
+
examples:
|
|
4440
|
+
- N/A
|
|
4441
|
+
- '0'
|
|
4442
|
+
- 'false'
|
|
4443
|
+
conditional:
|
|
4444
|
+
type: object
|
|
4445
|
+
description: |
|
|
4446
|
+
Defines conditional rules for including each array element in the result.
|
|
4447
|
+
x-celigo-ai-guidance:
|
|
4448
|
+
- |-
|
|
4449
|
+
Judged against this entry's own `extract` (the array source). The
|
|
4450
|
+
design scopes the UI's tab-level "Action to take if source field has
|
|
4451
|
+
no value" to copy-as-is tabs (no child `mappings`); the API accepts
|
|
4452
|
+
`fail_record_when_empty` on a mapped entry as well, and the mapper
|
|
4453
|
+
processor honors it there — the record fails when that array is
|
|
4454
|
+
missing or empty (`errors[]` entry `code: extract_empty`, `fatal:
|
|
4455
|
+
true`, message `<generate>: Source field has no value`; probed
|
|
4456
|
+
2026-10-09). Say so when writing it on a mapped entry: the user may
|
|
4457
|
+
not find the setting in the mapper's tab. To fail on an empty field
|
|
4458
|
+
inside each element, set the action on that child mapping instead.
|
|
4459
|
+
properties:
|
|
4460
|
+
when:
|
|
4461
|
+
type: string
|
|
4462
|
+
description: |
|
|
4463
|
+
Condition judged on the entry's extract — skip the elements the
|
|
4464
|
+
extract does not return, or fail the whole record when the source
|
|
4465
|
+
array is missing or empty.
|
|
4466
|
+
enum:
|
|
4467
|
+
- extract_not_empty
|
|
4468
|
+
- fail_record_when_empty
|
|
4469
|
+
x-enumDescriptions:
|
|
4470
|
+
extract_not_empty: Include an array element only when the extract returns a non-empty value for it
|
|
4471
|
+
fail_record_when_empty: Fail the record when the entry's source array is missing or empty
|
|
4472
|
+
examples:
|
|
4473
|
+
- extract_not_empty
|
|
4474
|
+
mappings:
|
|
4475
|
+
type: array
|
|
4476
|
+
description: |
|
|
4477
|
+
Contains recursive mapping definitions for complex array element transformations.
|
|
4478
|
+
|
|
4479
|
+
**Composite object mechanism**
|
|
4480
|
+
|
|
4481
|
+
When both 'extract' and 'mappings' are used together, the system implements a sophisticated
|
|
4482
|
+
"composite object" approach that is crucial for AI agents to understand:
|
|
4483
|
+
|
|
4484
|
+
1. The system starts with the complete input record
|
|
4485
|
+
|
|
4486
|
+
2. For each array element matched by the extract path, it creates a modified version of
|
|
4487
|
+
the input record where:
|
|
4488
|
+
- Array paths in the extract JSON path are REPLACED with single objects
|
|
4489
|
+
- Each array ([]) in the path is converted to a single object ({})
|
|
4490
|
+
- This preserves the hierarchical relationship between nested arrays
|
|
4491
|
+
|
|
4492
|
+
**Example**
|
|
4493
|
+
|
|
4494
|
+
Given an input record:
|
|
4495
|
+
```json
|
|
4496
|
+
{
|
|
4497
|
+
"customer": {
|
|
4498
|
+
"name": "John Doe",
|
|
4499
|
+
"orders": [
|
|
4500
|
+
{
|
|
4501
|
+
"id": "O-001",
|
|
4502
|
+
"items": [
|
|
4503
|
+
{"sku": "ABC", "qty": 2},
|
|
4504
|
+
{"sku": "XYZ", "qty": 1}
|
|
4505
|
+
]
|
|
4506
|
+
},
|
|
4507
|
+
{
|
|
4508
|
+
"id": "O-002",
|
|
4509
|
+
"items": [
|
|
4510
|
+
{"sku": "DEF", "qty": 3}
|
|
4511
|
+
]
|
|
4512
|
+
}
|
|
4513
|
+
]
|
|
4514
|
+
}
|
|
4515
|
+
}
|
|
4516
|
+
```
|
|
4517
|
+
|
|
4518
|
+
With extract path: `$.customer.orders[*].items[*]`
|
|
4519
|
+
|
|
4520
|
+
For each item, the system creates a composite object like:
|
|
4521
|
+
```json
|
|
4522
|
+
{
|
|
4523
|
+
"customer": {
|
|
4524
|
+
"name": "John Doe",
|
|
4525
|
+
"orders": { // Note: Array replaced with single object
|
|
4526
|
+
"id": "O-001",
|
|
4527
|
+
"items": { // Note: Array replaced with single object
|
|
4528
|
+
"sku": "ABC",
|
|
4529
|
+
"qty": 2
|
|
4530
|
+
}
|
|
4531
|
+
}
|
|
4532
|
+
}
|
|
4533
|
+
}
|
|
4534
|
+
```
|
|
4535
|
+
|
|
4536
|
+
Then in your mappings, you can access:
|
|
4537
|
+
- The current item: `$.customer.orders.items.sku`
|
|
4538
|
+
- The parent order: `$.customer.orders.id`
|
|
4539
|
+
- Top-level data: `$.customer.name`
|
|
4540
|
+
|
|
4541
|
+
This approach allows for precise mapping from deeply nested structures while maintaining
|
|
4542
|
+
access to all contextual parent data, without requiring complex array index management.
|
|
4543
|
+
|
|
4544
|
+
**Implementation guidance**
|
|
4545
|
+
|
|
4546
|
+
When implementing the composite object mechanism:
|
|
4547
|
+
|
|
4548
|
+
1. Analyze the extract path to identify all array patterns (`[*]` or `[number]`)
|
|
4549
|
+
2. For each array in the path, understand that it will be replaced with a single object
|
|
4550
|
+
3. In the mappings, use paths that reference these arrays as if they were objects
|
|
4551
|
+
4. Remember that every mapping still has access to the full input record context
|
|
4552
|
+
5. This mechanism is especially powerful when mapping hierarchical data like:
|
|
4553
|
+
- Order → Line Items → Taxes/Discounts
|
|
4554
|
+
- Customer → Addresses → Address Lines
|
|
4555
|
+
- Invoice → Line Items → Serial Numbers
|
|
4556
|
+
|
|
4557
|
+
The extract path effectively tells the system "iterate through these arrays",
|
|
4558
|
+
while the composite object mechanism ensures you can still access both the
|
|
4559
|
+
current array item AND its parent context during mapping.
|
|
4560
|
+
items:
|
|
4561
|
+
$ref: '#/components/schemas/items'
|
|
4562
|
+
examples:
|
|
4563
|
+
- - generate: itemName
|
|
4564
|
+
extract: $.name
|
|
4565
|
+
dataType: string
|
|
4566
|
+
status: Active
|
|
4567
|
+
- generate: itemPrice
|
|
4568
|
+
extract: $.price
|
|
4569
|
+
dataType: number
|
|
4570
|
+
status: Active
|
|
4571
|
+
if:
|
|
4572
|
+
properties:
|
|
4573
|
+
conditional:
|
|
4574
|
+
properties:
|
|
4575
|
+
when:
|
|
4576
|
+
const: fail_record_when_empty
|
|
4577
|
+
required:
|
|
4578
|
+
- when
|
|
4579
|
+
required:
|
|
4580
|
+
- conditional
|
|
4581
|
+
then:
|
|
4582
|
+
not:
|
|
4583
|
+
required:
|
|
4584
|
+
- default
|
|
4585
|
+
status:
|
|
4586
|
+
type: string
|
|
4587
|
+
description: |
|
|
4588
|
+
**Purpose**
|
|
4589
|
+
Controls whether the mapping is applied. Send it on every mapping entry.
|
|
4590
|
+
|
|
4591
|
+
**Guidance**
|
|
4592
|
+
Only `Active` rows run. `Draft` and `Inactive` rows keep their
|
|
4593
|
+
configuration, are saved with minimal validation, and are skipped at
|
|
4594
|
+
runtime and in preview; a non-Active parent skips its whole subtree
|
|
4595
|
+
whatever its children say. Imports (on save and in the mapper processor)
|
|
4596
|
+
and API response mappings reject a row missing this field (validation
|
|
4597
|
+
error: "Mapping object must have status field present."); a Tool's
|
|
4598
|
+
output mapping saves and runs one, which is why `required` doesn't
|
|
4599
|
+
list it.
|
|
4600
|
+
x-celigo-ai-guidance:
|
|
4601
|
+
- |-
|
|
4602
|
+
Emit `"Active"` for mappings that should run; `"Draft"` is also
|
|
4603
|
+
accepted and saves the mapping while bypassing the Active-only
|
|
4604
|
+
field validations. The value is case-sensitive. The API rejects:
|
|
4605
|
+
- Missing field: `[status_field_absent] Mapping object must have status field present.`
|
|
4606
|
+
- Wrong case (e.g. `"active"`): `[invalid_status_enums] active is not a valid enum for status field.`
|
|
4607
|
+
- |-
|
|
4608
|
+
`"Inactive"` is the user's "Set inactive" on a row: use it only when
|
|
4609
|
+
asked to disable or park a row, never to mean incomplete (that is
|
|
4610
|
+
`"Draft"`). Setting a parent `Inactive` means no `Active` row may
|
|
4611
|
+
remain under it — the save rejects an `Active` row under an
|
|
4612
|
+
`Inactive` parent (`[inactive_parent_active_child]` on `mappings`,
|
|
4613
|
+
no message text) and never cascades or promotes on its own; `Draft`
|
|
4614
|
+
descendants are kept as they are, and a `Draft` parent does not gate
|
|
4615
|
+
its children. The UI's Set inactive on a parent marks the parent and
|
|
4616
|
+
every child `Inactive`. Re-enabling a child
|
|
4617
|
+
means re-enabling its ancestors in the same payload. Edits that keep
|
|
4618
|
+
existing rows must carry their stored status forward — rewriting a
|
|
4619
|
+
`Draft` or `Inactive` row to `Active` turns a row the user parked
|
|
4620
|
+
back on.
|
|
4621
|
+
enum:
|
|
4622
|
+
- Active
|
|
4623
|
+
- Draft
|
|
4624
|
+
- Inactive
|
|
4625
|
+
x-enumDescriptions:
|
|
4626
|
+
Active: The mapping is enabled and applied during processing
|
|
4627
|
+
Draft: In-progress mapping; saved without the Active-only field validations and skipped at runtime
|
|
4628
|
+
Inactive: Disabled by the user; configuration kept, skipped at runtime and in preview
|
|
4629
|
+
examples:
|
|
4630
|
+
- Active
|
|
4631
|
+
conditional:
|
|
4632
|
+
type: object
|
|
4633
|
+
description: |
|
|
4634
|
+
**Purpose**
|
|
4635
|
+
Defines conditional processing rules for the entire mapping.
|
|
4636
|
+
|
|
4637
|
+
**Guidance**
|
|
4638
|
+
These conditions determine whether the mapping is applied based on record
|
|
4639
|
+
state or field content:
|
|
4640
|
+
|
|
4641
|
+
**When to Use**
|
|
4642
|
+
- When a mapping should only be applied in specific circumstances
|
|
4643
|
+
- To implement conditional logic without using complex handlebars expressions
|
|
4644
|
+
- For creating mappings that only run during create or update operations
|
|
4645
|
+
|
|
4646
|
+
**Available Conditions**
|
|
4647
|
+
|
|
4648
|
+
- `record_created`: Apply only when creating a new record
|
|
4649
|
+
Useful for setting initial values that should not be overwritten during updates
|
|
4650
|
+
|
|
4651
|
+
- `record_updated`: Apply only when updating an existing record
|
|
4652
|
+
Useful for transformation logic that should only run during updates
|
|
4653
|
+
|
|
4654
|
+
- `extract_not_empty`: Apply only when the extract field returns a value
|
|
4655
|
+
Useful for conditional mapping based on input data availability
|
|
4656
|
+
|
|
4657
|
+
- `fail_record_when_empty`: Fail the record when the extract field returns
|
|
4658
|
+
no value (the UI's "Cause record to fail" action when the source field
|
|
4659
|
+
has no value)
|
|
4660
|
+
|
|
4661
|
+
**Example**
|
|
4662
|
+
```json
|
|
4663
|
+
{
|
|
4664
|
+
"generate": "statusMessage",
|
|
4665
|
+
"dataType": "string",
|
|
4666
|
+
"status": "Active",
|
|
4667
|
+
"extract": "$.status.message",
|
|
4668
|
+
"conditional": {
|
|
4669
|
+
"when": "extract_not_empty" // Only map when status.message exists
|
|
4670
|
+
}
|
|
4671
|
+
}
|
|
4672
|
+
```
|
|
4673
|
+
x-celigo-ai-guidance:
|
|
4674
|
+
- |-
|
|
4675
|
+
`when` holds one value, and two different settings share it: the
|
|
4676
|
+
composite-import operation gate (`record_created` / `record_updated`,
|
|
4677
|
+
the UI's "Only perform mapping when") and the empty-source action
|
|
4678
|
+
(`extract_not_empty` / `fail_record_when_empty`, the UI's "Action to
|
|
4679
|
+
take if source field has no value"). A row cannot carry both — writing
|
|
4680
|
+
one replaces the other and the save succeeds, so a composite import
|
|
4681
|
+
row that needs both has to choose. Never author `fail_record_when_empty`
|
|
4682
|
+
on a row that already carries `record_created` or `record_updated`.
|
|
4683
|
+
properties:
|
|
4684
|
+
when:
|
|
4685
|
+
type: string
|
|
4686
|
+
description: |
|
|
4687
|
+
Condition that gates this mapping — either an operation gate on a
|
|
4688
|
+
composite (create-or-update) import or the action to take when the
|
|
4689
|
+
extract returns no value. Empty means null, undefined or an empty
|
|
4690
|
+
string; `0`, `false` and whitespace are values.
|
|
4691
|
+
x-celigo-ai-guidance:
|
|
4692
|
+
- |-
|
|
4693
|
+
`fail_record_when_empty` is the fourth "Action to take if source field
|
|
4694
|
+
has no value" and is mutually exclusive with the other three: send it
|
|
4695
|
+
with no `default` key. A `default`, a `lookupName` or a `hardCodedValue`
|
|
4696
|
+
on the same row — or a `default` on a `buildArrayHelper` entry — is
|
|
4697
|
+
rejected at save with `[unsupported_mapping] "<key>" and conditional.when
|
|
4698
|
+
"fail_record_when_empty" cannot be present in mapping simultaneously.`
|
|
4699
|
+
(the lookup variant adds `Use lookup "allowFailures" instead.`);
|
|
4700
|
+
lookups fail through `allowFailures: false`, and a hard-coded row
|
|
4701
|
+
always has a value. At runtime an empty extract fails the record with
|
|
4702
|
+
an `errors[]` entry `{code: "extract_empty", fatal: true, source:
|
|
4703
|
+
"mapping", message: "<generate>: Source field has no value"}`
|
|
4704
|
+
("Input field has no value" in a Transformation 2.0); `0` and `false`
|
|
4705
|
+
are values and map through.
|
|
4706
|
+
enum:
|
|
4707
|
+
- record_created
|
|
4708
|
+
- record_updated
|
|
4709
|
+
- extract_not_empty
|
|
4710
|
+
- fail_record_when_empty
|
|
4711
|
+
x-enumDescriptions:
|
|
4712
|
+
record_created: Apply this mapping only when creating a new record
|
|
4713
|
+
record_updated: Apply this mapping only when updating an existing record
|
|
4714
|
+
extract_not_empty: Apply this mapping only when the extract field returns a non-empty value
|
|
4715
|
+
fail_record_when_empty: Fail the record when the extract field returns no value
|
|
4716
|
+
examples:
|
|
4717
|
+
- record_created
|
|
4718
|
+
- record_updated
|
|
4719
|
+
- extract_not_empty
|
|
4720
|
+
- fail_record_when_empty
|
|
4721
|
+
required:
|
|
4722
|
+
- dataType
|
|
4723
|
+
if:
|
|
4724
|
+
properties:
|
|
4725
|
+
conditional:
|
|
4726
|
+
properties:
|
|
4727
|
+
when:
|
|
4728
|
+
const: fail_record_when_empty
|
|
4729
|
+
required:
|
|
4730
|
+
- when
|
|
4731
|
+
required:
|
|
4732
|
+
- conditional
|
|
4733
|
+
then:
|
|
4734
|
+
not:
|
|
4735
|
+
anyOf:
|
|
4736
|
+
- required:
|
|
4737
|
+
- default
|
|
4738
|
+
- required:
|
|
4739
|
+
- lookupName
|
|
4740
|
+
- required:
|
|
4741
|
+
- hardCodedValue
|
|
4742
|
+
Lookups:
|
|
4743
|
+
type: array
|
|
4744
|
+
description: |
|
|
4745
|
+
Configuration for value-to-value transformations using lookup tables.
|
|
4746
|
+
|
|
4747
|
+
**Purpose**
|
|
4748
|
+
|
|
4749
|
+
Lookups provide a way to translate values from one system to another. They transform
|
|
4750
|
+
input values into output values using either static mapping tables or
|
|
4751
|
+
dynamic lookup caches.
|
|
4752
|
+
|
|
4753
|
+
**Lookup mechanisms**
|
|
4754
|
+
|
|
4755
|
+
There are two distinct lookup mechanisms available:
|
|
4756
|
+
|
|
4757
|
+
1. **Static Lookups**: Define a simple key-value map object and store it as part of your resource
|
|
4758
|
+
- Best for: Small, fixed sets of values that rarely change
|
|
4759
|
+
- Implementation: Configure the `map` object with input-to-output value mappings
|
|
4760
|
+
- Example: Country codes, status values, simple translations
|
|
4761
|
+
|
|
4762
|
+
2. **Dynamic Lookups**: Reference an existing 'Lookup Cache' resource in your Celigo account
|
|
4763
|
+
- Best for: Large datasets, frequently changing values, or complex reference data
|
|
4764
|
+
- Implementation: Configure `_lookupCacheId` to reference cached data maintained independently
|
|
4765
|
+
- Example: Product catalogs, customer databases, pricing information
|
|
4766
|
+
|
|
4767
|
+
**Property usage**
|
|
4768
|
+
|
|
4769
|
+
There are two mutually exclusive ways to configure lookups, depending on which mechanism you choose:
|
|
4770
|
+
|
|
4771
|
+
1. **For Static Mappings**: Configure the `map` property with a direct key-value object
|
|
4772
|
+
```json
|
|
4773
|
+
"map": {"US": "United States", "CA": "Canada"}
|
|
4774
|
+
```
|
|
4775
|
+
|
|
4776
|
+
2. **For Dynamic Lookups**: Configure the following properties:
|
|
4777
|
+
- `_lookupCacheId`: Reference to the lookup cache resource
|
|
4778
|
+
- `extract`: JSON path to extract specific value from the returned lookup object
|
|
4779
|
+
|
|
4780
|
+
**When to use**
|
|
4781
|
+
|
|
4782
|
+
Lookups are ideal for:
|
|
4783
|
+
|
|
4784
|
+
1. **Value Translation**: Mapping codes or IDs to human-readable values
|
|
4785
|
+
|
|
4786
|
+
2. **Data Enrichment**: Adding related information to records during processing
|
|
4787
|
+
|
|
4788
|
+
3. **Normalization**: Ensuring consistent formatting of values across systems
|
|
4789
|
+
|
|
4790
|
+
**Implementation details**
|
|
4791
|
+
|
|
4792
|
+
Lookups can be referenced in:
|
|
4793
|
+
|
|
4794
|
+
1. **Field Mappings**: Direct use in field transformation configurations
|
|
4795
|
+
|
|
4796
|
+
2. **Handlebars Templates**: Use within templates with the syntax:
|
|
4797
|
+
```
|
|
4798
|
+
{{lookup 'lookupName' record.fieldName}}
|
|
4799
|
+
```
|
|
4800
|
+
|
|
4801
|
+
**Example usage**
|
|
4802
|
+
|
|
4803
|
+
```json
|
|
4804
|
+
"lookups": [
|
|
4805
|
+
{
|
|
4806
|
+
"name": "countryCodeToName",
|
|
4807
|
+
"map": {
|
|
4808
|
+
"US": "United States",
|
|
4809
|
+
"CA": "Canada",
|
|
4810
|
+
"UK": "United Kingdom"
|
|
4811
|
+
},
|
|
4812
|
+
"default": "Unknown Country",
|
|
4813
|
+
"allowFailures": true
|
|
4814
|
+
},
|
|
4815
|
+
{
|
|
4816
|
+
"name": "productDetails",
|
|
4817
|
+
"_lookupCacheId": "60a2c4e6f321d800129a1a3c",
|
|
4818
|
+
"extract": "$.details.price",
|
|
4819
|
+
"allowFailures": false
|
|
4820
|
+
}
|
|
4821
|
+
]
|
|
4822
|
+
```
|
|
4823
|
+
items:
|
|
4824
|
+
type: object
|
|
4825
|
+
properties:
|
|
4826
|
+
name:
|
|
4827
|
+
type: string
|
|
4828
|
+
description: |
|
|
4829
|
+
Unique identifier for the lookup table within this configuration.
|
|
4830
|
+
|
|
4831
|
+
This name must be unique within the scope where the lookup is defined and is used to reference
|
|
4832
|
+
the lookup in handlebars templates with the syntax {{lookup 'name' value}}.
|
|
4833
|
+
|
|
4834
|
+
Choose descriptive names that indicate the transformation purpose, such as:
|
|
4835
|
+
- "countryCodeToName" for country code to full name conversion
|
|
4836
|
+
- "statusMapping" for status code translations
|
|
4837
|
+
- "departmentCodes" for department code to name mapping
|
|
4838
|
+
examples:
|
|
4839
|
+
- countryCodeToName
|
|
4840
|
+
- statusMapping
|
|
4841
|
+
- departmentCodes
|
|
4842
|
+
map:
|
|
4843
|
+
type:
|
|
4844
|
+
- object
|
|
4845
|
+
- 'null'
|
|
4846
|
+
description: |
|
|
4847
|
+
The lookup mapping table as key-value pairs. The platform stores `null`
|
|
4848
|
+
here on dynamic lookups, which resolve values at runtime instead of
|
|
4849
|
+
from a static table.
|
|
4850
|
+
|
|
4851
|
+
This object contains the input values as keys and their corresponding
|
|
4852
|
+
output values. When a input value matches a key in this object,
|
|
4853
|
+
it will be replaced with the corresponding value.
|
|
4854
|
+
|
|
4855
|
+
The map should be kept to a reasonable size (typically under 100 entries)
|
|
4856
|
+
for optimal performance. For larger mapping requirements, consider using
|
|
4857
|
+
dynamic lookups instead.
|
|
4858
|
+
|
|
4859
|
+
Maps can include:
|
|
4860
|
+
- Simple code to name conversions: {"US": "United States"}
|
|
4861
|
+
- Status transformations: {"A": "Active", "I": "Inactive"}
|
|
4862
|
+
- ID to name mappings: {"100": "Marketing", "200": "Sales"}
|
|
4863
|
+
|
|
4864
|
+
Values can be strings, numbers, or booleans, but all are stored as strings
|
|
4865
|
+
in the configuration.
|
|
4866
|
+
examples:
|
|
4867
|
+
- US: United States
|
|
4868
|
+
UK: United Kingdom
|
|
4869
|
+
CA: Canada
|
|
4870
|
+
- A: Active
|
|
4871
|
+
I: Inactive
|
|
4872
|
+
P: Pending
|
|
4873
|
+
- 'true': 'Yes'
|
|
4874
|
+
'false': 'No'
|
|
4875
|
+
_lookupCacheId:
|
|
4876
|
+
type: string
|
|
4877
|
+
description: |
|
|
4878
|
+
Reference to a LookupCache resource that contains the reference data for the lookup.
|
|
4879
|
+
|
|
4880
|
+
**Purpose**
|
|
4881
|
+
|
|
4882
|
+
This field connects the lookup to an external data source that has been cached in the system.
|
|
4883
|
+
Unlike static lookups that use the `map` property, dynamic lookups can reference large datasets
|
|
4884
|
+
or frequently changing information without requiring constant updates to the integration.
|
|
4885
|
+
|
|
4886
|
+
**Implementation details**
|
|
4887
|
+
|
|
4888
|
+
The LookupCache resource referenced by this ID contains:
|
|
4889
|
+
- The data records to be used as a reference source
|
|
4890
|
+
- Configuration for how the data should be indexed and accessed
|
|
4891
|
+
- Caching parameters to balance performance with data freshness
|
|
4892
|
+
|
|
4893
|
+
**Usage patterns**
|
|
4894
|
+
|
|
4895
|
+
Commonly used to reference:
|
|
4896
|
+
- Product catalogs or SKU databases
|
|
4897
|
+
- Customer or account information
|
|
4898
|
+
- Pricing tables or discount rules
|
|
4899
|
+
- Complex business logic lookup tables
|
|
4900
|
+
|
|
4901
|
+
Format: 24-character hexadecimal string (MongoDB ObjectId)
|
|
4902
|
+
format: objectid
|
|
4903
|
+
x-celigo-refModel: lookupcaches
|
|
4904
|
+
examples:
|
|
4905
|
+
- 60a2c4e6f321d800129a1a3c
|
|
4906
|
+
- 5f8d43a1b9e5a80011a35f2c
|
|
4907
|
+
extract:
|
|
4908
|
+
type: string
|
|
4909
|
+
description: |
|
|
4910
|
+
JSON path expression that extracts a specific value from the cached lookup object.
|
|
4911
|
+
|
|
4912
|
+
**Purpose**
|
|
4913
|
+
|
|
4914
|
+
When using dynamic lookups with a LookupCache, this JSON path identifies which field to extract
|
|
4915
|
+
from the cached object after it has been retrieved using the lookup key.
|
|
4916
|
+
|
|
4917
|
+
**Implementation details**
|
|
4918
|
+
|
|
4919
|
+
- Must use JSON path syntax (similar to mapping extract fields)
|
|
4920
|
+
- Operates on the cached object returned by the lookup operation
|
|
4921
|
+
- Examples:
|
|
4922
|
+
- "$.name" - Extract the name field from the top level
|
|
4923
|
+
- "$.details.price" - Extract a nested price field
|
|
4924
|
+
- "$.attributes[0].value" - Extract a value from the first element of an array
|
|
4925
|
+
|
|
4926
|
+
**Usage scenario**
|
|
4927
|
+
|
|
4928
|
+
When a lookup cache contains complex objects:
|
|
4929
|
+
```json
|
|
4930
|
+
// Cache entry for key "PROD-123":
|
|
4931
|
+
{
|
|
4932
|
+
"id": "PROD-123",
|
|
4933
|
+
"name": "Premium Widget",
|
|
4934
|
+
"details": {
|
|
4935
|
+
"price": 99.99,
|
|
4936
|
+
"currency": "USD",
|
|
4937
|
+
"inStock": true
|
|
4938
|
+
}
|
|
4939
|
+
}
|
|
4940
|
+
```
|
|
4941
|
+
|
|
4942
|
+
Setting extract to "$.details.price" would return 99.99 as the lookup result.
|
|
4943
|
+
|
|
4944
|
+
If no extract is provided, the entire cached object is returned as the lookup result.
|
|
4945
|
+
examples:
|
|
4946
|
+
- $.name
|
|
4947
|
+
- $.details.price
|
|
4948
|
+
- $.attributes.color
|
|
4949
|
+
- $.category.name
|
|
4950
|
+
default:
|
|
4951
|
+
type:
|
|
4952
|
+
- string
|
|
4953
|
+
- 'null'
|
|
4954
|
+
description: |
|
|
4955
|
+
Default value to use when the source value is not found in the lookup map.
|
|
4956
|
+
The platform stores `null` here when no default is configured.
|
|
4957
|
+
|
|
4958
|
+
This value is used as a fallback when:
|
|
4959
|
+
1. The source value doesn't match any key in the map
|
|
4960
|
+
2. allowFailures is true or omitted
|
|
4961
|
+
|
|
4962
|
+
Setting an appropriate default helps prevent flow failures due to unexpected
|
|
4963
|
+
values and provides predictable behavior for edge cases.
|
|
4964
|
+
|
|
4965
|
+
Common default patterns include:
|
|
4966
|
+
- Descriptive unknowns: "Unknown Country", "Unspecified Status"
|
|
4967
|
+
- Original value indicators: "{Original Value}", "No mapping found"
|
|
4968
|
+
- Neutral values: "Other", "N/A", "Miscellaneous"
|
|
4969
|
+
|
|
4970
|
+
A save refuses a default together with an explicit `allowFailures: false`
|
|
4971
|
+
(422 `Lookups with default set can not have allowFailures explicitly set to
|
|
4972
|
+
false.`): a lookup either fails a miss (`allowFailures: false`, no default) or
|
|
4973
|
+
falls back to its default.
|
|
4974
|
+
examples:
|
|
4975
|
+
- Unknown
|
|
4976
|
+
- Other
|
|
4977
|
+
- N/A
|
|
4978
|
+
- Unmapped Value
|
|
4979
|
+
- '{Original Value}'
|
|
4980
|
+
x-celigo-ai-guidance:
|
|
4981
|
+
- 'Omit this field entirely when no fallback value is intended: a miss the lookup lets through then leaves the mapped field out, and `allowFailures: false` (which a save refuses alongside a default) fails it. An empty string is a value, not "no default" — the save accepts `default: ""`, and an allowed miss writes `""`.'
|
|
4982
|
+
- A default sends every unmapped value with no error, so add the missing key to the map when the destination needs the real value; keys match the extracted value exactly (case, spacing and suffixes count), and a save replaces the whole map.
|
|
4983
|
+
allowFailures:
|
|
4984
|
+
type:
|
|
4985
|
+
- boolean
|
|
4986
|
+
- 'null'
|
|
4987
|
+
description: |
|
|
4988
|
+
When true, missing lookup values will use the default value rather than causing an error.
|
|
4989
|
+
|
|
4990
|
+
**Behavior control**
|
|
4991
|
+
|
|
4992
|
+
This field determines how the system handles source values that don't exist in the map:
|
|
4993
|
+
|
|
4994
|
+
- true: Use the default value for missing mappings and continue processing
|
|
4995
|
+
- false: Treat missing mappings as errors, failing the record (`lookup_error` for a
|
|
4996
|
+
static map, `lookupcache_evaluation_failed` for a lookup cache)
|
|
4997
|
+
- omitted or null: the record doesn't fail either. On an import a static lookup writes
|
|
4998
|
+
its default if it has one, and a static or cache lookup without one leaves the
|
|
4999
|
+
mapped field out of the output, with no error
|
|
5000
|
+
|
|
5001
|
+
**Recommendation**
|
|
5002
|
+
|
|
5003
|
+
Set this to true when:
|
|
5004
|
+
- New source values might appear over time
|
|
5005
|
+
- Data quality issues could introduce unexpected values
|
|
5006
|
+
- Processing should continue even with imperfect mapping
|
|
5007
|
+
|
|
5008
|
+
Set this to false when:
|
|
5009
|
+
- Complete data accuracy is critical
|
|
5010
|
+
- All possible source values are known and controlled
|
|
5011
|
+
- Missing mappings indicate serious data problems that should be addressed
|
|
5012
|
+
|
|
5013
|
+
A default raises no error: records that miss go out with the default value and
|
|
5014
|
+
nothing reports them. Use true only when that fallback is acceptable at the
|
|
5015
|
+
destination, and set false explicitly when a missing value must stop the record.
|
|
5016
|
+
examples:
|
|
5017
|
+
- true
|
|
5018
|
+
- false
|
|
5019
|
+
x-celigo-ai-guidance:
|
|
5020
|
+
- 'Never leave this field out to mean "fail on a miss": on an import, an omitted or null value lets a missing key through without an error (with the default, or without the mapped field when there is none). Only an explicit false fails the record.'
|
|
5021
|
+
Transform:
|
|
5022
|
+
type: object
|
|
5023
|
+
description: |
|
|
5024
|
+
Configuration for transforming data during processing operations. This object enables
|
|
5025
|
+
reshaping of records.
|
|
5026
|
+
|
|
5027
|
+
**Transformation capabilities**
|
|
5028
|
+
|
|
5029
|
+
Celigo's transformation engine offers powerful features for data manipulation:
|
|
5030
|
+
- Precise field mapping with JSONPath expressions
|
|
5031
|
+
- Support for any level of nested arrays
|
|
5032
|
+
- Formula-based field value generation
|
|
5033
|
+
- Dynamic references to flow and integration settings
|
|
5034
|
+
|
|
5035
|
+
**Implementation approaches**
|
|
5036
|
+
|
|
5037
|
+
There are two distinct transformation mechanisms available:
|
|
5038
|
+
|
|
5039
|
+
**Rule-Based Transformation (`type: "expression"`)**
|
|
5040
|
+
- **Best For**: Most transformation scenarios from simple to complex
|
|
5041
|
+
- **Capabilities**: Field mapping, formula calculations, lookups, nested data handling
|
|
5042
|
+
- **Advantages**: Visual configuration, no coding required, intuitive interface
|
|
5043
|
+
- **Configuration**: Define rules in the `expression` object
|
|
5044
|
+
- **Use When**: You have clear mapping requirements or need to reshape data structure
|
|
5045
|
+
|
|
5046
|
+
**Script-Based Transformation (`type: "script"`)**
|
|
5047
|
+
- **Best For**: Extremely complex logic or proprietary algorithms
|
|
5048
|
+
- **Capabilities**: Full programmatic control, custom processing, complex business rules
|
|
5049
|
+
- **Advantages**: Maximum flexibility, can implement any transformation logic
|
|
5050
|
+
- **Configuration**: Reference a script in the `script` object
|
|
5051
|
+
- **Use When**: Visual transformation tools aren't sufficient for your use case
|
|
2601
5052
|
properties:
|
|
2602
|
-
|
|
2603
|
-
type: string
|
|
2604
|
-
description: Record field the row writes.
|
|
2605
|
-
examples:
|
|
2606
|
-
- customerId
|
|
2607
|
-
extract:
|
|
2608
|
-
type: string
|
|
2609
|
-
description: JSONPath into the request body that the value is read from.
|
|
2610
|
-
examples:
|
|
2611
|
-
- $.id
|
|
2612
|
-
dataType:
|
|
5053
|
+
type:
|
|
2613
5054
|
type: string
|
|
5055
|
+
description: |
|
|
5056
|
+
Determines which transformation mechanism to use. This choice affects which properties
|
|
5057
|
+
must be configured and how transformation logic is implemented.
|
|
5058
|
+
|
|
5059
|
+
**Available types**
|
|
5060
|
+
|
|
5061
|
+
**Rule-Based Transformation (`"expression"`)**
|
|
5062
|
+
- **Required Config**: The `expression` object with mapping definitions
|
|
5063
|
+
- **Behavior**: Applies declarative rules to reshape data
|
|
5064
|
+
- **Best For**: Most transformation scenarios from simple to complex
|
|
5065
|
+
- **Advantages**: Visual configuration, no coding required
|
|
5066
|
+
|
|
5067
|
+
**Script-Based Transformation (`"script"`)**
|
|
5068
|
+
- **Required Config**: The `script` object with _scriptId and function
|
|
5069
|
+
- **Behavior**: Executes custom JavaScript to transform data
|
|
5070
|
+
- **Best For**: Extremely complex logic or proprietary algorithms
|
|
5071
|
+
- **Advantages**: Maximum flexibility, can implement any logic
|
|
5072
|
+
|
|
5073
|
+
**Implementation guidance**
|
|
5074
|
+
|
|
5075
|
+
1. For standard data transformations, use `"expression"`
|
|
5076
|
+
2. For complex logic or specialized processing, use `"script"`
|
|
5077
|
+
3. When selecting a type, you must configure the corresponding object:
|
|
5078
|
+
- `type: "expression"` requires the `expression` object
|
|
5079
|
+
- `type: "script"` requires the `script` object
|
|
2614
5080
|
enum:
|
|
2615
|
-
-
|
|
2616
|
-
-
|
|
2617
|
-
- boolean
|
|
2618
|
-
- object
|
|
2619
|
-
- stringarray
|
|
2620
|
-
- numberarray
|
|
2621
|
-
- booleanarray
|
|
2622
|
-
- objectarray
|
|
5081
|
+
- expression
|
|
5082
|
+
- script
|
|
2623
5083
|
x-enumDescriptions:
|
|
2624
|
-
|
|
2625
|
-
|
|
2626
|
-
boolean: Single boolean value
|
|
2627
|
-
object: Nested object value
|
|
2628
|
-
stringarray: Array of strings
|
|
2629
|
-
numberarray: Array of numbers
|
|
2630
|
-
booleanarray: Array of booleans
|
|
2631
|
-
objectarray: Array of objects
|
|
2632
|
-
description: Data type the row writes.
|
|
2633
|
-
examples:
|
|
2634
|
-
- string
|
|
2635
|
-
sourceDataType:
|
|
2636
|
-
type: string
|
|
2637
|
-
description: Data type of the extracted value.
|
|
2638
|
-
examples:
|
|
2639
|
-
- string
|
|
2640
|
-
status:
|
|
2641
|
-
type: string
|
|
2642
|
-
description: Row status; `Active` rows run.
|
|
5084
|
+
expression: Rule-based transformation using declarative mapping definitions.
|
|
5085
|
+
script: Script-based transformation using custom JavaScript logic.
|
|
2643
5086
|
examples:
|
|
2644
|
-
-
|
|
2645
|
-
|
|
2646
|
-
|
|
2647
|
-
|
|
2648
|
-
|
|
2649
|
-
|
|
5087
|
+
- expression
|
|
5088
|
+
- script
|
|
5089
|
+
expression:
|
|
5090
|
+
type: object
|
|
5091
|
+
description: |
|
|
5092
|
+
Configuration for declarative rule-based transformations. This object enables reshaping data
|
|
5093
|
+
without requiring custom code.
|
|
5094
|
+
|
|
5095
|
+
**Usage context**
|
|
5096
|
+
|
|
5097
|
+
This object is REQUIRED when `transform.type` is set to "expression" and should not be
|
|
5098
|
+
configured otherwise. It provides a standardized way to define transformation rules that
|
|
5099
|
+
can map, modify, and generate data elements.
|
|
5100
|
+
|
|
5101
|
+
**Implementation guidance**
|
|
5102
|
+
|
|
5103
|
+
The expression system uses a rule-based approach where:
|
|
5104
|
+
- Field mappings define how input data is transformed to target fields
|
|
5105
|
+
- Formulas can be used to calculate or generate new values
|
|
5106
|
+
- Lookups can enrich data by fetching related information
|
|
5107
|
+
- Mode determines how records are processed (create new or modify existing)
|
|
5108
|
+
properties:
|
|
5109
|
+
version:
|
|
5110
|
+
type: string
|
|
5111
|
+
description: |
|
|
5112
|
+
Version of the expression format. Determines which rules
|
|
5113
|
+
property contains the transformation logic.
|
|
5114
|
+
enum:
|
|
5115
|
+
- '1'
|
|
5116
|
+
- '2'
|
|
5117
|
+
x-enumDescriptions:
|
|
5118
|
+
'1': Legacy format. Rules are in the `rules` array (array of arrays of extract/generate objects).
|
|
5119
|
+
'2': Current format. Rules are in the `rulesTwoDotZero` object with mode, mappings, and lookups.
|
|
5120
|
+
examples:
|
|
5121
|
+
- '1'
|
|
5122
|
+
- '2'
|
|
5123
|
+
rules:
|
|
5124
|
+
type: array
|
|
5125
|
+
description: |
|
|
5126
|
+
Transformation rules for version 1 expressions. An array of
|
|
5127
|
+
rule groups; each group is an array of field-mapping objects.
|
|
5128
|
+
Most transforms have a single group. Present when `version`
|
|
5129
|
+
is `"1"`. The output record contains ONLY the generated
|
|
5130
|
+
fields — every unmapped field is dropped (v1 has no
|
|
5131
|
+
equivalent of Transform 2.0's `modify` mode), and the
|
|
5132
|
+
record's trace key does not survive the rebuild.
|
|
5133
|
+
x-celigo-ai-guidance:
|
|
5134
|
+
- |-
|
|
5135
|
+
v1 rules REPLACE the record: a one-field rule group drops
|
|
5136
|
+
every other field, silently breaking downstream filters,
|
|
5137
|
+
router branch rules, and templates that referenced the
|
|
5138
|
+
dropped fields. Either map every field downstream logic
|
|
5139
|
+
needs forward, or author Transform 2.0 with
|
|
5140
|
+
``mode: "modify"`` instead.
|
|
5141
|
+
- |-
|
|
5142
|
+
An import's ``responseTransform`` is the exception: it accepts
|
|
5143
|
+
version ``"1"`` only (``"2"`` is refused with 422, verified live
|
|
5144
|
+
2026-10-21), so there, map every response field that response
|
|
5145
|
+
mapping needs.
|
|
5146
|
+
items:
|
|
5147
|
+
type: array
|
|
5148
|
+
items:
|
|
5149
|
+
type: object
|
|
5150
|
+
properties:
|
|
5151
|
+
extract:
|
|
5152
|
+
type: string
|
|
5153
|
+
description: |
|
|
5154
|
+
Source field path to read from. Supports multiple
|
|
5155
|
+
syntaxes: bare field names (`id`), dot notation
|
|
5156
|
+
(`fulfillment.shipment_id`), slash-prefixed paths
|
|
5157
|
+
for XML (`/FeedProcessingStatus`), wildcards (`*.id`,
|
|
5158
|
+
`*.[Internal ID]`), and array indexing (`SDF[0]`).
|
|
5159
|
+
generate:
|
|
5160
|
+
type: string
|
|
5161
|
+
description: |
|
|
5162
|
+
Target field name to write to. Typically a bare name
|
|
5163
|
+
(`id`) or dot path (`SDF.Filter.ID`).
|
|
5164
|
+
key:
|
|
5165
|
+
type: string
|
|
5166
|
+
description: |
|
|
5167
|
+
Auto-generated identifier for this rule, used by the
|
|
5168
|
+
UI to track individual rules for editing and reordering.
|
|
5169
|
+
required:
|
|
5170
|
+
- extract
|
|
5171
|
+
- generate
|
|
5172
|
+
rulesTwoDotZero:
|
|
5173
|
+
type: object
|
|
5174
|
+
description: |
|
|
5175
|
+
Configuration for version 2 transformation rules. This object contains the core logic
|
|
5176
|
+
for how data is mapped, enriched, and transformed.
|
|
5177
|
+
|
|
5178
|
+
**Capabilities**
|
|
5179
|
+
|
|
5180
|
+
Transformation 2.0 provides:
|
|
5181
|
+
- Precise field mapping with JSONPath expressions
|
|
5182
|
+
- Support for deeply nested data structures
|
|
5183
|
+
- Formula-based field generation
|
|
5184
|
+
- Dynamic lookups for data enrichment
|
|
5185
|
+
- Multiple operating modes to fit different scenarios
|
|
5186
|
+
properties:
|
|
5187
|
+
mode:
|
|
5188
|
+
type: string
|
|
5189
|
+
description: |
|
|
5190
|
+
Transformation mode that determines how records are handled during processing.
|
|
5191
|
+
|
|
5192
|
+
**Available modes**
|
|
5193
|
+
|
|
5194
|
+
**Create Mode (`"create"`)**
|
|
5195
|
+
- **Behavior**: Builds entirely new output records from inputs
|
|
5196
|
+
- **Use When**: Output structure differs significantly from input
|
|
5197
|
+
- **Advantage**: Clean slate approach, no field inheritance
|
|
5198
|
+
|
|
5199
|
+
**Modify Mode (`"modify"`)**
|
|
5200
|
+
- **Behavior**: Makes targeted edits to existing records
|
|
5201
|
+
- **Use When**: Output structure should remain similar to input
|
|
5202
|
+
- **Advantage**: Preserves unmapped fields from the original record
|
|
5203
|
+
enum:
|
|
5204
|
+
- create
|
|
5205
|
+
- modify
|
|
5206
|
+
x-enumDescriptions:
|
|
5207
|
+
create: Builds entirely new output records from inputs, ignoring unmapped fields.
|
|
5208
|
+
modify: Makes targeted edits to existing records, preserving unmapped fields.
|
|
5209
|
+
x-celigo-ai-guidance:
|
|
5210
|
+
- |-
|
|
5211
|
+
On a grouped record (the export groups rows, so the record is an
|
|
5212
|
+
array) only `create` can author output — build it from the rows with
|
|
5213
|
+
`$[0].field`, `$[*].field`, or a `buildArrayHelper` over `$[*]`.
|
|
5214
|
+
`modify` has no object to overlay onto an array: the record passes
|
|
5215
|
+
through untouched and the processor reports success. Either mode
|
|
5216
|
+
reshapes the inside of one record; neither changes how many records
|
|
5217
|
+
the page carries (that is the export's `preSavePage` hook) or whether
|
|
5218
|
+
the export groups at all (that is its grouping setting).
|
|
5219
|
+
examples:
|
|
5220
|
+
- create
|
|
5221
|
+
- modify
|
|
5222
|
+
mappings:
|
|
5223
|
+
$ref: '#/components/schemas/Mappings'
|
|
5224
|
+
lookups:
|
|
5225
|
+
allOf:
|
|
5226
|
+
- description: |
|
|
5227
|
+
Shared lookup tables used across all mappings defined in the transformation rules.
|
|
5228
|
+
|
|
5229
|
+
**Purpose**
|
|
5230
|
+
|
|
5231
|
+
Lookups provide centralized value translation that can be referenced from any mapping
|
|
5232
|
+
in your transformation configuration. They enable consistent translation of codes, IDs,
|
|
5233
|
+
and values between systems without duplicating translation logic.
|
|
5234
|
+
|
|
5235
|
+
**Usage in transformations**
|
|
5236
|
+
|
|
5237
|
+
Lookups are particularly valuable in transformations for:
|
|
5238
|
+
|
|
5239
|
+
- **Data Normalization**: Standardizing values from diverse source systems
|
|
5240
|
+
- **Code Translation**: Converting between different coding systems (e.g., status codes)
|
|
5241
|
+
- **Field Enrichment**: Adding descriptive values based on ID or code lookups
|
|
5242
|
+
- **Cross-Reference Resolution**: Mapping identifiers between integrated systems
|
|
5243
|
+
|
|
5244
|
+
**Implementation**
|
|
5245
|
+
|
|
5246
|
+
Lookups are defined once in this array and referenced by name in mappings:
|
|
5247
|
+
|
|
5248
|
+
```json
|
|
5249
|
+
"lookups": [
|
|
5250
|
+
{
|
|
5251
|
+
"name": "statusMapping",
|
|
5252
|
+
"map": {
|
|
5253
|
+
"A": "Active",
|
|
5254
|
+
"I": "Inactive",
|
|
5255
|
+
"P": "Pending"
|
|
5256
|
+
},
|
|
5257
|
+
"default": "Unknown Status"
|
|
5258
|
+
}
|
|
5259
|
+
]
|
|
5260
|
+
```
|
|
5261
|
+
|
|
5262
|
+
Then referenced in mappings using the lookupName property:
|
|
5263
|
+
|
|
5264
|
+
```json
|
|
5265
|
+
{
|
|
5266
|
+
"generate": "status",
|
|
5267
|
+
"dataType": "string",
|
|
5268
|
+
"extract": "$.statusCode",
|
|
5269
|
+
"lookupName": "statusMapping"
|
|
5270
|
+
}
|
|
5271
|
+
```
|
|
5272
|
+
|
|
5273
|
+
The system automatically applies the lookup during transformation processing.
|
|
5274
|
+
|
|
5275
|
+
For complete details on lookup properties and behavior, see the Lookups schema.
|
|
5276
|
+
- $ref: '#/components/schemas/Lookups'
|
|
5277
|
+
inputContext:
|
|
5278
|
+
type: string
|
|
5279
|
+
enum:
|
|
5280
|
+
- record
|
|
5281
|
+
- envelope
|
|
5282
|
+
x-enumDescriptions:
|
|
5283
|
+
record: The transform processor evaluates `mappings[].extract` JSONPath against the flat record itself (`$.field`, no `record.` segment) — the default when absent.
|
|
5284
|
+
envelope: The transform processor evaluates JSONPath against the wrapped runtime envelope `{record, job, testMode, settings, headers, queryParams}` (file-provider steps also carry `fileMeta`) — record fields need the `record.` segment (`$.record.field`), while `headers` and `queryParams` sit beside `record` (`$.headers['X-Id']`, `$.queryParams.src`).
|
|
5285
|
+
description: |
|
|
5286
|
+
Controls the JSON shape the transformTwoDotZero processor
|
|
5287
|
+
evaluates `mappings[].extract` JSONPath values against at
|
|
5288
|
+
flow runtime. Applies only to Transform 2.0 (v2,
|
|
5289
|
+
`rulesTwoDotZero`); v1 transforms (the `rules` array on
|
|
5290
|
+
`transform.expression.rules`) and script-mode transforms
|
|
5291
|
+
ignore this field.
|
|
5292
|
+
x-celigo-ai-guidance:
|
|
5293
|
+
- |-
|
|
5294
|
+
## Extract anchoring by mode
|
|
5295
|
+
|
|
5296
|
+
- `record` (default — absent / empty / undefined): the
|
|
5297
|
+
processor sees the FLAT record as its evaluation root.
|
|
5298
|
+
`mappings[].extract` JSONPath MUST anchor directly at
|
|
5299
|
+
`$` with NO `record.` segment — e.g. `"$.orderId"`,
|
|
5300
|
+
`"$.customer.email"`; PLACEHOLDER extracts use
|
|
5301
|
+
`"$.PLACEHOLDER_<field>"`.
|
|
5302
|
+
This is the dominant Celigo idiom and the right choice for new transforms.
|
|
5303
|
+
- `envelope`: the processor sees a wrapped object
|
|
5304
|
+
`{record: {...}, job, testMode, settings, headers,
|
|
5305
|
+
queryParams}` (plus `fileMeta` on file-provider steps).
|
|
5306
|
+
`mappings[].extract` JSONPath MUST include the
|
|
5307
|
+
`record.` segment for record fields — e.g.
|
|
5308
|
+
`"$.record.orderId"` — and reads `headers` and
|
|
5309
|
+
`queryParams` beside it (`$.headers['X-Id']`);
|
|
5310
|
+
PLACEHOLDER extracts use `"$.record.PLACEHOLDER_<field>"`.
|
|
5311
|
+
Pick this only when the transform was authored against
|
|
5312
|
+
the envelope shape on purpose.
|
|
5313
|
+
- |-
|
|
5314
|
+
Handlebars expressions inside `extract`
|
|
5315
|
+
(`{{record.field}}`, `{{dateFormat ... record.field}}`)
|
|
5316
|
+
ALWAYS reference the `record` root regardless of
|
|
5317
|
+
`inputContext` — only JSONPath anchoring flips.
|
|
5318
|
+
- |-
|
|
5319
|
+
In `envelope` mode the output is still a bare record: a
|
|
5320
|
+
`modify` transform returns the record with its mapped
|
|
5321
|
+
fields merged in (no `record` wrapper, no `job` or
|
|
5322
|
+
`settings` keys), and a `create` transform returns only
|
|
5323
|
+
the mapped fields.
|
|
5324
|
+
- |-
|
|
5325
|
+
Emit `inputContext` explicitly on new v2 transforms:
|
|
5326
|
+
unset is read as `record`, but stating it makes the
|
|
5327
|
+
extract-anchoring contract self-documenting and immune
|
|
5328
|
+
to a platform default change.
|
|
5329
|
+
- |-
|
|
5330
|
+
## Allowed values
|
|
5331
|
+
|
|
5332
|
+
- ``record`` (default — emitted when the field is absent
|
|
5333
|
+
/ empty / undefined): the transform processor sees
|
|
5334
|
+
the FLAT record itself as its evaluation root.
|
|
5335
|
+
``mappings[].extract`` JSONPath values MUST anchor
|
|
5336
|
+
directly at ``$`` with NO ``record.`` segment — for
|
|
5337
|
+
example ``"$.orderId"`` or
|
|
5338
|
+
``"$.customer.email"``. PLACEHOLDER extracts use
|
|
5339
|
+
``"$.PLACEHOLDER_<field>"``. This is the dominant
|
|
5340
|
+
Celigo idiom and the right choice for new transforms.
|
|
5341
|
+
|
|
5342
|
+
- ``envelope``: the transform processor sees a wrapped
|
|
5343
|
+
object of the shape
|
|
5344
|
+
``{record: {...}, job, testMode, settings, headers,
|
|
5345
|
+
queryParams}`` (plus ``fileMeta`` on file-provider
|
|
5346
|
+
steps; ``headers`` and ``queryParams`` sit beside
|
|
5347
|
+
``record``) — the
|
|
5348
|
+
same runtime-context envelope Handlebars / SQL /
|
|
5349
|
+
GraphQL templates render against. ``mappings[].extract``
|
|
5350
|
+
JSONPath values for record fields MUST include the
|
|
5351
|
+
``record.`` segment — for example ``"$.record.orderId"``
|
|
5352
|
+
or ``"$.record.customer.email"`` — while ``headers`` and
|
|
5353
|
+
``queryParams`` are read beside it
|
|
5354
|
+
(``"$.headers['X-Id']"``). PLACEHOLDER extracts
|
|
5355
|
+
use ``"$.record.PLACEHOLDER_<field>"``. Pick this
|
|
5356
|
+
mode only when the export was authored against the
|
|
5357
|
+
envelope shape on purpose (typically because an
|
|
5358
|
+
upstream step intentionally feeds the wrapped
|
|
5359
|
+
runtime context through to the transform).
|
|
5360
|
+
|
|
5361
|
+
## Handlebars expressions are NOT affected
|
|
5362
|
+
|
|
5363
|
+
Handlebars expressions inside ``extract``
|
|
5364
|
+
(``{{record.field}}``,
|
|
5365
|
+
``{{dateFormat ... record.field}}``, etc.) ALWAYS
|
|
5366
|
+
reference the runtime context's ``record`` root
|
|
5367
|
+
regardless of ``inputContext`` — the Handlebars runtime
|
|
5368
|
+
always sees the wrapped envelope. Only JSONPath
|
|
5369
|
+
behavior flips with this field.
|
|
5370
|
+
|
|
5371
|
+
## Agent guidance
|
|
5372
|
+
|
|
5373
|
+
Set this field explicitly on every new v2 transform
|
|
5374
|
+
the agent authors. Leaving it unset is interpreted as
|
|
5375
|
+
``record`` by the platform, but emitting
|
|
5376
|
+
``inputContext: record`` makes the contract
|
|
5377
|
+
self-documenting and prevents the transform from
|
|
5378
|
+
drifting into envelope mode if an upstream change ever
|
|
5379
|
+
changes the platform default. Read this value before
|
|
5380
|
+
writing ``mappings[].extract`` so the JSONPath form
|
|
5381
|
+
matches the runtime root.
|
|
5382
|
+
- |-
|
|
5383
|
+
## fileMeta on file-provider steps
|
|
5384
|
+
|
|
5385
|
+
File-provider exports and lookups populate a
|
|
5386
|
+
``fileMeta`` envelope key describing each record's
|
|
5387
|
+
source file: ``fileName``, ``fileSize``, and
|
|
5388
|
+
``lastModifiedTime`` (epoch milliseconds). Reach it
|
|
5389
|
+
as ``$.fileMeta.<field>`` in envelope mode, or as
|
|
5390
|
+
``{{fileMeta.<field>}}`` from a Handlebars extract in
|
|
5391
|
+
either mode. The keys are exactly these three —
|
|
5392
|
+
lowercase variants such as ``filesize`` or
|
|
5393
|
+
``filename`` resolve empty. The standalone transform
|
|
5394
|
+
processor substitutes sample fileMeta values when the
|
|
5395
|
+
posted data lacks them, so a resolving editor render
|
|
5396
|
+
is not proof the step provides fileMeta — only
|
|
5397
|
+
file-provider steps populate it at flow runtime.
|
|
5398
|
+
examples:
|
|
5399
|
+
- record
|
|
5400
|
+
- envelope
|
|
5401
|
+
script:
|
|
5402
|
+
type: object
|
|
5403
|
+
description: |
|
|
5404
|
+
Configuration for programmable script-based transformations. This object enables complex, custom
|
|
5405
|
+
transformation logic beyond what expression-based transformations can provide.
|
|
5406
|
+
|
|
5407
|
+
**Usage context**
|
|
5408
|
+
|
|
5409
|
+
This object is REQUIRED when `transform.type` is set to "script" and should not be configured
|
|
5410
|
+
otherwise. It provides a way to execute custom JavaScript code to transform data according to
|
|
5411
|
+
specialized business rules or complex algorithms.
|
|
5412
|
+
|
|
5413
|
+
**Implementation approach**
|
|
5414
|
+
|
|
5415
|
+
Script-based transformation works by:
|
|
5416
|
+
1. Executing the specified function from the referenced script
|
|
5417
|
+
2. Passing input data to the function
|
|
5418
|
+
3. Using the function's return value as the transformed output
|
|
5419
|
+
|
|
5420
|
+
**Common use cases**
|
|
5421
|
+
|
|
5422
|
+
Script transformation is ideal for:
|
|
5423
|
+
- Complex business logic that can't be expressed through mappings
|
|
5424
|
+
- Algorithmic transformations requiring computation
|
|
5425
|
+
- Dynamic transformations based on external factors
|
|
5426
|
+
- Legacy system data format compatibility
|
|
5427
|
+
- Multi-stage processing with intermediate steps
|
|
5428
|
+
|
|
5429
|
+
Only use script-based transformation when expression-based transformation is insufficient.
|
|
5430
|
+
Script transformation requires maintaining custom code, which adds complexity to the integration.
|
|
5431
|
+
properties:
|
|
5432
|
+
_scriptId:
|
|
5433
|
+
type: string
|
|
5434
|
+
description: |
|
|
5435
|
+
Reference to a predefined script resource containing the transformation logic.
|
|
5436
|
+
|
|
5437
|
+
The referenced script should contain the function specified in the
|
|
5438
|
+
'function' property. It must be a script in this account: any other id fails the save
|
|
5439
|
+
with 422 ("Only a script owned by the user or a script shared by the Integration App can
|
|
5440
|
+
be used at transform.script._scriptId.").
|
|
5441
|
+
format: objectid
|
|
5442
|
+
x-celigo-refModel: scripts
|
|
5443
|
+
examples:
|
|
5444
|
+
- 60a2c4e6f321d800129a1a3c
|
|
5445
|
+
- 5f8d43a1b9e5a80011a35f2c
|
|
5446
|
+
function:
|
|
5447
|
+
type: string
|
|
5448
|
+
description: |
|
|
5449
|
+
Name of the function within the script to execute for transformation. This function
|
|
5450
|
+
must exist in the script referenced by _scriptId.
|
|
5451
|
+
examples:
|
|
5452
|
+
- transformData
|
|
5453
|
+
- convertRecord
|
|
5454
|
+
- applyMapping
|
|
2650
5455
|
ApiRequest:
|
|
2651
5456
|
type: object
|
|
2652
5457
|
description: Request configuration for a builder-mode API endpoint.
|
|
@@ -2843,114 +5648,35 @@ components:
|
|
|
2843
5648
|
its mockResponse or a placeholder). Can include body, headers, pathParams, and
|
|
2844
5649
|
queryParams; only the body reaches the record the steps see.
|
|
2845
5650
|
transform:
|
|
2846
|
-
type: object
|
|
2847
5651
|
description: |-
|
|
2848
|
-
Optional transformation applied to the incoming request before processing.
|
|
2849
|
-
|
|
2850
|
-
|
|
2851
|
-
`queryParams`
|
|
2852
|
-
|
|
2853
|
-
|
|
2854
|
-
|
|
2855
|
-
description: Selects the transform form; `expression` runs the rules in `expression`.
|
|
2856
|
-
examples:
|
|
2857
|
-
- expression
|
|
2858
|
-
expression:
|
|
2859
|
-
type: object
|
|
2860
|
-
description: Transformation 2.0 rules applied to the request body.
|
|
2861
|
-
properties:
|
|
2862
|
-
version:
|
|
2863
|
-
type: string
|
|
2864
|
-
description: Rule format; `"2"` selects the rules in `rulesTwoDotZero`.
|
|
2865
|
-
examples:
|
|
2866
|
-
- '2'
|
|
2867
|
-
rulesTwoDotZero:
|
|
2868
|
-
type: object
|
|
2869
|
-
description: The rules applied to the request body.
|
|
2870
|
-
properties:
|
|
2871
|
-
mode:
|
|
2872
|
-
type: string
|
|
2873
|
-
enum:
|
|
2874
|
-
- create
|
|
2875
|
-
- modify
|
|
2876
|
-
x-enumDescriptions:
|
|
2877
|
-
create: Builds a new record from the mappings, dropping unmapped fields.
|
|
2878
|
-
modify: Edits the incoming record, keeping unmapped fields.
|
|
2879
|
-
description: How the mappings apply to the record; `modify` keeps the body's own fields beside the mapped ones.
|
|
2880
|
-
examples:
|
|
2881
|
-
- modify
|
|
2882
|
-
mappings:
|
|
2883
|
-
type: array
|
|
2884
|
-
description: Mapper 2.0 rows that write fields onto the record.
|
|
2885
|
-
items:
|
|
2886
|
-
type: object
|
|
2887
|
-
required:
|
|
2888
|
-
- dataType
|
|
2889
|
-
properties:
|
|
2890
|
-
generate:
|
|
2891
|
-
type: string
|
|
2892
|
-
description: Record field the row writes.
|
|
2893
|
-
examples:
|
|
2894
|
-
- customerId
|
|
2895
|
-
extract:
|
|
2896
|
-
type: string
|
|
2897
|
-
description: JSONPath into the request body that the value is read from.
|
|
2898
|
-
examples:
|
|
2899
|
-
- $.id
|
|
2900
|
-
dataType:
|
|
2901
|
-
type: string
|
|
2902
|
-
enum:
|
|
2903
|
-
- string
|
|
2904
|
-
- number
|
|
2905
|
-
- boolean
|
|
2906
|
-
- object
|
|
2907
|
-
- stringarray
|
|
2908
|
-
- numberarray
|
|
2909
|
-
- booleanarray
|
|
2910
|
-
- objectarray
|
|
2911
|
-
x-enumDescriptions:
|
|
2912
|
-
string: Single string value
|
|
2913
|
-
number: Single numeric value
|
|
2914
|
-
boolean: Single boolean value
|
|
2915
|
-
object: Nested object value
|
|
2916
|
-
stringarray: Array of strings
|
|
2917
|
-
numberarray: Array of numbers
|
|
2918
|
-
booleanarray: Array of booleans
|
|
2919
|
-
objectarray: Array of objects
|
|
2920
|
-
description: Data type the row writes.
|
|
2921
|
-
examples:
|
|
2922
|
-
- string
|
|
2923
|
-
sourceDataType:
|
|
2924
|
-
type: string
|
|
2925
|
-
description: Data type of the extracted value.
|
|
2926
|
-
examples:
|
|
2927
|
-
- string
|
|
2928
|
-
status:
|
|
2929
|
-
type: string
|
|
2930
|
-
description: Row status; `Active` rows run.
|
|
2931
|
-
examples:
|
|
2932
|
-
- Active
|
|
2933
|
-
mappings:
|
|
2934
|
-
type: array
|
|
2935
|
-
description: Child rows of an `object` row, with the same shape as this row.
|
|
2936
|
-
items:
|
|
2937
|
-
$ref: '#/components/schemas/items'
|
|
2938
|
-
_scriptId:
|
|
2939
|
-
type: string
|
|
2940
|
-
format: objectId
|
|
2941
|
-
x-celigo-refModel: scripts
|
|
2942
|
-
description: Reference to a script for custom transformation logic.
|
|
2943
|
-
examples:
|
|
2944
|
-
- 689212a2c42d988978e27a11
|
|
2945
|
-
function:
|
|
2946
|
-
type: string
|
|
2947
|
-
description: Function name in the script to execute.
|
|
2948
|
-
examples:
|
|
2949
|
-
- transformRequest
|
|
5652
|
+
Optional transformation applied to the incoming request before processing. It takes the
|
|
5653
|
+
same forms as an export's `transform`: Transformation 2.0 rules, legacy version 1 `rules`,
|
|
5654
|
+
or a `script`. In a test run the body is the only part of the request the rules see (under
|
|
5655
|
+
`record` when `inputContext` is `envelope`); `pathParams`, `queryParams` and headers are
|
|
5656
|
+
not passed to them.
|
|
5657
|
+
allOf:
|
|
5658
|
+
- $ref: '#/components/schemas/Transform'
|
|
2950
5659
|
x-celigo-ai-guidance:
|
|
2951
5660
|
- |-
|
|
2952
5661
|
Transforms the request data before it is processed by routers or responses.
|
|
2953
5662
|
Useful for normalizing data or extracting specific fields.
|
|
5663
|
+
- |-
|
|
5664
|
+
Put a script's id and function under `script` (`script._scriptId`, `script.function`).
|
|
5665
|
+
Sent at the top level of `transform` they are dropped without an error, and the API is
|
|
5666
|
+
saved with no transform at all.
|
|
5667
|
+
- |-
|
|
5668
|
+
In an API test run, an `envelope` input context holds only `job`, `lookupCacheOptions`,
|
|
5669
|
+
`record` (the request body), `settings` and `testMode`: no `pathParams`, and none of the
|
|
5670
|
+
`headers`, `queryParams` or `fileMeta` keys listed on `inputContext`. There
|
|
5671
|
+
`$.record.<field>` and `{{record.<field>}}` resolve while `$.pathParams`, `$.queryParams`
|
|
5672
|
+
and `$.headers` resolve to nothing even when the run's `mockRequest` carries them, so a
|
|
5673
|
+
test run cannot show whether rules that read request params or headers work; a real
|
|
5674
|
+
call's envelope was not probed.
|
|
5675
|
+
- |-
|
|
5676
|
+
On an API request transform, a `script._scriptId` that names no script fails the save
|
|
5677
|
+
with 422 `invalid_ref` and the message
|
|
5678
|
+
"<id> is not a valid builder.request.transform.script._scriptId", not the message
|
|
5679
|
+
quoted on `script._scriptId`. A script from another account was not probed on this path.
|
|
2954
5680
|
required:
|
|
2955
5681
|
- relativeURI
|
|
2956
5682
|
- method
|
|
@@ -3460,10 +6186,14 @@ components:
|
|
|
3460
6186
|
items:
|
|
3461
6187
|
$ref: '#/components/schemas/items-2'
|
|
3462
6188
|
hardCodedValue:
|
|
3463
|
-
type:
|
|
6189
|
+
type:
|
|
6190
|
+
- string
|
|
6191
|
+
- 'null'
|
|
3464
6192
|
description: |-
|
|
3465
6193
|
Static value written to the target field instead of extracting
|
|
3466
|
-
from input data.
|
|
6194
|
+
from input data. JSON `null` writes the destination field as null;
|
|
6195
|
+
it is what the mapper saves for its hard-coded
|
|
6196
|
+
"Use null as default value" choice.
|
|
3467
6197
|
x-celigo-ai-guidance:
|
|
3468
6198
|
- |-
|
|
3469
6199
|
The field name is exactly `hardCodedValue` (capital C). The
|
|
@@ -3775,10 +6505,14 @@ components:
|
|
|
3775
6505
|
items:
|
|
3776
6506
|
$ref: '#/components/schemas/items-2'
|
|
3777
6507
|
hardCodedValue:
|
|
3778
|
-
type:
|
|
6508
|
+
type:
|
|
6509
|
+
- string
|
|
6510
|
+
- 'null'
|
|
3779
6511
|
description: |-
|
|
3780
6512
|
Static value written to the target field instead of extracting
|
|
3781
|
-
from input data.
|
|
6513
|
+
from input data. JSON `null` writes the destination field as null;
|
|
6514
|
+
it is what the mapper saves for its hard-coded
|
|
6515
|
+
"Use null as default value" choice.
|
|
3782
6516
|
x-celigo-ai-guidance:
|
|
3783
6517
|
- |-
|
|
3784
6518
|
The field name is exactly `hardCodedValue` (capital C). The
|