@stack-spot/ai-chat-widget 2.3.0-alpha.1 → 2.3.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 +23 -0
- package/dist/StackspotAIWidget.d.ts +1 -5
- package/dist/StackspotAIWidget.d.ts.map +1 -1
- package/dist/StackspotAIWidget.js +2 -2
- package/dist/StackspotAIWidget.js.map +1 -1
- package/dist/app-metadata.json +5 -5
- package/dist/chat-interceptors/send-message.d.ts.map +1 -1
- package/dist/chat-interceptors/send-message.js +130 -1
- package/dist/chat-interceptors/send-message.js.map +1 -1
- package/dist/state/ChatEntry.d.ts.map +1 -1
- package/dist/state/ChatState.d.ts +4 -0
- package/dist/state/ChatState.d.ts.map +1 -1
- package/dist/state/ChatState.js.map +1 -1
- package/dist/utils/check-is-trial.d.ts.map +1 -1
- package/dist/utils/check-is-trial.js +2 -6
- package/dist/utils/check-is-trial.js.map +1 -1
- package/dist/utils/planning-tool.d.ts +17 -0
- package/dist/utils/planning-tool.d.ts.map +1 -0
- package/dist/utils/planning-tool.js +32 -0
- package/dist/utils/planning-tool.js.map +1 -0
- package/dist/utils/update-tool-step.d.ts +3 -0
- package/dist/utils/update-tool-step.d.ts.map +1 -0
- package/dist/utils/update-tool-step.js +23 -0
- package/dist/utils/update-tool-step.js.map +1 -0
- package/dist/views/Agents/AgentsTab.d.ts.map +1 -1
- package/dist/views/Agents/AgentsTab.js +3 -4
- package/dist/views/Agents/AgentsTab.js.map +1 -1
- package/dist/views/Agents/useAgentFavorites.d.ts.map +1 -1
- package/dist/views/Agents/useAgentFavorites.js +1 -3
- package/dist/views/Agents/useAgentFavorites.js.map +1 -1
- package/dist/views/Chat/ChatMessage.d.ts +1 -1
- package/dist/views/Chat/ChatMessage.d.ts.map +1 -1
- package/dist/views/Chat/ChatMessage.js +21 -6
- package/dist/views/Chat/ChatMessage.js.map +1 -1
- package/dist/views/Chat/StepsList.d.ts +13 -2
- package/dist/views/Chat/StepsList.d.ts.map +1 -1
- package/dist/views/Chat/StepsList.js +156 -18
- package/dist/views/Chat/StepsList.js.map +1 -1
- package/dist/views/Chat/styled.d.ts.map +1 -1
- package/dist/views/Chat/styled.js +17 -10
- package/dist/views/Chat/styled.js.map +1 -1
- package/dist/views/MessageInput/AgentSelector.d.ts.map +1 -1
- package/dist/views/MessageInput/AgentSelector.js +2 -8
- package/dist/views/MessageInput/AgentSelector.js.map +1 -1
- package/dist/views/MessageInput/ButtonAgent.js +1 -1
- package/dist/views/MessageInput/ButtonAgent.js.map +1 -1
- package/dist/views/MessageInput/ButtonBar.d.ts +1 -2
- package/dist/views/MessageInput/ButtonBar.d.ts.map +1 -1
- package/dist/views/MessageInput/ButtonBar.js +2 -2
- package/dist/views/MessageInput/ButtonBar.js.map +1 -1
- package/dist/views/MessageInput/QuickCommandSelector.js +1 -1
- package/dist/views/MessageInput/QuickCommandSelector.js.map +1 -1
- package/dist/views/MessageInput/dictionary.d.ts +1 -1
- package/dist/views/MessageInput/index.d.ts +1 -2
- package/dist/views/MessageInput/index.d.ts.map +1 -1
- package/dist/views/MessageInput/index.js +2 -2
- package/dist/views/MessageInput/index.js.map +1 -1
- package/dist/views/Steps/FlowChart/NodeStep.js +1 -1
- package/dist/views/Steps/FlowChart/NodeStep.js.map +1 -1
- package/dist/views/Steps/FlowChart/layout.d.ts +1 -1
- package/dist/views/Steps/FlowChart/layout.d.ts.map +1 -1
- package/dist/views/Steps/FlowChart/layout.js +1 -0
- package/dist/views/Steps/FlowChart/layout.js.map +1 -1
- package/dist/views/Steps/FlowChart/types.d.ts +1 -1
- package/dist/views/Steps/FlowChart/types.d.ts.map +1 -1
- package/dist/views/Steps/StepModal.js +2 -2
- package/dist/views/Steps/StepModal.js.map +1 -1
- package/dist/views/Steps/dictionary.d.ts +1 -1
- package/dist/views/Steps/utils.d.ts +1 -1
- package/dist/views/Steps/utils.d.ts.map +1 -1
- package/package.json +3 -3
- package/src/StackspotAIWidget.tsx +1 -7
- package/src/app-metadata.json +5 -5
- package/src/chat-interceptors/send-message.ts +146 -2
- package/src/state/ChatEntry.ts +6 -6
- package/src/state/ChatState.ts +4 -0
- package/src/utils/check-is-trial.ts +2 -5
- package/src/utils/planning-tool.ts +41 -0
- package/src/utils/update-tool-step.tsx +27 -0
- package/src/views/Agents/AgentsTab.tsx +3 -4
- package/src/views/Agents/useAgentFavorites.ts +1 -3
- package/src/views/Chat/ChatMessage.tsx +25 -5
- package/src/views/Chat/StepsList.tsx +340 -44
- package/src/views/Chat/styled.ts +17 -10
- package/src/views/MessageInput/AgentSelector.tsx +2 -7
- package/src/views/MessageInput/ButtonAgent.tsx +1 -1
- package/src/views/MessageInput/ButtonBar.tsx +1 -3
- package/src/views/MessageInput/QuickCommandSelector.tsx +1 -1
- package/src/views/MessageInput/index.tsx +4 -4
- package/src/views/Steps/FlowChart/NodeStep.tsx +1 -1
- package/src/views/Steps/FlowChart/layout.ts +1 -0
- package/src/views/Steps/FlowChart/types.ts +1 -1
- package/src/views/Steps/StepModal.tsx +2 -2
package/src/state/ChatEntry.ts
CHANGED
|
@@ -4,7 +4,7 @@ import { pull } from 'lodash'
|
|
|
4
4
|
import { LabeledAgent } from './types'
|
|
5
5
|
|
|
6
6
|
export interface ActionDataClick {
|
|
7
|
-
name?: string,
|
|
7
|
+
name?: string,
|
|
8
8
|
value?: string[],
|
|
9
9
|
}
|
|
10
10
|
|
|
@@ -44,9 +44,9 @@ export interface ChatAction extends SerializableAction {
|
|
|
44
44
|
* @default button
|
|
45
45
|
*/
|
|
46
46
|
buttonType?: 'submit' | 'button',
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
47
|
+
/**
|
|
48
|
+
* @default lg
|
|
49
|
+
*/
|
|
50
50
|
size?: 'lg' | 'md' | 'sm',
|
|
51
51
|
}
|
|
52
52
|
|
|
@@ -149,7 +149,7 @@ export interface TextChatEntry {
|
|
|
149
149
|
/*
|
|
150
150
|
* Options for radio, checkbox or button type.
|
|
151
151
|
*/
|
|
152
|
-
options?: { color?: ColorSchemeName, label: string, value?: string, hasInput?: boolean
|
|
152
|
+
options?: { color?: ColorSchemeName, label: string, value?: string, hasInput?: boolean}[],
|
|
153
153
|
/**
|
|
154
154
|
* Name to be used in input type fields.
|
|
155
155
|
*/
|
|
@@ -211,7 +211,7 @@ export class ChatEntry {
|
|
|
211
211
|
type: isMd ? 'md' : 'text',
|
|
212
212
|
content,
|
|
213
213
|
name: fieldName,
|
|
214
|
-
hiddenContent,
|
|
214
|
+
hiddenContent,
|
|
215
215
|
data,
|
|
216
216
|
updated: new Date().toISOString(),
|
|
217
217
|
})
|
package/src/state/ChatState.ts
CHANGED
|
@@ -33,6 +33,10 @@ export interface ChatPropertiesWithOptionalFeatures {
|
|
|
33
33
|
* Whether or not the chat is in a loading state.
|
|
34
34
|
*/
|
|
35
35
|
isLoading?: boolean,
|
|
36
|
+
/**
|
|
37
|
+
* Whether or not the chat is planning.
|
|
38
|
+
*/
|
|
39
|
+
isPlaning?: boolean,
|
|
36
40
|
/**
|
|
37
41
|
* The value of the next message. This is the value of the text typed in the textarea below the chat.
|
|
38
42
|
*/
|
|
@@ -1,9 +1,6 @@
|
|
|
1
1
|
import { NetworkClient } from '@stack-spot/portal-network'
|
|
2
2
|
|
|
3
3
|
export const checkIsTrial = () => {
|
|
4
|
-
const
|
|
5
|
-
|
|
6
|
-
const trialInfo = NetworkClient.sessionManager?.getSession()?.getTokenData()?.trial_account_status
|
|
7
|
-
return !!trialInfo
|
|
8
|
-
} return false
|
|
4
|
+
const trialInfo = NetworkClient.sessionManager?.getSession()?.getTokenData()?.trial_account_status
|
|
5
|
+
return !!trialInfo
|
|
9
6
|
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
class PlanningToolDictionaryHelper {
|
|
2
|
+
static instance: PlanningToolDictionaryHelper | undefined
|
|
3
|
+
private toolExecutionIdPlanningStep: Record<string, string> = {}
|
|
4
|
+
private toolExecutionIdToolStep: Record<string, string> = {}
|
|
5
|
+
private stepId: Record<string, number> = {}
|
|
6
|
+
|
|
7
|
+
private constructor() {
|
|
8
|
+
PlanningToolDictionaryHelper.instance = this
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
static create() {
|
|
12
|
+
return PlanningToolDictionaryHelper.instance ?? new PlanningToolDictionaryHelper()
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
setMessageIdPlanningStepToolExecutionId(messageId: string, toolExecutionId: string){
|
|
16
|
+
this.toolExecutionIdPlanningStep[toolExecutionId] = messageId
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
setMessageIdToolStepToolExecutionId(messageId: string, toolExecutionId: string){
|
|
20
|
+
this.toolExecutionIdToolStep[toolExecutionId] = messageId
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
setMessageIdForStepId(messageId: number, stepId: string){
|
|
24
|
+
this.stepId[stepId] = messageId
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
getMessageIdFromStepId(stepId: string){
|
|
28
|
+
return this.stepId[stepId]
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
getMessageIdPlanningStepFromToolExecutionId(toolExecutionId: string){
|
|
32
|
+
return this.toolExecutionIdPlanningStep[toolExecutionId]
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
getMessageIdToolStepFromToolExecutionId(toolExecutionId: string){
|
|
36
|
+
return this.toolExecutionIdToolStep[toolExecutionId]
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
export const planningToolDictionaryHelper = PlanningToolDictionaryHelper.create()
|
|
41
|
+
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { ChatEntry, TextChatEntry } from '../state/ChatEntry'
|
|
2
|
+
import { planningToolDictionaryHelper } from './planning-tool'
|
|
3
|
+
|
|
4
|
+
export const updateToolStep = (messages: ChatEntry[], executionId: string,
|
|
5
|
+
newStatus: 'pending' | 'running' | 'success' | 'error' | 'awaiting_approval') => {
|
|
6
|
+
|
|
7
|
+
// if last message is a user message, no update in tool status is needed
|
|
8
|
+
if (messages[messages.length-1].getValue().agentType === 'user') return
|
|
9
|
+
|
|
10
|
+
const messageId = planningToolDictionaryHelper.getMessageIdPlanningStepFromToolExecutionId(executionId)
|
|
11
|
+
const message = messages.find((message) => `${message.id}` === messageId)
|
|
12
|
+
let update = false
|
|
13
|
+
const messageValue = message?.getValue()
|
|
14
|
+
messageValue?.steps?.map((step) => {
|
|
15
|
+
if (step.type === 'step') {
|
|
16
|
+
const tool = step.attempts?.[0].tools?.[0]
|
|
17
|
+
if (tool?.executionId === executionId && step.status !== newStatus) {
|
|
18
|
+
step.status = newStatus
|
|
19
|
+
update = true
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
})
|
|
23
|
+
|
|
24
|
+
if (update) {
|
|
25
|
+
message?.setValue({ ...messageValue as TextChatEntry })
|
|
26
|
+
}
|
|
27
|
+
}
|
|
@@ -7,7 +7,7 @@ import { useMemo, useState } from 'react'
|
|
|
7
7
|
import { NavigationComponent } from '../../components/ComponentNavigator'
|
|
8
8
|
import { DescribedRadioGroup } from '../../components/form/DescribedRadioGroup'
|
|
9
9
|
import { WorkspaceTabNavigator } from '../../components/WorkspaceTabNavigator'
|
|
10
|
-
import { useCurrentChat
|
|
10
|
+
import { useCurrentChat } from '../../context/hooks'
|
|
11
11
|
import { useRightPanel } from '../../right-panel/hooks'
|
|
12
12
|
import { ChatProperties } from '../../state/ChatState'
|
|
13
13
|
import { AgentDescription } from './AgentDescription'
|
|
@@ -28,11 +28,10 @@ export const AgentsTab = ({ visibility, workspaceId, agent, showSubmitButton = t
|
|
|
28
28
|
const { useFavorites, onAddFavorite, onRemoveFavorite } = useAgentFavorites()
|
|
29
29
|
const [submitEnabled, setSubmitEnabled] = useState(false)
|
|
30
30
|
const listFavorites = useFavorites()
|
|
31
|
-
const
|
|
32
|
-
const agentDefault = agentToolsClient.agentDefault.useQuery({ enabled: isAgentEnabled })
|
|
31
|
+
const agentDefault = agentToolsClient.agentDefault.useQuery()
|
|
33
32
|
const agents = workspaceId
|
|
34
33
|
? workspaceAiClient.getAgentFromWorkspaceAi.useQuery({ workspaceId }) as AgentResponseWithBuiltIn[]
|
|
35
|
-
: agentToolsClient.agents.useQuery({ visibility }
|
|
34
|
+
: agentToolsClient.agents.useQuery({ visibility })
|
|
36
35
|
|
|
37
36
|
const initialValue = useMemo<AgentResponseWithBuiltIn | undefined>(
|
|
38
37
|
() => {
|
|
@@ -1,10 +1,8 @@
|
|
|
1
1
|
/* eslint-disable filenames/match-regex */
|
|
2
2
|
import { agentToolsClient } from '@stack-spot/portal-network'
|
|
3
|
-
import { useCurrentChatState } from '../../context/hooks'
|
|
4
3
|
|
|
5
4
|
export function useAgentFavorites() {
|
|
6
|
-
const
|
|
7
|
-
const useFavorites = () => agentToolsClient.agents.useQuery({ visibility: 'favorite' }, { enabled: isAgentEnabled })
|
|
5
|
+
const useFavorites = () => agentToolsClient.agents.useQuery({ visibility: 'favorite' })
|
|
8
6
|
const [addFavorite, pendingAddFav] = agentToolsClient.addFavorite.useMutation()
|
|
9
7
|
const [removeFavorite, pendingRemoveFav] = agentToolsClient.removeFavorite.useMutation()
|
|
10
8
|
|
|
@@ -9,7 +9,7 @@ import { PhoneInput } from 'react-international-phone'
|
|
|
9
9
|
import 'react-international-phone/style.css'
|
|
10
10
|
import { FileDescription } from '../../components/FileDescription'
|
|
11
11
|
import { Markdown } from '../../components/Markdown'
|
|
12
|
-
import { useChatEntry, useCurrentChat, useWidget } from '../../context/hooks'
|
|
12
|
+
import { useChatEntry, useChatMessages, useCurrentChat, useCurrentChatState, useWidget } from '../../context/hooks'
|
|
13
13
|
import { useMidnightUpdateView } from '../../hooks/midnight-update-view'
|
|
14
14
|
import { ChatEntry, SerializableAction, TextChatEntry } from '../../state/ChatEntry'
|
|
15
15
|
import { useDateFormatter } from '../../utils/date'
|
|
@@ -17,7 +17,7 @@ import { toolById } from '../../utils/tools'
|
|
|
17
17
|
import { AgentInfo } from './AgentInfo'
|
|
18
18
|
import { useChatScrollToBottomEffect } from './chat-scroll'
|
|
19
19
|
import { onCopyAll, onCopyCode, onLikeOrDislike } from './events'
|
|
20
|
-
import { StepsList } from './StepsList'
|
|
20
|
+
import { StepsList, StepsPlaceholder, ViewToolsDetails } from './StepsList'
|
|
21
21
|
|
|
22
22
|
export interface CustomRenderResult {
|
|
23
23
|
/**
|
|
@@ -218,7 +218,21 @@ export const ChatMessage = ({ message, isLast, beforeMessage, afterMessage, cust
|
|
|
218
218
|
{ searchAgentsRequest: { ids: entry.tools || [''] } }, { enabled: !!entry.tools })
|
|
219
219
|
const [copied, setCopied] = useState(false)
|
|
220
220
|
const [showUserButtonCopy, setShowUserButtonCopy] = useState(false)
|
|
221
|
-
|
|
221
|
+
const isPlanning = useCurrentChatState('isPlaning') ?? false
|
|
222
|
+
|
|
223
|
+
// when we have a steps but we are not showing any content of the step
|
|
224
|
+
// (because it is a tool and the user has already answered the question)
|
|
225
|
+
// we do not want to show an avatar with empty content, so we hide the entire message
|
|
226
|
+
const toolsStep = entry.steps?.find(s => s.type === 'tool')
|
|
227
|
+
const messages = useChatMessages(chat.id)
|
|
228
|
+
const userHasAlreadyAnswered = useMemo(() => {
|
|
229
|
+
const messageIndex = messages.findIndex((messageItem) => messageItem.id === message.id)
|
|
230
|
+
if (messages.length-1 === messageIndex) return false
|
|
231
|
+
const nextMessage = messages[messageIndex+1].getValue()
|
|
232
|
+
return nextMessage.agentType === 'user'
|
|
233
|
+
}, [messages, messages.length])
|
|
234
|
+
const isMessageHidden = toolsStep && userHasAlreadyAnswered
|
|
235
|
+
|
|
222
236
|
useChatScrollToBottomEffect(ref, [entry])
|
|
223
237
|
useMidnightUpdateView()
|
|
224
238
|
|
|
@@ -343,7 +357,8 @@ export const ChatMessage = ({ message, isLast, beforeMessage, afterMessage, cust
|
|
|
343
357
|
widget.set('panel', 'resources')
|
|
344
358
|
}
|
|
345
359
|
|
|
346
|
-
return (entry.content || entry.error || !!entry.steps?.length
|
|
360
|
+
return (entry.content || entry.error || !!entry.steps?.length ||
|
|
361
|
+
entry.upload?.length) && (!isMessageHidden || !toolsStep || isPlanning) && (
|
|
347
362
|
<li key={entry.messageId} className={entry.agentType} ref={ref}>
|
|
348
363
|
<div className="chat-message-container"
|
|
349
364
|
onMouseEnter={entry.agentType === 'user' ? () => setShowUserButtonCopy(true) : undefined}
|
|
@@ -356,11 +371,15 @@ export const ChatMessage = ({ message, isLast, beforeMessage, afterMessage, cust
|
|
|
356
371
|
{!!entry.badges?.length && <div className="badges">
|
|
357
372
|
{entry.badges.map((b, index) => <Badge key={index} colorPalette={b.color ?? 'cyan'} appearance="square">{b.label}</Badge>)}
|
|
358
373
|
</div>}
|
|
374
|
+
|
|
375
|
+
{!!entry.steps?.length && <StepsList steps={entry.steps} chatId={chat.id} messageId={message.id}
|
|
376
|
+
userHasAlreadyAnswered={userHasAlreadyAnswered} />}
|
|
377
|
+
|
|
359
378
|
{renderContent()}
|
|
360
379
|
|
|
361
|
-
{!!entry.steps?.length && <StepsList steps={entry.steps} chatId={chat.id} messageId={message.id} />}
|
|
362
380
|
</div>
|
|
363
381
|
)}
|
|
382
|
+
{isPlanning && entry.agentType === 'bot' && isLast && <StepsPlaceholder /> }
|
|
364
383
|
|
|
365
384
|
{entry.error && <Alert type="error">{entry.error}</Alert>}
|
|
366
385
|
</div>
|
|
@@ -416,6 +435,7 @@ export const ChatMessage = ({ message, isLast, beforeMessage, afterMessage, cust
|
|
|
416
435
|
</ImageBox>
|
|
417
436
|
)})}
|
|
418
437
|
</Button>
|
|
438
|
+
<ViewToolsDetails chatId={chat.id} />
|
|
419
439
|
</div>}
|
|
420
440
|
|
|
421
441
|
{shouldShowFooter && <div className="message-footer">
|