@fat-token/fat-js

1.3.0 • Public • Published

fat-js

npm (scoped)

Build Status

Coverage Status

Factom Asset Token client implementation in JS 💙

Currently supports FAT-0 and FAT-1 token standards.

Installation

NPM CLI:

npm i @fat-token/fat-js

Browser Bundle

A browser friendly bundle of the current fat-js version can be found at dist/fatjs.js

To build the bundle from source ensure you have browserify installed, and simply navigate to the root of the fat-js project and run:

npm run build

A fresh fatjs.js will be built in the dist directory.

Bundle Distribution

You can also use the latest version fat-js in your webpage via JSDeliver!:

<script src="https://cdn.jsdelivr.net/gh/Factom-Asset-Tokens/fat-js/dist/fatjs.js"></script>

The fat-js library will be made available under the global object fatjs

Transactions

Build and use FAT transactions

FAT-0

Transaction Builder

Example

const TransactionBuilder = require('fat-js').FAT0.TransactionBuilder

const tokenChainId = '013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec';

let tx = new TransactionBuilder(tokenChainId)
	.input("Fs1q7FHcW4Ti9tngdGAbA3CxMjhyXtNyB1BSdc8uR46jVUVCWtbJ", 150)
	.output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", 150)
	.build();

//with metadata
tx = new TransactionBuilder(tokenChainId)
            .input("Fs1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm", 150)
            .output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", 150)
            .metadata({type: 'fat-js test run', timestamp: new Date().getTime()})
            .build();

//You can also use string or  BigNumber(https://github.com/MikeMcl/bignumber.js/) format for larger transactions than a native JS integer would support
tx = new TransactionBuilder(testTokenChainId)
            .input("Fs1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm", '19007199254740991')
            .output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", '19007199254740991')
            .build();

Transaction

Example

const Transaction = require('fat-js').FAT0.Transaction

//From transaction builder
let tx = new TransactionBuilder(tokenChainId)
	.input("Fs1q7FHcW4Ti9tngdGAbA3CxMjhyXtNyB1BSdc8uR46jVUVCWtbJ", 150)
	.output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", 150)
	.build();

tx.getInputs(); // => {"FA1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm": new BigNumber(150)}

tx.getChainId(); // => "013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec"


//or from API response
const response =
    {
        entryhash: '68f3ca3a8c9f7a0cb32dc9717347cb179b63096e051a60ce8be9c292d29795af',
        timestamp: 1550696040,
        data:
            {
                inputs: {FA1zT4aFpEvcnPqPCigB3fvGu4Q4mTXY22iiuV69DqE1pNhdF2MC: new BigNumber(150)},
                outputs: {FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM: new BigNumber(150)}
            }
    };

tx = new Transaction(response);

tx.getEntryHash(); // => "68f3ca3a8c9f7a0cb32dc9717347cb179b63096e051a60ce8be9c292d29795af"

FAT-1

Transaction Builder

Example

const TransactionBuilder = require('fat-js').FAT1.TransactionBuilder

const tokenId = 'mytoken';
const tokenChainId = '013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec';

 let tx = new TransactionBuilder(testTokenChainId)
            .input("Fs1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm", [{min: 0, max: 3}, 150])
            .output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", [{min: 0, max: 3}, 150])
            .build();

//NF token metadata
tx = new TransactionBuilder(testTokenChainId)
            .coinbaseInput([10])
            .output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", [10])
            .tokenMetadata([
                {
                    ids: [10],
                    metadata: {type: 'fat-js test run', timestamp: new Date().getTime()},
                }
            ])
            .sk1("sk13Rp3LVmVvWqo8mff82aDJN2yNCzjUs2Zuq3MNQSA5oC5ZwFAuu")
            .build();

Transaction

Example

const Transaction = require('fat-js').FAT1.Transaction

//From transaction builder
let tx = new TransactionBuilder(testTokenChainId)
            .input("Fs1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm", [{min: 0, max: 3}, 150])
            .output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", [{min: 0, max: 3}, 150])
            .build();

tx.getInputs(); // => {"FA1PkAEbmo1XNangSnxmKqi1PN5sVDbQ6zsnXCsMUejT66WaDgkm":[{min: 0, max: 3}, 150]}

