@epam/ai-dial-chat-hooks 1.2.0-dev.3 → 1.2.0-dev.303

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 (104) hide show
  1. package/api-error/api-error.js +7 -4
  2. package/attachment/useAttachmentValidation/useAttachmentValidation.js +26 -19
  3. package/attachments.d.ts +10 -4
  4. package/catalog/catalog-derivations.js +1 -1
  5. package/catalog/deployment-id.js +8 -2
  6. package/catalog/map-deployment-limits-to-catalog.js +16 -24
  7. package/catalog/map-deployment-limits-to-input.js +81 -9
  8. package/catalog/map-deployment-to-catalog-item.js +34 -34
  9. package/catalog/map-entity-details-to-catalog.js +7 -0
  10. package/catalog/map-skill-to-catalog-item.js +55 -48
  11. package/catalog/publish.js +6 -5
  12. package/catalog/useApplicationCredentials/useApplicationCredentials.js +39 -0
  13. package/catalog/useCatalogEditNavigation/useCatalogEditNavigation.js +122 -101
  14. package/catalog/usePublishFolders/usePublishFolders.js +1 -1
  15. package/catalog/useSkillDetailsPanelData/useSkillDetailsPanelData.js +39 -39
  16. package/catalog/useSkillItemDetails.js +19 -17
  17. package/catalog.d.ts +159 -35
  18. package/catalog.js +23 -22
  19. package/conversation/announcement-message.js +16 -5
  20. package/conversation/conversation-transfer/export-conversation.js +24 -16
  21. package/conversation/conversation-transfer/import-conversation.js +80 -31
  22. package/conversation/conversation-transfer/queue.js +8 -5
  23. package/conversation/create-chat-stream-api.js +85 -49
  24. package/conversation/message-utils.js +44 -2
  25. package/conversation/stage.js +27 -0
  26. package/conversation/useActiveConversationSync/useActiveConversationSync.js +7 -8
  27. package/conversation/useAttachmentUpload/useAttachmentUpload.js +12 -5
  28. package/conversation/useConversationExport/useConversationExport.js +9 -9
  29. package/conversation/useConversationHandlers/message-utils.js +8 -5
  30. package/conversation/useConversationHandlers/useConversationHandlers.js +187 -177
  31. package/conversation/useConversationImport/useConversationImport.js +123 -121
  32. package/conversation/useConversationPanelItems/useConversationPanelItems.js +50 -32
  33. package/conversation/useConversationScroll/useConversationScroll.js +68 -64
  34. package/conversation/useConversationStream/apply-chunk.js +1 -1
  35. package/conversation/useConversationStream/frame-scheduler.js +39 -0
  36. package/conversation/useConversationStream/generation-resume.js +122 -64
  37. package/conversation/useConversationStream/useConversationStream.js +279 -116
  38. package/conversation/useMessageSelectionReply/useMessageSelectionReply.js +189 -0
  39. package/conversation/useTranscribeAudio/transcription-retry.js +5 -4
  40. package/conversation-overlay.d.ts +7 -0
  41. package/conversation-overlay.js +2 -0
  42. package/conversation-sources/useConversationSources/useConversationSources.js +31 -24
  43. package/conversation-sources.d.ts +1 -1
  44. package/conversation-transfer.d.ts +2 -1
  45. package/conversation.d.ts +328 -25
  46. package/conversation.js +32 -30
  47. package/file-manager-canvas.d.ts +418 -0
  48. package/file-manager-canvas.js +2 -0
  49. package/file-manager.d.ts +155 -359
  50. package/file-manager.js +25 -24
  51. package/files/attachment-canvas.js +116 -55
  52. package/files/attachment-types.js +14 -13
  53. package/files/dial-file-manager-copy-move.util.js +9 -8
  54. package/files/dial-file-manager-mapping.util.js +2 -1
  55. package/files/dial-file-manager-path.util.js +24 -2
  56. package/files/dial-file-manager.model.js +23 -19
  57. package/files/dial-file-manager.types.js +3 -3
  58. package/files/file-manager-variant.js +1 -1
  59. package/files/resolve-dial-file-api-path.js +11 -12
  60. package/files/useDialFileListing/useDialFileListing.js +140 -127
  61. package/files/useDialFileManager/useDialFileManager.js +139 -135
  62. package/files/useDialFileManagerSections/useDialFileManagerSections.js +155 -0
  63. package/files/useDialFileManagerTabConfig/useDialFileManagerTabConfig.js +20 -19
  64. package/files/useDialFileMutations/useDialFileMutations.js +65 -60
  65. package/files/useDialFileUploadBatch/useDialFileUploadBatch.js +117 -110
  66. package/files/useFileAttachmentPicker/useFileAttachmentPicker.js +48 -0
  67. package/index.d.ts +1281 -136
  68. package/index.js +136 -122
  69. package/mcp-apps/useMcpAppHostAdapter/useMcpAppHostAdapter.js +7 -5
  70. package/mcp-apps/useMcpAppHostContext/useMcpAppHostContext.js +1 -1
  71. package/mcp-apps/useMcpAppTools/useMcpAppTools.js +1 -1
  72. package/mcp-apps/useOpenMcpAppCanvas/useOpenMcpAppCanvas.js +25 -23
  73. package/mcp-apps.d.ts +8 -6
  74. package/oauth/toolset-id.js +5 -3
  75. package/oauth/useToolsetLogin/useToolsetLogin.js +8 -8
  76. package/oauth.d.ts +32 -0
  77. package/oauth.js +9 -9
  78. package/package.json +38 -23
  79. package/scheduled-task/scheduled-task-description.js +81 -0
  80. package/scheduled-task/scheduled-task-preparation.js +24 -0
  81. package/scheduled-task/scheduled-task-trigger.js +74 -71
  82. package/scheduled-task/scheduled-tasks-api-client.js +19 -0
  83. package/scheduled-task/use-scheduled-task-runs.js +194 -0
  84. package/scheduled-task/use-scheduled-tasks.js +93 -0
  85. package/scheduled-tasks.d.ts +197 -3
  86. package/scheduled-tasks.js +7 -2
  87. package/shared/application-schema.js +5 -2
  88. package/shared/cron-day-of-month.js +13 -0
  89. package/skill/skill-archive.js +19 -0
  90. package/skill/skill-types.js +8 -7
  91. package/skill/skill.js +53 -27
  92. package/skill/useSkillArchiveImport/useSkillArchiveImport.js +79 -0
  93. package/skill/useSkillEditorLoad.js +65 -59
  94. package/skill/useSkillEditorSubmit.js +108 -84
  95. package/skill/useSkillFileActions.js +70 -58
  96. package/skill-editor.d.ts +160 -8
  97. package/skill-editor.js +9 -8
  98. package/usage/map-usage-data-to-dashboard.js +66 -0
  99. package/usage/map-user-usage-to-model-limits.js +202 -0
  100. package/usage.d.ts +125 -0
  101. package/usage.js +3 -0
  102. package/usePageFileDrag/usePageFileDrag.js +3 -3
  103. package/utils.d.ts +26 -6
  104. package/utils.js +10 -10
