Deno & Fetch

Requirements

  • A Cardano wallet with sufficient ADA and assets

  • Multiple recipient Cardano wallet addresses

  • Node.js environment (v14+) or Deno runtime

  • Valid API key for authentication

Objectives

This guide demonstrates the flexibility of the Anvil API for creating complex transactions.

What You'll Accomplish:

  • Send different amounts of ADA to multiple recipients

  • Distribute different native assets to different addresses

  • Handle everything in a single transaction

API Request Structure

Payload Format

Send 10 ADA + 1 asset to address#1 and Send 5 ADA + 1 asset to address#2

{
  "changeAddress": "addr...",
  "outputs": [
    {
      "address": "addr...1",
      "lovelace": 10_000_000, // 10 ADA
      "assets": [
        {
          "policyId": "<policy_id>",
          "assetName": "<asset_name>",
          "quantity": 1
        }
      ]
    },
    {
      "address": "addr...2",
      "lovelace": 5_000_000, // 5 ADA
      "assets": [
        {
          "policyId": "<policy_id>",
          "assetName": "<asset_name>",
          "quantity": 1
        }
      ]
    }
    // Add as many outputs as needed
  ]
}

Implementation

Configuration and Parameters

// Wallet addresses
const SENDER_ADDRESS =
  "addr_test1qq7fc3ke49nkcsfglltut7apa9t3gdul4utwhxt6j2hdrw7pg4vk6erdshyhdj5xeq0vh8qdy34cpdfstvc8l9su8hgq679eew";
const RECEIVER_ADDRESS_1 =
  "addr_test1qrydyk6uw6cehk5u3zspyz3dhnwzmhfls2fp42vv5dv9g2z3885pg4kpkn30ptezc855lu3w5ey93zcr5lrezjmwkftqg8xvge";
const RECEIVER_ADDRESS_2 =
  "addr_test1qr0tkwvlln0v5fljdxceudmlpt5y6szc84vpj4skm836tgn4hsqaesgg97l8ppy5rsn0alj8pth6lqe20fdyydsdgw6sr74cyt";

// Asset information
const POLICY_ID = "360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13";
const ASSET_NAME_1 = "616e76696c61706963697032355f333837393837393739";
const ASSET_NAME_2 = "616e76696c61706963697032355f333837393732";

// API configuration
const X_API_KEY = "testnet_EyrkvCWDZqjkfLSe1pxaF0hXxUcByHEhHuXIBjt9";
const API_URL = "https://preprod.api.ada-anvil.app/v2/services";
const HEADERS = { "Content-Type": "application/json", "x-api-key": X_API_KEY };

Request Body

Body Structure for creating a custom transaction using the previously collected values.

const BODY = {
  changeAddress: SENDER_ADDRESS,
  outputs: [
    {
      address: RECEIVER_ADDRESS_1,
      lovelace: 10_000_000, // 10 ADA
      assets: [
        {
          assetName: ASSET_NAME_1,
          policyId: POLICY_ID,
          quantity: 1,
        },
      ],
    },
    {
      address: RECEIVER_ADDRESS_2,
      lovelace: 5_000_000, // 5 ADA
      assets: [
        {
          assetName: ASSET_NAME_2,
          policyId: POLICY_ID,
          quantity: 1,
        },
      ],
    },
  ],
};

API Call (using Node.js and Fetch)

Basic POST call with Fetch

custom-transaction.ts
const response = await fetch(`${API_URL}/transactions/build`, {
  method: "POST",
  headers: HEADERS,
  body: JSON.stringify(BODY),
});

const result = await response.json();
console.log(result);

Deno Command

deno run --allow-net custom-transaction.ts

Output

