Developers Forum for XinFin XDC Network

Denham Preen
Denham Preen

Posted on

Build an XDC Web3 Domains API using Envio

Want to build a real-time API for on-chain domain data on the XDC network? This guide walks you through how to use Envio’s HyperIndex to index and serve data from the Web3Domains smart contract.

💡 TL;DR


Step 0: Use pnpx envio init

Use the envio init flow and follow the prompts to create your boilerplate


Step 1: Define your indexer config

Start with a config.yaml file that defines the chain (XDC is network ID 50), the contract you want to index, and which events to listen to.

name: xdc-web3domains-indexer
networks:
- id: 50
  start_block: 0
  contracts:
  - name: Web3Domains
    address:
    - 0x295a7aB79368187a6CD03c464cfaAb04d799784E
    handler: src/EventHandlers.ts
    events:    
    - event: Transfer(address indexed from, address indexed to, uint256 indexed tokenId)      
    - event: NewURI(uint256 indexed tokenId, string tokenUri)    
Enter fullscreen mode Exit fullscreen mode

Step 2: Define your schema

We only care about three fields: the domain’s ID, current owner, and name. Define them in schema.graphql.

type Web3Domain {
  id: ID! # tokenId
  owner: String! @index # address of the owner of the domain
  name: String! @index # domain name
}
Enter fullscreen mode Exit fullscreen mode

Step 3: Handle events

Use TypeScript to react to events and keep your database in sync. Here’s the src/EventHandlers.ts file:

Quite simply we handle the Transfer event and newUri event to save and update our web3Domains entity with new owners and domain names.

import {
  Web3Domains,  
  Web3Domain,
} from "generated";

Web3Domains.Transfer.handler(async ({ event, context }) => {
  const { from, to, tokenId } = event.params;  
  const web3Domain = await context.Web3Domain.get(tokenId.toString());

  if (!web3Domain) {
    context.Web3Domain.set({
      id: tokenId.toString(),
      name: "tbd",
      owner: to,
    });
  } else {
    context.Web3Domain.set({
      ...web3Domain,
      owner: to,
    });
  }
});

Web3Domains.NewURI.handler(async ({ event, context }) => {
  const { tokenId, tokenUri } = event.params;
  const web3Domain = await context.Web3Domain.get(tokenId.toString());

  if (!web3Domain) {
    context.log.error("Transfer expected to happen before NewURI");
    return;
  }

  context.Web3Domain.set({
    ...web3Domain,
    name: tokenUri,
  });
});
Enter fullscreen mode Exit fullscreen mode

Step 4: Run your indexer locally

Prerequisites

Make sure you have the following installed:
Node.js (v18 or newer)
pnpm (v8 or newer)
Docker Desktop

Start the indexer

pnpm dev

Visit http://localhost:8080 to access the local GraphQL Playground.
Use testing as the password.


Step 5: Query your API

Here are a few example queries to get started:

Get address for a domain

query DomainByNameQuery {
  Web3Domain(where: {name: {_eq: "hello.xdc"}}) {
    id
    name
    owner
  }
}
Enter fullscreen mode Exit fullscreen mode

Get all domains owned by an address

query DomainByOwnerQuery {
  Web3Domain(where: {owner: {_eq: "0x0D29025FA6a82772B5a2ceeD27fb8F447e846901"}}) {
    id
    name
    owner
  }
}
Enter fullscreen mode Exit fullscreen mode

Live deployment

You can try all of this live here:
👉 https://envio.dev/app/enviodev/xdc-web3-domains
*Click into the playground


For more details, check out the Envio documentation.

Discussion (1)