## Sidecar example for `DED` balance of an account ### Installation Steps - `git clone https://github.com/paritytech/substrate-api-sidecar.git` - `cd substrate-api-sidecar` - `yarn` - `yarn build` #### Add .env file Create a new `.env` file in the root directory that will tell Sidecar to connect to the chain you want through a public endpoint, e.g. Polkadot Asset Hub, instead of your local node. #### Steps - `touch .env.polkadotassethub` in the root directory - and then edit the file and - add this line `SAS_SUBSTRATE_URL=wss://statemint-rpc.dwellir.com` - Save the changes This will connect Sidecar to the public endpoint that is provided by dwellir and it is an example. You can find other public endpoints from other providers. **IMPORTANT NOTE:** It is worth mentioning that in production environment we do not recommend using public endpoints but a full local node that you maintain. For the installation you need to have nodejs installed which I assume you already do. ### Run Sidecar Last you can start Sidecar by running the command - `NODE_ENV=polkadotassethub yarn start` in the root dir assuming that you named your `.env` file as mentioned previously. #### Sidecar Endpoints Now if you open any browser and give this address http://127.0.0.1:8080/ you will see all the endpoints that are available to you. #### Example Endpoint Check the asset balances of an account, e.g. `http://127.0.0.1:8080/accounts/155HWw3J9jyYphMm5is4vp9Bzj7ZRRd6HEzCPdWd8cq97KfT/asset-balances` ### Example script An example script to access the same endpoint can be done as follows: While your sidecar instance is running you open another terminal : - `mkdir demo-script` - `cd demo-script` - `touch index.js` - if you edit the `index.js` file you can paste this simple script ```javascript const axios = require('axios'); const BASE_URL = 'http://127.0.0.1:8080'; const main = async () => { const exampleAccount = '155HWw3J9jyYphMm5is4vp9Bzj7ZRRd6HEzCPdWd8cq97KfT'; const endpoint = `${BASE_URL}` + '/accounts/' + exampleAccount + '/asset-balances'; const response = await axios.get(endpoint, { params: { assets: [30] } }); console.log(response.data); }; main(); ``` - save the changes - to run this script you can install `axios` with `npm install axios` - and then `node index.js` #### Output - The result will be the `DED` (since `assetId` of DED is `30`) balance for this example account ```bash { at: { hash: '0x98e3a9f5f087005c296cd17c0c1709f2fa6d04b80a3369c38c244cb87140a0ad', height: '6045104' }, assets: [ { assetId: '30', balance: '15646078874736', isFrozen: 'isFrozen does not exist for this runtime', isSufficient: false } ] } ``` ## Asset-Transfer-API example for `DED` transfer ### Installation Steps Installation steps mentioned in the demo of asset-transfer-api in this [deep dive](https://youtu.be/H6BMBthmwTI?feature=shared) (at the 27 minute mark) #### Steps - `mkdir ata-demo` - `cd ata-demo` - `npm init -y` - `npm install @substrate/asset-transfer-api` ### Create DED transfer script `DED` is available only in Polkadot Asset Hub based on the info we have in the [registry](https://github.com/paritytech/asset-transfer-api-registry/blob/main/docs/registry.json). Thus, it would be a local transaction from one account in Polkadot Asset Hub to another account again in Polkadot Asset Hub. So the code will be very similar to the one shown in this [example](https://github.com/paritytech/asset-transfer-api/blob/main/examples/localParachainTx.ts) but with some slight changes. - while in `ata-demo` directory - `touch index.js` - Open the `index.js` file ```javascript const {AssetTransferApi, constructApiPromise} = require('@substrate/asset-transfer-api'); const main = async () => { const { api, specName, safeXcmVersion } = await constructApiPromise('wss://statemint-rpc.dwellir.com'); const assetApi = new AssetTransferApi(api, specName, safeXcmVersion); try { callInfo = await assetApi.createTransferTransaction( '1000', '0xF977814e90dA44bFA03b6295A0616a897441aceC', ['30'], ['100000'], { format: 'call', keepAlive: true, }, ); console.log(`The following call data that is returned:\n${JSON.stringify(callInfo, null, 4)}`); } catch (e) { console.error(e); throw Error(e); } const decoded = assetApi.decodeExtrinsic(callInfo.tx, 'call'); console.log(`\nThe following decoded tx:\n ${JSON.stringify(JSON.parse(decoded), null, 4)}`); }; main() .catch((err) => console.error(err)) .finally(() => process.exit()); ``` #### Output ```bash The following call data that is returned: { "origin": "statemint", "dest": "statemint", "direction": "local", "xcmVersion": null, "method": "assets::transferKeepAlive", "format": "call", "tx": "0x32097804f977814e90da44bfa03b6295a0616a897441acec821a0600" } The following decoded tx: { "args": { "id": "30", "target": { "Address20": "0xf977814e90da44bfa03b6295a0616a897441acec" }, "amount": "100,000" }, "method": "transferKeepAlive", "section": "assets" } ``` As shown also in the Deep Dive, you can copy paste the tx hash you see in the output and open [p-js apps](https://polkadot.js.org/apps/?rpc=wss%3A%2F%2Fsys.dotters.network%2Fstatemint#/extrinsics/decode) to submit it. ### DED transfer script - Create transfer, Sign & Submit **Prerequisites** - Have `nodejs` installed - Install the required packages (keyring, util crypto) with `npm install...` Add below code in a js file, e.g. `index.js` file ```javascript= const {AssetTransferApi, constructApiPromise, TxResult} = require('@substrate/asset-transfer-api'); const { Keyring } = require('@polkadot/keyring'); const { cryptoWaitReady } = require('@polkadot/util-crypto'); const main = async () => { const { api, specName, safeXcmVersion } = await constructApiPromise('wss://polkadot-asset-hub-rpc.polkadot.io'); const assetApi = new AssetTransferApi(api, specName, safeXcmVersion); let callInfo; try { callInfo = await assetApi.createTransferTransaction( '1000', '16VFgPxYcHQ95FLEPCF9rh89L5PYgNVuiwsfYacrZjjg6kcf', // Destination Account ['30'], ['100000000000'], // 10 DED { format: 'submittable', keepAlive: true, }, ); console.log(`The following call data that is returned:\n${JSON.stringify(callInfo, null, 4)}`); } catch (e) { console.error(e); throw Error(e); } const decoded = assetApi.decodeExtrinsic(callInfo.tx, 'call'); console.log(`\nThe following decoded tx:\n ${JSON.stringify(JSON.parse(decoded), null, 4)}`); await cryptoWaitReady(); const phrase = 'MNEMONIC PHRASE HERE'; const keyring = new Keyring(); const domi_keypair = keyring.addFromUri(phrase, { name: 'Domi' }, 'sr25519'); await callInfo.tx.signAndSend(domi_keypair); }; main() .catch((err) => console.error(err)) .finally(() => process.exit()); ``` - Change `Destination Account` in line 13 with the address that you wish to send `DED` to - Change the amount of `DED` in line 15 depending on how many `DED` you will like to send. - Replace 'MNEMONIC PHRASE HERE' with the seed of the account from which you will sign&send this transaction. - Caution: format in line 17 now is set to `submittable` - Run with `node index.js` **IMPORTANT NOTE** : The account from which you will sign & send this transaction needs to have enough `DOT` to cover the transaction fees. **Troubleshooting** If you get the error `TypeError: callInfo.tx.signAndSend is not a function` while trying to run this script, then you need to set the `format` option (line 17) to `submittable`.