Skip to content

Commit 7d50357

Browse files
authored
remove matomo and route to segment (MetaMask#9646)
1 parent 379950d commit 7d50357

File tree

10 files changed

+123
-362
lines changed

10 files changed

+123
-362
lines changed

Diff for: app/scripts/lib/background-metametrics.js

-14
This file was deleted.

Diff for: app/scripts/metamask-controller.js

+12-14
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ import {
2525
PhishingController,
2626
} from '@metamask/controllers'
2727
import { getTrackMetaMetricsEvent } from '../../shared/modules/metametrics'
28+
import { getBackgroundMetaMetricState } from '../../ui/app/selectors'
2829
import ComposableObservableStore from './lib/ComposableObservableStore'
2930
import AccountTracker from './lib/account-tracker'
3031
import createLoggerMiddleware from './lib/createLoggerMiddleware'
@@ -56,8 +57,6 @@ import getRestrictedMethods from './controllers/permissions/restrictedMethods'
5657
import nodeify from './lib/nodeify'
5758
import accountImporter from './account-import-strategies'
5859
import seedPhraseVerifier from './lib/seed-phrase-verifier'
59-
60-
import backgroundMetaMetricsEvent from './lib/background-metametrics'
6160
import { ENVIRONMENT_TYPE_BACKGROUND } from './lib/enums'
6261

6362
export default class MetamaskController extends EventEmitter {
@@ -1893,19 +1892,18 @@ export default class MetamaskController extends EventEmitter {
18931892
}
18941893

18951894
const metamaskState = await this.getState()
1896-
const version = this.platform.getVersion()
1897-
backgroundMetaMetricsEvent(
1898-
metamaskState,
1899-
version,
1900-
{
1901-
customVariables,
1902-
eventOpts: {
1903-
action,
1904-
category: 'Background',
1905-
name,
1906-
},
1895+
const additionalProperties = getBackgroundMetaMetricState(metamaskState)
1896+
1897+
this.trackMetaMetricsEvent({
1898+
event: name,
1899+
category: 'Background',
1900+
matomoEvent: true,
1901+
properties: {
1902+
action,
1903+
...additionalProperties,
1904+
...customVariables,
19071905
},
1908-
)
1906+
})
19091907
}
19101908

19111909
/**

Diff for: development/build/scripts.js

+3
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ const { makeStringTransform } = require('browserify-transform-tools')
1818
const conf = require('rc')('metamask', {
1919
INFURA_PROJECT_ID: process.env.INFURA_PROJECT_ID,
2020
SEGMENT_WRITE_KEY: process.env.SEGMENT_WRITE_KEY,
21+
SEGMENT_LEGACY_WRITE_KEY: process.env.SEGMENT_LEGACY_WRITE_KEY,
2122
})
2223

2324
const packageJSON = require('../../package.json')
@@ -324,6 +325,7 @@ function createScriptTasks ({ browserPlatforms, livereload }) {
324325
// inflating event volume.
325326
const SEGMENT_PROD_WRITE_KEY = opts.testing ? undefined : process.env.SEGMENT_PROD_WRITE_KEY
326327
const SEGMENT_DEV_WRITE_KEY = opts.testing ? undefined : conf.SEGMENT_WRITE_KEY
328+
const SEGMENT_LEGACY_WRITE_KEY = opts.testing ? undefined : conf.SEGMENT_LEGACY_WRITE_KEY
327329

328330
// Inject variables into bundle
329331
bundler.transform(envify({
@@ -343,6 +345,7 @@ function createScriptTasks ({ browserPlatforms, livereload }) {
343345
: conf.INFURA_PROJECT_ID
344346
),
345347
SEGMENT_WRITE_KEY: environment === 'production' ? SEGMENT_PROD_WRITE_KEY : SEGMENT_DEV_WRITE_KEY,
348+
SEGMENT_LEGACY_WRITE_KEY: environment === 'production' ? process.env.SEGMENT_LEGACY_WRITE_KEY : SEGMENT_LEGACY_WRITE_KEY,
346349
}), {
347350
global: true,
348351
})

Diff for: docs/creating-metrics-events.md

-72
This file was deleted.

Diff for: package.json

+1
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,7 @@
198198
"@storybook/storybook-deployer": "^2.8.6",
199199
"@testing-library/react": "^10.4.8",
200200
"@testing-library/react-hooks": "^3.2.1",
201+
"@types/react": "^16.9.53",
201202
"addons-linter": "1.14.0",
202203
"babel-loader": "^8.0.6",
203204
"babelify": "^10.0.0",

Diff for: shared/modules/metametrics.js

+32-2
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,10 @@ export const segment = process.env.SEGMENT_WRITE_KEY
5757
? new Analytics(process.env.SEGMENT_WRITE_KEY, { flushAt })
5858
: segmentNoop
5959

60+
export const segmentLegacy = process.env.SEGMENT_LEGACY_WRITE_KEY
61+
? new Analytics(process.env.SEGMENT_LEGACY_WRITE_KEY, { flushAt })
62+
: segmentNoop
63+
6064
/**
6165
* We attach context to every meta metrics event that help to qualify our analytics.
6266
* This type has all optional values because it represents a returned object from a
@@ -111,6 +115,12 @@ export const segment = process.env.SEGMENT_WRITE_KEY
111115
* @property {string} [currency] - ISO 4127 format currency for events with revenue, defaults to US dollars
112116
* @property {number} [value] - Abstract "value" that this event has for MetaMask.
113117
* @property {boolean} [excludeMetaMetricsId] - whether to exclude the user's metametrics id for anonymity
118+
* @property {string} [metaMetricsId] - an override for the metaMetricsId in the event one is created as part
119+
* of an asynchronous workflow, such as awaiting the result of the metametrics opt-in function that generates the
120+
* user's metametrics id.
121+
* @property {boolean} [matomoEvent] - is this event a holdover from matomo that needs further migration?
122+
* when true, sends the data to a special segment source that marks the event data as not conforming to our
123+
* ideal schema
114124
* @property {MetaMetricsDynamicContext} [eventContext] - additional context to attach to event
115125
*/
116126

@@ -137,7 +147,9 @@ export function getTrackMetaMetricsEvent (
137147
revenue,
138148
currency,
139149
value,
150+
metaMetricsId: metaMetricsIdOverride,
140151
excludeMetaMetricsId: excludeId,
152+
matomoEvent = false,
141153
eventContext = {},
142154
}) {
143155
if (!event || !category) {
@@ -199,8 +211,20 @@ export function getTrackMetaMetricsEvent (
199211
context,
200212
}
201213

214+
// If we are tracking sensitive data we will always use the anonymousId property
215+
// as well as our METAMETRICS_ANONYMOUS_ID. This prevents us from associating potentially
216+
// identifiable information with a specific id. During the opt in flow we will track all
217+
// events, but do so with the anonymous id. The one exception to that rule is after the
218+
// user opts in to MetaMetrics. When that happens we receive back the user's new MetaMetrics
219+
// id before it is fully persisted to state. To avoid a race condition we explicitly pass the
220+
// new id to the track method. In that case we will track the opt in event to the user's id.
221+
// In all other cases we use the metaMetricsId from state.
202222
if (excludeMetaMetricsId) {
203223
trackOptions.anonymousId = METAMETRICS_ANONYMOUS_ID
224+
} else if (isOptIn && metaMetricsIdOverride) {
225+
trackOptions.userId = metaMetricsIdOverride
226+
} else if (isOptIn) {
227+
trackOptions.anonymousId = METAMETRICS_ANONYMOUS_ID
204228
} else {
205229
trackOptions.userId = metaMetricsId
206230
}
@@ -210,12 +234,18 @@ export function getTrackMetaMetricsEvent (
210234
// If flushAt is greater than one the callback won't be triggered until after a number
211235
// of events have been queued equal to the flushAt value OR flushInterval passes. The
212236
// default flushInterval is ten seconds
213-
segment.track(trackOptions, (err) => {
237+
const callback = (err) => {
214238
if (err) {
215239
return reject(err)
216240
}
217241
return resolve()
218-
})
242+
}
243+
244+
if (matomoEvent === true) {
245+
segmentLegacy.track(trackOptions, callback)
246+
} else {
247+
segment.track(trackOptions, callback)
248+
}
219249
})
220250
}
221251
}

