Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: extend the time we resume the session without showing OTP #7212

Merged
merged 33 commits into from
Sep 27, 2023
Merged
Changes from 6 commits
Commits
Show all changes
33 commits
Select commit Hold shift + click to select a range
c5f5b88
feat: extend the time we resume the session without showing OTP
omridan159 Sep 13, 2023
2ca8e3d
feat: cleaning
omridan159 Sep 14, 2023
72b423c
feat: cleaning
omridan159 Sep 14, 2023
58e308b
Merge remote-tracking branch 'origin/main' into feat_updating-OTP-flow
omridan159 Sep 14, 2023
c222022
feat: cleaning
omridan159 Sep 14, 2023
79c9ba3
Merge remote-tracking branch 'origin/main' into feat_updating-OTP-flow
omridan159 Sep 18, 2023
61b0c8b
feat: extend the time we resume the session without showing OTP
omridan159 Sep 13, 2023
33fb7e6
feat: cleaning
omridan159 Sep 14, 2023
510554a
feat: cleaning
omridan159 Sep 14, 2023
2baf8c9
feat: cleaning
omridan159 Sep 14, 2023
c7045ac
feat: improve sdk init process
abretonc7s Sep 18, 2023
47b476a
feat: remove webrtc references
abretonc7s Sep 18, 2023
0437636
fix: do not remember me setting
abretonc7s Sep 19, 2023
b992025
feat: always update public key from deeplink
abretonc7s Sep 20, 2023
2a5eb2e
feat: disable logs
abretonc7s Sep 20, 2023
e13eaea
feat: update comm layer to 0.7.0
abretonc7s Sep 21, 2023
4bf0e48
Merge remote-tracking branch 'origin/main' into feat_updating-OTP-flow
omridan159 Sep 22, 2023
f9657c0
Merge remote-tracking branch 'origin/feat_updating-OTP-flow' into fea…
omridan159 Sep 22, 2023
f33c229
feat: extend the time we resume the session without showing OTP
omridan159 Sep 13, 2023
0538d66
feat: cleaning
omridan159 Sep 14, 2023
774ce2c
feat: cleaning
omridan159 Sep 14, 2023
e7bd536
feat: cleaning
omridan159 Sep 14, 2023
99ee6a6
feat: improve sdk init process
abretonc7s Sep 18, 2023
bc93b37
feat: remove webrtc references
abretonc7s Sep 18, 2023
306f55d
fix: do not remember me setting
abretonc7s Sep 19, 2023
29c5ac3
feat: always update public key from deeplink
abretonc7s Sep 20, 2023
8271394
feat: disable logs
abretonc7s Sep 20, 2023
d3e36e3
feat: update comm layer to 0.7.0
abretonc7s Sep 21, 2023
14b27e9
Merge remote-tracking branch 'origin/feat_updating-OTP-flow' into fea…
omridan159 Sep 22, 2023
54f645c
chore: reset the state 'lastAuthorized' after OTP approved
omridan159 Sep 22, 2023
81abc46
Merge remote-tracking branch 'origin/main' into feat_updating-OTP-flow
omridan159 Sep 22, 2023
8a4e538
building bitrise
christopherferreira9 Sep 26, 2023
a58d6bd
Merge branch 'main' into feat_updating-OTP-flow
christopherferreira9 Sep 26, 2023
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
98 changes: 70 additions & 28 deletions app/core/SDKConnect/SDKConnect.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ import { StackNavigationProp } from '@react-navigation/stack';
import BackgroundTimer from 'react-native-background-timer';
import DefaultPreference from 'react-native-default-preference';
import AppConstants from '../AppConstants';

