Skip to content
Merged
Show file tree
Hide file tree
Changes from all 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
252 changes: 85 additions & 167 deletions app/core/Engine/Engine.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ import {
} from '@metamask/transaction-controller';
import { GasFeeController } from '@metamask/gas-fee-controller';
import { AcceptOptions } from '@metamask/approval-controller';
import { HdKeyring } from '@metamask/eth-hd-keyring';
import {
type CaveatSpecificationConstraint,
PermissionController,
Expand All @@ -54,18 +53,9 @@ import {
} from '@metamask/permission-controller';
import SwapsController, { swapsUtils } from '@metamask/swaps-controller';
import { PPOMController } from '@metamask/ppom-validator';
import {
QrKeyring,
QrKeyringDeferredPromiseBridge,
} from '@metamask/eth-qr-keyring';
import { QrKeyringDeferredPromiseBridge } from '@metamask/eth-qr-keyring';
import { LoggingController } from '@metamask/logging-controller';
import { TokenSearchDiscoveryControllerMessenger } from '@metamask/token-search-discovery-controller';
import {
LedgerKeyring,
LedgerMobileBridge,
LedgerTransportMiddleware,
} from '@metamask/eth-ledger-bridge-keyring';
import { Encryptor, LEGACY_DERIVATION_OPTIONS, pbkdf2 } from '../Encryptor';
import { getDecimalChainId, isTestNet } from '../../util/networks';
import {
fetchEstimatedMultiLayerL1Fee,
Expand Down Expand Up @@ -130,7 +120,6 @@ import {
getSmartTransactionMetricsSensitiveProperties as getSmartTransactionMetricsSensitivePropertiesType,
} from '@metamask/smart-transactions-controller/dist/utils';
///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
import { snapKeyringBuilder } from '../SnapKeyring';
import { removeAccountsFromPermissions } from '../Permissions';
import { multichainBalancesControllerInit } from './controllers/multichain-balances-controller/multichain-balances-controller-init';
import { createMultichainRatesController } from './controllers/RatesController/utils';
Expand All @@ -147,9 +136,6 @@ import {
snapControllerInit,
snapInterfaceControllerInit,
snapsRegistryInit,
SnapControllerGetSnapAction,
SnapControllerIsMinimumPlatformVersionAction,
SnapControllerHandleRequestAction,
} from './controllers/snaps';
import { RestrictedMethods } from '../Permissions/constants';
///: END:ONLY_INCLUDE_IF
Expand Down Expand Up @@ -223,12 +209,13 @@ import { subjectMetadataControllerInit } from './controllers/subject-metadata-co
///: END:ONLY_INCLUDE_IF
import { PreferencesController } from '@metamask/preferences-controller';
import { preferencesControllerInit } from './controllers/preferences-controller-init';
import { snapKeyringBuilderInit } from './controllers/snap-keyring-builder-init';
///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
import { keyringControllerInit } from './controllers/keyring-controller-init';
///: END:ONLY_INCLUDE_IF

const NON_EMPTY = 'NON_EMPTY';

const encryptor = new Encryptor({
keyDerivationOptions: LEGACY_DERIVATION_OPTIONS,
});
// TODO: Replace "any" with type
// eslint-disable-next-line @typescript-eslint/no-explicit-any
let currentChainId: any;
Expand Down Expand Up @@ -554,89 +541,11 @@ export class Engine {
allowedEvents: [],
}),
});

if (!isProductSafetyDappScanningEnabled()) {
phishingController.maybeUpdateState();
}

const additionalKeyrings = [];

const qrKeyringBuilder = () => {
const keyring = new QrKeyring({ bridge: this.qrKeyringScanner });
// to fix the bug in #9560, forgetDevice will reset all keyring properties to default.
keyring.forgetDevice();
return keyring;
};
qrKeyringBuilder.type = QrKeyring.type;

additionalKeyrings.push(qrKeyringBuilder);

const bridge = new LedgerMobileBridge(new LedgerTransportMiddleware());
const ledgerKeyringBuilder = () => new LedgerKeyring({ bridge });
ledgerKeyringBuilder.type = LedgerKeyring.type;

additionalKeyrings.push(ledgerKeyringBuilder);

const hdKeyringBuilder = () =>
new HdKeyring({
cryptographicFunctions: { pbkdf2Sha512: pbkdf2 },
});
hdKeyringBuilder.type = HdKeyring.type;
additionalKeyrings.push(hdKeyringBuilder);

///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
const snapKeyringBuildMessenger = this.controllerMessenger.getRestricted({
name: 'SnapKeyring',
allowedActions: [
'ApprovalController:addRequest',
'ApprovalController:acceptRequest',
'ApprovalController:rejectRequest',
'ApprovalController:startFlow',
'ApprovalController:endFlow',
'ApprovalController:showSuccess',
'ApprovalController:showError',
'PhishingController:testOrigin',
'PhishingController:maybeUpdateState',
'KeyringController:getAccounts',
'AccountsController:setSelectedAccount',
'AccountsController:getAccountByAddress',
'AccountsController:setAccountName',
'AccountsController:setAccountNameAndSelectAccount',
'AccountsController:listMultichainAccounts',
SnapControllerHandleRequestAction,
SnapControllerGetSnapAction,
SnapControllerIsMinimumPlatformVersionAction,
],
allowedEvents: [],
});

additionalKeyrings.push(
snapKeyringBuilder(snapKeyringBuildMessenger, {
persistKeyringHelper: async () => {
// Necessary to only persist the keyrings, the `AccountsController` will
// automatically react to `KeyringController:stateChange`.
await this.keyringController.persistAllKeyrings();
},
removeAccountHelper: (address) => this.removeAccount(address),
}),
);