Diff for: ui/app/contexts/metametrics.js

+57-38
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import React, { Component, createContext, useEffect, useCallback, useState } from 'react'
1+
import React, { Component, createContext, useEffect, useCallback, useState, useMemo } from 'react'
22
import { useSelector } from 'react-redux'
33
import PropTypes from 'prop-types'
44
import { useHistory } from 'react-router-dom'
@@ -9,16 +9,15 @@ import {
99
getAccountType,
1010
getNumberOfAccounts,
1111
getNumberOfTokens,
12+
getCurrentChainId,
1213
} from '../selectors/selectors'
1314
import { getSendToken } from '../selectors/send'
1415
import {
1516
txDataSelector,
1617
} from '../selectors/confirm-transaction'
1718
import { getEnvironmentType } from '../../../app/scripts/lib/util'
18-
import {
19-
sendMetaMetricsEvent,
20-
} from '../helpers/utils/metametrics.util'
21-
import { sendCountIsTrackable } from '../../../shared/modules/metametrics'
19+
import { getTrackMetaMetricsEvent } from '../../../shared/modules/metametrics'
20+
import { getCurrentLocale } from '../ducks/metamask/metamask'
2221

2322
export const MetaMetricsContext = createContext(() => {
2423
captureException(
@@ -30,6 +29,8 @@ export function MetaMetricsProvider ({ children }) {
3029
const txData = useSelector(txDataSelector) || {}
3130
const network = useSelector(getCurrentNetworkId)
3231
const environmentType = getEnvironmentType()
32+
const chainId = useSelector(getCurrentChainId)
33+
const locale = useSelector(getCurrentLocale)
3334
const activeCurrency = useSelector(getSendToken)?.symbol
3435
const accountType = useSelector(getAccountType)
3536
const confirmTransactionOrigin = txData.origin
@@ -44,7 +45,7 @@ export function MetaMetricsProvider ({ children }) {
4445
previousPath: '',
4546
}))
4647

47-
const { previousPath, currentPath } = state
48+
const { currentPath } = state
4849

4950
useEffect(() => {
5051
const unlisten = history.listen(() => setState((prevState) => ({
@@ -55,45 +56,63 @@ export function MetaMetricsProvider ({ children }) {
5556
return unlisten
5657
}, [history])
5758

59+
/**
60+
* track a metametrics event
61+
*
62+
* @param {import('../../../shared/modules/metametrics').MetaMetricsEventPayload} - payload for event
63+
* @returns undefined
64+
*/
65+
const trackEvent = useMemo(() => {
66+
const referrer = confirmTransactionOrigin ? { url: confirmTransactionOrigin } : undefined
67+
const page = {
68+
path: currentPath,
69+
}
70+
return getTrackMetaMetricsEvent(global.platform.getVersion(), () => ({
71+
context: {
72+
referrer,
73+
page,
74+
},
75+
environmentType,
76+
locale: locale.replace('_', '-'),
77+
network,
78+
chainId,
79+
participateInMetaMetrics,
80+
metaMetricsId,
81+
metaMetricsSendCount,
82+
}))
83+
}, [network, chainId, locale, environmentType, participateInMetaMetrics, currentPath, confirmTransactionOrigin, metaMetricsId, metaMetricsSendCount])
84+
5885
const metricsEvent = useCallback((config = {}, overrides = {}) => {
5986
const { eventOpts = {} } = config
60-
const { name = '' } = eventOpts
61-
const { currentPath: overrideCurrentPath = '' } = overrides
62-
const isSendFlow = Boolean(name.match(/^send|^confirm/u) || overrideCurrentPath.match(/send|confirm/u))
63-
64-
if (participateInMetaMetrics || config.isOptIn) {
65-
return sendMetaMetricsEvent({
66-
network,
67-
environmentType,
68-
activeCurrency,
69-
accountType,
70-
confirmTransactionOrigin,
71-
metaMetricsId,
72-
numberOfTokens,
73-
numberOfAccounts,
74-
version: global.platform.getVersion(),
75-
...config,
76-
previousPath,
77-
currentPath,
78-
excludeMetaMetricsId: isSendFlow && !sendCountIsTrackable(metaMetricsSendCount + 1),
79-
...overrides,
80-
})
81-
}
8287

83-
return undefined
88+
return trackEvent({
89+
event: eventOpts.name,
90+
category: eventOpts.category,
91+
isOptIn: config.isOptIn,
92+
excludeMetaMetricsId: eventOpts.excludeMetaMetricsId ?? overrides.excludeMetaMetricsId ?? false,
93+
metaMetricsId: config.metaMetricsId,
94+
matomoEvent: true,
95+
properties: {
96+
action: eventOpts.action,
97+
number_of_tokens: numberOfTokens,
98+
number_of_accounts: numberOfAccounts,
99+
active_currency: activeCurrency,
100+
account_type: accountType,
101+
is_new_visit: config.is_new_visit,
102+
// the properties coming from this key will not match our standards for
103+
// snake_case on properties, and they may be redundant and/or not in the
104+
// proper location (origin not as a referrer, for example). This is a temporary
105+
// solution to not lose data, and the entire event system will be reworked in
106+
// forthcoming PRs to deprecate the old Matomo events in favor of the new schema.
107+
...config.customVariables,
108+
},
109+
})
84110
}, [
85-
network,
86-
environmentType,
87-
activeCurrency,
88111
accountType,
89-
confirmTransactionOrigin,
90-
participateInMetaMetrics,
91-
previousPath,
92-
metaMetricsId,
112+
activeCurrency,
93113
numberOfTokens,
94114
numberOfAccounts,
95-
currentPath,
96-
metaMetricsSendCount,
115+
trackEvent,
97116
])
98117

99118
return (

0 commit comments

Comments
 (0)