@uipath/maestro-builder-sdk 6.22.0 → 6.24.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (34) hide show
  1. package/dist/api-index.md +117 -117
  2. package/dist/api-members.md +346 -346
  3. package/dist/check.js +0 -52
  4. package/dist/core/actions.d.ts +0 -240
  5. package/dist/core/actions.js +0 -137
  6. package/dist/core/typed-raw-node.js +0 -5
  7. package/dist/decompile.js +0 -71
  8. package/dist/flow-node-registry.js +3 -1
  9. package/dist/flow-sdk.d.ts +2 -0
  10. package/dist/flow-sdk.js +2 -0
  11. package/dist/nodes/ai-patterns/flow/factories.d.ts +83 -0
  12. package/dist/nodes/ai-patterns/flow/factories.js +86 -0
  13. package/dist/nodes/ai-patterns/flow/family.d.ts +3 -0
  14. package/dist/nodes/ai-patterns/flow/family.js +8 -0
  15. package/dist/nodes/ai-patterns/flow/index.d.ts +3 -0
  16. package/dist/nodes/ai-patterns/flow/index.js +3 -0
  17. package/dist/nodes/ai-patterns/flow/node-type.d.ts +11 -0
  18. package/dist/nodes/ai-patterns/flow/node-type.js +106 -0
  19. package/dist/nodes/ai-patterns/flow/spec.d.ts +75 -0
  20. package/dist/nodes/ai-patterns/flow/spec.js +1 -0
  21. package/dist/nodes/conversation/flow/check.d.ts +17 -0
  22. package/dist/nodes/conversation/flow/check.js +54 -0
  23. package/dist/nodes/conversation/flow/factories.d.ts +58 -0
  24. package/dist/nodes/conversation/flow/factories.js +63 -0
  25. package/dist/nodes/conversation/flow/family.d.ts +3 -0
  26. package/dist/nodes/conversation/flow/family.js +8 -0
  27. package/dist/nodes/conversation/flow/index.d.ts +3 -0
  28. package/dist/nodes/conversation/flow/index.js +3 -0
  29. package/dist/nodes/conversation/flow/node-type.d.ts +14 -0
  30. package/dist/nodes/conversation/flow/node-type.js +117 -0
  31. package/dist/nodes/conversation/flow/spec.d.ts +60 -0
  32. package/dist/nodes/conversation/flow/spec.js +1 -0
  33. package/dist/serialize.js +0 -88
  34. package/package.json +2 -2
