Skip to content
This repository was archived by the owner on Jul 9, 2025. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from 11 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -278,7 +278,14 @@ export function CreateBotV2(props: CreateBotProps) {
</div>
</div>
<DialogFooter>
<Link href={templateRequestUrl} styles={{ root: { fontSize: '12px', float: 'left' } }} target="_blank">
<Link
href={templateRequestUrl}
styles={{ root: { fontSize: '12px', float: 'left' } }}
target="_blank"
onClick={() => {
TelemetryClient.track('NeedAnotherTemplateCLicked');
Comment thread
pavolum marked this conversation as resolved.
Outdated
}}
>
<FontIcon iconName="ChatInviteFriend" style={{ marginRight: '5px' }} />
{formatMessage('Need another template? Send us a request')}
</Link>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,11 @@ import querystring from 'query-string';
import axios from 'axios';
import { useRecoilValue } from 'recoil';

import { DialogCreationCopy } from '../../../constants';
import { CreationFlowStatus, DialogCreationCopy } from '../../../constants';
import { getAliasFromPayload, isElectron } from '../../../utils/electronUtil';
import { userHasNodeInstalledState } from '../../../recoilModel';
import { creationFlowTypeState, userHasNodeInstalledState } from '../../../recoilModel';
import { InstallDepModal } from '../../InstallDepModal';
import TelemetryClient from '../../../telemetry/TelemetryClient';

import { CreateBotV2 } from './CreateBot';

Expand All @@ -40,6 +41,7 @@ export function CreateOptionsV2(props: CreateOptionsProps) {
const { templates, onDismiss, onNext, onJumpToOpenModal, fetchReadMe } = props;
const [showNodeModal, setShowNodeModal] = useState(false);
const userHasNode = useRecoilValue(userHasNodeInstalledState);
const creationFlowType = useRecoilValue(creationFlowTypeState);

useEffect(() => {
// open bot directly if alias exist.
Expand All @@ -58,13 +60,21 @@ export function CreateOptionsV2(props: CreateOptionsProps) {
}
})
.catch((e) => {
TelemetryClient.track('NewBotDialogOpened', {
Comment thread
pavolum marked this conversation as resolved.
Outdated
isSkillBot: false,
fromAbsHandoff: true,
});
setIsOpenOptionsModal(true);
});
});

return;
}
}
TelemetryClient.track('NewBotDialogOpened', {
isSkillBot: creationFlowType === 'Skill',
fromAbsHandoff: false,
});
setIsOpenCreateModal(true);
}, [props.location?.search]);
const dialogWrapperProps = DialogCreationCopy.CREATE_OPTIONS;
Expand All @@ -89,7 +99,7 @@ export function CreateOptionsV2(props: CreateOptionsProps) {
},
};

