Add isError & ExtError (#16)
* Add isError & ExtError * Check fixes * Check fixes
This commit is contained in:
@@ -4,6 +4,7 @@ Utility methods for this package are split into groups
|
||||
|
||||
- [bn](bn.md) Utility methods to convert to and from `BN` objects
|
||||
- [buffer](buffer.md) Utility methods to convert to and from `Buffer` objects
|
||||
- [ext](ext.md) Extensions to basic classes
|
||||
- [hex](hex.md) Internal utilities to create and test for hex values
|
||||
- [is](is.md) Type checking utilities
|
||||
- [jsonrpc](jsonrpc.md) Convenience functions for values from @polkadot/jsonrpc
|
||||
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
# ext
|
||||
|
||||
Extensions to basic classes
|
||||
|
||||
- [ExtError](#exterror) Extension to the basic JS Error.
|
||||
|
||||
## ExtError
|
||||
|
||||
Extension to the basic JS Error.
|
||||
|
||||
```js
|
||||
ExtError (message: string = '', code: number = UNKNOWN_ERROR, value: any)
|
||||
```
|
||||
|
||||
|
||||
The built-in JavaScript Error class is extended by adding a code to allow for Error categorization. In addition to the normal `stack`, `message`, the numeric `code` and `data` (any types) parameters are available on the object.
|
||||
|
||||
```js
|
||||
const { ExtError } = require('@polkadot/util');
|
||||
|
||||
throw new ExtError('some message', ExtError.CODES.METHOD_NOT_FOUND); // => error.code = -32601
|
||||
```
|
||||
+18
@@ -4,6 +4,7 @@ Type checking utilities
|
||||
|
||||
- [isBN](#isbn) Tests for a `BN` object instance.
|
||||
- [isBuffer](#isbuffer) Tests for a `Buffer` object instance.
|
||||
- [isError](#iserror) Tests for a `Error` object instance.
|
||||
- [isFunction](#isfunction) Tests for a `function`.
|
||||
- [isHex](#ishex) Tests for a hex string.
|
||||
- [isInstanceOf](#isinstanceof) Tests for a instance of a class.
|
||||
@@ -46,6 +47,23 @@ import { isBuffer } from '@polkadot/util';
|
||||
console.log('isBuffer', isBuffer(Buffer.from([]))); // => true
|
||||
```
|
||||
|
||||
## isError
|
||||
|
||||
Tests for a `Error` object instance.
|
||||
|
||||
```js
|
||||
isError (value: any): boolean
|
||||
```
|
||||
|
||||
|
||||
Checks to see if the input object is an instance of `Error`.
|
||||
|
||||
```js
|
||||
import { isError } from '@polkadot/util';
|
||||
|
||||
console.log('isError', isError(new Error('message'))); // => true
|
||||
```
|
||||
|
||||
## isFunction
|
||||
|
||||
Tests for a `function`.
|
||||
|
||||
@@ -0,0 +1,56 @@
|
||||
// ISC, Copyright 2017 Jaco Greeff
|
||||
// @flow
|
||||
|
||||
import type { ExtErrorInterface } from '../types';
|
||||
|
||||
const isFunction = require('../is/function');
|
||||
|
||||
const UNKNOWN = -99999;
|
||||
|
||||
/**
|
||||
@name ExtError
|
||||
@signature ExtError (message: string = '', code: number = UNKNOWN_ERROR, value: any)
|
||||
@summary Extension to the basic JS Error.
|
||||
@description
|
||||
The built-in JavaScript Error class is extended by adding a code to allow for Error categorization. In addition to the normal `stack`, `message`, the numeric `code` and `data` (any types) parameters are available on the object.
|
||||
@example
|
||||
const { ExtError } = require('@polkadot/util');
|
||||
|
||||
throw new ExtError('some message', ExtError.CODES.METHOD_NOT_FOUND); // => error.code = -32601
|
||||
*/
|
||||
module.exports = class ExtError extends Error implements ExtErrorInterface {
|
||||
code: number;
|
||||
data: any;
|
||||
message: string;
|
||||
name: string;
|
||||
stack: string;
|
||||
|
||||
constructor (message: string = '', code: number = UNKNOWN, data: any) {
|
||||
super();
|
||||
|
||||
const extend = (name: string, value: any): void => {
|
||||
Object.defineProperty(this, name, {
|
||||
configurable: true,
|
||||
enumerable: false,
|
||||
value
|
||||
});
|
||||
};
|
||||
|
||||
extend('message', String(message));
|
||||
extend('name', this.constructor.name);
|
||||
extend('data', data);
|
||||
extend('code', code);
|
||||
|
||||
if (isFunction(Error.captureStackTrace)) {
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
} else {
|
||||
extend('stack', (new Error(message)).stack);
|
||||
}
|
||||
}
|
||||
|
||||
static CODES = {
|
||||
UNKNOWN,
|
||||
INVALID_JSONRPC: -99998,
|
||||
METHOD_NOT_FOUND: -32601 // Rust client
|
||||
};
|
||||
};
|
||||
@@ -0,0 +1,97 @@
|
||||
// ISC, Copyright 2017 Jaco Greeff
|
||||
|
||||
const ExtError = require('./error');
|
||||
const isError = require('../is/error');
|
||||
|
||||
describe('Error', () => {
|
||||
describe('constructor', () => {
|
||||
it('constructs an Error that is still an Error', () => {
|
||||
expect(
|
||||
isError(
|
||||
new ExtError()
|
||||
)
|
||||
).toEqual(true);
|
||||
});
|
||||
});
|
||||
|
||||
describe('static', () => {
|
||||
it('exposes the .CODES as a static', () => {
|
||||
expect(
|
||||
Object.keys(ExtError.CODES)
|
||||
).not.toEqual(0);
|
||||
});
|
||||
});
|
||||
|
||||
describe('constructor properties', () => {
|
||||
it('sets the .message property', () => {
|
||||
expect(
|
||||
new ExtError('test message').message
|
||||
).toEqual('test message');
|
||||
});
|
||||
|
||||
it("sets the .message to '' when not set", () => {
|
||||
expect(
|
||||
new ExtError().message
|
||||
).toEqual('');
|
||||
});
|
||||
|
||||
it('sets the .code property', () => {
|
||||
expect(
|
||||
new ExtError('test message', 1234).code
|
||||
).toEqual(1234);
|
||||
});
|
||||
|
||||
it('sets the .code to UKNOWN when not set', () => {
|
||||
expect(
|
||||
new ExtError('test message').code
|
||||
).toEqual(ExtError.CODES.UNKNOWN);
|
||||
});
|
||||
|
||||
it('sets the .data property', () => {
|
||||
const data = { some: { value: 'here' } };
|
||||
|
||||
expect(
|
||||
new ExtError('test message', 1234, data).data
|
||||
).toEqual(data);
|
||||
});
|
||||
});
|
||||
|
||||
describe('stack traces', () => {
|
||||
let captureStackTrace;
|
||||
|
||||
beforeEach(() => {
|
||||
captureStackTrace = Error.captureStackTrace;
|
||||
|
||||
Error.captureStackTrace = function (error) {
|
||||
Object.defineProperty(error, 'stack', {
|
||||
configurable: true,
|
||||
get: function getStack () {
|
||||
const value = 'some stack returned';
|
||||
|
||||
Object.defineProperty(this, 'stack', { value });
|
||||
|
||||
return value;
|
||||
}
|
||||
});
|
||||
};
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
Error.captureStackTrace = captureStackTrace;
|
||||
});
|
||||
|
||||
it('captures via captureStackTrace when available', () => {
|
||||
expect(
|
||||
new ExtError().stack
|
||||
).toEqual('some stack returned');
|
||||
});
|
||||
|
||||
it('captures via stack when captureStackTrace not available', () => {
|
||||
Error.captureStackTrace = null;
|
||||
|
||||
expect(
|
||||
new ExtError().stack.length
|
||||
).not.toEqual(0);
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,11 @@
|
||||
// ISC, Copyright 2017 Jaco Greeff
|
||||
// @flow
|
||||
|
||||
const ExtError = require('./error');
|
||||
|
||||
/**
|
||||
@summary Extensions to basic classes
|
||||
*/
|
||||
module.exports = {
|
||||
ExtError
|
||||
};
|
||||
+2
-1
@@ -3,6 +3,7 @@
|
||||
|
||||
const bn = require('./bn');
|
||||
const buffer = require('./buffer');
|
||||
const ext = require('./ext');
|
||||
const hex = require('./hex');
|
||||
const is = require('./is');
|
||||
const jsonrpc = require('./jsonrpc');
|
||||
@@ -13,5 +14,5 @@ const logger = require('./logger');
|
||||
@summary Utility methods for this package are split into groups
|
||||
*/
|
||||
module.exports = Object.assign(
|
||||
{}, bn, buffer, hex, is, jsonrpc, keccak, logger
|
||||
{}, bn, buffer, ext, hex, is, jsonrpc, keccak, logger
|
||||
);
|
||||
|
||||
@@ -0,0 +1,19 @@
|
||||
// ISC, Copyright 2017 Jaco Greeff
|
||||
// @flow
|
||||
|
||||
const isInstanceOf = require('./instanceOf');
|
||||
|
||||
/**
|
||||
@name isError
|
||||
@signature isError (value: any): boolean
|
||||
@summary Tests for a `Error` object instance.
|
||||
@description
|
||||
Checks to see if the input object is an instance of `Error`.
|
||||
@example
|
||||
import { isError } from '@polkadot/util';
|
||||
|
||||
console.log('isError', isError(new Error('message'))); // => true
|
||||
*/
|
||||
module.exports = function isError (value: any): boolean {
|
||||
return isInstanceOf(value, Error);
|
||||
};
|
||||
@@ -2,6 +2,8 @@
|
||||
// @flow
|
||||
|
||||
const isBN = require('./bn');
|
||||
const isBuffer = require('./buffer');
|
||||
const isError = require('./error');
|
||||
const isFunction = require('./function');
|
||||
const isHex = require('./hex');
|
||||
const isInstanceOf = require('./instanceOf');
|
||||
@@ -14,6 +16,8 @@ const isUndefined = require('./undefined');
|
||||
*/
|
||||
module.exports = {
|
||||
isBN,
|
||||
isBuffer,
|
||||
isError,
|
||||
isFunction,
|
||||
isHex,
|
||||
isInstanceOf,
|
||||
|
||||
+29
-1
@@ -4,7 +4,7 @@
|
||||
|
||||
const BN = require('bn.js');
|
||||
|
||||
const { isBN, isFunction, isHex, isInstanceOf, isNumber, isString, isUndefined } = require('./index');
|
||||
const { isBN, isBuffer, isError, isFunction, isHex, isInstanceOf, isNumber, isString, isUndefined } = require('./index');
|
||||
|
||||
describe('is', () => {
|
||||
describe('isBN', () => {
|
||||
@@ -21,6 +21,34 @@ describe('is', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('isBuffer', () => {
|
||||
it('returns true when a Buffer value', () => {
|
||||
expect(
|
||||
isBuffer(Buffer.from([]))
|
||||
).toEqual(true);
|
||||
});
|
||||
|
||||
it('returns false on non-Buffer values', () => {
|
||||
expect(
|
||||
isBuffer(0)
|
||||
).toEqual(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe('isError', () => {
|
||||
it('returns true when an Error value', () => {
|
||||
expect(
|
||||
isError(new Error('testing'))
|
||||
).toEqual(true);
|
||||
});
|
||||
|
||||
it('returns false on non-Error values', () => {
|
||||
expect(
|
||||
isError(0)
|
||||
).toEqual(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe('isFunction', () => {
|
||||
it('returns true on valid functions', () => {
|
||||
expect(
|
||||
|
||||
@@ -10,11 +10,23 @@ describe('jsonrpc', () => {
|
||||
'test_method',
|
||||
[
|
||||
{ name: 'b', type: 'A' },
|
||||
{ name: 'a', type: 'B' }
|
||||
{ name: 'a', type: 'B' },
|
||||
{ type: 'C' },
|
||||
{ type: 'D' }
|
||||
],
|
||||
{ type: 'A' }
|
||||
)
|
||||
).toEqual('test_method (b: A, a: B): A');
|
||||
).toEqual('test_method (b: A, a: B, C, D): A');
|
||||
});
|
||||
|
||||
it('empty inputs format correctly', () => {
|
||||
expect(
|
||||
jsonrpcSignature(
|
||||
'test_method',
|
||||
[],
|
||||
{ type: 'A' }
|
||||
)
|
||||
).toEqual('test_method (): A');
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -3,6 +3,12 @@
|
||||
|
||||
import type { InterfaceInputType, InterfaceOutputType } from '@polkadot/jsonrpc/types';
|
||||
|
||||
function formatParam (param: InterfaceInputType | InterfaceOutputType): string {
|
||||
return param.name
|
||||
? `${((param.name: any): string)}: ${param.type}`
|
||||
: param.type;
|
||||
}
|
||||
|
||||
/**
|
||||
@name jsonrpcSignature
|
||||
@signature jsonrpcSignature (name: string, _inputs: Array<InterfaceInputType>, _output: InterfaceOutputType): string
|
||||
@@ -17,9 +23,8 @@ import type { InterfaceInputType, InterfaceOutputType } from '@polkadot/jsonrpc/
|
||||
)); // => test_method (destination: Address): Address
|
||||
*/
|
||||
module.exports = function jsonrpcSignature (name: string, _inputs: Array<InterfaceInputType>, _output: InterfaceOutputType): string {
|
||||
const inputParams: string = _inputs
|
||||
.map(({ name, type }) => `${name}: ${type}`)
|
||||
.join(', ');
|
||||
const inputs: string = _inputs.map(formatParam).join(', ');
|
||||
const output: string = formatParam(_output);
|
||||
|
||||
return `${name} (${inputParams}): ${_output.type}`;
|
||||
return `${name} (${inputs}): ${output}`;
|
||||
};
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
// ISC, Copyright 2017 Jaco Greeff
|
||||
// @flow
|
||||
|
||||
export interface ExtErrorInterface {
|
||||
code: number;
|
||||
data: any;
|
||||
message: string;
|
||||
stack: string;
|
||||
}
|
||||
Reference in New Issue
Block a user