@amaster.ai/workflow-client 1.1.0-beta.73 → 1.1.0-beta.75

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/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- 'use strict';var httpClient=require('@amaster.ai/http-client');function l(e){if(!e)return {inputs:{},response_mode:"blocking",user:"anonymous"};if(typeof e=="object"&&("inputs"in e||"response_mode"in e||"user"in e||"files"in e||"trace_id"in e)){let t=e;return {inputs:t.inputs||{},response_mode:t.response_mode||"blocking",user:t.user||"anonymous",files:t.files,trace_id:t.trace_id}}return {inputs:e,response_mode:"blocking",user:"anonymous"}}function i(e=httpClient.createHttpClient()){return {async run(t,n){if(!t||t.includes("/"))return {data:null,error:{status:400,message:"Invalid workflowName: use workflow YAML filename without extension (no subpaths)"},status:400};let s=l(n),o=await e.request({url:`/api/runworkflow/${t}`,method:"post",headers:{"Content-Type":"application/json"},data:s});if(o.data?.data){let r=o.data.data;return {...o,data:{task_id:o.data.task_id||"",workflow_run_id:o.data.workflow_run_id||"",status:r.status||"unknown",outputs:r.outputs||{},error:r.error||null,elapsed_time:r.elapsed_time||0,total_tokens:r.total_tokens||0,total_steps:r.total_steps||0,created_at:r.created_at||0,finished_at:r.finished_at||0}}}return {data:null,error:o.error||{status:o.status,message:"Invalid workflow response structure"},status:o.status}}}}exports.createWorkflowClient=i;//# sourceMappingURL=index.cjs.map
1
+ 'use strict';var httpClient=require('@amaster.ai/http-client');function p(t){if(!t)return {inputs:{},response_mode:"blocking",user:"anonymous"};if(typeof t=="object"&&("inputs"in t||"response_mode"in t||"user"in t||"files"in t||"trace_id"in t)){let o=t;return {inputs:o.inputs||{},response_mode:o.response_mode||"blocking",user:o.user||"anonymous",files:o.files,trace_id:o.trace_id}}return {inputs:t,response_mode:"blocking",user:"anonymous"}}function d(t=httpClient.createHttpClient(),o={}){let{appId:s,env:u}=o;return {async run(i,l){if(!i||i.includes("/"))return {data:null,error:{status:400,message:"Invalid workflowName: use workflow YAML filename without extension (no subpaths)"},status:400};let r=p(l);r.inputs||(r.inputs={}),s&&r.inputs.app_id===void 0&&(r.inputs.app_id=s),u&&r.inputs.env===void 0&&(r.inputs.env=u);let e=await t.request({url:`/api/runworkflow/${i}`,method:"post",headers:{"Content-Type":"application/json",...u?{"x-env":u}:{},...s?{"x-tenant-id":s}:{}},data:r});if(e.data?.data){let n=e.data.data;return {...e,data:{task_id:e.data.task_id||"",workflow_run_id:e.data.workflow_run_id||"",status:n.status||"unknown",outputs:n.outputs||{},error:n.error||null,elapsed_time:n.elapsed_time||0,total_tokens:n.total_tokens||0,total_steps:n.total_steps||0,created_at:n.created_at||0,finished_at:n.finished_at||0}}}return {data:null,error:e.error||{status:e.status,message:"Invalid workflow response structure"},status:e.status}}}}exports.createWorkflowClient=d;//# sourceMappingURL=index.cjs.map
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/workflow-client.ts"],"names":["normalizeRunRequest","inputs","req","createWorkflowClient","http","createHttpClient","workflowName","normalizedRequest","response","innerData"],"mappings":"+DAmDA,SAASA,EACPC,CAAAA,CACoB,CACpB,GAAI,CAACA,CAAAA,CACH,OAAO,CAAE,MAAA,CAAQ,GAAI,aAAA,CAAe,UAAA,CAAY,KAAM,WAAY,CAAA,CAGpE,GACE,OAAOA,CAAAA,EAAW,QAAA,GACjB,WAAYA,CAAAA,EACX,eAAA,GAAmBA,GACnB,MAAA,GAAUA,CAAAA,EACV,UAAWA,CAAAA,EACX,UAAA,GAAcA,CAAAA,CAAAA,CAChB,CACA,IAAMC,CAAAA,CAAMD,EACZ,OAAO,CACL,MAAA,CAAQC,CAAAA,CAAI,MAAA,EAAU,GACtB,aAAA,CAAeA,CAAAA,CAAI,aAAA,EAAiB,UAAA,CACpC,IAAA,CAAMA,CAAAA,CAAI,MAAQ,WAAA,CAClB,KAAA,CAAOA,EAAI,KAAA,CACX,QAAA,CAAUA,EAAI,QAChB,CACF,CAEA,OAAO,CACL,MAAA,CAAQD,EACR,aAAA,CAAe,UAAA,CACf,IAAA,CAAM,WACR,CACF,CAEO,SAASE,CAAAA,CAAqBC,CAAAA,CAAmBC,2BAAAA,EAAiB,CAAmB,CAC1F,OAAO,CACL,MAAM,GAAA,CACJC,EACAL,CAAAA,CACqD,CACrD,GAAI,CAACK,CAAAA,EAAgBA,CAAAA,CAAa,QAAA,CAAS,GAAG,CAAA,CAC5C,OAAO,CACL,IAAA,CAAM,IAAA,CACN,KAAA,CAAO,CACL,MAAA,CAAQ,IACR,OAAA,CACE,kFACJ,CAAA,CACA,MAAA,CAAQ,GACV,CAAA,CAGF,IAAMC,CAAAA,CAAoBP,CAAAA,CAAoBC,CAAM,CAAA,CAS9CO,CAAAA,CAAW,MAAMJ,CAAAA,CAAK,OAAA,CAazB,CACD,GAAA,CAAK,CAAA,iBAAA,EAAoBE,CAAY,GACrC,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CAAE,cAAA,CAAgB,kBAAmB,EAC9C,IAAA,CAAMC,CACR,CAAC,CAAA,CAED,GAAIC,CAAAA,CAAS,MAAM,IAAA,CAAM,CACvB,IAAMC,CAAAA,CAAYD,CAAAA,CAAS,KAAK,IAAA,CAChC,OAAO,CACL,GAAGA,CAAAA,CACH,IAAA,CAAM,CACJ,OAAA,CAASA,CAAAA,CAAS,IAAA,CAAK,OAAA,EAAW,EAAA,CAClC,eAAA,CAAiBA,EAAS,IAAA,CAAK,eAAA,EAAmB,EAAA,CAClD,MAAA,CAAQC,CAAAA,CAAU,MAAA,EAAU,UAC5B,OAAA,CAASA,CAAAA,CAAU,SAAY,EAAC,CAChC,MAAOA,CAAAA,CAAU,KAAA,EAAS,IAAA,CAC1B,YAAA,CAAcA,CAAAA,CAAU,YAAA,EAAgB,EACxC,YAAA,CAAcA,CAAAA,CAAU,YAAA,EAAgB,CAAA,CACxC,WAAA,CAAaA,CAAAA,CAAU,aAAe,CAAA,CACtC,UAAA,CAAYA,CAAAA,CAAU,UAAA,EAAc,CAAA,CACpC,WAAA,CAAaA,EAAU,WAAA,EAAe,CACxC,CACF,CACF,CAEA,OAAO,CACL,IAAA,CAAM,IAAA,CACN,KAAA,CAAOD,CAAAA,CAAS,KAAA,EAAS,CACvB,MAAA,CAAQA,CAAAA,CAAS,MAAA,CACjB,OAAA,CAAS,qCACX,CAAA,CACA,OAAQA,CAAAA,CAAS,MACnB,CACF,CACF,CACF","file":"index.cjs","sourcesContent":["import { type ClientResult, createHttpClient, type HttpClient } from \"@amaster.ai/http-client\";\n\n// extractAppIdFromUrl removed — app_id now injected by Traefik middleware (X-App-ID header)\n// via scheduler's dynamic route creation in etcd\n\nexport type WorkflowResponseMode = \"blocking\" | \"streaming\";\n\nexport type WorkflowInputValue =\n | string\n | number\n | boolean\n | null\n | undefined\n | Record<string, unknown>\n | unknown[];\n\nexport type WorkflowFile = {\n name?: string;\n type?: string;\n url?: string;\n [key: string]: unknown;\n};\n\nexport type WorkflowRunRequest = {\n inputs?: Record<string, WorkflowInputValue>;\n response_mode?: WorkflowResponseMode;\n user?: string;\n files?: WorkflowFile[];\n trace_id?: string;\n};\n\nexport type WorkflowRunResponse<TOutput = Record<string, unknown>> = {\n task_id: string;\n workflow_run_id: string;\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n};\n\nexport type WorkflowClient = {\n run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;\n};\n\nfunction normalizeRunRequest(\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n): WorkflowRunRequest {\n if (!inputs) {\n return { inputs: {}, response_mode: \"blocking\", user: \"anonymous\" };\n }\n\n if (\n typeof inputs === \"object\" &&\n (\"inputs\" in inputs ||\n \"response_mode\" in inputs ||\n \"user\" in inputs ||\n \"files\" in inputs ||\n \"trace_id\" in inputs)\n ) {\n const req = inputs as WorkflowRunRequest;\n return {\n inputs: req.inputs || {},\n response_mode: req.response_mode || \"blocking\",\n user: req.user || \"anonymous\",\n files: req.files,\n trace_id: req.trace_id,\n };\n }\n\n return {\n inputs: inputs as Record<string, WorkflowInputValue>,\n response_mode: \"blocking\",\n user: \"anonymous\",\n };\n}\n\nexport function createWorkflowClient(http: HttpClient = createHttpClient()): WorkflowClient {\n return {\n async run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>> {\n if (!workflowName || workflowName.includes(\"/\")) {\n return {\n data: null,\n error: {\n status: 400,\n message:\n \"Invalid workflowName: use workflow YAML filename without extension (no subpaths)\",\n },\n status: 400,\n };\n }\n\n const normalizedRequest = normalizeRunRequest(inputs);\n\n // app_id is now injected by Traefik middleware via X-App-ID header,\n // no longer extracted from URL (which incorrectly included env suffix).\n // const appId = extractAppIdFromUrl();\n // if (appId && normalizedRequest.inputs) {\n // normalizedRequest.inputs.app_id = appId;\n // }\n\n const response = await http.request<{\n data: {\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n };\n task_id: string;\n workflow_run_id: string;\n }>({\n url: `/api/runworkflow/${workflowName}`,\n method: \"post\",\n headers: { \"Content-Type\": \"application/json\" },\n data: normalizedRequest,\n });\n\n if (response.data?.data) {\n const innerData = response.data.data;\n return {\n ...response,\n data: {\n task_id: response.data.task_id || \"\",\n workflow_run_id: response.data.workflow_run_id || \"\",\n status: innerData.status || \"unknown\",\n outputs: innerData.outputs || ({} as TOutput),\n error: innerData.error || null,\n elapsed_time: innerData.elapsed_time || 0,\n total_tokens: innerData.total_tokens || 0,\n total_steps: innerData.total_steps || 0,\n created_at: innerData.created_at || 0,\n finished_at: innerData.finished_at || 0,\n },\n };\n }\n\n return {\n data: null,\n error: response.error || {\n status: response.status,\n message: \"Invalid workflow response structure\",\n },\n status: response.status,\n };\n },\n };\n}\n"]}
1
+ {"version":3,"sources":["../src/workflow-client.ts"],"names":["normalizeRunRequest","inputs","req","createWorkflowClient","http","createHttpClient","options","appId","env","workflowName","normalizedRequest","response","innerData"],"mappings":"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","file":"index.cjs","sourcesContent":["import { type ClientResult, createHttpClient, type HttpClient } from \"@amaster.ai/http-client\";\n\n// extractAppIdFromUrl removed — app_id now injected by Traefik middleware (X-App-ID header)\n// via scheduler's dynamic route creation in etcd\n\nexport type WorkflowResponseMode = \"blocking\" | \"streaming\";\n\nexport type WorkflowInputValue =\n | string\n | number\n | boolean\n | null\n | undefined\n | Record<string, unknown>\n | unknown[];\n\nexport type WorkflowFile = {\n name?: string;\n type?: string;\n url?: string;\n [key: string]: unknown;\n};\n\nexport type WorkflowRunRequest = {\n inputs?: Record<string, WorkflowInputValue>;\n response_mode?: WorkflowResponseMode;\n user?: string;\n files?: WorkflowFile[];\n trace_id?: string;\n};\n\nexport type WorkflowRunResponse<TOutput = Record<string, unknown>> = {\n task_id: string;\n workflow_run_id: string;\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n};\n\nexport type WorkflowClient = {\n run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;\n};\n\nexport type WorkflowClientOptions = {\n appId?: string;\n env?: string;\n};\n\nfunction normalizeRunRequest(\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n): WorkflowRunRequest {\n if (!inputs) {\n return { inputs: {}, response_mode: \"blocking\", user: \"anonymous\" };\n }\n\n if (\n typeof inputs === \"object\" &&\n (\"inputs\" in inputs ||\n \"response_mode\" in inputs ||\n \"user\" in inputs ||\n \"files\" in inputs ||\n \"trace_id\" in inputs)\n ) {\n const req = inputs as WorkflowRunRequest;\n return {\n inputs: req.inputs || {},\n response_mode: req.response_mode || \"blocking\",\n user: req.user || \"anonymous\",\n files: req.files,\n trace_id: req.trace_id,\n };\n }\n\n return {\n inputs: inputs as Record<string, WorkflowInputValue>,\n response_mode: \"blocking\",\n user: \"anonymous\",\n };\n}\n\nexport function createWorkflowClient(\n http: HttpClient = createHttpClient(),\n options: WorkflowClientOptions = {}\n): WorkflowClient {\n const { appId, env } = options;\n\n return {\n async run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>> {\n if (!workflowName || workflowName.includes(\"/\")) {\n return {\n data: null,\n error: {\n status: 400,\n message:\n \"Invalid workflowName: use workflow YAML filename without extension (no subpaths)\",\n },\n status: 400,\n };\n }\n\n const normalizedRequest = normalizeRunRequest(inputs);\n\n if (!normalizedRequest.inputs) {\n normalizedRequest.inputs = {};\n }\n\n if (appId && normalizedRequest.inputs.app_id === undefined) {\n normalizedRequest.inputs.app_id = appId;\n }\n\n if (env && normalizedRequest.inputs.env === undefined) {\n normalizedRequest.inputs.env = env;\n }\n\n // Workflow callers can now provide appId/env through createWorkflowClient\n // so downstream workflows can wire direct model/entity headers from the\n // real runtime context without re-parsing browser URLs here.\n\n const response = await http.request<{\n data: {\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n };\n task_id: string;\n workflow_run_id: string;\n }>({\n url: `/api/runworkflow/${workflowName}`,\n method: \"post\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(env ? { \"x-env\": env } : {}),\n ...(appId ? { \"x-tenant-id\": appId } : {}),\n },\n data: normalizedRequest,\n });\n\n if (response.data?.data) {\n const innerData = response.data.data;\n return {\n ...response,\n data: {\n task_id: response.data.task_id || \"\",\n workflow_run_id: response.data.workflow_run_id || \"\",\n status: innerData.status || \"unknown\",\n outputs: innerData.outputs || ({} as TOutput),\n error: innerData.error || null,\n elapsed_time: innerData.elapsed_time || 0,\n total_tokens: innerData.total_tokens || 0,\n total_steps: innerData.total_steps || 0,\n created_at: innerData.created_at || 0,\n finished_at: innerData.finished_at || 0,\n },\n };\n }\n\n return {\n data: null,\n error: response.error || {\n status: response.status,\n message: \"Invalid workflow response structure\",\n },\n status: response.status,\n };\n },\n };\n}\n"]}
package/dist/index.d.cts CHANGED
@@ -30,6 +30,10 @@ type WorkflowRunResponse<TOutput = Record<string, unknown>> = {
30
30
  type WorkflowClient = {
31
31
  run<TOutput = Record<string, unknown>>(workflowName: string, inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;
32
32
  };
33
- declare function createWorkflowClient(http?: HttpClient): WorkflowClient;
33
+ type WorkflowClientOptions = {
34
+ appId?: string;
35
+ env?: string;
36
+ };
37
+ declare function createWorkflowClient(http?: HttpClient, options?: WorkflowClientOptions): WorkflowClient;
34
38
 
35
- export { type WorkflowClient, type WorkflowFile, type WorkflowInputValue, type WorkflowResponseMode, type WorkflowRunRequest, type WorkflowRunResponse, createWorkflowClient };
39
+ export { type WorkflowClient, type WorkflowClientOptions, type WorkflowFile, type WorkflowInputValue, type WorkflowResponseMode, type WorkflowRunRequest, type WorkflowRunResponse, createWorkflowClient };
package/dist/index.d.ts CHANGED
@@ -30,6 +30,10 @@ type WorkflowRunResponse<TOutput = Record<string, unknown>> = {
30
30
  type WorkflowClient = {
31
31
  run<TOutput = Record<string, unknown>>(workflowName: string, inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;
32
32
  };
33
- declare function createWorkflowClient(http?: HttpClient): WorkflowClient;
33
+ type WorkflowClientOptions = {
34
+ appId?: string;
35
+ env?: string;
36
+ };
37
+ declare function createWorkflowClient(http?: HttpClient, options?: WorkflowClientOptions): WorkflowClient;
34
38
 
35
- export { type WorkflowClient, type WorkflowFile, type WorkflowInputValue, type WorkflowResponseMode, type WorkflowRunRequest, type WorkflowRunResponse, createWorkflowClient };
39
+ export { type WorkflowClient, type WorkflowClientOptions, type WorkflowFile, type WorkflowInputValue, type WorkflowResponseMode, type WorkflowRunRequest, type WorkflowRunResponse, createWorkflowClient };
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- import {createHttpClient}from'@amaster.ai/http-client';function l(e){if(!e)return {inputs:{},response_mode:"blocking",user:"anonymous"};if(typeof e=="object"&&("inputs"in e||"response_mode"in e||"user"in e||"files"in e||"trace_id"in e)){let t=e;return {inputs:t.inputs||{},response_mode:t.response_mode||"blocking",user:t.user||"anonymous",files:t.files,trace_id:t.trace_id}}return {inputs:e,response_mode:"blocking",user:"anonymous"}}function i(e=createHttpClient()){return {async run(t,n){if(!t||t.includes("/"))return {data:null,error:{status:400,message:"Invalid workflowName: use workflow YAML filename without extension (no subpaths)"},status:400};let s=l(n),o=await e.request({url:`/api/runworkflow/${t}`,method:"post",headers:{"Content-Type":"application/json"},data:s});if(o.data?.data){let r=o.data.data;return {...o,data:{task_id:o.data.task_id||"",workflow_run_id:o.data.workflow_run_id||"",status:r.status||"unknown",outputs:r.outputs||{},error:r.error||null,elapsed_time:r.elapsed_time||0,total_tokens:r.total_tokens||0,total_steps:r.total_steps||0,created_at:r.created_at||0,finished_at:r.finished_at||0}}}return {data:null,error:o.error||{status:o.status,message:"Invalid workflow response structure"},status:o.status}}}}export{i as createWorkflowClient};//# sourceMappingURL=index.js.map
1
+ import {createHttpClient}from'@amaster.ai/http-client';function p(t){if(!t)return {inputs:{},response_mode:"blocking",user:"anonymous"};if(typeof t=="object"&&("inputs"in t||"response_mode"in t||"user"in t||"files"in t||"trace_id"in t)){let o=t;return {inputs:o.inputs||{},response_mode:o.response_mode||"blocking",user:o.user||"anonymous",files:o.files,trace_id:o.trace_id}}return {inputs:t,response_mode:"blocking",user:"anonymous"}}function d(t=createHttpClient(),o={}){let{appId:s,env:u}=o;return {async run(i,l){if(!i||i.includes("/"))return {data:null,error:{status:400,message:"Invalid workflowName: use workflow YAML filename without extension (no subpaths)"},status:400};let r=p(l);r.inputs||(r.inputs={}),s&&r.inputs.app_id===void 0&&(r.inputs.app_id=s),u&&r.inputs.env===void 0&&(r.inputs.env=u);let e=await t.request({url:`/api/runworkflow/${i}`,method:"post",headers:{"Content-Type":"application/json",...u?{"x-env":u}:{},...s?{"x-tenant-id":s}:{}},data:r});if(e.data?.data){let n=e.data.data;return {...e,data:{task_id:e.data.task_id||"",workflow_run_id:e.data.workflow_run_id||"",status:n.status||"unknown",outputs:n.outputs||{},error:n.error||null,elapsed_time:n.elapsed_time||0,total_tokens:n.total_tokens||0,total_steps:n.total_steps||0,created_at:n.created_at||0,finished_at:n.finished_at||0}}}return {data:null,error:e.error||{status:e.status,message:"Invalid workflow response structure"},status:e.status}}}}export{d as createWorkflowClient};//# sourceMappingURL=index.js.map
2
2
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/workflow-client.ts"],"names":["normalizeRunRequest","inputs","req","createWorkflowClient","http","createHttpClient","workflowName","normalizedRequest","response","innerData"],"mappings":"uDAmDA,SAASA,EACPC,CAAAA,CACoB,CACpB,GAAI,CAACA,CAAAA,CACH,OAAO,CAAE,MAAA,CAAQ,GAAI,aAAA,CAAe,UAAA,CAAY,KAAM,WAAY,CAAA,CAGpE,GACE,OAAOA,CAAAA,EAAW,QAAA,GACjB,WAAYA,CAAAA,EACX,eAAA,GAAmBA,GACnB,MAAA,GAAUA,CAAAA,EACV,UAAWA,CAAAA,EACX,UAAA,GAAcA,CAAAA,CAAAA,CAChB,CACA,IAAMC,CAAAA,CAAMD,EACZ,OAAO,CACL,MAAA,CAAQC,CAAAA,CAAI,MAAA,EAAU,GACtB,aAAA,CAAeA,CAAAA,CAAI,aAAA,EAAiB,UAAA,CACpC,IAAA,CAAMA,CAAAA,CAAI,MAAQ,WAAA,CAClB,KAAA,CAAOA,EAAI,KAAA,CACX,QAAA,CAAUA,EAAI,QAChB,CACF,CAEA,OAAO,CACL,MAAA,CAAQD,EACR,aAAA,CAAe,UAAA,CACf,IAAA,CAAM,WACR,CACF,CAEO,SAASE,CAAAA,CAAqBC,CAAAA,CAAmBC,gBAAAA,EAAiB,CAAmB,CAC1F,OAAO,CACL,MAAM,GAAA,CACJC,EACAL,CAAAA,CACqD,CACrD,GAAI,CAACK,CAAAA,EAAgBA,CAAAA,CAAa,QAAA,CAAS,GAAG,CAAA,CAC5C,OAAO,CACL,IAAA,CAAM,IAAA,CACN,KAAA,CAAO,CACL,MAAA,CAAQ,IACR,OAAA,CACE,kFACJ,CAAA,CACA,MAAA,CAAQ,GACV,CAAA,CAGF,IAAMC,CAAAA,CAAoBP,CAAAA,CAAoBC,CAAM,CAAA,CAS9CO,CAAAA,CAAW,MAAMJ,CAAAA,CAAK,OAAA,CAazB,CACD,GAAA,CAAK,CAAA,iBAAA,EAAoBE,CAAY,GACrC,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CAAE,cAAA,CAAgB,kBAAmB,EAC9C,IAAA,CAAMC,CACR,CAAC,CAAA,CAED,GAAIC,CAAAA,CAAS,MAAM,IAAA,CAAM,CACvB,IAAMC,CAAAA,CAAYD,CAAAA,CAAS,KAAK,IAAA,CAChC,OAAO,CACL,GAAGA,CAAAA,CACH,IAAA,CAAM,CACJ,OAAA,CAASA,CAAAA,CAAS,IAAA,CAAK,OAAA,EAAW,EAAA,CAClC,eAAA,CAAiBA,EAAS,IAAA,CAAK,eAAA,EAAmB,EAAA,CAClD,MAAA,CAAQC,CAAAA,CAAU,MAAA,EAAU,UAC5B,OAAA,CAASA,CAAAA,CAAU,SAAY,EAAC,CAChC,MAAOA,CAAAA,CAAU,KAAA,EAAS,IAAA,CAC1B,YAAA,CAAcA,CAAAA,CAAU,YAAA,EAAgB,EACxC,YAAA,CAAcA,CAAAA,CAAU,YAAA,EAAgB,CAAA,CACxC,WAAA,CAAaA,CAAAA,CAAU,aAAe,CAAA,CACtC,UAAA,CAAYA,CAAAA,CAAU,UAAA,EAAc,CAAA,CACpC,WAAA,CAAaA,EAAU,WAAA,EAAe,CACxC,CACF,CACF,CAEA,OAAO,CACL,IAAA,CAAM,IAAA,CACN,KAAA,CAAOD,CAAAA,CAAS,KAAA,EAAS,CACvB,MAAA,CAAQA,CAAAA,CAAS,MAAA,CACjB,OAAA,CAAS,qCACX,CAAA,CACA,OAAQA,CAAAA,CAAS,MACnB,CACF,CACF,CACF","file":"index.js","sourcesContent":["import { type ClientResult, createHttpClient, type HttpClient } from \"@amaster.ai/http-client\";\n\n// extractAppIdFromUrl removed — app_id now injected by Traefik middleware (X-App-ID header)\n// via scheduler's dynamic route creation in etcd\n\nexport type WorkflowResponseMode = \"blocking\" | \"streaming\";\n\nexport type WorkflowInputValue =\n | string\n | number\n | boolean\n | null\n | undefined\n | Record<string, unknown>\n | unknown[];\n\nexport type WorkflowFile = {\n name?: string;\n type?: string;\n url?: string;\n [key: string]: unknown;\n};\n\nexport type WorkflowRunRequest = {\n inputs?: Record<string, WorkflowInputValue>;\n response_mode?: WorkflowResponseMode;\n user?: string;\n files?: WorkflowFile[];\n trace_id?: string;\n};\n\nexport type WorkflowRunResponse<TOutput = Record<string, unknown>> = {\n task_id: string;\n workflow_run_id: string;\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n};\n\nexport type WorkflowClient = {\n run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;\n};\n\nfunction normalizeRunRequest(\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n): WorkflowRunRequest {\n if (!inputs) {\n return { inputs: {}, response_mode: \"blocking\", user: \"anonymous\" };\n }\n\n if (\n typeof inputs === \"object\" &&\n (\"inputs\" in inputs ||\n \"response_mode\" in inputs ||\n \"user\" in inputs ||\n \"files\" in inputs ||\n \"trace_id\" in inputs)\n ) {\n const req = inputs as WorkflowRunRequest;\n return {\n inputs: req.inputs || {},\n response_mode: req.response_mode || \"blocking\",\n user: req.user || \"anonymous\",\n files: req.files,\n trace_id: req.trace_id,\n };\n }\n\n return {\n inputs: inputs as Record<string, WorkflowInputValue>,\n response_mode: \"blocking\",\n user: \"anonymous\",\n };\n}\n\nexport function createWorkflowClient(http: HttpClient = createHttpClient()): WorkflowClient {\n return {\n async run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>> {\n if (!workflowName || workflowName.includes(\"/\")) {\n return {\n data: null,\n error: {\n status: 400,\n message:\n \"Invalid workflowName: use workflow YAML filename without extension (no subpaths)\",\n },\n status: 400,\n };\n }\n\n const normalizedRequest = normalizeRunRequest(inputs);\n\n // app_id is now injected by Traefik middleware via X-App-ID header,\n // no longer extracted from URL (which incorrectly included env suffix).\n // const appId = extractAppIdFromUrl();\n // if (appId && normalizedRequest.inputs) {\n // normalizedRequest.inputs.app_id = appId;\n // }\n\n const response = await http.request<{\n data: {\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n };\n task_id: string;\n workflow_run_id: string;\n }>({\n url: `/api/runworkflow/${workflowName}`,\n method: \"post\",\n headers: { \"Content-Type\": \"application/json\" },\n data: normalizedRequest,\n });\n\n if (response.data?.data) {\n const innerData = response.data.data;\n return {\n ...response,\n data: {\n task_id: response.data.task_id || \"\",\n workflow_run_id: response.data.workflow_run_id || \"\",\n status: innerData.status || \"unknown\",\n outputs: innerData.outputs || ({} as TOutput),\n error: innerData.error || null,\n elapsed_time: innerData.elapsed_time || 0,\n total_tokens: innerData.total_tokens || 0,\n total_steps: innerData.total_steps || 0,\n created_at: innerData.created_at || 0,\n finished_at: innerData.finished_at || 0,\n },\n };\n }\n\n return {\n data: null,\n error: response.error || {\n status: response.status,\n message: \"Invalid workflow response structure\",\n },\n status: response.status,\n };\n },\n };\n}\n"]}
1
+ {"version":3,"sources":["../src/workflow-client.ts"],"names":["normalizeRunRequest","inputs","req","createWorkflowClient","http","createHttpClient","options","appId","env","workflowName","normalizedRequest","response","innerData"],"mappings":"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","file":"index.js","sourcesContent":["import { type ClientResult, createHttpClient, type HttpClient } from \"@amaster.ai/http-client\";\n\n// extractAppIdFromUrl removed — app_id now injected by Traefik middleware (X-App-ID header)\n// via scheduler's dynamic route creation in etcd\n\nexport type WorkflowResponseMode = \"blocking\" | \"streaming\";\n\nexport type WorkflowInputValue =\n | string\n | number\n | boolean\n | null\n | undefined\n | Record<string, unknown>\n | unknown[];\n\nexport type WorkflowFile = {\n name?: string;\n type?: string;\n url?: string;\n [key: string]: unknown;\n};\n\nexport type WorkflowRunRequest = {\n inputs?: Record<string, WorkflowInputValue>;\n response_mode?: WorkflowResponseMode;\n user?: string;\n files?: WorkflowFile[];\n trace_id?: string;\n};\n\nexport type WorkflowRunResponse<TOutput = Record<string, unknown>> = {\n task_id: string;\n workflow_run_id: string;\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n};\n\nexport type WorkflowClient = {\n run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>>;\n};\n\nexport type WorkflowClientOptions = {\n appId?: string;\n env?: string;\n};\n\nfunction normalizeRunRequest(\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n): WorkflowRunRequest {\n if (!inputs) {\n return { inputs: {}, response_mode: \"blocking\", user: \"anonymous\" };\n }\n\n if (\n typeof inputs === \"object\" &&\n (\"inputs\" in inputs ||\n \"response_mode\" in inputs ||\n \"user\" in inputs ||\n \"files\" in inputs ||\n \"trace_id\" in inputs)\n ) {\n const req = inputs as WorkflowRunRequest;\n return {\n inputs: req.inputs || {},\n response_mode: req.response_mode || \"blocking\",\n user: req.user || \"anonymous\",\n files: req.files,\n trace_id: req.trace_id,\n };\n }\n\n return {\n inputs: inputs as Record<string, WorkflowInputValue>,\n response_mode: \"blocking\",\n user: \"anonymous\",\n };\n}\n\nexport function createWorkflowClient(\n http: HttpClient = createHttpClient(),\n options: WorkflowClientOptions = {}\n): WorkflowClient {\n const { appId, env } = options;\n\n return {\n async run<TOutput = Record<string, unknown>>(\n workflowName: string,\n inputs?: Record<string, WorkflowInputValue> | WorkflowRunRequest\n ): Promise<ClientResult<WorkflowRunResponse<TOutput>>> {\n if (!workflowName || workflowName.includes(\"/\")) {\n return {\n data: null,\n error: {\n status: 400,\n message:\n \"Invalid workflowName: use workflow YAML filename without extension (no subpaths)\",\n },\n status: 400,\n };\n }\n\n const normalizedRequest = normalizeRunRequest(inputs);\n\n if (!normalizedRequest.inputs) {\n normalizedRequest.inputs = {};\n }\n\n if (appId && normalizedRequest.inputs.app_id === undefined) {\n normalizedRequest.inputs.app_id = appId;\n }\n\n if (env && normalizedRequest.inputs.env === undefined) {\n normalizedRequest.inputs.env = env;\n }\n\n // Workflow callers can now provide appId/env through createWorkflowClient\n // so downstream workflows can wire direct model/entity headers from the\n // real runtime context without re-parsing browser URLs here.\n\n const response = await http.request<{\n data: {\n status: string;\n outputs: TOutput;\n error: string | null;\n elapsed_time: number;\n total_tokens: number;\n total_steps: number;\n created_at: number;\n finished_at: number;\n };\n task_id: string;\n workflow_run_id: string;\n }>({\n url: `/api/runworkflow/${workflowName}`,\n method: \"post\",\n headers: {\n \"Content-Type\": \"application/json\",\n ...(env ? { \"x-env\": env } : {}),\n ...(appId ? { \"x-tenant-id\": appId } : {}),\n },\n data: normalizedRequest,\n });\n\n if (response.data?.data) {\n const innerData = response.data.data;\n return {\n ...response,\n data: {\n task_id: response.data.task_id || \"\",\n workflow_run_id: response.data.workflow_run_id || \"\",\n status: innerData.status || \"unknown\",\n outputs: innerData.outputs || ({} as TOutput),\n error: innerData.error || null,\n elapsed_time: innerData.elapsed_time || 0,\n total_tokens: innerData.total_tokens || 0,\n total_steps: innerData.total_steps || 0,\n created_at: innerData.created_at || 0,\n finished_at: innerData.finished_at || 0,\n },\n };\n }\n\n return {\n data: null,\n error: response.error || {\n status: response.status,\n message: \"Invalid workflow response structure\",\n },\n status: response.status,\n };\n },\n };\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@amaster.ai/workflow-client",
3
- "version": "1.1.0-beta.73",
3
+ "version": "1.1.0-beta.75",
4
4
  "description": "Workflow execution client",
5
5
  "type": "module",
6
6
  "main": "./dist/index.cjs",
@@ -30,7 +30,7 @@
30
30
  "registry": "https://registry.npmjs.org/"
31
31
  },
32
32
  "dependencies": {
33
- "@amaster.ai/http-client": "1.1.0-beta.73"
33
+ "@amaster.ai/http-client": "1.1.0-beta.75"
34
34
  },
35
35
  "peerDependencies": {
36
36
  "axios": "^1.11.0"