1

I want to add my chain types to the Polkadot-js/apps in order to reflect the changes on frontend. I've tried generating types using this tutorial, but I've no idea how can I use them in Polkadot-js/apps for my custom chain. If anyone could point to a tutorial or an implementation to this, that'd be super helpful. Thank you.

1 Answer 1

2

In the Usage section of the Polkadot.js typegen tutorial it first shows how to extract the types from your custom type definitions, for example see how the Edgeware team releases versions their types for the community here, then when they create an instance of the API they introduce the types registry to inject the types and override existing types as described here so the API understands the types from the metadata.

For example, if you built your custom chain using the substrate-node-template but you changed the implementation so the default Balance type of u128 here became u64 instead, then you would create the instance of your API with:

import { ApiPromise, WsProvider } from '@polkadot/api';
const wsProvider = new WsProvider('ws://127.0.0.1:9944');
const api = await ApiPromise.create({
  provider: wsProvider,
  types: {
    Balance: 'u64'
  }
});

Alternatively you could create it using the syntax const api = new ApiPromise({ provider: wsProvider, types: { ... } }); as mentioned here.

So if you were building your frontend based on the substrate-front-end-template then you would add those custom types here where they create the instance of the API.

As mentioned at https://polkadot.js.org/apps/?rpc=ws%3A%2F%2F127.0.0.1%3A9944#/settings/developer, if you are a development team with at least a test network that is available and listed at https://polkadot.js.org/apps, then you could consider modifying the apps-config package and creating a Pull Request into the https://github.com/polkadot-js repository to add the types directly so they would be automatically configured when anyone tried to connect to it.

Or if you just wanted to interact with your custom Substrate node running on your local machine you could just go to: https://polkadot.js.org/apps/?rpc=ws%3A%2F%2F127.0.0.1%3A9944#/settings/developer, paste your additional types, and then press the Save button.

For example, below is an example of the custom types you might paste to be compatible with a recent release of the Polkadot.js API where you could add the correct AccountInfo type for your chain, such as providing a value of AccountInfoWithDualRefCount if your custom chain uses the old-style double refcount (with 4 bytes missing) if the API defaulted to more recent triple refcount. In the example below we have also assumed that the custom chain uses a custom Balance type of u64, an Address type of MultiAddress as shown here, and where a standalone chain is being used with two session keys (i.e. Grandpa, Aura) in the chain specification so custom Keys type of SessionKeys2 is used. If you were to modify your custom chain to use four session keys instead (i.e. Grandpa, Babe, ImOnline, AuthorityDiscovery) then you would change the value to SessionKeys4.

{
  AccountInfo: "AccountInfoWithDualRefCount",
  Keys: "SessionKeys2",
  Address: "MultiAddress",
  LookupSource: "MultiAddress",
  Balance: "u64",
  UserInfo: {
    "user_dna": "[u8; 16]"
    "user_name": "Text",
    "user_address": "AccountId",
    "user_storage_hash": "Hash",
    "user_dob": "Date",
    "user_reward": "Balance",
    "user_reward_at_block": "Moment"
  }
}

If you created your chain based on the substrate-node-template and in runtime/lib.rs you added the following types to configure the pallet-template.

impl pallet_template::Config for Runtime {
    type RuntimeEvent = RuntimeEvent;

    // https://polkadot.js.org/api/types
    type UserDNA = [u8; 16];
    type UserIndex = u64;
    type UserName = Vec<u8>; // Text
    type UserAddress = AccountId;
    type UserExternalStorageHash = Hash;
    // https://docs.rs/chrono/latest/chrono/
    type UserDOB = i64;
    // https://substrate.recipes/currency.html#just-plain-currency
    type UserReward = Balance;
    type UserRewardAtBlock = u64;
}

Then in pallets/template/src/lib.rs, you could use user-defined structs and use them to set and retrieve data from storage, as shown here in the Substrate kitties tutorial and elsewhere here.

#[derive(Encode, Decode, Clone, PartialEq, Eq)]
#[cfg_attr(feature = "std", derive(Debug))]
pub struct User(pub [u8; 16]);

#[cfg_attr(feature = "std", derive(Debug))]
#[derive(Encode, Decode, Default, Clone, PartialEq)]
// Generic type parameters
pub struct UserInfo<U, V, W, X, Y, Z> {
    pub user_name: U, // Text
    pub user_address: V, // AccountId
    pub user_storage_hash: W, // Hash
    pub user_dob: X, // i64
    pub user_reward: Y, // Balance
    pub user_reward_at_block: Z // u64
}
5
  • Thank you for your detailed answer. But, I'd want the types generated from typegen to be used in the polkadot-js/apps/packages/apps-config/src/api/typesBundle.ts instead of the Developer tab on explorer. Can you please explain how would I do that?
    – Discardo
    Commented Feb 8, 2023 at 5:49
  • There are example PRs with "custom types" here: github.com/polkadot-js/apps/pulls?q=is%3Apr+custom+types Commented Feb 8, 2023 at 9:50
  • At that link the best PR is by InterBTC github.com/polkadot-js/apps/pull/6779/files where they import custom types from NPM npmjs.com/package/@interlay/interbtc-types. PRs by Spartan, Subspace, KILT, and BitCountry are also good. You can't fetch from external json file like I did in this PR here github.com/polkadot-js/apps/pull/3084. Specify minmax for the metadata OverrideVersionedType (i.e. where min (v >= min) and max (v <= max)). Note that typesBundle.ts file is automatically generated by running yarn run build:extra Commented Feb 8, 2023 at 10:10
  • How did you get this json file for your chain?
    – Discardo
    Commented Feb 8, 2023 at 10:44
  • I wrote it manually Commented Feb 8, 2023 at 23:14

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.