import {
TransactionController,
WalletDevice,
Expand Down Expand Up @@ -53,7 +52,6 @@ import {
waitForEmptyRPCQueue,
waitForKeychainUnlocked,
} from './utils/wait.util';

import { Json } from '@metamask/controller-utils';
import { PROTOCOLS } from '../../constants/deeplinks';
import { Minimizer } from '../NativeModules';
Expand Down Expand Up @@ -84,6 +82,7 @@ export interface ConnectionProps {
initialConnection?: boolean;
originatorInfo?: OriginatorInfo;
validUntil: number;
lastAuthorized: number; // timestamp of last received activity
}
export interface ConnectedSessions {
[id: string]: Connection;
Expand Down Expand Up @@ -152,6 +151,11 @@ export class Connection extends EventEmitter2 {
isResumed = false;
initialConnection: boolean;

/*
* Timestamp of last activity, used to check if channel is still active and to prevent showing OTP approval modal too often.
*/
lastAuthorized: number;

/**
* Prevent double sending 'authorized' message.
*/
Expand Down Expand Up @@ -191,6 +195,7 @@ export class Connection extends EventEmitter2 {
rpcQueueManager,
originatorInfo,
approveHost,
lastAuthorized,
getApprovedHosts,
disapprove,
revalidate,
Expand All @@ -213,6 +218,7 @@ export class Connection extends EventEmitter2 {
super();
this.origin = origin;
this.channelId = id;
this.lastAuthorized = lastAuthorized;
this.reconnect = reconnect || false;
this.isResumed = false;
this.originatorInfo = originatorInfo;
Expand Down Expand Up @@ -324,30 +330,49 @@ export class Connection extends EventEmitter2 {
!this.initialConnection &&
this.origin === AppConstants.DEEPLINKS.ORIGIN_QR_CODE
) {
if (approvalController.get(this.channelId)) {
// cleaning previous pending approval
approvalController.reject(
this.channelId,
ethErrors.provider.userRejectedRequest(),
);
}
this.approvalPromise = undefined;
const currentTime = Date.now();
const channelWasActiveRecently =
!!this.lastAuthorized &&
currentTime - this.lastAuthorized < HOUR_IN_MS;

if (!this.otps) {
this.otps = generateOTP();
}
this.sendMessage({
type: MessageType.OTP,
otpAnswer: this.otps?.[0],
}).catch((err) => {
Logger.log(err, `SDKConnect:: Connection failed to send otp`);
});
// Prevent auto approval if metamask is killed and restarted
disapprove(this.channelId);
if (channelWasActiveRecently) {
this.approvalPromise = undefined;

// Always need to re-approve connection first.
await this.checkPermissions();
this.sendAuthorized(true);
// Prevent auto approval if metamask is killed and restarted
disapprove(this.channelId);

// Always need to re-approve connection first.
await this.checkPermissions({
lastAuthorized: this.lastAuthorized,
});

this.sendAuthorized(true);
} else {
if (approvalController.get(this.channelId)) {
// cleaning previous pending approval
approvalController.reject(
this.channelId,
ethErrors.provider.userRejectedRequest(),
);
}
this.approvalPromise = undefined;

if (!this.otps) {
this.otps = generateOTP();
}
this.sendMessage({
type: MessageType.OTP,
otpAnswer: this.otps?.[0],
}).catch((err) => {
Logger.log(err, `SDKConnect:: Connection failed to send otp`);
});
// Prevent auto approval if metamask is killed and restarted
disapprove(this.channelId);

// Always need to re-approve connection first.
await this.checkPermissions();
this.sendAuthorized(true);
}
} else if (
!this.initialConnection &&
this.origin === AppConstants.DEEPLINKS.ORIGIN_DEEPLINK
Expand Down Expand Up @@ -424,7 +449,7 @@ export class Connection extends EventEmitter2 {
// Wait for bridge to be ready before handling messages.
// It will wait until user accept/reject the connection request.
try {
await this.checkPermissions(message);
await this.checkPermissions({ message });
if (!this.receivedDisconnect) {
await waitForConnectionReadiness({ connection: this });
this.sendAuthorized();
Expand Down Expand Up @@ -630,9 +655,17 @@ export class Connection extends EventEmitter2 {
* @returns {boolean} true when host is approved or user approved the request.
* @throws error if the user reject approval request.
*/
private async checkPermissions(
_message?: CommunicationLayerMessage,
): Promise<boolean> {
private async checkPermissions({
// eslint-disable-next-line
message,
lastAuthorized,
}: {
message?: CommunicationLayerMessage;
lastAuthorized?: number;
} = {}): Promise<boolean> {
const channelWasActiveRecently =
!!lastAuthorized && Date.now() - lastAuthorized < HOUR_IN_MS;

// only ask approval if needed
const approved = this.isApproved({
channelId: this.channelId,
Expand Down Expand Up @@ -663,6 +696,10 @@ export class Connection extends EventEmitter2 {
this.revalidate({ channelId: this.channelId });
}

if (channelWasActiveRecently) {
return true;
}

const approvalRequest = {
origin: this.origin,
type: ApprovalTypes.CONNECT_ACCOUNTS,
Expand Down Expand Up @@ -825,6 +862,7 @@ export class SDKConnect extends EventEmitter2 {
otherPublicKey,
origin,
validUntil: Date.now() + DEFAULT_SESSION_TIMEOUT_MS,
lastAuthorized: Date.now(),
};

const initialConnection = this.approvedHosts[id] === undefined;
Expand Down Expand Up @@ -1251,11 +1289,15 @@ export class SDKConnect extends EventEmitter2 {
}

private _approveHost({ host }: approveHostProps) {
const channelId = host.replace(AppConstants.MM_SDK.SDK_REMOTE_ORIGIN, '');
if (this.disabledHosts[host]) {
// Might be useful for future feature.
} else {
// Host is approved for 24h.
this.approvedHosts[host] = Date.now() + DAY_IN_MS;
if (this.connections[channelId]) {
this.connections[channelId].lastAuthorized = Date.now();
}
// Prevent disabled hosts from being persisted.
DefaultPreference.set(
AppConstants.MM_SDK.SDK_APPROVEDHOSTS,
Expand Down