Calling ENS subdomain registrar contract in TS with web3?

I’m trying to call register method on the contract - 0xe65d8aaf34cb91087d1598e0a15b582f57f217d9 with web3 as follows:

 import Web3 from 'web3';
import { Transaction } from "ethereumjs-tx";

const provider = new Web3.providers.HttpProvider('https://mainnet.infura.io/v3/<YOUR-API-KEY> );
const domain = "testcs123";

const executeContract = async (abiEncodedData: string, contractAddress: string, fromAddress: string) => {
  const nonce = await web3js.eth.getTransactionCount(fromAddress);
  const gasPrice = web3js.utils.toHex(30* 1e9);
  const gasLimit = web3js.utils.toHex(210000);
  const rawTransaction = {"from":fromAddress, "gasPrice":gasPrice,"gasLimit":gasLimit,"to":contractAddress,"data":abiEncodedData,"nonce":web3js.utils.toHex(nonce)};
  const transaction = new Transaction(rawTransaction);
  transaction.sign(privateKey);
  const serializedTx = transaction.serialize();
  const rawTxHex = '0x' + serializedTx.toString('hex');

  web3js.eth.sendSignedTransaction(rawTxHex)
        .on('receipt', receipt => { console.log('Receipt: ', receipt); })
        .catch(error => { console.log('Error: ', error.message); });
}


const registerSubdomain = async (subdomainName: string, ownerAddress: string) => {
    // contract abi is the array that you can get from the ethereum wallet or etherscan
    const contractABI = [{"inputs":[{"internalType":"contract ENS","name":"ens","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"}],"name":"DomainConfigured","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"},{"indexed":false,"internalType":"string","name":"name","type":"string"}],"name":"DomainTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"}],"name":"DomainUnlisted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"},{"indexed":false,"internalType":"string","name":"subdomain","type":"string"},{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"referrer","type":"address"},{"indexed":false,"internalType":"uint256","name":"price","type":"uint256"}],"name":"NewRegistration","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"},{"indexed":true,"internalType":"address","name":"oldOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnerChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"},{"indexed":false,"internalType":"string","name":"subdomain","type":"string"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"expirationDate","type":"uint256"}],"name":"RentPaid","type":"event"},{"constant":true,"inputs":[],"name":"TLD_NODE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"uint256","name":"referralFeePPM","type":"uint256"}],"name":"configureDomain","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"uint256","name":"referralFeePPM","type":"uint256"},{"internalType":"address payable","name":"_owner","type":"address"},{"internalType":"address","name":"_transfer","type":"address"}],"name":"configureDomainFor","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"ens","outputs":[{"internalType":"contract ENS","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"}],"name":"migrate","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes32","name":"label","type":"bytes32"}],"name":"migrateSubdomain","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"migration","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"label","type":"bytes32"}],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"string","name":"subdomain","type":"string"}],"name":"payRent","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"string","name":"subdomain","type":"string"}],"name":"query","outputs":[{"internalType":"string","name":"domain","type":"string"},{"internalType":"uint256","name":"price","type":"uint256"},{"internalType":"uint256","name":"rent","type":"uint256"},{"internalType":"uint256","name":"referralFeePPM","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"string","name":"subdomain","type":"string"},{"internalType":"address","name":"_subdomainOwner","type":"address"},{"internalType":"address payable","name":"referrer","type":"address"},{"internalType":"address","name":"resolver","type":"address"}],"name":"register","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[],"name":"registrar","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"registrarOwner","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"string","name":"subdomain","type":"string"}],"name":"rentDue","outputs":[{"internalType":"uint256","name":"timestamp","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_migration","type":"address"}],"name":"setMigrationAddress","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"},{"internalType":"address","name":"resolver","type":"address"}],"name":"setResolver","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[],"name":"stop","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"stopped","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes4","name":"interfaceID","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"},{"internalType":"address payable","name":"newOwner","type":"address"}],"name":"transfer","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"string","name":"name","type":"string"}],"name":"unlistDomain","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"}];
    const contractAddress = "0xe65d8AAF34CB91087D1598e0A15B582F57F217d9";
    const domainLabelHash = web3js.utils.soliditySha3(domain);
    const referrerAddress = ownerAddress;
    const params = [domainLabelHash, subdomainName, ownerAddress, referrerAddress, publicResolver];
    // creating contract object
    // @ts-ignore
    const contract = new web3js.eth.Contract(contractABI, contractAddress);
    const abiEncodedData = contract.methods.register.apply(null, params).encodeABI();
    await executeContract(abiEncodedData, contractAddress, paymentAddress);
}

const subdomain: string = "testcs2";
const ownerAddress: string = "0x763528B87C3210502aF9C10d9103440C27C55937"
await registerSubdomain(subdomain, ownerAddress);

When I execute this subdomains are getting created like this https://app.ens.domains/name/0x136d3724c389b12a1b73b28c88f38e7853abb5ca29fcfe58dcddee512c0b9615.testcs123.eth
Registered in tx - https://etherscan.io/tx/0x64da9853725e12b971200b80df8d833ad5d4ab4f1d976742bd876da262d0ca75

But when I run the same function in smart contract via Etherscan.io I get a subdomain registered perfectly like https://app.ens.domains/name/iam.testcs123.eth
Registered in tx - https://etherscan.io/tx/0x794d9098a3b069e45cd98be876035fbb99894b9e0ae009ebb299b5a9147ff527

What am I doing wrong?

1 Like

Looks like your transaction went okay.

I can see your name here.

https://app.ens.domains/name/testcs2.testcs123.eth

What’s happening seems that our graph seems not indexing the label appropriately (via https://thegraph.com/explorer/subgraph/ensdomains/ens). When that happens, we can’t show the string until you go to the url to decode it and put into local storage. This usually work for second label domains as they only register with labelhash hence subgraph has to unmask using preimage at index. Not quite sure why it’s happening on subdomains when you are actually passing string, not labelhash.