@@ -1,4 +1,5 @@
1
- import { OAuthResourceKind as e, ToolsetAuthStatus as t, ToolsetAuthTypes as n, ToolsetCredentialsLevel as r, ToolsetOAuthInitiationResultType as i, ToolsetOAuthResultType as a } from "../types.js";
1
+ import { OAuthResourceKind as e, ToolsetAuthStatus as t, ToolsetAuthTypes as n, ToolsetOAuthInitiationResultType as r, ToolsetOAuthResultType as i } from "../types.js";
2
+ import { selectToolsetAuthStatus as a } from "../toolset-id.js";
2
3
  import { emitToolsetLoginSuccess as o } from "../../shared/toolset-login-events.js";
3
4
  import { waitForToolsetOAuthResult as s } from "../handshake.js";
4
5
  import { initiateOAuthLogin as c, navigateToolsetOAuthPopup as l, openToolsetOAuthPopup as u } from "../popup.js";
@@ -24,23 +25,22 @@ var f = /* @__PURE__ */ function(e) {
24
25
  codeChallengeMethod: _?.codeChallengeMethod
25
26
  }, x = v ? await (async () => {
26
27
  let t = u();
27
- return t ? (await g(p, m, n.OAuth), l(t, b, p, f, m, e.Toolset, y)) : { type: i.Blocked };
28
+ return t ? (await g(p, m, n.OAuth), l(t, b, p, f, m, e.Toolset, y)) : { type: r.Blocked };
28
29
  })() : c(b, p, f, m, y);
29
- if (x.type === i.Blocked) return { type: "popup-blocked" };
30
- if (x.type !== i.Started) return { type: "failure" };
30
+ if (x.type === r.Blocked) return { type: "popup-blocked" };
31
+ if (x.type !== r.Started) return { type: "failure" };
31
32
  let S = await s(x.popup, x.flowId, {
32
33
  toolsetId: p,
33
34
  credentialsLevel: m,
34
35
  callbackPath: f
35
36
  });
