Skip to content

Commit dcc9690

Browse files
Merge pull request #422 from monkvision/feature/MN-175/factorize-monitor-code
Feature/mn 175/factorize monitor code
2 parents a9b1aba + 917d572 commit dcc9690

File tree

19 files changed

+332
-181
lines changed

19 files changed

+332
-181
lines changed

package.json

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -49,9 +49,10 @@
4949
"@react-navigation/native": "^6.0.10",
5050
"@react-navigation/native-stack": "^6.6.1",
5151
"@reduxjs/toolkit": "^1.8.1",
52-
"@sentry/react": "^6.19.6",
52+
"@sentry/browser": "^7.36.0",
53+
"@sentry/react": "^7.36.0",
5354
"@sentry/react-native": "^4.13.0",
54-
"@sentry/tracing": "^6.19.7",
55+
"@sentry/tracing": "^7.36.0",
5556
"axios": "^0.26.1",
5657
"expo": "^44.0.6",
5758
"expo-application": "~4.0.1",

packages/corejs/.eslintrc.js

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,13 @@ module.exports = {
3535
'import/prefer-default-export': 'off',
3636
'no-plusplus': ['error', { allowForLoopAfterthoughts: true }],
3737
},
38+
settings: {
39+
'import/resolver': {
40+
node: {
41+
extensions: ['.js', '.jsx', '.ts', '.tsx'],
42+
},
43+
},
44+
},
3845
overrides: [
3946
{
4047
files: [

packages/corejs/package.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,10 @@
6969
"ts-jest": "^27.1.4",
7070
"typescript": "^4.6.3"
7171
},
72+
"peerDependencies": {
73+
"react": "*",
74+
"react-native": "*"
75+
},
7276
"publishConfig": {
7377
"access": "public"
7478
}

packages/corejs/src/index.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ import * as schemas from './schemas';
55
import * as slices from './slices';
66
import * as types from './types';
77

8+
export * from './monitoring';
9+
810
const reducers = {};
911
Object.values(slices).forEach((slice) => {
1012
const { name } = slice;
Lines changed: 133 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,133 @@
1+
import * as Sentry from '@sentry/browser';
2+
import { BrowserTracing } from '@sentry/tracing';
3+
import React, { createContext, PropsWithChildren, useCallback, useContext, useEffect, useMemo } from 'react';
4+
import { Primitive } from '@sentry/types';
5+
6+
import { MonitoringContext, MonitoringProps, SentryTransactionStatus } from './types';
7+
8+
export * from './types';
9+
10+
/**
11+
* Monitoring context which will create wrapper for monitoring functionality.
12+
*/
13+
export const Context = createContext<MonitoringContext | null>(null);
14+
15+
/**
16+
* Monitoring wrapper used to abstract Sentry functionality.
17+
*
18+
* @param {MonitoringProps} data - Configuration for sentry to override default configuration.
19+
* @return {React.ReactNode}
20+
*/
21+
export function MonitoringProvider({ children, config }: PropsWithChildren<MonitoringProps>) {
22+
useEffect(() => {
23+
Sentry.init({
24+
dsn: config.dsn,
25+
environment: config.environment,
26+
debug: config.debug,
27+
tracesSampleRate: config.tracesSampleRate,
28+
integrations: [
29+
new BrowserTracing({ tracePropagationTargets: config.tracingOrigins }),
30+
],
31+
});
32+
}, []);
33+
34+
/**
35+
* Updates user context information for future events.
36+
*
37+
* @param id {string} set user for in sentry
38+
* @return {void}
39+
*/
40+
const setMonitoringUser = useCallback((id: string): void => {
41+
Sentry.setUser({ id });
42+
}, []);
43+
44+
/**
45+
* Set key:value that will be sent as tags data with the event.
46+
*
47+
* Can also be used to unset a tag, by passing `undefined`.
48+
*
49+
* @param key String key of tag
50+
* @param value Value of tag
51+
* @return {void}
52+
*/
53+
const setMonitoringTag = useCallback((key: string, value: Primitive): void => {
54+
Sentry.setTag(key, value);
55+
}, []);
56+
57+
/**
58+
* Error handler function which is used to capture errors in sentry.
59+
*
60+
* @param error {Error | string} - Caught error that to be send to Sentry.io
61+
* @returns {string | null}
62+
*/
63+
const errorHandler = useCallback((error: Error | string): string | null => {
64+
if (!Sentry) {
65+
return null;
66+
}
67+
68+
return Sentry.captureException(error);
69+
}, []);
70+
71+
/**
72+
* Measure the performance of application based on functionality and operation based on it.
73+
* Return type of the function is the IIFE, which will helps to close the transaction and complete the measurement.
74+
*
75+
* @param name {string} - Name of transaction
76+
* @param operation {string} - Operation of transaction to be performed
77+
* @param [data] {{[key: string]: number | string}} - Data to be added on transaction
78+
* @returns {() => void} - Which will helps to close the transaction and complete the measurement.
79+
*/
80+
const measurePerformance = useCallback((name: string, op: string, data?: { [key: string]: number | string }): (() => void) => {
81+
// This will create a new Transaction
82+
const transaction = Sentry.startTransaction({ name, data, op });
83+
84+
// Set transaction on scope to associate with errors and get included span instrumentation
85+
// If there's currently an unfinished transaction, it may be dropped
86+
Sentry.getCurrentHub().configureScope((scope) => {
87+
scope.setSpan(transaction);
88+
});
89+
90+
return () => {
91+
transaction.setStatus(SentryTransactionStatus);
92+
transaction.finish();
93+
};
94+
}, []);
95+
96+
/**
97+
* Set the custom measurement on particular transaction
98+
*
99+
* @param transactionName Name of the transaction
100+
* @param name Name of the measurement
101+
* @param value Value of the measurement
102+
* @param [unit] Unit of the measurement. (Defaults to an empty string)
103+
* @return {void}
104+
*/
105+
const setMeasurement = useCallback((transactionName: string, name: string, value: number, unit?: string): void => {
106+
const transaction = Sentry.startTransaction({ name: transactionName, op: name });
107+
108+
setTimeout(() => {
109+
transaction.setMeasurement(name, value, unit);
110+
transaction.setMeasurement('frames_total', value, unit);
111+
transaction.setStatus(SentryTransactionStatus);
112+
transaction.finish();
113+
}, 100);
114+
}, []);
115+
116+
const monitoringContextValue = useMemo(
117+
() => ({ setMonitoringUser, setMonitoringTag, errorHandler, measurePerformance, setMeasurement }),
118+
[setMonitoringUser, setMonitoringTag, errorHandler, measurePerformance, setMeasurement],
119+
);
120+
121+
return (
122+
<Context.Provider value={monitoringContextValue}>
123+
{children}
124+
</Context.Provider>
125+
);
126+
}
127+
128+
/**
129+
* Custom hook which will provide monitoring context which will expose all the functionality.
130+
*/
131+
export function useMonitoring() {
132+
return useContext(Context);
133+
}
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
/**
2+
* Monitoring config interface
3+
*/
4+
export interface MonitoringConfig {
5+
/**
6+
* DSN key for sentry.io application
7+
*/
8+
dsn: string;
9+
/**
10+
* The current environment of your application (e.g. "production")
11+
*/
12+
environment: string;
13+
/**
14+
* Enable debug functionality in the SDK itself
15+
*/
16+
debug: boolean;
17+
/**
18+
* Sample rate to determine trace sampling.
19+
*
20+
* 0.0 = 0% chance of a given trace being sent (send no traces) 1.0 = 100% chance of a given trace being sent (send
21+
* all traces)
22+
*
23+
* Tracing is enabled if either this or `tracesSampler` is defined. If both are defined, `tracesSampleRate` is
24+
* ignored.
25+
*/
26+
tracesSampleRate: number;
27+
/**
28+
* Array of all the origin to browser trace.
29+
*/
30+
tracingOrigins: string[];
31+
}
32+
33+
/**
34+
* Monitoring context interface
35+
*/
36+
export interface MonitoringContext {
37+
/**
38+
* Set current user for sentry.
39+
*/
40+
setMonitoringUser: (id: string) => void;
41+
42+
/**
43+
* Store the error in the monitoring application.
44+
*/
45+
errorHandler: (error: Error | string) => string;
46+
47+
/**
48+
* Start Measure Performance
49+
*/
50+
measurePerformance: (name: string, op: string, data: { [key: string]: number | string } | null) => (() => void);
51+
52+
/**
53+
* Set custom measurement value
54+
*/
55+
setMeasurement: (transactionName: string, name: string, value: number, unit: string) => void;
56+
}
57+
58+
/**
59+
* Monitoring configuration interface
60+
*/
61+
export interface MonitoringProps {
62+
/**
63+
* Configuration to initialize Sentry
64+
*/
65+
config: MonitoringConfig;
66+
}
67+
68+
export const SentryTransactionStatus = 'success';

packages/corejs/src/types.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,3 +24,4 @@ export * from './views/reduxTypes';
2424
export * from './views/apiTypes';
2525
export * from './wheelAnalysis/entityTypes';
2626
export * from './wheelAnalysis/reduxTypes';
27+
export * from './monitoring/types';

packages/corejs/tsconfig.json

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
{
22
"compilerOptions": {
3+
"jsx": "react",
34
"outDir": "lib",
45
"allowJs": false,
56
"target": "es5",
@@ -9,8 +10,11 @@
910
"esModuleInterop": true,
1011
"moduleResolution": "node",
1112
"module": "commonjs",
12-
"lib": [ "es2015" ]
13+
"skipLibCheck": true,
14+
"lib": [ "es2015" ],
1315
},
1416
"include": ["src"],
15-
"exclude": ["node_modules"]
17+
"exclude": [
18+
"node_modules"
19+
]
1620
}

packages/toolkit/src/hooks/index.js

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
export { default as useSentry } from './useSentry';
21
export { default as useIcons } from './useIcons';
32
export { default as useToggle } from './useToggle';
43
export { default as useInterval } from './useInterval';

packages/toolkit/src/hooks/useSentry/index.js

Lines changed: 0 additions & 73 deletions
This file was deleted.

0 commit comments

Comments
 (0)