Skip to content

Commit

Permalink
feat(aa-sdk): sdk light client can call the alchemy client (#1236)
Browse files Browse the repository at this point in the history
# Pull Request Checklist

- [x] Did you add new tests and confirm existing tests pass? (`yarn test`)
- [x] Did you update relevant docs? (docs are found in the `site` folder, and guidelines for updating/adding docs can be found in the [contribution guide](https://github.com/alchemyplatform/aa-sdk/blob/main/CONTRIBUTING.md))
- [x] Do your commits follow the [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/) standard?
- [x] Does your PR title also follow the [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/) standard?
- [x] If you have a breaking change, is it [correctly reflected in your commit message](https://www.conventionalcommits.org/en/v1.0.0/#examples)? (e.g. `feat!: breaking change`)
- [x] Did you run lint (`yarn lint:check`) and fix any issues? (`yarn lint:write`)
- [x] Did you follow the [contribution guidelines](https://github.com/alchemyplatform/aa-sdk/blob/main/CONTRIBUTING.md)?

<!-- start pr-codex -->

---

## PR-Codex overview
This PR focuses on enhancing the `createLightAccountClient` function to support an `AlchemyTransport`, modifying its return type accordingly. Additionally, it introduces the `isAlchemyTransport` utility to check the transport type.

### Detailed summary
- Modified `createLightAccountClient` to return `AlchemySmartAccountClient` when using `AlchemyTransport`.
- Added `isAlchemyTransport` function to verify if the transport is an `AlchemyTransport`.
- Updated type parameters in `CreateLightAccountClientParams` to include `AlchemyTransport`.
- Enhanced documentation for the `createLightAccountClient` function.

> ✨ Ask PR-Codex anything about this PR by commenting with `/codex {your question}`

<!-- end pr-codex -->
  • Loading branch information
Blu-J committed Jan 10, 2025
1 parent 2d5dae9 commit cd9053b
Show file tree
Hide file tree
Showing 4 changed files with 172 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,21 @@ import {
erc7677Middleware,
LocalAccountSigner,
type BatchUserOperationCallData,
type SmartAccountClient,
type SmartAccountSigner,
type UserOperationCallData,
type UserOperationOverrides,
type UserOperationStruct,
} from "@aa-sdk/core";
import { custom, parseEther, type Address, publicActions } from "viem";
import {
custom,
parseEther,
type Address,
publicActions,
type Chain,
type Client,
type CustomTransport,
} from "viem";
import { setBalance } from "viem/actions";
import { resetBalance } from "~test/accounts.js";
import { accounts } from "~test/constants.js";
Expand All @@ -21,6 +30,15 @@ import { getMSCAUpgradeToData } from "../../msca/utils.js";
import type { LightAccountVersion } from "../types.js";
import { AccountVersionRegistry } from "../utils.js";
import { createLightAccountClient } from "./client.js";
import {
alchemy,
polygonMumbai,
alchemyEnhancedApiActions,
type AlchemyTransport,
type AlchemySmartAccountClient,
type AlchemyEnhancedApis,
} from "@account-kit/infra";
import { Alchemy, Network } from "alchemy-sdk";

const versions = Object.keys(
AccountVersionRegistry.LightAccount
Expand Down Expand Up @@ -387,4 +405,76 @@ describe("Light Account Tests", () => {
chain: instance.chain,
...(usePaymaster ? erc7677Middleware() : {}),
});

const givenAlchemyConnectedProvider = async ({
signer,
chain,
}: {
signer: SmartAccountSigner;
chain: Chain;
}) =>
createLightAccountClient({
transport: alchemy({
jwt: "test",
}),
chain,
signer,
accountAddress: "0x86f3B0211764971Ad0Fc8C8898d31f5d792faD84",
});
it("Should have some alchemy specific types", async () => {
const alchemy = new Alchemy({
network: Network.MATIC_MUMBAI,
apiKey: "test",
});
const chain = polygonMumbai;

const provider = (
await givenAlchemyConnectedProvider({ signer, chain })
).extend(alchemyEnhancedApiActions(alchemy));

assertType<Client<AlchemyTransport>>(provider);
assertType<AlchemySmartAccountClient>(provider);
assertType<SmartAccountClient>(provider);
assertType<AlchemyEnhancedApis>(provider);
assertType<AlchemyEnhancedApis>(
// @ts-expect-error
await givenAlchemyConnectedProvider({ signer, chain })
);
// @ts-expect-error
assertType<Client<CustomTransport>>(provider);
});
it("Should have some non-alchemy specific types", async () => {
const chain = polygonMumbai;

const signer: SmartAccountSigner = new LocalAccountSigner(
accounts.fundedAccountOwner
);
const provider = await givenConnectedProvider({
signer,
version: "v1.0.1",
});

assertType<SmartAccountClient>(provider);
assertType<Client<CustomTransport>>(provider);
assertType<AlchemyEnhancedApis>(
// @ts-expect-error
await givenAlchemyConnectedProvider({ signer, chain })
);
// @ts-expect-error
assertType<Client<AlchemyTransport>>(provider);
// @ts-expect-error
assertType<AlchemySmartAccountClient>(provider);
// @ts-expect-error
assertType<AlchemyEnhancedApis>(provider);

expect(() => {
const alchemy = new Alchemy({
network: Network.MATIC_MUMBAI,
apiKey: "test",
});

// @ts-expect-error
provider.extend(alchemyEnhancedApiActions(alchemy));
}).not.toBeFalsy();
});
});
48 changes: 43 additions & 5 deletions account-kit/smart-contracts/src/light-account/clients/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,17 @@ import {
lightAccountClientActions,
type LightAccountClientActions,
} from "../decorators/lightAccount.js";
import {
type AlchemySmartAccountClient,
type AlchemyTransport,
} from "@account-kit/infra";
import {
createLightAccountAlchemyClient,
type AlchemyLightAccountClientConfig,
} from "./alchemyClient.js";

export type CreateLightAccountClientParams<
TTransport extends Transport = Transport,
TTransport extends Transport | AlchemyTransport = Transport,
TChain extends Chain | undefined = Chain | undefined,
TSigner extends SmartAccountSigner = SmartAccountSigner
> = {
Expand All @@ -31,14 +39,28 @@ export type CreateLightAccountClientParams<
>;

export function createLightAccountClient<
TChain extends Chain | undefined = Chain | undefined,
TSigner extends SmartAccountSigner = SmartAccountSigner
>(
args: CreateLightAccountClientParams<Transport, TChain, TSigner>
params: AlchemyLightAccountClientConfig<TSigner> & {
transport: AlchemyTransport;
}
): Promise<
AlchemySmartAccountClient<
Chain | undefined,
LightAccount<TSigner>,
LightAccountClientActions<TSigner>
>
>;
export function createLightAccountClient<
TChain extends Chain | undefined = Chain | undefined,
TSigner extends SmartAccountSigner = SmartAccountSigner,
TTransport extends Transport = Transport
>(
args: CreateLightAccountClientParams<TTransport, TChain, TSigner>
): Promise<
SmartAccountClient<
CustomTransport,
Chain,
TChain,
LightAccount<TSigner>,
SmartAccountClientActions<Chain, SmartContractAccount> &
LightAccountClientActions<TSigner, LightAccount<TSigner>>
Expand All @@ -48,6 +70,8 @@ export function createLightAccountClient<
/**
* Creates a light account client using the provided parameters, including account information, transport mechanism, blockchain chain, and additional client configurations. This function first creates a light account and then uses it to create a smart account client, extending it with light account client actions.
*
* Also, we modified the return type to be the light account alchemy client if the transport is alchemy.
*
* @example
* ```ts
* import { createLightAccountClient } from "@account-kit/smart-contracts";
Expand All @@ -67,9 +91,16 @@ export function createLightAccountClient<
*/
export async function createLightAccountClient(
params: CreateLightAccountClientParams
): Promise<SmartAccountClient> {
): Promise<SmartAccountClient | AlchemySmartAccountClient> {
const { transport, chain } = params;

if (isAlchemyTransport(transport, chain)) {
return await createLightAccountAlchemyClient({
...params,
transport,
});
}

const lightAccount = await createLightAccount({
...params,
transport,
Expand All @@ -83,3 +114,10 @@ export async function createLightAccountClient(
account: lightAccount,
}).extend(lightAccountClientActions);
}

function isAlchemyTransport(
transport: Transport,
chain: Chain
): transport is AlchemyTransport {
return transport({ chain }).config.type === "alchemy";
}

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

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

0 comments on commit cd9053b

Please sign in to comment.