///: END:ONLY_INCLUDE_IF

this.keyringController = new KeyringController({
removeIdentity: (address: string) =>
this.preferencesController.removeIdentity(address),
encryptor,
messenger: this.controllerMessenger.getRestricted({
name: 'KeyringController',
allowedActions: [],
allowedEvents: [],
}),
state: initialKeyringState || initialState.KeyringController,
// @ts-expect-error To Do: Update the type of QRHardwareKeyring to Keyring<Json>
keyringBuilders: additionalKeyrings,
cacheEncryptionKey: true,
});

const accountTrackerController = new AccountTrackerController({
messenger: this.controllerMessenger.getRestricted({
name: 'AccountTrackerController',
Expand Down Expand Up @@ -666,75 +575,6 @@ export class Engine {
allowExternalServices: () => isBasicFunctionalityToggleEnabled(),
});

///: BEGIN:ONLY_INCLUDE_IF(preinstalled-snaps,external-snaps)
const authenticationControllerMessenger =
getAuthenticationControllerMessenger(this.controllerMessenger);
const authenticationController = createAuthenticationController({
messenger: authenticationControllerMessenger,
initialState: initialState.AuthenticationController,
metametrics: {
agent: Platform.MOBILE,
getMetaMetricsId: async () =>
(await MetaMetrics.getInstance().getMetaMetricsId()) || '',
},
});

const userStorageControllerMessenger = getUserStorageControllerMessenger(
this.controllerMessenger,
);
const userStorageController = createUserStorageController({
messenger: userStorageControllerMessenger,
initialState: initialState.UserStorageController,
nativeScryptCrypto: calculateScryptKey,
// @ts-expect-error Controller uses string for names rather than enum
trace,
config: {
contactSyncing: {
onContactUpdated: (profileId) => {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Contact Updated',
})
.build(),
);
},
onContactDeleted: (profileId) => {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Contact Deleted',
})
.build(),
);
},
onContactSyncErroneousSituation(profileId, situationMessage) {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Erroneous Situation',
additional_description: situationMessage,
})
.build(),
);
},
},
},
});
///: END:ONLY_INCLUDE_IF

const codefiTokenApiV2 = new CodefiTokenPricesServiceV2();

const smartTransactionsControllerTrackMetaMetricsEvent = (
Expand Down Expand Up @@ -805,20 +645,28 @@ export class Engine {
});

const existingControllersByName = {
KeyringController: this.keyringController,
NetworkController: networkController,
SmartTransactionsController: this.smartTransactionsController,
};

const initRequest = {
getState: () => store.getState(),
getGlobalChainId: () => currentChainId,
///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
removeAccount: this.removeAccount.bind(this),
///: END:ONLY_INCLUDE_IF
initialKeyringState,
qrKeyringScanner: this.qrKeyringScanner,
};

const { controllersByName } = initModularizedControllers({
controllerInitFunctions: {
PreferencesController: preferencesControllerInit,
AccountsController: accountsControllerInit,
///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
SnapKeyringBuilder: snapKeyringBuilderInit,
///: END:ONLY_INCLUDE_IF
KeyringController: keyringControllerInit,
PermissionController: permissionControllerInit,
///: BEGIN:ONLY_INCLUDE_IF(preinstalled-snaps,external-snaps)
SubjectMetadataController: subjectMetadataControllerInit,
Expand Down Expand Up @@ -901,6 +749,7 @@ export class Engine {
this.transactionController = transactionController;
this.permissionController = controllersByName.PermissionController;
this.preferencesController = preferencesController;
this.keyringController = controllersByName.KeyringController;

const multichainNetworkController =
controllersByName.MultichainNetworkController;
Expand Down Expand Up @@ -938,6 +787,75 @@ export class Engine {
controllersByName.NetworkEnablementController;
networkEnablementController.init();

///: BEGIN:ONLY_INCLUDE_IF(preinstalled-snaps,external-snaps)
const authenticationControllerMessenger =
getAuthenticationControllerMessenger(this.controllerMessenger);
const authenticationController = createAuthenticationController({
messenger: authenticationControllerMessenger,
initialState: initialState.AuthenticationController,
metametrics: {
agent: Platform.MOBILE,
getMetaMetricsId: async () =>
(await MetaMetrics.getInstance().getMetaMetricsId()) || '',
},
});

const userStorageControllerMessenger = getUserStorageControllerMessenger(
this.controllerMessenger,
);
const userStorageController = createUserStorageController({
messenger: userStorageControllerMessenger,
initialState: initialState.UserStorageController,
nativeScryptCrypto: calculateScryptKey,
// @ts-expect-error Controller uses string for names rather than enum
trace,
config: {
contactSyncing: {
onContactUpdated: (profileId) => {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Contact Updated',
})
.build(),
);
},
onContactDeleted: (profileId) => {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Contact Deleted',
})
.build(),
);
},
onContactSyncErroneousSituation(profileId, situationMessage) {
MetaMetrics.getInstance().trackEvent(
MetricsEventBuilder.createEventBuilder(
MetaMetricsEvents.PROFILE_ACTIVITY_UPDATED,
)
.addProperties({
profile_id: profileId,
feature_name: 'Contacts Sync',
action: 'Contacts Sync Erroneous Situation',
additional_description: situationMessage,
})
.build(),
);
},
},
},
});
///: END:ONLY_INCLUDE_IF

///: BEGIN:ONLY_INCLUDE_IF(keyring-snaps)
const multichainRatesControllerMessenger =
this.controllerMessenger.getRestricted({
Expand Down
Loading
Loading