Skip to content

Commit

Permalink
Begin migration to TypeScript (#302)
Browse files Browse the repository at this point in the history
  • Loading branch information
jdtzmn committed Mar 19, 2021
1 parent d7c9f89 commit 13d5c92
Show file tree
Hide file tree
Showing 70 changed files with 4,752 additions and 1,334 deletions.
15 changes: 14 additions & 1 deletion .eslintrc.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ module.exports = {
node: true,
mocha: true,
},
extends: ['airbnb-base', 'prettier'],
extends: ['airbnb-base', 'prettier', 'plugin:import/typescript'],
parser: '@typescript-eslint/parser',
parserOptions: {
ecmaVersion: 12,
Expand All @@ -15,6 +15,19 @@ module.exports = {
'no-restricted-syntax': ['error', 'LabeledStatement', 'WithStatement'],
'no-plusplus': ['error', { allowForLoopAfterthoughts: true }],
'max-classes-per-file': 'off',
'import/extensions': [
'error',
'ignorePackages',
{
js: 'never',
ts: 'never',
},
],
'lines-between-class-members': [
'error',
'always',
{ exceptAfterSingleLine: true },
],
},
ignorePatterns: [
'dist/',
Expand Down
4 changes: 2 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
unit:
node_modules/.bin/cucumber-js --tags "@unit.offline or @unit.algod or @unit.indexer or @unit.rekey or @unit.tealsign or @unit.dryrun or @unit.applications or @unit.responses or @unit.transactions or @unit.responses.231" tests/cucumber/features --require tests/cucumber/steps/index.js
node_modules/.bin/cucumber-js --tags "@unit.offline or @unit.algod or @unit.indexer or @unit.rekey or @unit.tealsign or @unit.dryrun or @unit.applications or @unit.responses or @unit.transactions or @unit.responses.231" tests/cucumber/features --require-module ts-node/register --require tests/cucumber/steps/index.js
integration:
node_modules/.bin/cucumber-js --tags "@algod or @assets or @auction or @kmd or @send or @template or @indexer or @rekey or @dryrun or @compile or @applications or @indexer.applications or @applications.verified or @indexer.231" tests/cucumber/features --require tests/cucumber/steps/index.js
node_modules/.bin/cucumber-js --tags "@algod or @assets or @auction or @kmd or @send or @template or @indexer or @rekey or @dryrun or @compile or @applications or @indexer.applications or @applications.verified or @indexer.231" tests/cucumber/features --require-module ts-node/register --require tests/cucumber/steps/index.js

docker-test:
./tests/cucumber/docker/run_docker.sh
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ For detailed information about the different API calls in `client`, visit https:
Running examples requires access to a running node. Follow the instructions in Algorand's [developer resources](https://developer.algorand.org/docs/run-a-node/setup/install/) to install a node on your computer.
Please refer to the instructions described in the [examples/README.md](examples/README.md) file for more information regarding running the examples.
**As portions of the codebase are written in TypeScript, examples cannot be run directly using `node`**. Please refer to the instructions described in the [examples/README.md](examples/README.md) file for more information regarding running the examples.
## SDK Development
Expand Down
2 changes: 1 addition & 1 deletion dist/algosdk.min.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion dist/algosdk.min.js.map

Large diffs are not rendered by default.

2 changes: 2 additions & 0 deletions dist/index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
import * as algosdk from './src/main';
export default algosdk;
52 changes: 52 additions & 0 deletions dist/src/encoding/address.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import { Address } from '../types/address';
export declare const ALGORAND_ZERO_ADDRESS_STRING = "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAY5HFKQ";
export declare const MALFORMED_ADDRESS_ERROR_MSG = "address seems to be malformed";
export declare const CHECKSUM_ADDRESS_ERROR_MSG = "wrong checksum for address";
export declare const INVALID_MSIG_VERSION_ERROR_MSG = "invalid multisig version";
export declare const INVALID_MSIG_THRESHOLD_ERROR_MSG = "bad multisig threshold";
export declare const INVALID_MSIG_PK_ERROR_MSG = "bad multisig public key - wrong length";
export declare const UNEXPECTED_PK_LEN_ERROR_MSG = "nacl public key length is not 32 bytes";
/**
* decodeAddress takes an Algorand address in string form and decodes it into a Uint8Array.
* @param address an Algorand address with checksum.
* @returns the decoded form of the address's public key and checksum
*/
export declare function decodeAddress(address: string | String): Address;
/**
* isValidAddress checks if a string is a valid Algorand address.
* @param address an Algorand address with checksum.
* @returns true if valid, false otherwise
*/
export declare function isValidAddress(address: string): boolean;
/**
* encodeAddress takes an Algorand address as a Uint8Array and encodes it into a string with checksum.
* @param address a raw Algorand address
* @returns the address and checksum encoded as a string.
*/
export declare function encodeAddress(address: Uint8Array | number[]): string;
/**
* fromMultisigPreImg takes multisig parameters and returns a 32 byte typed array public key,
* representing an address that identifies the "exact group, version, and public keys" that are required for signing.
* Hash("MultisigAddr" || version uint8 || threshold uint8 || PK1 || PK2 || ...)
* Encoding this output yields a human readable address.
* @param version multisig version
* @param threshold multisig threshold
* @param pks array of typed array public keys
*/
export declare function fromMultisigPreImg({ version, threshold, pks, }: {
version: number;
threshold: number;
pks: ArrayLike<ArrayLike<number>>;
}): number[];
/**
* fromMultisigPreImgAddrs takes multisig parameters and returns a human readable Algorand address.
* This is equivalent to fromMultisigPreImg, but interfaces with encoded addresses.
* @param version multisig version
* @param threshold multisig threshold
* @param addrs array of encoded addresses
*/
export declare function fromMultisigPreImgAddrs({ version, threshold, addrs, }: {
version: number;
threshold: number;
addrs: string[];
}): string;
30 changes: 30 additions & 0 deletions dist/src/encoding/encoding.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
/**
* This file is a wrapper of msgpack.js.
* The wrapper was written in order to ensure correct encoding of Algorand Transaction and other formats.
* In particular, it matches go-algorand blockchain client, written in go (https://www.github.com/algorand/go-algorand.
* Algorand's msgpack encoding follows to following rules -
* 1. Every integer must be encoded to the smallest type possible (0-255->8bit, 256-65535->16bit, etx)
* 2. All fields names must be sorted
* 3. All empty and 0 fields should be omitted
* 4. Every positive number must be encoded as uint
* 5. Binary blob should be used for binary data and string for strings
* */
export declare const ERROR_CONTAINS_EMPTY_STRING = "The object contains empty or 0 values. First empty or 0 value encountered during encoding: ";
/**
* containsEmpty returns true if any of the object's values are empty, false otherwise.
* Empty arrays considered empty
* @param obj
* @returns / {true, empty key} if contains empty, {false, undefined} otherwise
*/
export declare function containsEmpty(obj: Record<string | number | symbol, any>): {
containsEmpty: boolean;
firstEmptyKey: string;
};
/**
* encode encodes objects using msgpack
* @param obj a dictionary to be encoded. Must not contain empty or 0 values.
* @returns msgpack representation of the object
* @throws Error containing ERROR_CONTAINS_EMPTY_STRING if the object contains empty or zero values
*/
export declare function encode(obj: Record<string | number | symbol, any>): Uint8Array;
export declare function decode(buffer: ArrayLike<number>): unknown;
27 changes: 27 additions & 0 deletions dist/src/encoding/uint64.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/**
* encodeUint64 converts an integer to its binary representation.
* @param num The number to convert. This must be an unsigned integer less than
* 2^64.
* @returns An 8-byte typed array containing the big-endian encoding of the input
* integer.
*/
export declare function encodeUint64(num: number | bigint): Uint8Array;
/**
* decodeUint64 produces an integer from a binary representation.
* @param data An typed array containing the big-endian encoding of an unsigned integer
* less than 2^64. This array must be at most 8 bytes long.
* @param decodingMode Configure how the integer will be
* decoded.
*
* The options are:
* * "safe": The integer will be decoded as a Number, but if it is greater than
* Number.MAX_SAFE_INTEGER an error will be thrown.
* * "mixed": The integer will be decoded as a Number if it is less than or equal to
* Number.MAX_SAFE_INTEGER, otherwise it will be decoded as a BigInt.
* * "bigint": The integer will always be decoded as a BigInt.
*
* Defaults to "safe" if not included.
* @returns The integer that was encoded in the input data. The return type will
* be determined by the parameter decodingMode.
*/
export declare function decodeUint64(data: Uint8Array, decodingMode?: 'safe' | 'mixed' | 'bigint'): number | bigint;
128 changes: 128 additions & 0 deletions dist/src/main.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,128 @@
import * as txnBuilder from './transaction';
import bidBuilder from './bid';
import algod from './client/algod';
import kmd from './client/kmd';
import algodv2 from './client/v2/algod/algod';
import indexer from './client/v2/indexer/indexer';
import AnyTransaction from './types/transactions';
import { MultisigMetadata } from './types/multisig';
export declare const Algod: typeof algod.Algod;
export declare const Kmd: typeof kmd.Kmd;
export declare const Algodv2: typeof algodv2.AlgodClient;
export declare const Indexer: typeof indexer.IndexerClient;
export declare const MULTISIG_BAD_SENDER_ERROR_MSG = "The transaction sender address and multisig preimage do not match.";
/**
* signTransaction takes an object with either payment or key registration fields and
* a secret key and returns a signed blob.
*
* Payment transaction fields: from, to, amount, fee, firstRound, lastRound, genesisHash,
* note(optional), GenesisID(optional), closeRemainderTo(optional)
*
* Key registration fields: fee, firstRound, lastRound, voteKey, selectionKey, voteFirst,
* voteLast, voteKeyDilution, genesisHash, note(optional), GenesisID(optional)
*
* If the final calculated fee is lower than the protocol minimum fee, the fee will be increased to match the minimum.
* @param txn object with either payment or key registration fields
* @param sk Algorand Secret Key
* @returns object contains the binary signed transaction and its txID
*/
export declare function signTransaction(txn: AnyTransaction | txnBuilder.Transaction, sk: Uint8Array): {
txID: string;
blob: Uint8Array;
};
/**
* signBid takes an object with the following fields: bidder key, bid amount, max price, bid ID, auctionKey, auction ID,
* and a secret key and returns a signed blob to be inserted into a transaction Algorand note field.
* @param bid Algorand Bid
* @param sk Algorand secret key
* @returns Uint8Array binary signed bid
*/
export declare function signBid(bid: ConstructorParameters<typeof bidBuilder.Bid>[0], sk: Uint8Array): Uint8Array;
/**
* signBytes takes arbitrary bytes and a secret key, prepends the bytes with "MX" for domain separation, signs the bytes
* with the private key, and returns the signature.
* @param bytes Uint8array
* @param sk Algorand secret key
* @returns binary signature
*/
export declare function signBytes(bytes: Uint8Array, sk: Uint8Array): Uint8Array;
/**
* verifyBytes takes array of bytes, an address, and a signature and verifies if the signature is correct for the public
* key and the bytes (the bytes should have been signed with "MX" prepended for domain separation).
* @param bytes Uint8Array
* @param signature binary signature
* @param addr string address
* @returns bool
*/
export declare function verifyBytes(bytes: Uint8Array, signature: Uint8Array, addr: string): boolean;
/**
* signMultisigTransaction takes a raw transaction (see signTransaction), a multisig preimage, a secret key, and returns
* a multisig transaction, which is a blob representing a transaction and multisignature account preimage. The returned
* multisig txn can accumulate additional signatures through mergeMultisigTransactions or appendMultisigTransaction.
* @param txn object with either payment or key registration fields
* @param version multisig version
* @param threshold multisig threshold
* @param addrs a list of Algorand addresses representing possible signers for this multisig. Order is important.
* @param sk Algorand secret key. The corresponding pk should be in the pre image.
* @returns object containing txID, and blob of partially signed multisig transaction (with multisig preimage information)
* If the final calculated fee is lower than the protocol minimum fee, the fee will be increased to match the minimum.
*/
export declare function signMultisigTransaction(txn: AnyTransaction | txnBuilder.Transaction, { version, threshold, addrs }: MultisigMetadata, sk: Uint8Array): {
txID: string;
blob: Uint8Array;
};
/**
* mergeMultisigTransactions takes a list of multisig transaction blobs, and merges them.
* @param multisigTxnBlobs a list of blobs representing encoded multisig txns
* @returns blob representing encoded multisig txn
*/
export declare function mergeMultisigTransactions(multisigTxnBlobs: Uint8Array[]): Uint8Array;
/**
* appendSignMultisigTransaction takes a multisig transaction blob, and appends our signature to it.
* While we could derive public key preimagery from the partially-signed multisig transaction,
* we ask the caller to pass it back in, to ensure they know what they are signing.
* @param multisigTxnBlob an encoded multisig txn. Supports non-payment txn types.
* @param version multisig version
* @param threshold multisig threshold
* @param addrs a list of Algorand addresses representing possible signers for this multisig. Order is important.
* @param sk Algorand secret key
* @returns object containing txID, and blob representing encoded multisig txn
*/
export declare function appendSignMultisigTransaction(multisigTxnBlob: Uint8Array, { version, threshold, addrs }: MultisigMetadata, sk: Uint8Array): {
txID: any;
blob: Uint8Array;
};
/**
* multisigAddress takes multisig metadata (preimage) and returns the corresponding human readable Algorand address.
* @param version mutlisig version
* @param threshold multisig threshold
* @param addrs list of Algorand addresses
*/
export declare function multisigAddress({ version, threshold, addrs, }: MultisigMetadata): string;
/**
* encodeObj takes a javascript object and returns its msgpack encoding
* Note that the encoding sorts the fields alphabetically
* @param o js obj
* @returns Uint8Array binary representation
*/
export declare function encodeObj(o: Record<string | number | symbol, any>): Uint8Array;
/**
* decodeObj takes a Uint8Array and returns its javascript obj
* @param o Uint8Array to decode
* @returns object
*/
export declare function decodeObj(o: ArrayLike<number>): unknown;
export declare const ERROR_MULTISIG_BAD_SENDER: Error;
export declare const ERROR_INVALID_MICROALGOS: Error;
export { isValidAddress, encodeAddress, decodeAddress, } from './encoding/address';
export { encodeUint64, decodeUint64 } from './encoding/uint64';
export { generateAccount } from './account';
export { secretKeyToMnemonic, mnemonicToSecretKey } from './mnemonic/mnemonic';
export { default as modelsv2 } from './client/v2/algod/models/types';
export { mnemonicToMasterDerivationKey, masterDerivationKeyToMnemonic, } from './mnemonic/mnemonic';
export { microalgosToAlgos, algosToMicroalgos, INVALID_MICROALGOS_ERROR_MSG, } from './convert';
export { computeGroupID, assignGroupID } from './group';
export { makeLogicSig, signLogicSigTransaction, signLogicSigTransactionObject, logicSigFromByte, tealSign, tealSignFromProgram, } from './logicsig';
export { default as LogicTemplates } from './logicTemplates';
export * from './makeTxn';
export * from './transaction';
Loading

0 comments on commit 13d5c92

Please sign in to comment.