@@ -0,0 +1,83 @@
1
+ /**
2
+ * The AI-pattern factories, `summarize()` and `batchTransform()`. Moved from
3
+ * core/actions.ts in Phase 4 of docs/NODE_TYPE_ARCHITECTURE_DESIGN.md; the
4
+ * package entry re-exports them.
5
+ */
6
+ import { type ActionSpec } from '../../../core/actions.js';
7
+ import type { BatchTransformInputs, SummarizeInputs } from './spec.js';
8
+ /**
9
+ * Summarize a document with citations — the platform's **Summarize** node.
10
+ *
11
+ * @remarks
12
+ * **The node type is `uipath.pattern.deep-rag`.** The canvas calls it
13
+ * *Summarize*, its properties panel is titled *Summarize Configuration*, and
14
+ * the wire type stays `deep-rag` — it is the same node, under the name the
15
+ * backend service contract uses (`ECS.DeepRag`). There is no
16
+ * `uipath.pattern.summarize`. (A same-named inline-agent TOOL,
17
+ * `uipath.agent.resource.tool.builtin.summarize`, is a different family.)
18
+ *
19
+ * The answer's fields are **PascalCase** — `content.Text`,
20
+ * `content.Citations[].{Ordinal, PageNumber, Source, Reference}`. Lowercase
21
+ * `content.text` resolves to nothing at run time.
22
+ *
23
+ * A local run cannot reach the service: it returns the baked
24
+ * fixture shape, and only a real platform run (`uip maestro flow debug
25
+ * --attachment <var>=<file>`) calls the model.
26
+ *
27
+ * @example
28
+ * **Summarize an attached contract, with citations**
29
+ * ```ts
30
+ * flow('SummarizeDemo')
31
+ * .input({ documentFile: types.file })
32
+ * .output({ summary: types.string, citations: types.array })
33
+ * .step('summarizeContract', summarize({
34
+ * attachment: out('start', 'documentFile'),
35
+ * prompt: 'Write a 5-bullet executive summary covering scope, term and SLAs.',
36
+ * returnCitations: true,
37
+ * }))
38
+ * .return({
39
+ * summary: out('summarizeContract', 'content.Text'),
40
+ * citations: out('summarizeContract', 'content.Citations'),
41
+ * })
42
+ * ```
43
+ *
44
+ * @param inputs - The document (`attachment`), the question to answer (`prompt`),
45
+ * and whether to return citations.
46
+ * @returns An action spec to pass to `.step(name, …)`.
47
+ */
48
+ export declare function summarize(inputs: SummarizeInputs): ActionSpec;
49
+ /**
50
+ * Add AI-generated columns to a CSV — the platform's **Batch transform** node,
51
+ * `uipath.pattern.batch-transform` (service contract `ECS.BatchTransform`).
52
+ *
53
+ * @remarks
54
+ * The output is a **file handle for the enriched CSV**, not the rows:
55
+ * `{ ID, FullName, MimeType }` — the service writes a new
56
+ * `batch-transform-<uuid>.csv` and hands back its attachment. Note `ID`, two
57
+ * capitals: that is what the platform returns.
58
+ *
59
+ * Same dispatch story as {@link summarize} — dry-run fixture locally, a real
60
+ * model call only on a platform run.
61
+ *
62
+ * @example
63
+ * **Categorize each CSV row with two generated columns**
64
+ * ```ts
65
+ * flow('BatchTransformDemo')
66
+ * .input({ csvFile: types.file })
67
+ * .output({ result: types.file })
68
+ * .step('categorizeRows', batchTransform({
69
+ * attachment: out('start', 'csvFile'),
70
+ * prompt: 'Classify each row by category and write a one-line summary.',
71
+ * outputColumns: [
72
+ * { name: 'Category', description: 'One of: Utility, Software, Travel, Other' },
73
+ * { name: 'Summary', description: 'Plain-English one-line summary of the row' },
74
+ * ],
75
+ * }))
76
+ * .return({ result: out('categorizeRows') })
77
+ * ```
78
+ *
79
+ * @param inputs - The CSV (`attachment`), the instruction (`prompt`), and the
80
+ * `outputColumns` to add to each row.
81
+ * @returns An action spec to pass to `.step(name, …)`.
82
+ */
83
+ export declare function batchTransform(inputs: BatchTransformInputs): ActionSpec;
@@ -0,0 +1,86 @@
1
+ /**
2
+ * The AI-pattern factories, `summarize()` and `batchTransform()`. Moved from
3
+ * core/actions.ts in Phase 4 of docs/NODE_TYPE_ARCHITECTURE_DESIGN.md; the
4
+ * package entry re-exports them.
5
+ */
6
+ import { builtinActionSpec } from '../../../core/actions.js';
7
+ /**
8
+ * Summarize a document with citations — the platform's **Summarize** node.
9
+ *
10
+ * @remarks
11
+ * **The node type is `uipath.pattern.deep-rag`.** The canvas calls it
12
+ * *Summarize*, its properties panel is titled *Summarize Configuration*, and
13
+ * the wire type stays `deep-rag` — it is the same node, under the name the
14
+ * backend service contract uses (`ECS.DeepRag`). There is no
15
+ * `uipath.pattern.summarize`. (A same-named inline-agent TOOL,
16
+ * `uipath.agent.resource.tool.builtin.summarize`, is a different family.)
17
+ *
18
+ * The answer's fields are **PascalCase** — `content.Text`,
19
+ * `content.Citations[].{Ordinal, PageNumber, Source, Reference}`. Lowercase
20
+ * `content.text` resolves to nothing at run time.
21
+ *
22
+ * A local run cannot reach the service: it returns the baked
23
+ * fixture shape, and only a real platform run (`uip maestro flow debug
24
+ * --attachment <var>=<file>`) calls the model.
25
+ *
26
+ * @example
27
+ * **Summarize an attached contract, with citations**
28
+ * ```ts
29
+ * flow('SummarizeDemo')
30
+ * .input({ documentFile: types.file })
31
+ * .output({ summary: types.string, citations: types.array })
32
+ * .step('summarizeContract', summarize({
33
+ * attachment: out('start', 'documentFile'),
34
+ * prompt: 'Write a 5-bullet executive summary covering scope, term and SLAs.',
35
+ * returnCitations: true,
36
+ * }))
37
+ * .return({
38
+ * summary: out('summarizeContract', 'content.Text'),
39
+ * citations: out('summarizeContract', 'content.Citations'),
40
+ * })
41
+ * ```
42
+ *
43
+ * @param inputs - The document (`attachment`), the question to answer (`prompt`),
44
+ * and whether to return citations.
45
+ * @returns An action spec to pass to `.step(name, …)`.
46
+ */
47
+ export function summarize(inputs) {
48
+ return builtinActionSpec({ kind: 'summarize', inputs });
49
+ }
50
+ /**
51
+ * Add AI-generated columns to a CSV — the platform's **Batch transform** node,
52
+ * `uipath.pattern.batch-transform` (service contract `ECS.BatchTransform`).
53
+ *
54
+ * @remarks
55
+ * The output is a **file handle for the enriched CSV**, not the rows:
56
+ * `{ ID, FullName, MimeType }` — the service writes a new
57
+ * `batch-transform-<uuid>.csv` and hands back its attachment. Note `ID`, two
58
+ * capitals: that is what the platform returns.
59
+ *
60
+ * Same dispatch story as {@link summarize} — dry-run fixture locally, a real
61
+ * model call only on a platform run.
62
+ *
63
+ * @example
64
+ * **Categorize each CSV row with two generated columns**
65
+ * ```ts
66
+ * flow('BatchTransformDemo')
67
+ * .input({ csvFile: types.file })
68
+ * .output({ result: types.file })
69
+ * .step('categorizeRows', batchTransform({
70
+ * attachment: out('start', 'csvFile'),
71
+ * prompt: 'Classify each row by category and write a one-line summary.',
72
+ * outputColumns: [
73
+ * { name: 'Category', description: 'One of: Utility, Software, Travel, Other' },
74
+ * { name: 'Summary', description: 'Plain-English one-line summary of the row' },
75
+ * ],
76
+ * }))
77
+ * .return({ result: out('categorizeRows') })
78
+ * ```
79
+ *
80
+ * @param inputs - The CSV (`attachment`), the instruction (`prompt`), and the
81
+ * `outputColumns` to add to each row.
82
+ * @returns An action spec to pass to `.step(name, …)`.
83
+ */
84
+ export function batchTransform(inputs) {
85
+ return builtinActionSpec({ kind: 'batchTransform', inputs });
86
+ }
@@ -0,0 +1,3 @@
1
+ /** The AI-pattern node family, as flow-node-registry.ts lists it: `uipath.pattern.deep-rag` and `uipath.pattern.batch-transform`. */
2
+ import type { FlowNodeFamily } from '../../../flow-node-type.js';
3
+ export declare const aiPatternsFlowFamily: FlowNodeFamily;
@@ -0,0 +1,8 @@
1
+ import { aiPatternNodeTypes } from './node-type.js';
2
+ export const aiPatternsFlowFamily = {
3
+ id: 'ai-patterns',
4
+ title: 'AI patterns',
5
+ types: aiPatternNodeTypes,
6
+ // No node-local rules: what an AI-pattern step could get wrong is the service's to say.
7
+ diagnostics: {},
8
+ };
@@ -0,0 +1,3 @@
1
+ /** The AI-pattern family's public surface, which the package entry re-exports. */
2
+ export * from './spec.js';
3
+ export * from './factories.js';
@@ -0,0 +1,3 @@
1
+ /** The AI-pattern family's public surface, which the package entry re-exports. */
2
+ export * from './spec.js';
3
+ export * from './factories.js';
@@ -0,0 +1,11 @@
1
+ import type { FlowNodeType } from '../../../flow-node-type.js';
2
+ import type { BatchTransformInputs, SummarizeInputs } from './spec.js';
3
+ export type SummarizeSpec = {
4
+ kind: 'summarize';
5
+ inputs: SummarizeInputs;
6
+ };
7
+ export type BatchTransformSpec = {
8
+ kind: 'batchTransform';
9
+ inputs: BatchTransformInputs;
10
+ };
11
+ export declare const aiPatternNodeTypes: (FlowNodeType<SummarizeSpec> | FlowNodeType<BatchTransformSpec>)[];
@@ -0,0 +1,106 @@
1
+ /**
2
+ * The two AI-pattern node types: `uipath.pattern.deep-rag` (Summarize) and
3
+ * `uipath.pattern.batch-transform`, each bundled at 1.0. Moved from
4
+ * serialize.ts / decompile.ts in Phase 4 of docs/NODE_TYPE_ARCHITECTURE_DESIGN.md;
5
+ * serialized output and printed source unchanged.
6
+ */
7
+ import { Expr } from '../../../core/expr.js';
8
+ /** A value as the author wrote it: an expression back to an Expr, a literal string as itself, any other JSON as is. */
9
+ function lifted(raw, ctx) {
10
+ const text = Array.isArray(raw) ? undefined : ctx.sourceText(raw);
11
+ if (text === undefined)
12
+ return raw;
13
+ return text.startsWith('=js:') ? ctx.expr(text) : text;
14
+ }
15
+ /** A spec value as source: an Expr as the helper an author writes, `undefined` as itself, anything else as data. */
16
+ function printed(v, ctx) {
17
+ if (v === undefined)
18
+ return 'undefined';
19
+ return v instanceof Expr ? ctx.value(v) : ctx.json(v);
20
+ }
21
+ // Neither node carries a node-level `model`: both are `bpmn:ServiceTask`s whose
22
+ // `serviceType` the platform resolves from `definitions[]`, and every deployed
23
+ // instance of either carries none — v1's own structural checker fails a flow
24
+ // that has one. The resource model stays on the DEFINITION only, as it does for
25
+ // the published families. Per call (`model: 'omit'`), so a `rawNode` of either
26
+ // type keeps what it has always written.
27
+ const summarizeType = {
28
+ kind: 'summarize', typeName: 'uipath.pattern.deep-rag', version: '1.0', factory: 'summarize', definition: 'bundled',
29
+ rawNode: { factory: 'summarize()' },
30
+ // Each field is written under the NODE's own name, so the surface and the
31
+ // emitted file read alike.
32
+ serialize: ({ inputs }, ctx) => ({
33
+ model: 'omit',
34
+ inputs: {
35
+ attachment: ctx.render(inputs.attachment),
36
+ prompt: ctx.render(inputs.prompt),
37
+ returnCitations: inputs.returnCitations ?? false,
38
+ },
39
+ port: 'output',
40
+ }),
41
+ deserialize: (node, ctx) => {
42
+ const i = (node.inputs ?? {});
43
+ return {
44
+ kind: 'summarize',
45
+ inputs: {
46
+ attachment: lifted(i.attachment, ctx),
47
+ prompt: lifted(i.prompt, ctx),
48
+ // The flag defaults to false in the emitted node; only `true` was authored.
49
+ ...(ctx.plainValue(i.returnCitations) === true ? { returnCitations: true } : {}),
50
+ },
51
+ };
52
+ },
53
+ print: ({ inputs }, ctx) => ({
54
+ factory: 'summarize',
55
+ options: [
56
+ ['attachment', printed(inputs.attachment, ctx)],
57
+ ['prompt', printed(inputs.prompt, ctx)],
58
+ ['returnCitations', inputs.returnCitations === true ? 'true' : undefined],
59
+ ],
60
+ }),
61
+ // Deliberately none: references in the prompt, the attachment and the columns are not checked.
62
+ expressions: () => [],
63
+ output: () => ({ kind: 'opaque' }),
64
+ };
65
+ const batchTransformType = {
66
+ kind: 'batchTransform', typeName: 'uipath.pattern.batch-transform', version: '1.0', factory: 'batchTransform',
67
+ definition: 'bundled',
68
+ rawNode: { factory: 'batchTransform()' },
69
+ serialize: ({ inputs }, ctx) => ({
70
+ model: 'omit',
71
+ inputs: {
72
+ attachment: ctx.render(inputs.attachment),
73
+ prompt: ctx.render(inputs.prompt),
74
+ enableWebSearchGrounding: inputs.enableWebSearchGrounding ?? false,
75
+ // Rendered per column, so an expression in a description renders like every other input.
76
+ outputColumns: inputs.outputColumns.map((c) => Object.fromEntries(Object.entries(c).map(([k, v]) => [k, ctx.render(v)]))),
77
+ },
78
+ port: 'output',
79
+ }),
80
+ deserialize: (node, ctx) => {
81
+ const i = (node.inputs ?? {});
82
+ const cols = Array.isArray(i.outputColumns) ? i.outputColumns : [];
83
+ return {
84
+ kind: 'batchTransform',
85
+ inputs: {
86
+ attachment: lifted(i.attachment, ctx),
87
+ prompt: lifted(i.prompt, ctx),
88
+ outputColumns: cols.map((c) => ({ name: lifted(c.name, ctx), description: lifted(c.description, ctx) })),
89
+ ...(ctx.plainValue(i.enableWebSearchGrounding) === true ? { enableWebSearchGrounding: true } : {}),
90
+ },
91
+ };
92
+ },
93
+ print: ({ inputs }, ctx) => ({
94
+ factory: 'batchTransform',
95
+ options: [
96
+ ['attachment', printed(inputs.attachment, ctx)],
97
+ ['prompt', printed(inputs.prompt, ctx)],
98
+ ['outputColumns', `[${inputs.outputColumns.map((c) => `{ name: ${printed(c.name, ctx)}, description: ${printed(c.description, ctx)} }`).join(', ')}]`],
99
+ ['enableWebSearchGrounding', inputs.enableWebSearchGrounding === true ? 'true' : undefined],
100
+ ],
101
+ }),
102
+ // Deliberately none, as for Summarize.
103
+ expressions: () => [],
104
+ output: () => ({ kind: 'opaque' }),
105
+ };
106
+ export const aiPatternNodeTypes = [summarizeType, batchTransformType];
@@ -0,0 +1,75 @@
1
+ /**
2
+ * The AI-pattern family's authoring types (`uipath.pattern.deep-rag`,
3
+ * `uipath.pattern.batch-transform`), and their kinds' entries in
4
+ * `FlowActionSpecs`. Moved from core/actions.ts in Phase 4 of
5
+ * docs/NODE_TYPE_ARCHITECTURE_DESIGN.md.
6
+ */
7
+ import type { Expr } from '../../../core/expr.js';
8
+ export interface SummarizeInputs {
9
+ /**
10
+ * The document to summarize — a whole **Flow Attachment** object
11
+ * (`{ ID, FullName, MimeType, Metadata }`), not a path, id or URL.
12
+ *
13
+ * In practice that is a `file`-typed flow input:
14
+ *
15
+ * ```ts
16
+ * flow('SummarizeDemo')
17
+ * .input({ documentFile: types.file })
18
+ * .step('summarizeContract', summarize({ attachment: input('documentFile'), … }))
19
+ * ```
20
+ *
21
+ * `out('start', 'documentFile')` is the same value written the way the CANVAS
22
+ * writes it (`$vars.start.output.documentFile`, resolved through the input's
23
+ * `triggerNodeId` binding). Both forms run — measured on the real service —
24
+ * so prefer whichever the task asks for; `out('start', …)` is what a
25
+ * designer-made flow looks like.
26
+ *
27
+ * The service reads the file's CONTENT, and refuses one it cannot treat as a
28
+ * document: a PDF summarizes, a plain `.txt` comes back
29
+ * `[460005] … "No valid files to use for Summarization."`
30
+ */
31
+ attachment: Expr;
32
+ /** What the summary should cover, e.g. `'Write a 5-bullet executive summary…'`. */
33
+ prompt: string | Expr;
34
+ /**
35
+ * Ask the service for per-claim citations. Each is
36
+ * `{ Ordinal, PageNumber, Source, Reference }` and lands in
37
+ * `out('<step>', 'content.Citations')`. Defaults to `false`.
38
+ */
39
+ returnCitations?: boolean;
40
+ }
41
+ /** One column Batch Transform appends to the CSV. */
42
+ export interface OutputColumn {
43
+ /** The new column's header, e.g. `'Category'`. */
44
+ name: string;
45
+ /** What the model should put in it, e.g. `'One of: Utility, Software, Travel, Other'`. */
46
+ description: string;
47
+ }
48
+ export interface BatchTransformInputs {
49
+ /**
50
+ * The CSV to enrich — a whole **Flow Attachment** object, same shape and same
51
+ * two ways of referencing it as {@link SummarizeInputs.attachment}.
52
+ */
53
+ attachment: Expr;
54
+ /** How to process each row, e.g. `'Classify each row and write a one-line summary.'`. */
55
+ prompt: string | Expr;
56
+ /**
57
+ * The columns to add, in order. The node's own field name — an array of
58
+ * `{ name, description }`, one per new column.
59
+ */
60
+ outputColumns: OutputColumn[];
61
+ /** Let the model use web search while transforming. Defaults to `false`. */
62
+ enableWebSearchGrounding?: boolean;
63
+ }
64
+ declare module '../../../core/actions.js' {
65
+ interface FlowActionSpecs {
66
+ /** The spec {@link summarize} builds. */
67
+ summarize: {
68
+ inputs: SummarizeInputs;
69
+ };
70
+ /** The spec {@link batchTransform} builds. */
71
+ batchTransform: {
72
+ inputs: BatchTransformInputs;
73
+ };
74
+ }
75
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,17 @@
1
+ /**
2
+ * The conversation family's rules. Moved from check.ts in Phase 4 of
3
+ * docs/NODE_TYPE_ARCHITECTURE_DESIGN.md; codes and messages unchanged.
4
+ */
5
+ import type { DiagnosticCatalog } from '../../../core/nodes/family.js';
6
+ import type { FlowCheckContext } from '../../../flow-node-type.js';
7
+ export declare const CONVERSATION_DIAGNOSTICS: DiagnosticCatalog;
8
+ /**
9
+ * A conversational step (Phase 5C): send-message, wait-for-message, or
10
+ * get-conversation-context.
11
+ *
12
+ * Everything here is decidable offline and invisible later: the node's own
13
+ * schema requires `conversationId` (and `exchangeId`/`content` on send), and
14
+ * the two numeric limits are range-checked by the designer but silently
15
+ * clamped at run time.
16
+ */
17
+ export declare function checkConversational(kind: 'sendMessage' | 'waitForMessage' | 'conversationContext', inputs: Record<string, unknown> | undefined, ctx: FlowCheckContext): void;
@@ -0,0 +1,54 @@
1
+ import { Expr } from '../../../core/expr.js';
2
+ export const CONVERSATION_DIAGNOSTICS = {
3
+ CONVERSATION_NO_ID: { severity: 'error', summary: 'a conversational step with no conversationId' },
4
+ SEND_MESSAGE_NO_EXCHANGE: { severity: 'error', summary: 'sendMessage with no exchangeId' },
5
+ SEND_MESSAGE_NO_CONTENT: { severity: 'error', summary: 'sendMessage with no content' },
6
+ CONVERSATION_RANGE: { severity: 'error', summary: 'a history limit outside 1–40' },
7
+ };
8
+ /**
9
+ * A conversational step (Phase 5C): send-message, wait-for-message, or
10
+ * get-conversation-context.
11
+ *
12
+ * Everything here is decidable offline and invisible later: the node's own
13
+ * schema requires `conversationId` (and `exchangeId`/`content` on send), and
14
+ * the two numeric limits are range-checked by the designer but silently
15
+ * clamped at run time.
16
+ */
17
+ export function checkConversational(kind, inputs, ctx) {
18
+ const step = ctx.step;
19
+ const at = (code, message, suggestion) => ctx.report(code, message, suggestion);
20
+ const blank = (v) => v === undefined || v === null || (typeof v === 'string' && v.trim() === '');
21
+ const label = kind === 'sendMessage' ? 'sendMessage'
22
+ : kind === 'waitForMessage' ? 'waitForMessage' : 'conversationContext';
23
+ if (blank(inputs?.conversationId)) {
24
+ at('CONVERSATION_NO_ID', `${label} step "${step}" has no \`conversationId\`, which the node's schema requires — every `
25
+ + `conversational step is keyed by the conversation it belongs to. The conversation trigger publishes `
26
+ + `it as out('start', 'conversationId').`, `conversationId: out('start', 'conversationId')`);
27
+ }
28
+ if (kind === 'sendMessage') {
29
+ if (blank(inputs?.exchangeId)) {
30
+ at('SEND_MESSAGE_NO_EXCHANGE', `sendMessage step "${step}" has no \`exchangeId\` — the node's schema requires it, because a message `
31
+ + `belongs to one exchange (a user turn and its answers). A wait step publishes it as `
32
+ + `out('<waitStep>', 'conversationContext.latestExchangeId').`, `exchangeId: out('<waitStep>', 'conversationContext.latestExchangeId')`);
33
+ }
34
+ if (blank(inputs?.content)) {
35
+ at('SEND_MESSAGE_NO_CONTENT', `sendMessage step "${step}" has no \`content\` — the node's schema requires a non-empty message `
36
+ + `(Markdown), and an empty one posts a blank turn into the conversation.`, `content: 'Looking into it.'`);
37
+ }
38
+ }
39
+ const rangeCheck = (field, max) => {
40
+ const raw = inputs?.[field];
41
+ if (raw === undefined || raw instanceof Expr)
42
+ return;
43
+ const n = Number(raw);
44
+ if (!Number.isFinite(n) || !Number.isInteger(n) || n < 1 || n > max) {
45
+ at('CONVERSATION_RANGE', `${label} step "${step}"'s \`${field}\` is ${JSON.stringify(raw)}. The node accepts a whole number from `
46
+ + `1 to ${max} (the platform default is 20); anything else is clamped at run time, so the flow reads `
47
+ + `a different amount of history than it says.`, `${field}: 20`);
48
+ }
49
+ };
50
+ if (kind === 'waitForMessage')
51
+ rangeCheck('numExchanges', 40);
52
+ if (kind === 'conversationContext')
53
+ rangeCheck('exchangeLimit', 40);
54
+ }
@@ -0,0 +1,58 @@
1
+ /**
2
+ * The conversation factories, `sendMessage()`, `waitForMessage()` and
3
+ * `conversationContext()`. Moved from core/actions.ts in Phase 4 of
4
+ * docs/NODE_TYPE_ARCHITECTURE_DESIGN.md; the package entry re-exports them.
5
+ */
6
+ import { type ActionSpec } from '../../../core/actions.js';
7
+ import type { ConversationContextInputs, SendMessageInputs, WaitForMessageInputs } from './spec.js';
8
+ /**
9
+ * Post an assistant message into a live conversation
10
+ * (`uipath.conversational.send-message`).
11
+ *
12
+ * ```ts
13
+ * .step('answer', sendMessage({
14
+ * conversationId: out('start', 'conversationId'),
15
+ * exchangeId: out('listen', 'conversationContext.latestExchangeId'),
16
+ * content: 'Your order ships tomorrow.',
17
+ * }))
18
+ * ```
19
+ *
20
+ * The message is Markdown (`text/markdown` is the node's only supported type)
21
+ * and the role is always `assistant` — a flow speaks as the assistant.
22
+ *
23
+ * @param inputs - The conversation, the exchange, and what to say.
24
+ * @returns An action spec to pass to `.step(...)`.
25
+ */
26
+ export declare function sendMessage(inputs: SendMessageInputs): ActionSpec;
27
+ /**
28
+ * PAUSE until the person sends their next message
29
+ * (`uipath.conversational.wait-for-message`) — a catch event, like
30
+ * `waitForEvent`, so the flow suspends rather than polling.
31
+ *
32
+ * ```ts
33
+ * .step('listen', waitForMessage({ conversationId: out('start', 'conversationId') }))
34
+ * ```
35
+ *
36
+ * It resumes with the conversation context:
37
+ * `out('listen', 'conversationContext.messages')` is the transcript and
38
+ * `…conversationContext.latestExchangeId` is the turn to answer.
39
+ *
40
+ * @param inputs - The conversation to wait on, and how much history to return.
41
+ * @returns An action spec to pass to `.step(...)`.
42
+ */
43
+ export declare function waitForMessage(inputs: WaitForMessageInputs): ActionSpec;
44
+ /**
45
+ * READ a conversation's transcript so far without waiting
46
+ * (`uipath.conversational.get-conversation-context`) — the shape a
47
+ * conversational agent takes as its turn context.
48
+ *
49
+ * ```ts
50
+ * .step('history', conversationContext({
51
+ * conversationId: out('start', 'conversationId'), exchangeLimit: 10,
52
+ * }))
53
+ * ```
54
+ *
55
+ * @param inputs - The conversation to read, and how many exchanges to return.
56
+ * @returns An action spec to pass to `.step(...)`.
57
+ */
58
+ export declare function conversationContext(inputs: ConversationContextInputs): ActionSpec;
@@ -0,0 +1,63 @@
1
+ /**
2
+ * The conversation factories, `sendMessage()`, `waitForMessage()` and
3
+ * `conversationContext()`. Moved from core/actions.ts in Phase 4 of
4
+ * docs/NODE_TYPE_ARCHITECTURE_DESIGN.md; the package entry re-exports them.
5
+ */
6
+ import { builtinActionSpec } from '../../../core/actions.js';
7
+ /**
8
+ * Post an assistant message into a live conversation
9
+ * (`uipath.conversational.send-message`).
10
+ *
11
+ * ```ts
12
+ * .step('answer', sendMessage({
13
+ * conversationId: out('start', 'conversationId'),
14
+ * exchangeId: out('listen', 'conversationContext.latestExchangeId'),
15
+ * content: 'Your order ships tomorrow.',
16
+ * }))
17
+ * ```
18
+ *
19
+ * The message is Markdown (`text/markdown` is the node's only supported type)
20
+ * and the role is always `assistant` — a flow speaks as the assistant.
21
+ *
22
+ * @param inputs - The conversation, the exchange, and what to say.
23
+ * @returns An action spec to pass to `.step(...)`.
24
+ */
25
+ export function sendMessage(inputs) {
26
+ return builtinActionSpec({ kind: 'sendMessage', inputs });
27
+ }
28
+ /**
29
+ * PAUSE until the person sends their next message
30
+ * (`uipath.conversational.wait-for-message`) — a catch event, like
31
+ * `waitForEvent`, so the flow suspends rather than polling.
32
+ *
33
+ * ```ts
34
+ * .step('listen', waitForMessage({ conversationId: out('start', 'conversationId') }))
35
+ * ```
36
+ *
37
+ * It resumes with the conversation context:
38
+ * `out('listen', 'conversationContext.messages')` is the transcript and
39
+ * `…conversationContext.latestExchangeId` is the turn to answer.
40
+ *
41
+ * @param inputs - The conversation to wait on, and how much history to return.
42
+ * @returns An action spec to pass to `.step(...)`.
43
+ */
44
+ export function waitForMessage(inputs) {
45
+ return builtinActionSpec({ kind: 'waitForMessage', inputs });
46
+ }
47
+ /**
48
+ * READ a conversation's transcript so far without waiting
49
+ * (`uipath.conversational.get-conversation-context`) — the shape a
50
+ * conversational agent takes as its turn context.
51
+ *
52
+ * ```ts
53
+ * .step('history', conversationContext({
54
+ * conversationId: out('start', 'conversationId'), exchangeLimit: 10,
55
+ * }))
56
+ * ```
57
+ *
58
+ * @param inputs - The conversation to read, and how many exchanges to return.
59
+ * @returns An action spec to pass to `.step(...)`.
60
+ */
61
+ export function conversationContext(inputs) {
62
+ return builtinActionSpec({ kind: 'conversationContext', inputs });
63
+ }
@@ -0,0 +1,3 @@
1
+ /** The conversation node family, as flow-node-registry.ts lists it: the three `uipath.conversational.*` steps. */
2
+ import type { FlowNodeFamily } from '../../../flow-node-type.js';
3
+ export declare const conversationFlowFamily: FlowNodeFamily;
@@ -0,0 +1,8 @@
1
+ import { CONVERSATION_DIAGNOSTICS } from './check.js';
2
+ import { conversationNodeTypes } from './node-type.js';
3
+ export const conversationFlowFamily = {
4
+ id: 'conversation',
5
+ title: 'Conversation',
6
+ types: conversationNodeTypes,
7
+ diagnostics: CONVERSATION_DIAGNOSTICS,
8
+ };
@@ -0,0 +1,3 @@
1
+ /** The conversation family's public surface, which the package entry re-exports. */
2
+ export * from './spec.js';
3
+ export * from './factories.js';
@@ -0,0 +1,3 @@
1
+ /** The conversation family's public surface, which the package entry re-exports. */
2
+ export * from './spec.js';
3
+ export * from './factories.js';
@@ -0,0 +1,14 @@
1
+ import type { FlowVersionedNodeType } from '../../../flow-node-type.js';
2
+ import type { ConversationContextInputs, SendMessageInputs, WaitForMessageInputs } from './spec.js';
3
+ type Spec = {
4
+ kind: 'sendMessage';
5
+ inputs: SendMessageInputs;
6
+ } | {
7
+ kind: 'waitForMessage';
8
+ inputs: WaitForMessageInputs;
9
+ } | {
10
+ kind: 'conversationContext';
11
+ inputs: ConversationContextInputs;
12
+ };
13
+ export declare const conversationNodeTypes: FlowVersionedNodeType<Spec>[];
14
+ export {};