Skip to content

Commit e240010

Browse files
committed
Revert "refactor: approvalFlow remove"
This reverts commit 76f29aa.
1 parent b90eaba commit e240010

File tree

4 files changed

+144
-82
lines changed

4 files changed

+144
-82
lines changed

app/core/RPCMethods/RPCMethodMiddleware.ts

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,11 @@ import { Alert, ImageSourcePropType } from 'react-native';
33
import { getVersion } from 'react-native-device-info';
44
import { createAsyncMiddleware } from '@metamask/json-rpc-engine';
55
import { providerErrors, rpcErrors } from '@metamask/rpc-errors';
6-
import { SetFlowLoadingTextOptions } from '@metamask/approval-controller';
6+
import {
7+
EndFlowOptions,
8+
StartFlowOptions,
9+
SetFlowLoadingTextOptions,
10+
} from '@metamask/approval-controller';
711
import { recoverPersonalSignature } from '@metamask/eth-sig-util';
812
import RPCMethods from './index.js';
913
import { RPC } from '../../constants/network';
@@ -426,6 +430,19 @@ export const getRpcMethodMiddleware = ({
426430
return AppConstants.REQUEST_SOURCES.IN_APP_BROWSER;
427431
};
428432

433+
const startApprovalFlow = (opts: StartFlowOptions) => {
434+
checkTabActive();
435+
Engine.context.ApprovalController.clear(
436+
providerErrors.userRejectedRequest(),
437+
);
438+
439+
return Engine.context.ApprovalController.startFlow(opts);
440+
};
441+
442+
const endApprovalFlow = (opts: EndFlowOptions) => {
443+
Engine.context.ApprovalController.endFlow(opts);
444+
};
445+
429446
// eslint-disable-next-line @typescript-eslint/no-unused-vars
430447
const setApprovalFlowLoadingText = (opts: SetFlowLoadingTextOptions) => {
431448
Engine.context.ApprovalController.setFlowLoadingText(opts);
@@ -990,6 +1007,8 @@ export const getRpcMethodMiddleware = ({
9901007
request_source: getSource(),
9911008
request_platform: analytics?.platform,
9921009
},
1010+
startApprovalFlow,
1011+
endApprovalFlow,
9931012
hooks,
9941013
});
9951014
},

app/core/RPCMethods/utils.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import { JsonRpcMiddleware } from '@metamask/json-rpc-engine';
66
import { PermittedHandlerExport } from '@metamask/permission-controller';
77
import { Json, JsonRpcParams, hasProperty } from '@metamask/utils';
88
import EthQuery from '@metamask/eth-query';
9+
import Logger from '../../util/Logger';
910

