Skip to content

Commit

Permalink
Merge pull request #3997 from WalletConnect/feat/echo
Browse files Browse the repository at this point in the history
feat: decrypted notifications
  • Loading branch information
ganchoradkov authored Dec 19, 2023
2 parents 23f2f55 + 1f03e09 commit 51c3a97
Show file tree
Hide file tree
Showing 18 changed files with 390 additions and 8 deletions.
2 changes: 2 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion packages/core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,8 @@
"@walletconnect/utils": "2.10.6",
"events": "^3.3.0",
"lodash.isequal": "4.5.0",
"uint8arrays": "^3.1.0"
"uint8arrays": "^3.1.0",
"isomorphic-unfetch": "3.1.0"
},
"devDependencies": {
"@types/lodash.isequal": "4.5.6",
Expand Down
3 changes: 3 additions & 0 deletions packages/core/src/constants/echo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export const ECHO_CONTEXT = "echo";

export const ECHO_URL = "https://echo.walletconnect.com";
1 change: 1 addition & 0 deletions packages/core/src/constants/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ export * from "./pairing";
export * from "./history";
export * from "./expirer";
export * from "./verify";
export * from "./echo";
31 changes: 31 additions & 0 deletions packages/core/src/controllers/echo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { generateChildLogger, Logger } from "@walletconnect/logger";
import { IEchoClient } from "@walletconnect/types";
import { ECHO_CONTEXT, ECHO_URL } from "../constants";
import fetch from "isomorphic-unfetch";

export class EchoClient extends IEchoClient {
public readonly context = ECHO_CONTEXT;
constructor(public projectId: string, public logger: Logger) {
super(projectId, logger);
this.logger = generateChildLogger(logger, this.context);
}

public registerDeviceToken: IEchoClient["registerDeviceToken"] = async (params) => {
const { clientId, token, notificationType, enableEncrypted = false } = params;

const echoUrl = `${ECHO_URL}/${this.projectId}/clients`;

await fetch(echoUrl, {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
client_id: clientId,
type: notificationType,
token,
always_raw: enableEncrypted,
}),
});
};
}
1 change: 1 addition & 0 deletions packages/core/src/controllers/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,4 @@ export * from "./pairing";
export * from "./history";
export * from "./expirer";
export * from "./verify";
export * from "./echo";
12 changes: 11 additions & 1 deletion packages/core/src/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,15 @@ import {
} from "@walletconnect/logger";
import { CoreTypes, ICore } from "@walletconnect/types";

import { Crypto, Relayer, Pairing, JsonRpcHistory, Expirer, Verify } from "./controllers";
import {
Crypto,
Relayer,
Pairing,
JsonRpcHistory,
Expirer,
Verify,
EchoClient,
} from "./controllers";
import {
CORE_CONTEXT,
CORE_DEFAULT,
Expand Down Expand Up @@ -39,6 +47,7 @@ export class Core extends ICore {
public expirer: ICore["expirer"];
public pairing: ICore["pairing"];
public verify: ICore["verify"];
public echoClient: ICore["echoClient"];

private initialized = false;

Expand Down Expand Up @@ -77,6 +86,7 @@ export class Core extends ICore {
});
this.pairing = new Pairing(this, this.logger);
this.verify = new Verify(this.projectId || "", this.logger);
this.echoClient = new EchoClient(this.projectId || "", this.logger);
}