const options: IChoiceGroupOption[] = [
const getOptions = (): IChoiceGroupOption[] => [
{ key: 'Create', text: formatMessage('Create a new bot') },
{ key: 'Connect', text: formatMessage('Connect to an existing bot') },
];
Expand Down Expand Up @@ -121,7 +131,7 @@ export function CreateOptionsV2(props: CreateOptionsProps) {
dialogType={DialogTypes.Customer}
onDismiss={onDismiss}
>
<ChoiceGroup required defaultSelectedKey="B" options={options} onChange={handleChange} />
<ChoiceGroup required defaultSelectedKey="B" options={getOptions()} onChange={handleChange} />
Comment thread
pavolum marked this conversation as resolved.
Outdated
<DialogFooter>
<PrimaryButton data-testid="NextStepButton" text={formatMessage('Open')} onClick={handleJumpToNext} />
<DefaultButton text={formatMessage('Cancel')} onClick={onDismiss} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -181,7 +181,10 @@ const CreationFlowV2: React.FC<CreationFlowProps> = () => {
path="create/:runtimeLanguage/:templateId"
updateFolder={updateFolder}
onCurrentPathUpdate={updateCurrentPath}
onDismiss={handleDismiss}
onDismiss={() => {
TelemetryClient.track('CreationCancelled');
Comment thread
benbrown marked this conversation as resolved.
handleDismiss();
}}
onSubmit={handleSubmit}
/>
<DefineConversationV2
Expand All @@ -190,14 +193,20 @@ const CreationFlowV2: React.FC<CreationFlowProps> = () => {
path="create/:templateId"
updateFolder={updateFolder}
onCurrentPathUpdate={updateCurrentPath}
onDismiss={handleDismiss}
onDismiss={() => {
TelemetryClient.track('CreationCancelled');
handleDismiss();
}}
onSubmit={handleSubmit}
/>
<CreateOptionsV2
fetchReadMe={fetchReadMe}
path="create"
templates={templateProjects}
onDismiss={handleDismiss}
onDismiss={() => {
TelemetryClient.track('CreationCancelled');
handleDismiss();
}}
onJumpToOpenModal={handleJumpToOpenModal}
onNext={handleCreateNext}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import querystring from 'query-string';
import { FontWeights } from '@uifabric/styling';
import { DialogWrapper, DialogTypes } from '@bfc/ui-shared';
import { useRecoilValue } from 'recoil';
import { csharpFeedKey, functionsRuntimeKey, nodeFeedKey, QnABotTemplateId } from '@bfc/shared';
import { csharpFeedKey, FeedType, functionsRuntimeKey, nodeFeedKey, QnABotTemplateId } from '@bfc/shared';
import { RuntimeType, webAppRuntimeKey } from '@bfc/shared';
import { Dropdown, IDropdownOption } from 'office-ui-fabric-react/lib/Dropdown';
import camelCase from 'lodash/camelCase';
Expand All @@ -29,6 +29,8 @@ import { ImportSuccessNotificationWrapper } from '../../ImportModal/ImportSucces
import { dispatcherState, templateProjectsState } from '../../../recoilModel';
import { LocationSelectContent } from '../LocationSelectContent';
import { getAliasFromPayload, Profile } from '../../../utils/electronUtil';
import TelemetryClient from '../../../telemetry/TelemetryClient';
import { ImportFailedModal } from '../../ImportModal/ImportFailedModal';

// -------------------- Styles -------------------- //

Expand Down Expand Up @@ -291,6 +293,13 @@ const DefineConversationV2: React.FC<DefineConversationProps> = (props) => {
dataToSubmit.alias = await getAliasFromPayload(source, payload);
}
}
// creationExecuted: { runtimeChoice: RuntimeType; runtimeLanguage: FeedType; isPva: boolean; isAbs: boolean };
Comment thread
pavolum marked this conversation as resolved.
Outdated
TelemetryClient.track('creationExecuted', {
Comment thread
pavolum marked this conversation as resolved.
Outdated
runtimeChoice: dataToSubmit?.runtimeType,
runtimeLanguage: dataToSubmit?.runtimeLanguage as FeedType,
isPva: isImported,
isAbs: !!dataToSubmit?.source,
});
onSubmit({ ...dataToSubmit }, templateId || '');
},
[hasErrors, formData]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -175,12 +175,14 @@ export const PublishProfileDialog: React.FC<PublishProfileDialogProps> = (props)

// require tenant id to be set by plugin (handles multiple tenant scenario)
if (!tenantId) {
const errorMessage = formatMessage(
'An Azure tenant must be set in order to provision resources. Try recreating the publish profile and try again.'
);
TelemetryClient.track('ProvisionProfileCreateFailure', { message: errorMessage });
Comment thread
pavolum marked this conversation as resolved.
Outdated
const notification = createNotification({
type: 'error',
title: formatMessage('Error provisioning.'),
description: formatMessage(
'An Azure tenant must be set in order to provision resources. Try recreating the publish profile and try again.'
),
description: errorMessage,
});
addNotification(notification);
return;
Expand Down
3 changes: 3 additions & 0 deletions Composer/packages/client/src/pages/publish/PublishDialog.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ import { TextField } from 'office-ui-fabric-react/lib/TextField';
import formatMessage from 'format-message';
import { CheckboxVisibility, DetailsList } from 'office-ui-fabric-react/lib/DetailsList';

import TelemetryClient from '../../telemetry/TelemetryClient';

import { BotStatus } from './type';

export const PublishDialog = (props) => {
Expand Down Expand Up @@ -86,6 +88,7 @@ export const PublishDialog = (props) => {
setShowItems(cleanedItems);
};
const submit = async () => {
TelemetryClient.track('PublishStartBtnClick');
props.onDismiss();
await props.onSubmit(showItems);
cleanComments();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,10 @@ export const provisionDispatcher = () => {
notification.id
);
} catch (error) {
TelemetryClient.track('ProvisionProfileCreateFailure', {
message: error.response?.data || 'Error when provision target',
Comment thread
pavolum marked this conversation as resolved.
});

// set notification
const notification = createNotification(
getProvisionFailureNotification(error.response?.data || 'Error when provision target')
Expand Down Expand Up @@ -164,6 +168,9 @@ export const provisionDispatcher = () => {
if (response.data.status !== 500) {
notification = getProvisionPendingNotification(response.data.message);
} else {
TelemetryClient.track('ProvisionProfileCreateFailure', {
message: 'Error when provisioning',
Comment thread
pavolum marked this conversation as resolved.
Outdated
});
notification = getProvisionFailureNotification(response.data.message);
isCleanTimer = true;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ import * as qnaUtil from '../../utils/qnaUtil';
import { ClientStorage } from '../../utils/storage';
import { RuntimeOutputData } from '../types';
import { checkIfFunctionsMissing, missingFunctionsError } from '../../utils/runtimeErrors';
import TelemetryClient from '../../telemetry/TelemetryClient';

import { BotStatus, Text } from './../../constants';
import httpClient from './../../utils/httpUtil';
Expand All @@ -43,6 +44,7 @@ export const publishStorage = new ClientStorage(window.sessionStorage, 'publish'

export const publisherDispatcher = () => {
const publishFailure = async ({ set }: CallbackInterface, title: string, error, target, projectId: string) => {
TelemetryClient.track('PublishFailure', { message: title });
Comment thread
pavolum marked this conversation as resolved.
Outdated
if (target.name === defaultPublishConfig.name) {
set(botStatusState(projectId), BotStatus.failed);
set(botBuildTimeErrorState(projectId), { ...error, title });
Expand All @@ -59,6 +61,7 @@ export const publisherDispatcher = () => {
};

const publishSuccess = async ({ set }: CallbackInterface, projectId: string, data: PublishResult, target) => {
TelemetryClient.track('PublishSuccess');
const { endpointURL, status } = data;
if (target.name === defaultPublishConfig.name) {
if (status === PUBLISH_SUCCESS && endpointURL) {
Expand Down
16 changes: 15 additions & 1 deletion Composer/packages/types/src/telemetry.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

import { FeedType, RuntimeType } from './creation';
import { TelemetrySettings } from './settings';

export type ServerSettings = Partial<{ telemetry: TelemetrySettings }>;
Expand Down Expand Up @@ -120,6 +121,10 @@ type ResourcesItem = {
};

type PublishingEvents = {
CreateProvisionStarted: { newResourceGroup: boolean };
PublishStartBtnClick: undefined;
PublishSuccess: undefined;
PublishFailure: { message: string };
NewPublishingProfileStarted: undefined;
NewPublishingProfileSaved: { type: string; msAppId?: string; subscriptionId?: string };
PublishingProfileStarted: { target: string; projectId: string; msAppId?: string; subscriptionId?: string };
Expand All @@ -132,6 +137,14 @@ type PublishingEvents = {
ProvisionCancel: undefined;
ProvisionShowHandoff: undefined;
ProvisionAddResourcesCancel: undefined;
ProvisionProfileCreateFailure: { message: string };
};

type CreationEvents = {
NewBotDialogOpened: { fromAbsHandoff: boolean; isSkillBot: boolean };
CreationCancelled: undefined;
NeedAnotherTemplateCLicked: undefined;
Comment thread
pavolum marked this conversation as resolved.
Outdated
creationExecuted: { runtimeChoice: RuntimeType; runtimeLanguage: FeedType; isPva: boolean; isAbs: boolean };
Comment thread
pavolum marked this conversation as resolved.
Outdated
};

type AppSettingsEvents = {
Expand Down Expand Up @@ -238,7 +251,8 @@ export type TelemetryEvents = ApplicationEvents &
WebChatEvents &
LuEditorEvents &
OrchestratorEvents &
PropertyEditorEvents;
PropertyEditorEvents &
CreationEvents;

export type TelemetryEventName = keyof TelemetryEvents;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1195,6 +1195,7 @@ export const AzureProvisionDialog: React.FC = () => {
text={formatMessage('Create')}
onClick={() => {
const selectedResources = formData.requiredResources.concat(formData.enabledResources);
telemetryClient?.track('CreateProvisionStarted', { newResourceGroup: isNewResourceGroup });
onSubmit({
tenantId: formData.tenantId,
subscription: formData.subscriptionId,
Expand Down