1011
export const UNSUPPORTED_RPC_METHODS = new Set([
1112
// This is implemented later in our middleware stack – specifically, in

app/core/RPCMethods/wallet_addEthereumChain.js

Lines changed: 90 additions & 81 deletions
Original file line numberDiff line numberDiff line change
@@ -46,14 +46,18 @@ const addOrUpdateIndex = (array, value, comparator) => {
4646
* @param params.res - The JsonRpcEngine result object.
4747
* @param params.requestUserApproval - The callback to trigger user approval flow.
4848
* @param params.analytics - Analytics parameters to be passed when tracking event via `MetaMetrics`.
49+
* @param params.startApprovalFlow - Flow to trigger at approval start.
50+
* @param params.endApprovalFlow - Flow to trigger at approval end.
4951
* @param params.hooks - Method hooks passed to the method implementation.
50-
* @returns {Nothing}.
52+
* @returns {void}.
5153
*/
5254
export const wallet_addEthereumChain = async ({
5355
req,
5456
res,
5557
requestUserApproval,
5658
analytics,
59+
startApprovalFlow,
60+
endApprovalFlow,
5761
hooks,
5862
}) => {
5963
const {
@@ -195,97 +199,102 @@ export const wallet_addEthereumChain = async ({
195199
// If existing approval request was an add network request, wait for
196200
// it to be rejected and for the corresponding approval flow to be ended.
197201
await waitForInteraction();
202+
const { id: approvalFlowId } = startApprovalFlow();
198203

199204
try {
200-
await requestUserApproval({
201-
type: 'ADD_ETHEREUM_CHAIN',
202-
requestData,
203-
});
204-
} catch (error) {
205-
MetaMetrics.getInstance().trackEvent(
206-
MetricsEventBuilder.createEventBuilder(
207-
MetaMetricsEvents.NETWORK_REQUEST_REJECTED,
208-
)
209-
.addProperties({
210-
chain_id: getDecimalChainId(chainId),
211-
source: 'Custom Network API',
212-
symbol: ticker,
213-
...analytics,
214-
})
215-
.build(),
216-
);
217-
throw providerErrors.userRejectedRequest();
218-
}
219-
220-
let newNetworkConfiguration;
221-
if (existingNetworkConfiguration) {
222-
const currentChainId = selectEvmChainId(store.getState());
223-
224-
const rpcResult = addOrUpdateIndex(
225-
existingNetworkConfiguration.rpcEndpoints,
226-
{
227-
url: firstValidRPCUrl,
228-
failoverUrls: [],
229-
type: RpcEndpointType.Custom,
230-
name: chainName,
231-
},
232-
(endpoint) => endpoint.url === firstValidRPCUrl,
233-
);
234-
235-
const blockExplorerResult = addOrUpdateIndex(
236-
existingNetworkConfiguration.blockExplorerUrls,
237-
firstValidBlockExplorerUrl,
238-
(url) => url === firstValidBlockExplorerUrl,
239-
);
205+
try {
206+
await requestUserApproval({
207+
type: 'ADD_ETHEREUM_CHAIN',
208+
requestData,
209+
});
210+
} catch (error) {
211+
MetaMetrics.getInstance().trackEvent(
212+
MetricsEventBuilder.createEventBuilder(
213+
MetaMetricsEvents.NETWORK_REQUEST_REJECTED,
214+
)
215+
.addProperties({
216+
chain_id: getDecimalChainId(chainId),
217+
source: 'Custom Network API',
218+
symbol: ticker,
219+
...analytics,
220+
})
221+
.build(),
222+
);
223+
throw providerErrors.userRejectedRequest();
224+
}
240225

241-
const updatedNetworkConfiguration = {
242-
...existingNetworkConfiguration,
243-
rpcEndpoints: rpcResult.updatedArray,
244-
defaultRpcEndpointIndex: rpcResult.index,
245-
blockExplorerUrls: blockExplorerResult.updatedArray,
246-
defaultBlockExplorerUrlIndex: blockExplorerResult.index,
247-
};
226+
let newNetworkConfiguration;
227+
if (existingNetworkConfiguration) {
228+
const currentChainId = selectEvmChainId(store.getState());
248229

249-
newNetworkConfiguration = await NetworkController.updateNetwork(
250-
chainId,
251-
updatedNetworkConfiguration,
252-
currentChainId === chainId
253-
? {
254-
replacementSelectedRpcEndpointIndex:
255-
updatedNetworkConfiguration.defaultRpcEndpointIndex,
256-
}
257-
: undefined,
258-
);
259-
} else {
260-
newNetworkConfiguration = NetworkController.addNetwork({
261-
chainId,
262-
blockExplorerUrls: [firstValidBlockExplorerUrl],
263-
defaultRpcEndpointIndex: 0,
264-
defaultBlockExplorerUrlIndex: 0,
265-
name: chainName,
266-
nativeCurrency: ticker,
267-
rpcEndpoints: [
230+
const rpcResult = addOrUpdateIndex(
231+
existingNetworkConfiguration.rpcEndpoints,
268232
{
269233
url: firstValidRPCUrl,
270234
failoverUrls: [],
271-
name: chainName,
272235
type: RpcEndpointType.Custom,
236+
name: chainName,
273237
},
274-
],
275-
});
238+
(endpoint) => endpoint.url === firstValidRPCUrl,
239+
);
276240

277-
MetaMetrics.getInstance().trackEvent(
278-
MetricsEventBuilder.createEventBuilder(MetaMetricsEvents.NETWORK_ADDED)
279-
.addProperties({
280-
chain_id: getDecimalChainId(chainId),
281-
source: 'Custom Network API',
282-
symbol: ticker,
283-
...analytics,
284-
})
285-
.build(),
286-
);
241+
const blockExplorerResult = addOrUpdateIndex(
242+
existingNetworkConfiguration.blockExplorerUrls,
243+
firstValidBlockExplorerUrl,
244+
(url) => url === firstValidBlockExplorerUrl,
245+
);
246+
247+
const updatedNetworkConfiguration = {
248+
...existingNetworkConfiguration,
249+
rpcEndpoints: rpcResult.updatedArray,
250+
defaultRpcEndpointIndex: rpcResult.index,
251+
blockExplorerUrls: blockExplorerResult.updatedArray,
252+
defaultBlockExplorerUrlIndex: blockExplorerResult.index,
253+
};
254+
255+
newNetworkConfiguration = await NetworkController.updateNetwork(
256+
chainId,
257+
updatedNetworkConfiguration,
258+
currentChainId === chainId
259+
? {
260+
replacementSelectedRpcEndpointIndex:
261+
updatedNetworkConfiguration.defaultRpcEndpointIndex,
262+
}
263+
: undefined,
264+
);
265+
} else {
266+
newNetworkConfiguration = NetworkController.addNetwork({
267+
chainId,
268+
blockExplorerUrls: [firstValidBlockExplorerUrl],
269+
defaultRpcEndpointIndex: 0,
270+
defaultBlockExplorerUrlIndex: 0,
271+
name: chainName,
272+
nativeCurrency: ticker,
273+
rpcEndpoints: [
274+
{
275+
url: firstValidRPCUrl,
276+
failoverUrls: [],
277+
name: chainName,
278+
type: RpcEndpointType.Custom,
279+
},
280+
],
281+
});
282+
283+
MetaMetrics.getInstance().trackEvent(
284+
MetricsEventBuilder.createEventBuilder(MetaMetricsEvents.NETWORK_ADDED)
285+
.addProperties({
286+
chain_id: getDecimalChainId(chainId),
287+
source: 'Custom Network API',
288+
symbol: ticker,
289+
...analytics,
290+
})
291+
.build(),
292+
);
293+
}
294+
switchToNetworkAndMetrics(newNetworkConfiguration, true);
295+
} finally {
296+
endApprovalFlow({ id: approvalFlowId });
287297
}
288-
switchToNetworkAndMetrics(newNetworkConfiguration, true);
289298

290299
res.result = null;
291300
};

app/core/RPCMethods/wallet_addEthereumChain.test.js

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,8 @@ describe('RPC Method - wallet_addEthereumChain', () => {
113113
addCustomNetworkRequest: {},
114114
switchCustomNetworkRequest: {},
115115
requestUserApproval: jest.fn(() => Promise.resolve()),
116+
startApprovalFlow: jest.fn(() => ({ id: '1', loadingText: null })),
117+
endApprovalFlow: jest.fn(),
116118
hooks: {
117119
getCurrentChainIdForDomain: jest.fn(),
118120
getNetworkConfigurationByChainId: jest.fn(),
@@ -359,6 +361,37 @@ describe('RPC Method - wallet_addEthereumChain', () => {
359361
});
360362

361363
describe('Approval Flow', () => {
364+
it('should start and end a new approval flow if chain does not already exist', async () => {
365+
jest
366+
.spyOn(Engine.context.NetworkController, 'addNetwork')
367+
.mockReturnValue(networkConfigurationResult);
368+
369+
await wallet_addEthereumChain({
370+
req: {
371+
params: [correctParams],
372+
},
373+
...otherOptions,
374+
});
375+
376+
expect(otherOptions.startApprovalFlow).toBeCalledTimes(1);
377+
expect(otherOptions.endApprovalFlow).toBeCalledTimes(1);
378+
});
379+
380+
it('should end approval flow even if the approval process fails', async () => {
381+
await expect(
382+
wallet_addEthereumChain({
383+
req: {
384+
params: [correctParams],
385+
},
386+
...otherOptions,
387+
requestUserApproval: jest.fn(() => Promise.reject()),
388+
}),
389+
).rejects.toThrow(providerErrors.userRejectedRequest());
390+
391+
expect(otherOptions.startApprovalFlow).toBeCalledTimes(1);
392+
expect(otherOptions.endApprovalFlow).toBeCalledTimes(1);
393+
});
394+
362395
it('clears existing approval requests', async () => {
363396
Engine.context.ApprovalController.clear.mockClear();
364397

0 commit comments

Comments
 (0)