get context() {
Expand Down
3 changes: 2 additions & 1 deletion packages/sign-client/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { SignClient as Client } from "./client";

import { Session } from "./controllers/session";
export * from "./constants";

export const SessionStore = Session;
export const SignClient = Client;
export default Client;
2 changes: 2 additions & 0 deletions packages/types/src/core/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { IExpirer } from "./expirer";
import { IPairing } from "./pairing";
import { Logger } from "@walletconnect/logger";
import { IVerify } from "./verify";
import { IEchoClient } from "./echo";
export declare namespace CoreTypes {
interface Options {
projectId?: string;
Expand Down Expand Up @@ -54,6 +55,7 @@ export abstract class ICore extends IEvents {
public abstract expirer: IExpirer;
public abstract pairing: IPairing;
public abstract verify: IVerify;
public abstract echoClient: IEchoClient;

constructor(public opts?: CoreTypes.Options) {
super();
Expand Down
18 changes: 18 additions & 0 deletions packages/types/src/core/echo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { Logger } from "@walletconnect/logger";

export declare namespace EchoClientTypes {
type RegisterDeviceTokenParams = {
clientId: string;
token: string;
notificationType: "fcm" | "apns" | "apns-sandbox" | "noop";
enableEncrypted?: boolean;
};
}
export abstract class IEchoClient {
public abstract readonly context: string;
constructor(public projectId: string, public logger: Logger) {}

public abstract registerDeviceToken(
params: EchoClientTypes.RegisterDeviceTokenParams,
): Promise<void>;
}
1 change: 1 addition & 0 deletions packages/types/src/core/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ export * from "./keychain";
export * from "./expirer";
export * from "./pairing";
export * from "./verify";
export * from "./echo";
11 changes: 11 additions & 0 deletions packages/web3wallet/src/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import EventEmitter from "events";
import { CLIENT_CONTEXT } from "./constants";
import { Engine } from "./controllers";
import { IWeb3Wallet, Web3WalletTypes } from "./types";
import { Notifications } from "./utils";

export class Web3Wallet extends IWeb3Wallet {
public name: IWeb3Wallet["name"];
Expand All @@ -10,6 +11,7 @@ export class Web3Wallet extends IWeb3Wallet {
public events: IWeb3Wallet["events"] = new EventEmitter();
public engine: IWeb3Wallet["engine"];
public metadata: IWeb3Wallet["metadata"];
public static notifications: Web3WalletTypes.INotifications = Notifications;

static async init(opts: Web3WalletTypes.Options) {
const client = new Web3Wallet(opts);
Expand Down Expand Up @@ -173,6 +175,15 @@ export class Web3Wallet extends IWeb3Wallet {
}
};

public registerDeviceToken: IWeb3Wallet["registerDeviceToken"] = (params) => {
try {
return this.engine.registerDeviceToken(params);
} catch (error: any) {
this.logger.error(error.message);
throw error;
}
};

// ---------- Private ----------------------------------------------- //

private async initialize() {
Expand Down
5 changes: 5 additions & 0 deletions packages/web3wallet/src/controllers/engine.ts
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,11 @@ export class Engine extends IWeb3WalletEngine {
return this.authClient.formatMessage(params, iss);
};

// Push //
public registerDeviceToken: IWeb3WalletEngine["registerDeviceToken"] = (params) => {
return this.client.core.echoClient.registerDeviceToken(params);
};

// ---------- Private ----------------------------------------------- //

private onSessionRequest = (event: Web3WalletTypes.SessionRequest) => {
Expand Down
21 changes: 19 additions & 2 deletions packages/web3wallet/src/types/client.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
import EventEmmiter, { EventEmitter } from "events";
import { ICore, ProposalTypes, Verify } from "@walletconnect/types";
import { ICore, CoreTypes, ProposalTypes, Verify } from "@walletconnect/types";
import { AuthClientTypes } from "@walletconnect/auth-client";
import { IWeb3WalletEngine } from "./engine";
import { Logger } from "@walletconnect/logger";
import { JsonRpcPayload } from "@walletconnect/jsonrpc-utils";

export declare namespace Web3WalletTypes {
type Event = "session_proposal" | "session_request" | "session_delete" | "auth_request";
Expand Down Expand Up @@ -41,7 +42,21 @@ export declare namespace Web3WalletTypes {
name?: string;
}

type Metadata = AuthClientTypes.Metadata;
type Metadata = CoreTypes.Metadata;

interface INotifications {
decryptMessage: (params: {
topic: string;
encryptedMessage: string;
storageOptions?: CoreTypes.Options["storageOptions"];
storage?: CoreTypes.Options["storage"];
}) => Promise<JsonRpcPayload>;
getMetadata: (params: {
topic: string;
storageOptions?: CoreTypes.Options["storageOptions"];
storage?: CoreTypes.Options["storage"];
}) => Promise<CoreTypes.Metadata>;
}
}

export abstract class IWeb3WalletEvents extends EventEmmiter {
Expand Down Expand Up @@ -104,6 +119,8 @@ export abstract class IWeb3Wallet {
public abstract respondAuthRequest: IWeb3WalletEngine["respondAuthRequest"];
public abstract getPendingAuthRequests: IWeb3WalletEngine["getPendingAuthRequests"];
public abstract formatMessage: IWeb3WalletEngine["formatMessage"];
// push
public abstract registerDeviceToken: IWeb3WalletEngine["registerDeviceToken"];

// ---------- Event Handlers ----------------------------------------------- //
public abstract on: <E extends Web3WalletTypes.Event>(
Expand Down
6 changes: 6 additions & 0 deletions packages/web3wallet/src/types/engine.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import {
PendingRequestTypes,
ProposalTypes,
SessionTypes,
EchoClientTypes,
} from "@walletconnect/types";
import { IWeb3Wallet } from "./client";

Expand Down Expand Up @@ -83,4 +84,9 @@ export abstract class IWeb3WalletEngine {

// format payload to message string
public abstract formatMessage(payload: AuthEngineTypes.CacaoRequestPayload, iss: string): string;

// ---------- Push ------------------------------------------------- //
public abstract registerDeviceToken(
params: EchoClientTypes.RegisterDeviceTokenParams,
): Promise<void>;
}
1 change: 1 addition & 0 deletions packages/web3wallet/src/utils/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from "./notifications";
34 changes: 34 additions & 0 deletions packages/web3wallet/src/utils/notifications.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { Core } from "@walletconnect/core";
import { Web3WalletTypes } from "../types";
import { SessionStore } from "@walletconnect/sign-client";

export const Notifications: Web3WalletTypes.INotifications = {
decryptMessage: async (params) => {
const instance = {
core: new Core({
storageOptions: params.storageOptions,
storage: params.storage,
}),
} as any;
await instance.core.crypto.init();
const decoded = instance.core.crypto.decode(params.topic, params.encryptedMessage);
instance.core = null;
return decoded;
},
getMetadata: async (params) => {
const instances = {
core: new Core({
storageOptions: params.storageOptions,
storage: params.storage,
}),
sessionStore: null,
} as any;
instances.sessionStore = new SessionStore(instances.core, instances.core.logger);
await instances.sessionStore.init();
const session = instances.sessionStore.get(params.topic);
const metadata = session?.peer.metadata;
instances.core = null;
instances.sessionStore = null;
return metadata;
},
};
Loading

0 comments on commit 51c3a97

Please sign in to comment.