mirror of
https://github.com/Xahau/xahau.js.git
synced 2025-11-09 23:35:48 +00:00
Compare commits
192 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
de47263087 | ||
|
|
3b9679a673 | ||
|
|
f175966816 | ||
|
|
f1f5364d07 | ||
|
|
1b8b0c76ac | ||
|
|
1a8096ab18 | ||
|
|
f177771c67 | ||
|
|
081fcbfa32 | ||
|
|
0a5e4e2155 | ||
|
|
19eb88a00e | ||
|
|
c8f2967de0 | ||
|
|
b5564330f6 | ||
|
|
43ccb83f73 | ||
|
|
e2d92126c0 | ||
|
|
8c8eef45d5 | ||
|
|
a574e1158a | ||
|
|
af687a6aed | ||
|
|
016e82ab5d | ||
|
|
f300a412d7 | ||
|
|
75e2249cf3 | ||
|
|
1942bcb971 | ||
|
|
9393adf66f | ||
|
|
917aae9bf3 | ||
|
|
da36457d5c | ||
|
|
15a0ededc8 | ||
|
|
68d7864f93 | ||
|
|
1eddbf995f | ||
|
|
592385ac73 | ||
|
|
56d626f5b1 | ||
|
|
7a14300409 | ||
|
|
30fa8d658e | ||
|
|
c0101cb5e7 | ||
|
|
fd640cd65e | ||
|
|
11528eff92 | ||
|
|
3c9175459d | ||
|
|
bd4e0e01e2 | ||
|
|
cfcf6e473c | ||
|
|
50c6af3158 | ||
|
|
1d4310cd3a | ||
|
|
2191596e68 | ||
|
|
acf8f87a88 | ||
|
|
cfac146620 | ||
|
|
f3234ad853 | ||
|
|
b65fee3d85 | ||
|
|
82b294bc7d | ||
|
|
2a58573823 | ||
|
|
a96f71b7fd | ||
|
|
077f4a4c79 | ||
|
|
9a495467fb | ||
|
|
db2e62b219 | ||
|
|
2fafa493a2 | ||
|
|
7617c3005c | ||
|
|
5cdbb71277 | ||
|
|
f9339c36bf | ||
|
|
67dc57e9d0 | ||
|
|
757f3190d1 | ||
|
|
0d94a15ee7 | ||
|
|
7f1c80da1b | ||
|
|
f74e11bce0 | ||
|
|
d4c843e8e3 | ||
|
|
bae190b282 | ||
|
|
d2cbd70da8 | ||
|
|
5da78ce583 | ||
|
|
14bbe3e30b | ||
|
|
e52e2bbc68 | ||
|
|
b56752e45b | ||
|
|
4632f511ab | ||
|
|
e17b6f172d | ||
|
|
eb04e878ba | ||
|
|
c71febd116 | ||
|
|
69c1ccbb6b | ||
|
|
499b8c8d8b | ||
|
|
ea009f9a84 | ||
|
|
dc784d4567 | ||
|
|
9ffc8a2c0b | ||
|
|
5b20fe573e | ||
|
|
7e466bb80f | ||
|
|
1f8418b447 | ||
|
|
ccfc57fc62 | ||
|
|
1d31fccd72 | ||
|
|
9ac1a89e48 | ||
|
|
bfc0696324 | ||
|
|
e33e782f9e | ||
|
|
f2b591d1b2 | ||
|
|
fe9af5153d | ||
|
|
0dfdd0a601 | ||
|
|
4acc42e1b6 | ||
|
|
7c9a179865 | ||
|
|
c6296a4918 | ||
|
|
cc399f1164 | ||
|
|
e4ffb96646 | ||
|
|
8d34428dac | ||
|
|
353637a0c0 | ||
|
|
00713d8ec1 | ||
|
|
d949881e9f | ||
|
|
5075441a69 | ||
|
|
94a852cb8b | ||
|
|
06f847c2d0 | ||
|
|
0c2f9d0e62 | ||
|
|
11ed6b124f | ||
|
|
8767fc0068 | ||
|
|
66b07623b0 | ||
|
|
4f3635eef0 | ||
|
|
f638833759 | ||
|
|
ab9d1936d9 | ||
|
|
0fefb2bd2c | ||
|
|
6740eee495 | ||
|
|
aa6020e00d | ||
|
|
7bfe4a6cd8 | ||
|
|
aa467681e4 | ||
|
|
6b8cd6151d | ||
|
|
0d6aaee12a | ||
|
|
dc03c6e0ac | ||
|
|
0f4d957d14 | ||
|
|
71a13224a1 | ||
|
|
8097ed60ba | ||
|
|
408bb74214 | ||
|
|
9433b43873 | ||
|
|
896bf48c79 | ||
|
|
3dd21a7e11 | ||
|
|
ed79a04018 | ||
|
|
ebfe20defb | ||
|
|
28b148348d | ||
|
|
fe099f2c8b | ||
|
|
107c8c9f0f | ||
|
|
39e818b3e5 | ||
|
|
588ffa3d5c | ||
|
|
691e4dd114 | ||
|
|
55bc42725f | ||
|
|
cce55b9361 | ||
|
|
c23c6e4fc9 | ||
|
|
afdd60efe8 | ||
|
|
8f6ea573ff | ||
|
|
3271b544ef | ||
|
|
6e83130754 | ||
|
|
f6ebe32519 | ||
|
|
3caed3c761 | ||
|
|
ce1c55427a | ||
|
|
9cd72595f0 | ||
|
|
ad1d3e135f | ||
|
|
76866ab901 | ||
|
|
20b647dfbf | ||
|
|
99d08065e4 | ||
|
|
261fba3d21 | ||
|
|
e1d9de7b1f | ||
|
|
391b2f3622 | ||
|
|
86ff315ef2 | ||
|
|
8d8a850864 | ||
|
|
7bf2da6014 | ||
|
|
7eae3ce709 | ||
|
|
5f5e48e414 | ||
|
|
4f6a37f7b1 | ||
|
|
82613e7e8b | ||
|
|
588aa382a1 | ||
|
|
809d981987 | ||
|
|
cfc21fde8c | ||
|
|
5c06ef547b | ||
|
|
0990ad4a6f | ||
|
|
d8f967d2b8 | ||
|
|
fe1c3e7130 | ||
|
|
062148674c | ||
|
|
11320693fd | ||
|
|
7af7eaccb4 | ||
|
|
5d5cf868a2 | ||
|
|
ddf8fe5b1a | ||
|
|
dc24f6afe0 | ||
|
|
f7dac6ab25 | ||
|
|
4b4fc36ebd | ||
|
|
7626ea5ed8 | ||
|
|
7061e9afe4 | ||
|
|
a124635c2c | ||
|
|
c9704137b7 | ||
|
|
ab8d75d3cc | ||
|
|
5e720891f5 | ||
|
|
27ed1aadd5 | ||
|
|
001f203983 | ||
|
|
515047d2dc | ||
|
|
995606b1e6 | ||
|
|
b5081344da | ||
|
|
4f86691fb8 | ||
|
|
45aca016d4 | ||
|
|
7f33d8a71e | ||
|
|
af620755c5 | ||
|
|
a76b554cad | ||
|
|
ef1e9e1b70 | ||
|
|
fdbac63f46 | ||
|
|
377f1dbfa1 | ||
|
|
14b840f3fe | ||
|
|
beb1cc0cde | ||
|
|
ef2515507d | ||
|
|
a271b9e816 | ||
|
|
8a3d4a64db |
4
.babelrc
Normal file
4
.babelrc
Normal file
@@ -0,0 +1,4 @@
|
||||
{
|
||||
"presets": ["es2015", "stage-1"],
|
||||
"plugins": ["syntax-flow", "transform-flow-strip-types"]
|
||||
}
|
||||
@@ -4,6 +4,11 @@
|
||||
.*/ripple-lib/test/fixtures/.*
|
||||
.*/node_modules/flow-bin/.*
|
||||
.*/node_modules/webpack/.*
|
||||
.*/node_modules/babel-core/.*
|
||||
.*/node_modules/babel-eslint/.*
|
||||
.*/node_modules/babel-preset-es2015/.*
|
||||
.*/node_modules/babel-preset-stage-1/.*
|
||||
.*/node_modules/babel-register/.*
|
||||
|
||||
[include]
|
||||
./node_modules/
|
||||
|
||||
90
Gulpfile.js
90
Gulpfile.js
@@ -8,24 +8,49 @@ var rename = require('gulp-rename');
|
||||
var webpack = require('webpack');
|
||||
var bump = require('gulp-bump');
|
||||
var argv = require('yargs').argv;
|
||||
var assert = require('assert');
|
||||
var fs = require('fs');
|
||||
|
||||
var pkg = require('./package.json');
|
||||
|
||||
var uglifyOptions = {
|
||||
mangle: {
|
||||
except: ['_', 'RippleError', 'RippledError', 'UnexpectedError',
|
||||
'LedgerVersionError', 'ConnectionError', 'NotConnectedError',
|
||||
'DisconnectedError', 'TimeoutError', 'ResponseFormatError',
|
||||
'ValidationError', 'NotFoundError', 'MissingLedgerHistoryError',
|
||||
'PendingLedgerVersionError'
|
||||
]
|
||||
}
|
||||
};
|
||||
|
||||
function webpackConfig(extension, overrides) {
|
||||
overrides = overrides || {};
|
||||
var defaults = {
|
||||
cache: true,
|
||||
externals: [{
|
||||
'lodash': '_'
|
||||
}],
|
||||
entry: './src/index.js',
|
||||
output: {
|
||||
library: 'ripple',
|
||||
path: './build/',
|
||||
filename: ['ripple-', extension].join(pkg.version)
|
||||
},
|
||||
plugins: [
|
||||
new webpack.NormalModuleReplacementPlugin(/^ws$/, './wswrapper'),
|
||||
new webpack.NormalModuleReplacementPlugin(/^\.\/wallet$/, './wallet-web'),
|
||||
new webpack.NormalModuleReplacementPlugin(/^.*setup-api$/,
|
||||
'./setup-api-web')
|
||||
],
|
||||
module: {
|
||||
loaders: [{
|
||||
test: /jayson/,
|
||||
loader: 'null'
|
||||
}, {
|
||||
test: /\.js$/,
|
||||
exclude: /node_modules/,
|
||||
loader: 'babel-loader?optional=runtime'
|
||||
exclude: [/node_modules/],
|
||||
loader: 'babel-loader'
|
||||
}, {
|
||||
test: /\.json/,
|
||||
loader: 'json-loader'
|
||||
@@ -35,15 +60,70 @@ function webpackConfig(extension, overrides) {
|
||||
return _.assign({}, defaults, overrides);
|
||||
}
|
||||
|
||||
function webpackConfigForWebTest(testFileName, path) {
|
||||
var match = testFileName.match(/\/?([^\/]*)-test.js$/);
|
||||
if (!match) {
|
||||
assert(false, 'wrong filename:' + testFileName);
|
||||
}
|
||||
var configOverrides = {
|
||||
externals: [{
|
||||
'lodash': '_',
|
||||
'ripple-api': 'ripple',
|
||||
'net': 'null'
|
||||
}],
|
||||
entry: testFileName,
|
||||
output: {
|
||||
library: match[1].replace(/-/g, '_'),
|
||||
path: './test-compiled-for-web/' + (path ? path : ''),
|
||||
filename: match[1] + '-test.js'
|
||||
}
|
||||
};
|
||||
return webpackConfig('.js', configOverrides);
|
||||
}
|
||||
|
||||
gulp.task('build-tests', function(callback) {
|
||||
var times = 0;
|
||||
function done() {
|
||||
if (++times >= 5) {
|
||||
callback();
|
||||
}
|
||||
}
|
||||
webpack(webpackConfigForWebTest('./test/rangeset-test.js'), done);
|
||||
webpack(webpackConfigForWebTest('./test/connection-test.js'), done);
|
||||
webpack(webpackConfigForWebTest('./test/api-test.js'), done);
|
||||
webpack(webpackConfigForWebTest('./test/broadcast-api-test.js'), done);
|
||||
webpack(webpackConfigForWebTest('./test/integration/integration-test.js',
|
||||
'integration/'), done);
|
||||
});
|
||||
|
||||
function createLink(from, to) {
|
||||
if (fs.existsSync(to)) {
|
||||
fs.unlinkSync(to);
|
||||
}
|
||||
fs.linkSync(from, to);
|
||||
}
|
||||
|
||||
function createBuildLink(callback) {
|
||||
return function(err, res) {
|
||||
createLink('./build/ripple-' + pkg.version + '.js',
|
||||
'./build/ripple-latest.js');
|
||||
callback(err, res);
|
||||
};
|
||||
}
|
||||
|
||||
gulp.task('build', function(callback) {
|
||||
webpack(webpackConfig('.js'), callback);
|
||||
webpack(webpackConfig('.js'), createBuildLink(callback));
|
||||
});
|
||||
|
||||
gulp.task('build-min', ['build'], function() {
|
||||
return gulp.src(['./build/ripple-', '.js'].join(pkg.version))
|
||||
.pipe(uglify())
|
||||
.pipe(uglify(uglifyOptions))
|
||||
.pipe(rename(['ripple-', '-min.js'].join(pkg.version)))
|
||||
.pipe(gulp.dest('./build/'));
|
||||
.pipe(gulp.dest('./build/'))
|
||||
.on('end', function() {
|
||||
createLink('./build/ripple-' + pkg.version + '-min.js',
|
||||
'./build/ripple-latest-min.js');
|
||||
});
|
||||
});
|
||||
|
||||
gulp.task('build-debug', function(callback) {
|
||||
|
||||
64
HISTORY.md
64
HISTORY.md
@@ -1,3 +1,67 @@
|
||||
##0.16.5
|
||||
**Changes**
|
||||
+ [Filter insufficient source funds paths from pathfind results](https://github.com/ripple/ripple-lib/pull/688)
|
||||
|
||||
##0.16.4
|
||||
**Changes**
|
||||
+ [Update ws to 1.0.1](https://github.com/ripple/ripple-lib/pull/682)
|
||||
|
||||
##0.16.2
|
||||
**Changes**
|
||||
+ [Bump ripple-binary-codec dependency version to 0.1.1 to fix issue with computeLedgerHash for transactions with DeliverMin]
|
||||
|
||||
##0.16.1
|
||||
**Changes**
|
||||
+ [FIX: Use assert not assert-diff](https://github.com/ripple/ripple-lib/commit/f6ebe325193e7208c5ee8d8e84a7504714f0009e)
|
||||
|
||||
##0.16.0
|
||||
**Breaking Changes**
|
||||
+ [Fix types of XRP values in getServerInfo response](https://github.com/ripple/ripple-lib/commit/99d08065e4bda3dda6ae1f183adbd11abc70a9b7)
|
||||
+ [Change error event format and fix crash due to error event on webscocket](https://github.com/ripple/ripple-lib/commit/9cd72595f0efc062d77b9d625695d6030c524cc6)
|
||||
|
||||
**Changes**
|
||||
+ [Fix generateAddress docs and add error event listener to boilerplate](https://github.com/ripple/ripple-lib/commit/809d981987a2890fac3a73a40a05c598b9040334)
|
||||
+ [Allow setting maxLedgerVersion to null to specify no maximum](https://github.com/ripple/ripple-lib/commit/82613e7e8b360d1ae1552eab4559ab4763c06d7e)
|
||||
+ [Add support for client certificates](https://github.com/ripple/ripple-lib/commit/5f5e48e4140345d166b8c1a3ee0847b0d9e2d893)
|
||||
+ [getFee returns a string not float](https://github.com/ripple/ripple-lib/commit/7bf2da6014c87e164542e69356efeaabb575a157)
|
||||
+ [Fix parsing of quality for getTrustlines](https://github.com/ripple/ripple-lib/commit/86ff315ef2a39dfdc2ce97e0e1c4aa73f04e363b)
|
||||
+ [Fix DeliverMin value when specifying minAmount](Fix DeliverMin value when specifying minAmount)
|
||||
+ [http server example](https://github.com/ripple/ripple-lib/commit/76866ab901ea46a2dd73181605e0f7f4220043d4)
|
||||
|
||||
|
||||
##0.15.2
|
||||
**Changes**
|
||||
+ [Fix support for proxy credentials in proxy URL and fix error when there are more than 10 outstanding requests](https://github.com/ripple/ripple-lib/commit/0990ad4a6f1d59ca9d2cb859b4e2d71693f3fc4b)
|
||||
|
||||
##0.15.1
|
||||
**Changes**
|
||||
+ [Fix babel-polyfill require](https://github.com/ripple/ripple-lib/commit/062148674c3b1293ab82c28e25615ddd530339fa)
|
||||
+ [Fix samples](https://github.com/ripple/ripple-lib/commit/5d5cf868a2ddb1b1cd40e4a4f0a782d0066c2055)
|
||||
+ [add unit tests for RippleAPIBroadcast](https://github.com/ripple/ripple-lib/commit/ddf8fe5b1a9c750490dca98fb9ffaaf8017f87e0)
|
||||
|
||||
##0.15.0
|
||||
**Breaking Changes**
|
||||
+ ["servers" parameter changed to single "server"](https://github.com/ripple/ripple-lib/commit/7061e9afe46f0682254d098adeff3dd7157521a1)
|
||||
|
||||
**Changes**
|
||||
+ [fix handling memos in prepareSettings](https://github.com/ripple/ripple-lib/commit/c9704137b7b538e8dbf31c483bcdcf2dcfd7cd75)
|
||||
+ [Docs: SusPay warnings, offline mode, and other tweaks](https://github.com/ripple/ripple-lib/commit/4b4fc36ebd93f1360781a65f2869bd2c4f0a5093)
|
||||
+ [Fix prepareOrderCancellation documentation](https://github.com/ripple/ripple-lib/commit/5e720891f579fd73d43c64e5ec519d9121023c10)
|
||||
|
||||
##0.14.0
|
||||
**Breaking Changes**
|
||||
+ [prepareOrderCancellation now takes orderCancellation specification](https://github.com/ripple/ripple-lib/commit/7f33d8a71e56289e5a5e0ead1c74f75ebcde72bc)
|
||||
+ [Rename "ledgerClosed" event to "ledger" and change format](https://github.com/ripple/ripple-lib/commit/8a3d4a64db5fbf560ebf87dc62e0212513c5e18a)
|
||||
|
||||
**Changes**
|
||||
+ [Fix proxy support and add support for proxy authorization](https://github.com/ripple/ripple-lib/commit/14b840f3feca758e0384b746c94e36d8bf59b8c2)
|
||||
+ [Fix trace option](https://github.com/ripple/ripple-lib/commit/af620755c53556c55eed12de4b0013ef5a349ce2)
|
||||
+ [Allow memos on all transaction types](https://github.com/ripple/ripple-lib/commit/b5081344da8e66fbd3a5113cc3313325ef72a494)
|
||||
+ [Add documentation for RippleAPI options](https://github.com/ripple/ripple-lib/commit/a76b554cadb9f9f918b06f8386bc29355682a1a4)
|
||||
+ [Docs: more on basic types, tx types](https://github.com/ripple/ripple-lib/commit/fdbac63f466b4fd3be701d4878800d856692e26e)
|
||||
+ [Docs: revised introductory material](https://github.com/ripple/ripple-lib/commit/ef2515507dbd3c6a426ab5b31332a1bdf72d5b2d)
|
||||
+ [boost coverage to almost 100%](https://github.com/ripple/ripple-lib/commit/995606b1e6f3643af34d9fd442ccd31f320b03eb)
|
||||
|
||||
##0.13.2
|
||||
|
||||
**Changes**
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#ripple-lib
|
||||
|
||||
A JavaScript API for interacting with Ripple in Node.js and the browser
|
||||
A JavaScript API for interacting with Ripple in Node.js
|
||||
|
||||
[](https://circleci.com/gh/ripple/ripple-lib/tree/develop) [](https://coveralls.io/r/ripple/ripple-lib?branch=develop)
|
||||
|
||||
@@ -8,7 +8,7 @@ A JavaScript API for interacting with Ripple in Node.js and the browser
|
||||
|
||||
###Features
|
||||
|
||||
+ Connect to a rippled server in JavaScript (Node.js or browser)
|
||||
+ Connect to a rippled server in Node.js
|
||||
+ Issue [rippled API](https://ripple.com/build/rippled-apis/) requests
|
||||
+ Listen to events on the Ripple network (transaction, ledger, etc.)
|
||||
+ Sign and submit transactions to the Ripple network
|
||||
@@ -30,7 +30,7 @@ Then see the [documentation](https://github.com/ripple/ripple-lib/blob/develop/d
|
||||
|
||||
##Generating Documentation
|
||||
|
||||
The continuous integration tests require that the documentation stays up-to-date. If you make changes the the JSON schemas, fixtures, or documentation sources, you must update the documentation by running `npm run docgen`.
|
||||
The continuous integration tests require that the documentation stays up-to-date. If you make changes to the JSON schemas, fixtures, or documentation sources, you must update the documentation by running `npm run docgen`.
|
||||
|
||||
##More Information
|
||||
|
||||
|
||||
12
circle.yml
12
circle.yml
@@ -1,7 +1,19 @@
|
||||
machine:
|
||||
node:
|
||||
version: 0.12.0
|
||||
hosts:
|
||||
testripple.circleci.com: 127.0.0.1
|
||||
dependencies:
|
||||
pre:
|
||||
- npm -g install npm@latest-2
|
||||
- wget https://s3-us-west-2.amazonaws.com/ripple-debs/rippled_0.30.1-b11-1.deb
|
||||
- sudo dpkg -i rippled_0.30.1-b11-1.deb
|
||||
test:
|
||||
pre:
|
||||
- rippled -a --start --conf "$HOME/$CIRCLE_PROJECT_REPONAME/test/integration/rippled.cfg":
|
||||
background: true
|
||||
override:
|
||||
- scripts/ci.sh "$CIRCLE_NODE_INDEX" "$CIRCLE_NODE_TOTAL":
|
||||
parallel: true
|
||||
post:
|
||||
- killall /usr/bin/rippled
|
||||
|
||||
1040
docs/index.md
1040
docs/index.md
File diff suppressed because it is too large
Load Diff
@@ -1,7 +1,7 @@
|
||||
'use strict';
|
||||
const RippleAPI = require('../../src').RippleAPI; // require('ripple-lib')
|
||||
|
||||
const api = new RippleAPI({servers: ['wss://s1.ripple.com:443']});
|
||||
const api = new RippleAPI({server: 'wss://s1.ripple.com:443'});
|
||||
const address = 'r3kmLJN5D28dHuH8vZNUZpMC43pEHpaocV';
|
||||
|
||||
api.connect().then(() => {
|
||||
|
||||
38
docs/samples/cancelall.js
Normal file
38
docs/samples/cancelall.js
Normal file
@@ -0,0 +1,38 @@
|
||||
'use strict';
|
||||
const RippleAPI = require('../../dist/npm').RippleAPI; // require('ripple-lib')
|
||||
|
||||
const address = 'rLDYrujdKUfVx28T9vRDAbyJ7G2WVXKo4K';
|
||||
const secret = '';
|
||||
|
||||
const api = new RippleAPI({server: 'wss://s1.ripple.com:443'});
|
||||
const instructions = {maxLedgerVersionOffset: 5};
|
||||
|
||||
function fail(message) {
|
||||
console.error(message);
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
function cancelOrder(orderSequence) {
|
||||
console.log('Cancelling order: ' + orderSequence.toString());
|
||||
return api.prepareOrderCancellation(address, {orderSequence}, instructions)
|
||||
.then(prepared => {
|
||||
const signing = api.sign(prepared.txJSON, secret);
|
||||
return api.submit(signing.signedTransaction);
|
||||
});
|
||||
}
|
||||
|
||||
function cancelAllOrders(orderSequences) {
|
||||
if (orderSequences.length === 0) {
|
||||
return Promise.resolve();
|
||||
}
|
||||
const orderSequence = orderSequences.pop();
|
||||
return cancelOrder(orderSequence).then(() => cancelAllOrders(orderSequences));
|
||||
}
|
||||
|
||||
api.connect().then(() => {
|
||||
console.log('Connected...');
|
||||
return api.getOrders(address).then(orders => {
|
||||
const orderSequences = orders.map(order => order.properties.sequence);
|
||||
return cancelAllOrders(orderSequences);
|
||||
}).then(() => process.exit(0));
|
||||
}).catch(fail);
|
||||
@@ -4,13 +4,13 @@ const RippleAPI = require('../../src').RippleAPI; // require('ripple-lib')
|
||||
const address = 'INSERT ADDRESS HERE';
|
||||
const secret = 'INSERT SECRET HERE';
|
||||
|
||||
const api = new RippleAPI({servers: ['wss://s1.ripple.com:443']});
|
||||
const api = new RippleAPI({server: 'wss://s1.ripple.com:443'});
|
||||
const instructions = {maxLedgerVersionOffset: 5};
|
||||
|
||||
const payment = {
|
||||
source: {
|
||||
address: address,
|
||||
amount: {
|
||||
maxAmount: {
|
||||
value: '0.01',
|
||||
currency: 'XRP'
|
||||
}
|
||||
|
||||
@@ -6,23 +6,28 @@
|
||||
"r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59"
|
||||
```
|
||||
|
||||
Every Ripple account has an *address*, which is a base58-encoding of a hash of the account's public key.
|
||||
Every Ripple account has an *address*, which is a base58-encoding of a hash of the account's public key. Ripple addresses always start with the lowercase letter `r`.
|
||||
|
||||
## Account Sequence Number
|
||||
|
||||
Every Ripple account has a *sequence number* that is used to order transactions. Every transaction must have a sequence number and transaction can only be executed in order by sequence number. This prevents one transaction from executing twice and transactions executing out of order. The sequence number starts at `1` and increments for each transaction that the account makes.
|
||||
Every Ripple account has a *sequence number* that is used to keep transactions in order. Every transaction must have a sequence number. A transaction can only be executed if it has the next sequence number in order, of the account sending it. This prevents one transaction from executing twice and transactions executing out of order. The sequence number starts at `1` and increments for each transaction that the account makes.
|
||||
|
||||
## Currency
|
||||
|
||||
Currencies are represented as either 3-character currency codes or 40-character uppercase hexadecimal strings. We recommend using uppercase [ISO 4217 Currency Codes](http://www.xe.com/iso4217.php) only. The string "XRP" is disallowed on trustlines because it is reserved for the Ripple native currency. The following characters are permitted: all uppercase and lowercase letters, digits, as well as the symbols `?`, `!`, `@`, `#`, `$`, `%`, `^`, `&`, `*`, `<`, `>`, `(`, `)`, `{`, `}`, `[`, `]`, and `|`.
|
||||
|
||||
## Value
|
||||
A *value* is a quantity of a currency represented as a decimal string (string encoding is used because javascript numbers do not have sufficient precision).
|
||||
A *value* is a quantity of a currency represented as a decimal string. Be careful: JavaScript's native number format does not have sufficient precision to represent all values. XRP has different precision from other currencies.
|
||||
|
||||
**XRP** has 6 significant digits past the decimal point. In other words, XRP cannot be divided into positive values smaller than `0.000001` (1e-6). XRP has a maximum value of `100000000000` (1e11).
|
||||
|
||||
**Non-XRP values** have 16 decimal digits of precision, with a maximum value of `9999999999999999e80`. The smallest positive non-XRP value is `1e-81`.
|
||||
|
||||
An XRP value has 6 significant digits past the decimal point. A non-XRP value has 16 total digits of precision.
|
||||
|
||||
## Amount
|
||||
|
||||
Example amount:
|
||||
|
||||
```json
|
||||
{
|
||||
"currency": "USD",
|
||||
@@ -31,6 +36,7 @@ An XRP value has 6 significant digits past the decimal point. A non-XRP value ha
|
||||
}
|
||||
```
|
||||
|
||||
Example XRP amount:
|
||||
```json
|
||||
{
|
||||
"currency": "XRP",
|
||||
@@ -38,7 +44,7 @@ An XRP value has 6 significant digits past the decimal point. A non-XRP value ha
|
||||
}
|
||||
```
|
||||
|
||||
An *amount* is data structure representing a currency, a quantity of that currency, and the counterparty on the trustline that holds the value (for all currencies besides "XRP").
|
||||
An *amount* is data structure representing a currency, a quantity of that currency, and the counterparty on the trustline that holds the value. For XRP, there is no counterparty.
|
||||
|
||||
A *lax amount* allows the counterparty to be omitted for all currencies. If the counterparty is not specified in an amount within a transaction specification, then any counterparty may be used for that amount.
|
||||
|
||||
|
||||
@@ -1,10 +1,23 @@
|
||||
## Boilerplate
|
||||
|
||||
Use the following [boilerplate code](https://en.wikipedia.org/wiki/Boilerplate_code) to wrap your custom code using RippleAPI.
|
||||
|
||||
```javascript
|
||||
const {RippleAPI} = require('ripple-lib');
|
||||
|
||||
const api = new RippleAPI({
|
||||
servers: ['wss://s1.ripple.com']
|
||||
server: 'wss://s1.ripple.com' // Public rippled server hosted by Ripple, Inc.
|
||||
});
|
||||
api.on('error', (errorCode, errorMessage) => {
|
||||
console.log(errorCode + ': ' + errorMessage);
|
||||
});
|
||||
api.on('connected', () => {
|
||||
console.log('connected');
|
||||
});
|
||||
api.on('disconnected', (code) => {
|
||||
// code - [close code](https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent) sent by the server
|
||||
// will be 1000 if this was normal closure
|
||||
console.log('disconnected, code:', code);
|
||||
});
|
||||
api.connect().then(() => {
|
||||
/* insert code here */
|
||||
@@ -13,22 +26,43 @@ api.connect().then(() => {
|
||||
}).catch(console.error);
|
||||
```
|
||||
|
||||
To get started, first install [nodejs](https://nodejs.org) version `0.12.0` or greater, then:
|
||||
RippleAPI is designed to work in [NodeJS](https://nodejs.org) (version `0.12.0` or greater) using [Babel](https://babeljs.io/) for [ECMAScript 6](https://babeljs.io/docs/learn-es2015/) support.
|
||||
|
||||
`npm install -g babel`
|
||||
|
||||
`npm install ripple-lib`
|
||||
|
||||
Then create a script based on the boilerplate shown here and run with:
|
||||
|
||||
`babel-node script.js`
|
||||
|
||||
The code samples in this documentation are written in ES6, but `RippleAPI` will work with ES5 also. Regardless of whether you use ES5 or ES6, the methods that return promises will return ES6-style promises.
|
||||
The code samples in this documentation are written in ES6, but `RippleAPI` will work with ES5 also. Regardless of whether you use ES5 or ES6, the methods that return promises will return [ES6-style promises](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise).
|
||||
|
||||
<aside class="notice">
|
||||
All the code snippets in this documentation assume that you have surrounded them with this boilerplate.
|
||||
</aside>
|
||||
|
||||
<aside class="notice">
|
||||
Dont forget the "catch" or errors may not be visible.
|
||||
If you omit the "catch" section, errors may not be visible.
|
||||
</aside>
|
||||
|
||||
<aside class="notice">
|
||||
The "error" event is emitted whenever an error occurs that cannot be associated with a specific request. If the listener is not registered, an exception will be thrown whenever the event is emitted.
|
||||
</aside>
|
||||
|
||||
### Parameters
|
||||
|
||||
The RippleAPI constructor optionally takes one argument, an object with the following options:
|
||||
|
||||
<%- renderSchema('input/api-options.json') %>
|
||||
|
||||
If you omit the `server` parameter, RippleAPI operates [offline](#offline-functionality).
|
||||
|
||||
|
||||
### Installation ###
|
||||
|
||||
1. Install [NodeJS](https://nodejs.org) and the Node Package Manager (npm). Most Linux distros have a package for NodeJS, but make sure you have version `0.12.0` or higher.
|
||||
2. Use npm to install [Babel](https://babeljs.io/) globally:
|
||||
`npm install -g babel-cli`
|
||||
3. Use npm to install RippleAPI:
|
||||
`npm install ripple-lib`
|
||||
|
||||
After you have installed ripple-lib, you can create scripts using the [boilerplate](#boilerplate) and run them using babel-node:
|
||||
`babel-node script.js`
|
||||
|
||||
<aside class="notice">
|
||||
Instead of using babel-node in production, we recommend using Babel to transpile to ECMAScript 5 first.
|
||||
</aside>
|
||||
|
||||
|
||||
24
docs/src/combine.md.ejs
Normal file
24
docs/src/combine.md.ejs
Normal file
@@ -0,0 +1,24 @@
|
||||
## combine
|
||||
|
||||
`combine(signedTransactions: Array<string>): {signedTransaction: string, id: string}`
|
||||
|
||||
Combines signed transactions from multiple accounts for a multisignature transaction. The signed transaction must subsequently be [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema("input/combine.json") %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns an object with the following structure:
|
||||
|
||||
<%- renderSchema("output/sign.json") %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const signedTransactions = <%- importFile('test/fixtures/requests/combine.json') %>;
|
||||
return api.combine(signedTransactions);
|
||||
```
|
||||
|
||||
<%- renderFixture("responses/combine.json") %>
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
`connect(): Promise<void>`
|
||||
|
||||
Tells the RippleAPI instance to connect to its server(s).
|
||||
Tells the RippleAPI instance to connect to its rippled server.
|
||||
|
||||
### Parameters
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
`disconnect(): Promise<void>`
|
||||
|
||||
Tells the RippleAPI instance to disconnect from its server(s).
|
||||
Tells the RippleAPI instance to disconnect from its rippled server.
|
||||
|
||||
### Parameters
|
||||
|
||||
|
||||
@@ -1,35 +1,45 @@
|
||||
# API Events
|
||||
|
||||
## ledgerClosed
|
||||
## ledger
|
||||
|
||||
This event is emitted whenever a new ledger version is validated on the connected server.
|
||||
|
||||
### Return Value
|
||||
|
||||
<%- renderSchema('output/ledger-closed.json') %>
|
||||
<%- renderSchema('output/ledger-event.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
api.on('ledgerClosed', ledger => {
|
||||
api.on('ledger', ledger => {
|
||||
console.log(JSON.stringify(ledger, null, 2));
|
||||
});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/ledger-closed.json') %>
|
||||
<%- renderFixture('responses/ledger-event.json') %>
|
||||
|
||||
## error
|
||||
|
||||
This event is emitted when there is an error on the connection to the server.
|
||||
This event is emitted when there is an error on the connection to the server that cannot be associated to a specific request.
|
||||
|
||||
### Return Value
|
||||
|
||||
The first parameter is a string indicating the error type, which may be `badMessage` (meaning that rippled returned a malformed message), or one of the [rippled Universal Errors](https://ripple.com/build/rippled-apis/#universal-errors). The second parameter is a message explaining the error, or the message that caused the error in the case of `badMessage`.
|
||||
The first parameter is a string indicating the error type:
|
||||
* `badMessage` - rippled returned a malformed message
|
||||
* `websocket` - the websocket library emitted an error
|
||||
* one of the error codes found in the [rippled Universal Errors](https://ripple.com/build/rippled-apis/#universal-errors).
|
||||
|
||||
The second parameter is a message explaining the error.
|
||||
|
||||
The third parameter is:
|
||||
* the message that caused the error for `badMessage`
|
||||
* the error object emitted for `websocket`
|
||||
* the parsed response for rippled errors
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
api.on('error', (errorCode, errorMessage) => {
|
||||
api.on('error', (errorCode, errorMessage, data) => {
|
||||
console.log(errorCode + ': ' + errorMessage);
|
||||
});
|
||||
```
|
||||
@@ -37,3 +47,35 @@ api.on('error', (errorCode, errorMessage) => {
|
||||
```
|
||||
tooBusy: The server is too busy to help you now.
|
||||
```
|
||||
|
||||
## connected
|
||||
|
||||
This event is emitted after connection successfully opened.
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
api.on('connected', () => {
|
||||
console.log('Connection is open now.');
|
||||
});
|
||||
```
|
||||
|
||||
## disconnected
|
||||
|
||||
This event is emitted when connection is closed.
|
||||
|
||||
### Return Value
|
||||
|
||||
The only parameter is a number containing the [close code](https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent) send by the server.
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
api.on('disconnected', (code) => {
|
||||
if (code !== 1000) {
|
||||
console.log('Connection is closed due to error.');
|
||||
} else {
|
||||
console.log('Connection is closed normally.');
|
||||
}
|
||||
});
|
||||
```
|
||||
|
||||
@@ -6,7 +6,7 @@ Generate a new Ripple address and corresponding secret.
|
||||
|
||||
### Parameters
|
||||
|
||||
This method has no parameters.
|
||||
<%- renderSchema('input/generate-address.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
@@ -17,8 +17,7 @@ This method returns an object with the following structure:
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
return api.generateAddress()
|
||||
.then(result => {/* ... */});
|
||||
return api.generateAddress();
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/generate-address.json') %>
|
||||
|
||||
@@ -10,7 +10,7 @@ Returns aggregate balances by currency plus a breakdown of assets and obligation
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an array of objects with the following structure:
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<%- renderSchema('output/get-balance-sheet.json') %>
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
`getFee(): Promise<number>`
|
||||
|
||||
Returns the estimated transaction fee for the server(s) the RippleAPI instance is connected to.
|
||||
Returns the estimated transaction fee for the rippled server the RippleAPI instance is connected to.
|
||||
|
||||
### Parameters
|
||||
|
||||
@@ -10,7 +10,7 @@ This method has no parameters.
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with a floating point value representing the estimated fee to submit a transaction, expressed in XRP.
|
||||
This method returns a promise that resolves with a string encoded floating point value representing the estimated fee to submit a transaction, expressed in XRP.
|
||||
|
||||
### Example
|
||||
|
||||
@@ -19,5 +19,5 @@ return api.getFee().then(fee => {/* ... */});
|
||||
```
|
||||
|
||||
```json
|
||||
0.012
|
||||
"0.012"
|
||||
```
|
||||
|
||||
26
docs/src/getPaymentChannel.md.ejs
Normal file
26
docs/src/getPaymentChannel.md.ejs
Normal file
@@ -0,0 +1,26 @@
|
||||
## getPaymentChannel
|
||||
|
||||
`getPaymentChannel(id: string): Promise<Object>`
|
||||
|
||||
Returns specified payment channel.
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/get-payment-channel.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<%- renderSchema('output/get-payment-channel.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const channelId =
|
||||
'E30E709CF009A1F26E0E5C48F7AA1BFB79393764F15FB108BDC6E06D3CBD8415';
|
||||
return api.getPaymentChannel(channelId).then(channel =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/get-payment-channel.json') %>
|
||||
@@ -1,5 +1,6 @@
|
||||
<% include introduction.md.ejs %>
|
||||
<% include boilerplate.md.ejs %>
|
||||
<% include offline.md.ejs %>
|
||||
<% include basictypes.md.ejs %>
|
||||
<% include transactions.md.ejs %>
|
||||
<% include specifications.md.ejs %>
|
||||
@@ -20,17 +21,24 @@
|
||||
<% include getOrderbook.md.ejs %>
|
||||
<% include getSettings.md.ejs %>
|
||||
<% include getAccountInfo.md.ejs %>
|
||||
<% include getPaymentChannel.md.ejs %>
|
||||
<% include getLedger.md.ejs %>
|
||||
<% include preparePayment.md.ejs %>
|
||||
<% include prepareTrustline.md.ejs %>
|
||||
<% include prepareOrder.md.ejs %>
|
||||
<% include prepareOrderCancellation.md.ejs %>
|
||||
<% include prepareSettings.md.ejs %>
|
||||
<% include prepareSuspendedPaymentCreation.md.ejs %>
|
||||
<% include prepareSuspendedPaymentCancellation.md.ejs %>
|
||||
<% include prepareSuspendedPaymentExecution.md.ejs %>
|
||||
<% include prepareEscrowCreation.md.ejs %>
|
||||
<% include prepareEscrowCancellation.md.ejs %>
|
||||
<% include prepareEscrowExecution.md.ejs %>
|
||||
<% include preparePaymentChannelCreate.md.ejs %>
|
||||
<% include preparePaymentChannelClaim.md.ejs %>
|
||||
<% include preparePaymentChannelFund.md.ejs %>
|
||||
<% include sign.md.ejs %>
|
||||
<% include combine.md.ejs %>
|
||||
<% include submit.md.ejs %>
|
||||
<% include generateAddress.md.ejs %>
|
||||
<% include signPaymentChannelClaim.md.ejs %>
|
||||
<% include verifyPaymentChannelClaim.md.ejs %>
|
||||
<% include computeLedgerHash.md.ejs %>
|
||||
<% include events.md.ejs %>
|
||||
|
||||
@@ -1,5 +1,12 @@
|
||||
# Introduction
|
||||
|
||||
RippleAPI allows you to query and submit transactions to a node on the Ripple network.
|
||||
RippleAPI is the official client library to the Ripple Consensus Ledger. Currently, RippleAPI is only available in JavaScript.
|
||||
Using RippleAPI, you can:
|
||||
|
||||
* [Query transactions from the network](#gettransaction)
|
||||
* [Sign](#sign) transactions securely without connecting to any server
|
||||
* [Submit](#submit) transactions to the Ripple Consensus Ledger, including [Payments](#payment), [Orders](#order), [Settings changes](#settings), and [other types](#transaction-types)
|
||||
* [Generate a new Ripple Address](#generateaddress)
|
||||
* ... and [much more](#api-methods).
|
||||
|
||||
RippleAPI only provides access to *validated*, *immutable* transaction data.
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
`isConnected(): boolean`
|
||||
|
||||
Checks if the RippleAPI instance is connected to its server(s).
|
||||
Checks if the RippleAPI instance is connected to its rippled server.
|
||||
|
||||
### Parameters
|
||||
|
||||
|
||||
27
docs/src/offline.md.ejs
Normal file
27
docs/src/offline.md.ejs
Normal file
@@ -0,0 +1,27 @@
|
||||
## Offline functionality
|
||||
|
||||
RippleAPI can also function without internet connectivity. This can be useful in order to generate secrets and sign transactions from a secure, isolated machine.
|
||||
|
||||
To instantiate RippleAPI in offline mode, use the following boilerplate code:
|
||||
|
||||
```javascript
|
||||
const {RippleAPI} = require('ripple-lib');
|
||||
|
||||
const api = new RippleAPI();
|
||||
/* insert code here */
|
||||
```
|
||||
|
||||
Methods that depend on the state of the Ripple Consensus Ledger are unavailable in offline mode. To prepare transactions offline, you **must** specify the `fee`, `sequence`, and `maxLedgerVersion` parameters in the [transaction instructions](#transaction-instructions). The following methods should work offline:
|
||||
|
||||
* [preparePayment](#preparepayment)
|
||||
* [prepareTrustline](#preparetrustline)
|
||||
* [prepareOrder](#prepareorder)
|
||||
* [prepareOrderCancellation](#prepareordercancellation)
|
||||
* [prepareSettings](#preparesettings)
|
||||
* [prepareEscrowCreation](#prepareescrowcreation)
|
||||
* [prepareEscrowCancellation](#prepareescrowcancellation)
|
||||
* [prepareEscrowExecution](#prepareescrowexecution)
|
||||
* [sign](#sign)
|
||||
* [generateAddress](#generateaddress)
|
||||
* [computeLedgerHash](#computeledgerhash)
|
||||
|
||||
30
docs/src/prepareEscrowCancellation.md.ejs
Normal file
30
docs/src/prepareEscrowCancellation.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## prepareEscrowCancellation
|
||||
|
||||
`prepareEscrowCancellation(address: string, escrowCancellation: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare an escrow cancellation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-escrow-cancellation.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const escrowCancellation = <%- importFile('test/fixtures/requests/prepare-escrow-cancellation.json') %>;
|
||||
return api.prepareEscrowCancellation(address, escrowCancellation).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-escrow-cancellation.json') %>
|
||||
30
docs/src/prepareEscrowCreation.md.ejs
Normal file
30
docs/src/prepareEscrowCreation.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## prepareEscrowCreation
|
||||
|
||||
`prepareEscrowCreation(address: string, escrowCreation: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare an escrow creation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-escrow-creation.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const escrowCreation = <%- importFile('test/fixtures/requests/prepare-escrow-creation.json') %>;
|
||||
return api.prepareEscrowCreation(address, escrowCreation).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-escrow-creation.json') %>
|
||||
30
docs/src/prepareEscrowExecution.md.ejs
Normal file
30
docs/src/prepareEscrowExecution.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## prepareEscrowExecution
|
||||
|
||||
`prepareEscrowExecution(address: string, escrowExecution: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare an escrow execution transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-escrow-execution.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const escrowExecution = <%- importFile('test/fixtures/requests/prepare-escrow-execution.json') %>;
|
||||
return api.prepareEscrowExecution(address, escrowExecution).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-escrow-execution.json') %>
|
||||
@@ -13,7 +13,7 @@ Prepare an order transaction. The prepared transaction must subsequently be [sig
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare" methods have the same return type.
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
## prepareOrderCancellation
|
||||
|
||||
`prepareOrderCancellation(address: string, sequence: number, instructions: Object): Promise<Object>`
|
||||
`prepareOrderCancellation(address: string, orderCancellation: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare an order cancellation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
@@ -13,7 +13,7 @@ Prepare an order cancellation transaction. The prepared transaction must subsequ
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare" methods have the same return type.
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema("output/prepare.json") %>
|
||||
@@ -22,8 +22,8 @@ All "prepare" methods have the same return type.
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const sequence = 123;
|
||||
return api.prepareOrderCancellation(address, sequence)
|
||||
const orderCancellation = {orderSequence: 123};
|
||||
return api.prepareOrderCancellation(address, orderCancellation)
|
||||
.then(prepared => {/* ... */});
|
||||
```
|
||||
|
||||
|
||||
30
docs/src/preparePaymentChannelClaim.md.ejs
Normal file
30
docs/src/preparePaymentChannelClaim.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## preparePaymentChannelClaim
|
||||
|
||||
`preparePaymentChannelClaim(address: string, paymentChannelClaim: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a payment channel claim transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-payment-channel-claim.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const paymentChannelClaim = <%- importFile('test/fixtures/requests/prepare-payment-channel-claim.json') %>;
|
||||
return api.preparePaymentChannelClaim(address, paymentChannelClaim).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-payment-channel-claim.json') %>
|
||||
30
docs/src/preparePaymentChannelCreate.md.ejs
Normal file
30
docs/src/preparePaymentChannelCreate.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## preparePaymentChannelCreate
|
||||
|
||||
`preparePaymentChannelCreate(address: string, paymentChannelCreate: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a payment channel creation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-payment-channel-create.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const paymentChannelCreate = <%- importFile('test/fixtures/requests/prepare-payment-channel-create.json') %>;
|
||||
return api.preparePaymentChannelCreate(address, paymentChannelCreate).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-payment-channel-create.json') %>
|
||||
30
docs/src/preparePaymentChannelFund.md.ejs
Normal file
30
docs/src/preparePaymentChannelFund.md.ejs
Normal file
@@ -0,0 +1,30 @@
|
||||
## preparePaymentChannelFund
|
||||
|
||||
`preparePaymentChannelFund(address: string, paymentChannelFund: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a payment channel fund transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-payment-channel-fund.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const paymentChannelFund = <%- importFile('test/fixtures/requests/prepare-payment-channel-fund.json') %>;
|
||||
return api.preparePaymentChannelFund(address, paymentChannelFund).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-payment-channel-fund.json') %>
|
||||
@@ -1,30 +0,0 @@
|
||||
## prepareSuspendedPaymentCancellation
|
||||
|
||||
`prepareSuspendedPaymentCancellation(address: string, suspendedPaymentCancellation: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a suspended payment cancellation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-suspended-payment-cancellation.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const suspendedPaymentCancellation = <%- importFile('test/fixtures/requests/prepare-suspended-payment-cancellation.json') %>;
|
||||
return api.prepareSuspendedPaymentCancellation(address, suspendedPaymentCancellation).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-suspended-payment-cancellation.json') %>
|
||||
@@ -1,30 +0,0 @@
|
||||
## prepareSuspendedPaymentCreation
|
||||
|
||||
`prepareSuspendedPaymentCreation(address: string, suspendedPaymentCreation: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a suspended payment creation transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-suspended-payment-creation.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const suspendedPaymentCreation = <%- importFile('test/fixtures/requests/prepare-suspended-payment-creation.json') %>;
|
||||
return api.prepareSuspendedPaymentCreation(address, suspendedPaymentCreation).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-suspended-payment-creation.json') %>
|
||||
@@ -1,30 +0,0 @@
|
||||
## prepareSuspendedPaymentExecution
|
||||
|
||||
`prepareSuspendedPaymentExecution(address: string, suspendedPaymentExecution: Object, instructions: Object): Promise<Object>`
|
||||
|
||||
Prepare a suspended payment execution transaction. The prepared transaction must subsequently be [signed](#sign) and [submitted](#submit).
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema('input/prepare-suspended-payment-execution.json') %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a promise that resolves with an object with the following structure:
|
||||
|
||||
<aside class="notice">
|
||||
All "prepare*" methods have the same return type.
|
||||
</aside>
|
||||
|
||||
<%- renderSchema('output/prepare.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const suspendedPaymentExecution = <%- importFile('test/fixtures/requests/prepare-suspended-payment-execution.json') %>;
|
||||
return api.prepareSuspendedPaymentExecution(address, suspendedPaymentExecution).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
<%- renderFixture('responses/prepare-suspended-payment-execution.json') %>
|
||||
@@ -23,7 +23,7 @@ All "prepare*" methods have the same return type.
|
||||
```javascript
|
||||
const address = 'r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59';
|
||||
const trustline = <%- importFile('test/fixtures/requests/prepare-trustline.json') %>;
|
||||
return api.preparePayment(address, trustline).then(prepared =>
|
||||
return api.prepareTrustline(address, trustline).then(prepared =>
|
||||
{/* ... */});
|
||||
```
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
## sign
|
||||
|
||||
`sign(txJSON: string, secret: string): {signedTransaction: string, id: string}`
|
||||
`sign(txJSON: string, secret: string, options: Object): {signedTransaction: string, id: string}`
|
||||
|
||||
Sign a prepared transaction. The signed transaction must subsequently be [submitted](#submit).
|
||||
|
||||
|
||||
28
docs/src/signPaymentChannelClaim.md.ejs
Normal file
28
docs/src/signPaymentChannelClaim.md.ejs
Normal file
@@ -0,0 +1,28 @@
|
||||
## signPaymentChannelClaim
|
||||
|
||||
`signPaymentChannelClaim(channel: string, amount: string, privateKey: string): string`
|
||||
|
||||
Sign a payment channel claim. The signature can be submitted in a subsequent [PaymentChannelClaim](#preparePaymmentChannelClaim) transaction.
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema("input/sign-payment-channel-claim.json") %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns a signature string:
|
||||
|
||||
<%- renderSchema("output/sign-payment-channel-claim.json") %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const channel =
|
||||
'3E18C05AD40319B809520F1A136370C4075321B285217323396D6FD9EE1E9037';
|
||||
const amount = '.00001';
|
||||
const privateKey =
|
||||
'ACCD3309DB14D1A4FC9B1DAE608031F4408C85C73EE05E035B7DC8B25840107A';
|
||||
return api.signPaymentChannelClaim(channel, amount, privateKey);
|
||||
```
|
||||
|
||||
<%- renderFixture("responses/sign-payment-channel-claim.json") %>
|
||||
@@ -52,32 +52,62 @@ See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderFixture('requests/prepare-settings.json') %>
|
||||
|
||||
## Suspended Payment Creation
|
||||
## Escrow Creation
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/suspended-payment-creation.json') %>
|
||||
<%- renderSchema('specifications/escrow-creation.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-suspended-payment-creation.json') %>
|
||||
<%- renderFixture('requests/prepare-escrow-creation.json') %>
|
||||
|
||||
## Suspended Payment Cancellation
|
||||
## Escrow Cancellation
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/suspended-payment-cancellation.json') %>
|
||||
<%- renderSchema('specifications/escrow-cancellation.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-suspended-payment-cancellation.json') %>
|
||||
<%- renderFixture('requests/prepare-escrow-cancellation.json') %>
|
||||
|
||||
## Suspended Payment Execution
|
||||
## Escrow Execution
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/suspended-payment-execution.json') %>
|
||||
<%- renderSchema('specifications/escrow-execution.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-suspended-payment-execution.json') %>
|
||||
<%- renderFixture('requests/prepare-escrow-execution.json') %>
|
||||
|
||||
## Payment Channel Create
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/payment-channel-create.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-payment-channel-create.json') %>
|
||||
|
||||
## Payment Channel Fund
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/payment-channel-fund.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-payment-channel-fund.json') %>
|
||||
|
||||
## Payment Channel Claim
|
||||
|
||||
See [Transaction Types](#transaction-types) for a description.
|
||||
|
||||
<%- renderSchema('specifications/payment-channel-claim.json') %>
|
||||
|
||||
### Example
|
||||
|
||||
<%- renderFixture('requests/prepare-payment-channel-claim.json') %>
|
||||
|
||||
@@ -6,40 +6,58 @@ A transaction type is specified by the strings in the first column in the table
|
||||
|
||||
Type | Description
|
||||
---- | -----------
|
||||
[payment](#payment) | A `payment` transaction represents a transfer of value from one account to another. Depending on the path taken, additional exchanges of value may occur atomically to facilitate the payment.
|
||||
[payment](#payment) | A `payment` transaction represents a transfer of value from one account to another. Depending on the [path](https://ripple.com/build/paths/) taken, additional exchanges of value may occur atomically to facilitate the payment.
|
||||
[order](#order) | An `order` transaction creates a limit order. It defines an intent to exchange currencies, and creates an order in the Ripple Consensus Ledger's order book if not completely fulfilled when placed. Orders can be partially fulfilled.
|
||||
[orderCancellation](#order-cancellation) | An `orderCancellation` transaction cancels an order in the Ripple Consensus Ledger's order book.
|
||||
[trustline](#trustline) | A `trustline` transactions creates or modifies a trust line between two accounts.
|
||||
[settings](#settings) | A `settings` transaction modifies the settings of an account in the Ripple Consensus Ledger.
|
||||
[suspendedPaymentCreation](#suspended-payment-creation) | A `suspendedPaymentCreation` transaction creates a suspended payment on the ledger, which locks XRP until a cryptographic condition is met or it expires. It is like an escrow service where the Ripple network acts as the escrow agent.
|
||||
[suspendedPaymentCancellation](#suspended-payment-cancellation) | A `suspendedPaymentCancellation` transaction unlocks the funds in a suspended payment and sends them back to the creator of the suspended payment, but it will only work after the suspended payment expires.
|
||||
[suspendedPaymentExecution](#suspended-payment-execution) | A `suspendedPaymentExecution` transaction unlocks the funds in a suspended payment and sends them to the destination of the suspended payment, but it will only work if the cryptographic condition is provided.
|
||||
[escrowCreation](#escrow-creation) | An `escrowCreation` transaction creates an escrow on the ledger, which locks XRP until a cryptographic condition is met or it expires. It is like an escrow service where the Ripple network acts as the escrow agent.
|
||||
[escrowCancellation](#escrow-cancellation) | An `escrowCancellation` transaction unlocks the funds in an escrow and sends them back to the creator of the escrow, but it will only work after the escrow expires.
|
||||
[escrowExecution](#escrow-execution) | An `escrowExecution` transaction unlocks the funds in an escrow and sends them to the destination of the escrow, but it will only work if the cryptographic condition is provided.
|
||||
|
||||
## Transaction Flow
|
||||
|
||||
Executing a transaction with `RippleAPI` requires the following four steps:
|
||||
|
||||
1. prepare - Create an unsigned transaction based on a [specification](#transaction-specifications) and [instructions](#transaction-instructions).
|
||||
2. sign - Cryptographically sign the transaction locally and save the [transaction ID](#transaction-id). Signing is how the owner of an account authorizes a transaction to take place.
|
||||
3. submit - Submit the transaction to the connected server.
|
||||
4. verify - Verify that the transaction got validated by querying with [getTransaction](#gettransaction). This is necessary because transactions may fail even if they were successfully submitted. It is recommended that you specify a `maxLedgerVersion` in the instructions when preparing a transaction because without it there is no way to know that a failed transaction will never succeeed in the future. It is impossible for a transaction to succeed after the network ledger version exceeds the `maxLedgerVersion` provided in the transaction instructions.
|
||||
1. Prepare - Create an unsigned transaction based on a [specification](#transaction-specifications) and [instructions](#transaction-instructions). There is a method to prepare each type of transaction:
|
||||
* [preparePayment](#preparepayment)
|
||||
* [prepareTrustline](#preparetrustline)
|
||||
* [prepareOrder](#prepareorder)
|
||||
* [prepareOrderCancellation](#prepareordercancellation)
|
||||
* [prepareSettings](#preparesettings)
|
||||
* [prepareEscrowCreation](#prepareescrowcreation)
|
||||
* [prepareEscrowCancellation](#prepareescrowcancellation)
|
||||
* [prepareEscrowExecution](#prepareescrowexecution)
|
||||
2. [Sign](#sign) - Cryptographically sign the transaction locally and save the [transaction ID](#transaction-id). Signing is how the owner of an account authorizes a transaction to take place. For multisignature transactions, the `signedTransaction` fields returned by `sign` must be collected and passed to the [combine](#combine) method.
|
||||
3. [Submit](#submit) - Submit the transaction to the connected server.
|
||||
4. Verify - Verify that the transaction got validated by querying with [getTransaction](#gettransaction). This is necessary because transactions may fail even if they were successfully submitted.
|
||||
|
||||
## Transaction Fees
|
||||
|
||||
Every transaction requires a *fee* to be paid in XRP. The fee is destroyed; it is not sent to any other party. The purpose of the fee is to prevent denial of service attacks on the Ripple network.
|
||||
Every transaction must destroy a small amount of XRP as a cost to send the transaction. This is also called a *transaction fee*. The transaction cost is designed to increase along with the load on the Ripple network, making it very expensive to deliberately or inadvertently overload the network.
|
||||
|
||||
You can choose the size of the fee you want to pay or let a default be used. The fee is like a bid in an auction for slots in the next ledger closing. If the fee you choose is too low, your transaction will not be included in the next ledger closing. You can get an estimate of the fee required to be included in the next ledger closing with the [getFee](#getfee) method.
|
||||
You can choose the size of the fee you want to pay or let a default be used. You can get an estimate of the fee required to be included in the next ledger closing with the [getFee](#getfee) method.
|
||||
|
||||
## Transaction Instructions
|
||||
|
||||
Transactions instructions indicates how to execute a transaction, complementary with the [transaction specification](#transaction-specifications).
|
||||
Transaction instructions indicate how to execute a transaction, complementary with the [transaction specification](#transaction-specifications).
|
||||
|
||||
<%- renderSchema("objects/instructions.json") %>
|
||||
|
||||
We recommended that you specify a `maxLedgerVersion` so that you can quickly determine that a failed transaction will never succeeed in the future. It is impossible for a transaction to succeed after the network ledger version exceeds the transaction's `maxLedgerVersion`. If you omit `maxLedgerVersion`, the "prepare*" method automatically supplies a `maxLedgerVersion` equal to the current ledger plus 3, which it includes in the return value from the "prepare*" method.
|
||||
|
||||
## Transaction ID
|
||||
|
||||
```json
|
||||
"F4AB442A6D4CBB935D66E1DA7309A5FC71C7143ED4049053EC14E3875B0CF9BF"
|
||||
```
|
||||
|
||||
A hash of the transaction that can be used to identify it. A transaction can be looked up by its ID using the [getTransaction](#gettransaction) method.
|
||||
A transaction ID is a 64-bit hexadecimal string that uniquely identifies the transaction. The transaction ID is derived from the transaction instruction and specifications, using a strong hash function.
|
||||
|
||||
You can look up a transaction by ID using the [getTransaction](#gettransaction) method.
|
||||
|
||||
## Transaction Memos
|
||||
|
||||
Every transaction can optionally have an array of memos for user applications. The `memos` field in each [transaction specification](#transaction-specifications) is an array of objects with the following structure:
|
||||
|
||||
<%- renderSchema('objects/memos.json') %>
|
||||
|
||||
31
docs/src/verifyPaymentChannelClaim.md.ejs
Normal file
31
docs/src/verifyPaymentChannelClaim.md.ejs
Normal file
@@ -0,0 +1,31 @@
|
||||
## verifyPaymentChannelClaim
|
||||
|
||||
`verifyPaymentChannelClaim(channel: string, amount: string, signature: string, publicKey: string): boolean`
|
||||
|
||||
Verify a payment channel claim signature.
|
||||
|
||||
### Parameters
|
||||
|
||||
<%- renderSchema("input/verify-payment-channel-claim.json") %>
|
||||
|
||||
### Return Value
|
||||
|
||||
This method returns `true` if the claim signature is valid.
|
||||
|
||||
<%- renderSchema("output/verify-payment-channel-claim.json") %>
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const channel =
|
||||
'3E18C05AD40319B809520F1A136370C4075321B285217323396D6FD9EE1E9037';
|
||||
const amount = '.00001';
|
||||
const signature = <%- importFile("test/fixtures/responses/sign-payment-channel-claim.json") %>;
|
||||
const publicKey =
|
||||
'02F89EAEC7667B30F33D0687BBA86C3FE2A08CCA40A9186C5BDE2DAA6FA97A37D8';
|
||||
return api.verifyPaymentChannelClaim(channel, amount, signature, publicKey);
|
||||
```
|
||||
|
||||
```json
|
||||
true
|
||||
```
|
||||
398
npm-shrinkwrap.json
generated
398
npm-shrinkwrap.json
generated
@@ -1,248 +1,170 @@
|
||||
{
|
||||
"name": "ripple-lib",
|
||||
"version": "0.13.2",
|
||||
"version": "0.17.6",
|
||||
"dependencies": {
|
||||
"ajv": {
|
||||
"version": "1.4.8",
|
||||
"from": "https://registry.npmjs.org/ajv/-/ajv-1.4.8.tgz",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-1.4.8.tgz",
|
||||
"dependencies": {
|
||||
"json-stable-stringify": {
|
||||
"version": "1.0.0",
|
||||
"from": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.0.tgz",
|
||||
"resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.0.tgz",
|
||||
"dependencies": {
|
||||
"jsonify": {
|
||||
"version": "0.0.0",
|
||||
"from": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz",
|
||||
"resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
"agent-base": {
|
||||
"version": "2.0.1",
|
||||
"from": "agent-base@>=2.0.0 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/agent-base/-/agent-base-2.0.1.tgz"
|
||||
},
|
||||
"babel-polyfill": {
|
||||
"version": "6.2.0",
|
||||
"from": "babel-polyfill@*",
|
||||
"resolved": "https://registry.npmjs.org/babel-polyfill/-/babel-polyfill-6.2.0.tgz",
|
||||
"dependencies": {
|
||||
"core-js": {
|
||||
"version": "1.2.6",
|
||||
"from": "core-js@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/core-js/-/core-js-1.2.6.tgz"
|
||||
},
|
||||
"babel-regenerator-runtime": {
|
||||
"version": "6.2.0",
|
||||
"from": "babel-regenerator-runtime@>=6.2.0 <7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/babel-regenerator-runtime/-/babel-regenerator-runtime-6.2.0.tgz"
|
||||
}
|
||||
}
|
||||
"version": "6.9.1",
|
||||
"from": "babel-polyfill@>=6.3.14 <7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/babel-polyfill/-/babel-polyfill-6.9.1.tgz"
|
||||
},
|
||||
"babel-runtime": {
|
||||
"version": "5.8.29",
|
||||
"from": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-5.8.29.tgz",
|
||||
"resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-5.8.29.tgz",
|
||||
"version": "6.9.2",
|
||||
"from": "babel-runtime@>=6.3.19 <7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.9.2.tgz"
|
||||
},
|
||||
"base-x": {
|
||||
"version": "1.0.4",
|
||||
"from": "base-x@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/base-x/-/base-x-1.0.4.tgz"
|
||||
},
|
||||
"bignumber.js": {
|
||||
"version": "2.3.0",
|
||||
"from": "bignumber.js@>=2.0.3 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-2.3.0.tgz"
|
||||
},
|
||||
"bn.js": {
|
||||
"version": "4.11.6",
|
||||
"from": "bn.js@>=4.11.3 <5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz"
|
||||
},
|
||||
"brorand": {
|
||||
"version": "1.0.5",
|
||||
"from": "brorand@>=1.0.5 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/brorand/-/brorand-1.0.5.tgz"
|
||||
},
|
||||
"cipher-base": {
|
||||
"version": "1.0.2",
|
||||
"from": "cipher-base@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.2.tgz"
|
||||
},
|
||||
"core-js": {
|
||||
"version": "2.4.0",
|
||||
"from": "core-js@>=2.4.0 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/core-js/-/core-js-2.4.0.tgz"
|
||||
},
|
||||
"create-hash": {
|
||||
"version": "1.1.2",
|
||||
"from": "create-hash@>=1.1.2 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.2.tgz"
|
||||
},
|
||||
"debug": {
|
||||
"version": "2.2.0",
|
||||
"from": "debug@>=2.0.0 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz"
|
||||
},
|
||||
"decimal.js": {
|
||||
"version": "5.0.8",
|
||||
"from": "decimal.js@>=5.0.8 <6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-5.0.8.tgz"
|
||||
},
|
||||
"elliptic": {
|
||||
"version": "5.2.1",
|
||||
"from": "elliptic@>=5.1.0 <6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/elliptic/-/elliptic-5.2.1.tgz",
|
||||
"dependencies": {
|
||||
"core-js": {
|
||||
"version": "1.2.3",
|
||||
"from": "https://registry.npmjs.org/core-js/-/core-js-1.2.3.tgz",
|
||||
"resolved": "https://registry.npmjs.org/core-js/-/core-js-1.2.3.tgz"
|
||||
"bn.js": {
|
||||
"version": "3.3.0",
|
||||
"from": "bn.js@>=3.1.1 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bn.js/-/bn.js-3.3.0.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"bignumber.js": {
|
||||
"version": "2.1.0",
|
||||
"from": "bignumber.js@>=2.0.3 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-2.1.0.tgz"
|
||||
"extend": {
|
||||
"version": "3.0.0",
|
||||
"from": "extend@>=3.0.0 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/extend/-/extend-3.0.0.tgz"
|
||||
},
|
||||
"hash.js": {
|
||||
"version": "1.0.3",
|
||||
"from": "hash.js@>=1.0.3 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.0.3.tgz"
|
||||
},
|
||||
"https-proxy-agent": {
|
||||
"version": "1.0.0",
|
||||
"from": "https-proxy-agent@>=1.0.0 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-1.0.0.tgz",
|
||||
"dependencies": {
|
||||
"agent-base": {
|
||||
"version": "2.0.1",
|
||||
"from": "agent-base@>=2.0.0 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/agent-base/-/agent-base-2.0.1.tgz",
|
||||
"dependencies": {
|
||||
"semver": {
|
||||
"version": "5.0.3",
|
||||
"from": "semver@>=5.0.1 <5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/semver/-/semver-5.0.3.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"debug": {
|
||||
"version": "2.2.0",
|
||||
"from": "debug@>=2.0.0 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz",
|
||||
"dependencies": {
|
||||
"ms": {
|
||||
"version": "0.7.1",
|
||||
"from": "ms@0.7.1",
|
||||
"resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"extend": {
|
||||
"version": "3.0.0",
|
||||
"from": "extend@>=3.0.0 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/extend/-/extend-3.0.0.tgz"
|
||||
}
|
||||
}
|
||||
"resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-1.0.0.tgz"
|
||||
},
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
},
|
||||
"jsonschema": {
|
||||
"version": "1.1.1",
|
||||
"from": "jsonschema@latest",
|
||||
"resolved": "https://registry.npmjs.org/jsonschema/-/jsonschema-1.1.1.tgz"
|
||||
},
|
||||
"lodash": {
|
||||
"version": "3.10.1",
|
||||
"from": "lodash@>=3.1.0 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/lodash/-/lodash-3.10.1.tgz"
|
||||
},
|
||||
"ms": {
|
||||
"version": "0.7.1",
|
||||
"from": "ms@0.7.1",
|
||||
"resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz"
|
||||
},
|
||||
"options": {
|
||||
"version": "0.0.6",
|
||||
"from": "options@>=0.0.5",
|
||||
"resolved": "https://registry.npmjs.org/options/-/options-0.0.6.tgz"
|
||||
},
|
||||
"regenerator-runtime": {
|
||||
"version": "0.9.5",
|
||||
"from": "regenerator-runtime@>=0.9.5 <0.10.0",
|
||||
"resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.9.5.tgz"
|
||||
},
|
||||
"ripemd160": {
|
||||
"version": "1.0.1",
|
||||
"from": "ripemd160@>=1.0.0 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-1.0.1.tgz"
|
||||
},
|
||||
"ripple-address-codec": {
|
||||
"version": "2.0.1",
|
||||
"from": "ripple-address-codec@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-address-codec/-/ripple-address-codec-2.0.1.tgz",
|
||||
"dependencies": {
|
||||
"hash.js": {
|
||||
"version": "1.0.3",
|
||||
"from": "hash.js@>=1.0.3 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.0.3.tgz",
|
||||
"dependencies": {
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"x-address-codec": {
|
||||
"version": "0.7.2",
|
||||
"from": "x-address-codec@>=0.7.0 <0.8.0",
|
||||
"resolved": "https://registry.npmjs.org/x-address-codec/-/x-address-codec-0.7.2.tgz",
|
||||
"dependencies": {
|
||||
"base-x": {
|
||||
"version": "1.0.1",
|
||||
"from": "base-x@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/base-x/-/base-x-1.0.1.tgz"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
"resolved": "https://registry.npmjs.org/ripple-address-codec/-/ripple-address-codec-2.0.1.tgz"
|
||||
},
|
||||
"ripple-binary-codec": {
|
||||
"version": "0.1.0",
|
||||
"from": "ripple-binary-codec@0.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-binary-codec/-/ripple-binary-codec-0.1.0.tgz",
|
||||
"version": "0.1.10",
|
||||
"from": "ripple-binary-codec@>=0.1.10 <0.2.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-binary-codec/-/ripple-binary-codec-0.1.10.tgz",
|
||||
"dependencies": {
|
||||
"bn.js": {
|
||||
"version": "3.3.0",
|
||||
"from": "bn.js@>=3.2.0 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bn.js/-/bn.js-3.3.0.tgz"
|
||||
},
|
||||
"create-hash": {
|
||||
"version": "1.1.2",
|
||||
"from": "create-hash@>=1.1.2 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.2.tgz",
|
||||
"dependencies": {
|
||||
"cipher-base": {
|
||||
"version": "1.0.2",
|
||||
"from": "cipher-base@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.2.tgz"
|
||||
},
|
||||
"ripemd160": {
|
||||
"version": "1.0.1",
|
||||
"from": "ripemd160@>=1.0.0 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-1.0.1.tgz"
|
||||
},
|
||||
"sha.js": {
|
||||
"version": "2.4.4",
|
||||
"from": "sha.js@>=2.3.6 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.4.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"decimal.js": {
|
||||
"version": "4.0.3",
|
||||
"from": "decimal.js@>=4.0.2 <5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-4.0.3.tgz"
|
||||
},
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
"lodash": {
|
||||
"version": "4.17.4",
|
||||
"from": "lodash@>=4.12.0 <5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"ripple-hashes": {
|
||||
"version": "0.1.0",
|
||||
"from": "ripple-hashes@0.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-hashes/-/ripple-hashes-0.1.0.tgz",
|
||||
"dependencies": {
|
||||
"create-hash": {
|
||||
"version": "1.1.2",
|
||||
"from": "create-hash@>=1.1.2 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.2.tgz",
|
||||
"dependencies": {
|
||||
"cipher-base": {
|
||||
"version": "1.0.2",
|
||||
"from": "cipher-base@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.2.tgz"
|
||||
},
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
},
|
||||
"ripemd160": {
|
||||
"version": "1.0.1",
|
||||
"from": "ripemd160@>=1.0.0 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-1.0.1.tgz"
|
||||
},
|
||||
"sha.js": {
|
||||
"version": "2.4.4",
|
||||
"from": "sha.js@>=2.3.6 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.4.tgz"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
"version": "0.3.0",
|
||||
"from": "ripple-hashes@>=0.3.0 <0.4.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-hashes/-/ripple-hashes-0.3.0.tgz"
|
||||
},
|
||||
"ripple-keypairs": {
|
||||
"version": "0.10.0",
|
||||
"from": "ripple-keypairs@>=0.10.0 <0.11.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-keypairs/-/ripple-keypairs-0.10.0.tgz",
|
||||
"dependencies": {
|
||||
"babel-runtime": {
|
||||
"version": "5.8.38",
|
||||
"from": "babel-runtime@>=5.8.20 <6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-5.8.38.tgz"
|
||||
},
|
||||
"bn.js": {
|
||||
"version": "3.3.0",
|
||||
"from": "bn.js@>=3.1.1 <4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/bn.js/-/bn.js-3.3.0.tgz"
|
||||
},
|
||||
"brorand": {
|
||||
"version": "1.0.5",
|
||||
"from": "brorand@>=1.0.5 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/brorand/-/brorand-1.0.5.tgz"
|
||||
},
|
||||
"elliptic": {
|
||||
"version": "5.2.1",
|
||||
"from": "elliptic@>=5.1.0 <6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/elliptic/-/elliptic-5.2.1.tgz",
|
||||
"dependencies": {
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"hash.js": {
|
||||
"version": "1.0.3",
|
||||
"from": "hash.js@>=1.0.3 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.0.3.tgz",
|
||||
"dependencies": {
|
||||
"inherits": {
|
||||
"version": "2.0.1",
|
||||
"from": "inherits@>=2.0.1 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.1.tgz"
|
||||
}
|
||||
}
|
||||
"core-js": {
|
||||
"version": "1.2.6",
|
||||
"from": "core-js@>=1.0.0 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/core-js/-/core-js-1.2.6.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -251,56 +173,30 @@
|
||||
"from": "ripple-lib-transactionparser@>=0.6.0 <0.7.0",
|
||||
"resolved": "https://registry.npmjs.org/ripple-lib-transactionparser/-/ripple-lib-transactionparser-0.6.0.tgz"
|
||||
},
|
||||
"semver": {
|
||||
"version": "5.0.3",
|
||||
"from": "semver@>=5.0.1 <5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/semver/-/semver-5.0.3.tgz"
|
||||
},
|
||||
"sha.js": {
|
||||
"version": "2.4.5",
|
||||
"from": "sha.js@>=2.3.6 <3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.5.tgz"
|
||||
},
|
||||
"ultron": {
|
||||
"version": "1.0.2",
|
||||
"from": "ultron@>=1.0.0 <1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ultron/-/ultron-1.0.2.tgz"
|
||||
},
|
||||
"ws": {
|
||||
"version": "1.1.1",
|
||||
"from": "ws@>=1.0.1 <2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/ws/-/ws-1.1.1.tgz"
|
||||
},
|
||||
"x-address-codec": {
|
||||
"version": "0.7.2",
|
||||
"from": "ws@>=0.7.1 <0.8.0",
|
||||
"resolved": "https://registry.npmjs.org/ws/-/ws-0.7.2.tgz",
|
||||
"dependencies": {
|
||||
"options": {
|
||||
"version": "0.0.6",
|
||||
"from": "options@>=0.0.5",
|
||||
"resolved": "https://registry.npmjs.org/options/-/options-0.0.6.tgz"
|
||||
},
|
||||
"ultron": {
|
||||
"version": "1.0.2",
|
||||
"from": "ultron@>=1.0.0 <1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/ultron/-/ultron-1.0.2.tgz"
|
||||
},
|
||||
"bufferutil": {
|
||||
"version": "1.1.0",
|
||||
"from": "bufferutil@>=1.1.0 <1.2.0",
|
||||
"resolved": "https://registry.npmjs.org/bufferutil/-/bufferutil-1.1.0.tgz",
|
||||
"dependencies": {
|
||||
"bindings": {
|
||||
"version": "1.2.1",
|
||||
"from": "bindings@>=1.2.0 <1.3.0",
|
||||
"resolved": "https://registry.npmjs.org/bindings/-/bindings-1.2.1.tgz"
|
||||
},
|
||||
"nan": {
|
||||
"version": "1.8.4",
|
||||
"from": "nan@>=1.8.0 <1.9.0",
|
||||
"resolved": "https://registry.npmjs.org/nan/-/nan-1.8.4.tgz"
|
||||
}
|
||||
}
|
||||
},
|
||||
"utf-8-validate": {
|
||||
"version": "1.1.0",
|
||||
"from": "utf-8-validate@>=1.1.0 <1.2.0",
|
||||
"resolved": "https://registry.npmjs.org/utf-8-validate/-/utf-8-validate-1.1.0.tgz",
|
||||
"dependencies": {
|
||||
"bindings": {
|
||||
"version": "1.2.1",
|
||||
"from": "bindings@>=1.2.0 <1.3.0",
|
||||
"resolved": "https://registry.npmjs.org/bindings/-/bindings-1.2.1.tgz"
|
||||
},
|
||||
"nan": {
|
||||
"version": "1.8.4",
|
||||
"from": "nan@>=1.8.0 <1.9.0",
|
||||
"resolved": "https://registry.npmjs.org/nan/-/nan-1.8.4.tgz"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
"from": "x-address-codec@>=0.7.0 <0.8.0",
|
||||
"resolved": "https://registry.npmjs.org/x-address-codec/-/x-address-codec-0.7.2.tgz"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
46
package.json
46
package.json
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "ripple-lib",
|
||||
"version": "0.13.2",
|
||||
"version": "0.17.7",
|
||||
"license": "ISC",
|
||||
"description": "A JavaScript API for interacting with Ripple in Node.js and the browser",
|
||||
"files": [
|
||||
@@ -15,40 +15,48 @@
|
||||
"test": "test"
|
||||
},
|
||||
"dependencies": {
|
||||
"ajv": "^1.4.8",
|
||||
"babel-polyfill": "^6.2.0",
|
||||
"babel-runtime": "^5.5.4",
|
||||
"babel-polyfill": "^6.3.14",
|
||||
"babel-runtime": "^6.3.19",
|
||||
"bignumber.js": "^2.0.3",
|
||||
"https-proxy-agent": "^1.0.0",
|
||||
"jsonschema": "^1.1.1",
|
||||
"lodash": "^3.1.0",
|
||||
"ripple-address-codec": "^2.0.1",
|
||||
"ripple-binary-codec": "^0.1.0",
|
||||
"ripple-hashes": "^0.1.0",
|
||||
"ripple-binary-codec": "^0.1.10",
|
||||
"ripple-hashes": "^0.3.0",
|
||||
"ripple-keypairs": "^0.10.0",
|
||||
"ripple-lib-transactionparser": "^0.6.0",
|
||||
"ws": "^0.7.1"
|
||||
"ws": "^1.0.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"assert-diff": "^1.0.1",
|
||||
"babel": "^5.8.21",
|
||||
"babel-core": "^5.8.22",
|
||||
"babel-eslint": "^4.1.3",
|
||||
"babel-loader": "^5.3.2",
|
||||
"coveralls": "^2.10.0",
|
||||
"babel-cli": "^6.4.0",
|
||||
"babel-core": "^6.4.0",
|
||||
"babel-eslint": "^6.0.4",
|
||||
"babel-loader": "^6.2.1",
|
||||
"babel-plugin-syntax-flow": "^6.3.13",
|
||||
"babel-plugin-transform-flow-strip-types": "^6.4.0",
|
||||
"babel-preset-es2015": "^6.3.13",
|
||||
"babel-preset-stage-1": "^6.3.13",
|
||||
"babel-register": "^6.3.13",
|
||||
"coveralls": "^2.11.9",
|
||||
"doctoc": "^0.15.0",
|
||||
"ejs": "^2.3.4",
|
||||
"eslint": "^1.3.0",
|
||||
"eslint-plugin-flowtype": "^1.0.0",
|
||||
"eslint": "^2.9.0",
|
||||
"eventemitter2": "^0.4.14",
|
||||
"flow-bin": "^0.14",
|
||||
"gulp": "^3.8.10",
|
||||
"gulp-bump": "^0.1.13",
|
||||
"gulp-rename": "^1.2.0",
|
||||
"gulp-uglify": "^1.1.0",
|
||||
"istanbul": "^0.3.5",
|
||||
"http-server": "^0.8.5",
|
||||
"istanbul": "^1.1.0-alpha.1",
|
||||
"jayson": "^1.2.2",
|
||||
"json-loader": "^0.5.2",
|
||||
"json-schema-to-markdown-table": "^0.4.0",
|
||||
"mocha": "^2.1.0",
|
||||
"mocha-in-sauce": "^0.0.1",
|
||||
"mocha-junit-reporter": "^1.9.1",
|
||||
"null-loader": "^0.1.1",
|
||||
"webpack": "^1.5.3",
|
||||
"yargs": "^1.3.1"
|
||||
},
|
||||
@@ -62,10 +70,12 @@
|
||||
"watch": "babel -w -D --optional runtime -d dist/npm/ src/",
|
||||
"compile-with-source-maps": "babel -D --optional runtime -s -t -d dist/npm/ src/",
|
||||
"prepublish": "npm run clean && npm run compile",
|
||||
"test": "istanbul test _mocha",
|
||||
"test": "babel-node ./node_modules/.bin/istanbul cover ./node_modules/mocha/bin/_mocha",
|
||||
"coveralls": "cat ./coverage/lcov.info | coveralls",
|
||||
"lint": "if ! [ -f eslintrc ]; then curl -o eslintrc 'https://raw.githubusercontent.com/ripple/javascript-style-guide/es6/eslintrc'; echo 'parser: babel-eslint' >> eslintrc; fi; eslint -c eslintrc src/",
|
||||
"perf": "./scripts/perf_test.sh"
|
||||
"perf": "./scripts/perf_test.sh",
|
||||
"start": "babel-node scripts/http.js",
|
||||
"sauce": "babel-node scripts/sauce-runner.js"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
||||
18
scripts/checkeol.sh
Executable file
18
scripts/checkeol.sh
Executable file
@@ -0,0 +1,18 @@
|
||||
#!/bin/bash
|
||||
|
||||
function checkEOL {
|
||||
local changedFiles=$(git --no-pager diff --name-only -M100% --diff-filter=AM --relative $(git merge-base FETCH_HEAD origin/HEAD) FETCH_HEAD)
|
||||
local result=0
|
||||
for name in $changedFiles; do
|
||||
grep -c -U -q $'\r' $name
|
||||
if [ $? -eq 0 ]; then
|
||||
echo "windows eol found in $name" >&2
|
||||
result=1
|
||||
fi
|
||||
done
|
||||
if [ $result -eq 1 ]; then
|
||||
false
|
||||
fi
|
||||
}
|
||||
|
||||
checkEOL
|
||||
@@ -3,6 +3,10 @@
|
||||
NODE_INDEX="$1"
|
||||
TOTAL_NODES="$2"
|
||||
|
||||
function checkEOL {
|
||||
./scripts/checkeol.sh
|
||||
}
|
||||
|
||||
typecheck() {
|
||||
npm install -g flow-bin
|
||||
flow --version
|
||||
@@ -11,7 +15,7 @@ typecheck() {
|
||||
|
||||
lint() {
|
||||
echo "eslint $(node_modules/.bin/eslint --version)"
|
||||
npm list babel-eslint | grep babel-eslint
|
||||
npm list babel-eslint
|
||||
REPO_URL="https://raw.githubusercontent.com/ripple/javascript-style-guide"
|
||||
curl "$REPO_URL/es6/eslintrc" > ./eslintrc
|
||||
echo "parser: babel-eslint" >> ./eslintrc
|
||||
@@ -20,6 +24,7 @@ lint() {
|
||||
|
||||
unittest() {
|
||||
# test "src"
|
||||
mocha test --reporter mocha-junit-reporter --reporter-options mochaFile=$CIRCLE_TEST_REPORTS/test-results.xml
|
||||
npm test --coverage
|
||||
npm run coveralls
|
||||
|
||||
@@ -29,11 +34,33 @@ unittest() {
|
||||
mkdir -p test-compiled/node_modules
|
||||
ln -nfs ../../dist/npm test-compiled/node_modules/ripple-api
|
||||
mocha --opts test-compiled/mocha.opts test-compiled
|
||||
|
||||
#compile tests for browser testing
|
||||
#gulp build-min build-tests
|
||||
#node --harmony test-compiled/mocked-server.js > /dev/null &
|
||||
|
||||
#echo "Running tests in PhantomJS"
|
||||
#mocha-phantomjs test/localrunner.html
|
||||
#echo "Running tests using minified version in PhantomJS"
|
||||
#mocha-phantomjs test/localrunnermin.html
|
||||
|
||||
#echo "Running tests in SauceLabs"
|
||||
#http-server &
|
||||
#npm run sauce
|
||||
|
||||
#pkill -f mocked-server.js
|
||||
#pkill -f http-server
|
||||
rm -rf test-compiled
|
||||
}
|
||||
|
||||
integrationtest() {
|
||||
mocha test/integration/integration-test.js
|
||||
mocha test/integration/http-integration-test.js
|
||||
|
||||
# run integration tests in PhantomJS
|
||||
#gulp build-tests build-min
|
||||
#echo "Running integragtion tests in PhantomJS"
|
||||
#mocha-phantomjs test/localintegrationrunner.html
|
||||
}
|
||||
|
||||
doctest() {
|
||||
@@ -46,9 +73,9 @@ doctest() {
|
||||
}
|
||||
|
||||
oneNode() {
|
||||
checkEOL
|
||||
doctest
|
||||
lint
|
||||
typecheck
|
||||
unittest
|
||||
integrationtest
|
||||
}
|
||||
@@ -56,7 +83,7 @@ oneNode() {
|
||||
twoNodes() {
|
||||
case "$NODE_INDEX" in
|
||||
0) doctest; lint; integrationtest;;
|
||||
1) typecheck; unittest;;
|
||||
1) checkEOL; unittest;;
|
||||
*) echo "ERROR: invalid usage"; exit 2;;
|
||||
esac
|
||||
}
|
||||
@@ -64,7 +91,7 @@ twoNodes() {
|
||||
threeNodes() {
|
||||
case "$NODE_INDEX" in
|
||||
0) doctest; lint; integrationtest;;
|
||||
1) typecheck;;
|
||||
1) checkEOL;;
|
||||
2) unittest;;
|
||||
*) echo "ERROR: invalid usage"; exit 2;;
|
||||
esac
|
||||
|
||||
16
scripts/http.js
Normal file
16
scripts/http.js
Normal file
@@ -0,0 +1,16 @@
|
||||
'use strict';
|
||||
|
||||
const createHTTPServer = require('../src/http').createHTTPServer;
|
||||
const port = 5990;
|
||||
const serverUrl = 'wss://s1.ripple.com';
|
||||
|
||||
|
||||
function main() {
|
||||
const server = createHTTPServer({server: serverUrl}, port);
|
||||
server.start().then(() => {
|
||||
console.log('Server started on port ' + String(port));
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
main();
|
||||
@@ -16,28 +16,3 @@ echo ""
|
||||
echo "publish to npm"
|
||||
npm publish
|
||||
exit_on_error
|
||||
|
||||
rm -rf dist/bower
|
||||
echo ""
|
||||
echo "publish to bower"
|
||||
|
||||
git clone git@github.com:ripple/bower-ripple.git dist/bower
|
||||
gulp bower
|
||||
exit_on_error
|
||||
|
||||
cd dist/bower
|
||||
version=$(cat bower.json | grep -Eo '([0-9]\.?)+(-rc([0-9])+)?')
|
||||
echo "version: $version"
|
||||
git add ripple.js ripple-debug.js ripple-min.js bower.json
|
||||
exit_on_error
|
||||
|
||||
git commit -m "[TASK] add v$version"
|
||||
exit_on_error
|
||||
|
||||
git tag "v$version"
|
||||
exit_on_error
|
||||
|
||||
git push origin master
|
||||
git push --tags origin master
|
||||
|
||||
cd ../..
|
||||
|
||||
@@ -16,28 +16,3 @@ echo ""
|
||||
echo "publish rc to npm"
|
||||
npm publish --tag beta
|
||||
exit_on_error
|
||||
|
||||
rm -rf dist/bower
|
||||
echo ""
|
||||
echo "publish to bower"
|
||||
|
||||
git clone git@github.com:ripple/bower-ripple.git dist/bower
|
||||
gulp bower
|
||||
exit_on_error
|
||||
|
||||
cd dist/bower
|
||||
version=$(cat bower.json | grep -Eo '([0-9]\.?)+(-rc([0-9])+)?')
|
||||
echo "version: $version"
|
||||
git add ripple.js ripple-debug.js ripple-min.js bower.json
|
||||
exit_on_error
|
||||
|
||||
git commit -m "[TASK] add v$version"
|
||||
exit_on_error
|
||||
|
||||
git tag "v$version"
|
||||
exit_on_error
|
||||
|
||||
git push origin master
|
||||
git push --tags origin master
|
||||
|
||||
cd ../..
|
||||
|
||||
@@ -1,12 +0,0 @@
|
||||
rm -rf dist/bower
|
||||
git clone git@github.com:ripple/bower-ripple.git dist/bower
|
||||
gulp bower
|
||||
cd dist/bower
|
||||
version=$(cat bower.json | grep -Eo '([0-9]\.?)+(-rc[0-9])?')
|
||||
echo "version: $version"
|
||||
git add ripple.js ripple-debug.js ripple-min.js bower.json
|
||||
git commit -m "[TASK] add v$version"
|
||||
git tag "v$version"
|
||||
git push origin master
|
||||
git push --tags origin master
|
||||
cd ..
|
||||
100
scripts/sauce-runner.js
Normal file
100
scripts/sauce-runner.js
Normal file
@@ -0,0 +1,100 @@
|
||||
|
||||
const _ = require('lodash');
|
||||
const MochaSauce = require('mocha-in-sauce');
|
||||
|
||||
const testUrl = 'http://testripple.circleci.com:8080/test/saucerunner.html';
|
||||
|
||||
|
||||
function main() {
|
||||
// uncomment for more debug info
|
||||
// process.env.DEBUG = '*';
|
||||
|
||||
// configure
|
||||
const config = {
|
||||
name: 'RippleAPI',
|
||||
host: 'localhost',
|
||||
port: 4445,
|
||||
maxDuration: 180000,
|
||||
// the current build name (optional)
|
||||
build: Date.now(),
|
||||
url: testUrl,
|
||||
runSauceConnect: true
|
||||
};
|
||||
|
||||
if (process.env.CIRCLE_BUILD_NUM) {
|
||||
config.build = process.env.CIRCLE_BUILD_NUM;
|
||||
config.tags = [process.env.CIRCLE_BRANCH, process.env.CIRCLE_SHA1];
|
||||
config.tunnelIdentifier = process.env.CIRCLE_BUILD_NUM;
|
||||
}
|
||||
|
||||
const sauce = new MochaSauce(config);
|
||||
|
||||
sauce.concurrency(5);
|
||||
|
||||
// setup what browsers to test with
|
||||
sauce.browser({browserName: 'firefox', platform: 'Linux',
|
||||
version: '43'});
|
||||
sauce.browser({browserName: 'firefox', platform: 'Windows 8.1',
|
||||
version: '43'});
|
||||
sauce.browser({browserName: 'firefox', platform: 'OS X 10.11',
|
||||
version: '43'});
|
||||
sauce.browser({browserName: 'safari', platform: 'OS X 10.11',
|
||||
version: '9'});
|
||||
sauce.browser({browserName: 'safari', platform: 'OS X 10.10',
|
||||
version: '8'});
|
||||
sauce.browser({browserName: 'safari', platform: 'OS X 10.9',
|
||||
version: '7'});
|
||||
sauce.browser({browserName: 'chrome', platform: 'OS X 10.11',
|
||||
version: '47'});
|
||||
sauce.browser({browserName: 'chrome', platform: 'Linux',
|
||||
version: '47'});
|
||||
sauce.browser({browserName: 'chrome', platform: 'Windows 8.1',
|
||||
version: '47'});
|
||||
sauce.browser({browserName: 'internet explorer', platform: 'Windows 10',
|
||||
version: '11'});
|
||||
sauce.browser({browserName: 'MicrosoftEdge', platform: 'Windows 10',
|
||||
version: '20'});
|
||||
|
||||
sauce.on('init', function(browser) {
|
||||
console.log(' init : %s %s', browser.browserName, browser.platform);
|
||||
});
|
||||
|
||||
sauce.on('start', function(browser) {
|
||||
console.log(' start : %s %s', browser.browserName, browser.platform);
|
||||
});
|
||||
|
||||
sauce.on('end', function(browser, res) {
|
||||
console.log(' end : %s %s : %d failures', browser.browserName,
|
||||
browser.platform, res && res.failures);
|
||||
});
|
||||
|
||||
sauce.on('connected', sauceConnectProcess => {
|
||||
sauceConnectProcess.on('exit', function(code, /* signal */) {
|
||||
if (code > 0) {
|
||||
console.log('something wrong - exiting');
|
||||
process.exit();
|
||||
} else {
|
||||
console.log('normal tunnel exit');
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
sauce.start(function(err, res) {
|
||||
let failure = false;
|
||||
if (err) {
|
||||
console.log('Error starting Sauce');
|
||||
console.error(err);
|
||||
process.exitCode = 2;
|
||||
} else {
|
||||
console.log('-------------- done --------------');
|
||||
failure = _.some(res, 'failures');
|
||||
console.log('Tests are failed:', failure);
|
||||
if (failure) {
|
||||
process.exitCode = 1;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
main();
|
||||
170
src/api.js
Normal file
170
src/api.js
Normal file
@@ -0,0 +1,170 @@
|
||||
/* @flow */
|
||||
'use strict' // eslint-disable-line strict
|
||||
|
||||
/* eslint-disable max-len */
|
||||
// Enable core-js polyfills. This allows use of ES6/7 extensions listed here:
|
||||
// https://github.com/zloirock/core-js/blob/fb0890f32dabe8d4d88a4350d1b268446127132e/shim.js#L1-L103
|
||||
/* eslint-enable max-len */
|
||||
|
||||
// In node.js env, polyfill might be already loaded (from any npm package),
|
||||
// that's why we do this check.
|
||||
if (!global._babelPolyfill) {
|
||||
require('babel-polyfill')
|
||||
}
|
||||
|
||||
const _ = require('lodash')
|
||||
const EventEmitter = require('events').EventEmitter
|
||||
const common = require('./common')
|
||||
const server = require('./server/server')
|
||||
const connect = server.connect
|
||||
const disconnect = server.disconnect
|
||||
const getServerInfo = server.getServerInfo
|
||||
const getFee = server.getFee
|
||||
const isConnected = server.isConnected
|
||||
const getLedgerVersion = server.getLedgerVersion
|
||||
const getTransaction = require('./ledger/transaction')
|
||||
const getTransactions = require('./ledger/transactions')
|
||||
const getTrustlines = require('./ledger/trustlines')
|
||||
const getBalances = require('./ledger/balances')
|
||||
const getBalanceSheet = require('./ledger/balance-sheet')
|
||||
const getPaths = require('./ledger/pathfind')
|
||||
const getOrders = require('./ledger/orders')
|
||||
const getOrderbook = require('./ledger/orderbook')
|
||||
const getSettings = require('./ledger/settings')
|
||||
const getAccountInfo = require('./ledger/accountinfo')
|
||||
const getPaymentChannel = require('./ledger/payment-channel')
|
||||
const preparePayment = require('./transaction/payment')
|
||||
const prepareTrustline = require('./transaction/trustline')
|
||||
const prepareOrder = require('./transaction/order')
|
||||
const prepareOrderCancellation = require('./transaction/ordercancellation')
|
||||
const prepareEscrowCreation =
|
||||
require('./transaction/escrow-creation')
|
||||
const prepareEscrowExecution =
|
||||
require('./transaction/escrow-execution')
|
||||
const prepareEscrowCancellation =
|
||||
require('./transaction/escrow-cancellation')
|
||||
const preparePaymentChannelCreate =
|
||||
require('./transaction/payment-channel-create')
|
||||
const preparePaymentChannelFund =
|
||||
require('./transaction/payment-channel-fund')
|
||||
const preparePaymentChannelClaim =
|
||||
require('./transaction/payment-channel-claim')
|
||||
const prepareSettings = require('./transaction/settings')
|
||||
const sign = require('./transaction/sign')
|
||||
const combine = require('./transaction/combine')
|
||||
const submit = require('./transaction/submit')
|
||||
const errors = require('./common').errors
|
||||
const generateAddress =
|
||||
require('./offline/generate-address').generateAddressAPI
|
||||
const computeLedgerHash = require('./offline/ledgerhash')
|
||||
const signPaymentChannelClaim =
|
||||
require('./offline/sign-payment-channel-claim')
|
||||
const verifyPaymentChannelClaim =
|
||||
require('./offline/verify-payment-channel-claim')
|
||||
const getLedger = require('./ledger/ledger')
|
||||
|
||||
type APIOptions = {
|
||||
server?: string,
|
||||
feeCushion?: number,
|
||||
trace?: boolean,
|
||||
proxy?: string,
|
||||
timeout?: number
|
||||
}
|
||||
|
||||
// prevent access to non-validated ledger versions
|
||||
class RestrictedConnection extends common.Connection {
|
||||
request(request, timeout) {
|
||||
const ledger_index = request.ledger_index
|
||||
if (ledger_index !== undefined && ledger_index !== 'validated') {
|
||||
if (!_.isNumber(ledger_index) || ledger_index > this._ledgerVersion) {
|
||||
return Promise.reject(new errors.LedgerVersionError(
|
||||
`ledgerVersion ${ledger_index} is greater than server\'s ` +
|
||||
`most recent validated ledger: ${this._ledgerVersion}`))
|
||||
}
|
||||
}
|
||||
return super.request(request, timeout)
|
||||
}
|
||||
}
|
||||
|
||||
class RippleAPI extends EventEmitter {
|
||||
constructor(options: APIOptions = {}) {
|
||||
common.validate.apiOptions(options)
|
||||
super()
|
||||
this._feeCushion = options.feeCushion || 1.2
|
||||
const serverURL = options.server
|
||||
if (serverURL !== undefined) {
|
||||
this.connection = new RestrictedConnection(serverURL, options)
|
||||
this.connection.on('ledgerClosed', message => {
|
||||
this.emit('ledger', server.formatLedgerClose(message))
|
||||
})
|
||||
this.connection.on('error', (errorCode, errorMessage, data) => {
|
||||
this.emit('error', errorCode, errorMessage, data)
|
||||
})
|
||||
this.connection.on('connected', () => {
|
||||
this.emit('connected')
|
||||
})
|
||||
this.connection.on('disconnected', code => {
|
||||
this.emit('disconnected', code)
|
||||
})
|
||||
} else {
|
||||
// use null object pattern to provide better error message if user
|
||||
// tries to call a method that requires a connection
|
||||
this.connection = new RestrictedConnection(null, options)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_.assign(RippleAPI.prototype, {
|
||||
connect,
|
||||
disconnect,
|
||||
isConnected,
|
||||
getServerInfo,
|
||||
getFee,
|
||||
getLedgerVersion,
|
||||
|
||||
getTransaction,
|
||||
getTransactions,
|
||||
getTrustlines,
|
||||
getBalances,
|
||||
getBalanceSheet,
|
||||
getPaths,
|
||||
getOrders,
|
||||
getOrderbook,
|
||||
getSettings,
|
||||
getAccountInfo,
|
||||
getPaymentChannel,
|
||||
getLedger,
|
||||
|
||||
preparePayment,
|
||||
prepareTrustline,
|
||||
prepareOrder,
|
||||
prepareOrderCancellation,
|
||||
prepareEscrowCreation,
|
||||
prepareEscrowExecution,
|
||||
prepareEscrowCancellation,
|
||||
preparePaymentChannelCreate,
|
||||
preparePaymentChannelFund,
|
||||
preparePaymentChannelClaim,
|
||||
prepareSettings,
|
||||
sign,
|
||||
combine,
|
||||
submit,
|
||||
|
||||
generateAddress,
|
||||
computeLedgerHash,
|
||||
signPaymentChannelClaim,
|
||||
verifyPaymentChannelClaim,
|
||||
errors
|
||||
})
|
||||
|
||||
// these are exposed only for use by unit tests; they are not part of the API
|
||||
RippleAPI._PRIVATE = {
|
||||
validate: common.validate,
|
||||
RangeSet: require('./common/rangeset').RangeSet,
|
||||
ledgerUtils: require('./ledger/utils'),
|
||||
schemaValidator: require('./common/schema-validator')
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
RippleAPI
|
||||
}
|
||||
70
src/broadcast.js
Normal file
70
src/broadcast.js
Normal file
@@ -0,0 +1,70 @@
|
||||
'use strict' // eslint-disable-line strict
|
||||
const _ = require('lodash')
|
||||
const RippleAPI = require('./api').RippleAPI
|
||||
|
||||
class RippleAPIBroadcast extends RippleAPI {
|
||||
constructor(servers, options) {
|
||||
super(options)
|
||||
this.ledgerVersion = 0
|
||||
|
||||
const apis = servers.map(server => new RippleAPI(
|
||||
_.assign({}, options, {server})
|
||||
))
|
||||
|
||||
// exposed for testing
|
||||
this._apis = apis
|
||||
|
||||
this.getMethodNames().forEach(name => {
|
||||
this[name] = function() { // eslint-disable-line no-loop-func
|
||||
return Promise.race(apis.map(api => api[name](...arguments)))
|
||||
}
|
||||
})
|
||||
|
||||
// connection methods must be overridden to apply to all api instances
|
||||
this.connect = function() {
|
||||
return Promise.all(apis.map(api => api.connect()))
|
||||
}
|
||||
this.disconnect = function() {
|
||||
return Promise.all(apis.map(api => api.disconnect()))
|
||||
}
|
||||
this.isConnected = function() {
|
||||
return _.every(apis.map(api => api.isConnected()))
|
||||
}
|
||||
|
||||
// synchronous methods are all passed directly to the first api instance
|
||||
const defaultAPI = apis[0]
|
||||
const syncMethods = ['sign', 'generateAddress', 'computeLedgerHash']
|
||||
syncMethods.forEach(name => {
|
||||
this[name] = defaultAPI[name].bind(defaultAPI)
|
||||
})
|
||||
|
||||
apis.forEach(api => {
|
||||
api.on('ledger', this.onLedgerEvent.bind(this))
|
||||
api.on('error', (errorCode, errorMessage, data) =>
|
||||
this.emit('error', errorCode, errorMessage, data))
|
||||
})
|
||||
}
|
||||
|
||||
onLedgerEvent(ledger) {
|
||||
if (ledger.ledgerVersion > this.ledgerVersion) {
|
||||
this.ledgerVersion = ledger.ledgerVersion
|
||||
this.emit('ledger', ledger)
|
||||
}
|
||||
}
|
||||
|
||||
getMethodNames() {
|
||||
const methodNames = []
|
||||
for (const name in RippleAPI.prototype) {
|
||||
if (RippleAPI.prototype.hasOwnProperty(name)) {
|
||||
if (typeof RippleAPI.prototype[name] === 'function') {
|
||||
methodNames.push(name)
|
||||
}
|
||||
}
|
||||
}
|
||||
return methodNames
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
RippleAPIBroadcast
|
||||
}
|
||||
21
src/common/browser-hacks.js
Normal file
21
src/common/browser-hacks.js
Normal file
@@ -0,0 +1,21 @@
|
||||
'use strict' // eslint-disable-line strict
|
||||
|
||||
function setPrototypeOf(object, prototype) {
|
||||
// Object.setPrototypeOf not supported on Internet Explorer 9
|
||||
/* eslint-disable */
|
||||
Object.setPrototypeOf ? Object.setPrototypeOf(object, prototype) :
|
||||
object.__proto__ = prototype;
|
||||
/* eslint-enable */
|
||||
}
|
||||
|
||||
function getConstructorName(object) {
|
||||
// hack for internet explorer
|
||||
return process.browser ?
|
||||
object.constructor.toString().match(/^function\s+([^(]*)/)[1] :
|
||||
object.constructor.name
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
getConstructorName,
|
||||
setPrototypeOf
|
||||
}
|
||||
@@ -1,256 +1,449 @@
|
||||
'use strict';
|
||||
const {EventEmitter} = require('events');
|
||||
const WebSocket = require('ws');
|
||||
const parseURL = require('url').parse;
|
||||
const RangeSet = require('./rangeset').RangeSet;
|
||||
'use strict' // eslint-disable-line strict
|
||||
|
||||
const _ = require('lodash')
|
||||
const {EventEmitter} = require('events')
|
||||
const WebSocket = require('ws')
|
||||
const parseURL = require('url').parse
|
||||
const RangeSet = require('./rangeset').RangeSet
|
||||
const {RippledError, DisconnectedError, NotConnectedError,
|
||||
TimeoutError, ResponseFormatError, ConnectionError} = require('./errors');
|
||||
TimeoutError, ResponseFormatError, ConnectionError,
|
||||
RippledNotInitializedError} = require('./errors')
|
||||
|
||||
function isStreamMessageType(type) {
|
||||
return type === 'ledgerClosed' ||
|
||||
type === 'transaction' ||
|
||||
type === 'path_find';
|
||||
type === 'path_find'
|
||||
}
|
||||
|
||||
class Connection extends EventEmitter {
|
||||
constructor(url, options = {}) {
|
||||
super();
|
||||
this._url = url;
|
||||
this._proxyURL = options.proxyURL;
|
||||
this._authorization = options.authorization;
|
||||
this._timeout = options.timeout || (20 * 1000);
|
||||
this._isReady = false;
|
||||
this._ws = null;
|
||||
this._ledgerVersion = null;
|
||||
this._availableLedgerVersions = new RangeSet();
|
||||
this._nextRequestID = 1;
|
||||
super()
|
||||
this.setMaxListeners(Infinity)
|
||||
this._url = url
|
||||
this._trace = options.trace
|
||||
if (this._trace) {
|
||||
// for easier unit testing
|
||||
this._console = console
|
||||
}
|
||||
this._proxyURL = options.proxy
|
||||
this._proxyAuthorization = options.proxyAuthorization
|
||||
this._authorization = options.authorization
|
||||
this._trustedCertificates = options.trustedCertificates
|
||||
this._key = options.key
|
||||
this._passphrase = options.passphrase
|
||||
this._certificate = options.certificate
|
||||
this._timeout = options.timeout || (20 * 1000)
|
||||
this._isReady = false
|
||||
this._ws = null
|
||||
this._ledgerVersion = null
|
||||
this._availableLedgerVersions = new RangeSet()
|
||||
this._nextRequestID = 1
|
||||
this._retry = 0
|
||||
this._retryTimer = null
|
||||
this._onOpenErrorBound = null
|
||||
this._onUnexpectedCloseBound = null
|
||||
this._fee_base = null
|
||||
this._fee_ref = null
|
||||
}
|
||||
|
||||
_updateLedgerVersions(data) {
|
||||
this._ledgerVersion = Number(data.ledger_index)
|
||||
if (data.validated_ledgers) {
|
||||
this._availableLedgerVersions.reset()
|
||||
this._availableLedgerVersions.parseAndAddRanges(
|
||||
data.validated_ledgers)
|
||||
} else {
|
||||
this._availableLedgerVersions.addValue(this._ledgerVersion)
|
||||
}
|
||||
}
|
||||
|
||||
_updateFees(data) {
|
||||
this._fee_base = Number(data.fee_base)
|
||||
this._fee_ref = Number(data.fee_ref)
|
||||
}
|
||||
|
||||
// return value is array of arguments to Connection.emit
|
||||
_parseMessage(message) {
|
||||
const data = JSON.parse(message);
|
||||
const data = JSON.parse(message)
|
||||
if (data.type === 'response') {
|
||||
if (!(Number.isInteger(data.id) && data.id >= 0)) {
|
||||
throw new ResponseFormatError('valid id not found in response');
|
||||
throw new ResponseFormatError('valid id not found in response')
|
||||
}
|
||||
return [data.id.toString(), data];
|
||||
return [data.id.toString(), data]
|
||||
} else if (isStreamMessageType(data.type)) {
|
||||
if (data.type === 'ledgerClosed') {
|
||||
this._ledgerVersion = Number(data.ledger_index);
|
||||
this._availableLedgerVersions.reset();
|
||||
this._availableLedgerVersions.parseAndAddRanges(
|
||||
data.validated_ledgers);
|
||||
this._updateLedgerVersions(data)
|
||||
this._updateFees(data)
|
||||
}
|
||||
return [data.type, data];
|
||||
return [data.type, data]
|
||||
} else if (data.type === undefined && data.error) {
|
||||
return ['error', data.error, data.error_message]; // e.g. slowDown
|
||||
return ['error', data.error, data.error_message, data] // e.g. slowDown
|
||||
}
|
||||
throw new ResponseFormatError('unrecognized message type: ' + data.type);
|
||||
throw new ResponseFormatError('unrecognized message type: ' + data.type)
|
||||
}
|
||||
|
||||
_onMessage(message) {
|
||||
let parameters;
|
||||
let parameters
|
||||
if (this._trace) {
|
||||
this._console.log(message)
|
||||
}
|
||||
try {
|
||||
parameters = this._parseMessage(message);
|
||||
parameters = this._parseMessage(message)
|
||||
} catch (error) {
|
||||
this.emit('error', 'badMessage', message);
|
||||
return;
|
||||
this.emit('error', 'badMessage', error.message, message)
|
||||
return
|
||||
}
|
||||
// we don't want this inside the try/catch or exceptions in listener
|
||||
// will be caught
|
||||
this.emit.apply(this, parameters);
|
||||
this.emit(...parameters)
|
||||
}
|
||||
|
||||
get _state() {
|
||||
return this._ws ? this._ws.readyState : WebSocket.CLOSED;
|
||||
return this._ws ? this._ws.readyState : WebSocket.CLOSED
|
||||
}
|
||||
|
||||
get _shouldBeConnected() {
|
||||
return this._ws !== null;
|
||||
return this._ws !== null
|
||||
}
|
||||
|
||||
isConnected() {
|
||||
return this._state === WebSocket.OPEN && this._isReady;
|
||||
return this._state === WebSocket.OPEN && this._isReady
|
||||
}
|
||||
|
||||
_onUnexpectedClose() {
|
||||
this._isReady = false;
|
||||
this.connect().then();
|
||||
_onUnexpectedClose(beforeOpen, resolve, reject, code) {
|
||||
if (this._onOpenErrorBound) {
|
||||
this._ws.removeListener('error', this._onOpenErrorBound)
|
||||
this._onOpenErrorBound = null
|
||||
}
|
||||
// just in case
|
||||
this._ws.removeAllListeners('open')
|
||||
this._ws = null
|
||||
this._isReady = false
|
||||
if (beforeOpen) {
|
||||
// connection was closed before it was properly opened, so we must return
|
||||
// error to connect's caller
|
||||
this.connect().then(resolve, reject)
|
||||
} else {
|
||||
// if first parameter ws lib sends close code,
|
||||
// but sometimes it forgots about it, so default to 1006 - CLOSE_ABNORMAL
|
||||
this.emit('disconnected', code || 1006)
|
||||
this._retryConnect()
|
||||
}
|
||||
}
|
||||
|
||||
_calculateTimeout(retriesCount) {
|
||||
return (retriesCount < 40)
|
||||
// First, for 2 seconds: 20 times per second
|
||||
? (1000 / 20)
|
||||
: (retriesCount < 40 + 60)
|
||||
// Then, for 1 minute: once per second
|
||||
? (1000)
|
||||
: (retriesCount < 40 + 60 + 60)
|
||||
// Then, for 10 minutes: once every 10 seconds
|
||||
? (10 * 1000)
|
||||
// Then: once every 30 seconds
|
||||
: (30 * 1000)
|
||||
}
|
||||
|
||||
_retryConnect() {
|
||||
this._retry += 1
|
||||
const retryTimeout = this._calculateTimeout(this._retry)
|
||||
this._retryTimer = setTimeout(() => {
|
||||
this.emit('reconnecting', this._retry)
|
||||
this.connect().catch(this._retryConnect.bind(this))
|
||||
}, retryTimeout)
|
||||
}
|
||||
|
||||
_clearReconnectTimer() {
|
||||
clearTimeout(this._retryTimer)
|
||||
this._retryTimer = null
|
||||
}
|
||||
|
||||
_onOpen() {
|
||||
if (!this._ws) {
|
||||
return Promise.reject(new DisconnectedError())
|
||||
}
|
||||
if (this._onOpenErrorBound) {
|
||||
this._ws.removeListener('error', this._onOpenErrorBound)
|
||||
this._onOpenErrorBound = null
|
||||
}
|
||||
|
||||
const request = {
|
||||
command: 'subscribe',
|
||||
streams: ['ledger']
|
||||
};
|
||||
return this.request(request).then(response => {
|
||||
this._ledgerVersion = Number(response.ledger_index);
|
||||
this._availableLedgerVersions.parseAndAddRanges(
|
||||
response.validated_ledgers);
|
||||
this._isReady = true;
|
||||
this.emit('connected');
|
||||
});
|
||||
}
|
||||
return this.request(request).then(data => {
|
||||
if (_.isEmpty(data) || !data.ledger_index) {
|
||||
// rippled instance doesn't have validated ledgers
|
||||
return this._disconnect(false).then(() => {
|
||||
throw new RippledNotInitializedError('Rippled not initialized')
|
||||
})
|
||||
}
|
||||
|
||||
this._updateLedgerVersions(data)
|
||||
this._updateFees(data)
|
||||
this._rebindOnUnxpectedClose()
|
||||
|
||||
this._retry = 0
|
||||
this._ws.on('error', error => {
|
||||
if (process.browser && error && error.type === 'error') {
|
||||
// we are in browser, ignore error - `close` event will be fired
|
||||
// after error
|
||||
return
|
||||
}
|
||||
this.emit('error', 'websocket', error.message, error)
|
||||
})
|
||||
|
||||
this._isReady = true
|
||||
this.emit('connected')
|
||||
|
||||
return undefined
|
||||
})
|
||||
}
|
||||
|
||||
_createWebSocket(url, proxyURL, authorization) {
|
||||
const options = {};
|
||||
if (proxyURL !== undefined) {
|
||||
const parsedURL = parseURL(url);
|
||||
const proxyOptions = parseURL(proxyURL);
|
||||
proxyOptions.secureEndpoint = (parsedURL.protocol === 'wss:');
|
||||
let HttpsProxyAgent;
|
||||
_rebindOnUnxpectedClose() {
|
||||
if (this._onUnexpectedCloseBound) {
|
||||
this._ws.removeListener('close', this._onUnexpectedCloseBound)
|
||||
}
|
||||
this._onUnexpectedCloseBound =
|
||||
this._onUnexpectedClose.bind(this, false, null, null)
|
||||
this._ws.once('close', this._onUnexpectedCloseBound)
|
||||
}
|
||||
|
||||
_unbindOnUnxpectedClose() {
|
||||
if (this._onUnexpectedCloseBound) {
|
||||
this._ws.removeListener('close', this._onUnexpectedCloseBound)
|
||||
}
|
||||
this._onUnexpectedCloseBound = null
|
||||
}
|
||||
|
||||
_onOpenError(reject, error) {
|
||||
this._onOpenErrorBound = null
|
||||
this._unbindOnUnxpectedClose()
|
||||
reject(new NotConnectedError(error && error.message))
|
||||
}
|
||||
|
||||
_createWebSocket() {
|
||||
const options = {}
|
||||
if (this._proxyURL !== undefined) {
|
||||
const parsedURL = parseURL(this._url)
|
||||
const parsedProxyURL = parseURL(this._proxyURL)
|
||||
const proxyOverrides = _.omit({
|
||||
secureEndpoint: (parsedURL.protocol === 'wss:'),
|
||||
secureProxy: (parsedProxyURL.protocol === 'https:'),
|
||||
auth: this._proxyAuthorization,
|
||||
ca: this._trustedCertificates,
|
||||
key: this._key,
|
||||
passphrase: this._passphrase,
|
||||
cert: this._certificate
|
||||
}, _.isUndefined)
|
||||
const proxyOptions = _.assign({}, parsedProxyURL, proxyOverrides)
|
||||
let HttpsProxyAgent
|
||||
try {
|
||||
HttpsProxyAgent = require('https-proxy-agent');
|
||||
HttpsProxyAgent = require('https-proxy-agent')
|
||||
} catch (error) {
|
||||
throw new Error('"proxy" option is not supported in the browser');
|
||||
throw new Error('"proxy" option is not supported in the browser')
|
||||
}
|
||||
options.agent = new HttpsProxyAgent(proxyOptions);
|
||||
options.agent = new HttpsProxyAgent(proxyOptions)
|
||||
}
|
||||
if (authorization !== undefined) {
|
||||
const base64 = new Buffer(authorization).toString('base64');
|
||||
options.headers = {Authorization: `Basic ${base64}`};
|
||||
if (this._authorization !== undefined) {
|
||||
const base64 = new Buffer(this._authorization).toString('base64')
|
||||
options.headers = {Authorization: `Basic ${base64}`}
|
||||
}
|
||||
return new WebSocket(url, options);
|
||||
const optionsOverrides = _.omit({
|
||||
ca: this._trustedCertificates,
|
||||
key: this._key,
|
||||
passphrase: this._passphrase,
|
||||
cert: this._certificate
|
||||
}, _.isUndefined)
|
||||
const websocketOptions = _.assign({}, options, optionsOverrides)
|
||||
const websocket = new WebSocket(this._url, null, websocketOptions)
|
||||
// we will have a listener for each outstanding request,
|
||||
// so we have to raise the limit (the default is 10)
|
||||
if (typeof websocket.setMaxListeners === 'function') {
|
||||
websocket.setMaxListeners(Infinity)
|
||||
}
|
||||
return websocket
|
||||
}
|
||||
|
||||
connect() {
|
||||
this._clearReconnectTimer()
|
||||
return new Promise((resolve, reject) => {
|
||||
if (!this._url) {
|
||||
reject(new ConnectionError(
|
||||
'Cannot connect because no server was specified'));
|
||||
'Cannot connect because no server was specified'))
|
||||
}
|
||||
if (this._state === WebSocket.OPEN) {
|
||||
resolve();
|
||||
resolve()
|
||||
} else if (this._state === WebSocket.CONNECTING) {
|
||||
this._ws.once('open', resolve);
|
||||
this._ws.once('open', resolve)
|
||||
} else {
|
||||
this._ws = this._createWebSocket(this._url, this._proxyURL,
|
||||
this._authorization);
|
||||
this._ws.on('message', this._onMessage.bind(this));
|
||||
this._ws.once('close', () => this._onUnexpectedClose);
|
||||
this._ws.once('open', () => this._onOpen().then(resolve, reject));
|
||||
this._ws = this._createWebSocket()
|
||||
// when an error causes the connection to close, the close event
|
||||
// should still be emitted; the "ws" documentation says: "The close
|
||||
// event is also emitted when then underlying net.Socket closes the
|
||||
// connection (end or close)."
|
||||
// In case if there is connection error (say, server is not responding)
|
||||
// we must return this error to connection's caller. After successful
|
||||
// opening, we will forward all errors to main api object.
|
||||
this._onOpenErrorBound = this._onOpenError.bind(this, reject)
|
||||
this._ws.once('error', this._onOpenErrorBound)
|
||||
this._ws.on('message', this._onMessage.bind(this))
|
||||
// in browser close event can came before open event, so we must
|
||||
// resolve connect's promise after reconnect in that case.
|
||||
// after open event we will rebound _onUnexpectedCloseBound
|
||||
// without resolve and reject functions
|
||||
this._onUnexpectedCloseBound = this._onUnexpectedClose.bind(this, true,
|
||||
resolve, reject)
|
||||
this._ws.once('close', this._onUnexpectedCloseBound)
|
||||
this._ws.once('open', () => this._onOpen().then(resolve, reject))
|
||||
}
|
||||
});
|
||||
})
|
||||
}
|
||||
|
||||
disconnect() {
|
||||
return this._disconnect(true)
|
||||
}
|
||||
|
||||
_disconnect(calledByUser) {
|
||||
if (calledByUser) {
|
||||
this._clearReconnectTimer()
|
||||
this._retry = 0
|
||||
}
|
||||
return new Promise(resolve => {
|
||||
if (this._state === WebSocket.CLOSED) {
|
||||
resolve();
|
||||
resolve()
|
||||
} else if (this._state === WebSocket.CLOSING) {
|
||||
this._ws.once('close', resolve);
|
||||
this._ws.once('close', resolve)
|
||||
} else {
|
||||
this._ws.removeListener('close', this._onUnexpectedClose);
|
||||
this._ws.once('close', () => {
|
||||
this._ws = null;
|
||||
this._isReady = false;
|
||||
resolve();
|
||||
});
|
||||
this._ws.close();
|
||||
if (this._onUnexpectedCloseBound) {
|
||||
this._ws.removeListener('close', this._onUnexpectedCloseBound)
|
||||
this._onUnexpectedCloseBound = null
|
||||
}
|
||||
this._ws.once('close', code => {
|
||||
this._ws = null
|
||||
this._isReady = false
|
||||
if (calledByUser) {
|
||||
this.emit('disconnected', code || 1000) // 1000 - CLOSE_NORMAL
|
||||
}
|
||||
resolve()
|
||||
})
|
||||
this._ws.close()
|
||||
}
|
||||
});
|
||||
})
|
||||
}
|
||||
|
||||
reconnect() {
|
||||
return this.disconnect().then(() => this.connect());
|
||||
return this.disconnect().then(() => this.connect())
|
||||
}
|
||||
|
||||
_whenReady(promise) {
|
||||
return new Promise((resolve, reject) => {
|
||||
if (!this._shouldBeConnected) {
|
||||
reject(new NotConnectedError());
|
||||
reject(new NotConnectedError())
|
||||
} else if (this._state === WebSocket.OPEN && this._isReady) {
|
||||
promise.then(resolve, reject);
|
||||
promise.then(resolve, reject)
|
||||
} else {
|
||||
this.once('connected', () => promise.then(resolve, reject));
|
||||
this.once('connected', () => promise.then(resolve, reject))
|
||||
}
|
||||
});
|
||||
})
|
||||
}
|
||||
|
||||
getLedgerVersion() {
|
||||
return this._whenReady(Promise.resolve(this._ledgerVersion));
|
||||
return this._whenReady(Promise.resolve(this._ledgerVersion))
|
||||
}
|
||||
|
||||
hasLedgerVersions(lowLedgerVersion, highLedgerVersion) {
|
||||
return this._whenReady(Promise.resolve(
|
||||
this._availableLedgerVersions.containsRange(
|
||||
lowLedgerVersion, highLedgerVersion || this._ledgerVersion)));
|
||||
lowLedgerVersion, highLedgerVersion || this._ledgerVersion)))
|
||||
}
|
||||
|
||||
hasLedgerVersion(ledgerVersion) {
|
||||
return this.hasLedgerVersions(ledgerVersion, ledgerVersion);
|
||||
return this.hasLedgerVersions(ledgerVersion, ledgerVersion)
|
||||
}
|
||||
|
||||
getFeeBase() {
|
||||
return this._whenReady(Promise.resolve(Number(this._fee_base)))
|
||||
}
|
||||
|
||||
getFeeRef() {
|
||||
return this._whenReady(Promise.resolve(Number(this._fee_ref)))
|
||||
}
|
||||
|
||||
_send(message) {
|
||||
if (this._trace) {
|
||||
this._console.log(message)
|
||||
}
|
||||
return new Promise((resolve, reject) => {
|
||||
this._ws.send(message, undefined, (error, result) => {
|
||||
if (error) {
|
||||
reject(new DisconnectedError(error.message));
|
||||
reject(new DisconnectedError(error.message))
|
||||
} else {
|
||||
resolve(result);
|
||||
resolve(result)
|
||||
}
|
||||
});
|
||||
});
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
request(request, timeout) {
|
||||
return new Promise((resolve, reject) => {
|
||||
if (!this._shouldBeConnected) {
|
||||
reject(new NotConnectedError());
|
||||
reject(new NotConnectedError())
|
||||
}
|
||||
|
||||
let timer = null;
|
||||
const self = this;
|
||||
const id = this._nextRequestID;
|
||||
this._nextRequestID += 1;
|
||||
const eventName = id.toString();
|
||||
let timer = null
|
||||
const self = this
|
||||
const id = this._nextRequestID
|
||||
this._nextRequestID += 1
|
||||
const eventName = id.toString()
|
||||
|
||||
function onDisconnect() {
|
||||
clearTimeout(timer);
|
||||
self.removeAllListeners(eventName);
|
||||
reject(new DisconnectedError());
|
||||
clearTimeout(timer)
|
||||
self.removeAllListeners(eventName)
|
||||
reject(new DisconnectedError())
|
||||
}
|
||||
|
||||
function cleanup() {
|
||||
clearTimeout(timer);
|
||||
self.removeAllListeners(eventName);
|
||||
clearTimeout(timer)
|
||||
self.removeAllListeners(eventName)
|
||||
if (self._ws !== null) {
|
||||
self._ws.removeListener('close', onDisconnect);
|
||||
self._ws.removeListener('close', onDisconnect)
|
||||
}
|
||||
}
|
||||
|
||||
function _resolve(response) {
|
||||
cleanup();
|
||||
resolve(response);
|
||||
cleanup()
|
||||
resolve(response)
|
||||
}
|
||||
|
||||
function _reject(error) {
|
||||
cleanup();
|
||||
reject(error);
|
||||
cleanup()
|
||||
reject(error)
|
||||
}
|
||||
|
||||
this.once(eventName, response => {
|
||||
if (response.status === 'error') {
|
||||
_reject(new RippledError(response.error));
|
||||
_reject(new RippledError(response.error))
|
||||
} else if (response.status === 'success') {
|
||||
_resolve(response.result);
|
||||
_resolve(response.result)
|
||||
} else {
|
||||
_reject(new ResponseFormatError(
|
||||
'unrecognized status: ' + response.status));
|
||||
'unrecognized status: ' + response.status))
|
||||
}
|
||||
});
|
||||
})
|
||||
|
||||
this._ws.once('close', onDisconnect);
|
||||
this._ws.once('close', onDisconnect)
|
||||
|
||||
// JSON.stringify automatically removes keys with value of 'undefined'
|
||||
const message = JSON.stringify(Object.assign({}, request, {id}));
|
||||
const message = JSON.stringify(Object.assign({}, request, {id}))
|
||||
|
||||
this._whenReady(this._send(message)).then(() => {
|
||||
const delay = timeout || this._timeout;
|
||||
timer = setTimeout(() => _reject(new TimeoutError()), delay);
|
||||
}).catch(_reject);
|
||||
});
|
||||
const delay = timeout || this._timeout
|
||||
timer = setTimeout(() => _reject(new TimeoutError()), delay)
|
||||
}).catch(_reject)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = Connection;
|
||||
module.exports = Connection
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
'use strict';
|
||||
const flagIndices = require('./txflags').txFlagIndices.AccountSet;
|
||||
'use strict' // eslint-disable-line strict
|
||||
const flagIndices = require('./txflags').txFlagIndices.AccountSet
|
||||
|
||||
const accountRootFlags = {
|
||||
PasswordSpent: 0x00010000, // password set fee is spent
|
||||
@@ -10,7 +10,7 @@ const accountRootFlags = {
|
||||
NoFreeze: 0x00200000, // permanently disallowed freezing trustlines
|
||||
GlobalFreeze: 0x00400000, // trustlines globally frozen
|
||||
DefaultRipple: 0x00800000
|
||||
};
|
||||
}
|
||||
|
||||
const AccountFlags = {
|
||||
passwordSpent: accountRootFlags.PasswordSpent,
|
||||
@@ -21,7 +21,7 @@ const AccountFlags = {
|
||||
noFreeze: accountRootFlags.NoFreeze,
|
||||
globalFreeze: accountRootFlags.GlobalFreeze,
|
||||
defaultRipple: accountRootFlags.DefaultRipple
|
||||
};
|
||||
}
|
||||
|
||||
const AccountFlagIndices = {
|
||||
requireDestinationTag: flagIndices.asfRequireDest,
|
||||
@@ -32,7 +32,7 @@ const AccountFlagIndices = {
|
||||
noFreeze: flagIndices.asfNoFreeze,
|
||||
globalFreeze: flagIndices.asfGlobalFreeze,
|
||||
defaultRipple: flagIndices.asfDefaultRipple
|
||||
};
|
||||
}
|
||||
|
||||
const AccountFields = {
|
||||
EmailHash: {name: 'emailHash', encoding: 'hex',
|
||||
@@ -40,10 +40,10 @@ const AccountFields = {
|
||||
MessageKey: {name: 'messageKey'},
|
||||
Domain: {name: 'domain', encoding: 'hex'},
|
||||
TransferRate: {name: 'transferRate', defaults: 0, shift: 9}
|
||||
};
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
AccountFields,
|
||||
AccountFlagIndices,
|
||||
AccountFlags
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1,29 +1,43 @@
|
||||
'use strict';
|
||||
const util = require('util');
|
||||
'use strict' // eslint-disable-line strict
|
||||
const util = require('util')
|
||||
const browserHacks = require('./browser-hacks')
|
||||
|
||||
class RippleError extends Error {
|
||||
// this is needed because extending builtins doesn't work in babel 6.x
|
||||
function extendableBuiltin(cls) {
|
||||
function ExtendableBuiltin() {
|
||||
cls.apply(this, arguments)
|
||||
}
|
||||
ExtendableBuiltin.prototype = Object.create(cls.prototype)
|
||||
browserHacks.setPrototypeOf(ExtendableBuiltin, cls)
|
||||
return ExtendableBuiltin
|
||||
}
|
||||
|
||||
class RippleError extends extendableBuiltin(Error) {
|
||||
constructor(message, data) {
|
||||
super(message);
|
||||
this.name = this.constructor.name;
|
||||
this.message = message;
|
||||
this.data = data;
|
||||
Error.captureStackTrace(this, this.constructor.name);
|
||||
super(message)
|
||||
|
||||
this.name = browserHacks.getConstructorName(this)
|
||||
this.message = message
|
||||
this.data = data
|
||||
if (Error.captureStackTrace) {
|
||||
Error.captureStackTrace(this, this.constructor.name)
|
||||
}
|
||||
}
|
||||
|
||||
toString() {
|
||||
let result = '[' + this.name + '(' + this.message;
|
||||
let result = '[' + this.name + '(' + this.message
|
||||
if (this.data) {
|
||||
result += ', ' + util.inspect(this.data);
|
||||
result += ', ' + util.inspect(this.data)
|
||||
}
|
||||
result += ')]';
|
||||
return result;
|
||||
result += ')]'
|
||||
return result
|
||||
}
|
||||
|
||||
/* console.log in node uses util.inspect on object, and util.inspect allows
|
||||
us to cutomize its output:
|
||||
https://nodejs.org/api/util.html#util_custom_inspect_function_on_objects */
|
||||
inspect() {
|
||||
return this.toString();
|
||||
return this.toString()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -39,6 +53,8 @@ class NotConnectedError extends ConnectionError {}
|
||||
|
||||
class DisconnectedError extends ConnectionError {}
|
||||
|
||||
class RippledNotInitializedError extends ConnectionError {}
|
||||
|
||||
class TimeoutError extends ConnectionError {}
|
||||
|
||||
class ResponseFormatError extends ConnectionError {}
|
||||
@@ -47,20 +63,20 @@ class ValidationError extends RippleError {}
|
||||
|
||||
class NotFoundError extends RippleError {
|
||||
constructor(message) {
|
||||
super(message || 'Not found');
|
||||
super(message || 'Not found')
|
||||
}
|
||||
}
|
||||
|
||||
class MissingLedgerHistoryError extends RippleError {
|
||||
constructor(message) {
|
||||
super(message || 'Server is missing ledger history in the specified range');
|
||||
super(message || 'Server is missing ledger history in the specified range')
|
||||
}
|
||||
}
|
||||
|
||||
class PendingLedgerVersionError extends RippleError {
|
||||
constructor(message) {
|
||||
super(message || 'maxLedgerVersion is greater than server\'s'
|
||||
+ ' most recent validated ledger');
|
||||
+ ' most recent validated ledger')
|
||||
}
|
||||
}
|
||||
|
||||
@@ -71,6 +87,7 @@ module.exports = {
|
||||
RippledError,
|
||||
NotConnectedError,
|
||||
DisconnectedError,
|
||||
RippledNotInitializedError,
|
||||
TimeoutError,
|
||||
ResponseFormatError,
|
||||
ValidationError,
|
||||
@@ -78,4 +95,4 @@ module.exports = {
|
||||
PendingLedgerVersionError,
|
||||
MissingLedgerHistoryError,
|
||||
LedgerVersionError
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
'use strict';
|
||||
const utils = require('./utils');
|
||||
'use strict' // eslint-disable-line strict
|
||||
const utils = require('./utils')
|
||||
|
||||
module.exports = {
|
||||
Connection: require('./connection'),
|
||||
@@ -19,4 +19,4 @@ module.exports = {
|
||||
iso8601ToRippleTime: utils.iso8601ToRippleTime,
|
||||
rippleTimeToISO8601: utils.rippleTimeToISO8601,
|
||||
isValidSecret: utils.isValidSecret
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1,61 +1,61 @@
|
||||
/* @flow */
|
||||
'use strict';
|
||||
const _ = require('lodash');
|
||||
const assert = require('assert');
|
||||
const ranges = Symbol();
|
||||
'use strict' // eslint-disable-line strict
|
||||
const _ = require('lodash')
|
||||
const assert = require('assert')
|
||||
const ranges = Symbol()
|
||||
|
||||
function mergeIntervals(intervals: Array<[number, number]>) {
|
||||
const stack = [[-Infinity, -Infinity]];
|
||||
const stack = [[-Infinity, -Infinity]]
|
||||
_.forEach(_.sortBy(intervals, x => x[0]), interval => {
|
||||
const lastInterval = stack.pop();
|
||||
const lastInterval = stack.pop()
|
||||
if (interval[0] <= lastInterval[1] + 1) {
|
||||
stack.push([lastInterval[0], Math.max(interval[1], lastInterval[1])]);
|
||||
stack.push([lastInterval[0], Math.max(interval[1], lastInterval[1])])
|
||||
} else {
|
||||
stack.push(lastInterval);
|
||||
stack.push(interval);
|
||||
stack.push(lastInterval)
|
||||
stack.push(interval)
|
||||
}
|
||||
});
|
||||
return stack.slice(1);
|
||||
})
|
||||
return stack.slice(1)
|
||||
}
|
||||
|
||||
class RangeSet {
|
||||
constructor() {
|
||||
this.reset();
|
||||
this.reset()
|
||||
}
|
||||
|
||||
reset() {
|
||||
this[ranges] = [];
|
||||
this[ranges] = []
|
||||
}
|
||||
|
||||
serialize() {
|
||||
return this[ranges].map(range =>
|
||||
range[0].toString() + '-' + range[1].toString()).join(',');
|
||||
range[0].toString() + '-' + range[1].toString()).join(',')
|
||||
}
|
||||
|
||||
addRange(start: number, end: number) {
|
||||
assert(start <= end, 'invalid range');
|
||||
this[ranges] = mergeIntervals(this[ranges].concat([[start, end]]));
|
||||
assert(start <= end, 'invalid range')
|
||||
this[ranges] = mergeIntervals(this[ranges].concat([[start, end]]))
|
||||
}
|
||||
|
||||
addValue(value: number) {
|
||||
this.addRange(value, value);
|
||||
this.addRange(value, value)
|
||||
}
|
||||
|
||||
parseAndAddRanges(rangesString: string) {
|
||||
const rangeStrings = rangesString.split(',');
|
||||
const rangeStrings = rangesString.split(',')
|
||||
_.forEach(rangeStrings, rangeString => {
|
||||
const range = rangeString.split('-').map(Number);
|
||||
this.addRange(range[0], range.length === 1 ? range[0] : range[1]);
|
||||
});
|
||||
const range = rangeString.split('-').map(Number)
|
||||
this.addRange(range[0], range.length === 1 ? range[0] : range[1])
|
||||
})
|
||||
}
|
||||
|
||||
containsRange(start: number, end: number) {
|
||||
return _.some(this[ranges], range => range[0] <= start && range[1] >= end);
|
||||
return _.some(this[ranges], range => range[0] <= start && range[1] >= end)
|
||||
}
|
||||
|
||||
containsValue(value: number) {
|
||||
return this.containsRange(value, value);
|
||||
return this.containsRange(value, value)
|
||||
}
|
||||
}
|
||||
|
||||
module.exports.RangeSet = RangeSet;
|
||||
module.exports.RangeSet = RangeSet
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
// flow is disabled for this file until support for requiring json is added:
|
||||
// https://github.com/facebook/flow/issues/167
|
||||
'use strict';
|
||||
const _ = require('lodash');
|
||||
const assert = require('assert');
|
||||
const Ajv = require('ajv');
|
||||
const ValidationError = require('./errors').ValidationError;
|
||||
const {isValidAddress} = require('ripple-address-codec');
|
||||
const {isValidSecret} = require('./utils');
|
||||
'use strict' // eslint-disable-line strict
|
||||
const _ = require('lodash')
|
||||
const assert = require('assert')
|
||||
const Validator = require('jsonschema').Validator
|
||||
const ValidationError = require('./errors').ValidationError
|
||||
const {isValidAddress} = require('ripple-address-codec')
|
||||
const {isValidSecret} = require('./utils')
|
||||
|
||||
function loadSchemas() {
|
||||
// listed explicitly for webpack (instead of scanning schemas directory)
|
||||
@@ -16,11 +16,13 @@ function loadSchemas() {
|
||||
require('./schemas/objects/hash128.json'),
|
||||
require('./schemas/objects/hash256.json'),
|
||||
require('./schemas/objects/sequence.json'),
|
||||
require('./schemas/objects/signature.json'),
|
||||
require('./schemas/objects/issue.json'),
|
||||
require('./schemas/objects/ledgerversion.json'),
|
||||
require('./schemas/objects/max-adjustment.json'),
|
||||
require('./schemas/objects/memo.json'),
|
||||
require('./schemas/objects/memos.json'),
|
||||
require('./schemas/objects/public-key.json'),
|
||||
require('./schemas/objects/uint32.json'),
|
||||
require('./schemas/objects/value.json'),
|
||||
require('./schemas/objects/source-adjustment.json'),
|
||||
@@ -43,25 +45,30 @@ function loadSchemas() {
|
||||
require('./schemas/objects/signed-value.json'),
|
||||
require('./schemas/objects/orderbook.json'),
|
||||
require('./schemas/objects/instructions.json'),
|
||||
require('./schemas/objects/settings.json'),
|
||||
require('./schemas/specifications/settings.json'),
|
||||
require('./schemas/specifications/payment.json'),
|
||||
require('./schemas/specifications/suspended-payment-cancellation.json'),
|
||||
require('./schemas/specifications/escrow-cancellation.json'),
|
||||
require('./schemas/specifications/order-cancellation.json'),
|
||||
require('./schemas/specifications/order.json'),
|
||||
require('./schemas/specifications/suspended-payment-execution.json'),
|
||||
require('./schemas/specifications/suspended-payment-creation.json'),
|
||||
require('./schemas/specifications/escrow-execution.json'),
|
||||
require('./schemas/specifications/escrow-creation.json'),
|
||||
require('./schemas/specifications/payment-channel-create.json'),
|
||||
require('./schemas/specifications/payment-channel-fund.json'),
|
||||
require('./schemas/specifications/payment-channel-claim.json'),
|
||||
require('./schemas/specifications/trustline.json'),
|
||||
require('./schemas/output/sign.json'),
|
||||
require('./schemas/output/submit.json'),
|
||||
require('./schemas/output/get-account-info.json'),
|
||||
require('./schemas/output/get-balances.json'),
|
||||
require('./schemas/output/get-balance-sheet'),
|
||||
require('./schemas/output/get-balance-sheet.json'),
|
||||
require('./schemas/output/get-ledger.json'),
|
||||
require('./schemas/output/get-orderbook.json'),
|
||||
require('./schemas/output/get-orders.json'),
|
||||
require('./schemas/output/order-change.json'),
|
||||
require('./schemas/output/get-payment-channel.json'),
|
||||
require('./schemas/output/prepare.json'),
|
||||
require('./schemas/output/ledger-closed.json'),
|
||||
require('./schemas/output/ledger-event.json'),
|
||||
require('./schemas/output/get-paths.json'),
|
||||
require('./schemas/output/get-server-info.json'),
|
||||
require('./schemas/output/get-settings.json'),
|
||||
@@ -70,12 +77,15 @@ function loadSchemas() {
|
||||
require('./schemas/output/get-transaction.json'),
|
||||
require('./schemas/output/get-transactions.json'),
|
||||
require('./schemas/output/get-trustlines.json'),
|
||||
require('./schemas/output/sign-payment-channel-claim.json'),
|
||||
require('./schemas/output/verify-payment-channel-claim.json'),
|
||||
require('./schemas/input/get-balances.json'),
|
||||
require('./schemas/input/get-balance-sheet.json'),
|
||||
require('./schemas/input/get-ledger.json'),
|
||||
require('./schemas/input/get-orders.json'),
|
||||
require('./schemas/input/get-orderbook.json'),
|
||||
require('./schemas/input/get-paths.json'),
|
||||
require('./schemas/input/get-payment-channel.json'),
|
||||
require('./schemas/input/api-options.json'),
|
||||
require('./schemas/input/get-settings.json'),
|
||||
require('./schemas/input/get-account-info.json'),
|
||||
@@ -87,33 +97,60 @@ function loadSchemas() {
|
||||
require('./schemas/input/prepare-trustline.json'),
|
||||
require('./schemas/input/prepare-order-cancellation.json'),
|
||||
require('./schemas/input/prepare-settings.json'),
|
||||
require('./schemas/input/prepare-suspended-payment-creation.json'),
|
||||
require('./schemas/input/prepare-suspended-payment-cancellation.json'),
|
||||
require('./schemas/input/prepare-suspended-payment-execution.json'),
|
||||
require('./schemas/input/compute-ledger-hash'),
|
||||
require('./schemas/input/sign'),
|
||||
require('./schemas/input/submit')
|
||||
];
|
||||
const titles = _.map(schemas, schema => schema.title);
|
||||
const duplicates = _.keys(_.pick(_.countBy(titles), count => count > 1));
|
||||
assert(duplicates.length === 0, 'Duplicate schemas for: ' + duplicates);
|
||||
const ajv = new Ajv();
|
||||
_.forEach(schemas, schema => ajv.addSchema(schema, schema.title));
|
||||
ajv.addFormat('address', isValidAddress);
|
||||
ajv.addFormat('secret', isValidSecret);
|
||||
return ajv;
|
||||
require('./schemas/input/prepare-escrow-creation.json'),
|
||||
require('./schemas/input/prepare-escrow-cancellation.json'),
|
||||
require('./schemas/input/prepare-escrow-execution.json'),
|
||||
require('./schemas/input/prepare-payment-channel-create.json'),
|
||||
require('./schemas/input/prepare-payment-channel-fund.json'),
|
||||
require('./schemas/input/prepare-payment-channel-claim.json'),
|
||||
require('./schemas/input/compute-ledger-hash.json'),
|
||||
require('./schemas/input/sign.json'),
|
||||
require('./schemas/input/submit.json'),
|
||||
require('./schemas/input/generate-address.json'),
|
||||
require('./schemas/input/sign-payment-channel-claim.json'),
|
||||
require('./schemas/input/verify-payment-channel-claim.json'),
|
||||
require('./schemas/input/combine.json')
|
||||
]
|
||||
const titles = _.map(schemas, schema => schema.title)
|
||||
const duplicates = _.keys(_.pick(_.countBy(titles), count => count > 1))
|
||||
assert(duplicates.length === 0, 'Duplicate schemas for: ' + duplicates)
|
||||
const v = new Validator()
|
||||
// Register custom format validators that ignore undefined instances
|
||||
// since jsonschema will still call the format validator on a missing
|
||||
// (optional) property
|
||||
v.customFormats.address = function(instance) {
|
||||
if (instance === undefined) {
|
||||
return true
|
||||
}
|
||||
return isValidAddress(instance)
|
||||
}
|
||||
v.customFormats.secret = function(instance) {
|
||||
if (instance === undefined) {
|
||||
return true
|
||||
}
|
||||
return isValidSecret(instance)
|
||||
}
|
||||
|
||||
// Register under the root URI '/'
|
||||
_.forEach(schemas, schema => v.addSchema(schema, '/' + schema.title))
|
||||
return v
|
||||
}
|
||||
|
||||
const ajv = loadSchemas();
|
||||
const v = loadSchemas()
|
||||
|
||||
function schemaValidate(schemaName: string, object: any): void {
|
||||
const isValid = ajv.validate(schemaName, object);
|
||||
if (!isValid) {
|
||||
throw new ValidationError(ajv.errorsText());
|
||||
// Lookup under the root URI '/'
|
||||
const schema = v.getSchema('/' + schemaName)
|
||||
if (schema === undefined) {
|
||||
throw new ValidationError('no schema for ' + schemaName)
|
||||
}
|
||||
const result = v.validate(object, schema)
|
||||
if (!result.valid) {
|
||||
throw new ValidationError(result.errors.join())
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
schemaValidate,
|
||||
isValidSecret
|
||||
};
|
||||
}
|
||||
|
||||
@@ -3,21 +3,57 @@
|
||||
"title": "api-options",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"trace": {"type": "boolean"},
|
||||
"feeCushion": {"$ref": "value"},
|
||||
"servers": {
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string",
|
||||
"format": "uri",
|
||||
"pattern": "^wss?://"
|
||||
}
|
||||
"trace": {
|
||||
"type": "boolean",
|
||||
"description": "If true, log rippled requests and responses to stdout."
|
||||
},
|
||||
"feeCushion": {
|
||||
"type": "number",
|
||||
"minimum": 1,
|
||||
"description": "Factor to multiply estimated fee by to provide a cushion in case the required fee rises during submission of a transaction. Defaults to `1.2`."
|
||||
},
|
||||
"server": {
|
||||
"type": "string",
|
||||
"description": "URI for rippled websocket port to connect to. Must start with `wss://` or `ws://`.",
|
||||
"format": "uri",
|
||||
"pattern": "^wss?://"
|
||||
},
|
||||
"proxy": {
|
||||
"format": "uri"
|
||||
"format": "uri",
|
||||
"description": "URI for HTTP/HTTPS proxy to use to connect to the rippled server."
|
||||
},
|
||||
"timeout": {
|
||||
"type": "integer",
|
||||
"description": "Timeout in milliseconds before considering a request to have failed.",
|
||||
"minimum": 1
|
||||
},
|
||||
"proxyAuthorization": {
|
||||
"type": "string",
|
||||
"description": "Username and password for HTTP basic authentication to the proxy in the format **username:password**."
|
||||
},
|
||||
"authorization": {
|
||||
"type": "string"
|
||||
"type": "string",
|
||||
"description": "Username and password for HTTP basic authentication to the rippled server in the format **username:password**."
|
||||
},
|
||||
"trustedCertificates": {
|
||||
"type": "array",
|
||||
"description": "Array of PEM-formatted SSL certificates to trust when connecting to a proxy. This is useful if you want to use a self-signed certificate on the proxy server. Note: Each element must contain a single certificate; concatenated certificates are not valid.",
|
||||
"items": {
|
||||
"type": "string",
|
||||
"description": "A PEM-formatted SSL certificate to trust when connecting to a proxy."
|
||||
}
|
||||
},
|
||||
"key": {
|
||||
"type": "string",
|
||||
"description": "A string containing the private key of the client in PEM format. (Can be an array of keys)."
|
||||
},
|
||||
"passphrase": {
|
||||
"type": "string",
|
||||
"description": "The passphrase for the private key of the client."
|
||||
},
|
||||
"certificate": {
|
||||
"type": "string",
|
||||
"description": "A string containing the certificate key of the client in PEM format. (Can be an array of certificates)."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false
|
||||
|
||||
19
src/common/schemas/input/combine.json
Normal file
19
src/common/schemas/input/combine.json
Normal file
@@ -0,0 +1,19 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "combineParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"signedTransactions": {
|
||||
"type": "array",
|
||||
"description": "An array of signed transactions (from the output of [sign](#sign)) to combine.",
|
||||
"items": {
|
||||
"type": "string",
|
||||
"pattern": "^[A-F0-9]+$",
|
||||
"description": "A single-signed transaction represented as an uppercase hexadecimal string (from the output of [sign](#sign))"
|
||||
},
|
||||
"minLength": 1
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["signedTransactions"]
|
||||
}
|
||||
29
src/common/schemas/input/generate-address.json
Normal file
29
src/common/schemas/input/generate-address.json
Normal file
@@ -0,0 +1,29 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "generateAddressParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"options": {
|
||||
"type": "object",
|
||||
"description": "Options to control how the address and secret are generated.",
|
||||
"properties": {
|
||||
"entropy": {
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"maximum": 255
|
||||
},
|
||||
"description": "The entropy to use to generate the seed."
|
||||
},
|
||||
"algorithm": {
|
||||
"type": "string",
|
||||
"enum": ["ecdsa-secp256k1", "ed25519"],
|
||||
"description": "The digital signature algorithm to generate an address for. Can be `ecdsa-secp256k1` (default) or `ed25519`."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false
|
||||
}
|
||||
},
|
||||
"additionalProperties": false
|
||||
}
|
||||
14
src/common/schemas/input/get-payment-channel.json
Normal file
14
src/common/schemas/input/get-payment-channel.json
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "getPaymentChannelParameters",
|
||||
"description": "Parameters for getPaymentChannel",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"id": {
|
||||
"$ref": "hash256",
|
||||
"description": "256-bit hexadecimal channel identifier."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["id"]
|
||||
}
|
||||
@@ -1,18 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "prepareSuspendedPaymentCreationParameters",
|
||||
"title": "prepareEscrowCancellationParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"suspendedPaymentCreation": {
|
||||
"$ref": "suspendedPaymentCreation",
|
||||
"description": "The specification of the suspended payment creation to prepare."
|
||||
"escrowCancellation": {
|
||||
"$ref": "escrowCancellation",
|
||||
"description": "The specification of the escrow cancellation to prepare."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "suspendedPaymentCreation"]
|
||||
"required": ["address", "escrowCancellation"]
|
||||
}
|
||||
@@ -1,18 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "prepareSuspendedPaymentExecutionParameters",
|
||||
"title": "prepareEscrowCreationParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"suspendedPaymentExecution": {
|
||||
"$ref": "suspendedPaymentExecution",
|
||||
"description": "The specification of the suspended payment execution to prepare."
|
||||
"escrowCreation": {
|
||||
"$ref": "escrowCreation",
|
||||
"description": "The specification of the escrow creation to prepare."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "suspendedPaymentExecution"]
|
||||
"required": ["address", "escrowCreation"]
|
||||
}
|
||||
@@ -1,18 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "prepareSuspendedPaymentCancellationParameters",
|
||||
"title": "prepareEscrowExecutionParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"suspendedPaymentCancellation": {
|
||||
"$ref": "suspendedPaymentCancellation",
|
||||
"description": "The specification of the suspended payment cancellation to prepare."
|
||||
"escrowExecution": {
|
||||
"$ref": "escrowExecution",
|
||||
"description": "The specification of the escrow execution to prepare."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "suspendedPaymentCancellation"]
|
||||
"required": ["address", "escrowExecution"]
|
||||
}
|
||||
@@ -7,12 +7,12 @@
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"sequence": {
|
||||
"$ref": "sequence",
|
||||
"description": "The account sequence number of the transaction that created the order to cancel."
|
||||
"orderCancellation": {
|
||||
"$ref": "orderCancellation",
|
||||
"description": "The specification of the order cancellation to prepare."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "sequence"]
|
||||
"required": ["address", "orderCancellation"]
|
||||
}
|
||||
|
||||
18
src/common/schemas/input/prepare-payment-channel-claim.json
Normal file
18
src/common/schemas/input/prepare-payment-channel-claim.json
Normal file
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "preparePaymentChannelClaimParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"paymentChannelClaim": {
|
||||
"$ref": "paymentChannelClaim",
|
||||
"description": "Details of the channel and claim."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "paymentChannelClaim"]
|
||||
}
|
||||
18
src/common/schemas/input/prepare-payment-channel-create.json
Normal file
18
src/common/schemas/input/prepare-payment-channel-create.json
Normal file
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "preparePaymentChannelCreateParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"paymentChannelCreate": {
|
||||
"$ref": "paymentChannelCreate",
|
||||
"description": "The specification of the payment channel to create."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "paymentChannelCreate"]
|
||||
}
|
||||
18
src/common/schemas/input/prepare-payment-channel-fund.json
Normal file
18
src/common/schemas/input/prepare-payment-channel-fund.json
Normal file
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "preparePaymentChannelFundParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"address": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the account that is creating the transaction."
|
||||
},
|
||||
"paymentChannelFund": {
|
||||
"$ref": "paymentChannelFund",
|
||||
"description": "The channel to fund, and the details of how to fund it."
|
||||
},
|
||||
"instructions": {"$ref": "instructions"}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["address", "paymentChannelFund"]
|
||||
}
|
||||
21
src/common/schemas/input/sign-payment-channel-claim.json
Normal file
21
src/common/schemas/input/sign-payment-channel-claim.json
Normal file
@@ -0,0 +1,21 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "signPaymentChannelClaimParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"channel": {
|
||||
"$ref": "hash256",
|
||||
"description": "256-bit hexadecimal channel identifier."
|
||||
},
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP authorized by the claim."
|
||||
},
|
||||
"privateKey": {
|
||||
"$ref": "publicKey",
|
||||
"description": "The private key to sign the payment channel claim."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["channel", "amount", "privateKey"]
|
||||
}
|
||||
@@ -11,6 +11,17 @@
|
||||
"type": "string",
|
||||
"format": "secret",
|
||||
"description": "The secret of the account that is initiating the transaction."
|
||||
},
|
||||
"options": {
|
||||
"type": "object",
|
||||
"description": "Options that control the type of signature that will be generated.",
|
||||
"properties": {
|
||||
"signAs": {
|
||||
"$ref": "address",
|
||||
"description": "The account that the signature should count for in multisigning."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
|
||||
25
src/common/schemas/input/verify-payment-channel-claim.json
Normal file
25
src/common/schemas/input/verify-payment-channel-claim.json
Normal file
@@ -0,0 +1,25 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "verifyPaymentChannelClaimParameters",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"channel": {
|
||||
"$ref": "hash256",
|
||||
"description": "256-bit hexadecimal channel identifier."
|
||||
},
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP authorized by the claim."
|
||||
},
|
||||
"signature": {
|
||||
"$ref": "signature",
|
||||
"description": "Signature of this claim."
|
||||
},
|
||||
"publicKey": {
|
||||
"$ref": "publicKey",
|
||||
"description": "Public key of the channel's sender"
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["channel", "amount", "signature", "publicKey"]
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "amount",
|
||||
"link": "amount",
|
||||
"description": "An Amount on the Ripple Protocol, used also for XRP in the ripple-rest API",
|
||||
"description": "An Amount on the Ripple Protocol",
|
||||
"allOf": [
|
||||
{"$ref": "amountbase"},
|
||||
{"required": ["value"]}
|
||||
|
||||
@@ -18,13 +18,21 @@
|
||||
"$ref": "value"
|
||||
},
|
||||
"maxLedgerVersion": {
|
||||
"description": "The highest ledger version that the transaction can be included in.",
|
||||
"$ref": "ledgerVersion"
|
||||
"description": "The highest ledger version that the transaction can be included in. If this option and `maxLedgerVersionOffset` are both omitted, the `maxLedgerVersion` option will default to 3 greater than the current validated ledger version (equivalent to `maxLedgerVersionOffset=3`). Use `null` to not set a maximum ledger version.",
|
||||
"oneOf": [
|
||||
{"$ref": "ledgerVersion"},
|
||||
{"type": "null"}
|
||||
]
|
||||
},
|
||||
"maxLedgerVersionOffset": {
|
||||
"description": "Offset from current legder version to highest ledger version that the transaction can be included in.",
|
||||
"description": "Offset from current validated legder version to highest ledger version that the transaction can be included in.",
|
||||
"type": "integer",
|
||||
"minimum": 0
|
||||
},
|
||||
"signersCount": {
|
||||
"description": "Number of signers that will be signing this transaction.",
|
||||
"type": "integer",
|
||||
"minimum": 1
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "memos",
|
||||
"link": "transaction-memos",
|
||||
"description": "Array of memos to attach to the transaction.",
|
||||
"type": "array",
|
||||
"items": {
|
||||
|
||||
7
src/common/schemas/objects/public-key.json
Normal file
7
src/common/schemas/objects/public-key.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "publicKey",
|
||||
"description": "The hexadecimal representation of a secp256k1 or Ed25519 public key.",
|
||||
"type": "string",
|
||||
"pattern": "^[A-F0-9]+$"
|
||||
}
|
||||
103
src/common/schemas/objects/settings.json
Normal file
103
src/common/schemas/objects/settings.json
Normal file
@@ -0,0 +1,103 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "settingsPlusMemos",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"passwordSpent": {
|
||||
"type": "boolean",
|
||||
"description": "Indicates that the account has used its free SetRegularKey transaction."
|
||||
},
|
||||
"requireDestinationTag": {
|
||||
"type": "boolean",
|
||||
"description": "Requires incoming payments to specify a destination tag."
|
||||
},
|
||||
"requireAuthorization": {
|
||||
"type": "boolean",
|
||||
"description": "If set, this account must individually approve other users in order for those users to hold this account’s issuances."
|
||||
},
|
||||
"disallowIncomingXRP": {
|
||||
"type": "boolean",
|
||||
"description": "Indicates that client applications should not send XRP to this account. Not enforced by rippled."
|
||||
},
|
||||
"disableMasterKey": {
|
||||
"type": "boolean",
|
||||
"description": "Disallows use of the master key to sign transactions for this account."
|
||||
},
|
||||
"enableTransactionIDTracking": {
|
||||
"type": "boolean",
|
||||
"description": "Track the ID of this account’s most recent transaction."
|
||||
},
|
||||
"noFreeze": {
|
||||
"type": "boolean",
|
||||
"description": "Permanently give up the ability to freeze individual trust lines. This flag can never be disabled after being enabled."
|
||||
},
|
||||
"globalFreeze": {
|
||||
"type": "boolean",
|
||||
"description": "Freeze all assets issued by this account."
|
||||
},
|
||||
"defaultRipple": {
|
||||
"type": "boolean",
|
||||
"description": "Enable [rippling](https://ripple.com/knowledge_center/understanding-the-noripple-flag/) on this account’s trust lines by default. (New in [rippled 0.27.3](https://github.com/ripple/rippled/releases/tag/0.27.3))"
|
||||
},
|
||||
"emailHash": {
|
||||
"description": "Hash of an email address to be used for generating an avatar image. Conventionally, clients use Gravatar to display this image. Use `null` to clear.",
|
||||
"oneOf": [
|
||||
{"type": "null"},
|
||||
{"$ref": "hash128"}
|
||||
]
|
||||
},
|
||||
"messageKey": {
|
||||
"type": "string",
|
||||
"description": "Public key for sending encrypted messages to this account. Conventionally, it should be a secp256k1 key, the same encryption that is used by the rest of Ripple."
|
||||
},
|
||||
"domain": {
|
||||
"type": "string",
|
||||
"description": " The domain that owns this account, as a hexadecimal string representing the ASCII for the domain in lowercase."
|
||||
},
|
||||
"transferRate": {
|
||||
"description": " The fee to charge when users transfer this account’s issuances, as the decimal amount that must be sent to deliver 1 unit. Has precision up to 9 digits beyond the decimal point. Use `null` to set no fee.",
|
||||
"oneOf": [
|
||||
{"type": "null"},
|
||||
{"type": "number", "minimum": 1, "maximum": 4.294967295}
|
||||
]
|
||||
},
|
||||
"regularKey": {
|
||||
"oneOf": [
|
||||
{"$ref": "address"},
|
||||
{"type": "null"}
|
||||
],
|
||||
"description": "The public key of a new keypair, to use as the regular key to this account, as a base-58-encoded string in the same format as an account address. Use `null` to remove the regular key."
|
||||
},
|
||||
"signers": {
|
||||
"type": "object",
|
||||
"description": "Settings that determine what sets of accounts can be used to sign a transaction on behalf of this account using multisigning.",
|
||||
"properties": {
|
||||
"threshold": {
|
||||
"$ref": "uint32",
|
||||
"description": "A target number for the signer weights. A multi-signature from this list is valid only if the sum weights of the signatures provided is equal or greater than this value. To delete the signers setting, use the value `0`."
|
||||
},
|
||||
"weights": {
|
||||
"type": "array",
|
||||
"description": "Weights of signatures for each signer.",
|
||||
"items": {
|
||||
"type": "object",
|
||||
"description": "An association of an address and a weight.",
|
||||
"properties": {
|
||||
"address": {"$ref": "address"},
|
||||
"weight": {
|
||||
"$ref": "uint32",
|
||||
"description": "The weight that the signature of this account counts as towards the threshold."
|
||||
}
|
||||
},
|
||||
"required": ["address", "weight"],
|
||||
"additionalProperties": false
|
||||
},
|
||||
"minItems": 1,
|
||||
"maxItems": 8
|
||||
}
|
||||
}
|
||||
},
|
||||
"memos": {"$ref": "memos"}
|
||||
},
|
||||
"additionalProperties": false
|
||||
}
|
||||
7
src/common/schemas/objects/signature.json
Normal file
7
src/common/schemas/objects/signature.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "signature",
|
||||
"description": "The hexadecimal representation of a signature.",
|
||||
"type": "string",
|
||||
"pattern": "^[A-F0-9]+$"
|
||||
}
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "tag",
|
||||
"description": "An arbitrary unsigned 32-bit integer most commonly used to identify a non-Ripple account.",
|
||||
"description": "An arbitrary unsigned 32-bit integer that identifies a reason for payment or a non-Ripple account.",
|
||||
"type": "integer",
|
||||
"$ref": "uint32"
|
||||
}
|
||||
|
||||
@@ -2,9 +2,10 @@
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "transactionType",
|
||||
"link": "transaction-types",
|
||||
"description": "The type of the tranasction.",
|
||||
"description": "The type of the transaction.",
|
||||
"type": "string",
|
||||
"enum": ["payment", "order", "orderCancellation", "trustline", "settings",
|
||||
"suspendedPaymentCreation", "suspendedPaymentCancellation",
|
||||
"suspendedPaymentExecution"]
|
||||
"escrowCreation", "escrowCancellation",
|
||||
"escrowExecution", "paymentChannelCreate",
|
||||
"paymentChannelFund", "paymentChannelClaim"]
|
||||
}
|
||||
|
||||
67
src/common/schemas/output/get-payment-channel.json
Normal file
67
src/common/schemas/output/get-payment-channel.json
Normal file
@@ -0,0 +1,67 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "getPaymentChannel",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"account": {
|
||||
"$ref": "address",
|
||||
"description": "Address that created the payment channel."
|
||||
},
|
||||
"destination": {
|
||||
"$ref": "address",
|
||||
"description": "Address to receive XRP claims against this channel."
|
||||
},
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "The total amount of XRP funded in this channel."
|
||||
},
|
||||
"balance": {
|
||||
"$ref": "value",
|
||||
"description": "The total amount of XRP delivered by this channel."
|
||||
},
|
||||
"settleDelay": {
|
||||
"type": "number",
|
||||
"description": "Amount of seconds the source address must wait before closing the channel if it has unclaimed XRP."
|
||||
},
|
||||
"expiration": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "Time when this channel expires."
|
||||
},
|
||||
"publicKey": {
|
||||
"$ref": "publicKey",
|
||||
"description": "Public key of the key pair the source will use to sign claims against this channel."
|
||||
},
|
||||
"cancelAfter": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "Time when this channel expires as specified at creation."
|
||||
},
|
||||
"sourceTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Source tag."
|
||||
},
|
||||
"destinationTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Destination tag."
|
||||
},
|
||||
"previousAffectingTransactionID": {
|
||||
"$ref": "hash256",
|
||||
"description": "Hash value representing the most recent transaction that affected this payment channel."
|
||||
},
|
||||
"previousAffectingTransactionLedgerVersion": {
|
||||
"$ref": "ledgerVersion",
|
||||
"description": "The ledger version that the transaction identified by the `previousAffectingTransactionID` was validated in."
|
||||
}
|
||||
},
|
||||
"required": [
|
||||
"account",
|
||||
"destination",
|
||||
"amount",
|
||||
"balance",
|
||||
"settleDelay",
|
||||
"previousAffectingTransactionID",
|
||||
"previousAffectingTransactionLedgerVersion"
|
||||
],
|
||||
"additionalProperties": false
|
||||
}
|
||||
@@ -83,7 +83,7 @@
|
||||
"description": "The time since the ledger was closed, in seconds."
|
||||
},
|
||||
"baseFeeXRP": {
|
||||
"type": "number",
|
||||
"$ref": "value",
|
||||
"description": "Base fee, in XRP. This may be represented in scientific notation such as 1e-05 for 0.00005."
|
||||
},
|
||||
"hash": {
|
||||
@@ -91,14 +91,12 @@
|
||||
"description": "Unique hash for the ledger, as an uppercase hexadecimal string."
|
||||
},
|
||||
"reserveBaseXRP": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "Minimum amount of XRP (not drops) necessary for every account to keep in reserve."
|
||||
"$ref": "value",
|
||||
"description": "Minimum amount of XRP necessary for every account to keep in reserve."
|
||||
},
|
||||
"reserveIncrementXRP": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "Amount of XRP (not drops) added to the account reserve for each object an account is responsible for in the ledger."
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP added to the account reserve for each object an account is responsible for in the ledger."
|
||||
},
|
||||
"ledgerVersion": {
|
||||
"type": "integer",
|
||||
|
||||
@@ -1,73 +1,8 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "getSettings",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"passwordSpent": {
|
||||
"type": "boolean",
|
||||
"description": "Indicates that the account has used its free SetRegularKey transaction."
|
||||
},
|
||||
"requireDestinationTag": {
|
||||
"type": "boolean",
|
||||
"description": "Requires incoming payments to specify a destination tag."
|
||||
},
|
||||
"requireAuthorization": {
|
||||
"type": "boolean",
|
||||
"description": "If set, this account must individually approve other users in order for those users to hold this account’s issuances."
|
||||
},
|
||||
"disallowIncomingXRP": {
|
||||
"type": "boolean",
|
||||
"description": "Indicates that client applications should not send XRP to this account. Not enforced by rippled."
|
||||
},
|
||||
"disableMasterKey": {
|
||||
"type": "boolean",
|
||||
"description": "Disallows use of the master key to sign transactions for this account."
|
||||
},
|
||||
"enableTransactionIDTracking": {
|
||||
"type": "boolean",
|
||||
"description": "Track the ID of this account’s most recent transaction."
|
||||
},
|
||||
"noFreeze": {
|
||||
"type": "boolean",
|
||||
"description": "Permanently give up the ability to freeze individual trust lines. This flag can never be disabled after being enabled."
|
||||
},
|
||||
"globalFreeze": {
|
||||
"type": "boolean",
|
||||
"description": "Freeze all assets issued by this account."
|
||||
},
|
||||
"defaultRipple": {
|
||||
"type": "boolean",
|
||||
"description": "Enable [rippling](https://ripple.com/knowledge_center/understanding-the-noripple-flag/) on this account’s trust lines by default. (New in [rippled 0.27.3](https://github.com/ripple/rippled/releases/tag/0.27.3))"
|
||||
},
|
||||
"emailHash": {
|
||||
"description": "Hash of an email address to be used for generating an avatar image. Conventionally, clients use Gravatar to display this image. Use `null` to clear.",
|
||||
"oneOf": [
|
||||
{"type": "null"},
|
||||
{"$ref": "hash128"}
|
||||
]
|
||||
},
|
||||
"messageKey": {
|
||||
"type": "string",
|
||||
"description": "Public key for sending encrypted messages to this account. Conventionally, it should be a secp256k1 key, the same encryption that is used by the rest of Ripple."
|
||||
},
|
||||
"domain": {
|
||||
"type": "string",
|
||||
"description": " The domain that owns this account, as a hexadecimal string representing the ASCII for the domain in lowercase."
|
||||
},
|
||||
"transferRate": {
|
||||
"description": " The fee to charge when users transfer this account’s issuances, represented as billionths of a unit. Use `null` to set no fee.",
|
||||
"oneOf": [
|
||||
{"type": "null"},
|
||||
{"type": "number", "minimum": 1, "maximum": 4.294967295}
|
||||
]
|
||||
},
|
||||
"regularKey": {
|
||||
"oneOf": [
|
||||
{"$ref": "address"},
|
||||
{"type": "null"}
|
||||
],
|
||||
"description": "The public key of a new keypair, to use as the regular key to this account, as a base-58-encoded string in the same format as an account address. Use `null` to remove the regular key."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false
|
||||
"$ref": "settingsPlusMemos",
|
||||
"not": {
|
||||
"required": ["memos"]
|
||||
}
|
||||
}
|
||||
|
||||
@@ -59,20 +59,38 @@
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["suspendedPaymentCreation"]},
|
||||
"specification": {"$ref": "suspendedPaymentCreation"}
|
||||
"type": {"enum": ["escrowCreation"]},
|
||||
"specification": {"$ref": "escrowCreation"}
|
||||
}
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["suspendedPaymentCancellation"]},
|
||||
"specification": {"$ref": "suspendedPaymentCancellation"}
|
||||
"type": {"enum": ["escrowCancellation"]},
|
||||
"specification": {"$ref": "escrowCancellation"}
|
||||
}
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["suspendedPaymentExecution"]},
|
||||
"specification": {"$ref": "suspendedPaymentExecution"}
|
||||
"type": {"enum": ["escrowExecution"]},
|
||||
"specification": {"$ref": "escrowExecution"}
|
||||
}
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["paymentChannelCreate"]},
|
||||
"specification": {"$ref": "paymentChannelCreate"}
|
||||
}
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["paymentChannelFund"]},
|
||||
"specification": {"$ref": "paymentChannelFund"}
|
||||
}
|
||||
},
|
||||
{
|
||||
"properties": {
|
||||
"type": {"enum": ["paymentChannelClaim"]},
|
||||
"specification": {"$ref": "paymentChannelClaim"}
|
||||
}
|
||||
}
|
||||
]
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
"state": {
|
||||
"properties": {
|
||||
"balance": {
|
||||
"$ref": "value",
|
||||
"$ref": "signedValue",
|
||||
"description": "The balance on the trustline, representing which party owes the other and by how much."
|
||||
}
|
||||
},
|
||||
|
||||
@@ -1,18 +1,12 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "ledgerClosed",
|
||||
"description": "A ledgerClosed event message",
|
||||
"title": "ledgerEvent",
|
||||
"description": "A ledger event message",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"feeBase": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "Base fee, in drops."
|
||||
},
|
||||
"feeReference": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "Cost of the 'reference transaction' in 'fee units'."
|
||||
"baseFeeXRP": {
|
||||
"$ref": "value",
|
||||
"description": "Base fee, in XRP."
|
||||
},
|
||||
"ledgerHash": {
|
||||
"$ref": "hash256",
|
||||
@@ -27,14 +21,12 @@
|
||||
"format": "date-time",
|
||||
"description": "The time at which this ledger closed."
|
||||
},
|
||||
"reserveBase": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"description": "The minimum reserve, in drops of XRP, that is required for an account."
|
||||
"reserveBaseXRP": {
|
||||
"$ref": "value",
|
||||
"description": "The minimum reserve, in XRP, that is required for an account."
|
||||
},
|
||||
"reserveIncrement": {
|
||||
"type": "integer",
|
||||
"minimum": 0,
|
||||
"reserveIncrementXRP": {
|
||||
"$ref": "value",
|
||||
"description": "The increase in account reserve that is added for each item the account owns, such as offers or trust lines."
|
||||
},
|
||||
"transactionCount": {
|
||||
@@ -48,7 +40,7 @@
|
||||
}
|
||||
},
|
||||
"addtionalProperties": false,
|
||||
"required": ["feeBase", "feeReference", "ledgerHash", "ledgerTimestamp",
|
||||
"reserveBase", "reserveIncrement", "transactionCount",
|
||||
"required": ["baseFeeXRP", "ledgerHash", "ledgerTimestamp",
|
||||
"reserveBaseXRP", "reserveIncrementXRP", "transactionCount",
|
||||
"ledgerVersion", "validatedLedgerVersions"]
|
||||
}
|
||||
@@ -17,6 +17,10 @@
|
||||
"$ref": "value",
|
||||
"description": "The XRP fee that was charged for the transaction."
|
||||
},
|
||||
"deliveredAmount": {
|
||||
"$ref": "amount",
|
||||
"description": "For payment transactions, it is impossible to reliably compute the actual delivered amount from the balanceChanges due to fixed precision. If the payment is not a partial payment and the transaction succeeded, the deliveredAmount should always be considered to be the amount specified in the transaction."
|
||||
},
|
||||
"balanceChanges": {
|
||||
"type": "object",
|
||||
"additionalProperties": {
|
||||
|
||||
@@ -21,12 +21,15 @@
|
||||
"description": "The initiating account's sequence number for this transaction."
|
||||
},
|
||||
"maxLedgerVersion": {
|
||||
"$ref": "ledgerVersion",
|
||||
"description": "The highest ledger version that the transaction can be included in."
|
||||
"oneOf": [
|
||||
{"$ref": "ledgerVersion"},
|
||||
{"type": "null"}
|
||||
],
|
||||
"description": "The highest ledger version that the transaction can be included in. Set to `null` if there is no maximum."
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
"required": ["fee", "sequence"]
|
||||
"required": ["fee", "sequence", "maxLedgerVersion"]
|
||||
}
|
||||
},
|
||||
"additionalProperties": false,
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "signPaymentChannelClaim",
|
||||
"type": "string",
|
||||
"$ref": "signature",
|
||||
"additionalProperties": false
|
||||
}
|
||||
@@ -5,7 +5,7 @@
|
||||
"properties": {
|
||||
"resultCode": {
|
||||
"type": "string",
|
||||
"description": "The result code returned by rippled. [List of tranasction responses](http://pages.lightthenight.org/gba/SanFran15/ripple)"
|
||||
"description": "The result code returned by rippled. [List of transaction responses](https://ripple.com/build/transactions/#full-transaction-response-list)"
|
||||
},
|
||||
"resultMessage": {
|
||||
"type": "string",
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "verifyPaymentChannelClaim",
|
||||
"type": "boolean",
|
||||
"additionalProperties": false
|
||||
}
|
||||
19
src/common/schemas/specifications/escrow-cancellation.json
Normal file
19
src/common/schemas/specifications/escrow-cancellation.json
Normal file
@@ -0,0 +1,19 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "escrowCancellation",
|
||||
"link": "escrow-cancellation",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"memos": {"$ref": "memos"},
|
||||
"owner": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the owner of the escrow to cancel."
|
||||
},
|
||||
"escrowSequence": {
|
||||
"$ref": "sequence",
|
||||
"description": "The [account sequence number](#account-sequence-number) of the [Escrow Creation](#escrow-creation) transaction for the escrow to cancel."
|
||||
}
|
||||
},
|
||||
"required": ["owner", "escrowSequence"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
42
src/common/schemas/specifications/escrow-creation.json
Normal file
42
src/common/schemas/specifications/escrow-creation.json
Normal file
@@ -0,0 +1,42 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "escrowCreation",
|
||||
"link": "escrow-creation",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP for sender to escrow."
|
||||
},
|
||||
"destination": {
|
||||
"$ref": "address",
|
||||
"description": "Address to receive escrowed XRP."
|
||||
},
|
||||
"memos": {"$ref": "memos"},
|
||||
"condition": {
|
||||
"type": "string",
|
||||
"description": "A hex value representing a [PREIMAGE-SHA-256 crypto-condition](https://tools.ietf.org/html/draft-thomas-crypto-conditions-02#section-8.1). If present, `fulfillment` is required upon execution.",
|
||||
"pattern": "^[A-F0-9]{0,256}$"
|
||||
},
|
||||
"allowCancelAfter": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "If present, the escrow may be cancelled after this time."
|
||||
},
|
||||
"allowExecuteAfter": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "If present, the escrow can not be executed before this time."
|
||||
},
|
||||
"sourceTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Source tag."
|
||||
},
|
||||
"destinationTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Destination tag."
|
||||
}
|
||||
},
|
||||
"required": ["amount", "destination"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
29
src/common/schemas/specifications/escrow-execution.json
Normal file
29
src/common/schemas/specifications/escrow-execution.json
Normal file
@@ -0,0 +1,29 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "escrowExecution",
|
||||
"link": "escrow-execution",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"memos": {"$ref": "memos"},
|
||||
"owner": {
|
||||
"$ref": "address",
|
||||
"description": "The address of the owner of the escrow to execute."
|
||||
},
|
||||
"escrowSequence": {
|
||||
"$ref": "sequence",
|
||||
"description": "The [account sequence number](#account-sequence-number) of the [Escrow Creation](#escrow-creation) transaction for the escrow to execute."
|
||||
},
|
||||
"condition": {
|
||||
"type": "string",
|
||||
"description": "A hex value representing a [PREIMAGE-SHA-256 crypto-condition](https://tools.ietf.org/html/draft-thomas-crypto-conditions-02#section-8.1). This must match the original `condition` from the escrow creation transaction.",
|
||||
"pattern": "^[A-F0-9]{0,256}$"
|
||||
},
|
||||
"fulfillment": {
|
||||
"type": "string",
|
||||
"description": "A hex value representing the [PREIMAGE-SHA-256 crypto-condition](https://tools.ietf.org/html/draft-thomas-crypto-conditions-02#section-8.1) fulfillment for `condition`.",
|
||||
"pattern": "^[A-F0-9]+$"
|
||||
}
|
||||
},
|
||||
"required": ["owner", "escrowSequence"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
@@ -7,7 +7,8 @@
|
||||
"orderSequence": {
|
||||
"$ref": "sequence",
|
||||
"description": "The [account sequence number](#account-sequence-number) of the order to cancel."
|
||||
}
|
||||
},
|
||||
"memos": {"$ref": "memos"}
|
||||
},
|
||||
"required": ["orderSequence"],
|
||||
"additionalProperties": false
|
||||
|
||||
@@ -33,7 +33,12 @@
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "Time after which the offer is no longer active, as an [ISO 8601 date-time](https://en.wikipedia.org/wiki/ISO_8601)."
|
||||
}
|
||||
},
|
||||
"orderToReplace": {
|
||||
"$ref": "sequence",
|
||||
"description": "The [account sequence number](#account-sequence-number) of an order to cancel before the new order is created, effectively replacing the old order."
|
||||
},
|
||||
"memos": {"$ref": "memos"}
|
||||
},
|
||||
"required": ["direction", "quantity", "totalPrice"],
|
||||
"additionalProperties": false,
|
||||
|
||||
38
src/common/schemas/specifications/payment-channel-claim.json
Normal file
38
src/common/schemas/specifications/payment-channel-claim.json
Normal file
@@ -0,0 +1,38 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "paymentChannelClaim",
|
||||
"link": "payment-channel-claim",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"channel": {
|
||||
"$ref": "hash256",
|
||||
"description": "256-bit hexadecimal channel identifier."
|
||||
},
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "XRP balance of this channel after claim is processed."
|
||||
},
|
||||
"balance": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP authorized by signature."
|
||||
},
|
||||
"signature": {
|
||||
"$ref": "signature",
|
||||
"description": "Signature of this claim."
|
||||
},
|
||||
"publicKey": {
|
||||
"$ref": "publicKey",
|
||||
"description": "Public key of the channel's sender"
|
||||
},
|
||||
"renew": {
|
||||
"type": "boolean",
|
||||
"description": "Clear the channel's expiration time."
|
||||
},
|
||||
"close": {
|
||||
"type": "boolean",
|
||||
"description": "Request to close the channel."
|
||||
}
|
||||
},
|
||||
"required": ["channel"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "paymentChannelCreate",
|
||||
"link": "payment-channel-create",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP for sender to set aside in this channel."
|
||||
},
|
||||
"destination": {
|
||||
"$ref": "address",
|
||||
"description": "Address to receive XRP claims against this channel."
|
||||
},
|
||||
"settleDelay": {
|
||||
"type": "number",
|
||||
"description": "Amount of seconds the source address must wait before closing the channel if it has unclaimed XRP."
|
||||
},
|
||||
"publicKey": {
|
||||
"$ref": "publicKey",
|
||||
"description": "Public key of the key pair the source will use to sign claims against this channel."
|
||||
},
|
||||
"cancelAfter": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "Time when this channel expires."
|
||||
},
|
||||
"sourceTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Source tag."
|
||||
},
|
||||
"destinationTag": {
|
||||
"$ref": "tag",
|
||||
"description": "Destination tag."
|
||||
}
|
||||
},
|
||||
"required": ["amount", "destination", "settleDelay", "publicKey"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
23
src/common/schemas/specifications/payment-channel-fund.json
Normal file
23
src/common/schemas/specifications/payment-channel-fund.json
Normal file
@@ -0,0 +1,23 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"title": "paymentChannelFund",
|
||||
"link": "payment-channel-fund",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"amount": {
|
||||
"$ref": "value",
|
||||
"description": "Amount of XRP to fund the channel with."
|
||||
},
|
||||
"channel": {
|
||||
"$ref": "hash256",
|
||||
"description": "256-bit hexadecimal channel identifier."
|
||||
},
|
||||
"expiration": {
|
||||
"type": "string",
|
||||
"format": "date-time",
|
||||
"description": "New expiration for this channel."
|
||||
}
|
||||
},
|
||||
"required": ["amount", "channel"],
|
||||
"additionalProperties": false
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user