tx.getChainId(); // => "013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec"


//or from API response
const response =
    {
        entryhash: '68f3ca3a8c9f7a0cb32dc9717347cb179b63096e051a60ce8be9c292d29795af',
        timestamp: 1550696040,
        data:
            {
                inputs: {FA1zT4aFpEvcnPqPCigB3fvGu4Q4mTXY22iiuV69DqE1pNhdF2MC: [{min: 0, max: 3}, 150]},
                outputs: {FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM: [{min: 0, max: 3}, 150]}
            }
    };

tx = new Transaction(response);

tx.getEntryHash(); // => "68f3ca3a8c9f7a0cb32dc9717347cb179b63096e051a60ce8be9c292d29795af"

Issuance

Build and model issuances of FAT tokens

FAT-0

IssuanceBuilder

const IssuanceBuilder = require('fat-js').FAT0.IssuanceBuilder

const issuance = new IssuanceBuilder("mytoken", "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762", "sk11pz4AG9XgB1eNVkbppYAWsgyg7sftDXqBASsagKJqvVRKYodCU")
            .symbol('TTK')
            .supply(1000000)
            .metadata({'abc': 123})
            .build();

Issuance

const Issuance = require('fat-js').FAT0.Issuance

//From Builder
const builder = new IssuanceBuilder("mytoken", "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762", "sk11pz4AG9XgB1eNVkbppYAWsgyg7sftDXqBASsagKJqvVRKYodCU")
            .symbol('TTK');

let issuance = new Issuance(builder);

issuance.getChainId(); // => 013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec

//Or from API response
const data = {
            "chainid": "eb55f75551acfb9c4d8dc1f09f11f2512d8aa98ebc1c0d05652ce8d92102fad8",
            "tokenid": "test0",
            "issuerid": "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762",
            "entryhash": "d58588edb831afba683c69eb72bb8c825b198ae2ec02206d54926880727d91b1",
            "timestamp": 1548276060,
            "issuance": {
                "type": "FAT-0",
                "supply": 99999999,
                "symbol": "T0"
	}
};

issuance = new Issuance(data);

issuance.getTimestamp(); // => 1548276060

FAT-1

IssuanceBuilder

const IssuanceBuilder = require('fat-js').FAT1.IssuanceBuilder

const issuance = new IssuanceBuilder("mytoken", "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762", "sk11pz4AG9XgB1eNVkbppYAWsgyg7sftDXqBASsagKJqvVRKYodCU")
            .symbol('TNF')
            .supply(-1)
            .metadata({'abc': 123})
            .build();

Issuance

const Issuance = require('fat-js').FAT1.Issuance

//From Builder
const builder = new IssuanceBuilder("mytoken", "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762", "sk11pz4AG9XgB1eNVkbppYAWsgyg7sftDXqBASsagKJqvVRKYodCU")
            .symbol('TTK');

let issuance = new Issuance(builder);

issuance.getChainId(); // => 013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec

//Or from API response
const data = {
            "chainid": "eb55f75551acfb9c4d8dc1f09f11f2512d8aa98ebc1c0d05652ce8d92102fad8",
            "tokenid": "test0",
            "issuerid": "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762",
            "entryhash": "d58588edb831afba683c69eb72bb8c825b198ae2ec02206d54926880727d91b1",
            "timestamp": 1548276060,
            "issuance": {
                "type": "FAT-0",
                "supply": 99999999,
                "symbol": "T0"
	}
};

issuance = new Issuance(data);

issuance.getTimestamp(); // => 1548276060

CLI

Complete CLI Builder Documentation

Complete CLI Documentation

Instantiate FAT CLI

const CLIBuilder = require('fat-js').CLIBuilder
let cli = new CLIBuilder()
    .host('fatnode.mysite.com')
    .port(8078)
	.timeout(3500) //optional, timeout ms
    .build();

Daemon CLI

Get Daemon Properties

Get a object containing a readout of properties for the connected fatd node

const properties = await cli.getDaemonProperties();

/*
{
  "fatdversion": "r162.3d7f272",
  "apiversion": "1"
}
*/

