@stack-spot/portal-network 0.195.1 → 0.196.0-beta.1
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/CHANGELOG.md +79 -0
- package/dist/api/agent-tools.d.ts +135 -148
- package/dist/api/agent-tools.d.ts.map +1 -1
- package/dist/api/agent-tools.js +41 -4
- package/dist/api/agent-tools.js.map +1 -1
- package/dist/api/agent.d.ts +55 -55
- package/dist/api/agent.d.ts.map +1 -1
- package/dist/api/ai.d.ts +196 -25
- package/dist/api/ai.d.ts.map +1 -1
- package/dist/api/ai.js +153 -22
- package/dist/api/ai.js.map +1 -1
- package/dist/api/cloudPlatformHorizon.d.ts +178 -9
- package/dist/api/cloudPlatformHorizon.d.ts.map +1 -1
- package/dist/api/cloudPlatformHorizon.js +69 -1
- package/dist/api/cloudPlatformHorizon.js.map +1 -1
- package/dist/api/codeShift.d.ts +315 -62
- package/dist/api/codeShift.d.ts.map +1 -1
- package/dist/api/codeShift.js +153 -12
- package/dist/api/codeShift.js.map +1 -1
- package/dist/api/discover.d.ts +23 -12
- package/dist/api/discover.d.ts.map +1 -1
- package/dist/api/discover.js +10 -0
- package/dist/api/discover.js.map +1 -1
- package/dist/api-addresses.d.ts.map +1 -1
- package/dist/client/account.d.ts +233 -233
- package/dist/client/account.d.ts.map +1 -1
- package/dist/client/agent-tools.d.ts +152 -126
- package/dist/client/agent-tools.d.ts.map +1 -1
- package/dist/client/agent-tools.js +29 -2
- package/dist/client/agent-tools.js.map +1 -1
- package/dist/client/agent.d.ts +46 -46
- package/dist/client/agent.d.ts.map +1 -1
- package/dist/client/ai.d.ts +120 -110
- package/dist/client/ai.d.ts.map +1 -1
- package/dist/client/ai.js +29 -2
- package/dist/client/ai.js.map +1 -1
- package/dist/client/api-management.d.ts +2 -2
- package/dist/client/cloud-account.d.ts +13 -13
- package/dist/client/cloud-platform-horizon.d.ts +38 -19
- package/dist/client/cloud-platform-horizon.d.ts.map +1 -1
- package/dist/client/cloud-platform-horizon.js +19 -1
- package/dist/client/cloud-platform-horizon.js.map +1 -1
- package/dist/client/cloud-platform.d.ts +50 -50
- package/dist/client/cloud-runtimes.d.ts +4 -4
- package/dist/client/cloud-services.d.ts +17 -17
- package/dist/client/cloud-services.d.ts.map +1 -1
- package/dist/client/code-shift.d.ts +349 -258
- package/dist/client/code-shift.d.ts.map +1 -1
- package/dist/client/code-shift.js +82 -1
- package/dist/client/code-shift.js.map +1 -1
- package/dist/client/content.d.ts +127 -132
- package/dist/client/content.d.ts.map +1 -1
- package/dist/client/data-integration.d.ts +55 -55
- package/dist/client/data-integration.d.ts.map +1 -1
- package/dist/client/discover.d.ts +15 -9
- package/dist/client/discover.d.ts.map +1 -1
- package/dist/client/discover.js +208 -0
- package/dist/client/discover.js.map +1 -1
- package/dist/client/event-bus.d.ts.map +1 -1
- package/dist/client/gen-ai-inference.d.ts +20 -20
- package/dist/client/insights.d.ts +7 -7
- package/dist/client/notification.d.ts +10 -10
- package/dist/client/runtime-manager.d.ts +8 -8
- package/dist/client/types.d.ts +14 -0
- package/dist/client/types.d.ts.map +1 -1
- package/dist/client/workflow.d.ts +10 -10
- package/dist/client/workspace-ai.d.ts +53 -53
- package/dist/client/workspace-manager.d.ts +77 -77
- package/dist/client/workspace-search.d.ts +2 -2
- package/dist/client/workspace.d.ts +58 -105
- package/dist/client/workspace.d.ts.map +1 -1
- package/dist/error/dictionary/cloud-platform.d.ts +6 -0
- package/dist/error/dictionary/cloud-platform.d.ts.map +1 -1
- package/dist/error/dictionary/cloud-platform.js +6 -0
- package/dist/error/dictionary/cloud-platform.js.map +1 -1
- package/dist/utils/StreamedJson.d.ts.map +1 -1
- package/dist/utils/StreamedJson.js +9 -1
- package/dist/utils/StreamedJson.js.map +1 -1
- package/package.json +2 -2
- package/src/api/agent-tools.ts +182 -150
- package/src/api/ai.ts +381 -40
- package/src/api/cloudPlatformHorizon.ts +412 -9
- package/src/api/codeShift.ts +607 -69
- package/src/api/discover.ts +35 -12
- package/src/client/agent-tools.ts +20 -2
- package/src/client/ai.ts +25 -10
- package/src/client/cloud-platform-horizon.ts +12 -4
- package/src/client/code-shift.ts +50 -1
- package/src/client/discover.ts +220 -3
- package/src/client/types.ts +17 -2
- package/src/error/dictionary/cloud-platform.ts +6 -0
- package/src/utils/StreamedJson.tsx +9 -2
package/src/client/discover.ts
CHANGED
|
@@ -1,12 +1,17 @@
|
|
|
1
1
|
import { HttpError } from '@oazapfts/runtime'
|
|
2
|
+
import { findLast, last } from 'lodash'
|
|
2
3
|
import { getApiAddresses } from '../api-addresses'
|
|
3
4
|
import { ConversationResponse } from '../api/ai'
|
|
4
|
-
import { create, create1, create2, defaults, deleteById, deleteById1, deleteById2, getAll, getAll1, getAll2, getAllByHypothesis, getById, getById1, getById2, GetOpportunityResponse } from '../api/discover'
|
|
5
|
+
import { create, create1, create2, defaults, deleteById, deleteById1, deleteById2, getAll, getAll1, getAll2, getAllByHypothesis, getById, getById1, getById2, GetOpportunityResponse, MessageRequest } from '../api/discover'
|
|
5
6
|
import { DefaultAPIError } from '../error/DefaultAPIError'
|
|
6
7
|
import { StackspotAPIError } from '../error/StackspotAPIError'
|
|
8
|
+
import { StreamedJson } from '../utils/StreamedJson'
|
|
7
9
|
import { baseDictionary } from '../error/dictionary/base'
|
|
10
|
+
import { formatJson } from '../utils/string'
|
|
8
11
|
import { ReactQueryNetworkClient } from '../network/ReactQueryNetworkClient'
|
|
9
12
|
import { aiClient } from './ai'
|
|
13
|
+
import { ChatAgentTool, ChatResponseWithSteps, FixedChatResponse, StepChatStep } from './types'
|
|
14
|
+
import { agentToolsClient } from './agent-tools'
|
|
10
15
|
|
|
11
16
|
export interface ChatConversionDetails extends ConversationResponse {
|
|
12
17
|
opportunityName?: string,
|
|
@@ -67,8 +72,8 @@ class DiscoverClient extends ReactQueryNetworkClient {
|
|
|
67
72
|
{ ...variables, page: variables.page, size: variables.size ?? 40 },
|
|
68
73
|
)
|
|
69
74
|
|
|
70
|
-
const filteredItems = variables.filter
|
|
71
|
-
? chatsHistory.filter((chat) => chat.title.toLowerCase().includes(variables.filter!.toLowerCase()))
|
|
75
|
+
const filteredItems = variables.filter
|
|
76
|
+
? chatsHistory.filter((chat) => chat.title.toLowerCase().includes(variables.filter!.toLowerCase()))
|
|
72
77
|
: chatsHistory
|
|
73
78
|
|
|
74
79
|
const enrichedChats = filteredItems?.map(chat => {
|
|
@@ -84,6 +89,218 @@ class DiscoverClient extends ReactQueryNetworkClient {
|
|
|
84
89
|
return enrichedChats as ChatConversionDetails[]
|
|
85
90
|
},
|
|
86
91
|
})
|
|
92
|
+
|
|
93
|
+
private static async toolsOfAgent(agentId?: string) {
|
|
94
|
+
try {
|
|
95
|
+
const agent = agentId ? await agentToolsClient.agent.query({ agentId }) : undefined
|
|
96
|
+
if (!agent) return []
|
|
97
|
+
const tools: (Omit<ChatAgentTool, 'duration' | 'prompt' | 'output'>)[] = []
|
|
98
|
+
agent.toolkits?.builtin_toolkits?.forEach(kit => kit.tools?.forEach(({ id, name, description }) => {
|
|
99
|
+
if (id) tools.push({ image: kit.image_url, id, name: name || id, description })
|
|
100
|
+
}))
|
|
101
|
+
agent.toolkits?.custom_toolkits?.forEach(kit => kit.tools?.forEach(({ id, name, description }) => {
|
|
102
|
+
if (id) tools.push({ image: kit.avatar ?? undefined, id, name: name || id, description })
|
|
103
|
+
}))
|
|
104
|
+
return tools
|
|
105
|
+
} catch {
|
|
106
|
+
return []
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
sendChatMessage(request: MessageRequest & { agentId: string }, minChangeIntervalMS?: number): StreamedJson<ChatResponseWithSteps> {
|
|
112
|
+
const abortController = new AbortController()
|
|
113
|
+
const headers = {
|
|
114
|
+
'Content-Type': 'application/json',
|
|
115
|
+
'Accept': 'text/event-stream',
|
|
116
|
+
}
|
|
117
|
+
const events = this.stream(
|
|
118
|
+
this.resolveURL('/v2/ai/chat'),
|
|
119
|
+
{ method: 'post', body: JSON.stringify(request), headers, signal: abortController.signal },
|
|
120
|
+
)
|
|
121
|
+
/**
|
|
122
|
+
* This function treats events in the streaming that deals with the execution of tools. Since these events are not concatenated like
|
|
123
|
+
* normal streamings of data, we need this separate function to deal with them. It transforms the internal data model of the
|
|
124
|
+
* StreamedJson object whenever an event is triggered.
|
|
125
|
+
*/
|
|
126
|
+
async function transform(event: Partial<FixedChatResponse>, data: Partial<ChatResponseWithSteps>) {
|
|
127
|
+
const info = event.agent_info
|
|
128
|
+
|
|
129
|
+
if (!info) return
|
|
130
|
+
|
|
131
|
+
const tools = await DiscoverClient.toolsOfAgent(request.agentId)
|
|
132
|
+
data.steps = data.steps ? [...data.steps] : []
|
|
133
|
+
|
|
134
|
+
if (info.type === 'planning' && info.action === 'end') {
|
|
135
|
+
data.steps.push({
|
|
136
|
+
id: 'planning',
|
|
137
|
+
type: 'planning',
|
|
138
|
+
status: 'success',
|
|
139
|
+
duration: info.duration || 0,
|
|
140
|
+
steps: info.data?.steps?.map(s => s.goal) ?? [],
|
|
141
|
+
goal: info.data?.plan_goal ?? '',
|
|
142
|
+
})
|
|
143
|
+
|
|
144
|
+
info.data?.steps.forEach(s => data.steps?.push({
|
|
145
|
+
id: s.id,
|
|
146
|
+
type: 'step',
|
|
147
|
+
status: 'pending',
|
|
148
|
+
input: s.goal,
|
|
149
|
+
attempts: [{
|
|
150
|
+
tools: s.tools?.map(t => ({
|
|
151
|
+
...(tools.find(({ id }) => id === t.tool_id) ?? { id: t.tool_id, name: t.tool_id }),
|
|
152
|
+
executionId: t.tool_execution_id,
|
|
153
|
+
goal: t.goal,
|
|
154
|
+
})),
|
|
155
|
+
}],
|
|
156
|
+
}))
|
|
157
|
+
data.steps.push({ id: 'answer', type: 'answer', status: 'pending' })
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
if (info.type === 'planning' && info.action === 'awaiting_approval') {
|
|
161
|
+
data.steps.push({
|
|
162
|
+
id: 'planning',
|
|
163
|
+
type: 'planning',
|
|
164
|
+
status: 'awaiting_approval',
|
|
165
|
+
user_question: info.data?.user_question,
|
|
166
|
+
duration: info.duration || 0,
|
|
167
|
+
steps: info.data?.steps?.map(s => s.goal) ?? [],
|
|
168
|
+
goal: info.data?.plan_goal ?? '',
|
|
169
|
+
})
|
|
170
|
+
info.data?.steps.forEach(s => data.steps?.push({
|
|
171
|
+
id: s.id,
|
|
172
|
+
type: 'step',
|
|
173
|
+
status: 'pending',
|
|
174
|
+
input: s.goal,
|
|
175
|
+
attempts: [{
|
|
176
|
+
tools: s.tools?.map(t => ({
|
|
177
|
+
...(tools.find(({ id }) => id === t.tool_id) ?? { id: t.tool_id, name: t.tool_id }),
|
|
178
|
+
executionId: t.tool_execution_id,
|
|
179
|
+
goal: t.goal,
|
|
180
|
+
})),
|
|
181
|
+
}],
|
|
182
|
+
}))
|
|
183
|
+
data.steps.push({ id: 'answer', type: 'answer', status: 'pending' })
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
if (info.type === 'step' && info.action === 'start') {
|
|
187
|
+
const step = data.steps.find(s => s.id === info.id)
|
|
188
|
+
if (step) step.status = 'running'
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
if (info.type === 'step' && info.action === 'end') {
|
|
192
|
+
const step = data.steps.find(s => s.id === info.id) as StepChatStep
|
|
193
|
+
if (step) {
|
|
194
|
+
step.status = 'success'
|
|
195
|
+
step.duration = info.duration
|
|
196
|
+
const lastToolId = last(step.attempts[0].tools)?.id
|
|
197
|
+
const lastAttemptOfLastTool = findLast(step.attempts.map(a => a.tools).flat(), t => t?.id === lastToolId)
|
|
198
|
+
step.output = lastAttemptOfLastTool?.output
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
if (info.type === 'tool' && info.action === 'awaiting_approval') {
|
|
203
|
+
const tool = tools.find(({ id }) => id === info.data?.tool_id)
|
|
204
|
+
data.steps.push({
|
|
205
|
+
id: info.id,
|
|
206
|
+
type: 'tool',
|
|
207
|
+
status: 'awaiting_approval',
|
|
208
|
+
duration: info.duration || 0,
|
|
209
|
+
input: info.data?.input,
|
|
210
|
+
user_question: info.data?.user_question,
|
|
211
|
+
attempts: [{
|
|
212
|
+
tools: [{
|
|
213
|
+
executionId: info.id,
|
|
214
|
+
id: info.data?.tool_id ?? '',
|
|
215
|
+
name: tool?.name ?? '',
|
|
216
|
+
goal: tool?.goal,
|
|
217
|
+
...tool,
|
|
218
|
+
}],
|
|
219
|
+
}],
|
|
220
|
+
})
|
|
221
|
+
data.steps.push({ id: 'answer', type: 'answer', status: 'pending' })
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
if (info.type === 'tool' && info.action === 'start') {
|
|
225
|
+
const currentStep = data.steps.find(s => s.status === 'running') as StepChatStep
|
|
226
|
+
if (!info.data) return
|
|
227
|
+
|
|
228
|
+
//There might be a tool with status awaiting_approval, so we want to inform tool has already started
|
|
229
|
+
if (!currentStep || !currentStep.attempts[0].tools) {
|
|
230
|
+
const input = formatJson(info.data.input)
|
|
231
|
+
const tool = tools.find(({ id }) => id === info.data?.tool_id) ?? { id: info.data?.tool_id, name: info.data?.tool_id }
|
|
232
|
+
data.steps.push({
|
|
233
|
+
id: info.id,
|
|
234
|
+
type: 'tool',
|
|
235
|
+
status: 'running',
|
|
236
|
+
duration: info.duration || 0,
|
|
237
|
+
input: info.data?.input,
|
|
238
|
+
user_question: info.data?.user_question,
|
|
239
|
+
attempts: [{
|
|
240
|
+
tools: [{ ...tool, executionId: info.id, input }],
|
|
241
|
+
}],
|
|
242
|
+
})
|
|
243
|
+
} else {
|
|
244
|
+
const toolInFirstAttempt = currentStep.attempts[0].tools?.find(t => t.executionId === info.id)
|
|
245
|
+
//One step might have multiple tools. When in an approval mode, we might not have all the tools in the array yet.
|
|
246
|
+
//So we make sure to add any tools that are not in there.
|
|
247
|
+
if (!toolInFirstAttempt) {
|
|
248
|
+
const input = formatJson(info.data.input)
|
|
249
|
+
const tool = tools?.find(({ id }) => id === info.data?.tool_id) ?? { id: info.data?.tool_id, name: info.data?.tool_id }
|
|
250
|
+
currentStep.attempts[info.data.attempt - 1].tools?.push({
|
|
251
|
+
...tool,
|
|
252
|
+
executionId: info.id,
|
|
253
|
+
input,
|
|
254
|
+
})
|
|
255
|
+
} else {
|
|
256
|
+
const input = formatJson(info.data.input)
|
|
257
|
+
if (info.data.attempt === 1) {
|
|
258
|
+
toolInFirstAttempt.input = input
|
|
259
|
+
} else {
|
|
260
|
+
const tool = tools.find(({ id }) => id === info.data?.tool_id) ?? { id: info.data?.tool_id, name: info.data?.tool_id }
|
|
261
|
+
currentStep.attempts[info.data.attempt - 1] ??= { tools: [] }
|
|
262
|
+
currentStep.attempts[info.data.attempt - 1].tools?.push({
|
|
263
|
+
...tool,
|
|
264
|
+
executionId: info.id,
|
|
265
|
+
input,
|
|
266
|
+
})
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
if (info.type === 'tool' && info.action === 'end') {
|
|
273
|
+
const currentStep = data.steps.find(s => s.status === 'running') as StepChatStep
|
|
274
|
+
if (!currentStep || !info.data) return
|
|
275
|
+
const tool = currentStep.attempts[info.data.attempt - 1]?.tools?.find(t => t.executionId === info.id)
|
|
276
|
+
if (tool) {
|
|
277
|
+
tool.output = formatJson(info.data.output)
|
|
278
|
+
tool.duration = info.duration
|
|
279
|
+
}
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
if (info.type === 'final_answer' && info.action === 'start') {
|
|
283
|
+
const answerStep = last(data.steps)
|
|
284
|
+
if (answerStep) answerStep.status = 'running'
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
if (info.type === 'chat' && info.action === 'end') {
|
|
288
|
+
const answerStep = last(data.steps)
|
|
289
|
+
if (answerStep) {
|
|
290
|
+
answerStep.status = 'success'
|
|
291
|
+
answerStep.duration = info.duration
|
|
292
|
+
}
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
return new StreamedJson({
|
|
297
|
+
eventsPromise: events,
|
|
298
|
+
abortController,
|
|
299
|
+
minChangeIntervalMS,
|
|
300
|
+
ignoreKeys: ['agent_info'],
|
|
301
|
+
transform,
|
|
302
|
+
})
|
|
303
|
+
}
|
|
87
304
|
}
|
|
88
305
|
|
|
89
306
|
export const discoverClient = new DiscoverClient()
|
package/src/client/types.ts
CHANGED
|
@@ -361,10 +361,25 @@ export interface FixedChatResponse extends ChatResponse3 {
|
|
|
361
361
|
agent_info: AgentInfo,
|
|
362
362
|
tools?: string[],
|
|
363
363
|
}
|
|
364
|
+
export interface OpportunitiesPMAgent {
|
|
365
|
+
title: string,
|
|
366
|
+
description: string,
|
|
367
|
+
}
|
|
368
|
+
|
|
369
|
+
export type HypothesisPMAgent = OpportunitiesPMAgent
|
|
364
370
|
|
|
371
|
+
export type PrfaqPMAgent = {
|
|
372
|
+
title: string,
|
|
373
|
+
content: string,
|
|
374
|
+
}
|
|
365
375
|
export interface ChatResponseWithSteps extends FixedChatResponse {
|
|
366
376
|
steps: ChatStep[],
|
|
367
377
|
}
|
|
378
|
+
export interface ChatResponseWithPMResources {
|
|
379
|
+
opportunities?: OpportunitiesPMAgent[],
|
|
380
|
+
hypothesis?: HypothesisPMAgent[],
|
|
381
|
+
prfaq?: PrfaqPMAgent,
|
|
382
|
+
}
|
|
368
383
|
|
|
369
384
|
export type OazapftsFunction<Variables = any, Result = any> = (variables: Variables, opts?: RequestOpts) => Promise<Result>
|
|
370
385
|
|
|
@@ -380,12 +395,12 @@ export type FixVariables<
|
|
|
380
395
|
|
|
381
396
|
export type ReplaceResult<T extends (...args: any[]) => Promise<any>, Fix> = (...args: Parameters<T>) => Promise<Fix>
|
|
382
397
|
|
|
383
|
-
export interface AgentResponseWithBuiltIn extends Omit<ListAgentResponse, 'conversation_starter' | 'avatar'>
|
|
398
|
+
export interface AgentResponseWithBuiltIn extends Omit<ListAgentResponse, 'conversation_starter' | 'avatar'> {
|
|
384
399
|
builtIn?: boolean,
|
|
385
400
|
spaceName?: string,
|
|
386
401
|
conversation_starter?: string[] | null,
|
|
387
402
|
avatar?: string | null | undefined,
|
|
388
|
-
}
|
|
403
|
+
}
|
|
389
404
|
|
|
390
405
|
export type AgentVisibilityLevel = AgentVisibilityLevelEnum | VisibilityLevelEnum
|
|
391
406
|
|
|
@@ -39,6 +39,9 @@ export const scfDictionary = {
|
|
|
39
39
|
SCF_VPN_ERROR: 'VPN operation failed.',
|
|
40
40
|
SCF_VPN_NOT_FOUND_ERROR: 'VPN with ID {1} not found.',
|
|
41
41
|
SCF_VPN_NOT_READY_ERROR: 'VPN with ID {1} not ready.',
|
|
42
|
+
SCF_DNS_ZONE_NOT_EMPTY_ERROR: 'DNS Zone with ID {1} is not empty.',
|
|
43
|
+
SCF_FOLDER_NOT_EMPTY_ERROR: 'Folder with ID {1} is not empty.',
|
|
44
|
+
SCF_PROJECT_NOT_EMPTY_ERROR: 'Project with ID {1} is not empty.',
|
|
42
45
|
},
|
|
43
46
|
pt: {
|
|
44
47
|
SCF_CERTIFICATE_ERROR: 'Falha na operação de Certificado.',
|
|
@@ -78,5 +81,8 @@ export const scfDictionary = {
|
|
|
78
81
|
SCF_VPN_ERROR: 'Falha na operação de VPN.',
|
|
79
82
|
SCF_VPN_NOT_FOUND_ERROR: 'VPN com ID {1} não encontrada.',
|
|
80
83
|
SCF_VPN_NOT_READY_ERROR: 'VPN com ID {1} não está pronta.',
|
|
84
|
+
SCF_DNS_ZONE_NOT_EMPTY_ERROR: 'DNS Zone com ID {1} não está vazia.',
|
|
85
|
+
SCF_FOLDER_NOT_EMPTY_ERROR: 'Folder com ID {1} não está vazia.',
|
|
86
|
+
SCF_PROJECT_NOT_EMPTY_ERROR: 'Project com ID {1} não está vazia.',
|
|
81
87
|
},
|
|
82
88
|
} satisfies Dictionary
|
|
@@ -64,7 +64,14 @@ export class StreamedJson<T> {
|
|
|
64
64
|
for await (const event of events) {
|
|
65
65
|
if (this.error) return
|
|
66
66
|
if (event.data) {
|
|
67
|
-
|
|
67
|
+
let json
|
|
68
|
+
try {
|
|
69
|
+
json = JSON.parse(event.data)
|
|
70
|
+
} catch (e) {
|
|
71
|
+
// eslint-disable-next-line no-console
|
|
72
|
+
console.warn('Mal formed JSON in streaming:', event.data)
|
|
73
|
+
continue
|
|
74
|
+
}
|
|
68
75
|
await this.transform?.(json, this.data)
|
|
69
76
|
this.merge(json, this.data)
|
|
70
77
|
if (new Date().getTime() - lastChangeCall >= minChangeIntervalMS) {
|
|
@@ -138,7 +145,7 @@ export class StreamedJson<T> {
|
|
|
138
145
|
onChange(listener: (value: Partial<T>) => void) {
|
|
139
146
|
if (this.fullPromise.resolved) {
|
|
140
147
|
listener(this.data)
|
|
141
|
-
return () => {}
|
|
148
|
+
return () => { }
|
|
142
149
|
}
|
|
143
150
|
this.onChangeListeners.push(listener)
|
|
144
151
|
return () => {
|