> ## Documentation Index
> Fetch the complete documentation index at: https://docs.rhinestone.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# Quickstart

Create a smart account and send a crosschain transaction in a Node.js script. No browser or wallet connection required.

## Prerequisites

<Note>You don't need an API key to get started. For production use, you'll need one. For production setups that sponsor user fees or use dashboard API keys, see the [Security guide](./advanced/security) to proxy Orchestrator requests via a backend and avoid exposing your key.</Note>

You will need some testnet funds. To get testnet ETH, you can use a faucet from [Quicknode](https://faucet.quicknode.com/drip) or [Alchemy](https://www.alchemy.com/faucets). To get testnet USDC, use [Circle Faucet](https://faucet.circle.com/).

Install the Rhinestone SDK:

<CodeGroup>
  ```bash npm theme={null}
  npm install viem @rhinestone/sdk
  ```

  ```bash pnpm theme={null}
  pnpm add viem @rhinestone/sdk
  ```

  ```bash bun theme={null}
  bun install viem @rhinestone/sdk
  ```
</CodeGroup>

<Steps>
  <Step title="Create a Wallet">
    Let's create a smart account with a single owner:

    ```ts theme={null}
    import { RhinestoneSDK } from '@rhinestone/sdk'
    import { generatePrivateKey, privateKeyToAccount } from 'viem/accounts'
    import { baseSepolia, arbitrumSepolia } from 'viem/chains'
    import {
      createPublicClient,
      createWalletClient,
      encodeFunctionData,
      erc20Abi,
      type Hex,
      http,
      parseEther,
    } from 'viem'

    const fundingPrivateKey = process.env.FUNDING_PRIVATE_KEY
    if (!fundingPrivateKey) {
      throw new Error('FUNDING_PRIVATE_KEY is not set')
    }

    const sourceChain = baseSepolia
    const targetChain = arbitrumSepolia

    // You can use an existing PK here
    const privateKey = generatePrivateKey()
    console.log(`Owner private key: ${privateKey}`)
    const account = privateKeyToAccount(privateKey)

    const rhinestone = new RhinestoneSDK({
      apiKey: process.env.RHINESTONE_API_KEY,
    })
    const rhinestoneAccount = await rhinestone.createAccount({
      owners: {
        type: 'ecdsa',
        accounts: [account],
      },
    })
    const address = rhinestoneAccount.getAddress()
    console.log(`Smart account address: ${address}`)
    ```
  </Step>

  <Step title="Fund the Account">
    Send ETH to the smart account. The Orchestrator handles deployment and token conversion on the destination chain.

    ```ts theme={null}
    const publicClient = createPublicClient({
      chain: sourceChain,
      transport: http(),
    })
    const fundingAccount = privateKeyToAccount(fundingPrivateKey as Hex)
    const fundingClient = createWalletClient({
      account: fundingAccount,
      chain: sourceChain,
      transport: http(),
    })

    const txHash = await fundingClient.sendTransaction({
      to: address,
      value: parseEther('0.001'),
    })
    await publicClient.waitForTransactionReceipt({ hash: txHash })
    ```
  </Step>

  <Step title="Send a Cross-chain Transaction">
    Finally, let's make a cross-chain token transfer:

    ```ts theme={null}
    const usdcAmount = 1n

    const transaction = await rhinestoneAccount.sendTransaction({
      sourceChains: [sourceChain],
      targetChain,
      calls: [
        {
          to: 'USDC',
          value: 0n,
          data: encodeFunctionData({
            abi: erc20Abi,
            functionName: 'transfer',
            args: ['0xd8da6bf26964af9d7eed9e03e53415d37aa96045', usdcAmount],
          }),
        },
      ],
      tokenRequests: [
        {
          address: 'USDC',
          amount: usdcAmount,
        },
      ],
    })
    console.log('Transaction', transaction)

    const transactionResult = await rhinestoneAccount.waitForExecution(transaction)
    console.log('Result', transactionResult)
    ```

    After running that, you will get a smart account deployed on both Base Sepolia and Arbitrum Sepolia, and make a cross-chain USDC transfer.

    Note that you don't need to manage the gas tokens or do the ETH → USDC swap when making a transfer. The Orchestrator will handle that for you!
  </Step>
</Steps>

<Info>
  **Building a browser app?** Use the [Reown + Rhinestone example](https://github.com/rhinestonewtf/e2e-examples/tree/main/reown) to get wallet connection working with MetaMask or any WalletConnect-compatible wallet.
</Info>

<Warning>
  **Going to production?** Never expose your Rhinestone API key in the browser. Read the [Security guide](./advanced/security) to proxy Orchestrator requests safely via a backend.
</Warning>

## Next Steps

<CardGroup cols={3}>
  <Card title="Sponsor fees" icon="fuel" href="./tutorials/sponsor-fees">
    Cover gas, bridging, and swap fees for your users across any chain.
  </Card>

  <Card title="Smart account setup" icon="settings" href="./core/create-account">
    Configure signers: passkeys, embedded wallets, multisig, and more.
  </Card>

  <Card title="Smart Sessions" icon="key" href="./smart-sessions/overview">
    Add session keys for one-click UX and automated transactions.
  </Card>

  <Card title="EIP-7702" icon="zap" href="./core/eip-7702">
    Add smart account features to an existing EOA without changing its address.
  </Card>
</CardGroup>