Get Daemon Library Compatibility

Get a an array of compatibility warning objects for the combination of the current fat-js and fatd versions. Zero elements returned means full compatibility.

const issues = await cli.getCompatibility();

/*
[
  {
    "severity": "WARN",
    "message": "You are using a version of fatd with unofficial local code changes. Unexpected or inconsistent behavior may occur"
  }
]
*/

Get Daemon Sync Status

Get a object containing a readout of properties for the connected fatd node

const properties = await cli.getDaemonProperties();

/*
{
  "jsonrpc": "2.0",
  "result": {
    "syncheight": 70990,
    "factomheight": 70990
  },
  "id": 6482
}
*/

Get Balance of Address For All Tracked Tokens Tokens

Get the numeric count of tokens, either non fungible or fungible, for each token type (chain) an address owns greater than 0 of. The keys of the object returned are the chain Ids, and values are the balances, represented as BigNumbers

const balances = await cli.getBalances('FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM');

/*
{
  "0cccd100a1801c0cf4aa2104b15dec94fe6f45d0f3347b016ed20d81059494df": new BigNumber("9007199254743301"),
  "962a18328c83f370113ff212bae21aaf34e5252bc33d59c9db3df2a6bfda966f": new BigNumber("19248")
}
*/

Token CLI

Complete FAT-0 Token CLI Documentation

Complete FAT-1 Token CLI Documentation

The token CLI allows access to both FAT-0 and FAT-1 data from fatd.

Before creating a token you must create a token CLI instance using the token's chain ID:

Instantiate Token CLI

const tokenCLI = await cli.getTokenCLI('013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec');

Fat-js will automatically and asynchronously determine the proper FAT token type to use for the CLI.

You can also synchronously generate a token CLI instance if if you already know the token type:

const tokenCLI = await cli.getTokenCLISync('013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec','FAT-0');

Get Issuance

Get a FAT issuance entry for the selected token

const issuance = await tokenCLI.getIssuance();

Get Transaction

Get a FAT transaction Object by its entryhash

const transaction = await tokenCLI.getTransaction('d9b6ca250c97fdbe48eb3972a7d4b906aac54f2048982acfcb6019bc2a018be9');

Get Transactions

Get a paged list of FAT transactions.

const transactions = await tokenCLI.getTransactions();

Get Balance

Get the numeric balance of a public Factoid address. Returned as a BigNumber

let balance = await tokenCLI.getBalance('FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM');

/*
new BigNumber(150)
*/

Note: The NF token balance count is returned for FAT-1 tokens

Get Non-Fungible Balance

Get the tokens owned by a public Factoid address.

let tokens = await tokenCLI.getNFBalance(params);

/*
[
  0,
  1,
  3,
  4
]
*/

Send A Transaction

Send a FAT-0 or FAT-1 transaction.

const tx = new TransactionBuilder(tokenChainId)
	.input("Fs1q7FHcW4Ti9tngdGAbA3CxMjhyXtNyB1BSdc8uR46jVUVCWtbJ", 150)
	.output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", 150)
	.build();

const result = await tokenCLI.sendTransaction(tx);

/*
{
  "chainid": "eb55f75551acfb9c4d8dc1f09f11f2512d8aa98ebc1c0d05652ce8d92102fad8",
  "txid": "6eeb96a4b7cb58cb5e7455c96b4d5db74a627485291820c3f3f3e2a7854ebfbe",
  "entryhash": "5a6c6d1a2c8275c5854e5ecc54a10814834580ea4114d0c0f4348d21849284e2"
}
*/

Submitting Transactions & Issuances Directly to Factom

After building and signing a FAT issuance or transaction, you can submit it directly to Factom without using fatd as an intermediary using the factom-js library

All you need to get started are Entry Credits and a Factomd endpoint

Transaction

const { FactomCli } = require('factom');
const cli = new FactomCli(); // Default factomd connection to localhost:8088 and walletd connection to localhost:8089

const tokenChainId = '013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec';

