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

refactor: use message event type down the line #50

Merged
merged 2 commits into from
Aug 8, 2024
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
21 changes: 17 additions & 4 deletions src/handlers/signer.handlers.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import type {
} from '../types/icrc-requests';
import type {IcrcReadyResponse, IcrcSupportedStandardsResponse} from '../types/icrc-responses';
import {JSON_RPC_VERSION_2, type RpcId, type RpcResponseWithError} from '../types/rpc';
import type {SignerMessageEvent} from '../types/signer';
import {handleStatusRequest, handleSupportedStandards, notifyError} from './signer.handlers';

describe('Signer handlers', () => {
Expand Down Expand Up @@ -44,7 +45,10 @@ describe('Signer handlers', () => {

describe('notifyReady', () => {
it('should post a message with the msg', () => {
const {handled} = handleStatusRequest({data: statusRequest, origin});
const {handled} = handleStatusRequest({
data: statusRequest,
origin
} as unknown as SignerMessageEvent);

expect(handled).toBeTruthy();

Expand All @@ -58,7 +62,10 @@ describe('Signer handlers', () => {
});

it('should not handle msg if not status request', () => {
const {handled} = handleStatusRequest({data: supportedStandardsRequest, origin});
const {handled} = handleStatusRequest({
data: supportedStandardsRequest,
origin
} as unknown as SignerMessageEvent);

expect(handled).toBeFalsy();
});
Expand All @@ -85,7 +92,10 @@ describe('Signer handlers', () => {

describe('notifySupportedStandards', () => {
it('should post a message with the msg', () => {
const {handled} = handleSupportedStandards({data: supportedStandardsRequest, origin});
const {handled} = handleSupportedStandards({
data: supportedStandardsRequest,
origin
} as unknown as SignerMessageEvent);

expect(handled).toBeTruthy();

Expand All @@ -100,7 +110,10 @@ describe('Signer handlers', () => {
expect(postMessageMock).toHaveBeenCalledWith(expectedMessage, origin);
});
it('should not handle msg if not status request', () => {
const {handled} = handleSupportedStandards({data: statusRequest, origin});
const {handled} = handleSupportedStandards({
data: statusRequest,
origin
} as unknown as SignerMessageEvent);

expect(handled).toBeFalsy();
});
Expand Down
20 changes: 7 additions & 13 deletions src/handlers/signer.handlers.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import {SIGNER_SUPPORTED_STANDARDS} from '../constants/signer.constants';
import type {SignerMessageEventData} from '../signer';
import {
IcrcWalletStatusRequestSchema,
IcrcWalletSupportedStandardsRequestSchema
Expand All @@ -12,22 +11,17 @@ import {
type RpcResponseError,
type RpcResponseWithError
} from '../types/rpc';
import type {SignerMessageEvent} from '../types/signer';

interface Notify {
id: RpcId;
origin: string;
}
type Notify = {id: RpcId} & Pick<SignerMessageEvent, 'origin'>;

export const handleStatusRequest = ({
data,
...rest
}: {data: SignerMessageEventData} & Pick<Notify, 'origin'>): {handled: boolean} => {
export const handleStatusRequest = ({data, origin}: SignerMessageEvent): {handled: boolean} => {
const {success: isStatusRequest, data: statusData} =
IcrcWalletStatusRequestSchema.safeParse(data);

if (isStatusRequest) {
const {id} = statusData;
notifyReady({id, ...rest});
notifyReady({id, origin});
return {handled: true};
}

Expand All @@ -46,14 +40,14 @@ const notifyReady = ({id, origin}: Notify): void => {

export const handleSupportedStandards = ({
data,
...rest
}: {data: SignerMessageEventData} & Pick<Notify, 'origin'>): {handled: boolean} => {
origin
}: SignerMessageEvent): {handled: boolean} => {
const {success: isSupportedStandardsRequest, data: supportedStandardsData} =
IcrcWalletSupportedStandardsRequestSchema.safeParse(data);

if (isSupportedStandardsRequest) {
const {id} = supportedStandardsData;
notifySupportedStandards({id, ...rest});
notifySupportedStandards({id, origin});
return {handled: true};
}

Expand Down
13 changes: 8 additions & 5 deletions src/signer.spec.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import {type MockInstance} from 'vitest';
import {SIGNER_SUPPORTED_STANDARDS, SignerErrorCode} from './constants/signer.constants';
import * as signerHandlers from './handlers/signer.handlers';
import {Signer, type SignerMessageEventData, type SignerParameters} from './signer';
import {Signer, type SignerParameters} from './signer';
import {ICRC25_SUPPORTED_STANDARDS, ICRC29_STATUS} from './types/icrc';
import {JSON_RPC_VERSION_2} from './types/rpc';
import type {SignerMessageEventData} from './types/signer';

describe('Signer', () => {
const mockParameters: SignerParameters = {};
Expand Down Expand Up @@ -121,10 +122,12 @@ describe('Signer', () => {

window.dispatchEvent(messageEvent);

expect(handleStatusRequestSpy).toHaveBeenCalledWith({
data: messageEvent.data,
origin: testOrigin
});
expect(handleStatusRequestSpy).toHaveBeenCalledWith(
expect.objectContaining({
data: messageEvent.data,
origin: testOrigin
})
);
});

it('should notify an error if a message from different origin is dispatched', () => {
Expand Down
42 changes: 9 additions & 33 deletions src/signer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,8 @@ import {
handleSupportedStandards,
notifyError
} from './handlers/signer.handlers';
import type {
IcrcWalletPermissionsRequest,
IcrcWalletRequestPermissionsRequest,
IcrcWalletStatusRequest,
IcrcWalletSupportedStandardsRequest
} from './types/icrc-requests';
import {RpcRequestSchema} from './types/rpc';
import type {SignerMessageEvent} from './types/signer';

/**
* The parameters to initialize a signer.
Expand All @@ -20,15 +15,6 @@ import {RpcRequestSchema} from './types/rpc';
// eslint-disable-next-line @typescript-eslint/no-empty-interface
export interface SignerParameters {}

export type SignerMessageEventData = Partial<
| IcrcWalletStatusRequest
| IcrcWalletRequestPermissionsRequest
| IcrcWalletPermissionsRequest
| IcrcWalletSupportedStandardsRequest
>;

type SignerMessageEvent = MessageEvent<SignerMessageEventData>;

export class Signer {
#walletOrigin: string | undefined | null;

Expand Down Expand Up @@ -61,28 +47,24 @@ export class Signer {
void this.onMessage(message);
};

private readonly onMessage = async ({
data: msgData,
origin
}: SignerMessageEvent): Promise<void> => {
const {success, data: requestData} = RpcRequestSchema.safeParse(msgData);
private readonly onMessage = async (message: SignerMessageEvent): Promise<void> => {
const {data, origin} = message;

const {success, data: requestData} = RpcRequestSchema.safeParse(data);

if (!success) {
// We are only interested in JSON-RPC messages, so we are ignoring any other messages emitted at the window level, as the consumer might be using other events.
return;
}

this.assertAndSetOrigin({msgData, origin});
this.assertAndSetOrigin(message);

const {handled: statusRequestHandled} = handleStatusRequest({origin, data: msgData});
const {handled: statusRequestHandled} = handleStatusRequest(message);
if (statusRequestHandled) {
return;
}

const {handled: supportedStandardsRequestHandled} = handleSupportedStandards({
origin,
data: msgData
});
const {handled: supportedStandardsRequestHandled} = handleSupportedStandards(message);
if (supportedStandardsRequestHandled) {
return;
}
Expand All @@ -97,13 +79,7 @@ export class Signer {
});
};

private assertAndSetOrigin({
msgData,
origin
}: {
origin: string;
msgData: SignerMessageEventData;
}): void {
private assertAndSetOrigin({data: msgData, origin}: SignerMessageEvent): void {
if (nonNullish(this.#walletOrigin) && this.#walletOrigin !== origin) {
const {data} = RpcRequestSchema.safeParse(msgData);

Expand Down
15 changes: 15 additions & 0 deletions src/types/signer.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import type {
IcrcWalletPermissionsRequest,
IcrcWalletRequestPermissionsRequest,
IcrcWalletStatusRequest,
IcrcWalletSupportedStandardsRequest
} from './icrc-requests';

export type SignerMessageEventData = Partial<
| IcrcWalletStatusRequest
| IcrcWalletRequestPermissionsRequest
| IcrcWalletPermissionsRequest
| IcrcWalletSupportedStandardsRequest
>;

export type SignerMessageEvent = MessageEvent<SignerMessageEventData>;