{
  "hash": "7befd78854418b5465d505fa853a0631c1e8165bb0557b15ec6f194fcacd19a9",
  "complete": "84a600d90102838258205bf3681e7bfe3322c5e05cda80a5a784177d3239f1aae6d929c8a86be3474198018258206a6bb5dafa917de09a2b727d4050c785f59f39f1b819e43a34570c8a5377cadf00825820e490036d4c93cca91ada4365a2ea99d6a6b030338d041c02ba0a77e91c417eac01018482583900c8d25b5c76b19bda9c88a0120a2dbcdc2ddd3f82921aa98ca35854285139e81456c1b4e2f0af22c1e94ff22ea648588b03a7c7914b6eb256821a00989680a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a157616e76696c61706963697032355f3338373938373937390182583900debb399ffcdeca27f269b19e377f0ae84d40583d58195616d9e3a5a275bc01dcc1082fbe7084941c26fefe470aefaf832a7a5a42360d43b5821a004c4b40a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a154616e76696c61706963697032355f33383739373201a300581d605d2018b32a3752c252a8f08f5d34daf8ff8993da9c30d5bf94e26522011a00155cc0028201d8184a49616e76696c2d746167825839003c9c46d9a9676c4128ffd7c5fba1e95714379faf16eb997a92aed1bbc145596d646d85c976ca86c81ecb9c0d246b80b5305b307f961c3dd0821a1c5c8558a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a3581b616e76696c61706963697032355f3137343130333330373738303401581b616e76696c61706963697032355f3137343130333331383531353001581b616e76696c61706963697032355f3137343133363330393135333801021a0003429d031a0522114b081a0521f52b0ed9010281581c5d2018b32a3752c252a8f08f5d34daf8ff8993da9c30d5bf94e26522a100d9010281825820292af64334964e4e37e09a65aa7b14bf91a286236817ccc13acc660ccd2f3b725840003c389bf132640f78158f180b14f057a9919924b79c5e4771a9bccb0c225cde1bf3f1e5da4aac0649d8d905aa6dbe8734fa9da0053af103b1c0e480fbb25503",
  "stripped": "84a600d90102838258205bf3681e7bfe3322c5e05cda80a5a784177d3239f1aae6d929c8a86be3474198018258206a6bb5dafa917de09a2b727d4050c785f59f39f1b819e43a34570c8a5377cadf00825820e490036d4c93cca91ada4365a2ea99d6a6b030338d041c02ba0a77e91c417eac01018482583900c8d25b5c76b19bda9c88a0120a2dbcdc2ddd3f82921aa98ca35854285139e81456c1b4e2f0af22c1e94ff22ea648588b03a7c7914b6eb256821a00989680a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a157616e76696c61706963697032355f3338373938373937390182583900debb399ffcdeca27f269b19e377f0ae84d40583d58195616d9e3a5a275bc01dcc1082fbe7084941c26fefe470aefaf832a7a5a42360d43b5821a004c4b40a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a154616e76696c61706963697032355f33383739373201a300581d605d2018b32a3752c252a8f08f5d34daf8ff8993da9c30d5bf94e26522011a00155cc0028201d8184a49616e76696c2d746167825839003c9c46d9a9676c4128ffd7c5fba1e95714379faf16eb997a92aed1bbc145596d646d85c976ca86c81ecb9c0d246b80b5305b307f961c3dd0821a1c5c8558a1581c360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13a3581b616e76696c61706963697032355f3137343130333330373738303401581b616e76696c61706963697032355f3137343130333331383531353001581b616e76696c61706963697032355f3137343133363330393135333801021a0003429d031a0522114b081a0521f52b0ed9010281581c5d2018b32a3752c252a8f08f5d34daf8ff8993da9c30d5bf94e26522a0f5f6",
  "witnessSet": "a100d9010281825820292af64334964e4e37e09a65aa7b14bf91a286236817ccc13acc660ccd2f3b725840003c389bf132640f78158f180b14f057a9919924b79c5e4771a9bccb0c225cde1bf3f1e5da4aac0649d8d905aa6dbe8734fa9da0053af103b1c0e480fbb25503"
}

Complete Example (Deno/Node.js)

custom-transaction.ts
// Wallet addresses
const SENDER_ADDRESS =
  "addr_test1qq7fc3ke49nkcsfglltut7apa9t3gdul4utwhxt6j2hdrw7pg4vk6erdshyhdj5xeq0vh8qdy34cpdfstvc8l9su8hgq679eew";
const RECEIVER_ADDRESS_1 =
  "addr_test1qrydyk6uw6cehk5u3zspyz3dhnwzmhfls2fp42vv5dv9g2z3885pg4kpkn30ptezc855lu3w5ey93zcr5lrezjmwkftqg8xvge";
const RECEIVER_ADDRESS_2 =
  "addr_test1qr0tkwvlln0v5fljdxceudmlpt5y6szc84vpj4skm836tgn4hsqaesgg97l8ppy5rsn0alj8pth6lqe20fdyydsdgw6sr74cyt";

// Asset information
const POLICY_ID = "360fd38656e5204f22ec058d18d5a90c18745ca8325e51d077c38a13";
const ASSET_NAME_1 = "616e76696c61706963697032355f333837393837393739";
const ASSET_NAME_2 = "616e76696c61706963697032355f333837393732";

// API configuration
const X_API_KEY = "testnet_EyrkvCWDZqjkfLSe1pxaF0hXxUcByHEhHuXIBjt9";
const API_URL = "https://preprod.api.ada-anvil.app/v2/services";
const HEADERS = { "Content-Type": "application/json", "x-api-key": X_API_KEY };

const requestBody = {
  changeAddress: SENDER_ADDRESS,
  outputs: [
    {
      address: RECEIVER_ADDRESS_1,
      lovelace: 10_000_000, // 10 ADA
      assets: [
        {
          assetName: ASSET_NAME_1,
          policyId: POLICY_ID,
          quantity: 1,
        },
      ],
    },
    {
      address: RECEIVER_ADDRESS_2,
      lovelace: 5_000_000, // 5 ADA
      assets: [
        {
          assetName: ASSET_NAME_2,
          policyId: POLICY_ID,
          quantity: 1,
        },
      ],
    },
  ],
};

const response = await fetch(`${API_URL}/transactions/build`, {
  method: "POST",
  headers: HEADERS,
  body: JSON.stringify(requestBody),
});

const result = await response.json();
console.log(result);

Running the Example

Node.js

node custom-transaction.js

Deno

deno run --allow-net custom-transaction.ts

Last updated

Was this helpful?