# Integrate with Turnkey

## Demo Repository

{% embed url="<https://github.com/Enclave-Money/enclave-turnkey-demo>" %}

## Step 1: Install Enclave Money

```
npm install enclavemoney
```

## Step 2: Initialize Enclave Client

```typescript
import { Enclave, SignMode } from 'enclavemoney';
const API_KEY = 'your-api-key-here';
const enclave = new Enclave(API_KEY);
```

## Step 3: Create Account with Turnkey as Signing Key

In the snippet given below we:

* Import 3rd party dependencies
* &#x20;Retrieve the active Turnkey signing key address
* Create an Enclave account on all supported networks using the Turnkey signing key

```typescript
import { useState, useEffect } from "react";
import { useTurnkey } from "@turnkey/sdk-react";
import { formatUnits, parseUnits, isAddress, ethers, getBytes } from 'ethers';

....

const { turnkey, getActiveClient } = useTurnkey();

const client = await getActiveClient();

// The user's sub-organization id
const organizationId = user?.organization.organizationId;

// Get the user's wallets
const wallets = await client?.getWallets({
  organizationId,
});

// Get the first wallet of the user
const walletId = wallets?.wallets[0].walletId ?? "";

// Use the `walletId` to get the accounts associated with the wallet
const accounts = await client?.getWalletAccounts({
  organizationId,
  walletId,
});

const signingKey = accounts?.accounts[0].address;

const account = await enclave.createSmartAccount(signingKey);
console.log('Smart Account created:', account.wallet.scw_address);

```

The user can transfer USDC to the account address returned from the createSmartAccount response and start transacting on any supported chain with their USDC deposits.

## Step 3: Build User Operation

In the example below we build a user operation to transfer USDC. This requires the user to have an account (created in **Step 2**) and the user must transfer USDC to their account. The user can deposit USDC on any supported chain and spend their funds on any chain.

<pre class="language-typescript"><code class="lang-typescript">// Define the transaction details
// Define the USDC contract address on Optimism
const usdcContractAddress = '&#x3C;Insert USDC Contract Address for Chain ID>'; 

// Define the recipient address and amount to transfer
const recipientAddress = '0x...'; // Replace with the recipient's address
const amount = ethers.parseUnits('1', 6); // Amount of USDC to transfer (1 USDC)

// Create the call data for the ERC20 transfer
const erc20Interface = new ethers.Interface([
    'function transfer(address to, uint256 amount)'
]);
const encodedData = erc20Interface.encodeFunctionData('transfer', [recipientAddress, amount]);

const transactionDetails = [{
    encodedData, 
    targetContractAddress: usdcContractAddress,
    value: 0 // Assuming no ETH is being transferred, only USDC
}];

// Define the order data - Describes how much the user wants to spend from their chain-abstracted balances
// Understanding order type
// AMOUNT_OUT: User needs 100 USDC on the target network. The user will be charged 100 + fees.
// AMOUNT_IN : User is charged 100 USDC and receives (100 - fees) on target network 
<strong>const orderData = {
</strong>    amount: amount.toString(), // Amount of USDC required for the transfer 
    type: 'AMOUNT_OUT'
};

// Build the transaction
const builtTxn = await enclave.buildTransaction(
    transactionDetails,
    chainId, // chainId of the network you want to execute the transaction on
    account.wallet.scw_address, // User's smart account address
    orderData,
    undefined, // Pass custom ERC4337 paymaster signature if required
    SignMode.ECDSA // ECDSA Signature Mode (for secp256k1)
);
</code></pre>

## Step 4: Sign User Operation

In the snippet below we create a Turnkey ethers signer and sign the user operation hash (buildTxn.messageToSign) retriveed in **Step 3**.

```typescript
const turnkeySigner = new TurnkeySigner({
    client: client,
    organizationId: user.organization.organizationId,
    signWith: accounts.accounts[0].address,
}) 
console.log("UserOpHash To Sign: ", builtTxn.messageToSign);

const msgBytes = getBytes(builtTxn.messageToSign);
const signature = await turnkeySigner.signMessage(msgBytes);
```

## Step 5: Submit User Operation

In the code snippet given below we use the enclave SDK to submit the signed user operation using builtTxn from **Step 3** and the signature from **Step 4**

```typescript
const txnResult = await enclave.submitTransaction(
  signature,
  builtTxn.userOp,
  chainId, // chainId of the network you want to execute the transaction on
  enclaveAddress,
  SignMode.ECDSA
);
```

## Conclusion

Congratulations! You have now added chain abstraction capabilities to your application using Turnkey as the signing key. This effectively allows your users to spend their unified USDC balance across chains for executing any on-chain action using their preferred authentication, authorization and signing methods provided by Turnkey (ex. Email, Google, Passkey, etc).


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.enclave.money/integrate-with-enclave-money/sdk-reference/integrate-with-turnkey.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
