Skip to content

Commit

Permalink
fix: Throttle restart conversation (microsoft#7824)
Browse files Browse the repository at this point in the history
* Throttle restart

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

* Remove await

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

* Updated throttle time

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

* Unit test update

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

* Enable only on connected

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

* removed if

Signed-off-by: Srinaath Ravichandran <srravich@microsoft.com>

Co-authored-by: Srinaath Ravichandran <srravich@microsoft.com>
  • Loading branch information
srinaath and Srinaath Ravichandran committed May 14, 2021
1 parent 376d87b commit e09a9f7
Show file tree
Hide file tree
Showing 3 changed files with 48 additions and 21 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ export type WebChatHeaderProps = {
onSaveTranscript: (conversationId: string) => void;
onOpenBotInEmulator: () => void;
onCloseWebChat: () => void;
isRestartButtonDisabled: boolean;
};

export const WebChatHeader: React.FC<WebChatHeaderProps> = ({
Expand All @@ -54,6 +55,7 @@ export const WebChatHeader: React.FC<WebChatHeaderProps> = ({
onOpenBotInEmulator: openBotInEmulator,
onSetRestartOption,
onCloseWebChat,
isRestartButtonDisabled,
}) => {
const menuProps: IContextualMenuProps = {
items: [
Expand Down Expand Up @@ -114,6 +116,7 @@ export const WebChatHeader: React.FC<WebChatHeaderProps> = ({
split
aria-roledescription="split button"
ariaLabel="restart-conversation"
disabled={isRestartButtonDisabled}
iconProps={{ iconName: 'Refresh' }}
menuProps={menuProps}
splitButtonAriaLabel="See 2 other restart conversation options"
Expand Down
63 changes: 42 additions & 21 deletions Composer/packages/client/src/components/WebChat/WebChatPanel.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

import React, { useMemo, useEffect, useState, useRef } from 'react';
import React, { useMemo, useEffect, useState, useRef, useCallback } from 'react';
import { useRecoilValue } from 'recoil';
import {
ConversationActivityTraffic,
Expand All @@ -11,6 +11,7 @@ import {
import { AxiosResponse } from 'axios';
import formatMessage from 'format-message';
import { v4 as uuid } from 'uuid';
import throttle from 'lodash/throttle';

import TelemetryClient from '../../telemetry/TelemetryClient';
import { BotStatus } from '../../constants';
Expand Down Expand Up @@ -55,9 +56,10 @@ export const WebChatPanel: React.FC<WebChatPanelProps> = ({
const { projectId, botUrl, secrets, botName, activeLocale, botStatus } = botData;
const [chats, setChatData] = useState<Record<string, ChatData>>({});
const [currentConversation, setCurrentConversation] = useState<string>('');
const [currentRestartOption, onSetRestartOption] = useState<RestartOption>(RestartOption.NewUserID);
const [isRestartButtonDisabled, setIsRestartButtonDisabled] = useState(false);
const conversationService = useMemo(() => new ConversationService(directlineHostUrl), [directlineHostUrl]);
const webChatPanelRef = useRef<HTMLDivElement>(null);
const [currentRestartOption, onSetRestartOption] = useState<RestartOption>(RestartOption.NewUserID);
const webChatTrafficChannel = useRef<WebSocket>();

useEffect(() => {
Expand Down Expand Up @@ -134,6 +136,10 @@ export const WebChatPanel: React.FC<WebChatPanelProps> = ({
}
}, [botUrl]);

useEffect(() => {
setIsRestartButtonDisabled(botStatus !== BotStatus.connected);
}, [botStatus]);

const sendInitialActivities = async (chatData: ChatData) => {
try {
await conversationService.sendInitialActivity(chatData.conversationId, [chatData.user]);
Expand Down Expand Up @@ -176,24 +182,36 @@ export const WebChatPanel: React.FC<WebChatPanelProps> = ({
};
}, [isWebChatPanelVisible]);

const onRestartConversationClick = async (oldConversationId: string, requireNewUserId: boolean) => {
try {
TelemetryClient.track('WebChatConversationRestarted', {
restartType: requireNewUserId ? 'NewUserId' : 'SameUserId',
});
const chatData = await conversationService.restartConversation(
chats[oldConversationId],
requireNewUserId,
activeLocale,
secrets
);
setConversationData(chatData);
sendInitialActivities(chatData);
clearWebChatLogs(projectId);
} catch (ex) {
// DL errors are handled through socket above.
}
};
const handleThrottledRestart: (oldChatData: ChatData, requireNewUserId: boolean) => void = useCallback(
throttle(
async (oldChatData: ChatData, requireNewUserId: boolean) => {
try {
setIsRestartButtonDisabled(true);
const chatData = await conversationService.restartConversation(
oldChatData,
requireNewUserId,
activeLocale,
secrets
);

TelemetryClient.track('WebChatConversationRestarted', {
restartType: requireNewUserId ? 'NewUserId' : 'SameUserId',
});

setConversationData(chatData);
sendInitialActivities(chatData);
clearWebChatLogs(projectId);
} catch (ex) {
// DL errors are handled through socket above.
} finally {
setIsRestartButtonDisabled(false);
}
},
1000,
{ leading: true }
),
[]
);

const onSaveTranscriptClick = async (conversationId: string) => {
try {
Expand Down Expand Up @@ -233,6 +251,7 @@ export const WebChatPanel: React.FC<WebChatPanelProps> = ({
botName={botName}
conversationId={currentConversation}
currentRestartOption={currentRestartOption}
isRestartButtonDisabled={isRestartButtonDisabled}
onCloseWebChat={() => {
setWebChatPanelVisibility(false);
TelemetryClient.track('WebChatPaneClosed');
Expand All @@ -241,7 +260,9 @@ export const WebChatPanel: React.FC<WebChatPanelProps> = ({
openBotInEmulator(projectId);
TelemetryClient.track('EmulatorButtonClicked', { isRoot: true, projectId, location: 'WebChatPane' });
}}
onRestartConversation={onRestartConversationClick}
onRestartConversation={(oldConversationId: string, requireNewUserId: boolean) =>
handleThrottledRestart(chats[oldConversationId], requireNewUserId)
}
onSaveTranscript={onSaveTranscriptClick}
onSetRestartOption={onSetRestartOption}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ describe('<WebChatHeader />', () => {
onSaveTranscript: mockOnSaveTranscript,
onOpenBotInEmulator: jest.fn(),
onCloseWebChat: jest.fn(),
isRestartButtonDisabled: false,
};

afterEach(() => {
Expand All @@ -43,6 +44,7 @@ describe('<WebChatHeader />', () => {
onSaveTranscript: mockOnSaveTranscript,
onOpenBotInEmulator: jest.fn(),
onCloseWebChat: jest.fn(),
isRestartButtonDisabled: false,
};

const { findByText } = render(<WebChatHeader {...props} />);
Expand All @@ -68,6 +70,7 @@ describe('<WebChatHeader />', () => {
onSaveTranscript: mockOnSaveTranscript,
onOpenBotInEmulator: jest.fn(),
onCloseWebChat: jest.fn(),
isRestartButtonDisabled: false,
};

const { findByText } = render(<WebChatHeader {...props} />);
Expand Down

0 comments on commit e09a9f7

Please sign in to comment.