feat: enable internal telemetry (#431)

* add packages

* initial setup

* tracking only events and page views

* add key and check if key is present and insights instantiated
This commit is contained in:
alex-krasn 2020-07-23 09:04:55 -07:00 коммит произвёл GitHub
Родитель f4b4d5ded4
Коммит 41294c8aa1
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
10 изменённых файлов: 230 добавлений и 25 удалений

Просмотреть файл

@ -17,6 +17,8 @@
"dependencies": {
"@azure/storage-blob": "10.3.0",
"@fluentui/react": "^7.117.2",
"@microsoft/applicationinsights-react-js": "^3.0.1",
"@microsoft/applicationinsights-web": "^2.5.6",
"axios": "^0.19.0",
"bootstrap": "^4.4.1",
"chart.js": "^2.9.3",

Просмотреть файл

@ -7,7 +7,6 @@ import { connect } from "react-redux";
import { BrowserRouter } from "react-router-dom";
import { ToastContainer } from "react-toastify";
import { IAppError, IApplicationState, IProject, ErrorCode } from "./models/applicationState";
import { strings } from "./common/strings";
import IAppErrorActions, * as appErrorActions from "./redux/actions/appErrorActions";
import { ErrorHandler } from "./react/components/common/errorHandler/errorHandler";
import { KeyboardManager } from "./react/components/common/keyboardManager/keyboardManager";
@ -18,7 +17,8 @@ import { Sidebar } from "./react/components/shell/sidebar";
import { StatusBar } from "./react/components/shell/statusBar";
import { StatusBarMetrics } from "./react/components/shell/statusBarMetrics";
import { TitleBar } from "./react/components/shell/titleBar";
import { SkipButton } from "./react/components/shell/skipButton";
import { getAppInsights } from './services/telemetryService';
import TelemetryProvider from "./providers/telemetry/telemetryProvider";
import "./App.scss";
import "react-toastify/dist/ReactToastify.css";
@ -47,11 +47,11 @@ function mapDispatchToProps(dispatch) {
*/
@connect(mapStateToProps, mapDispatchToProps)
export default class App extends React.Component<IAppProps> {
appInsights: any = null;
constructor(props, context) {
super(props, context);
this.state = {
currentProject: this.props.currentProject,
currentProject: this.props.currentProject,
};
}
@ -73,28 +73,29 @@ export default class App extends React.Component<IAppProps> {
onError={this.props.actions.showError}
onClearError={this.props.actions.clearError} />
{/* Don't render app contents during a render error */}
<SkipButton skipTo="skipToMainContent">{strings.common.skipToMainContent}</SkipButton>
{(!this.props.appError || this.props.appError.errorCode !== ErrorCode.GenericRenderError) &&
<KeyboardManager>
<BrowserRouter>
<div className={`app-shell platform-${platform}`}>
<TitleBar icon="TagGroup">
<div className="app-shortcuts-menu-icon">
<KeyboardShortcuts />
<TelemetryProvider after={() => { this.appInsights = getAppInsights() }}>
<div className={`app-shell platform-${platform}`}>
<TitleBar icon="TagGroup">
<div className="app-shortcuts-menu-icon">
<KeyboardShortcuts />
</div>
<div className="app-help-menu-icon">
<HelpMenu />
</div>
</TitleBar>
<div className="app-main">
<Sidebar project={this.props.currentProject} />
<MainContentRouter />
</div>
<StatusBar>
<StatusBarMetrics project={this.props.currentProject} />
</StatusBar>
<ToastContainer className="frtt-toast-container" role="alert" />
</div>
<div className="app-help-menu-icon">
<HelpMenu />
</div>
</TitleBar>
<div className="app-main">
<Sidebar project={this.props.currentProject} />
<MainContentRouter />
</div>
<StatusBar>
<StatusBarMetrics project={this.props.currentProject} />
</StatusBar>
<ToastContainer className="frtt-toast-container" role="alert"/>
</div>
</TelemetryProvider>
</BrowserRouter>
</KeyboardManager>
}

Просмотреть файл

@ -42,4 +42,5 @@ export const constants = {
pdfjsCMapUrl(version: string) {
return `https://fotts.azureedge.net/npm/pdfjs-dist/${version}/cmaps/`;
},
insightsKey: "dd15609c-c451-4e00-b193-abdf3e1d36e8",
};

Просмотреть файл

@ -0,0 +1,40 @@
import React, {Component, Fragment} from 'react';
import {withAITracking} from '@microsoft/applicationinsights-react-js';
import {ai} from '../../services/telemetryService';
import {withRouter} from 'react-router-dom';
import { constants } from '../../common/constants';
/**
* This Component provides telemetry with Azure App Insights
*
* NOTE: the package '@microsoft/applicationinsights-react-js' has a HOC withAITracking that requires this to be a Class Component rather than a Functional Component
*/
class TelemetryProvider extends Component {
state = {
initialized: false
};
componentDidMount() {
const {history} = this.props;
const { initialized } = this.state;
const AppInsightsInstrumentationKey = constants.insightsKey; // <-Paste your AppInsightsInstrumentationKey here
if (!Boolean(initialized) && Boolean(AppInsightsInstrumentationKey) && Boolean(history)) {
ai.initialize(AppInsightsInstrumentationKey, history);
this.setState({initialized: true});
}
this.props.after();
}
render() {
const {children} = this.props;
return (
<Fragment >
{children}
</Fragment>
);
}
}
export default withRouter(withAITracking(ai.reactPlugin, TelemetryProvider));

Просмотреть файл

@ -6,6 +6,7 @@ import { Customizer, IColumn, ICustomizations, Modal, DetailsList, SelectionMode
import { getDarkGreyTheme, getPrimaryGreenTheme, getPrimaryGreyTheme } from "../../../../common/themes";
import { strings } from "../../../../common/strings";
import { IModel } from "./modelCompose";
import { getAppInsights } from '../../../../services/telemetryService';
export interface IComposeModelViewProps {
@ -23,6 +24,7 @@ export default class ComposeModelView extends React.Component<IComposeModelViewP
*
*/
private modelName: string = "";
private appInsights: any = null;
constructor(props) {
super(props);
@ -33,6 +35,10 @@ export default class ComposeModelView extends React.Component<IComposeModelViewP
}
}
public componentDidMount() {
this.appInsights = getAppInsights();
}
public render() {
const columns: IColumn[] = [
{
@ -145,7 +151,10 @@ export default class ComposeModelView extends React.Component<IComposeModelViewP
this.props.onComposeConfirm(this.modelName);
this.setState({
hideModal: true,
})
});
}
if (this.appInsights) {
this.appInsights.trackEvent({ name: "MODEL_COMPOSE_EVENT" });
}
}

Просмотреть файл

@ -39,7 +39,7 @@ import IAppTitleActions, * as appTitleActions from "../../../../redux/actions/ap
import ComposeModelView from "./composeModelView";
import { ViewSelection } from "./viewSelection";
import PreventLeaving from "../../common/preventLeaving/preventLeaving";
import allSettled from "promise.allsettled"
import allSettled from "promise.allsettled";
export interface IModelComposePageProps extends RouteComponentProps, React.Props<ModelComposePage> {
recentProjects: IProject[];

Просмотреть файл

@ -39,6 +39,7 @@ import { getPrimaryGreenTheme, getPrimaryWhiteTheme,
import axios from "axios";
import { IAnalyzeModelInfo } from './predictResult';
import RecentModelsView from "./recentModelsView";
import { getAppInsights } from '../../../../services/telemetryService';
pdfjsLib.GlobalWorkerOptions.workerSrc = constants.pdfjsWorkerSrc(pdfjsLib.version);
const cMapUrl = constants.pdfjsCMapUrl(pdfjsLib.version);
@ -109,6 +110,8 @@ function mapDispatchToProps(dispatch) {
@connect(mapStateToProps, mapDispatchToProps)
export default class PredictPage extends React.Component<IPredictPageProps, IPredictPageState> {
private appInsights: any = null;
public state: IPredictPageState = {
couldNotGetRecentModel: false,
selectionIndexTracker: -1,
@ -149,6 +152,7 @@ export default class PredictPage extends React.Component<IPredictPageProps, IPre
if (projectId) {
await this.loadProject(projectId);
}
this.appInsights = getAppInsights();
document.title = strings.predict.title + " - " + strings.appName;
}
@ -678,6 +682,9 @@ export default class PredictPage extends React.Component<IPredictPageProps, IPre
isPredicting: false,
});
});
if (this.appInsights) {
this.appInsights.trackEvent({ name: "ANALYZE_EVENT" });
}
}
private getPageCount() {

Просмотреть файл

@ -25,6 +25,7 @@ import url from "url";
import PreventLeaving from "../../common/preventLeaving/preventLeaving";
import ServiceHelper from "../../../../services/serviceHelper";
import { getPrimaryGreenTheme, getGreenWithWhiteBackgroundTheme } from "../../../../common/themes";
import { getAppInsights } from '../../../../services/telemetryService';
export interface ITrainPageProps extends RouteComponentProps, React.Props<TrainPage> {
connections: IConnection[];
@ -74,6 +75,7 @@ function mapDispatchToProps(dispatch) {
@connect(mapStateToProps, mapDispatchToProps)
export default class TrainPage extends React.Component<ITrainPageProps, ITrainPageState> {
private appInsights: any = null;
constructor(props) {
super(props);
@ -102,6 +104,7 @@ export default class TrainPage extends React.Component<ITrainPageProps, ITrainPa
this.showCheckboxPreview(project);
this.updateCurrTrainRecord(this.getProjectTrainRecord());
}
this.appInsights = getAppInsights();
document.title = strings.train.title + " - " + strings.appName;
}
@ -252,6 +255,9 @@ export default class TrainPage extends React.Component<ITrainPageProps, ITrainPa
trainMessage: err.message,
});
});
if (this.appInsights) {
this.appInsights.trackEvent({ name: "TRAIN_MODEL_EVENT" });
}
}
private handleViewTypeClick = (viewType: "tableView" | "chartView"): void => {

Просмотреть файл

@ -0,0 +1,51 @@
import {ApplicationInsights} from '@microsoft/applicationinsights-web';
import {ReactPlugin} from '@microsoft/applicationinsights-react-js';
let reactPlugin = null;
let appInsights = null;
/**
* Create the App Insights Telemetry Service
* @return {{reactPlugin: ReactPlugin, appInsights: Object, initialize: Function}} - Object
*/
const createTelemetryService = () => {
/**
* Initialize the Application Insights class
* @param {string} instrumentationKey - Application Insights Instrumentation Key
* @param {Object} browserHistory - client's browser history, supplied by the withRouter HOC
* @return {void}
*/
const initialize = (instrumentationKey: string, browserHistory: any): void => {
if (!browserHistory) {
throw new Error('Could not initialize Telemetry Service');
}
if (!instrumentationKey) {
throw new Error('Telemetry Service Instrumentation key not provided.')
}
reactPlugin = new ReactPlugin();
appInsights = new ApplicationInsights({
config: {
instrumentationKey,
maxBatchInterval: 0,
disableAjaxTracking: true,
enableUnhandledPromiseRejectionTracking: true,
extensions: [reactPlugin],
extensionConfig: {
[reactPlugin.identifier]: {
history: browserHistory
}
}
}
});
appInsights.loadAppInsights();
};
return {reactPlugin, appInsights, initialize};
};
export const ai = createTelemetryService();
export const getAppInsights = () => appInsights;

Просмотреть файл

@ -1421,6 +1421,94 @@
"@types/istanbul-reports" "^1.1.1"
"@types/yargs" "^13.0.0"
"@microsoft/applicationinsights-analytics-js@2.5.6":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-analytics-js/-/applicationinsights-analytics-js-2.5.6.tgz#0a2862aa896eb0d467a626b332e2c65ef821ec87"
integrity sha512-ExNn0Z1Q5mfYqlKgsiXLXWkiSf2XaK5LlVJ9TJQjL2gv6EPXVjKU/6QaFH5ekBmKvvt2bsBK/I/nUUt2n3eiQg==
dependencies:
"@microsoft/applicationinsights-common" "2.5.6"
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/dynamicproto-js" "^0.5.2"
"@microsoft/applicationinsights-channel-js@2.5.6":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-channel-js/-/applicationinsights-channel-js-2.5.6.tgz#ea97f6d0b4eaccddbdbca36287d5a1f7aff6dd9e"
integrity sha512-J0PKqkOwlS5jGX6LylQ6DPLrw6HAMb0bLbs5w9a+jNFXm3yB1RPtxhlaylZZG7BO+4KjfanX2PdBesE2wOtLcw==
dependencies:
"@microsoft/applicationinsights-common" "2.5.6"
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/applicationinsights-common@2.5.6", "@microsoft/applicationinsights-common@^2.5.4":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-common/-/applicationinsights-common-2.5.6.tgz#ce93e719ccdbfb264c1f159ef1809762eda9447d"
integrity sha512-ISrUcIHii2WbEG9diOqlJSM42t5qvHCfWCyatQUwJTW3fS+JDS4Kbq4vBEeMHRW5ka2SFSkO40uMwcZxL0SoOw==
dependencies:
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/applicationinsights-core-js@2.5.6", "@microsoft/applicationinsights-core-js@^2.5.4":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-core-js/-/applicationinsights-core-js-2.5.6.tgz#c18e76c65d1478599f3323d798375e543ee2a421"
integrity sha512-KDepyGJIMc0CpFw5GVVwG9MYl8ztDGdVpCFPaY+hrYN8bkzSb2vHjT/jV8pefcSkmrDOK8THqm2nTYnPo127ag==
dependencies:
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/dynamicproto-js" "^0.5.2"
"@microsoft/applicationinsights-dependencies-js@2.5.6":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-dependencies-js/-/applicationinsights-dependencies-js-2.5.6.tgz#4e8aadad85f70238e7c4b5abec89addb8d8363a9"
integrity sha512-Ld9OzIczRssZLoyuah2Lgp7O6tfgb/IuA1av4ZRKP9Ki5/4iyrC9dqRViM5P0rKHv5nOk9hghoVaYc+OCQn30g==
dependencies:
"@microsoft/applicationinsights-common" "2.5.6"
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/dynamicproto-js" "^0.5.2"
"@microsoft/applicationinsights-properties-js@2.5.6":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-properties-js/-/applicationinsights-properties-js-2.5.6.tgz#4de2a150c0deb6f0746c908cecb7f888ced798b2"
integrity sha512-tn9PzxUkomhSfO6vPeCNIjcCysmg4xRkntkkXconUbfZoYmrrh0jK11cmW1E3c7U5Pb8RyUqvPyGaBVOIG+QQw==
dependencies:
"@microsoft/applicationinsights-common" "2.5.6"
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/applicationinsights-react-js@^3.0.1":
version "3.0.1"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-react-js/-/applicationinsights-react-js-3.0.1.tgz#d13653d3d3e52c8187b056be4589f21937747ee2"
integrity sha512-x6IkcSsm7hjHwlIDJ4pyMTmCW4z9OrS7WwPZfJ/y2v5pXcsRttgZIbxMVlpp+2GV9lS41+bfonmyf/o5pdFCvA==
dependencies:
"@microsoft/applicationinsights-common" "^2.5.4"
"@microsoft/applicationinsights-core-js" "^2.5.4"
"@microsoft/applicationinsights-shims" "^1.0.1"
history "^4.10.1"
"@microsoft/applicationinsights-shims@1.0.1", "@microsoft/applicationinsights-shims@^1.0.1":
version "1.0.1"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-shims/-/applicationinsights-shims-1.0.1.tgz#814ae118940a892052ea0fc3677e60dc4f0dc374"
integrity sha512-nPjUBSpvX5Dnkovp2lZzrg0/uSvYNtbAclWwVP7t8J1hy5OJ3xr3KPNaz79+b84G16Rj861ybau9Gbk7inXkTg==
"@microsoft/applicationinsights-web@^2.5.6":
version "2.5.6"
resolved "https://registry.yarnpkg.com/@microsoft/applicationinsights-web/-/applicationinsights-web-2.5.6.tgz#3e15c514229a2b6c19a36cb6ad5d1d270e0dac5e"
integrity sha512-o5DlixrdFf2FAOv9AOgaN9u1zhVyYhbWoeXDZj9eaOdDgQQq9FzHGLwPUUhqMc/cQN+k2I2PDELnjqHag0VLKQ==
dependencies:
"@microsoft/applicationinsights-analytics-js" "2.5.6"
"@microsoft/applicationinsights-channel-js" "2.5.6"
"@microsoft/applicationinsights-common" "2.5.6"
"@microsoft/applicationinsights-core-js" "2.5.6"
"@microsoft/applicationinsights-dependencies-js" "2.5.6"
"@microsoft/applicationinsights-properties-js" "2.5.6"
"@microsoft/applicationinsights-shims" "1.0.1"
"@microsoft/dynamicproto-js" "^0.5.2"
"@microsoft/dynamicproto-js@^0.5.2":
version "0.5.3"
resolved "https://registry.yarnpkg.com/@microsoft/dynamicproto-js/-/dynamicproto-js-0.5.3.tgz#fd7933c22dd646d20f37176406eda6042dfb7efc"
integrity sha512-ky1oQ030kQlj/fv1+NLmY/g4D6YJb55Yg22KAoZGixFnc7UMjHJHjqZ0v3gtdyZykan3ZxRwwc2n1nWayyM38g==
"@microsoft/load-themed-styles@^1.10.26":
version "1.10.55"
resolved "https://registry.yarnpkg.com/@microsoft/load-themed-styles/-/load-themed-styles-1.10.55.tgz#f48b0112db8f409dc7cc37674587be59d3992ec4"
@ -6156,7 +6244,7 @@ hex-color-regex@^1.1.0:
resolved "https://registry.yarnpkg.com/hex-color-regex/-/hex-color-regex-1.1.0.tgz#4c06fccb4602fe2602b3c93df82d7e7dbf1a8a8e"
integrity sha512-l9sfDFsuqtOqKDsQdqrMRk0U85RZc0RtOR9yPI7mRVOa4FsR/BVnZ0shmQRM96Ji99kYZP/7hn1cedc1+ApsTQ==
history@^4.9.0:
history@^4.10.1, history@^4.9.0:
version "4.10.1"
resolved "https://registry.yarnpkg.com/history/-/history-4.10.1.tgz#33371a65e3a83b267434e2b3f3b1b4c58aad4cf3"
integrity sha512-36nwAD620w12kuzPAsyINPWJqlNbij+hpK1k9XRloDtym8mxzGYl2c17LnV6IAGB2Dmg4tEa7G7DlawS0+qjew==