UNPKG

@biconomy/permission-context-builder

Version:

ERC-7715 Permission Context Builder utility package.

108 lines 6.04 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.getDigest = exports._prepareMockEnableData = exports.encodeEnableSessions = exports.getContext = void 0; const general_1 = require("./types/general.js"); const viem_1 = require("viem"); const ethers_1 = require("ethers"); const methods_1 = require("./utils/methods.js"); const signers_1 = require("./types/signers.js"); const accounts_1 = require("viem/accounts"); const webauthn_p256_1 = require("webauthn-p256"); const constants_1 = require("./utils/constants.js"); const getContext = async (walletClient, { smartAccountAddress, permissions, expiry, signer }) => { if (walletClient.chain === undefined) { throw new Error("Chain is undefined"); } const chainId = walletClient.chain?.id; const uint160Address = BigInt(constants_1.smartSessionAddress[chainId]); const nonceKey = uint160Address << BigInt(32); let signers = []; if (signer.type === "keys") { const publicKeys = signer.data.ids.map((id) => (0, methods_1.decodeDIDToPublicKey)(id)); publicKeys.forEach(key => { if (key.keyType === methods_1.KEY_TYPES.secp256k1) { const eoaAddress = (0, accounts_1.publicKeyToAddress)(key.key); const signer = { type: signers_1.SignerType.EOA, data: eoaAddress }; signers.push(signer); } if (key.keyType === methods_1.KEY_TYPES.secp256r1) { const passkeyPublicKey = (0, webauthn_p256_1.parsePublicKey)(key.key); const signer = { type: signers_1.SignerType.PASSKEY, data: (0, viem_1.encodeAbiParameters)((0, viem_1.parseAbiParameters)('uint256, uint256'), [passkeyPublicKey.x, passkeyPublicKey.y]) }; signers.push(signer); } }); } const signerId = (0, viem_1.keccak256)((0, viem_1.encodeAbiParameters)((0, viem_1.parseAbiParameters)("address, bytes"), [constants_1.multiKeySignerAddress[chainId], (0, methods_1.encodeSigners)(signers)])); const actions = permissions.map(permission => ({ actionId: (0, viem_1.keccak256)((0, viem_1.encodePacked)(["address", "bytes4"], [permission.data.target, (0, viem_1.toFunctionSelector)(permission.data.functionName)])), actionPolicies: [{ policy: constants_1.timeFramePolicyAddress[chainId], initData: (0, viem_1.encodePacked)(["uint128", "uint128"], [BigInt(expiry), BigInt(0)]) }] })); const enableData = await (0, exports._prepareMockEnableData)({ smartAccountAddress, signers, walletClient, userOpPolicies: [], actions, erc1271Policies: [], }); const context = (0, viem_1.encodePacked)(['uint192', 'bytes', 'bytes32', 'bytes'], [ nonceKey, general_1.EXECUTE_SINGLE, signerId, (0, exports.encodeEnableSessions)(enableData) ]); return context; }; exports.getContext = getContext; const encodeEnableSessions = (enableData) => { return ethers_1.ethers.utils.defaultAbiCoder.encode([ 'tuple(address isigner, bytes isignerInitData, tuple(address policy, bytes initData)[] userOpPolicies, tuple(address policy, bytes initData)[] erc1271Policies, tuple(bytes32 actionId, tuple(address policy, bytes initData)[] actionPolicies)[] actions, bytes permissionEnableSig)' ], [{ isigner: enableData.isigner, isignerInitData: enableData.isignerInitData, userOpPolicies: enableData.userOpPolicies, erc1271Policies: enableData.erc1271Policies, actions: enableData.actions.map(action => ({ actionId: action.actionId, actionPolicies: action.actionPolicies })), permissionEnableSig: enableData.permissionEnableSig }]); }; exports.encodeEnableSessions = encodeEnableSessions; const _prepareMockEnableData = async ({ smartAccountAddress, signers, walletClient, userOpPolicies, actions, erc1271Policies, }) => { if (walletClient.account === undefined) { throw new Error("Account is undefined"); } if (walletClient.chain === undefined) { throw new Error("Chain is undefined"); } const chainId = walletClient.chain?.id; let enableData = { isigner: constants_1.multiKeySignerAddress[chainId], isignerInitData: (0, viem_1.toBytes)((0, methods_1.encodeSigners)(signers)), userOpPolicies, erc1271Policies, actions, permissionEnableSig: (0, viem_1.toBytes)("") }; const digest = await (0, exports.getDigest)(walletClient, smartAccountAddress, enableData, general_1.SmartSessionMode.UNSAFE_ENABLE); enableData.permissionEnableSig = (0, viem_1.toBytes)((0, viem_1.encodePacked)(['address', 'bytes'], [constants_1.mockValidator[chainId], await walletClient.signMessage({ account: walletClient.account, message: digest })])); return enableData; }; exports._prepareMockEnableData = _prepareMockEnableData; const getDigest = async (walletClient, smartAccountAddress, enableData, mode) => { if (walletClient.chain === undefined) { throw new Error("Chain is undefined"); } const chainId = walletClient.chain?.id; const abi = [ "function getDigest(address isigner, address account, tuple(address isigner, bytes isignerInitData, tuple(address policy, bytes initData)[] userOpPolicies, tuple(address policy, bytes initData)[] erc1271Policies, tuple(bytes32 actionId, tuple(address policy, bytes initData)[] actionPolicies)[] actions, bytes permissionEnableSig) data, uint8 mode) view returns (bytes32)" ]; const provider = new ethers_1.ethers.providers.JsonRpcProvider(walletClient.chain.rpcUrls.default.http[0]); const contract = new ethers_1.ethers.Contract(constants_1.smartSessionAddress[chainId], abi, provider); const digest = await contract.getDigest(constants_1.multiKeySignerAddress[chainId], smartAccountAddress, enableData, mode); return digest; }; exports.getDigest = getDigest; //# sourceMappingURL=contextBuilder.js.map