36
- if (S.type === a.Success) return o({
37
+ if (S.type === i.Success) return o({
37
38
  toolsetId: p,
38
39
  credentialsLevel: m
39
40
  }), { type: "success" };
40
- if (S.type === a.Failure) return { type: "failure" };
41
+ if (S.type === i.Failure) return { type: "failure" };
41
42
  try {
42
- let e = await h(p);
43
- if ((m === r.User ? e.authSettings?.userLevelAuthStatus : e.authSettings?.globalAuthStatus) === t.SignedIn) return o({
43
+ if (a((await h(p)).authSettings, m) === t.SignedIn) return o({
44
44
  toolsetId: p,
45
45
  credentialsLevel: m
46
46
  }), { type: "success" };
package/oauth.d.ts CHANGED
@@ -1,3 +1,4 @@
1
+ import { DialToolsetAuthSettingsDto } from '@epam/ai-dial-chat-api-client';
1
2
  import { DialToolsetDto } from '@epam/ai-dial-chat-api-client';
2
3
  import { ToolsetLoginBodyDto } from '@epam/ai-dial-chat-api-client';
3
4
  import { ToolsetLogoutBodyDto } from '@epam/ai-dial-chat-api-client';
@@ -74,6 +75,19 @@ export declare const isPublicToolsetId: (toolsetId: string) => boolean;
74
75
  */
75
76
  export declare const navigateToolsetOAuthPopup: (popup: Window, auth: ToolsetOAuthSettings, toolsetId: string, callbackPath: string, credentialsLevel?: ToolsetCredentialsLevel, resourceKind?: OAuthResourceKind, offlineUsageConsent?: boolean) => ToolsetOAuthInitiationResult;
76
77
 
78
+ /**
79
+ * Encodes a toolset id to its single-encoded form regardless of whether the
80
+ * value received it in was already percent-encoded or the raw,
81
+ * human-readable form — decoding first then re-encoding once is idempotent
82
+ * either way, since `decodeToolsetId` on a raw (unencoded) id is a no-op.
83
+ * Use this instead of `encodeToolsetId` at a boundary that cannot guarantee
84
+ * which form it receives, such as a `postMessage` payload from an embedded
85
+ * iframe: calling `encodeToolsetId` directly on a value the sender already
86
+ * encoded escapes the existing `%` characters a second time (`%20` becomes
87
+ * `%2520`), which the backend only ever undoes once and so 404s on.
88
+ */
89
+ export declare const normalizeToolsetId: (toolsetId: string) => string;
90
+
77
91
  /** Arguments handed to the host's exchange callback. */
78
92
  export declare interface OAuthExchangeParams {
79
93
  /** One-time authorization code the provider returned. */
@@ -115,6 +129,24 @@ export declare enum OAuthResourceKind {
115
129
  */
116
130
  export declare const openToolsetOAuthPopup: () => Window | null;
117
131
 
132
+ /**
133
+ * Resolves which credentials level a toolset's login applies to, per DIAL
134
+ * Core's public/private toolset convention: a `public`-bucket toolset is
135
+ * shared credentials-wise at `User` level, while a private/workspace toolset
136
+ * is scoped at `Global` level. Every surface that drives a toolset login
137
+ * (the sign-in-interrupt dialog, the QuickApps editor iframe bridge,
138
+ * `useToolsetLogin`) must resolve the level this way rather than assuming one.
139
+ */
140
+ export declare const resolveToolsetCredentialsLevel: (toolsetId: string) => ToolsetCredentialsLevel.User | ToolsetCredentialsLevel.Global;
141
+
142
+ /**
143
+ * Picks the auth-status field matching one credentials level out of a
144
+ * toolset's `authSettings` — DIAL Core reports `userLevelAuthStatus` and
145
+ * `globalAuthStatus` as independent fields rather than one status keyed by
146
+ * level.
147
+ */
148
+ export declare const selectToolsetAuthStatus: (authSettings: Pick<DialToolsetAuthSettingsDto, "userLevelAuthStatus" | "globalAuthStatus"> | undefined, credentialsLevel: ToolsetCredentialsLevel) => string | undefined;
149
+
118
150
  export declare const subscribeToolsetLoginSuccess: <T>(listener: (detail: ToolsetLoginSuccessDetail<T>) => void) => (() => void);
119
151
 
120
152
  /** `sessionStorage` key the flow writes its `ToolsetRedirectState` under, in the popup it opens. */
package/oauth.js CHANGED
@@ -1,9 +1,9 @@
1
- import { decodeToolsetId as e, encodeToolsetId as t, isPublicToolsetId as n } from "./oauth/toolset-id.js";
2
- import { OAuthResourceKind as r, TOOLSET_REDIRECT_STATE_KEY as i, ToolsetAuthStatus as a, ToolsetAuthTypes as o, ToolsetCredentialsLevel as s, ToolsetOAuthCallbackQuery as c, ToolsetOAuthChannelControlType as l, ToolsetOAuthFailureReason as u, ToolsetOAuthInitiationResultType as d, ToolsetOAuthResultType as f, WithLogin as p } from "./oauth/types.js";
3
- import { emitToolsetLoginSuccess as m, subscribeToolsetLoginSuccess as h } from "./shared/toolset-login-events.js";
4
- import { getToolsetOAuthChannelName as g, waitForToolsetOAuthResult as _ } from "./oauth/handshake.js";
5
- import { buildToolsetAuthorizeUrl as v, getToolsetRedirectUri as y } from "./oauth/authorize-url.js";
6
- import { initiateOAuthLogin as b, navigateToolsetOAuthPopup as x, openToolsetOAuthPopup as S } from "./oauth/popup.js";
7
- import { ToolsetLoginOutcomeType as C, useToolsetLogin as w } from "./oauth/useToolsetLogin/useToolsetLogin.js";
8
- import { useOAuthCallbackCompletion as T } from "./oauth/useOAuthCallbackCompletion/useOAuthCallbackCompletion.js";
9
- export { r as OAuthResourceKind, i as TOOLSET_REDIRECT_STATE_KEY, a as ToolsetAuthStatus, o as ToolsetAuthTypes, s as ToolsetCredentialsLevel, C as ToolsetLoginOutcomeType, c as ToolsetOAuthCallbackQuery, l as ToolsetOAuthChannelControlType, u as ToolsetOAuthFailureReason, d as ToolsetOAuthInitiationResultType, f as ToolsetOAuthResultType, p as WithLogin, v as buildToolsetAuthorizeUrl, e as decodeToolsetId, m as emitToolsetLoginSuccess, t as encodeToolsetId, g as getToolsetOAuthChannelName, y as getToolsetRedirectUri, b as initiateOAuthLogin, n as isPublicToolsetId, x as navigateToolsetOAuthPopup, S as openToolsetOAuthPopup, h as subscribeToolsetLoginSuccess, T as useOAuthCallbackCompletion, w as useToolsetLogin, _ as waitForToolsetOAuthResult };
1
+ import { OAuthResourceKind as e, TOOLSET_REDIRECT_STATE_KEY as t, ToolsetAuthStatus as n, ToolsetAuthTypes as r, ToolsetCredentialsLevel as i, ToolsetOAuthCallbackQuery as a, ToolsetOAuthChannelControlType as o, ToolsetOAuthFailureReason as s, ToolsetOAuthInitiationResultType as c, ToolsetOAuthResultType as l, WithLogin as u } from "./oauth/types.js";
2
+ import { decodeToolsetId as d, encodeToolsetId as f, isPublicToolsetId as p, normalizeToolsetId as m, resolveToolsetCredentialsLevel as h, selectToolsetAuthStatus as g } from "./oauth/toolset-id.js";
3
+ import { emitToolsetLoginSuccess as _, subscribeToolsetLoginSuccess as v } from "./shared/toolset-login-events.js";
4
+ import { getToolsetOAuthChannelName as y, waitForToolsetOAuthResult as b } from "./oauth/handshake.js";
5
+ import { buildToolsetAuthorizeUrl as x, getToolsetRedirectUri as S } from "./oauth/authorize-url.js";
6
+ import { initiateOAuthLogin as C, navigateToolsetOAuthPopup as w, openToolsetOAuthPopup as T } from "./oauth/popup.js";
7
+ import { ToolsetLoginOutcomeType as E, useToolsetLogin as D } from "./oauth/useToolsetLogin/useToolsetLogin.js";
8
+ import { useOAuthCallbackCompletion as O } from "./oauth/useOAuthCallbackCompletion/useOAuthCallbackCompletion.js";
9
+ export { e as OAuthResourceKind, t as TOOLSET_REDIRECT_STATE_KEY, n as ToolsetAuthStatus, r as ToolsetAuthTypes, i as ToolsetCredentialsLevel, E as ToolsetLoginOutcomeType, a as ToolsetOAuthCallbackQuery, o as ToolsetOAuthChannelControlType, s as ToolsetOAuthFailureReason, c as ToolsetOAuthInitiationResultType, l as ToolsetOAuthResultType, u as WithLogin, x as buildToolsetAuthorizeUrl, d as decodeToolsetId, _ as emitToolsetLoginSuccess, f as encodeToolsetId, y as getToolsetOAuthChannelName, S as getToolsetRedirectUri, C as initiateOAuthLogin, p as isPublicToolsetId, w as navigateToolsetOAuthPopup, m as normalizeToolsetId, T as openToolsetOAuthPopup, h as resolveToolsetCredentialsLevel, g as selectToolsetAuthStatus, v as subscribeToolsetLoginSuccess, O as useOAuthCallbackCompletion, D as useToolsetLogin, b as waitForToolsetOAuthResult };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@epam/ai-dial-chat-hooks",
3
3
  "description": "Framework-level React hooks extracted from AI DIAL Chat for building custom chat interfaces",
4
- "version": "1.2.0-dev.3",
4
+ "version": "1.2.0-dev.303",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",
7
7
  "main": "./index.js",
@@ -29,6 +29,11 @@
29
29
  "import": "./conversation.js",
30
30
  "default": "./conversation.js"
31
31
  },
32
+ "./conversation-overlay": {
33
+ "types": "./conversation-overlay.d.ts",
34
+ "import": "./conversation-overlay.js",
35
+ "default": "./conversation-overlay.js"
36
+ },
32
37
  "./conversation-transfer": {
33
38
  "types": "./conversation-transfer.d.ts",
34
39
  "import": "./conversation-transfer.js",
@@ -44,6 +49,11 @@
44
49
  "import": "./file-manager.js",
45
50
  "default": "./file-manager.js"
46
51
  },
52
+ "./file-manager-canvas": {
53
+ "types": "./file-manager-canvas.d.ts",
54
+ "import": "./file-manager-canvas.js",
55
+ "default": "./file-manager-canvas.js"
56
+ },
47
57
  "./source-content": {
48
58
  "types": "./source-content.d.ts",
49
59
  "import": "./source-content.js",
@@ -89,6 +99,11 @@
89
99
  "import": "./utils.js",
90
100
  "default": "./utils.js"
91
101
  },
102
+ "./usage": {
103
+ "types": "./usage.d.ts",
104
+ "import": "./usage.js",
105
+ "default": "./usage.js"
106
+ },
92
107
  "./mcp-apps": {
93
108
  "types": "./mcp-apps.d.ts",
94
109
  "import": "./mcp-apps.js",
@@ -96,8 +111,8 @@
96
111
  }
97
112
  },
98
113
  "dependencies": {
99
- "@epam/ai-dial-chat-api-client": "1.2.0-dev.3",
100
- "dompurify": "3.4.15",
114
+ "@epam/ai-dial-chat-api-client": "1.2.0-dev.303",
115
+ "dompurify": "3.4.16",
101
116
  "fflate": "^0.8.3",
102
117
  "lru-cache": "^10.4.3",
103
118
  "mime-types": "^3.0.2",
@@ -105,22 +120,22 @@
105
120
  },
106
121
  "peerDependencies": {
107
122
  "react": "^19.2.8",
108
- "@epam/ai-dial-attachment-canvas": "1.2.0-dev.3",
109
- "@epam/ai-dial-attachment-input": "1.2.0-dev.3",
110
- "@epam/ai-dial-builder-form": "1.2.0-dev.3",
111
- "@epam/ai-dial-catalog": "1.2.0-dev.3",
112
- "@epam/ai-dial-chat-overlay": "1.2.0-dev.3",
113
- "@epam/ai-dial-chat-shared": "1.2.0-dev.3",
114
- "@epam/ai-dial-mcp-apps": "1.2.0-dev.3",
115
- "@epam/ai-dial-publish-panel": "1.2.0-dev.3",
116
- "@epam/ai-dial-quotations": "1.2.0-dev.3",
117
- "@epam/ai-dial-react-file-manager": "^0.2.0",
118
- "@epam/ai-dial-scheduled-tasks": "1.2.0-dev.3",
119
- "@epam/ai-dial-share": "1.2.0-dev.3",
120
- "@epam/ai-dial-skill-editor": "1.2.0-dev.3",
121
- "@epam/ai-dial-source-panel": "1.2.0-dev.3",
122
- "@epam/ai-dial-ui-kit": "^0.14.2",
123
- "@modelcontextprotocol/sdk": "^1.29.0",
123
+ "@epam/ai-dial-attachment-canvas": "1.2.0-dev.303",
124
+ "@epam/ai-dial-attachment-input": "1.2.0-dev.303",
125
+ "@epam/ai-dial-catalog": "1.2.0-dev.303",
126
+ "@epam/ai-dial-chat-overlay": "1.2.0-dev.303",
127
+ "@epam/ai-dial-chat-shared": "1.2.0-dev.303",
128
+ "@epam/ai-dial-mcp-apps": "1.2.0-dev.303",
129
+ "@epam/ai-dial-publish-panel": "1.2.0-dev.303",
130
+ "@epam/ai-dial-quotations": "1.2.0-dev.303",
131
+ "@epam/ai-dial-react-file-manager": "^0.3.0-dev.25",
132
+ "@epam/ai-dial-scheduled-tasks": "1.2.0-dev.303",
133
+ "@epam/ai-dial-share": "1.2.0-dev.303",
134
+ "@epam/ai-dial-skill-editor": "1.2.0-dev.303",
135
+ "@epam/ai-dial-source-panel": "1.2.0-dev.303",
136
+ "@epam/ai-dial-ui-kit": "^0.15.0-dev.39",
137
+ "@epam/ai-dial-usage-dashboard": "1.2.0-dev.303",
138
+ "@modelcontextprotocol/sdk": "^1.32.1",
124
139
  "@epam/pdf-highlighter-kit": "^0.0.19",
125
140
  "@mcp-ui/client": "^7.1.1"
126
141
  },
@@ -131,9 +146,6 @@
131
146
  "@epam/ai-dial-attachment-input": {
132
147
  "optional": true
133
148
  },
134
- "@epam/ai-dial-builder-form": {
135
- "optional": true
136
- },
137
149
  "@epam/ai-dial-catalog": {
138
150
  "optional": true
139
151
  },
@@ -170,6 +182,9 @@
170
182
  "@epam/ai-dial-ui-kit": {
171
183
  "optional": true
172
184
  },
185
+ "@epam/ai-dial-usage-dashboard": {
186
+ "optional": true
187
+ },
173
188
  "@mcp-ui/client": {
174
189
  "optional": true
175
190
  },
@@ -182,7 +197,7 @@
182
197
  },
183
198
  "sideEffects": [
184
199
  "./oauth.js",
185
- "./file-manager.js",
200
+ "./file-manager-canvas.js",
186
201
  "./shared/toolset-login-events.js",
187
202
  "./files/attachment-canvas.js"
188
203
  ],
@@ -0,0 +1,81 @@
1
+ import { CRON_LAST_DAY_OF_MONTH as e } from "../shared/cron-day-of-month.js";
2
+ //#region src/scheduled-task/scheduled-task-description.ts
3
+ var t = /* @__PURE__ */ function(e) {
4
+ return e.OneTime = "oneTime", e.Hourly = "hourly", e.EveryNMinutes = "everyNMinutes", e.Daily = "daily", e.Weekly = "weekly", e.Monthly = "monthly", e.Custom = "custom", e.Invalid = "invalid", e;
5
+ }({}), n = (t, { timeZone: n = "UTC", referenceDate: r = /* @__PURE__ */ new Date() } = {}) => {
6
+ let i = (e, t = {}) => ({
7
+ kind: e,
8
+ sourceTimezone: "utc",
9
+ ...t
10
+ });
11
+ if (t.date && t.cron) return i("invalid");
12
+ if (t.date) {
13
+ let e = new Date(t.date);
14
+ return Number.isNaN(e.getTime()) ? i("invalid") : i("oneTime", { date: e });
15
+ }
16
+ let a = t.cron?.fields;
17
+ if (!a || Object.keys(a).length === 0) return i("invalid");
18
+ let o = () => i("custom", { expression: JSON.stringify(a) }), s = {
19
+ hour: [0, 23],
20
+ minute: [0, 59],
21
+ day: [1, 31],
22
+ day_of_week: [0, 6],
23
+ month: [1, 12],
24
+ second: [0, 59]
25
+ };
26
+ for (let [e, t] of Object.entries(a)) {
27
+ if (t == null) continue;
28
+ if (!t.trim()) return i("invalid");
29
+ let n = s[e];
30
+ if (n && /^-?\d+$/.test(t) && (Number(t) < n[0] || Number(t) > n[1])) return i("invalid");
31
+ if (e === "second" && t !== "0" || ![
32
+ "hour",
33
+ "minute",
34
+ "day",
35
+ "day_of_week"
36
+ ].includes(e) && t !== "*" && !(e === "second" && t === "0")) return o();
37
+ }
38
+ let c = a.hour, l = a.minute, u = a.day === "*" ? void 0 : a.day, d = u === e, f = a.day_of_week === "*" ? void 0 : a.day_of_week, p = f ? [
39
+ "monday",
40
+ "tuesday",
41
+ "wednesday",
42
+ "thursday",
43
+ "friday",
44
+ "saturday",
45
+ "sunday"
46
+ ].findIndex((e) => e === f.toLowerCase() || e.slice(0, 3) === f.toLowerCase()) : -1, m = p >= 0 ? String(p) : f;
47
+ if (u && m || u && !d && !/^\d+$/.test(u) || m && !/^\d+$/.test(m)) return o();
48
+ let h = c == null || c === "*", g = l?.match(/^\*\/(\d+)$/);
49
+ if (h && g && !u && !m) {
50
+ let e = Number(g[1]);
51
+ return e > 0 && e <= 59 ? i("everyNMinutes", { intervalMinutes: e }) : i("invalid");
52
+ }
53
+ if (!l || !/^\d+$/.test(l) || !h && !/^\d+$/.test(c) || h && (u || m)) return o();
54
+ let _ = new Date(r);
55
+ if (Number.isNaN(_.getTime())) return i("invalid");
56
+ if (_.setUTCHours(h ? 0 : Number(c), Number(l), 0, 0), m) {
57
+ let e = (Number(m) + 1) % 7;
58
+ _.setUTCDate(_.getUTCDate() + (e - _.getUTCDay() + 7) % 7);
59
+ }
60
+ let v = new Intl.DateTimeFormat("en-GB", {
61
+ timeZone: n,
62
+ hourCycle: "h23",
63
+ year: "numeric",
64
+ month: "2-digit",
65
+ day: "2-digit",
66
+ hour: "2-digit",
67
+ minute: "2-digit"
68
+ }).formatToParts(_), y = (e) => v.find((t) => t.type === e)?.value ?? "", b = new Date(Date.UTC(Number(y("year")), Number(y("month")) - 1, Number(y("day")))), x = Date.UTC(_.getUTCFullYear(), _.getUTCMonth(), _.getUTCDate()), S = Math.round((b.getTime() - x) / 864e5), C = y("hour") + ":" + y("minute");
69
+ return h ? i("hourly", { time: y("minute") }) : m ? i("weekly", {
70
+ time: C,
71
+ dayOfWeek: String((Number(m) + S + 7) % 7)
72
+ }) : d ? S === 1 ? i("monthly", {
73
+ time: C,
74
+ dayOfMonth: "1"
75
+ }) : o() : u ? S === 0 || Number(u) <= 28 && Number(u) + S >= 1 && Number(u) + S <= 28 ? i("monthly", {
76
+ time: C,
77
+ dayOfMonth: String(Number(u) + S)
78
+ }) : o() : i("daily", { time: C });
79
+ };
80
+ //#endregion
81
+ export { t as ScheduledTaskTriggerDescriptionKind, n as describeScheduledTaskTrigger };
@@ -0,0 +1,24 @@
1
+ import { mapFormValuesToCreateBody as e, mapFormValuesToUpdateBody as t } from "./scheduled-task-trigger.js";
2
+ import { validateScheduledTaskFormValues as n } from "@epam/ai-dial-scheduled-tasks/validation";
3
+ //#region src/scheduled-task/scheduled-task-preparation.ts
4
+ var r = (t, r) => {
5
+ let i = n(t, r);
6
+ return Object.keys(i).length > 0 ? {
7
+ ok: !1,
8
+ errors: i
9
+ } : {
10
+ ok: !0,
11
+ body: e(t)
12
+ };
13
+ }, i = (e, r) => {
14
+ let i = n(e, r);
15
+ return Object.keys(i).length > 0 ? {
16
+ ok: !1,
17
+ errors: i
18
+ } : {
19
+ ok: !0,
20
+ body: t(e)
21
+ };
22
+ };
23
+ //#endregion
24
+ export { r as prepareScheduledTaskCreateBody, i as prepareScheduledTaskUpdateBody };
@@ -1,59 +1,64 @@
1
1
  import { padTwoDigits as e } from "../shared/formatting.js";
2
2
  import { UnsupportedTriggerReason as t } from "./scheduled-task-mapping.js";
3
- import { apSchedulerDayToJsDay as n, jsDayToApSchedulerDay as r } from "../shared/cron-weekday.js";
4
- import { ScheduledTaskRepeat as i } from "@epam/ai-dial-scheduled-tasks";
3
+ import { getUtcDayShift as n, toLocalDayOfMonth as r, toUtcCronDayOfMonth as i } from "../shared/cron-day-of-month.js";
4
+ import { apSchedulerDayToJsDay as a, jsDayToApSchedulerDay as o } from "../shared/cron-weekday.js";
5
+ import { ScheduledTaskRepeat as s } from "@epam/ai-dial-scheduled-tasks";
5
6
  //#region src/scheduled-task/scheduled-task-trigger.ts
6
- var a = new Set([
7
+ var c = new Set([
7
8
  "hour",
8
9
  "minute",
9
10
  "day_of_week",
10
11
  "day"
11
- ]), o = "09:00", s = (e) => {
12
- if (e.repeat === i.Hourly) {
12
+ ]), l = "09:00", u = (e) => {
13
+ if (e.repeat === s.Hourly) {
13
14
  let t = /* @__PURE__ */ new Date();
14
15
  return t.setHours(0, Number(e.minute), 0, 0), {
15
16
  hour: "*",
16
17
  minute: String(t.getUTCMinutes())
17
18
  };
18
19
  }
19
- let [t, a] = e.time.split(":"), o = Number(t), s = Number(a), c = /* @__PURE__ */ new Date();
20
- c.setHours(o, s, 0, 0);
21
- let l = e.repeat === i.Weekly && !!e.dayOfWeek, u = e.repeat === i.Monthly && !!e.dayOfMonth;
22
- if (l) {
23
- let t = (n(Number(e.dayOfWeek)) - c.getDay() + 7) % 7;
24
- c.setDate(c.getDate() + t);
25
- } else u && c.setDate(Number(e.dayOfMonth));
26
- let d = {
27
- hour: String(c.getUTCHours()),
28
- minute: String(c.getUTCMinutes())
20
+ let [t, r] = e.time.split(":"), c = Number(t), l = Number(r), u = /* @__PURE__ */ new Date();
21
+ u.setHours(c, l, 0, 0);
22
+ let d = e.repeat === s.Weekly && !!e.dayOfWeek, f = e.repeat === s.Monthly && !!e.dayOfMonth;
23
+ if (d) {
24
+ let t = (a(Number(e.dayOfWeek)) - u.getDay() + 7) % 7;
25
+ u.setDate(u.getDate() + t);
26
+ }
27
+ let p = {
28
+ hour: String(u.getUTCHours()),
29
+ minute: String(u.getUTCMinutes())
29
30
  };
30
- return l && (d.day_of_week = String(r(c.getUTCDay()))), u && (d.day = String(c.getUTCDate())), d;
31
- }, c = (e, t) => {
31
+ return d && (p.day_of_week = String(o(u.getUTCDay()))), f && (p.day = i(Number(e.dayOfMonth), n(u))), p;
32
+ }, d = (e, t) => {
32
33
  let [n, r, i] = e.split("-").map(Number), a = new Date(n, r - 1, i);
33
34
  return t === "start" ? a.setHours(0, 0, 0, 0) : a.setHours(23, 59, 59, 999), a.toISOString();
34
- }, l = (e) => {
35
- let t = e.repeat === i.OneTime ? { date: new Date(e.runAt ?? "").toISOString() } : { cron: {
36
- fields: s(e),
37
- ...e.startDate ? { startDate: c(e.startDate, "start") } : {},
38
- ...e.endDate ? { endDate: c(e.endDate, "end") } : {}
35
+ }, f = (e) => {
36
+ let t = e.repeat === s.OneTime ? { date: new Date(e.runAt ?? "").toISOString() } : { cron: {
37
+ fields: u(e),
38
+ ...e.startDate ? { startDate: d(e.startDate, "start") } : {},
39
+ ...e.endDate ? { endDate: d(e.endDate, "end") } : {}
39
40
  } }, n = e.description?.trim();
40
41
  return {
41
42
  displayName: e.displayName.trim(),
42
43
  trigger: t,
43
44
  model: e.modelId,
44
45
  prompt: e.prompt.trim(),
46
+ ...e.skillUrls?.length ? { skillUrls: [...new Set(e.skillUrls)] } : {},
45
47
  ...n ? { description: n } : {}
46
48
  };
47
- }, u = (e) => l(e), d = (t) => {
49
+ }, p = (e) => ({
50
+ ...f(e),
51
+ skillUrls: [...new Set(e.skillUrls ?? [])]
52
+ }), m = (t) => {
48
53
  let n = new Date(t);
49
54
  return `${n.getFullYear()}-${e(n.getMonth() + 1)}-${e(n.getDate())}T${e(n.getHours())}:${e(n.getMinutes())}`;
50
- }, f = (t) => {
55
+ }, h = (t) => {
51
56
  let n = new Date(t);
52
57
  return `${n.getFullYear()}-${e(n.getMonth() + 1)}-${e(n.getDate())}`;
53
- }, p = (t) => {
54
- let i = new Set(Object.entries(t).filter(([, e]) => e != null).map(([e]) => e)), o = [...i].filter((e) => !a.has(e)), s = i.has("day_of_week"), c = i.has("day");
55
- if (o.length > 0 || s && c || !i.has("hour") || !i.has("minute")) return { ok: !1 };
56
- if (t.hour === "*" && /^\d+$/.test(String(t.minute)) && !s && !c) {
58
+ }, g = (t) => {
59
+ let i = new Set(Object.entries(t).filter(([, e]) => e != null).map(([e]) => e)), s = [...i].filter((e) => !c.has(e)), l = i.has("day_of_week"), u = i.has("day");
60
+ if (s.length > 0 || l && u || !i.has("hour") || !i.has("minute")) return { ok: !1 };
61
+ if (t.hour === "*" && /^\d+$/.test(String(t.minute)) && !l && !u) {
57
62
  let e = /* @__PURE__ */ new Date();
58
63
  return e.setUTCHours(0, Number(t.minute), 0, 0), {
59
64
  ok: !0,
@@ -61,84 +66,82 @@ var a = new Set([
61
66
  minute: String(e.getMinutes())
62
67
  };
63
68
  }
64
- let l = Number(t.hour), u = Number(t.minute);
65
- if (Number.isNaN(l) || Number.isNaN(u)) return { ok: !1 };
66
- let d = /* @__PURE__ */ new Date();
67
- if (d.setUTCHours(l, u, 0, 0), s) {
69
+ let d = Number(t.hour), f = Number(t.minute);
70
+ if (Number.isNaN(d) || Number.isNaN(f)) return { ok: !1 };
71
+ let p = /* @__PURE__ */ new Date();
72
+ if (p.setUTCHours(d, f, 0, 0), l) {
68
73
  let e = Number(t.day_of_week);
69
74
  if (Number.isNaN(e)) return { ok: !1 };
70
- let r = (n(e) - d.getUTCDay() + 7) % 7;
71
- d.setUTCDate(d.getUTCDate() + r);
72
- } else if (c) {
73
- let e = Number(t.day);
74
- if (Number.isNaN(e)) return { ok: !1 };
75
- d.setUTCDate(e);
75
+ let n = (a(e) - p.getUTCDay() + 7) % 7;
76
+ p.setUTCDate(p.getUTCDate() + n);
76
77
  }
77
- return {
78
+ let m = u ? r(String(t.day), n(p)) : void 0;
79
+ return u && !m ? { ok: !1 } : {
78
80
  ok: !0,
79
81
  isHourly: !1,
80
- time: `${e(d.getHours())}:${e(d.getMinutes())}`,
81
- ...s ? { dayOfWeek: String(r(d.getDay())) } : {},
82
- ...c ? { dayOfMonth: String(d.getDate()) } : {}
82
+ time: `${e(p.getHours())}:${e(p.getMinutes())}`,
83
+ ...l ? { dayOfWeek: String(o(p.getDay())) } : {},
84
+ ...m ? { dayOfMonth: m } : {}
83
85
  };
84
- }, m = (e) => {
85
- if (!e.model || !e.prompt) return {
86
+ }, _ = (e) => {
87
+ if (!e.model || typeof e.prompt != "string" || !e.prompt.trim() && !e.skillUrls?.length) return {
86
88
  ok: !1,
87
89
  reason: t.MissingRequiredFields
88
90
  };
89
- let { date: n, cron: r } = e.trigger, a = !!n;
90
- if (a === !!r) return {
91
+ let { date: n, cron: r } = e.trigger, i = !!n;
92
+ if (i === !!r) return {
91
93
  ok: !1,
92
94
  reason: t.UnsupportedTriggerType
93
95
  };
94
- let s = {
96
+ let a = {
95
97
  displayName: e.displayName,
96
98
  modelId: e.model,
97
99
  prompt: e.prompt,
100
+ skillUrls: [...new Set(e.skillUrls ?? [])],
98
101
  ...e.description ? { description: e.description } : {}
99
102
  };
100
- if (a) return {
103
+ if (i) return {
101
104
  ok: !0,
102
105
  values: {
103
- ...s,
104
- repeat: i.OneTime,
105
- runAt: d(n),
106
- time: o
106
+ ...a,
107
+ repeat: s.OneTime,
108
+ runAt: m(n),
109
+ time: l
107
110
  }
108
111
  };
109
112
  if (!r) return {
110
113
  ok: !1,
111
114
  reason: t.UnsupportedTriggerType
112
115
  };
113
- let c = p(r.fields);
114
- if (!c.ok) return {
116
+ let o = g(r.fields);
117
+ if (!o.ok) return {
115
118
  ok: !1,
116
119
  reason: t.UnsupportedCronShape
117
120
  };
118
- if (c.isHourly) return {
121
+ if (o.isHourly) return {
119
122
  ok: !0,
120
123
  values: {
121
- ...s,
122
- repeat: i.Hourly,
123
- time: o,
124
- minute: c.minute,
125
- ...r.startDate ? { startDate: f(r.startDate) } : {},
126
- ...r.endDate ? { endDate: f(r.endDate) } : {}
124
+ ...a,
125
+ repeat: s.Hourly,
126
+ time: l,
127
+ minute: o.minute,
128
+ ...r.startDate ? { startDate: h(r.startDate) } : {},
129
+ ...r.endDate ? { endDate: h(r.endDate) } : {}
127
130
  }
128
131
  };
129
- let l = i.Daily;
130
- return c.dayOfWeek ? l = i.Weekly : c.dayOfMonth && (l = i.Monthly), {
132
+ let c = s.Daily;
133
+ return o.dayOfWeek ? c = s.Weekly : o.dayOfMonth && (c = s.Monthly), {
131
134
  ok: !0,
132
135
  values: {
133
- ...s,
134
- repeat: l,
135
- time: c.time,
136
- ...c.dayOfWeek ? { dayOfWeek: c.dayOfWeek } : {},
137
- ...c.dayOfMonth ? { dayOfMonth: c.dayOfMonth } : {},
138
- ...r.startDate ? { startDate: f(r.startDate) } : {},
139
- ...r.endDate ? { endDate: f(r.endDate) } : {}
136
+ ...a,
137
+ repeat: c,
138
+ time: o.time,
139
+ ...o.dayOfWeek ? { dayOfWeek: o.dayOfWeek } : {},
140
+ ...o.dayOfMonth ? { dayOfMonth: o.dayOfMonth } : {},
141
+ ...r.startDate ? { startDate: h(r.startDate) } : {},
142
+ ...r.endDate ? { endDate: h(r.endDate) } : {}
140
143
  }
141
144
  };
142
145
  };
143
146
  //#endregion
144
- export { l as mapFormValuesToCreateBody, u as mapFormValuesToUpdateBody, m as mapScheduledTaskDtoToFormValues };
147
+ export { f as mapFormValuesToCreateBody, p as mapFormValuesToUpdateBody, _ as mapScheduledTaskDtoToFormValues };
@@ -0,0 +1,19 @@
1
+ //#region src/scheduled-task/scheduled-tasks-api-client.ts
2
+ var e = (e) => {
3
+ if (!Array.isArray(e.items)) throw TypeError("Scheduled tasks API returned a malformed page response");
4
+ return e;
5
+ }, t = (t) => ({
6
+ listScheduledTasks: async ({ signal: n, ...r } = {}) => e(await t.listScheduledTasks(r, n ? { signal: n } : void 0)),
7
+ listScheduledTaskRuns: async ({ signal: n, ...r }) => e(await t.listScheduledTaskRuns(r, n ? { signal: n } : void 0)),
8
+ createScheduledTask: (e) => t.createScheduledTask({ createScheduledTaskBodyDto: e }),
9
+ getScheduledTask: (e) => t.getScheduledTask({ scheduleId: e }),
10
+ updateScheduledTask: (e, n) => t.updateScheduledTask({
11
+ scheduleId: e,
12
+ updateScheduledTaskBodyDto: n
13
+ }),
14
+ pauseScheduledTask: (e) => t.pauseScheduledTask({ scheduleId: e }),
15
+ resumeScheduledTask: (e) => t.resumeScheduledTask({ scheduleId: e }),
16
+ deleteScheduledTask: (e) => t.deleteScheduledTask({ scheduleId: e })
17
+ });
18
+ //#endregion
19
+ export { t as createScheduledTasksApiClient };