const tx = new TransactionBuilder(tokenChainId)
	.input("Fs1q7FHcW4Ti9tngdGAbA3CxMjhyXtNyB1BSdc8uR46jVUVCWtbJ", 150)
	.output("FA3aECpw3gEZ7CMQvRNxEtKBGKAos3922oqYLcHQ9NqXHudC6YBM", 150)
	.build();

//get the signed transaction entry
//"cast" the chain and entry objects to prevent compatibility issues
const entry = Entry.builder(tx.getEntry()).build();

await cli.add(entry, "Es32PjobTxPTd73dohEFRegMFRLv3X5WZ4FXEwNN8kE2pMDfeMym"); //commit the transaction entry to the token chain

Issuance

const { FactomCli } = require('factom');
const cli = new FactomCli(); // Default factomd connection to localhost:8088 and walletd connection to localhost:8089

const tokenChainId = '013de826902b7d075f00101649ca4fa7b49b5157cba736b2ca90f67e2ad6e8ec';

const issuance = new IssuanceBuilder("mytoken", "888888d027c59579fc47a6fc6c4a5c0409c7c39bc38a86cb5fc0069978493762", "sk11pz4AG9XgB1eNVkbppYAWsgyg7sftDXqBASsagKJqvVRKYodCU")
            .symbol('TTK')
            .supply(1000000)
            .metadata({'abc': 123})
            .build();

//"cast" the chain and entry objects to prevent compatibility issues
const chain = new Chain(Entry.builder(issuance.getChain().firstEntry).build());
const entry = Entry.builder(issuance.getEntry()).build();

await cli.add(chain, "Es32PjobTxPTd73dohEFRegMFRLv3X5WZ4FXEwNN8kE2pMDfeMym"); //create the token chain on Factom

await cli.add(entry, "Es32PjobTxPTd73dohEFRegMFRLv3X5WZ4FXEwNN8kE2pMDfeMym"); //commit the signed issuance entry to the token chain

Utility Methods

Calculate Token Chain ID

Get token chain ID from token ID and issuer root chain ID

const util = require('fat-js').util

const chainId = util.getChainId('mytoken', '888888b2e7c7c63655fa85e0b0c43b4b036a6bede51d38964426f122f61c5584').toString('hex')

/*
0dce2c10a51a7df92e2e9e4f848da054509ff9761311bd58ebcc55df656fb409
*/

Validate Non-Fungible Token ID Range

Take an array of integers or integer ranges representing NF token IDs and validate them

let valid = util.validateNFIds([0, 1, 2, {min: 3, max: 3}, {min: 4, max: 100}]);

/*
=> true
*/

valid = util.validateNFIds([0, 1, 2, -3]); //negative ID
valid = util.validateNFIds([0, 1, 2, {min: 3, max: 2}]); //min > max
valid = util.validateNFIds([0, 1, 2, {min: 3, abc: 4}]); //malformed range or int
valid = util.validateNFIds([0, 1, 2, {min: 3, max: 2}]); //min < max
valid = util.validateNFIds([0, 1, 2, {min: 3, max: 3}, {min: 3, max: 4}]); //overlapping range

/*
=> false
*/

Reduce Non-Fungible Token ID Range

Take an array of integers representing NF token IDs and group them into ID ranges

const ranges = util.reduceNFIds([0, 1, 2, 5, 99, 100, 101, 102])

/*
[
  {
    "min": 0,
    "max": 2
  },
  5,
  {
    "min": 99,
    "max": 102
  }
]
*/

Expand Non-Fungible Token ID Range

Take an array of ID ranges representing NF token IDs expand them into an array of integers

const numbers = util.expandNFIds([{min: 0, max: 3}, 5, 9])

/*
[
  0,
  1,
  2,
  3,
  5,
  9
]
*/

Count Non-Fungible Token ID Range

Take an array of ID ranges representing NF token IDs get the count of tokens represented

const count = util.countNFIds([{min: 0, max: 3}, 5, 9])

/*
6
*/

Legal

MIT Licensed

Icons by Icons8

Readme

Keywords

none

Package Sidebar

Install

npm i @fat-token/fat-js

Weekly Downloads

1

Version

1.3.0

License

MIT

Unpacked Size

828 kB

Total Files

48

Last publish

Collaborators

  • drkatz
  • paulbernier