Add missing types (#504)

* Update rpc

* Simplify Type

* Create AbstractInt

* Add integers

* Add missing types

* Add tests for negative numbers

* Use abstract class

* Fix comments

* Bump packages

* FIx bugs

* Fix lint

* EOF add line

* Fix comment

* Typo
This commit is contained in:
Amaury Martiny
2018-12-20 18:12:25 +01:00
committed by Jaco Greeff
parent c53c574a55
commit b934846248
30 changed files with 436 additions and 126 deletions
+1 -1
View File
@@ -33,6 +33,6 @@
"@polkadot/jsonrpc": "^0.34.10",
"@polkadot/rpc-provider": "^0.34.10",
"@polkadot/types": "^0.34.10",
"@polkadot/util": "^0.33.21"
"@polkadot/util": "^0.33.22"
}
}
+3 -3
View File
@@ -30,10 +30,10 @@
"homepage": "https://github.com/polkadot-js/api/tree/master/packages/rpc-provider#readme",
"dependencies": {
"@babel/runtime": "^7.2.0",
"@polkadot/keyring": "^0.33.21",
"@polkadot/keyring": "^0.33.22",
"@polkadot/storage": "^0.34.10",
"@polkadot/util": "^0.33.21",
"@polkadot/util-crypto": "^0.33.21",
"@polkadot/util": "^0.33.22",
"@polkadot/util-crypto": "^0.33.22",
"@types/nock": "^9.3.0",
"eventemitter3": "^3.1.0",
"isomorphic-fetch": "^2.2.1",
+1 -1
View File
@@ -12,6 +12,6 @@
"dependencies": {
"@babel/runtime": "^7.2.0",
"@polkadot/types": "^0.34.10",
"@polkadot/util": "^0.33.21"
"@polkadot/util": "^0.33.22"
}
}
+3 -3
View File
@@ -30,9 +30,9 @@
"homepage": "https://github.com/polkadot-js/api/tree/master/packages/type-storage#readme",
"dependencies": {
"@babel/runtime": "^7.2.0",
"@polkadot/keyring": "^0.33.21",
"@polkadot/keyring": "^0.33.22",
"@polkadot/types": "^0.34.10",
"@polkadot/util": "^0.33.21",
"@polkadot/util-crypto": "^0.33.21"
"@polkadot/util": "^0.33.22",
"@polkadot/util-crypto": "^0.33.22"
}
}
+2 -2
View File
@@ -30,8 +30,8 @@
"homepage": "https://github.com/polkadot-js/api/tree/master/packages/types#readme",
"dependencies": {
"@babel/runtime": "^7.2.0",
"@polkadot/keyring": "^0.33.21",
"@polkadot/util": "^0.33.21",
"@polkadot/keyring": "^0.33.22",
"@polkadot/util": "^0.33.22",
"core-js": "^2.6.1"
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I128
* @description
* An 128-bit signed integer
*/
export default class I128 extends Int {
constructor (value?: AnyNumber) {
super(value, 128, false);
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I16
* @description
* An 16-bit signed integer
*/
export default class I16 extends Int {
constructor (value?: AnyNumber) {
super(value, 16, false);
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I256
* @description
* An 256-bit signed integer
*/
export default class I256 extends Int {
constructor (value?: AnyNumber) {
super(value, 256, false);
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I32
* @description
* An 32-bit signed integer
*/
export default class I32 extends Int {
constructor (value?: AnyNumber) {
super(value, 32, false);
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I64
* @description
* An 64-bit signed integer
*/
export default class I64 extends Int {
constructor (value?: AnyNumber) {
super(value, 64, false);
}
}
+18
View File
@@ -0,0 +1,18 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from './types';
import Int from './codec/Int';
/**
* @name I8
* @description
* An 8-bit signed integer
*/
export default class I8 extends Int {
constructor (value?: AnyNumber) {
super(value, 8, false);
}
}
+13
View File
@@ -0,0 +1,13 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import I8 from './I8';
/**
* @name LocKPeriods
* @description
* A number of lock periods.
*/
export default class LocKPeriods extends I8 {
}
@@ -1290,7 +1290,7 @@
{
"name": "ForcingNewEra",
"modifier": 0,
"type": "()",
"type": "Null",
"documentation": [
" We are forcing a new era."
]
@@ -1344,13 +1344,13 @@
"type": "Compact<ReferendumIndex>"
},
{
"name": "approve_proposal",
"type": "bool"
"name": "vote",
"type": "Vote"
}
],
"documentation": [
" Vote in a referendum. If `approve_proposal` is true, the vote is to enact the proposal;",
" false would be a vote to keep the status quo."
" Vote in a referendum. If `vote.is_aye()`, the vote is to enact the proposal;",
" otherwise it is a vote to keep the status quo."
]
},
{
@@ -1461,6 +1461,14 @@
" The delay before enactment for all public referenda."
]
},
{
"name": "MaxLockPeriods",
"modifier": 1,
"type": "LockPeriods",
"documentation": [
" The maximum number of additional lock periods a voter may offer to strengthen their vote. Multiples of `PublicDelay`."
]
},
{
"name": "VotingPeriod",
"modifier": 1,
@@ -1531,13 +1539,15 @@
},
{
"name": "VoteOf",
"modifier": 0,
"modifier": 1,
"type": {
"key": "(ReferendumIndex,AccountId)",
"value": "bool"
"value": "Vote"
},
"documentation": [
" Get the vote, if Some, of `who`."
" Get the vote in a given referendum of a particular voter. The result is meaningful only if `voters_for` includes the",
" voter when called with the referendum (you'll get the default `Vote` value otherwise). If you don't want to check",
" `voters_for`, then you can also check for simple existence with `VoteOf::exists` first."
]
}
]
+1 -1
View File
@@ -5,7 +5,7 @@
import BN from 'bn.js';
import { bnToBn, bnToHex, bnToU8a, isString, isU8a, u8aToBn } from '@polkadot/util';
import { UIntBitLength } from './codec/UInt';
import { UIntBitLength } from './codec/AbstractInt';
import { AnyNumber, Codec } from './types';
const BITLENGTH: UIntBitLength = 64;
+7 -6
View File
@@ -2,7 +2,6 @@
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import Compact from './codec/Compact';
import Text from './Text';
type Mapper = (value: string) => string;
@@ -21,17 +20,17 @@ export default class Type extends Text {
constructor (value: Text | Uint8Array | string = '') {
// First decode it with Text
const textValue = new Text(value).toString();
const textValue = new Text(value);
// Then cleanup the textValue to get the @polkadot/types type, and pass the
// sanitized value to constructor
super(
Type.decodeType(
textValue
textValue.toString()
)
);
this._originalLength = textValue.length;
this._originalLength = textValue.encodedLength;
}
private static decodeType (value: string): string {
@@ -50,6 +49,8 @@ export default class Type extends Text {
Type._removeGenerics(),
// alias String -> Text (compat with jsonrpc methods)
Type._alias('String', 'Text'),
// alias () -> Null
Type._alias('\\\(\\\)', 'Null'),
// alias Vec<u8> -> Bytes
Type._alias('Vec<u8>', 'Bytes'),
// alias RawAddress -> Address
@@ -70,7 +71,7 @@ export default class Type extends Text {
// NOTE Length is used in the decoding calculations, so return the original (pre-cleanup)
// length of the data. Since toU8a is disabled, this does not affect encoding, but rather
// only the decoding leg, allowing the decoders to work with original pointers
return this._originalLength + Compact.encodeU8a(this._originalLength).length;
return this._originalLength;
}
/**
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U128
* @description
* An 128-bit number
* An 128-bit unsigned integer
*/
export default class U128 extends UInt {
constructor (value?: AnyNumber) {
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U16
* @description
* An 16-bit number
* An 16-bit unsigned integer
*/
export default class U16 extends UInt {
constructor (value?: AnyNumber) {
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U256
* @description
* An 256-bit number
* An 256-bit unsigned integer
*/
export default class U256 extends UInt {
constructor (value?: AnyNumber) {
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U32
* @description
* An 32-bit number
* An 32-bit unsigned integer
*/
export default class U32 extends UInt {
constructor (value?: AnyNumber) {
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U64
* @description
* An 64-bit number
* An 64-bit unsigned integer
*/
export default class U64 extends UInt {
constructor (value?: AnyNumber) {
+1 -1
View File
@@ -9,7 +9,7 @@ import UInt from './codec/UInt';
/**
* @name U8
* @description
* An 8-bit number
* An 8-bit unsigned integer
*/
export default class U8 extends UInt {
constructor (value?: AnyNumber) {
+13
View File
@@ -0,0 +1,13 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import I8 from './I8';
/**
* @name Vote
* @description
* A number of lock periods, plus a vote, one way or the other.
*/
export default class Vote extends I8 {
}
+102
View File
@@ -0,0 +1,102 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber, Codec } from '../types';
import BN from 'bn.js';
import { bnToBn, hexToBn, isHex, isString, isU8a, u8aToBn } from '@polkadot/util';
export type UIntBitLength = 8 | 16 | 32 | 64 | 128 | 256;
export const DEFAULT_UINT_BITS = 64;
/**
* @name AbstractInt
* @ignore
* @noInheritDoc
*/
// TODO:
// - Apart from encoding/decoding we don't actually keep check on the sizes, is this good enough?
export default abstract class AbstractInt extends BN implements Codec {
protected _bitLength: UIntBitLength;
private _isHexJson: boolean;
constructor (
isNegative: boolean,
value: AnyNumber = 0,
bitLength: UIntBitLength = DEFAULT_UINT_BITS, isHexJson: boolean = true) {
super(
AbstractInt.decodeAbstracInt(value, bitLength, isNegative)
);
this._bitLength = bitLength;
this._isHexJson = isHexJson;
}
static decodeAbstracInt (value: AnyNumber, bitLength: UIntBitLength, isNegative: boolean): string {
// This function returns a string, which will be passed in the BN
// constructor. It would be ideal to actually return a BN, but there's a
// bug: https://github.com/indutny/bn.js/issues/206.
if (isHex(value)) {
return hexToBn(value, { isLe: true, isNegative }).toString();
} else if (isU8a(value)) {
// NOTE When passing u8a in (typically from decoded data), it is always LE
return u8aToBn(value.subarray(0, bitLength / 8), { isLe: true, isNegative }).toString();
} else if (isString(value)) {
return new BN(value, 10).toString();
}
return bnToBn(value).toString();
}
/**
* @description The length of the value when encoded as a Uint8Array
*/
get encodedLength (): number {
return this._bitLength / 8;
}
/**
* @description Returns the number of bits in the value
*/
bitLength (): UIntBitLength {
return this._bitLength;
}
/**
* @description Returns the BN representation of the number. (Compatibility)
*/
toBn (): BN {
return this;
}
/**
* @description Returns a hex string representation of the value
*/
abstract toHex (): string;
/**
* @description Converts the Object to JSON, typically used for RPC transfers
*/
toJSON (): any {
return this._isHexJson
? this.toHex()
: this.toNumber();
}
/**
* @description Returns the string representation of the value
* @param base The base to use for the conversion
*/
toString (base?: number): string {
// only included here since we do not inherit docs
return super.toString(base);
}
/**
* @description Encodes the value as a Uint8Array as per the parity-codec specifications
* @param isBare true when the value has none of the type-specific prefixes (internal)
*/
abstract toU8a (isBare?: boolean): Uint8Array;
}
+2 -1
View File
@@ -7,8 +7,9 @@ import { bnToBn, compactAddLength, compactFromU8a, compactStripLength, compactTo
import { DEFAULT_BITLENGTH } from '@polkadot/util/compact/defaults';
import { AnyNumber, Codec, Constructor } from '../types';
import { UIntBitLength } from './AbstractInt';
import Base from './Base';
import UInt, { UIntBitLength } from './UInt';
import UInt from './UInt';
import Moment from '../Moment';
/**
+51
View File
@@ -0,0 +1,51 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import Int from './Int';
describe('Int', () => {
it('provides a toBn interface', () => {
expect(
new Int(-1234).toBn().toNumber()
).toEqual(-1234);
});
it('provides a toNumber interface', () => {
expect(
new Int(-1234).toNumber()
).toEqual(-1234);
});
it('converts to LE from the provided value', () => {
expect(
new Int(-1234).toU8a()
).toEqual(new Uint8Array([46, 251, 255, 255, 255, 255, 255, 255]));
});
it('converts to LE from the provided value (bitLength)', () => {
expect(
new Int(-1234, 32).toU8a()
).toEqual(new Uint8Array([46, 251, 255, 255]));
});
it('converts to hex/string', () => {
const i = new Int('0x12', 16);
expect(i.toHex()).toEqual('0x0012');
expect(i.toString()).toEqual('18');
});
it('converts to equivalents', () => {
const a = new Int('-123');
expect(
new Int(a).toNumber()
).toEqual(-123);
});
it('converts to JSON depending on flags', () => {
expect(new Int(0x12, 16).toJSON()).toEqual('0x0012');
expect(new Int(0x12, 16, false).toJSON()).toEqual(0x12);
});
});
+55
View File
@@ -0,0 +1,55 @@
// Copyright 2017-2018 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber } from '../types';
import { bnToHex, bnToU8a } from '@polkadot/util';
import AbstractInt, { DEFAULT_UINT_BITS, UIntBitLength } from './AbstractInt';
/**
* @name Int
* @description
* A generic signed integer codec. For Substrate all numbers are LE encoded,
* this handles the encoding and decoding of those numbers. Upon construction
* the bitLength is provided and any additional use keeps the number to this
* length. This extends `BN`, so all methods available on a normal `BN` object
* is available here.
* @noInheritDoc
*/
export default class Int extends AbstractInt {
constructor (
value: AnyNumber = 0,
bitLength: UIntBitLength = DEFAULT_UINT_BITS, isHexJson: boolean = true) {
super(
true,
value,
bitLength,
isHexJson
);
}
/**
* @description Returns a hex string representation of the value
*/
toHex (): string {
return bnToHex(this, {
bitLength: this._bitLength,
isLe: false,
isNegative: true
});
}
/**
* @description Encodes the value as a Uint8Array as per the parity-codec specifications
* @param isBare true when the value has none of the type-specific prefixes (internal)
*/
toU8a (isBare?: boolean): Uint8Array {
return bnToU8a(this, {
bitLength: this._bitLength,
isLe: true,
isNegative: true
});
}
}
+26 -78
View File
@@ -2,99 +2,43 @@
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
import { AnyNumber, Codec } from '../types';
import { AnyNumber } from '../types';
import BN from 'bn.js';
import { bnToBn, bnToHex, bnToU8a, hexToBn, isHex, isString, isU8a, u8aToBn } from '@polkadot/util';
import { bnToHex, bnToU8a } from '@polkadot/util';
export type UIntBitLength = 8 | 16 | 32 | 64 | 128 | 256;
export const DEFAULT_UINT_BITS = 64;
import AbstractInt, { DEFAULT_UINT_BITS, UIntBitLength } from './AbstractInt';
/**
* @name UInt
* @description
* A generic number codec. For Substrate all numbers are LE encoded, this handles the encoding
* and decoding of those numbers. Upon construction the bitLength is provided and any additional
* use keeps the number to this length. This extends `BN`, so all methods available on a normal
* `BN` object is available here.
* A generic unsigned integer codec. For Substrate all numbers are LE encoded,
* this handles the encoding and decoding of those numbers. Upon construction
* the bitLength is provided and any additional use keeps the number to this
* length. This extends `BN`, so all methods available on a normal `BN` object
* is available here.
* @noInheritDoc
*/
// TODO:
// - Apart from encoding/decoding we don't actually keep check on the sizes, is this good enough?
export default class UInt extends BN implements Codec {
protected _bitLength: UIntBitLength;
private _isHexJson: boolean;
constructor (value: AnyNumber = 0, bitLength: UIntBitLength = DEFAULT_UINT_BITS, isHexJson: boolean = true) {
export default class UInt extends AbstractInt {
constructor (
value: AnyNumber = 0,
bitLength: UIntBitLength = DEFAULT_UINT_BITS, isHexJson: boolean = true) {
super(
UInt.decodeUInt(value, bitLength)
false,
value,
bitLength,
isHexJson
);
this._bitLength = bitLength;
this._isHexJson = isHexJson;
}
static decodeUInt (value: AnyNumber, bitLength: UIntBitLength): string {
// This function returns a string, which will be passed in the BN
// constructor. It would be ideal to actually return a BN, but there's a
// bug: https://github.com/indutny/bn.js/issues/206.
if (isHex(value)) {
return hexToBn(value).toString();
} else if (isU8a(value)) {
// NOTE When passing u8a in (typically from decoded data), it is always LE
return u8aToBn(value.subarray(0, bitLength / 8), true).toString();
} else if (isString(value)) {
return new BN(value, 10).toString();
}
return bnToBn(value).toString();
}
/**
* @description The length of the value when encoded as a Uint8Array
*/
get encodedLength (): number {
return this._bitLength / 8;
}
/**
* @description Returns the number of bits in the value
*/
bitLength (): UIntBitLength {
return this._bitLength;
}
/**
* @description Returns the BN representation of the number. (Compatibility)
*/
toBn (): BN {
return this;
}
/**
* @description Returns a hex string representation of the value
*/
toHex (): string {
return bnToHex(this, this._bitLength);
}
/**
* @description Converts the Object to JSON, typically used for RPC transfers
*/
toJSON (): any {
return this._isHexJson
? this.toHex()
: this.toNumber();
}
/**
* @description Returns the string representation of the value
* @param base The base to use for the conversion
*/
toString (base?: number): string {
// only included here since we do not inherit docs
return super.toString(base);
return bnToHex(this, {
bitLength: this._bitLength,
isLe: false,
isNegative: false
});
}
/**
@@ -102,6 +46,10 @@ export default class UInt extends BN implements Codec {
* @param isBare true when the value has none of the type-specific prefixes (internal)
*/
toU8a (isBare?: boolean): Uint8Array {
return bnToU8a(this, this._bitLength, true);
return bnToU8a(this, {
bitLength: this._bitLength,
isLe: true,
isNegative: false
});
}
}
+8
View File
@@ -43,8 +43,15 @@ export { default as Gas } from './Gas';
// export { default as H512 } from './H512';
export { default as Hash } from './Hash';
export { default as Header } from './Header';
export { default as i8 } from './I8';
export { default as i16 } from './I16';
export { default as i32 } from './I32';
export { default as i64 } from './I64';
export { default as i128 } from './I128';
export { default as i256 } from './I256';
export { default as InherentOfflineReport } from './InherentOfflineReport';
export { default as KeyValue } from './KeyValue';
export { default as LockPeriods } from './LockPeriods';
export { default as Metadata } from './Metadata';
export { default as Method } from './Method';
export { default as MisbehaviorReport } from './MisbehaviorReport';
@@ -82,5 +89,6 @@ export { default as u64 } from './U64';
export { default as u128 } from './U128';
export { default as u256 } from './U256';
export { default as ValidatorPrefs } from './ValidatorPrefs';
export { default as Vote } from './Vote';
export { default as VoteThreshold } from './VoteThreshold';
export { default as VoteIndex } from './VoteIndex';
File diff suppressed because one or more lines are too long