Skip to content

Commit

Permalink
feat: adding WalletConnect, added tests for SingleSignPage
Browse files Browse the repository at this point in the history
  • Loading branch information
dianasavvatina committed Dec 9, 2024
1 parent 8cd5564 commit 96f1a71
Show file tree
Hide file tree
Showing 11 changed files with 176 additions and 9 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ export const TezSignPage = ({ operation, message }: BeaconSignPageProps) => {

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testId="TezSignPage">
<form>
<Header message={message} mode="single" operation={operation} />
<ModalBody>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ export const ContractCallSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="ContractCallSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const DelegationSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="DelegationSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const FinalizeUnstakeSignPage = ({
);
return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="FinalizeUnstakeSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ export const OriginationOperationSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="OriginationOperationSignPage">
<form>
<ModalHeader marginBottom="24px">
<Flex alignItems="center" justifyContent="center">
Expand Down
135 changes: 135 additions & 0 deletions apps/web/src/components/SendFlow/sdk/SingleSignPage.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
import { BeaconMessageType, NetworkType, type OperationRequestOutput } from "@airgap/beacon-wallet";
import type { BatchWalletOperation } from "@taquito/taquito/dist/types/wallet/batch-operation";
import {
type EstimatedAccountOperations,
type Operation,
executeOperations,
mockContractCall,
mockContractOrigination,
mockDelegationOperation,
mockFinalizeUnstakeOperation,
mockImplicitAccount,
mockStakeOperation,
mockTezOperation,
mockUndelegationOperation,
mockUnstakeOperation,
} from "@umami/core";
import { WalletClient, makeStore, networksActions, useGetSecretKey } from "@umami/state";
import { executeParams } from "@umami/test-utils";
import { GHOSTNET, makeToolkit } from "@umami/tezos";

import {
act,
dynamicModalContextMock,
renderInModal,
screen,
userEvent,
waitFor,
} from "../../../testUtils";
import { SuccessStep } from "../SuccessStep";
import { type SdkSignPageProps, type SignHeaderProps } from "../utils";
import { SingleSignPage } from "./SingleSignPage";

jest.mock("@umami/core", () => ({
...jest.requireActual("@umami/core"),
executeOperations: jest.fn(),
makeToolkit: jest.fn(),
}));

jest.mock("@umami/tezos", () => ({
...jest.requireActual("@umami/tezos"),
makeToolkit: jest.fn(),
}));

jest.mock("@umami/state", () => ({
...jest.requireActual("@umami/state"),
useGetSecretKey: jest.fn(),
}));

describe("<SingleSignPage />", () => {
it("calls the correct modal", async () => {
const store = makeStore();
const user = userEvent.setup();

const message = {
id: "messageid",
type: BeaconMessageType.OperationRequest,
network: { type: NetworkType.GHOSTNET },
appMetadata: {},
} as OperationRequestOutput;

// check all types of Modals called by SingleSignOperation
const mockedOperations: Record<string, Operation> = {
TezSignPage: mockTezOperation(0),
ContractCallSignPage: mockContractCall(0),
DelegationSignPage: mockDelegationOperation(0),
UndelegationSignPage: mockUndelegationOperation(0),
OriginationOperationSignPage: mockContractOrigination(0),
StakeSignPage: mockStakeOperation(0),
UnstakeSignPage: mockUnstakeOperation(0),
FinalizeUnstakeSignPage: mockFinalizeUnstakeOperation(0),
};

const operation: EstimatedAccountOperations = {
type: "implicit" as const,
sender: mockImplicitAccount(0),
signer: mockImplicitAccount(0),
operations: [],
estimates: [executeParams({ fee: 123 })],
};
const headerProps: SignHeaderProps = {
network: GHOSTNET,
appName: message.appMetadata.name,
appIcon: message.appMetadata.icon,
};
store.dispatch(networksActions.setCurrent(GHOSTNET));

for (const key in mockedOperations) {
operation.operations = [mockedOperations[key]];
const signProps: SdkSignPageProps = {
headerProps: headerProps,
operation: operation,
requestId: { sdkType: "beacon", id: message.id },
};

jest.mocked(useGetSecretKey).mockImplementation(() => () => Promise.resolve("secretKey"));

jest
.mocked(executeOperations)
.mockResolvedValue({ opHash: "ophash" } as BatchWalletOperation);
jest.spyOn(WalletClient, "respond").mockResolvedValue();

await renderInModal(<SingleSignPage {...signProps} />, store);

expect(screen.getByText("Ghostnet")).toBeInTheDocument();
expect(screen.queryByText("Mainnet")).not.toBeInTheDocument();
expect(screen.getByTestId(key)).toBeInTheDocument(); // e.g. TezSignPage

const signButton = screen.getByRole("button", {
name: "Confirm Transaction",
});
await waitFor(() => expect(signButton).toBeDisabled());

await act(() => user.type(screen.getByLabelText("Password"), "ThisIsAPassword"));

await waitFor(() => expect(signButton).toBeEnabled());
await act(() => user.click(signButton));

expect(makeToolkit).toHaveBeenCalledWith({
type: "mnemonic",
secretKey: "secretKey",
network: GHOSTNET,
});

await waitFor(() =>
expect(WalletClient.respond).toHaveBeenCalledWith({
type: BeaconMessageType.OperationResponse,
id: message.id,
transactionHash: "ophash",
})
);
expect(dynamicModalContextMock.openWith).toHaveBeenCalledWith(<SuccessStep hash="ophash" />);
dynamicModalContextMock.openWith.mockClear();
}
});
});
2 changes: 1 addition & 1 deletion apps/web/src/components/SendFlow/sdk/StakeSignPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const StakeSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="StakeSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ export const UndelegationSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="UndelegationSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
2 changes: 1 addition & 1 deletion apps/web/src/components/SendFlow/sdk/UnstakeSignPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const UnstakeSignPage = ({

return (
<FormProvider {...form}>
<ModalContent>
<ModalContent data-testid="UnstakeSignPage">
<form>
<Header headerProps={headerProps} />
<ModalBody>
Expand Down
2 changes: 1 addition & 1 deletion packages/core/src/Operation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ export type Unstake = {
amount: string;
};

type FinalizeUnstake = {
export type FinalizeUnstake = {
type: "finalize_unstake";
sender: Address;
};
Expand Down
32 changes: 32 additions & 0 deletions packages/core/src/testUtils.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,16 @@ import {
import { type StoredContactInfo } from "./Contact";
import { type Delegate } from "./Delegate";
import {
type ContractCall,
type ContractOrigination,
type Delegation,
type FA12Transfer,
type FA2Transfer,
type FinalizeUnstake,
type Stake,
type TezTransfer,
type Undelegation,
type Unstake,
} from "./Operation";
import {
type FA12TokenBalance,
Expand Down Expand Up @@ -395,6 +399,34 @@ export const mockContractOrigination = (
sender: mockImplicitAddress(index),
});

export const mockContractCall = (
index: number,
code: MichelsonV1Expression = []
): ContractCall => ({
type: "contract_call",
entrypoint: "test-entrypoint",
amount: String(index),
contract: mockContractAddress(index),
args: code,
});

export const mockStakeOperation = (index: number): Stake => ({
type: "stake",
amount: String(index),
sender: mockImplicitAddress(index),
});

export const mockUnstakeOperation = (index: number): Unstake => ({
type: "unstake",
amount: String(index),
sender: mockImplicitAddress(index),
});

export const mockFinalizeUnstakeOperation = (index: number): FinalizeUnstake => ({
type: "finalize_unstake",
sender: mockImplicitAddress(index),
});

export const mockImplicitContact = (index: number, label?: string): StoredContactInfo => ({
name: label || `Contact ${index}`,
pkh: mockImplicitAddress(index).pkh,
Expand Down

1 comment on commit 96f1a71

@github-actions
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Title Lines Statements Branches Functions
apps/desktop Coverage: 83%
83.88% (1764/2103) 79.35% (838/1056) 78.45% (448/571)
apps/web Coverage: 83%
83.88% (1764/2103) 79.35% (838/1056) 78.45% (448/571)
packages/components Coverage: 97%
97.51% (196/201) 95.91% (94/98) 88.13% (52/59)
packages/core Coverage: 81%
82.47% (207/251) 72.72% (88/121) 81.35% (48/59)
packages/crypto Coverage: 100%
100% (43/43) 90.9% (10/11) 100% (7/7)
packages/data-polling Coverage: 97%
95.27% (141/148) 87.5% (21/24) 92.85% (39/42)
packages/multisig Coverage: 98%
98.47% (129/131) 85.71% (18/21) 100% (36/36)
packages/social-auth Coverage: 100%
100% (21/21) 100% (11/11) 100% (3/3)
packages/state Coverage: 85%
84.78% (819/966) 80.86% (186/230) 78.59% (301/383)
packages/tezos Coverage: 89%
88.72% (118/133) 94.59% (35/37) 86.84% (33/38)
packages/tzkt Coverage: 89%
87.32% (62/71) 87.5% (14/16) 80.48% (33/41)

Please sign in to comment.