mirror of
https://github.com/Xahau/xahau.js.git
synced 2025-12-06 17:27:59 +00:00
Compare commits
113 Commits
@xrplf/sec
...
xrpl@4.2.0
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5b16d0cfe3 | ||
|
|
35e40d9d71 | ||
|
|
ea9e3dcc98 | ||
|
|
61da4c567a | ||
|
|
189abc1a26 | ||
|
|
ce5ca316ca | ||
|
|
991a1d29a4 | ||
|
|
23d26c8c2e | ||
|
|
abdb192c69 | ||
|
|
84943ae0b6 | ||
|
|
d8126807a4 | ||
|
|
7a2fa3fcaa | ||
|
|
76c3355858 | ||
|
|
11e724253b | ||
|
|
f34d1a7a63 | ||
|
|
7bf6fecc71 | ||
|
|
303c2b983c | ||
|
|
448164da70 | ||
|
|
9f72c8d384 | ||
|
|
e42d418662 | ||
|
|
305f2c48bf | ||
|
|
b7dfcbf075 | ||
|
|
b04efe8c9e | ||
|
|
e3188b83ed | ||
|
|
f4011b58e7 | ||
|
|
00614753ff | ||
|
|
b3a76bd9c0 | ||
|
|
24e9ad7c12 | ||
|
|
c2dd2edbcc | ||
|
|
c9207337aa | ||
|
|
a6852dd588 | ||
|
|
3a604ce69a | ||
|
|
663b80f1d0 | ||
|
|
92eb809397 | ||
|
|
799cd65386 | ||
|
|
29d145138b | ||
|
|
496f774154 | ||
|
|
0395c14392 | ||
|
|
2a77e2cd91 | ||
|
|
619c9ae13a | ||
|
|
8beb1292b5 | ||
|
|
649bf7d277 | ||
|
|
e0d368791b | ||
|
|
be9b48b071 | ||
|
|
55892c8b89 | ||
|
|
b1b4995047 | ||
|
|
a726a5a4f9 | ||
|
|
8992d3914e | ||
|
|
c2e01b3d10 | ||
|
|
8bfe5b42b8 | ||
|
|
385a56a1f7 | ||
|
|
f3960c3ccc | ||
|
|
a46e86f17e | ||
|
|
8f5d210806 | ||
|
|
17c91cdd3a | ||
|
|
74a41832ce | ||
|
|
275c95752b | ||
|
|
3bc3c2029b | ||
|
|
c9ef96e0a2 | ||
|
|
00f1a6bcdd | ||
|
|
3858a09e1f | ||
|
|
3aaf526107 | ||
|
|
1460cf5026 | ||
|
|
7e733c4446 | ||
|
|
735ac2eb07 | ||
|
|
c79a5db8f2 | ||
|
|
8e2aba3b78 | ||
|
|
39fed49654 | ||
|
|
a0678857a1 | ||
|
|
38e2091fd2 | ||
|
|
a528d6632a | ||
|
|
ab081e7db9 | ||
|
|
493c56c0fa | ||
|
|
c73b2c5a86 | ||
|
|
02e2b0e48e | ||
|
|
d3b03a536d | ||
|
|
036f1f9850 | ||
|
|
92849e57ce | ||
|
|
32f0d7b121 | ||
|
|
b27bbb49b3 | ||
|
|
23adb4924b | ||
|
|
9b3bb9c14b | ||
|
|
d441361999 | ||
|
|
fb94f2a020 | ||
|
|
7b56a49dae | ||
|
|
212686baae | ||
|
|
4d6fef597c | ||
|
|
8b596a6687 | ||
|
|
8afc9ad506 | ||
|
|
3b08d7d379 | ||
|
|
616ad4af60 | ||
|
|
dbdb35abb5 | ||
|
|
445a05e6ef | ||
|
|
ccad092fc2 | ||
|
|
faa23b430e | ||
|
|
923e5d16ac | ||
|
|
602ac481d7 | ||
|
|
b322396a99 | ||
|
|
b9af7bdb6c | ||
|
|
bdb3ad7f3e | ||
|
|
1fdbf85d47 | ||
|
|
3e3911464f | ||
|
|
be732a4a6b | ||
|
|
e505843dc6 | ||
|
|
ff9489ba10 | ||
|
|
365763d6f7 | ||
|
|
9349a6ba1a | ||
|
|
34f35a5912 | ||
|
|
05f16068ff | ||
|
|
ddda7f4552 | ||
|
|
38406212c3 | ||
|
|
62a0d39ac3 | ||
|
|
0e6ab4e4ee |
@@ -63,17 +63,10 @@ online_delete=256
|
|||||||
[debug_logfile]
|
[debug_logfile]
|
||||||
/var/log/rippled/debug.log
|
/var/log/rippled/debug.log
|
||||||
|
|
||||||
[sntp_servers]
|
|
||||||
time.windows.com
|
|
||||||
time.apple.com
|
|
||||||
time.nist.gov
|
|
||||||
pool.ntp.org
|
|
||||||
|
|
||||||
[ips]
|
[ips]
|
||||||
r.ripple.com 51235
|
r.ripple.com 51235
|
||||||
|
|
||||||
[validators_file]
|
|
||||||
validators.txt
|
|
||||||
|
|
||||||
[rpc_startup]
|
[rpc_startup]
|
||||||
{ "command": "log_level", "severity": "info" }
|
{ "command": "log_level", "severity": "info" }
|
||||||
@@ -170,3 +163,25 @@ fixNFTokenRemint
|
|||||||
# 2.0.0 Amendments
|
# 2.0.0 Amendments
|
||||||
XChainBridge
|
XChainBridge
|
||||||
DID
|
DID
|
||||||
|
# 2.2.0-b3 Amendments
|
||||||
|
fixNFTokenReserve
|
||||||
|
fixInnerObjTemplate
|
||||||
|
fixAMMOverflowOffer
|
||||||
|
PriceOracle
|
||||||
|
fixEmptyDID
|
||||||
|
fixXChainRewardRounding
|
||||||
|
fixPreviousTxnID
|
||||||
|
fixAMMv1_1
|
||||||
|
# 2.3.0 Amendments
|
||||||
|
AMMClawback
|
||||||
|
fixAMMv1_2
|
||||||
|
Credentials
|
||||||
|
NFTokenMintOffer
|
||||||
|
MPTokensV1
|
||||||
|
fixNFTokenPageLinks
|
||||||
|
fixInnerObjTemplate2
|
||||||
|
fixEnforceNFTokenTrustline
|
||||||
|
fixReducedOffersV2
|
||||||
|
DeepFreeze
|
||||||
|
DynamicNFT
|
||||||
|
PermissionedDomains
|
||||||
|
|||||||
30
.coderabbit.yaml
Normal file
30
.coderabbit.yaml
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
# yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json
|
||||||
|
language: "en-US"
|
||||||
|
reviews:
|
||||||
|
# Set the profile for reviews. Assertive profile yields more feedback, that may be considered nitpicky.
|
||||||
|
profile: "chill"
|
||||||
|
# Approve the review once CodeRabbit's comments are resolved. Note: In GitLab, all discussions must be resolved.
|
||||||
|
request_changes_workflow: false
|
||||||
|
# Generate a high level summary of the changes in the PR/MR description.
|
||||||
|
high_level_summary: false
|
||||||
|
# Generate a poem in the walkthrough comment.
|
||||||
|
poem: true
|
||||||
|
# Post review details on each review. Additionally, post a review status when a review is skipped in certain cases.
|
||||||
|
review_status: true
|
||||||
|
# Generate walkthrough in a markdown collapsible section.
|
||||||
|
collapse_walkthrough: false
|
||||||
|
# Generate sequence diagrams in the walkthrough.
|
||||||
|
sequence_diagrams: false
|
||||||
|
# Abort the in-progress review if the pull request is closed or merged.
|
||||||
|
abort_on_close: true
|
||||||
|
auto_review:
|
||||||
|
# Automatic Review | Automatic code review
|
||||||
|
enabled: true
|
||||||
|
# Review draft PRs/MRs.
|
||||||
|
drafts: false
|
||||||
|
# Ignore reviewing if the title of the pull request contains any of these keywords (case-insensitive).
|
||||||
|
ignore_title_keywords:
|
||||||
|
- build(
|
||||||
|
chat:
|
||||||
|
# Enable the bot to reply automatically without requiring the user to tag it.
|
||||||
|
auto_reply: true
|
||||||
58
.github/workflows/codeql-analysis.yml
vendored
58
.github/workflows/codeql-analysis.yml
vendored
@@ -12,13 +12,11 @@
|
|||||||
name: "CodeQL"
|
name: "CodeQL"
|
||||||
|
|
||||||
on:
|
on:
|
||||||
push:
|
|
||||||
branches: [ main, 1.x ]
|
|
||||||
pull_request:
|
pull_request:
|
||||||
# The branches below must be a subset of the branches above
|
# The branches below must be a subset of the branches above
|
||||||
branches: [ main ]
|
branches: [main]
|
||||||
schedule:
|
schedule:
|
||||||
- cron: '44 5 * * 6'
|
- cron: "44 5 * * 6"
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
analyze:
|
analyze:
|
||||||
@@ -28,40 +26,40 @@ jobs:
|
|||||||
strategy:
|
strategy:
|
||||||
fail-fast: false
|
fail-fast: false
|
||||||
matrix:
|
matrix:
|
||||||
language: [ 'javascript' ]
|
language: ["javascript"]
|
||||||
# CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python' ]
|
# CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python' ]
|
||||||
# Learn more:
|
# Learn more:
|
||||||
# https://docs.github.com/en/free-pro-team@latest/github/finding-security-vulnerabilities-and-errors-in-your-code/configuring-code-scanning#changing-the-languages-that-are-analyzed
|
# https://docs.github.com/en/free-pro-team@latest/github/finding-security-vulnerabilities-and-errors-in-your-code/configuring-code-scanning#changing-the-languages-that-are-analyzed
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout repository
|
- name: Checkout repository
|
||||||
uses: actions/checkout@v3
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
# Initializes the CodeQL tools for scanning.
|
# Initializes the CodeQL tools for scanning.
|
||||||
- name: Initialize CodeQL
|
- name: Initialize CodeQL
|
||||||
uses: github/codeql-action/init@v2
|
uses: github/codeql-action/init@v3
|
||||||
with:
|
with:
|
||||||
languages: ${{ matrix.language }}
|
languages: ${{ matrix.language }}
|
||||||
# If you wish to specify custom queries, you can do so here or in a config file.
|
# If you wish to specify custom queries, you can do so here or in a config file.
|
||||||
# By default, queries listed here will override any specified in a config file.
|
# By default, queries listed here will override any specified in a config file.
|
||||||
# Prefix the list here with "+" to use these queries and those in the config file.
|
# Prefix the list here with "+" to use these queries and those in the config file.
|
||||||
# queries: ./path/to/local/query, your-org/your-repo/queries@main
|
# queries: ./path/to/local/query, your-org/your-repo/queries@main
|
||||||
|
|
||||||
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
|
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
|
||||||
# If this step fails, then you should remove it and run the build manually (see below)
|
# If this step fails, then you should remove it and run the build manually (see below)
|
||||||
- name: Autobuild
|
- name: Autobuild
|
||||||
uses: github/codeql-action/autobuild@v2
|
uses: github/codeql-action/autobuild@v3
|
||||||
|
|
||||||
# ℹ️ Command-line programs to run using the OS shell.
|
# ℹ️ Command-line programs to run using the OS shell.
|
||||||
# 📚 https://git.io/JvXDl
|
# 📚 https://git.io/JvXDl
|
||||||
|
|
||||||
# ✏️ If the Autobuild fails above, remove it and uncomment the following three lines
|
# ✏️ If the Autobuild fails above, remove it and uncomment the following three lines
|
||||||
# and modify them (or add more) to build your code if your project
|
# and modify them (or add more) to build your code if your project
|
||||||
# uses a compiled language
|
# uses a compiled language
|
||||||
|
|
||||||
#- run: |
|
#- run: |
|
||||||
# make bootstrap
|
# make bootstrap
|
||||||
# make release
|
# make release
|
||||||
|
|
||||||
- name: Perform CodeQL Analysis
|
- name: Perform CodeQL Analysis
|
||||||
uses: github/codeql-action/analyze@v2
|
uses: github/codeql-action/analyze@v3
|
||||||
|
|||||||
71
.github/workflows/nodejs.yml
vendored
71
.github/workflows/nodejs.yml
vendored
@@ -4,7 +4,7 @@
|
|||||||
name: Node.js CI
|
name: Node.js CI
|
||||||
|
|
||||||
env:
|
env:
|
||||||
RIPPLED_DOCKER_IMAGE: rippleci/rippled:2.0.0-b4
|
RIPPLED_DOCKER_IMAGE: rippleci/rippled:develop
|
||||||
|
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
@@ -19,22 +19,22 @@ jobs:
|
|||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
node-version: [16.x]
|
node-version: [18.x]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
- name: Use Node.js ${{ matrix.node-version }}
|
||||||
uses: actions/setup-node@v3
|
uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node-version }}
|
node-version: ${{ matrix.node-version }}
|
||||||
|
|
||||||
- name: Setup npm version 9
|
- name: Setup npm version 10
|
||||||
run: |
|
run: |
|
||||||
npm i -g npm@9 --registry=https://registry.npmjs.org
|
npm i -g npm@10 --registry=https://registry.npmjs.org
|
||||||
|
|
||||||
- name: Cache node modules
|
- name: Cache node modules
|
||||||
id: cache-nodemodules
|
id: cache-nodemodules
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
env:
|
env:
|
||||||
cache-name: cache-node-modules
|
cache-name: cache-node-modules
|
||||||
with:
|
with:
|
||||||
@@ -45,7 +45,6 @@ jobs:
|
|||||||
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
||||||
${{ runner.os }}-deps-
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install Dependencies
|
||||||
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
||||||
@@ -60,22 +59,22 @@ jobs:
|
|||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
node-version: [16.x, 18.x, 20.x]
|
node-version: [18.x, 20.x, 22.x]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
- name: Use Node.js ${{ matrix.node-version }}
|
||||||
uses: actions/setup-node@v3
|
uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node-version }}
|
node-version: ${{ matrix.node-version }}
|
||||||
|
|
||||||
- name: Setup npm version 9
|
- name: Setup npm version 10
|
||||||
run: |
|
run: |
|
||||||
npm i -g npm@9 --registry=https://registry.npmjs.org
|
npm i -g npm@10 --registry=https://registry.npmjs.org
|
||||||
|
|
||||||
- name: Cache node modules
|
- name: Cache node modules
|
||||||
id: cache-nodemodules
|
id: cache-nodemodules
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
env:
|
env:
|
||||||
cache-name: cache-node-modules
|
cache-name: cache-node-modules
|
||||||
with:
|
with:
|
||||||
@@ -86,7 +85,6 @@ jobs:
|
|||||||
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
||||||
${{ runner.os }}-deps-
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install Dependencies
|
||||||
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
||||||
@@ -101,27 +99,27 @@ jobs:
|
|||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
node-version: [16.x, 18.x, 20.x]
|
node-version: [18.x, 20.x, 22.x]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Run docker in background
|
- name: Run docker in background
|
||||||
run: |
|
run: |
|
||||||
docker run --detach --rm --name rippled-service -p 6006:6006 --volume "${{ github.workspace }}/.ci-config/":"/opt/ripple/etc/" --health-cmd="wget localhost:6006 || exit 1" --health-interval=5s --health-retries=10 --health-timeout=2s --env GITHUB_ACTIONS=true --env CI=true ${{ env.RIPPLED_DOCKER_IMAGE }} /opt/ripple/bin/rippled -a --conf /opt/ripple/etc/rippled.cfg
|
docker run --detach --rm -p 6006:6006 --volume "${{ github.workspace }}/.ci-config/":"/etc/opt/ripple/" --name rippled-service --health-cmd="rippled server_info || exit 1" --health-interval=5s --health-retries=10 --health-timeout=2s --env GITHUB_ACTIONS=true --env CI=true --entrypoint bash ${{ env.RIPPLED_DOCKER_IMAGE }} -c "rippled -a"
|
||||||
|
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
- name: Use Node.js ${{ matrix.node-version }}
|
||||||
uses: actions/setup-node@v3
|
uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node-version }}
|
node-version: ${{ matrix.node-version }}
|
||||||
|
|
||||||
- name: Setup npm version 9
|
- name: Setup npm version 10
|
||||||
run: |
|
run: |
|
||||||
npm i -g npm@9 --registry=https://registry.npmjs.org
|
npm i -g npm@10 --registry=https://registry.npmjs.org
|
||||||
|
|
||||||
- name: Cache node modules
|
- name: Cache node modules
|
||||||
id: cache-nodemodules
|
id: cache-nodemodules
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
env:
|
env:
|
||||||
cache-name: cache-node-modules
|
cache-name: cache-node-modules
|
||||||
with:
|
with:
|
||||||
@@ -132,7 +130,6 @@ jobs:
|
|||||||
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
||||||
${{ runner.os }}-deps-
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install Dependencies
|
||||||
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
||||||
@@ -153,27 +150,27 @@ jobs:
|
|||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
node-version: [16.x]
|
node-version: [18.x]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
- name: Use Node.js ${{ matrix.node-version }}
|
||||||
uses: actions/setup-node@v3
|
uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node-version }}
|
node-version: ${{ matrix.node-version }}
|
||||||
|
|
||||||
- name: Run docker in background
|
- name: Run docker in background
|
||||||
run: |
|
run: |
|
||||||
docker run --detach --rm --name rippled-service -p 6006:6006 --volume "${{ github.workspace }}/.ci-config/":"/opt/ripple/etc/" --health-cmd="wget localhost:6006 || exit 1" --health-interval=5s --health-retries=10 --health-timeout=2s --env GITHUB_ACTIONS=true --env CI=true ${{ env.RIPPLED_DOCKER_IMAGE }} /opt/ripple/bin/rippled -a --conf /opt/ripple/etc/rippled.cfg
|
docker run --detach --rm -p 6006:6006 --volume "${{ github.workspace }}/.ci-config/":"/etc/opt/ripple/" --name rippled-service --health-cmd="rippled server_info || exit 1" --health-interval=5s --health-retries=10 --health-timeout=2s --env GITHUB_ACTIONS=true --env CI=true --entrypoint bash ${{ env.RIPPLED_DOCKER_IMAGE }} -c "rippled -a"
|
||||||
|
|
||||||
- name: Setup npm version 9
|
- name: Setup npm version 10
|
||||||
run: |
|
run: |
|
||||||
npm i -g npm@9 --registry=https://registry.npmjs.org
|
npm i -g npm@10 --registry=https://registry.npmjs.org
|
||||||
|
|
||||||
- name: Cache node modules
|
- name: Cache node modules
|
||||||
id: cache-nodemodules
|
id: cache-nodemodules
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
env:
|
env:
|
||||||
cache-name: cache-node-modules
|
cache-name: cache-node-modules
|
||||||
with:
|
with:
|
||||||
@@ -184,7 +181,6 @@ jobs:
|
|||||||
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
||||||
${{ runner.os }}-deps-
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install Dependencies
|
||||||
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
||||||
@@ -205,22 +201,22 @@ jobs:
|
|||||||
|
|
||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
node-version: [16.x, 18.x, 20.x]
|
node-version: [18.x, 20.x, 22.x]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
- name: Use Node.js ${{ matrix.node-version }}
|
- name: Use Node.js ${{ matrix.node-version }}
|
||||||
uses: actions/setup-node@v3
|
uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: ${{ matrix.node-version }}
|
node-version: ${{ matrix.node-version }}
|
||||||
|
|
||||||
- name: Setup npm version 9
|
- name: Setup npm version 10
|
||||||
run: |
|
run: |
|
||||||
npm i -g npm@9 --registry=https://registry.npmjs.org
|
npm i -g npm@10 --registry=https://registry.npmjs.org
|
||||||
|
|
||||||
- name: Cache node modules
|
- name: Cache node modules
|
||||||
id: cache-nodemodules
|
id: cache-nodemodules
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
env:
|
env:
|
||||||
cache-name: cache-node-modules
|
cache-name: cache-node-modules
|
||||||
with:
|
with:
|
||||||
@@ -231,7 +227,6 @@ jobs:
|
|||||||
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
key: ${{ runner.os }}-deps-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }}
|
||||||
restore-keys: |
|
restore-keys: |
|
||||||
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
${{ runner.os }}-deps-${{ matrix.node-version }}-
|
||||||
${{ runner.os }}-deps-
|
|
||||||
|
|
||||||
- name: Install Dependencies
|
- name: Install Dependencies
|
||||||
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
if: steps.cache-nodemodules.outputs.cache-hit != 'true'
|
||||||
|
|||||||
2
.vscode/settings.json
vendored
2
.vscode/settings.json
vendored
@@ -39,7 +39,7 @@
|
|||||||
"enable": true
|
"enable": true
|
||||||
},
|
},
|
||||||
"editor.codeActionsOnSave": {
|
"editor.codeActionsOnSave": {
|
||||||
"source.fixAll.eslint": true
|
"source.fixAll.eslint": "explicit"
|
||||||
},
|
},
|
||||||
"files.insertFinalNewline": true,
|
"files.insertFinalNewline": true,
|
||||||
"files.trimFinalNewlines": true,
|
"files.trimFinalNewlines": true,
|
||||||
|
|||||||
@@ -58,6 +58,10 @@ Warning: Use at your own risk.
|
|||||||
|
|
||||||
XRP Ledger explorer, API, metrics, and analytics using a graph database that is synchronized live with the XRPL.
|
XRP Ledger explorer, API, metrics, and analytics using a graph database that is synchronized live with the XRPL.
|
||||||
|
|
||||||
|
- **[XRPLWin](https://xrplwin.com)**
|
||||||
|
|
||||||
|
XRP Ledger and Xahau explorer, Hooks explorer, metrics, and analytics using a XWA backend that is synchronized live with the XRPL and Xahau.
|
||||||
|
|
||||||
## Data monitoring
|
## Data monitoring
|
||||||
|
|
||||||
- **[zerptracker](https://zerptracker.com)**
|
- **[zerptracker](https://zerptracker.com)**
|
||||||
|
|||||||
@@ -12,7 +12,7 @@
|
|||||||
|
|
||||||
### Requirements
|
### Requirements
|
||||||
|
|
||||||
We use Node v16 for development - that is the version that our linters require.
|
We use Node v18 for development - that is the version that our linters require.
|
||||||
You must also use `npm` v7. You can check your `npm` version with:
|
You must also use `npm` v7. You can check your `npm` version with:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
@@ -64,18 +64,20 @@ From the top-level xrpl.js folder (one level above `packages`), run the followin
|
|||||||
```bash
|
```bash
|
||||||
npm install
|
npm install
|
||||||
# sets up the rippled standalone Docker container - you can skip this step if you already have it set up
|
# sets up the rippled standalone Docker container - you can skip this step if you already have it set up
|
||||||
docker run -p 6006:6006 --interactive -t --volume $PWD/.ci-config:/opt/ripple/etc/ --platform linux/amd64 rippleci/rippled:2.0.0-b4 /opt/ripple/bin/rippled -a --conf /opt/ripple/etc/rippled.cfg
|
docker run -p 6006:6006 --rm -it --name rippled_standalone --volume $PWD/.ci-config:/etc/opt/ripple/ --entrypoint bash rippleci/rippled:develop -c 'rippled -a'
|
||||||
npm run build
|
npm run build
|
||||||
npm run test:integration
|
npm run test:integration
|
||||||
```
|
```
|
||||||
|
|
||||||
Breaking down the command:
|
Breaking down the command:
|
||||||
* `docker run -p 6006:6006` starts a Docker container with an open port for admin WebSocket requests.
|
* `docker run -p 6006:6006` starts a Docker container with an open port for admin WebSocket requests.
|
||||||
* `--interactive` allows you to interact with the container.
|
`--rm` tells docker to close the container after processes are done running.
|
||||||
* `-t` starts a terminal in the container for you to send commands to.
|
* `-it` allows you to interact with the container.
|
||||||
* `--volume $PWD/.ci-config:/config/` identifies the `rippled.cfg` and `validators.txt` to import. It must be an absolute path, so we use `$PWD` instead of `./`.
|
`--name rippled_standalone` is an instance name for clarity
|
||||||
|
* `--volume $PWD/.ci-config:/etc/opt/ripple/` identifies the `rippled.cfg` and `validators.txt` to import. It must be an absolute path, so we use `$PWD` instead of `./`.
|
||||||
* `rippleci/rippled` is an image that is regularly updated with the latest `rippled` releases
|
* `rippleci/rippled` is an image that is regularly updated with the latest `rippled` releases
|
||||||
* `/opt/ripple/bin/rippled -a --conf /opt/ripple/etc/rippled.cfg` starts `rippled` in standalone mode
|
* `--entrypoint bash rippleci/rippled:develop` manually overrides the entrypoint (for the latest version of rippled on the `develop` branch)
|
||||||
|
* `-c 'rippled -a'` provides the bash command to start `rippled` in standalone mode from the manual entrypoint
|
||||||
|
|
||||||
### Browser Tests
|
### Browser Tests
|
||||||
|
|
||||||
@@ -90,7 +92,7 @@ This should be run from the `xrpl.js` top level folder (one above the `packages`
|
|||||||
```bash
|
```bash
|
||||||
npm run build
|
npm run build
|
||||||
# sets up the rippled standalone Docker container - you can skip this step if you already have it set up
|
# sets up the rippled standalone Docker container - you can skip this step if you already have it set up
|
||||||
docker run -p 6006:6006 --interactive -t --volume $PWD/.ci-config:/opt/ripple/etc/ --platform linux/amd64 rippleci/rippled:2.0.0-b3 /opt/ripple/bin/rippled -a --conf /opt/ripple/etc/rippled.cfg
|
docker run -p 6006:6006 --rm -it --name rippled_standalone --volume $PWD/.ci-config:/etc/opt/ripple/ --entrypoint bash rippleci/rippled:develop -c 'rippled -a'
|
||||||
npm run test:browser
|
npm run test:browser
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -104,6 +106,8 @@ The 4 packages currently here are:
|
|||||||
2. ripple-binary-codec - A library for serializing and deserializing transactions for the ledger.
|
2. ripple-binary-codec - A library for serializing and deserializing transactions for the ledger.
|
||||||
3. ripple-keypairs - A library for generating and using cryptographic keypairs.
|
3. ripple-keypairs - A library for generating and using cryptographic keypairs.
|
||||||
4. ripple-address-codec - A library for encoding and decoding XRP Ledger addresses and seeds.
|
4. ripple-address-codec - A library for encoding and decoding XRP Ledger addresses and seeds.
|
||||||
|
5. isomorphic - A collection of isomorphic implementations of crypto and utility functions.
|
||||||
|
6. secret-numbers - Generate XRPL Accounts with a number-based secret: 8 chunks of 6 digits.
|
||||||
|
|
||||||
Each package has it's own README which dives deeper into what it's main purpose is, and the core functionality it offers.
|
Each package has it's own README which dives deeper into what it's main purpose is, and the core functionality it offers.
|
||||||
They also run tests independently as they were originally in separate repositories.
|
They also run tests independently as they were originally in separate repositories.
|
||||||
@@ -128,13 +132,13 @@ For every file in `src`, we try to have a corresponding file in `test` with unit
|
|||||||
|
|
||||||
The goal is to maintain above 80% code coverage, and generally any new feature or bug fix should be accompanied by unit tests, and integration tests if applicable.
|
The goal is to maintain above 80% code coverage, and generally any new feature or bug fix should be accompanied by unit tests, and integration tests if applicable.
|
||||||
|
|
||||||
For an example of a unit test, check out the [autofill tests here](./packages/xrpl/test/client/autofill.ts).
|
For an example of a unit test, check out the [autofill tests here](./packages/xrpl/test/client/autofill.test.ts).
|
||||||
|
|
||||||
If your code connects to the ledger (ex. Adding a new transaction type) it's handy to write integration tests to ensure that you can successfully interact with the ledger. Integration tests are generally run against a docker instance of rippled which contains the latest updates. Since standalone mode allows us to manually close ledgers, this allows us to run integration tests at a much faster rate than if we had to wait 4-5 seconds per transaction for the ledger to validate the transaction. [See above](#running-tests) for how to start up the docker container to run integration tests.
|
If your code connects to the ledger (ex. Adding a new transaction type) it's handy to write integration tests to ensure that you can successfully interact with the ledger. Integration tests are generally run against a docker instance of rippled which contains the latest updates. Since standalone mode allows us to manually close ledgers, this allows us to run integration tests at a much faster rate than if we had to wait 4-5 seconds per transaction for the ledger to validate the transaction. [See above](#running-tests) for how to start up the docker container to run integration tests.
|
||||||
|
|
||||||
All integration tests should be written in the `test/integration` folder, with new `Requests` and `Transactions` tests being in their respective folders.
|
All integration tests should be written in the `test/integration` folder, with new `Requests` and `Transactions` tests being in their respective folders.
|
||||||
|
|
||||||
For an example of how to write an integration test for `xrpl.js`, you can look at the [Payment integration test](./packages/xrpl/test/integration/transactions/payment.ts).
|
For an example of how to write an integration test for `xrpl.js`, you can look at the [Payment integration test](./packages/xrpl/test/integration/transactions/payment.test.ts).
|
||||||
|
|
||||||
## Generate reference docs
|
## Generate reference docs
|
||||||
|
|
||||||
|
|||||||
33
MIGRATION.md
33
MIGRATION.md
@@ -2,12 +2,15 @@
|
|||||||
|
|
||||||
In xrpl.js 3.0, we've made significant improvements that result in a 60% reduction in bundle size for browser applications. We've also eliminated the need for polyfills with minimal disruption to existing code. This was achieved by replacing node-specific dependencies with ones that are compatible with browsers.
|
In xrpl.js 3.0, we've made significant improvements that result in a 60% reduction in bundle size for browser applications. We've also eliminated the need for polyfills with minimal disruption to existing code. This was achieved by replacing node-specific dependencies with ones that are compatible with browsers.
|
||||||
|
|
||||||
The main change you'll notice is the update replacing `Buffer` with `Uint8Array` across the board. This was done since browsers don't support `Buffer`. Fortunately, this transition is relatively straightforward, as `Buffer` is a subclass of `Uint8Array`, meaning in many circumstances `Buffer` can be directly replaced by `Uint8Array`. The primary difference is that `Buffer` has additional helper functions. We've listed the affected client library functions below in the `Uint8Array` section for your reference.
|
The two main changes you'll notice are:
|
||||||
|
* A breaking change to `Wallet` object creation, to use a more performant algorithm by default. See [here](#8-wallet-functions-default-to-ed25519-instead-of-secp256k1-signing-algorithm) for details.
|
||||||
|
* Replacing `Buffer` with `Uint8Array` across the board. This was done since browsers don't support `Buffer`. Fortunately, this transition is relatively straightforward, as `Buffer` is a subclass of `Uint8Array`, meaning in many circumstances `Buffer` can be directly replaced by `Uint8Array`. The primary difference is that `Buffer` has additional helper functions. We've listed the affected client library functions below in the `Uint8Array` section for your reference.
|
||||||
|
|
||||||
This migration guide also applies to:
|
This migration guide also applies to:
|
||||||
`ripple-address-codec` 4.3.1 -> 5.0.0
|
- `ripple-address-codec` 4.3.1 -> 5.0.0
|
||||||
`ripple-binary-codec` 1.11.0 -> 2.0.0
|
- `ripple-binary-codec` 1.11.0 -> 2.0.0
|
||||||
`ripple-keypairs` 1.3.1 -> 2.0.0
|
- `ripple-keypairs` 1.3.1 -> 2.0.0
|
||||||
|
- `xrpl-secret-numbers` 0.3.4 -> `@xrplf/secret-numbers` 1.0.0
|
||||||
|
|
||||||
# Why update to 3.0?
|
# Why update to 3.0?
|
||||||
|
|
||||||
@@ -229,9 +232,27 @@ This was done to remove a hard dependency on `https-proxy-agent` when running
|
|||||||
authorization: 'authorization'
|
authorization: 'authorization'
|
||||||
}`
|
}`
|
||||||
|
|
||||||
### 8. Bug fix: Setting an explicit `algorithm` when generating a wallet works now
|
### 8. `Wallet` functions default to `ed25519` instead of `secp256k1` signing algorithm
|
||||||
|
|
||||||
`Wallet.generate()` and `Wallet.fromSeed` were ignoring the `algorithm` parameter. This means that if you were manually specifying `algorithm` in any `Wallet` constructors, you may generate a different `Wallet` keypair when upgrading to 3.0. In that case to get the same generated wallets as before, don’t specify the `algorithm` parameter.
|
In previous releases of this library, `Wallet.generate()` and `Wallet.fromSeed` were ignoring the `algorithm` parameter. Instead, the algorithm was assumed from the seed provided; if it started with `sEd`, it would use `ed25519`, and otherwise it would use `secp256k1`. However, seeds do not actually have algorithms; a seed starting with `s...` can still use the `ed25519` algorithm.
|
||||||
|
|
||||||
|
With 3.0, we updated the default signing algorithm used by the `Wallet` object to always be `ed25519` in order to default to the higher-performance algorithm. This is a breaking change to all functions used to generate a Wallet, so if you have a pre-existing XRPL account that you're using to generate a specific Wallet using older versions of xrpl.js, you may need to specify that you are using `secp256k1` as the algorithm to decode your private key / seed / etc to get the same behavior as before. See below for specifically how to update your code.
|
||||||
|
|
||||||
|
If you are creating new accounts each time (ex. via `Client.fundWallet` or `Wallet.generate`), you do not need to specify the signing algorithm.
|
||||||
|
|
||||||
|
**Before**
|
||||||
|
```
|
||||||
|
Wallet.fromSeed('s...')
|
||||||
|
Wallet.fromEntropy(entropy)
|
||||||
|
deriveKeyPair(seed="s...")
|
||||||
|
```
|
||||||
|
|
||||||
|
**After**
|
||||||
|
```
|
||||||
|
Wallet.fromSeed(seed='s...',algorithm: 'ecdsa-secp256k1')
|
||||||
|
Wallet.fromEntropy(entropy, opts={algorithm: 'ecdsa-secp256k1'})
|
||||||
|
deriveKeypair(seed='s...', opts={ algorithm: 'ecdsa-secp256k1' }) (ripple-keypairs)
|
||||||
|
```
|
||||||
|
|
||||||
### 9. `AssertionError` → `Error`
|
### 9. `AssertionError` → `Error`
|
||||||
|
|
||||||
|
|||||||
@@ -19,13 +19,13 @@ See the full reference documentation for all classes, methods, and utilities.
|
|||||||
4. Subscribing to changes in the ledger ([Ex. ledger, transactions, & more...](https://xrpl.org/subscribe.html))
|
4. Subscribing to changes in the ledger ([Ex. ledger, transactions, & more...](https://xrpl.org/subscribe.html))
|
||||||
5. Parsing ledger data into more convenient formats ([`xrpToDrops`](https://js.xrpl.org/functions/xrpToDrops.html) and [`rippleTimeToISOTime`](https://js.xrpl.org/functions/rippleTimeToISOTime.html))
|
5. Parsing ledger data into more convenient formats ([`xrpToDrops`](https://js.xrpl.org/functions/xrpToDrops.html) and [`rippleTimeToISOTime`](https://js.xrpl.org/functions/rippleTimeToISOTime.html))
|
||||||
|
|
||||||
All of which works in Node.js (tested for v16+) & web browsers (tested for Chrome).
|
All of which works in Node.js (tested for v18+) & web browsers (tested for Chrome).
|
||||||
|
|
||||||
# Quickstart
|
# Quickstart
|
||||||
|
|
||||||
### Requirements
|
### Requirements
|
||||||
|
|
||||||
+ **[Node.js v16](https://nodejs.org/)** is recommended. We also support v18 and v20. Other versions may work but are not frequently tested.
|
+ **[Node.js v18](https://nodejs.org/)** is recommended. We also support v20 and v22. Other versions may work but are not frequently tested.
|
||||||
|
|
||||||
### Installing xrpl.js
|
### Installing xrpl.js
|
||||||
|
|
||||||
@@ -56,7 +56,7 @@ async function main() {
|
|||||||
});
|
});
|
||||||
console.log(response);
|
console.log(response);
|
||||||
|
|
||||||
client.disconnect();
|
await client.disconnect();
|
||||||
}
|
}
|
||||||
main();
|
main();
|
||||||
```
|
```
|
||||||
|
|||||||
17493
package-lock.json
generated
17493
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@@ -25,7 +25,7 @@
|
|||||||
"@types/chai": "^4.2.21",
|
"@types/chai": "^4.2.21",
|
||||||
"@types/jest": "^29.2.2",
|
"@types/jest": "^29.2.2",
|
||||||
"@types/lodash": "^4.14.136",
|
"@types/lodash": "^4.14.136",
|
||||||
"@types/node": "^16.18.38",
|
"@types/node": "^18.19.29",
|
||||||
"@types/ws": "^8.2.0",
|
"@types/ws": "^8.2.0",
|
||||||
"@typescript-eslint/eslint-plugin": "^5.28.0",
|
"@typescript-eslint/eslint-plugin": "^5.28.0",
|
||||||
"@typescript-eslint/parser": "^5.28.0",
|
"@typescript-eslint/parser": "^5.28.0",
|
||||||
@@ -58,13 +58,13 @@
|
|||||||
"typescript": "^5.1.6",
|
"typescript": "^5.1.6",
|
||||||
"webpack": "^5.81.0",
|
"webpack": "^5.81.0",
|
||||||
"webpack-bundle-analyzer": "^4.1.0",
|
"webpack-bundle-analyzer": "^4.1.0",
|
||||||
"webpack-cli": "^5.0.1"
|
"webpack-cli": "^6.0.1"
|
||||||
},
|
},
|
||||||
"workspaces": [
|
"workspaces": [
|
||||||
"./packages/*"
|
"./packages/*"
|
||||||
],
|
],
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=16.0.0",
|
"node": ">=18.0.0",
|
||||||
"npm": ">=7.10.0 < 10.0.0"
|
"npm": ">=7.10.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,13 @@
|
|||||||
# @xrplf/isomorphic Release History
|
# @xrplf/isomorphic Release History
|
||||||
|
|
||||||
|
## Unreleased
|
||||||
|
|
||||||
|
## 1.0.1 (2024-06-03)
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
|
||||||
|
* Throw error if `hexToBytes` or `hexToString` is provided a string that is not in hex
|
||||||
|
|
||||||
## 1.0.0 (2024-02-01)
|
## 1.0.0 (2024-02-01)
|
||||||
|
|
||||||
Initial release providing isomorphic and tree-shakable implementations of:
|
Initial release providing isomorphic and tree-shakable implementations of:
|
||||||
@@ -14,21 +22,3 @@ Initial release providing isomorphic and tree-shakable implementations of:
|
|||||||
* randomBytes
|
* randomBytes
|
||||||
* stringToHex
|
* stringToHex
|
||||||
* ws
|
* ws
|
||||||
|
|
||||||
## 1.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
## Added
|
|
||||||
* hexToString
|
|
||||||
* stringToHex
|
|
||||||
|
|
||||||
## 1.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
Initial release providing isomorphic and tree-shakable implementations of:
|
|
||||||
|
|
||||||
* ripemd160
|
|
||||||
* sha256
|
|
||||||
* sha512
|
|
||||||
* bytesToHash
|
|
||||||
* hashToBytes
|
|
||||||
* randomBytes
|
|
||||||
* ws_
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@xrplf/isomorphic",
|
"name": "@xrplf/isomorphic",
|
||||||
"version": "1.0.0",
|
"version": "1.0.1",
|
||||||
"description": "A collection of isomorphic and tree-shakeable crypto hashes and utils for xrpl.js",
|
"description": "A collection of isomorphic and tree-shakeable crypto hashes and utils for xrpl.js",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"crypto",
|
"crypto",
|
||||||
@@ -33,7 +33,7 @@
|
|||||||
"ws": "^8.13.0"
|
"ws": "^8.13.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/node": "^16.18.38",
|
"@types/node": "^18.18.38",
|
||||||
"@types/ws": "^8.5.6"
|
"@types/ws": "^8.5.6"
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
@@ -43,6 +43,6 @@
|
|||||||
"license": "ISC",
|
"license": "ISC",
|
||||||
"prettier": "@xrplf/prettier-config",
|
"prettier": "@xrplf/prettier-config",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=16.0.0"
|
"node": ">=18.0.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import type {
|
|||||||
RandomBytesFn,
|
RandomBytesFn,
|
||||||
StringToHexFn,
|
StringToHexFn,
|
||||||
} from './types'
|
} from './types'
|
||||||
|
import { HEX_REGEX } from './shared'
|
||||||
|
|
||||||
/* eslint-disable func-style -- Typed to ensure uniformity between node and browser implementations and docs */
|
/* eslint-disable func-style -- Typed to ensure uniformity between node and browser implementations and docs */
|
||||||
export const bytesToHex: typeof BytesToHexFn = (bytes) => {
|
export const bytesToHex: typeof BytesToHexFn = (bytes) => {
|
||||||
@@ -22,6 +23,9 @@ export const bytesToHex: typeof BytesToHexFn = (bytes) => {
|
|||||||
export const hexToBytes: typeof HexToBytesFn = (hex): Uint8Array => {
|
export const hexToBytes: typeof HexToBytesFn = (hex): Uint8Array => {
|
||||||
const len = hex.length
|
const len = hex.length
|
||||||
const array = new Uint8Array(len / 2)
|
const array = new Uint8Array(len / 2)
|
||||||
|
if (!HEX_REGEX.test(hex)) {
|
||||||
|
throw new Error('Invalid hex string')
|
||||||
|
}
|
||||||
for (let i = 0; i < array.length; i++) {
|
for (let i = 0; i < array.length; i++) {
|
||||||
const j = i * 2
|
const j = i * 2
|
||||||
const hexByte = hex.slice(j, j + 2)
|
const hexByte = hex.slice(j, j + 2)
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import { randomBytes as cryptoRandomBytes } from 'crypto'
|
import { randomBytes as cryptoRandomBytes } from 'crypto'
|
||||||
import type { BytesToHexFn, HexToBytesFn, RandomBytesFn } from './types'
|
import type { BytesToHexFn, HexToBytesFn, RandomBytesFn } from './types'
|
||||||
import { HexToStringFn, StringToHexFn } from './types'
|
import { HexToStringFn, StringToHexFn } from './types'
|
||||||
|
import { HEX_REGEX } from './shared'
|
||||||
|
|
||||||
const OriginalBuffer = Symbol('OriginalBuffer')
|
const OriginalBuffer = Symbol('OriginalBuffer')
|
||||||
|
|
||||||
@@ -64,6 +65,9 @@ export const bytesToHex: typeof BytesToHexFn = (bytes) => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const hexToBytes: typeof HexToBytesFn = (hex) => {
|
export const hexToBytes: typeof HexToBytesFn = (hex) => {
|
||||||
|
if (!HEX_REGEX.test(hex)) {
|
||||||
|
throw new Error('Invalid hex string')
|
||||||
|
}
|
||||||
return toUint8Array(Buffer.from(hex, 'hex'))
|
return toUint8Array(Buffer.from(hex, 'hex'))
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -75,6 +79,9 @@ export const hexToString: typeof HexToStringFn = (
|
|||||||
hex: string,
|
hex: string,
|
||||||
encoding = 'utf8',
|
encoding = 'utf8',
|
||||||
): string => {
|
): string => {
|
||||||
|
if (!HEX_REGEX.test(hex)) {
|
||||||
|
throw new Error('Invalid hex string')
|
||||||
|
}
|
||||||
return new TextDecoder(encoding).decode(hexToBytes(hex))
|
return new TextDecoder(encoding).decode(hexToBytes(hex))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
import { concatBytes } from '@noble/hashes/utils'
|
import { concatBytes } from '@noble/hashes/utils'
|
||||||
|
|
||||||
|
export const HEX_REGEX = /^[A-F0-9]*$/iu
|
||||||
|
|
||||||
export function concat(views: Uint8Array[]): Uint8Array {
|
export function concat(views: Uint8Array[]): Uint8Array {
|
||||||
return concatBytes(...views)
|
return concatBytes(...views)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,10 +23,18 @@ describe('utils', function () {
|
|||||||
expect(hexToBytes('DEADBEEF')).toEqual(new Uint8Array([222, 173, 190, 239]))
|
expect(hexToBytes('DEADBEEF')).toEqual(new Uint8Array([222, 173, 190, 239]))
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('hexToBytes - DEADBEEF', () => {
|
||||||
|
expect(hexToBytes('DEADBEEF')).toEqual(new Uint8Array([222, 173, 190, 239]))
|
||||||
|
})
|
||||||
|
|
||||||
it('bytesToHex - DEADBEEF', () => {
|
it('bytesToHex - DEADBEEF', () => {
|
||||||
expect(bytesToHex([222, 173, 190, 239])).toEqual('DEADBEEF')
|
expect(bytesToHex([222, 173, 190, 239])).toEqual('DEADBEEF')
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('bytesToHex - bad hex', () => {
|
||||||
|
expect(() => hexToBytes('hello')).toThrow(new Error('Invalid hex string'))
|
||||||
|
})
|
||||||
|
|
||||||
it('bytesToHex - 010203', () => {
|
it('bytesToHex - 010203', () => {
|
||||||
expect(bytesToHex([1, 2, 3])).toEqual('010203')
|
expect(bytesToHex([1, 2, 3])).toEqual('010203')
|
||||||
})
|
})
|
||||||
@@ -43,6 +51,10 @@ describe('utils', function () {
|
|||||||
expect(hexToString('6465616462656566D68D')).toEqual('deadbeef֍')
|
expect(hexToString('6465616462656566D68D')).toEqual('deadbeef֍')
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('hexToString - bad hex', () => {
|
||||||
|
expect(() => hexToString('hello')).toThrow(new Error('Invalid hex string'))
|
||||||
|
})
|
||||||
|
|
||||||
it('stringToHex - deadbeef+infinity symbol (utf8)', () => {
|
it('stringToHex - deadbeef+infinity symbol (utf8)', () => {
|
||||||
expect(stringToHex('deadbeef֍')).toEqual('6465616462656566D68D')
|
expect(stringToHex('deadbeef֍')).toEqual('6465616462656566D68D')
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -15,25 +15,6 @@
|
|||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
||||||
* Execute test in a browser in addition to node
|
* Execute test in a browser in addition to node
|
||||||
|
|
||||||
## 5.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* `Buffer` has been replaced with `UInt8Array` for both params and return values. `Buffer` may continue to work with params since they extend `UInt8Arrays`.
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
|
||||||
|
|
||||||
## 5.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* Bump typescript to 5.x
|
|
||||||
* Remove Node 14 support
|
|
||||||
* Remove `assert` dependency. If you were catching `AssertionError` you need to change to `Error`.
|
|
||||||
* Remove `create-hash` in favor of `@noble/hashes`
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Execute test in a browser in addition to node
|
|
||||||
|
|
||||||
## 4.3.1 (2023-09-27)
|
## 4.3.1 (2023-09-27)
|
||||||
### Fixed
|
### Fixed
|
||||||
* Fix source-maps not finding their designated source
|
* Fix source-maps not finding their designated source
|
||||||
|
|||||||
@@ -34,6 +34,6 @@
|
|||||||
},
|
},
|
||||||
"prettier": "@xrplf/prettier-config",
|
"prettier": "@xrplf/prettier-config",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">= 16"
|
"node": ">= 18"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,26 @@
|
|||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
|
|
||||||
|
## 2.3.0 (2025-2-13)
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Support for the AMMClawback amendment (XLS-73)
|
||||||
|
* Support for the Permissioned Domains amendment (XLS-80).
|
||||||
|
|
||||||
|
## 2.2.0 (2024-12-23)
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Support for the Multi-Purpose Token amendment (XLS-33)
|
||||||
|
|
||||||
|
## 2.1.0 (2024-06-03)
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Support for the Price Oracles amendment (XLS-47).
|
||||||
|
* Support for the `DynamicNFT` amendment (XLS-46)
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
* Better error handling/error messages for serialization/deserialization errors.
|
||||||
|
|
||||||
## 2.0.0 (2024-02-01)
|
## 2.0.0 (2024-02-01)
|
||||||
|
|
||||||
### BREAKING CHANGES
|
### BREAKING CHANGES
|
||||||
@@ -19,23 +39,6 @@
|
|||||||
* `Comparable` is now a generic type so that it allows `compareTo` methods to take more that the type itself.
|
* `Comparable` is now a generic type so that it allows `compareTo` methods to take more that the type itself.
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
||||||
|
|
||||||
## 2.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* `Buffer` has been replaced with `UInt8Array` for both params and return values. `Buffer` may continue to work with params since they extend `UInt8Arrays`.
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
|
||||||
|
|
||||||
## 2.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* Bump typescript to 5.x
|
|
||||||
* Remove Node 14 support
|
|
||||||
* Remove decimal.js and big-integer. Use `BigNumber` from `bignumber.js` instead of `Decimal` and the native `BigInt` instead of `bigInt`.
|
|
||||||
* Remove `assert` dependency. If you were catching `AssertionError` you need to change to `Error`.
|
|
||||||
* Remove `create-hash` in favor of `@noble/hashes`
|
|
||||||
|
|
||||||
### Changes
|
### Changes
|
||||||
* Update type definitions which causing errors in tests that the code already supported
|
* Update type definitions which causing errors in tests that the code already supported
|
||||||
* `makeParser` to accept a `Buffer` in addition to `string`
|
* `makeParser` to accept a `Buffer` in addition to `string`
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "ripple-binary-codec",
|
"name": "ripple-binary-codec",
|
||||||
"version": "2.0.0",
|
"version": "2.3.0",
|
||||||
"description": "XRP Ledger binary codec",
|
"description": "XRP Ledger binary codec",
|
||||||
"files": [
|
"files": [
|
||||||
"dist/*",
|
"dist/*",
|
||||||
@@ -11,7 +11,7 @@
|
|||||||
"test": "test"
|
"test": "test"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@xrplf/isomorphic": "^1.0.0",
|
"@xrplf/isomorphic": "^1.0.1",
|
||||||
"bignumber.js": "^9.0.0",
|
"bignumber.js": "^9.0.0",
|
||||||
"ripple-address-codec": "^5.0.0"
|
"ripple-address-codec": "^5.0.0"
|
||||||
},
|
},
|
||||||
@@ -41,6 +41,6 @@
|
|||||||
"readmeFilename": "README.md",
|
"readmeFilename": "README.md",
|
||||||
"prettier": "@xrplf/prettier-config",
|
"prettier": "@xrplf/prettier-config",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">= 16"
|
"node": ">= 18"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -144,14 +144,18 @@ class BinaryParser {
|
|||||||
if (type === 0) {
|
if (type === 0) {
|
||||||
type = this.readUInt8()
|
type = this.readUInt8()
|
||||||
if (type === 0 || type < 16) {
|
if (type === 0 || type < 16) {
|
||||||
throw new Error('Cannot read FieldOrdinal, type_code out of range')
|
throw new Error(
|
||||||
|
`Cannot read FieldOrdinal, type_code ${type} out of range`,
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (nth === 0) {
|
if (nth === 0) {
|
||||||
nth = this.readUInt8()
|
nth = this.readUInt8()
|
||||||
if (nth === 0 || nth < 16) {
|
if (nth === 0 || nth < 16) {
|
||||||
throw new Error('Cannot read FieldOrdinal, field_code out of range')
|
throw new Error(
|
||||||
|
`Cannot read FieldOrdinal, field_code ${nth} out of range`,
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import { JsonObject, SerializedType } from './serialized-type'
|
|||||||
import BigNumber from 'bignumber.js'
|
import BigNumber from 'bignumber.js'
|
||||||
import { bytesToHex, concat, hexToBytes } from '@xrplf/isomorphic/utils'
|
import { bytesToHex, concat, hexToBytes } from '@xrplf/isomorphic/utils'
|
||||||
import { readUInt32BE, writeUInt32BE } from '../utils'
|
import { readUInt32BE, writeUInt32BE } from '../utils'
|
||||||
|
import { Hash192 } from './hash-192'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constants for validating amounts
|
* Constants for validating amounts
|
||||||
@@ -16,6 +17,7 @@ const MAX_IOU_PRECISION = 16
|
|||||||
const MAX_DROPS = new BigNumber('1e17')
|
const MAX_DROPS = new BigNumber('1e17')
|
||||||
const MIN_XRP = new BigNumber('1e-6')
|
const MIN_XRP = new BigNumber('1e-6')
|
||||||
const mask = BigInt(0x00000000ffffffff)
|
const mask = BigInt(0x00000000ffffffff)
|
||||||
|
const mptMask = BigInt(0x8000000000000000)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* BigNumber configuration for Amount IOUs
|
* BigNumber configuration for Amount IOUs
|
||||||
@@ -27,20 +29,28 @@ BigNumber.config({
|
|||||||
],
|
],
|
||||||
})
|
})
|
||||||
|
|
||||||
/**
|
interface AmountObjectIOU extends JsonObject {
|
||||||
* Interface for JSON objects that represent amounts
|
|
||||||
*/
|
|
||||||
interface AmountObject extends JsonObject {
|
|
||||||
value: string
|
value: string
|
||||||
currency: string
|
currency: string
|
||||||
issuer: string
|
issuer: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface AmountObjectMPT extends JsonObject {
|
||||||
|
value: string
|
||||||
|
mpt_issuance_id: string
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Type guard for AmountObject
|
* Interface for JSON objects that represent amounts
|
||||||
*/
|
*/
|
||||||
function isAmountObject(arg): arg is AmountObject {
|
type AmountObject = AmountObjectIOU | AmountObjectMPT
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type guard for AmountObjectIOU
|
||||||
|
*/
|
||||||
|
function isAmountObjectIOU(arg): arg is AmountObjectIOU {
|
||||||
const keys = Object.keys(arg).sort()
|
const keys = Object.keys(arg).sort()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
keys.length === 3 &&
|
keys.length === 3 &&
|
||||||
keys[0] === 'currency' &&
|
keys[0] === 'currency' &&
|
||||||
@@ -49,6 +59,17 @@ function isAmountObject(arg): arg is AmountObject {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type guard for AmountObjectMPT
|
||||||
|
*/
|
||||||
|
function isAmountObjectMPT(arg): arg is AmountObjectMPT {
|
||||||
|
const keys = Object.keys(arg).sort()
|
||||||
|
|
||||||
|
return (
|
||||||
|
keys.length === 2 && keys[0] === 'mpt_issuance_id' && keys[1] === 'value'
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class for serializing/Deserializing Amounts
|
* Class for serializing/Deserializing Amounts
|
||||||
*/
|
*/
|
||||||
@@ -60,7 +81,7 @@ class Amount extends SerializedType {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Construct an amount from an IOU or string amount
|
* Construct an amount from an IOU, MPT or string amount
|
||||||
*
|
*
|
||||||
* @param value An Amount, object representing an IOU, or a string
|
* @param value An Amount, object representing an IOU, or a string
|
||||||
* representing an integer amount
|
* representing an integer amount
|
||||||
@@ -88,7 +109,7 @@ class Amount extends SerializedType {
|
|||||||
return new Amount(amount)
|
return new Amount(amount)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isAmountObject(value)) {
|
if (isAmountObjectIOU(value)) {
|
||||||
const number = new BigNumber(value.value)
|
const number = new BigNumber(value.value)
|
||||||
Amount.assertIouIsValid(number)
|
Amount.assertIouIsValid(number)
|
||||||
|
|
||||||
@@ -124,6 +145,24 @@ class Amount extends SerializedType {
|
|||||||
return new Amount(concat([amount, currency, issuer]))
|
return new Amount(concat([amount, currency, issuer]))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (isAmountObjectMPT(value)) {
|
||||||
|
Amount.assertMptIsValid(value.value)
|
||||||
|
|
||||||
|
let leadingByte = new Uint8Array(1)
|
||||||
|
leadingByte[0] |= 0x60
|
||||||
|
|
||||||
|
const num = BigInt(value.value)
|
||||||
|
|
||||||
|
const intBuf = [new Uint8Array(4), new Uint8Array(4)]
|
||||||
|
writeUInt32BE(intBuf[0], Number(num >> BigInt(32)), 0)
|
||||||
|
writeUInt32BE(intBuf[1], Number(num & BigInt(mask)), 0)
|
||||||
|
|
||||||
|
amount = concat(intBuf)
|
||||||
|
|
||||||
|
const mptIssuanceID = Hash192.from(value.mpt_issuance_id).toBytes()
|
||||||
|
return new Amount(concat([leadingByte, amount, mptIssuanceID]))
|
||||||
|
}
|
||||||
|
|
||||||
throw new Error('Invalid type to construct an Amount')
|
throw new Error('Invalid type to construct an Amount')
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -134,8 +173,12 @@ class Amount extends SerializedType {
|
|||||||
* @returns An Amount object
|
* @returns An Amount object
|
||||||
*/
|
*/
|
||||||
static fromParser(parser: BinaryParser): Amount {
|
static fromParser(parser: BinaryParser): Amount {
|
||||||
const isXRP = parser.peek() & 0x80
|
const isIOU = parser.peek() & 0x80
|
||||||
const numBytes = isXRP ? 48 : 8
|
if (isIOU) return new Amount(parser.read(48))
|
||||||
|
|
||||||
|
// the amount can be either MPT or XRP at this point
|
||||||
|
const isMPT = parser.peek() & 0x20
|
||||||
|
const numBytes = isMPT ? 33 : 8
|
||||||
return new Amount(parser.read(numBytes))
|
return new Amount(parser.read(numBytes))
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -156,7 +199,9 @@ class Amount extends SerializedType {
|
|||||||
const num = (msb << BigInt(32)) | lsb
|
const num = (msb << BigInt(32)) | lsb
|
||||||
|
|
||||||
return `${sign}${num.toString()}`
|
return `${sign}${num.toString()}`
|
||||||
} else {
|
}
|
||||||
|
|
||||||
|
if (this.isIOU()) {
|
||||||
const parser = new BinaryParser(this.toString())
|
const parser = new BinaryParser(this.toString())
|
||||||
const mantissa = parser.read(8)
|
const mantissa = parser.read(8)
|
||||||
const currency = Currency.fromParser(parser) as Currency
|
const currency = Currency.fromParser(parser) as Currency
|
||||||
@@ -182,6 +227,27 @@ class Amount extends SerializedType {
|
|||||||
issuer: issuer.toJSON(),
|
issuer: issuer.toJSON(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this.isMPT()) {
|
||||||
|
const parser = new BinaryParser(this.toString())
|
||||||
|
const leadingByte = parser.read(1)
|
||||||
|
const amount = parser.read(8)
|
||||||
|
const mptID = Hash192.fromParser(parser) as Hash192
|
||||||
|
|
||||||
|
const isPositive = leadingByte[0] & 0x40
|
||||||
|
const sign = isPositive ? '' : '-'
|
||||||
|
|
||||||
|
const msb = BigInt(readUInt32BE(amount.slice(0, 4), 0))
|
||||||
|
const lsb = BigInt(readUInt32BE(amount.slice(4), 0))
|
||||||
|
const num = (msb << BigInt(32)) | lsb
|
||||||
|
|
||||||
|
return {
|
||||||
|
value: `${sign}${num.toString()}`,
|
||||||
|
mpt_issuance_id: mptID.toString(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new Error('Invalid amount to construct JSON')
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -224,6 +290,29 @@ class Amount extends SerializedType {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Validate MPT.value amount
|
||||||
|
*
|
||||||
|
* @param decimal BigNumber object representing MPT.value
|
||||||
|
* @returns void, but will throw if invalid amount
|
||||||
|
*/
|
||||||
|
private static assertMptIsValid(amount: string): void {
|
||||||
|
if (amount.indexOf('.') !== -1) {
|
||||||
|
throw new Error(`${amount.toString()} is an illegal amount`)
|
||||||
|
}
|
||||||
|
|
||||||
|
const decimal = new BigNumber(amount)
|
||||||
|
if (!decimal.isZero()) {
|
||||||
|
if (decimal < BigNumber(0)) {
|
||||||
|
throw new Error(`${amount.toString()} is an illegal amount`)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Number(BigInt(amount) & BigInt(mptMask)) != 0) {
|
||||||
|
throw new Error(`${amount.toString()} is an illegal amount`)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Ensure that the value after being multiplied by the exponent does not
|
* Ensure that the value after being multiplied by the exponent does not
|
||||||
* contain a decimal.
|
* contain a decimal.
|
||||||
@@ -248,7 +337,25 @@ class Amount extends SerializedType {
|
|||||||
* @returns true if Native (XRP)
|
* @returns true if Native (XRP)
|
||||||
*/
|
*/
|
||||||
private isNative(): boolean {
|
private isNative(): boolean {
|
||||||
return (this.bytes[0] & 0x80) === 0
|
return (this.bytes[0] & 0x80) === 0 && (this.bytes[0] & 0x20) === 0
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test if this amount is in units of MPT
|
||||||
|
*
|
||||||
|
* @returns true if MPT
|
||||||
|
*/
|
||||||
|
private isMPT(): boolean {
|
||||||
|
return (this.bytes[0] & 0x80) === 0 && (this.bytes[0] & 0x20) !== 0
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test if this amount is in units of IOU
|
||||||
|
*
|
||||||
|
* @returns true if IOU
|
||||||
|
*/
|
||||||
|
private isIOU(): boolean {
|
||||||
|
return (this.bytes[0] & 0x80) !== 0
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -33,6 +33,9 @@ class Blob extends SerializedType {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (typeof value === 'string') {
|
if (typeof value === 'string') {
|
||||||
|
if (!/^[A-F0-9]*$/iu.test(value)) {
|
||||||
|
throw new Error('Cannot construct Blob from a non-hex string')
|
||||||
|
}
|
||||||
return new Blob(hexToBytes(value))
|
return new Blob(hexToBytes(value))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
19
packages/ripple-binary-codec/src/types/hash-192.ts
Normal file
19
packages/ripple-binary-codec/src/types/hash-192.ts
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
import { Hash } from './hash'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Hash with a width of 192 bits
|
||||||
|
*/
|
||||||
|
class Hash192 extends Hash {
|
||||||
|
static readonly width = 24
|
||||||
|
static readonly ZERO_192: Hash192 = new Hash192(new Uint8Array(Hash192.width))
|
||||||
|
|
||||||
|
constructor(bytes?: Uint8Array) {
|
||||||
|
if (bytes && bytes.byteLength === 0) {
|
||||||
|
bytes = Hash192.ZERO_192.bytes
|
||||||
|
}
|
||||||
|
|
||||||
|
super(bytes ?? Hash192.ZERO_192.bytes)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export { Hash192 }
|
||||||
@@ -4,6 +4,7 @@ import { Blob } from './blob'
|
|||||||
import { Currency } from './currency'
|
import { Currency } from './currency'
|
||||||
import { Hash128 } from './hash-128'
|
import { Hash128 } from './hash-128'
|
||||||
import { Hash160 } from './hash-160'
|
import { Hash160 } from './hash-160'
|
||||||
|
import { Hash192 } from './hash-192'
|
||||||
import { Hash256 } from './hash-256'
|
import { Hash256 } from './hash-256'
|
||||||
import { Issue } from './issue'
|
import { Issue } from './issue'
|
||||||
import { PathSet } from './path-set'
|
import { PathSet } from './path-set'
|
||||||
@@ -25,6 +26,7 @@ const coreTypes: Record<string, typeof SerializedType> = {
|
|||||||
Currency,
|
Currency,
|
||||||
Hash128,
|
Hash128,
|
||||||
Hash160,
|
Hash160,
|
||||||
|
Hash192,
|
||||||
Hash256,
|
Hash256,
|
||||||
Issue,
|
Issue,
|
||||||
PathSet,
|
PathSet,
|
||||||
@@ -51,6 +53,7 @@ export {
|
|||||||
Currency,
|
Currency,
|
||||||
Hash128,
|
Hash128,
|
||||||
Hash160,
|
Hash160,
|
||||||
|
Hash192,
|
||||||
Hash256,
|
Hash256,
|
||||||
PathSet,
|
PathSet,
|
||||||
STArray,
|
STArray,
|
||||||
|
|||||||
@@ -67,7 +67,7 @@ class SerializedType {
|
|||||||
* Can be customized for sidechains and amendments.
|
* Can be customized for sidechains and amendments.
|
||||||
* @returns any type, if not overloaded returns hexString representation of bytes
|
* @returns any type, if not overloaded returns hexString representation of bytes
|
||||||
*/
|
*/
|
||||||
toJSON(_definitions?: XrplDefinitionsBase): JSON {
|
toJSON(_definitions?: XrplDefinitionsBase, _fieldName?: string): JSON {
|
||||||
return this.toHex()
|
return this.toHex()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -14,7 +14,13 @@ const OBJECT_END_MARKER = Uint8Array.from([0xe1])
|
|||||||
*/
|
*/
|
||||||
function isObjects(args): args is Array<JsonObject> {
|
function isObjects(args): args is Array<JsonObject> {
|
||||||
return (
|
return (
|
||||||
Array.isArray(args) && (args.length === 0 || typeof args[0] === 'object')
|
Array.isArray(args) &&
|
||||||
|
args.every(
|
||||||
|
(arg) =>
|
||||||
|
typeof arg === 'object' &&
|
||||||
|
Object.keys(arg).length === 1 &&
|
||||||
|
typeof Object.values(arg)[0] === 'object',
|
||||||
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import { BinaryParser } from '../serdes/binary-parser'
|
|||||||
import { BinarySerializer, BytesList } from '../serdes/binary-serializer'
|
import { BinarySerializer, BytesList } from '../serdes/binary-serializer'
|
||||||
|
|
||||||
import { STArray } from './st-array'
|
import { STArray } from './st-array'
|
||||||
|
import { UInt64 } from './uint-64'
|
||||||
|
|
||||||
const OBJECT_END_MARKER_BYTE = Uint8Array.from([0xe1])
|
const OBJECT_END_MARKER_BYTE = Uint8Array.from([0xe1])
|
||||||
const OBJECT_END_MARKER = 'ObjectEndMarker'
|
const OBJECT_END_MARKER = 'ObjectEndMarker'
|
||||||
@@ -137,6 +138,8 @@ class STObject extends SerializedType {
|
|||||||
? this.from(xAddressDecoded[field.name], undefined, definitions)
|
? this.from(xAddressDecoded[field.name], undefined, definitions)
|
||||||
: field.type.name === 'STArray'
|
: field.type.name === 'STArray'
|
||||||
? STArray.from(xAddressDecoded[field.name], definitions)
|
? STArray.from(xAddressDecoded[field.name], definitions)
|
||||||
|
: field.type.name === 'UInt64'
|
||||||
|
? UInt64.from(xAddressDecoded[field.name], field.name)
|
||||||
: field.associatedType.from(xAddressDecoded[field.name])
|
: field.associatedType.from(xAddressDecoded[field.name])
|
||||||
|
|
||||||
if (associatedValue == undefined) {
|
if (associatedValue == undefined) {
|
||||||
@@ -182,7 +185,7 @@ class STObject extends SerializedType {
|
|||||||
|
|
||||||
accumulator[field.name] = objectParser
|
accumulator[field.name] = objectParser
|
||||||
.readFieldValue(field)
|
.readFieldValue(field)
|
||||||
.toJSON(definitions)
|
.toJSON(definitions, field.name)
|
||||||
}
|
}
|
||||||
|
|
||||||
return accumulator
|
return accumulator
|
||||||
|
|||||||
@@ -2,10 +2,20 @@ import { UInt } from './uint'
|
|||||||
import { BinaryParser } from '../serdes/binary-parser'
|
import { BinaryParser } from '../serdes/binary-parser'
|
||||||
import { bytesToHex, concat, hexToBytes } from '@xrplf/isomorphic/utils'
|
import { bytesToHex, concat, hexToBytes } from '@xrplf/isomorphic/utils'
|
||||||
import { readUInt32BE, writeUInt32BE } from '../utils'
|
import { readUInt32BE, writeUInt32BE } from '../utils'
|
||||||
|
import { DEFAULT_DEFINITIONS, XrplDefinitionsBase } from '../enums'
|
||||||
|
|
||||||
const HEX_REGEX = /^[a-fA-F0-9]{1,16}$/
|
const HEX_REGEX = /^[a-fA-F0-9]{1,16}$/
|
||||||
|
const BASE10_REGEX = /^[0-9]{1,20}$/
|
||||||
const mask = BigInt(0x00000000ffffffff)
|
const mask = BigInt(0x00000000ffffffff)
|
||||||
|
|
||||||
|
function useBase10(fieldName: string): boolean {
|
||||||
|
return (
|
||||||
|
fieldName === 'MaximumAmount' ||
|
||||||
|
fieldName === 'OutstandingAmount' ||
|
||||||
|
fieldName === 'MPTAmount'
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Derived UInt class for serializing/deserializing 64 bit UInt
|
* Derived UInt class for serializing/deserializing 64 bit UInt
|
||||||
*/
|
*/
|
||||||
@@ -29,7 +39,10 @@ class UInt64 extends UInt {
|
|||||||
* @param val A UInt64, hex-string, bigInt, or number
|
* @param val A UInt64, hex-string, bigInt, or number
|
||||||
* @returns A UInt64 object
|
* @returns A UInt64 object
|
||||||
*/
|
*/
|
||||||
static from<T extends UInt64 | string | bigint | number>(val: T): UInt64 {
|
static from<T extends UInt64 | string | bigint | number>(
|
||||||
|
val: T,
|
||||||
|
fieldName = '',
|
||||||
|
): UInt64 {
|
||||||
if (val instanceof UInt64) {
|
if (val instanceof UInt64) {
|
||||||
return val
|
return val
|
||||||
}
|
}
|
||||||
@@ -51,11 +64,18 @@ class UInt64 extends UInt {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (typeof val === 'string') {
|
if (typeof val === 'string') {
|
||||||
if (!HEX_REGEX.test(val)) {
|
if (useBase10(fieldName)) {
|
||||||
|
if (!BASE10_REGEX.test(val)) {
|
||||||
|
throw new Error(`${fieldName} ${val} is not a valid base 10 string`)
|
||||||
|
}
|
||||||
|
val = BigInt(val).toString(16) as T
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof val === 'string' && !HEX_REGEX.test(val)) {
|
||||||
throw new Error(`${val} is not a valid hex-string`)
|
throw new Error(`${val} is not a valid hex-string`)
|
||||||
}
|
}
|
||||||
|
|
||||||
const strBuf = val.padStart(16, '0')
|
const strBuf = (val as string).padStart(16, '0')
|
||||||
buf = hexToBytes(strBuf)
|
buf = hexToBytes(strBuf)
|
||||||
return new UInt64(buf)
|
return new UInt64(buf)
|
||||||
}
|
}
|
||||||
@@ -76,8 +96,16 @@ class UInt64 extends UInt {
|
|||||||
*
|
*
|
||||||
* @returns a hex-string
|
* @returns a hex-string
|
||||||
*/
|
*/
|
||||||
toJSON(): string {
|
toJSON(
|
||||||
return bytesToHex(this.bytes)
|
_definitions: XrplDefinitionsBase = DEFAULT_DEFINITIONS,
|
||||||
|
fieldName = '',
|
||||||
|
): string {
|
||||||
|
const hexString = bytesToHex(this.bytes)
|
||||||
|
if (useBase10(fieldName)) {
|
||||||
|
return BigInt('0x' + hexString).toString(10)
|
||||||
|
}
|
||||||
|
|
||||||
|
return hexString
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
import { coreTypes } from '../src/types'
|
import { coreTypes } from '../src/types'
|
||||||
import fixtures from './fixtures/data-driven-tests.json'
|
import fixtures from './fixtures/data-driven-tests.json'
|
||||||
|
|
||||||
|
import { makeParser } from '../src/binary'
|
||||||
const { Amount } = coreTypes
|
const { Amount } = coreTypes
|
||||||
|
|
||||||
function amountErrorTests() {
|
function amountErrorTests() {
|
||||||
@@ -25,6 +27,16 @@ describe('Amount', function () {
|
|||||||
it('can be parsed from', function () {
|
it('can be parsed from', function () {
|
||||||
expect(Amount.from('1000000') instanceof Amount).toBe(true)
|
expect(Amount.from('1000000') instanceof Amount).toBe(true)
|
||||||
expect(Amount.from('1000000').toJSON()).toEqual('1000000')
|
expect(Amount.from('1000000').toJSON()).toEqual('1000000')
|
||||||
|
|
||||||
|
// it not valid to have negative XRP. But we test it anyways
|
||||||
|
// to ensure logic correctness for toJSON of the Amount class
|
||||||
|
{
|
||||||
|
const parser = makeParser('0000000000000001')
|
||||||
|
const value = parser.readType(Amount)
|
||||||
|
const json = value.toJSON()
|
||||||
|
expect(json).toEqual('-1')
|
||||||
|
}
|
||||||
|
|
||||||
const fixture = {
|
const fixture = {
|
||||||
value: '1',
|
value: '1',
|
||||||
issuer: '0000000000000000000000000000000000000000',
|
issuer: '0000000000000000000000000000000000000000',
|
||||||
@@ -38,5 +50,35 @@ describe('Amount', function () {
|
|||||||
}
|
}
|
||||||
expect(amt.toJSON()).toEqual(rewritten)
|
expect(amt.toJSON()).toEqual(rewritten)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('can be parsed from MPT', function () {
|
||||||
|
let fixture = {
|
||||||
|
value: '100',
|
||||||
|
mpt_issuance_id: '00002403C84A0A28E0190E208E982C352BBD5006600555CF',
|
||||||
|
}
|
||||||
|
let amt = Amount.from(fixture)
|
||||||
|
expect(amt.toJSON()).toEqual(fixture)
|
||||||
|
|
||||||
|
fixture = {
|
||||||
|
value: '9223372036854775807',
|
||||||
|
mpt_issuance_id: '00002403C84A0A28E0190E208E982C352BBD5006600555CF',
|
||||||
|
}
|
||||||
|
amt = Amount.from(fixture)
|
||||||
|
expect(amt.toJSON()).toEqual(fixture)
|
||||||
|
|
||||||
|
// it not valid to have negative MPT. But we test it anyways
|
||||||
|
// to ensure logic correctness for toJSON of the Amount class
|
||||||
|
{
|
||||||
|
const parser = makeParser(
|
||||||
|
'20000000000000006400002403C84A0A28E0190E208E982C352BBD5006600555CF',
|
||||||
|
)
|
||||||
|
const value = parser.readType(Amount)
|
||||||
|
const json = value.toJSON()
|
||||||
|
expect(json).toEqual({
|
||||||
|
mpt_issuance_id: '00002403C84A0A28E0190E208E982C352BBD5006600555CF',
|
||||||
|
value: '-100',
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
amountErrorTests()
|
amountErrorTests()
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ function assertEqualAmountJSON(actual, expected) {
|
|||||||
}
|
}
|
||||||
expect(actual.currency).toEqual(expected.currency)
|
expect(actual.currency).toEqual(expected.currency)
|
||||||
expect(actual.issuer).toEqual(expected.issuer)
|
expect(actual.issuer).toEqual(expected.issuer)
|
||||||
|
expect(actual.mpt_issuance_id).toEqual(expected.mpt_issuance_id)
|
||||||
expect(
|
expect(
|
||||||
actual.value === expected.value ||
|
actual.value === expected.value ||
|
||||||
new BigNumber(actual.value).eq(new BigNumber(expected.value)),
|
new BigNumber(actual.value).eq(new BigNumber(expected.value)),
|
||||||
@@ -207,12 +208,12 @@ function amountParsingTests() {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
const parser = makeParser(f.expected_hex)
|
const parser = makeParser(f.expected_hex)
|
||||||
const testName = `values_tests[${i}] parses ${f.expected_hex.slice(
|
const hexToJsonTestName = `values_tests[${i}] parses ${f.expected_hex.slice(
|
||||||
0,
|
0,
|
||||||
16,
|
16,
|
||||||
)}...
|
)}...
|
||||||
as ${JSON.stringify(f.test_json)}`
|
as ${JSON.stringify(f.test_json)}`
|
||||||
it(testName, () => {
|
it(hexToJsonTestName, () => {
|
||||||
const value = parser.readType(Amount)
|
const value = parser.readType(Amount)
|
||||||
// May not actually be in canonical form. The fixtures are to be used
|
// May not actually be in canonical form. The fixtures are to be used
|
||||||
// also for json -> binary;
|
// also for json -> binary;
|
||||||
@@ -223,6 +224,15 @@ function amountParsingTests() {
|
|||||||
expect((exponent.e ?? 0) - 15).toEqual(f?.exponent)
|
expect((exponent.e ?? 0) - 15).toEqual(f?.exponent)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const jsonToHexTestName = `values_tests[${i}] parses ${JSON.stringify(
|
||||||
|
f.test_json,
|
||||||
|
)}...
|
||||||
|
as ${f.expected_hex.slice(0, 16)}`
|
||||||
|
it(jsonToHexTestName, () => {
|
||||||
|
const amt = Amount.from(f.test_json)
|
||||||
|
expect(amt.toHex()).toEqual(f.expected_hex)
|
||||||
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -238,19 +248,19 @@ function fieldParsingTests() {
|
|||||||
it('Field throws when type code out of range', () => {
|
it('Field throws when type code out of range', () => {
|
||||||
const parser = makeParser('0101')
|
const parser = makeParser('0101')
|
||||||
expect(() => parser.readField()).toThrow(
|
expect(() => parser.readField()).toThrow(
|
||||||
new Error('Cannot read FieldOrdinal, type_code out of range'),
|
new Error('Cannot read FieldOrdinal, type_code 1 out of range'),
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
it('Field throws when field code out of range', () => {
|
it('Field throws when field code out of range', () => {
|
||||||
const parser = makeParser('1001')
|
const parser = makeParser('1001')
|
||||||
expect(() => parser.readFieldOrdinal()).toThrow(
|
expect(() => parser.readFieldOrdinal()).toThrow(
|
||||||
new Error('Cannot read FieldOrdinal, field_code out of range'),
|
new Error('Cannot read FieldOrdinal, field_code 1 out of range'),
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
it('Field throws when both type and field code out of range', () => {
|
it('Field throws when both type and field code out of range', () => {
|
||||||
const parser = makeParser('000101')
|
const parser = makeParser('000101')
|
||||||
expect(() => parser.readFieldOrdinal()).toThrow(
|
expect(() => parser.readFieldOrdinal()).toThrow(
|
||||||
new Error('Cannot read FieldOrdinal, type_code out of range'),
|
new Error('Cannot read FieldOrdinal, type_code 1 out of range'),
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
it('readUIntN', () => {
|
it('readUIntN', () => {
|
||||||
|
|||||||
@@ -4868,6 +4868,36 @@
|
|||||||
"TxnSignature": "AACD31A04CAE14670FC483A1382F393AA96B49C84479B58067F049FBD772999325667A6AA2520A63756EE84F3657298815019DD56A1AECE796B08535C4009C08",
|
"TxnSignature": "AACD31A04CAE14670FC483A1382F393AA96B49C84479B58067F049FBD772999325667A6AA2520A63756EE84F3657298815019DD56A1AECE796B08535C4009C08",
|
||||||
"URI": "6469645F6578616D706C65"
|
"URI": "6469645F6578616D706C65"
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"binary": "1200332FFFFFFFFF2033000004D2750B6469645F6578616D706C65701C0863757272656E6379701D0870726F7669646572811401476926B590BA3245F63C829116A0A3AF7F382DF018E020301700000000000001E2041003011A0000000000000000000000000000000000000000021A0000000000000000000000005553440000000000E1F1",
|
||||||
|
"json": {
|
||||||
|
"TransactionType": "OracleSet",
|
||||||
|
"Account": "rfmDuhDyLGgx94qiwf3YF8BUV5j6KSvE8",
|
||||||
|
"OracleDocumentID": 1234,
|
||||||
|
"LastUpdateTime": 4294967295,
|
||||||
|
"PriceDataSeries": [
|
||||||
|
{
|
||||||
|
"PriceData": {
|
||||||
|
"BaseAsset": "XRP",
|
||||||
|
"QuoteAsset": "USD",
|
||||||
|
"AssetPrice": "00000000000001E2",
|
||||||
|
"Scale": 3
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"Provider": "70726F7669646572",
|
||||||
|
"URI": "6469645F6578616D706C65",
|
||||||
|
"AssetClass": "63757272656E6379"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"binary": "1200342033000004D2811401476926B590BA3245F63C829116A0A3AF7F382D",
|
||||||
|
"json": {
|
||||||
|
"TransactionType": "OracleDelete",
|
||||||
|
"Account": "rfmDuhDyLGgx94qiwf3YF8BUV5j6KSvE8",
|
||||||
|
"OracleDocumentID": 1234
|
||||||
|
}
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"ledgerData": [{
|
"ledgerData": [{
|
||||||
|
|||||||
@@ -2499,7 +2499,7 @@
|
|||||||
"type_id": 6,
|
"type_id": 6,
|
||||||
"is_native": true,
|
"is_native": true,
|
||||||
"type": "Amount",
|
"type": "Amount",
|
||||||
"expected_hex": "0000000000000001",
|
"error": "Value is negative",
|
||||||
"is_negative": true
|
"is_negative": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -2914,6 +2914,170 @@
|
|||||||
"type": "Amount",
|
"type": "Amount",
|
||||||
"error": "10000000000000000000 absolute XRP is bigger than max native value 100000000000.0",
|
"error": "10000000000000000000 absolute XRP is bigger than max native value 100000000000.0",
|
||||||
"is_negative": true
|
"is_negative": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "9223372036854775808"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value is too large"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "18446744073709551615"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value is too large"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "-1"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value is negative"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "10.1"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value has decimal point"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "10",
|
||||||
|
"value": "10"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "mpt_issuance_id has invalid hash length"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "10",
|
||||||
|
"issuer": "rrrrrrrrrrrrrrrrrrrrBZbvji"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Issuer not valid for MPT"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "10",
|
||||||
|
"currency": "USD"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Currency not valid for MPT"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "a"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value has incorrect hex format"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0xy"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value has bad hex character"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "/"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Value has bad character"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0x8000000000000000"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Hex value out of range"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id": "00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0xFFFFFFFFFFFFFFFF"
|
||||||
|
},
|
||||||
|
"type": "Amount",
|
||||||
|
"error": "Hex value out of range"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "9223372036854775807"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "607FFFFFFFFFFFFFFF00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "60000000000000000000002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "-0"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "60000000000000000000002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "100"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "60000000000000006400002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0xa"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "60000000000000000A00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"test_json": {
|
||||||
|
"mpt_issuance_id":"00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"value": "0x7FFFFFFFFFFFFFFF"
|
||||||
|
},
|
||||||
|
"type_id": 6,
|
||||||
|
"is_native": false,
|
||||||
|
"type": "Amount",
|
||||||
|
"expected_hex": "607FFFFFFFFFFFFFFF00002403C84A0A28E0190E208E982C352BBD5006600555CF",
|
||||||
|
"is_negative": false
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,11 @@
|
|||||||
import { Hash128, Hash160, Hash256, AccountID, Currency } from '../src/types'
|
import {
|
||||||
|
Hash128,
|
||||||
|
Hash160,
|
||||||
|
Hash192,
|
||||||
|
Hash256,
|
||||||
|
AccountID,
|
||||||
|
Currency,
|
||||||
|
} from '../src/types'
|
||||||
|
|
||||||
describe('Hash128', function () {
|
describe('Hash128', function () {
|
||||||
it('has a static width member', function () {
|
it('has a static width member', function () {
|
||||||
@@ -51,6 +58,33 @@ describe('Hash160', function () {
|
|||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe('Hash192', function () {
|
||||||
|
it('has a static width member', function () {
|
||||||
|
expect(Hash192.width).toBe(24)
|
||||||
|
})
|
||||||
|
it('has a ZERO_192 member', function () {
|
||||||
|
expect(Hash192.ZERO_192.toJSON()).toBe(
|
||||||
|
'000000000000000000000000000000000000000000000000',
|
||||||
|
)
|
||||||
|
})
|
||||||
|
it('can be compared against another', function () {
|
||||||
|
const h1 = Hash192.from('100000000000000000000000000000000000000000000000')
|
||||||
|
const h2 = Hash192.from('200000000000000000000000000000000000000000000000')
|
||||||
|
const h3 = Hash192.from('000000000000000000000000000000000000000000000003')
|
||||||
|
expect(h1.lt(h2)).toBe(true)
|
||||||
|
expect(h3.lt(h2)).toBe(true)
|
||||||
|
})
|
||||||
|
|
||||||
|
it('throws when constructed from invalid hash length', () => {
|
||||||
|
expect(() =>
|
||||||
|
Hash192.from('10000000000000000000000000000000000000000000000'),
|
||||||
|
).toThrow(new Error('Invalid Hash length 23'))
|
||||||
|
expect(() =>
|
||||||
|
Hash192.from('10000000000000000000000000000000000000000000000000'),
|
||||||
|
).toThrow(new Error('Invalid Hash length 25'))
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
describe('Hash256', function () {
|
describe('Hash256', function () {
|
||||||
it('has a static width member', function () {
|
it('has a static width member', function () {
|
||||||
expect(Hash256.width).toBe(32)
|
expect(Hash256.width).toBe(32)
|
||||||
|
|||||||
@@ -73,7 +73,9 @@ describe('Signing data', function () {
|
|||||||
const customPaymentDefinitions = JSON.parse(
|
const customPaymentDefinitions = JSON.parse(
|
||||||
JSON.stringify(normalDefinitions),
|
JSON.stringify(normalDefinitions),
|
||||||
)
|
)
|
||||||
customPaymentDefinitions.TRANSACTION_TYPES.Payment = 31
|
|
||||||
|
// custom number would need to updated in case it has been used by an existing transaction type
|
||||||
|
customPaymentDefinitions.TRANSACTION_TYPES.Payment = 200
|
||||||
|
|
||||||
const newDefs = new XrplDefinitions(customPaymentDefinitions)
|
const newDefs = new XrplDefinitions(customPaymentDefinitions)
|
||||||
const actual = encodeForSigning(tx_json, newDefs)
|
const actual = encodeForSigning(tx_json, newDefs)
|
||||||
@@ -82,7 +84,7 @@ describe('Signing data', function () {
|
|||||||
'53545800', // signingPrefix
|
'53545800', // signingPrefix
|
||||||
// TransactionType
|
// TransactionType
|
||||||
'12',
|
'12',
|
||||||
'001F',
|
'00C8',
|
||||||
// Flags
|
// Flags
|
||||||
'22',
|
'22',
|
||||||
'80000000',
|
'80000000',
|
||||||
@@ -176,7 +178,9 @@ describe('Signing data', function () {
|
|||||||
const customPaymentDefinitions = JSON.parse(
|
const customPaymentDefinitions = JSON.parse(
|
||||||
JSON.stringify(normalDefinitions),
|
JSON.stringify(normalDefinitions),
|
||||||
)
|
)
|
||||||
customPaymentDefinitions.TRANSACTION_TYPES.Payment = 31
|
|
||||||
|
// custom number would need to updated in case it has been used by an existing transaction type
|
||||||
|
customPaymentDefinitions.TRANSACTION_TYPES.Payment = 200
|
||||||
|
|
||||||
const newDefs = new XrplDefinitions(customPaymentDefinitions)
|
const newDefs = new XrplDefinitions(customPaymentDefinitions)
|
||||||
const signingAccount = 'rJZdUusLDtY9NEsGea7ijqhVrXv98rYBYN'
|
const signingAccount = 'rJZdUusLDtY9NEsGea7ijqhVrXv98rYBYN'
|
||||||
@@ -187,7 +191,7 @@ describe('Signing data', function () {
|
|||||||
'534D5400', // signingPrefix
|
'534D5400', // signingPrefix
|
||||||
// TransactionType
|
// TransactionType
|
||||||
'12',
|
'12',
|
||||||
'001F',
|
'00C8',
|
||||||
// Flags
|
// Flags
|
||||||
'22',
|
'22',
|
||||||
'80000000',
|
'80000000',
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import { UInt8, UInt64 } from '../src/types'
|
import { UInt8, UInt64 } from '../src/types'
|
||||||
import { encode } from '../src'
|
import { encode, decode } from '../src'
|
||||||
|
|
||||||
const binary =
|
const binary =
|
||||||
'11007222000300003700000000000000003800000000000000006280000000000000000000000000000000000000005553440000000000000000000000000000000000000000000000000166D5438D7EA4C680000000000000000000000000005553440000000000AE123A8556F3CF91154711376AFB0F894F832B3D67D5438D7EA4C680000000000000000000000000005553440000000000F51DFC2A09D62CBBA1DFBDD4691DAC96AD98B90F'
|
'11007222000300003700000000000000003800000000000000006280000000000000000000000000000000000000005553440000000000000000000000000000000000000000000000000166D5438D7EA4C680000000000000000000000000005553440000000000AE123A8556F3CF91154711376AFB0F894F832B3D67D5438D7EA4C680000000000000000000000000005553440000000000F51DFC2A09D62CBBA1DFBDD4691DAC96AD98B90F'
|
||||||
@@ -96,6 +96,40 @@ const jsonEntry2 = {
|
|||||||
index: '0000041EFD027808D3F78C8352F97E324CB816318E00B977C74ECDDC7CD975B2',
|
index: '0000041EFD027808D3F78C8352F97E324CB816318E00B977C74ECDDC7CD975B2',
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const mptIssuanceEntryBinary =
|
||||||
|
'11007E220000006224000002DF25000002E434000000000000000030187FFFFFFFFFFFFFFF30190000000000000064552E78C1FFBDDAEE077253CEB12CFEA83689AA0899F94762190A357208DADC76FE701EC1EC7B226E616D65223A2255532054726561737572792042696C6C20546F6B656E222C2273796D626F6C223A225553544254222C22646563696D616C73223A322C22746F74616C537570706C79223A313030303030302C22697373756572223A225553205472656173757279222C22697373756544617465223A22323032342D30332D3235222C226D6174757269747944617465223A22323032352D30332D3235222C226661636556616C7565223A2231303030222C22696E74657265737452617465223A22322E35222C22696E7465726573744672657175656E6379223A22517561727465726C79222C22636F6C6C61746572616C223A22555320476F7665726E6D656E74222C226A7572697364696374696F6E223A22556E6974656420537461746573222C22726567756C61746F7279436F6D706C69616E6365223A2253454320526567756C6174696F6E73222C22736563757269747954797065223A2254726561737572792042696C6C222C2265787465726E616C5F75726C223A2268747470733A2F2F6578616D706C652E636F6D2F742D62696C6C2D746F6B656E2D6D657461646174612E6A736F6E227D8414A4D893CFBC4DC6AE877EB585F90A3B47528B958D051003'
|
||||||
|
|
||||||
|
const mptIssuanceEntryJson = {
|
||||||
|
AssetScale: 3,
|
||||||
|
Flags: 98,
|
||||||
|
Issuer: 'rGpdGXDV2RFPeLEfWS9RFo5Nh9cpVDToZa',
|
||||||
|
LedgerEntryType: 'MPTokenIssuance',
|
||||||
|
MPTokenMetadata:
|
||||||
|
'7B226E616D65223A2255532054726561737572792042696C6C20546F6B656E222C2273796D626F6C223A225553544254222C22646563696D616C73223A322C22746F74616C537570706C79223A313030303030302C22697373756572223A225553205472656173757279222C22697373756544617465223A22323032342D30332D3235222C226D6174757269747944617465223A22323032352D30332D3235222C226661636556616C7565223A2231303030222C22696E74657265737452617465223A22322E35222C22696E7465726573744672657175656E6379223A22517561727465726C79222C22636F6C6C61746572616C223A22555320476F7665726E6D656E74222C226A7572697364696374696F6E223A22556E6974656420537461746573222C22726567756C61746F7279436F6D706C69616E6365223A2253454320526567756C6174696F6E73222C22736563757269747954797065223A2254726561737572792042696C6C222C2265787465726E616C5F75726C223A2268747470733A2F2F6578616D706C652E636F6D2F742D62696C6C2D746F6B656E2D6D657461646174612E6A736F6E227D',
|
||||||
|
MaximumAmount: '9223372036854775807',
|
||||||
|
OutstandingAmount: '100',
|
||||||
|
OwnerNode: '0000000000000000',
|
||||||
|
PreviousTxnID:
|
||||||
|
'2E78C1FFBDDAEE077253CEB12CFEA83689AA0899F94762190A357208DADC76FE',
|
||||||
|
PreviousTxnLgrSeq: 740,
|
||||||
|
Sequence: 735,
|
||||||
|
}
|
||||||
|
|
||||||
|
const mptokenEntryJson = {
|
||||||
|
Account: 'raDQsd1s8rqGjL476g59a9vVNi1rSwrC44',
|
||||||
|
Flags: 0,
|
||||||
|
LedgerEntryType: 'MPToken',
|
||||||
|
MPTAmount: '100',
|
||||||
|
MPTokenIssuanceID: '000002DF71CAE59C9B7E56587FFF74D4EA5830D9BE3CE0CC',
|
||||||
|
OwnerNode: '0000000000000000',
|
||||||
|
PreviousTxnID:
|
||||||
|
'222EF3C7E82D8A44984A66E2B8E357CB536EC2547359CCF70E56E14BC4C284C8',
|
||||||
|
PreviousTxnLgrSeq: 741,
|
||||||
|
}
|
||||||
|
|
||||||
|
const mptokenEntryBinary =
|
||||||
|
'11007F220000000025000002E5340000000000000000301A000000000000006455222EF3C7E82D8A44984A66E2B8E357CB536EC2547359CCF70E56E14BC4C284C881143930DB9A74C26D96CB58ADFFD7E8BB78BCFE62340115000002DF71CAE59C9B7E56587FFF74D4EA5830D9BE3CE0CC'
|
||||||
|
|
||||||
it('compareToTests[0]', () => {
|
it('compareToTests[0]', () => {
|
||||||
expect(UInt8.from(124).compareTo(UInt64.from(124))).toBe(0)
|
expect(UInt8.from(124).compareTo(UInt64.from(124))).toBe(0)
|
||||||
})
|
})
|
||||||
@@ -144,3 +178,20 @@ it('valueOf tests', () => {
|
|||||||
|
|
||||||
expect(val.valueOf() | 0x2).toBe(3)
|
expect(val.valueOf() | 0x2).toBe(3)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it('UInt64 is parsed as base 10 for MPT amounts', () => {
|
||||||
|
expect(encode(mptIssuanceEntryJson)).toEqual(mptIssuanceEntryBinary)
|
||||||
|
expect(decode(mptIssuanceEntryBinary)).toEqual(mptIssuanceEntryJson)
|
||||||
|
|
||||||
|
expect(encode(mptokenEntryJson)).toEqual(mptokenEntryBinary)
|
||||||
|
expect(decode(mptokenEntryBinary)).toEqual(mptokenEntryJson)
|
||||||
|
|
||||||
|
const decodedIssuance = decode(mptIssuanceEntryBinary)
|
||||||
|
expect(typeof decodedIssuance.MaximumAmount).toBe('string')
|
||||||
|
expect(decodedIssuance.MaximumAmount).toBe('9223372036854775807')
|
||||||
|
expect(decodedIssuance.OutstandingAmount).toBe('100')
|
||||||
|
|
||||||
|
const decodedToken = decode(mptokenEntryBinary)
|
||||||
|
expect(typeof decodedToken.MPTAmount).toBe('string')
|
||||||
|
expect(decodedToken.MPTAmount).toBe('100')
|
||||||
|
})
|
||||||
|
|||||||
@@ -19,29 +19,6 @@
|
|||||||
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
||||||
|
|
||||||
## 2.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* `Buffer` has been replaced with `UInt8Array` for both params and return values. `Buffer` may continue to work with params since they extend `UInt8Arrays`.
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
|
||||||
|
|
||||||
## 2.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* Bump typescript to 5.x
|
|
||||||
* Remove Node 14 support
|
|
||||||
* Remove `assert` dependency. If you were catching `AssertionError` you need to change to `Error`.
|
|
||||||
* Fix `deriveKeypair` ignoring manual decoding algorithm. (Specifying algorithm=`ed25519` in `opts` now works on secrets like `sNa1...`)
|
|
||||||
* Remove `crypto` polyfills, `create-hash`, `elliptic`, `hash.js`, and their many dependencies in favor of `@noble/hashes` and `@nobel/curves`
|
|
||||||
* Remove `bytesToHex` and `hexToBytes`. They can now be found in `@xrplf/isomorphic/utils`
|
|
||||||
* `verifyTransaction` will throw an error if there is no signature
|
|
||||||
* Improved key algorithm detection. It will now throw Errors with helpful messages
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
|
||||||
|
|
||||||
## 1.3.1 (2023-09-27)
|
## 1.3.1 (2023-09-27)
|
||||||
### Fixed
|
### Fixed
|
||||||
* Fix source-maps not finding their designated source
|
* Fix source-maps not finding their designated source
|
||||||
|
|||||||
@@ -36,6 +36,6 @@
|
|||||||
"license": "ISC",
|
"license": "ISC",
|
||||||
"prettier": "@xrplf/prettier-config",
|
"prettier": "@xrplf/prettier-config",
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">= 16"
|
"node": ">= 18"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,24 +19,3 @@ Subscribe to [the **xrpl-announce** mailing list](https://groups.google.com/g/xr
|
|||||||
* Unit tests run in a browser and node.
|
* Unit tests run in a browser and node.
|
||||||
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
||||||
|
|
||||||
## 1.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
### BREAKING CHANGES:
|
|
||||||
* Moved all methods that were on `Utils` are now individually exported.
|
|
||||||
* `Buffer` has been replaced with `UInt8Array` for both params and return values. `Buffer` may continue to work with params since they extend `UInt8Arrays`.
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Eliminates 4 runtime dependencies: `base-x`, `base64-js`, `buffer`, and `ieee754`.
|
|
||||||
|
|
||||||
## 1.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
* Add `xrpl-secret-numbers` by @WietseWind to the mono repo.
|
|
||||||
* `unpkg` and `jsdelivr` support was simplified.
|
|
||||||
* Unit tests run in a browser and node.
|
|
||||||
* Remove `brorand` as a dependency and use `@xrplf/isomorphic` instead.
|
|
||||||
|
|
||||||
### BREAKING CHANGES:
|
|
||||||
* `xrpl-secret-numbers` is now `@xrplf/secret-numbers`.
|
|
||||||
* The bundled file produced changed from `dist/browerified.js` to `build/xrplf-secret-numbers-latest.js`.
|
|
||||||
* Bundle variable is `xrplf_secret_numbers` instead of using browserify's loader.
|
|
||||||
|
|||||||
@@ -4,9 +4,71 @@ Subscribe to [the **xrpl-announce** mailing list](https://groups.google.com/g/xr
|
|||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
|
|
||||||
|
## 4.2.0 (2025-2-13)
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Support for the AMMClawback amendment (XLS-73)
|
||||||
|
* Adds utility function `convertTxFlagsToNumber`
|
||||||
|
* Support for the Permissioned Domains amendment (XLS-80).
|
||||||
|
* Support for the `simulate` RPC ([XLS-69](https://github.com/XRPLF/XRPL-Standards/tree/master/XLS-0069-simulate))
|
||||||
|
* Support for XLS-77d Deep-Freeze amendment
|
||||||
|
|
||||||
|
### Changed
|
||||||
|
* Deprecated `setTransactionFlagsToNumber`. Start using convertTxFlagsToNumber instead
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
* Include `network_id` field in the `server_state` response interface.
|
||||||
|
|
||||||
|
## 4.1.0 (2024-12-23)
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Added new MPT transaction definitions (XLS-33)
|
||||||
|
* New `MPTAmount` type support for `Payment` and `Clawback` transactions
|
||||||
|
* `parseTransactionFlags` as a utility function in the xrpl package to streamline transactions flags-to-map conversion
|
||||||
|
* Support for XLS-70d (Credentials)
|
||||||
|
* Support for the `DynamicNFT` amendment (XLS-46)
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
* `TransactionStream` model supports APIv2
|
||||||
|
* `TransactionStream` model includes `close_time_iso` field
|
||||||
|
* `Ledger` model includes `close_time_iso` field
|
||||||
|
|
||||||
|
## 4.0.0 (2024-07-15)
|
||||||
|
|
||||||
|
### BREAKING CHANGES
|
||||||
|
* Use rippled api_version v2 as default while maintaining support for v1.
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Add `nfts_by_issuer` clio-only API definition
|
||||||
|
* Add `include_deleted` to ledgerEntry request and `deleted_ledger_index` to ledgerEntry response
|
||||||
|
* Support for the `fixPreviousTxnID` amendment.
|
||||||
|
* Support for the user version of the `feature` RPC.
|
||||||
|
* Add `hash` field to `ledger` command response
|
||||||
|
|
||||||
|
### Removed
|
||||||
|
* Remove references to the Hooks testnet faucet in the xrpl.js code repository.
|
||||||
|
|
||||||
|
## 3.1.0 (2024-06-03)
|
||||||
|
|
||||||
|
### BREAKING CHANGES
|
||||||
|
* Small fix in the API to use a new flag name `tfNoDirectRipple` instead of the existing flag name `tfNoRippleDirect`
|
||||||
|
* Node.js has been upgraded to a minimum version of 18
|
||||||
|
* `fetch` now relies on the native javascript environment in browsers and Node.js
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Support for the Price Oracles amendment (XLS-47).
|
||||||
|
|
||||||
|
### Fixed
|
||||||
|
* Typo in `Channel` type `source_tab` -> `source_tag`
|
||||||
|
* Fix `client.requestAll` to handle filters better
|
||||||
|
* Add the missing `AMMDeposit` flag `tfTwoAssetIfEmpty`
|
||||||
|
* Add missing `lsfAMMNode` flag to `RippleState` ledger object
|
||||||
|
* Add `PreviousFields` to `DeletedNode` metadata type
|
||||||
|
|
||||||
## 3.0.0 (2024-02-01)
|
## 3.0.0 (2024-02-01)
|
||||||
|
|
||||||
### BREAKING CHANGES
|
### BREAKING CHANGES
|
||||||
|
* The default signing algorithm in the `Wallet` was changed from secp256k1 to ed25519
|
||||||
* Bump typescript to 5.x
|
* Bump typescript to 5.x
|
||||||
* Remove Node 14 support
|
* Remove Node 14 support
|
||||||
* Remove `crypto` polyfills, `create-hash`, `elliptic`, `hash.js`, and their many dependencies in favor of `@noble/hashes` and `@nobel/curves`
|
* Remove `crypto` polyfills, `create-hash`, `elliptic`, `hash.js`, and their many dependencies in favor of `@noble/hashes` and `@nobel/curves`
|
||||||
@@ -52,80 +114,6 @@ Bundler configurations are much more simplified. See [../UNIQUE_STEPS](Unique St
|
|||||||
* Deprecated:
|
* Deprecated:
|
||||||
* `convertHexToString` in favor of `@xrplf/isomorphic/utils`'s `hexToString`
|
* `convertHexToString` in favor of `@xrplf/isomorphic/utils`'s `hexToString`
|
||||||
* `convertStringToHex` in favor of `@xrplf/isomorphic/utils`'s `stringToHex`
|
* `convertStringToHex` in favor of `@xrplf/isomorphic/utils`'s `stringToHex`
|
||||||
|
|
||||||
## 3.0.0 Beta 1 (2023-11-30)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* `Transaction` type has been redefined to include all transactions and `SubmittableTransaction` was created to define the old value. The following functions which only handle transactions to be submitted now use `SubmittableTransaction`:
|
|
||||||
* `Client.autofill`
|
|
||||||
* `Client.submit`
|
|
||||||
* `Client.submitAndWait`
|
|
||||||
* `Client.prepareTransaction`
|
|
||||||
* `getSignedTx`
|
|
||||||
* `isAccountDelete`
|
|
||||||
* `dropsToXRP` and `Client.getXrpBalance` now return a `number` instead of a `string`
|
|
||||||
* `Buffer` has been replaced with `UInt8Array` for both params and return values. `Buffer` may continue to work with params since they extend `UInt8Arrays`.
|
|
||||||
|
|
||||||
### Bundling Changes
|
|
||||||
* `Buffer` and `process` polyfills are no longer required.
|
|
||||||
|
|
||||||
### Changes
|
|
||||||
* Deprecated:
|
|
||||||
* `convertHexToString` in favor of `@xrplf/isomorphic/utils`'s `hexToString`
|
|
||||||
* `convertStringToHex` in favor of `@xrplf/isomorphic/utils`'s `stringToHex`
|
|
||||||
* Remove `lodash` as a dependency
|
|
||||||
* Remove many polyfills that were only used for testing in the browser
|
|
||||||
* Remove `util` from bundle by switching `inspect` to `JSON.stringify`
|
|
||||||
* Add type for metadata for specific transactions(`Payment`, `NFTokenMint`, `NFTokenCreateOffer`, `NFTokenAcceptOffer`, `NFTokenCancelOffer`)
|
|
||||||
|
|
||||||
### Fixed
|
|
||||||
* Fixed Wallet.generate() ignoring the `algorithm` parameter (Only a problem once binary-codec fix for `derive_keypair` is added)
|
|
||||||
* Fixed Wallet.fromSeed() ignoring the `algorithm` parameter
|
|
||||||
* Added pseudo-transaction support to hash functions and response types
|
|
||||||
|
|
||||||
## 3.0.0 Beta 0 (2023-10-19)
|
|
||||||
|
|
||||||
### Breaking Changes
|
|
||||||
* Bump typescript to 5.x
|
|
||||||
* Remove Node 14 support
|
|
||||||
* Remove `crypto` polyfills, `create-hash`, `elliptic`, `hash.js`, and their many dependencies in favor of `@noble/hashes` and `@nobel/curves`
|
|
||||||
* Remove `bip32` and `bip39` in favor of `@scure/bip32` and `@scure/bip39`
|
|
||||||
* Remove `assert` dependency. If you were catching `AssertionError` you need to change to `Error`
|
|
||||||
* Configuring a proxy:
|
|
||||||
* Instead of passing various parameters on the `ConnectionsOptions` you know specify the `agent` parameter. This object can use be created by libraries such as `https-proxy-agent` or any that implements the `http.Agent`.
|
|
||||||
* This was changed to both support the latest `https-proxy-agent` and to remove the need to include the package in bundlers. Tests will still be done using `https-proxy-agent` and only tested in a node environment which was the only way it was previously supported anyway
|
|
||||||
* Remove `BroadcastClient` which was deprecated
|
|
||||||
* Uses `@xrplf/secret-numbers` instead of `xrpl-secret-numbers`
|
|
||||||
* Improve key algorithm detection. It will now throw Errors with helpful messages
|
|
||||||
* Move `authorizeChannel` from `wallet/signer` to `wallet/authorizeChannel` to solve a circular dependency issue.
|
|
||||||
* When using a bundler you must remove the mapping of `ws` to `WSWrapper`. ex. `ws: 'xrpl/dist/npm/client/WSWrapper'`. See [../UNIQUE_STEPS](Unique Steps) for the new, much smaller, configs.
|
|
||||||
|
|
||||||
### Bundling Changes
|
|
||||||
Bundler configurations are much more simplified. See [../UNIQUE_STEPS](Unique Steps) for the new, much smaller, configs.
|
|
||||||
* removed the following polyfills:
|
|
||||||
* `assert`
|
|
||||||
* `crypto-browserify`
|
|
||||||
* `https-browserify`
|
|
||||||
* `os-browserify`
|
|
||||||
* `stream-browserify`
|
|
||||||
* `stream-http`
|
|
||||||
* `url`
|
|
||||||
* `util` - previously added automatically by `webpack`
|
|
||||||
* `events` - previously added automatically by `webpack` but manual for `vite`
|
|
||||||
* Removed mappings for:
|
|
||||||
* `ws` to `WsWrapper`
|
|
||||||
* Excluding `https-proxy-agent`
|
|
||||||
|
|
||||||
### Changed
|
|
||||||
* Remove `lodash` as a dependency
|
|
||||||
* Remove many polyfills that were only used for testing in the browser
|
|
||||||
* Remove `util` from bundle by switching `inspect` to `JSON.stringify`
|
|
||||||
* Add type for metadata for specific transactions(`Payment`, `NFTokenMint`, `NFTokenCreateOffer`, `NFTokenAcceptOffer`, `NFTokenCancelOffer`)
|
|
||||||
|
|
||||||
### Fixed
|
|
||||||
* Fixed Wallet.generate() ignoring the `algorithm` parameter (Only a problem once binary-codec fix for `derive_keypair` is added)
|
|
||||||
* Fixed Wallet.fromSeed() ignoring the `algorithm` parameter
|
|
||||||
* Added pseudo-transaction support to hash functions and response types
|
|
||||||
|
|
||||||
## 2.14.1 (2024-02-01)
|
## 2.14.1 (2024-02-01)
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "xrpl",
|
"name": "xrpl",
|
||||||
"version": "3.0.0",
|
"version": "4.2.0",
|
||||||
"license": "ISC",
|
"license": "ISC",
|
||||||
"description": "A TypeScript/JavaScript API for interacting with the XRP Ledger in Node.js and the browser",
|
"description": "A TypeScript/JavaScript API for interacting with the XRP Ledger in Node.js and the browser",
|
||||||
"files": [
|
"files": [
|
||||||
@@ -24,17 +24,16 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@scure/bip32": "^1.3.1",
|
"@scure/bip32": "^1.3.1",
|
||||||
"@scure/bip39": "^1.2.1",
|
"@scure/bip39": "^1.2.1",
|
||||||
"@xrplf/isomorphic": "^1.0.0",
|
"@xrplf/isomorphic": "^1.0.1",
|
||||||
"@xrplf/secret-numbers": "^1.0.0",
|
"@xrplf/secret-numbers": "^1.0.0",
|
||||||
"bignumber.js": "^9.0.0",
|
"bignumber.js": "^9.0.0",
|
||||||
"cross-fetch": "^4.0.0",
|
|
||||||
"eventemitter3": "^5.0.1",
|
"eventemitter3": "^5.0.1",
|
||||||
"ripple-address-codec": "^5.0.0",
|
"ripple-address-codec": "^5.0.0",
|
||||||
"ripple-binary-codec": "^2.0.0",
|
"ripple-binary-codec": "^2.3.0",
|
||||||
"ripple-keypairs": "^2.0.0"
|
"ripple-keypairs": "^2.0.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/node": "^16.18.38",
|
"@types/node": "^18.18.38",
|
||||||
"eventemitter3": "^5.0.1",
|
"eventemitter3": "^5.0.1",
|
||||||
"https-proxy-agent": "^7.0.1",
|
"https-proxy-agent": "^7.0.1",
|
||||||
"karma": "^6.4.1",
|
"karma": "^6.4.1",
|
||||||
@@ -42,9 +41,9 @@
|
|||||||
"karma-jasmine": "^5.1.0",
|
"karma-jasmine": "^5.1.0",
|
||||||
"karma-webpack": "^5.0.0",
|
"karma-webpack": "^5.0.0",
|
||||||
"lodash": "^4.17.4",
|
"lodash": "^4.17.4",
|
||||||
"react": "^18.2.0",
|
"react": "^19.0.0",
|
||||||
"run-s": "^0.0.0",
|
"run-s": "^0.0.0",
|
||||||
"typedoc": "0.25.0",
|
"typedoc": "0.27.6",
|
||||||
"ws": "^8.14.2"
|
"ws": "^8.14.2"
|
||||||
},
|
},
|
||||||
"resolutions": {
|
"resolutions": {
|
||||||
@@ -87,6 +86,6 @@
|
|||||||
"xrpl"
|
"xrpl"
|
||||||
],
|
],
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=16.0.0"
|
"node": ">=18.0.0"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,170 +0,0 @@
|
|||||||
/* eslint-disable max-depth -- needed for attestation checking */
|
|
||||||
/* eslint-disable @typescript-eslint/consistent-type-assertions -- needed here */
|
|
||||||
/* eslint-disable no-await-in-loop -- needed here */
|
|
||||||
import {
|
|
||||||
AccountObjectsRequest,
|
|
||||||
LedgerEntry,
|
|
||||||
Client,
|
|
||||||
XChainAccountCreateCommit,
|
|
||||||
XChainBridge,
|
|
||||||
XChainCommit,
|
|
||||||
XChainCreateClaimID,
|
|
||||||
xrpToDrops,
|
|
||||||
Wallet,
|
|
||||||
getXChainClaimID,
|
|
||||||
} from '../../src'
|
|
||||||
|
|
||||||
async function sleep(sec: number): Promise<void> {
|
|
||||||
return new Promise((resolve) => {
|
|
||||||
setTimeout(resolve, sec * 1000)
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
const lockingClient = new Client('wss://s.devnet.rippletest.net:51233')
|
|
||||||
const issuingClient = new Client(
|
|
||||||
'wss://sidechain-net2.devnet.rippletest.net:51233',
|
|
||||||
)
|
|
||||||
const MAX_LEDGERS_WAITED = 5
|
|
||||||
const LEDGER_CLOSE_TIME = 4
|
|
||||||
|
|
||||||
void bridgeTransfer()
|
|
||||||
|
|
||||||
async function bridgeTransfer(): Promise<void> {
|
|
||||||
await lockingClient.connect()
|
|
||||||
await issuingClient.connect()
|
|
||||||
const lockingChainDoor = 'rnQAXXWoFNN6PEqwqsdTngCtFPCrmfuqFJ'
|
|
||||||
|
|
||||||
const accountObjectsRequest: AccountObjectsRequest = {
|
|
||||||
command: 'account_objects',
|
|
||||||
account: lockingChainDoor,
|
|
||||||
type: 'bridge',
|
|
||||||
}
|
|
||||||
const lockingAccountObjects = (
|
|
||||||
await lockingClient.request(accountObjectsRequest)
|
|
||||||
).result.account_objects
|
|
||||||
// There will only be one here - a door account can only have one bridge per currency
|
|
||||||
const bridgeData = lockingAccountObjects.filter(
|
|
||||||
(obj) =>
|
|
||||||
obj.LedgerEntryType === 'Bridge' &&
|
|
||||||
obj.XChainBridge.LockingChainIssue.currency === 'XRP',
|
|
||||||
)[0] as LedgerEntry.Bridge
|
|
||||||
const bridge: XChainBridge = bridgeData.XChainBridge
|
|
||||||
console.log(bridge)
|
|
||||||
|
|
||||||
console.log('Creating wallet on the locking chain via the faucet...')
|
|
||||||
const { wallet: wallet1 } = await lockingClient.fundWallet()
|
|
||||||
console.log(wallet1)
|
|
||||||
const wallet2 = Wallet.generate()
|
|
||||||
|
|
||||||
console.log(
|
|
||||||
`Creating ${wallet2.classicAddress} on the issuing chain via the bridge...`,
|
|
||||||
)
|
|
||||||
|
|
||||||
const fundTx: XChainAccountCreateCommit = {
|
|
||||||
TransactionType: 'XChainAccountCreateCommit',
|
|
||||||
Account: wallet1.classicAddress,
|
|
||||||
XChainBridge: bridge,
|
|
||||||
SignatureReward: bridgeData.SignatureReward,
|
|
||||||
Destination: wallet2.classicAddress,
|
|
||||||
Amount: (
|
|
||||||
parseInt(bridgeData.MinAccountCreateAmount as string, 10) * 2
|
|
||||||
).toString(),
|
|
||||||
}
|
|
||||||
const fundResponse = await lockingClient.submitAndWait(fundTx, {
|
|
||||||
wallet: wallet1,
|
|
||||||
})
|
|
||||||
console.log(fundResponse)
|
|
||||||
|
|
||||||
console.log(
|
|
||||||
'Waiting for the attestation to go through... (usually 8-12 seconds)',
|
|
||||||
)
|
|
||||||
let ledgersWaited = 0
|
|
||||||
let initialBalance = 0
|
|
||||||
while (ledgersWaited < MAX_LEDGERS_WAITED) {
|
|
||||||
await sleep(LEDGER_CLOSE_TIME)
|
|
||||||
try {
|
|
||||||
initialBalance = await issuingClient.getXrpBalance(wallet2.classicAddress)
|
|
||||||
console.log(
|
|
||||||
`Wallet ${wallet2.classicAddress} has been funded with a balance of ${initialBalance} XRP`,
|
|
||||||
)
|
|
||||||
break
|
|
||||||
} catch (_error) {
|
|
||||||
ledgersWaited += 1
|
|
||||||
if (ledgersWaited === MAX_LEDGERS_WAITED) {
|
|
||||||
// This error should never be hit if the bridge is running
|
|
||||||
throw Error('Destination account creation via the bridge failed.')
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
console.log(
|
|
||||||
`Transferring funds from ${wallet1.classicAddress} on the locking chain to ` +
|
|
||||||
`${wallet2.classicAddress} on the issuing_chain...`,
|
|
||||||
)
|
|
||||||
|
|
||||||
// Fetch the claim ID for the transfer
|
|
||||||
console.log('Step 1: Fetching the claim ID for the transfer...')
|
|
||||||
const claimIdTx: XChainCreateClaimID = {
|
|
||||||
TransactionType: 'XChainCreateClaimID',
|
|
||||||
Account: wallet2.classicAddress,
|
|
||||||
XChainBridge: bridge,
|
|
||||||
SignatureReward: bridgeData.SignatureReward,
|
|
||||||
OtherChainSource: wallet1.classicAddress,
|
|
||||||
}
|
|
||||||
const claimIdResult = await issuingClient.submitAndWait(claimIdTx, {
|
|
||||||
wallet: wallet2,
|
|
||||||
})
|
|
||||||
console.log(claimIdResult)
|
|
||||||
|
|
||||||
// Extract new claim ID from metadata
|
|
||||||
const xchainClaimId = getXChainClaimID(claimIdResult.result.meta)
|
|
||||||
if (xchainClaimId == null) {
|
|
||||||
// This shouldn't trigger assuming the transaction succeeded
|
|
||||||
throw Error('Could not extract XChainClaimID')
|
|
||||||
}
|
|
||||||
|
|
||||||
console.log(`Claim ID for the transfer: ${xchainClaimId}`)
|
|
||||||
|
|
||||||
console.log(
|
|
||||||
'Step 2: Locking the funds on the locking chain with an XChainCommit transaction...',
|
|
||||||
)
|
|
||||||
const commitTx: XChainCommit = {
|
|
||||||
TransactionType: 'XChainCommit',
|
|
||||||
Account: wallet1.classicAddress,
|
|
||||||
Amount: xrpToDrops(1),
|
|
||||||
XChainBridge: bridge,
|
|
||||||
XChainClaimID: xchainClaimId,
|
|
||||||
OtherChainDestination: wallet2.classicAddress,
|
|
||||||
}
|
|
||||||
const commitResult = await lockingClient.submitAndWait(commitTx, {
|
|
||||||
wallet: wallet1,
|
|
||||||
})
|
|
||||||
console.log(commitResult)
|
|
||||||
|
|
||||||
console.log(
|
|
||||||
'Waiting for the attestation to go through... (usually 8-12 seconds)',
|
|
||||||
)
|
|
||||||
ledgersWaited = 0
|
|
||||||
while (ledgersWaited < MAX_LEDGERS_WAITED) {
|
|
||||||
await sleep(LEDGER_CLOSE_TIME)
|
|
||||||
const currentBalance = await issuingClient.getXrpBalance(
|
|
||||||
wallet2.classicAddress,
|
|
||||||
)
|
|
||||||
console.log(initialBalance, currentBalance)
|
|
||||||
if (currentBalance > initialBalance) {
|
|
||||||
console.log('Transfer is complete')
|
|
||||||
console.log(
|
|
||||||
`New balance of ${wallet2.classicAddress} is ${currentBalance} XRP`,
|
|
||||||
)
|
|
||||||
break
|
|
||||||
}
|
|
||||||
|
|
||||||
ledgersWaited += 1
|
|
||||||
if (ledgersWaited === MAX_LEDGERS_WAITED) {
|
|
||||||
throw Error('Bridge transfer failed.')
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
await lockingClient.disconnect()
|
|
||||||
await issuingClient.disconnect()
|
|
||||||
}
|
|
||||||
@@ -56,7 +56,7 @@ async function claimPayChannel(): Promise<void> {
|
|||||||
Channel: hashes.hashPaymentChannel(
|
Channel: hashes.hashPaymentChannel(
|
||||||
wallet1.classicAddress,
|
wallet1.classicAddress,
|
||||||
wallet2.classicAddress,
|
wallet2.classicAddress,
|
||||||
paymentChannelResponse.result.Sequence ?? 0,
|
paymentChannelResponse.result.tx_json.Sequence ?? 0,
|
||||||
),
|
),
|
||||||
Amount: '100',
|
Amount: '100',
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,11 @@
|
|||||||
import { Client, Payment } from '../../src'
|
import { Client, Payment } from '../../src'
|
||||||
|
|
||||||
|
// Prerequisites for this snippet. Please verify these conditions after a reset of the
|
||||||
|
// test network:
|
||||||
|
// - destination_account must have a trust line with the destination_amount.issuer
|
||||||
|
// - There must be appropriate DEX Offers or XRP/TST AMM for the cross-currency exchange
|
||||||
|
|
||||||
|
// PathFind RPC requires the use of a Websocket client only
|
||||||
const client = new Client('wss://s.altnet.rippletest.net:51233')
|
const client = new Client('wss://s.altnet.rippletest.net:51233')
|
||||||
|
|
||||||
async function createTxWithPaths(): Promise<void> {
|
async function createTxWithPaths(): Promise<void> {
|
||||||
@@ -8,22 +14,17 @@ async function createTxWithPaths(): Promise<void> {
|
|||||||
const { wallet } = await client.fundWallet(null, {
|
const { wallet } = await client.fundWallet(null, {
|
||||||
usageContext: 'code snippets',
|
usageContext: 'code snippets',
|
||||||
})
|
})
|
||||||
const destination_account = 'rKT4JX4cCof6LcDYRz8o3rGRu7qxzZ2Zwj'
|
const destination_account = 'rJPeZVPty1bXXbDR9oKscg2irqABr7sP3t'
|
||||||
const destination_amount = {
|
const destination_amount = {
|
||||||
value: '0.001',
|
value: '0.001',
|
||||||
currency: 'USD',
|
currency: 'TST',
|
||||||
issuer: 'rVnYNK9yuxBz4uP8zC8LEFokM2nqH3poc',
|
issuer: 'rP9jPyP5kyvFRb6ZiRghAGw5u8SGAmU4bd',
|
||||||
}
|
}
|
||||||
|
|
||||||
const resp = await client.request({
|
const resp = await client.request({
|
||||||
// TOOD: Replace with path_find - https://github.com/XRPLF/xrpl.js/issues/2385
|
command: 'path_find',
|
||||||
command: 'ripple_path_find',
|
subcommand: 'create',
|
||||||
source_account: wallet.classicAddress,
|
source_account: wallet.classicAddress,
|
||||||
source_currencies: [
|
|
||||||
{
|
|
||||||
currency: 'XRP',
|
|
||||||
},
|
|
||||||
],
|
|
||||||
destination_account,
|
destination_account,
|
||||||
destination_amount,
|
destination_amount,
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ async function sendEscrow(): Promise<void> {
|
|||||||
TransactionType: 'EscrowFinish',
|
TransactionType: 'EscrowFinish',
|
||||||
Account: wallet1.classicAddress,
|
Account: wallet1.classicAddress,
|
||||||
Owner: wallet1.classicAddress,
|
Owner: wallet1.classicAddress,
|
||||||
OfferSequence: Number(createEscrowResponse.result.Sequence),
|
OfferSequence: Number(createEscrowResponse.result.tx_json.Sequence),
|
||||||
}
|
}
|
||||||
|
|
||||||
await client.submit(finishTx, {
|
await client.submit(finishTx, {
|
||||||
|
|||||||
@@ -14,13 +14,11 @@ export interface FaucetWallet {
|
|||||||
export enum FaucetNetwork {
|
export enum FaucetNetwork {
|
||||||
Testnet = 'faucet.altnet.rippletest.net',
|
Testnet = 'faucet.altnet.rippletest.net',
|
||||||
Devnet = 'faucet.devnet.rippletest.net',
|
Devnet = 'faucet.devnet.rippletest.net',
|
||||||
HooksV3Testnet = 'hooks-testnet-v3.xrpl-labs.com',
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const FaucetNetworkPaths: Record<string, string> = {
|
export const FaucetNetworkPaths: Record<string, string> = {
|
||||||
[FaucetNetwork.Testnet]: '/accounts',
|
[FaucetNetwork.Testnet]: '/accounts',
|
||||||
[FaucetNetwork.Devnet]: '/accounts',
|
[FaucetNetwork.Devnet]: '/accounts',
|
||||||
[FaucetNetwork.HooksV3Testnet]: '/accounts',
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -33,10 +31,6 @@ export const FaucetNetworkPaths: Record<string, string> = {
|
|||||||
export function getFaucetHost(client: Client): FaucetNetwork | undefined {
|
export function getFaucetHost(client: Client): FaucetNetwork | undefined {
|
||||||
const connectionUrl = client.url
|
const connectionUrl = client.url
|
||||||
|
|
||||||
if (connectionUrl.includes('hooks-testnet-v3')) {
|
|
||||||
return FaucetNetwork.HooksV3Testnet
|
|
||||||
}
|
|
||||||
|
|
||||||
// 'altnet' for Ripple Testnet server and 'testnet' for XRPL Labs Testnet server
|
// 'altnet' for Ripple Testnet server and 'testnet' for XRPL Labs Testnet server
|
||||||
if (connectionUrl.includes('altnet') || connectionUrl.includes('testnet')) {
|
if (connectionUrl.includes('altnet') || connectionUrl.includes('testnet')) {
|
||||||
return FaucetNetwork.Testnet
|
return FaucetNetwork.Testnet
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import fetch from 'cross-fetch'
|
|
||||||
import { isValidClassicAddress } from 'ripple-address-codec'
|
import { isValidClassicAddress } from 'ripple-address-codec'
|
||||||
|
|
||||||
import type { Client } from '../client'
|
import type { Client } from '../client'
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import {
|
|||||||
TimeoutError,
|
TimeoutError,
|
||||||
XrplError,
|
XrplError,
|
||||||
} from '../errors'
|
} from '../errors'
|
||||||
|
import type { APIVersion } from '../models'
|
||||||
import { Response, RequestResponseMap } from '../models/methods'
|
import { Response, RequestResponseMap } from '../models/methods'
|
||||||
import { BaseRequest, ErrorResponse } from '../models/methods/baseMethod'
|
import { BaseRequest, ErrorResponse } from '../models/methods/baseMethod'
|
||||||
|
|
||||||
@@ -35,10 +36,10 @@ export default class RequestManager {
|
|||||||
* @param timer - The timer associated with the promise.
|
* @param timer - The timer associated with the promise.
|
||||||
* @returns A promise that resolves to the specified generic type.
|
* @returns A promise that resolves to the specified generic type.
|
||||||
*/
|
*/
|
||||||
public async addPromise<R extends BaseRequest, T = RequestResponseMap<R>>(
|
public async addPromise<
|
||||||
newId: string | number,
|
R extends BaseRequest,
|
||||||
timer: ReturnType<typeof setTimeout>,
|
T = RequestResponseMap<R, APIVersion>,
|
||||||
): Promise<T> {
|
>(newId: string | number, timer: ReturnType<typeof setTimeout>): Promise<T> {
|
||||||
return new Promise<T>((resolve, reject) => {
|
return new Promise<T>((resolve, reject) => {
|
||||||
this.promisesAwaitingResponse.set(newId, {
|
this.promisesAwaitingResponse.set(newId, {
|
||||||
resolve,
|
resolve,
|
||||||
@@ -55,7 +56,10 @@ export default class RequestManager {
|
|||||||
* @param response - Response to return.
|
* @param response - Response to return.
|
||||||
* @throws Error if no existing promise with the given ID.
|
* @throws Error if no existing promise with the given ID.
|
||||||
*/
|
*/
|
||||||
public resolve(id: string | number, response: Response): void {
|
public resolve(
|
||||||
|
id: string | number,
|
||||||
|
response: Partial<Response<APIVersion>>,
|
||||||
|
): void {
|
||||||
const promise = this.promisesAwaitingResponse.get(id)
|
const promise = this.promisesAwaitingResponse.get(id)
|
||||||
if (promise == null) {
|
if (promise == null) {
|
||||||
throw new XrplError(`No existing promise with id ${id}`, {
|
throw new XrplError(`No existing promise with id ${id}`, {
|
||||||
@@ -111,10 +115,10 @@ export default class RequestManager {
|
|||||||
* @returns Request ID, new request form, and the promise for resolving the request.
|
* @returns Request ID, new request form, and the promise for resolving the request.
|
||||||
* @throws XrplError if request with the same ID is already pending.
|
* @throws XrplError if request with the same ID is already pending.
|
||||||
*/
|
*/
|
||||||
public createRequest<R extends BaseRequest, T = RequestResponseMap<R>>(
|
public createRequest<
|
||||||
request: R,
|
R extends BaseRequest,
|
||||||
timeout: number,
|
T = RequestResponseMap<R, APIVersion>,
|
||||||
): [string | number, string, Promise<T>] {
|
>(request: R, timeout: number): [string | number, string, Promise<T>] {
|
||||||
let newId: string | number
|
let newId: string | number
|
||||||
if (request.id == null) {
|
if (request.id == null) {
|
||||||
newId = this.nextId
|
newId = this.nextId
|
||||||
@@ -171,7 +175,9 @@ export default class RequestManager {
|
|||||||
* @param response - The response to handle.
|
* @param response - The response to handle.
|
||||||
* @throws ResponseFormatError if the response format is invalid, RippledError if rippled returns an error.
|
* @throws ResponseFormatError if the response format is invalid, RippledError if rippled returns an error.
|
||||||
*/
|
*/
|
||||||
public handleResponse(response: Partial<Response | ErrorResponse>): void {
|
public handleResponse(
|
||||||
|
response: Partial<Response<APIVersion> | ErrorResponse>,
|
||||||
|
): void {
|
||||||
if (
|
if (
|
||||||
response.id == null ||
|
response.id == null ||
|
||||||
!(typeof response.id === 'string' || typeof response.id === 'number')
|
!(typeof response.id === 'string' || typeof response.id === 'number')
|
||||||
@@ -205,8 +211,7 @@ export default class RequestManager {
|
|||||||
}
|
}
|
||||||
// status no longer needed because error is thrown if status is not "success"
|
// status no longer needed because error is thrown if status is not "success"
|
||||||
delete response.status
|
delete response.status
|
||||||
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Must be a valid Response here
|
this.resolve(response.id, response)
|
||||||
this.resolve(response.id, response as unknown as Response)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ import {
|
|||||||
ConnectionError,
|
ConnectionError,
|
||||||
XrplError,
|
XrplError,
|
||||||
} from '../errors'
|
} from '../errors'
|
||||||
import type { RequestResponseMap } from '../models'
|
import type { APIVersion, RequestResponseMap } from '../models'
|
||||||
import { BaseRequest } from '../models/methods/baseMethod'
|
import { BaseRequest } from '../models/methods/baseMethod'
|
||||||
|
|
||||||
import ConnectionManager from './ConnectionManager'
|
import ConnectionManager from './ConnectionManager'
|
||||||
@@ -267,6 +267,7 @@ export class Connection extends EventEmitter {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Disconnect the websocket, then connect again.
|
* Disconnect the websocket, then connect again.
|
||||||
|
*
|
||||||
*/
|
*/
|
||||||
public async reconnect(): Promise<void> {
|
public async reconnect(): Promise<void> {
|
||||||
/*
|
/*
|
||||||
@@ -287,10 +288,10 @@ export class Connection extends EventEmitter {
|
|||||||
* @returns The response from the rippled server.
|
* @returns The response from the rippled server.
|
||||||
* @throws NotConnectedError if the Connection isn't connected to a server.
|
* @throws NotConnectedError if the Connection isn't connected to a server.
|
||||||
*/
|
*/
|
||||||
public async request<R extends BaseRequest, T = RequestResponseMap<R>>(
|
public async request<
|
||||||
request: R,
|
R extends BaseRequest,
|
||||||
timeout?: number,
|
T = RequestResponseMap<R, APIVersion>,
|
||||||
): Promise<T> {
|
>(request: R, timeout?: number): Promise<T> {
|
||||||
if (!this.shouldBeConnected || this.ws == null) {
|
if (!this.shouldBeConnected || this.ws == null) {
|
||||||
throw new NotConnectedError(JSON.stringify(request), request)
|
throw new NotConnectedError(JSON.stringify(request), request)
|
||||||
}
|
}
|
||||||
@@ -468,6 +469,7 @@ export class Connection extends EventEmitter {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Starts a heartbeat to check the connection with the server.
|
* Starts a heartbeat to check the connection with the server.
|
||||||
|
*
|
||||||
*/
|
*/
|
||||||
private startHeartbeatInterval(): void {
|
private startHeartbeatInterval(): void {
|
||||||
this.clearHeartbeatInterval()
|
this.clearHeartbeatInterval()
|
||||||
|
|||||||
@@ -9,7 +9,12 @@ import {
|
|||||||
ValidationError,
|
ValidationError,
|
||||||
XrplError,
|
XrplError,
|
||||||
} from '../errors'
|
} from '../errors'
|
||||||
import type { LedgerIndex, Balance } from '../models/common'
|
import {
|
||||||
|
APIVersion,
|
||||||
|
LedgerIndex,
|
||||||
|
Balance,
|
||||||
|
DEFAULT_API_VERSION,
|
||||||
|
} from '../models/common'
|
||||||
import {
|
import {
|
||||||
Request,
|
Request,
|
||||||
// account methods
|
// account methods
|
||||||
@@ -35,14 +40,19 @@ import type {
|
|||||||
MarkerRequest,
|
MarkerRequest,
|
||||||
MarkerResponse,
|
MarkerResponse,
|
||||||
SubmitResponse,
|
SubmitResponse,
|
||||||
|
SimulateRequest,
|
||||||
} from '../models/methods'
|
} from '../models/methods'
|
||||||
import type { BookOffer, BookOfferCurrency } from '../models/methods/bookOffers'
|
import type { BookOffer, BookOfferCurrency } from '../models/methods/bookOffers'
|
||||||
|
import {
|
||||||
|
SimulateBinaryResponse,
|
||||||
|
SimulateJsonResponse,
|
||||||
|
} from '../models/methods/simulate'
|
||||||
import type {
|
import type {
|
||||||
EventTypes,
|
EventTypes,
|
||||||
OnEventToListenerMap,
|
OnEventToListenerMap,
|
||||||
} from '../models/methods/subscribe'
|
} from '../models/methods/subscribe'
|
||||||
import type { SubmittableTransaction } from '../models/transactions'
|
import type { SubmittableTransaction } from '../models/transactions'
|
||||||
import { setTransactionFlagsToNumber } from '../models/utils/flags'
|
import { convertTxFlagsToNumber } from '../models/utils/flags'
|
||||||
import {
|
import {
|
||||||
ensureClassicAddress,
|
ensureClassicAddress,
|
||||||
submitRequest,
|
submitRequest,
|
||||||
@@ -88,8 +98,23 @@ import {
|
|||||||
} from './partialPayment'
|
} from './partialPayment'
|
||||||
|
|
||||||
export interface ClientOptions extends ConnectionUserOptions {
|
export interface ClientOptions extends ConnectionUserOptions {
|
||||||
|
/**
|
||||||
|
* Multiplication 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.
|
||||||
|
*
|
||||||
|
* @category Fee
|
||||||
|
*/
|
||||||
feeCushion?: number
|
feeCushion?: number
|
||||||
|
/**
|
||||||
|
* Maximum transaction cost to allow, in decimal XRP. Must be a string-encoded
|
||||||
|
* number. Defaults to '2'.
|
||||||
|
*
|
||||||
|
* @category Fee
|
||||||
|
*/
|
||||||
maxFeeXRP?: string
|
maxFeeXRP?: string
|
||||||
|
/**
|
||||||
|
* Duration to wait for a request to timeout.
|
||||||
|
*/
|
||||||
timeout?: number
|
timeout?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -198,6 +223,12 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
*/
|
*/
|
||||||
public buildVersion: string | undefined
|
public buildVersion: string | undefined
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API Version used by the server this client is connected to
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public apiVersion: APIVersion = DEFAULT_API_VERSION
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates a new Client with a websocket connection to a rippled server.
|
* Creates a new Client with a websocket connection to a rippled server.
|
||||||
*
|
*
|
||||||
@@ -211,7 +242,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* const client = new Client('wss://s.altnet.rippletest.net:51233')
|
* const client = new Client('wss://s.altnet.rippletest.net:51233')
|
||||||
* ```
|
* ```
|
||||||
*/
|
*/
|
||||||
// eslint-disable-next-line max-lines-per-function -- okay because we have to set up all the connection handlers
|
/* eslint-disable max-lines-per-function -- the constructor requires more lines to implement the logic */
|
||||||
public constructor(server: string, options: ClientOptions = {}) {
|
public constructor(server: string, options: ClientOptions = {}) {
|
||||||
super()
|
super()
|
||||||
if (typeof server !== 'string' || !/wss?(?:\+unix)?:\/\//u.exec(server)) {
|
if (typeof server !== 'string' || !/wss?(?:\+unix)?:\/\//u.exec(server)) {
|
||||||
@@ -275,6 +306,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
this.emit('path_find', path)
|
this.emit('path_find', path)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
/* eslint-enable max-lines-per-function */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the url that the client is connected to.
|
* Get the url that the client is connected to.
|
||||||
@@ -291,7 +323,6 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* additional request body parameters.
|
* additional request body parameters.
|
||||||
*
|
*
|
||||||
* @category Network
|
* @category Network
|
||||||
*
|
|
||||||
* @param req - Request to send to the server.
|
* @param req - Request to send to the server.
|
||||||
* @returns The response from the server.
|
* @returns The response from the server.
|
||||||
*
|
*
|
||||||
@@ -304,16 +335,20 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* console.log(response)
|
* console.log(response)
|
||||||
* ```
|
* ```
|
||||||
*/
|
*/
|
||||||
public async request<R extends Request, T = RequestResponseMap<R>>(
|
public async request<
|
||||||
req: R,
|
R extends Request,
|
||||||
): Promise<T> {
|
V extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
const response = await this.connection.request<R, T>({
|
T = RequestResponseMap<R, V>,
|
||||||
|
>(req: R): Promise<T> {
|
||||||
|
const request = {
|
||||||
...req,
|
...req,
|
||||||
account: req.account
|
account:
|
||||||
? // eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Must be string
|
typeof req.account === 'string'
|
||||||
ensureClassicAddress(req.account as string)
|
? ensureClassicAddress(req.account)
|
||||||
: undefined,
|
: undefined,
|
||||||
})
|
api_version: req.api_version ?? this.apiVersion,
|
||||||
|
}
|
||||||
|
const response = await this.connection.request<R, T>(request)
|
||||||
|
|
||||||
// mutates `response` to add warnings
|
// mutates `response` to add warnings
|
||||||
handlePartialPayment(req.command, response)
|
handlePartialPayment(req.command, response)
|
||||||
@@ -422,9 +457,10 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* const allResponses = await client.requestAll({ command: 'transaction_data' });
|
* const allResponses = await client.requestAll({ command: 'transaction_data' });
|
||||||
* console.log(allResponses);
|
* console.log(allResponses);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
public async requestAll<
|
public async requestAll<
|
||||||
T extends MarkerRequest,
|
T extends MarkerRequest,
|
||||||
U = RequestAllResponseMap<T>,
|
U = RequestAllResponseMap<T, APIVersion>,
|
||||||
>(request: T, collect?: string): Promise<U[]> {
|
>(request: T, collect?: string): Promise<U[]> {
|
||||||
/*
|
/*
|
||||||
* The data under collection is keyed based on the command. Fail if command
|
* The data under collection is keyed based on the command. Fail if command
|
||||||
@@ -441,7 +477,6 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
const countTo: number = request.limit == null ? Infinity : request.limit
|
const countTo: number = request.limit == null ? Infinity : request.limit
|
||||||
let count = 0
|
let count = 0
|
||||||
let marker: unknown = request.marker
|
let marker: unknown = request.marker
|
||||||
let lastBatchLength: number
|
|
||||||
const results: U[] = []
|
const results: U[] = []
|
||||||
do {
|
do {
|
||||||
const countRemaining = clamp(countTo - count, MIN_LIMIT, MAX_LIMIT)
|
const countRemaining = clamp(countTo - count, MIN_LIMIT, MAX_LIMIT)
|
||||||
@@ -453,7 +488,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
// eslint-disable-next-line no-await-in-loop -- Necessary for this, it really has to wait
|
// eslint-disable-next-line no-await-in-loop -- Necessary for this, it really has to wait
|
||||||
const singleResponse = await this.connection.request(repeatProps)
|
const singleResponse = await this.connection.request(repeatProps)
|
||||||
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Should be true
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Should be true
|
||||||
const singleResult = (singleResponse as MarkerResponse).result
|
const singleResult = (singleResponse as MarkerResponse<APIVersion>).result
|
||||||
if (!(collectKey in singleResult)) {
|
if (!(collectKey in singleResult)) {
|
||||||
throw new XrplError(`${collectKey} not in result`)
|
throw new XrplError(`${collectKey} not in result`)
|
||||||
}
|
}
|
||||||
@@ -465,11 +500,8 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
// Make sure we handle when no data (not even an empty array) is returned.
|
// Make sure we handle when no data (not even an empty array) is returned.
|
||||||
if (Array.isArray(collectedData)) {
|
if (Array.isArray(collectedData)) {
|
||||||
count += collectedData.length
|
count += collectedData.length
|
||||||
lastBatchLength = collectedData.length
|
|
||||||
} else {
|
|
||||||
lastBatchLength = 0
|
|
||||||
}
|
}
|
||||||
} while (Boolean(marker) && count < countTo && lastBatchLength !== 0)
|
} while (Boolean(marker) && count < countTo)
|
||||||
return results
|
return results
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -627,7 +659,10 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* @param signersCount - The expected number of signers for this transaction.
|
* @param signersCount - The expected number of signers for this transaction.
|
||||||
* Only used for multisigned transactions.
|
* Only used for multisigned transactions.
|
||||||
* @returns The autofilled transaction.
|
* @returns The autofilled transaction.
|
||||||
|
* @throws ValidationError If Amount and DeliverMax fields are not identical in a Payment Transaction
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
// eslint-disable-next-line complexity -- handling Payment transaction API v2 requires more logic
|
||||||
public async autofill<T extends SubmittableTransaction>(
|
public async autofill<T extends SubmittableTransaction>(
|
||||||
transaction: T,
|
transaction: T,
|
||||||
signersCount?: number,
|
signersCount?: number,
|
||||||
@@ -635,8 +670,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
const tx = { ...transaction }
|
const tx = { ...transaction }
|
||||||
|
|
||||||
setValidAddresses(tx)
|
setValidAddresses(tx)
|
||||||
|
tx.Flags = convertTxFlagsToNumber(tx)
|
||||||
setTransactionFlagsToNumber(tx)
|
|
||||||
|
|
||||||
const promises: Array<Promise<void>> = []
|
const promises: Array<Promise<void>> = []
|
||||||
if (tx.NetworkID == null) {
|
if (tx.NetworkID == null) {
|
||||||
@@ -655,6 +689,34 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
promises.push(checkAccountDeleteBlockers(this, tx))
|
promises.push(checkAccountDeleteBlockers(this, tx))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment -- ignore type-assertions on the DeliverMax property
|
||||||
|
// @ts-expect-error -- DeliverMax property exists only at the RPC level, not at the protocol level
|
||||||
|
if (tx.TransactionType === 'Payment' && tx.DeliverMax != null) {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- This is a valid null check for Amount
|
||||||
|
if (tx.Amount == null) {
|
||||||
|
// If only DeliverMax is provided, use it to populate the Amount field
|
||||||
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment -- ignore type-assertions on the DeliverMax property
|
||||||
|
// @ts-expect-error -- DeliverMax property exists only at the RPC level, not at the protocol level
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unsafe-assignment -- DeliverMax is a known RPC-level property
|
||||||
|
tx.Amount = tx.DeliverMax
|
||||||
|
}
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment -- ignore type-assertions on the DeliverMax property
|
||||||
|
// @ts-expect-error -- DeliverMax property exists only at the RPC level, not at the protocol level
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- This is a valid null check for Amount
|
||||||
|
if (tx.Amount != null && tx.Amount !== tx.DeliverMax) {
|
||||||
|
return Promise.reject(
|
||||||
|
new ValidationError(
|
||||||
|
'PaymentTransaction: Amount and DeliverMax fields must be identical when both are provided',
|
||||||
|
),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment -- ignore type-assertions on the DeliverMax property
|
||||||
|
// @ts-expect-error -- DeliverMax property exists only at the RPC level, not at the protocol level
|
||||||
|
delete tx.DeliverMax
|
||||||
|
}
|
||||||
|
|
||||||
return Promise.all(promises).then(() => tx)
|
return Promise.all(promises).then(() => tx)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -707,6 +769,41 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
return submitRequest(this, signedTx, opts?.failHard)
|
return submitRequest(this, signedTx, opts?.failHard)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Simulates an unsigned transaction.
|
||||||
|
* Steps performed on a transaction:
|
||||||
|
* 1. Autofill.
|
||||||
|
* 2. Sign & Encode.
|
||||||
|
* 3. Submit.
|
||||||
|
*
|
||||||
|
* @category Core
|
||||||
|
*
|
||||||
|
* @param transaction - A transaction to autofill, sign & encode, and submit.
|
||||||
|
* @param opts - (Optional) Options used to sign and submit a transaction.
|
||||||
|
* @param opts.binary - If true, return the metadata in a binary encoding.
|
||||||
|
*
|
||||||
|
* @returns A promise that contains SimulateResponse.
|
||||||
|
* @throws RippledError if the simulate request fails.
|
||||||
|
*/
|
||||||
|
|
||||||
|
public async simulate<Binary extends boolean = false>(
|
||||||
|
transaction: SubmittableTransaction | string,
|
||||||
|
opts?: {
|
||||||
|
// If true, return the binary-encoded representation of the results.
|
||||||
|
binary?: Binary
|
||||||
|
},
|
||||||
|
): Promise<
|
||||||
|
Binary extends true ? SimulateBinaryResponse : SimulateJsonResponse
|
||||||
|
> {
|
||||||
|
// send request
|
||||||
|
const binary = opts?.binary ?? false
|
||||||
|
const request: SimulateRequest =
|
||||||
|
typeof transaction === 'string'
|
||||||
|
? { command: 'simulate', tx_blob: transaction, binary }
|
||||||
|
: { command: 'simulate', tx_json: transaction, binary }
|
||||||
|
return this.request(request)
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Asynchronously submits a transaction and verifies that it has been included in a
|
* Asynchronously submits a transaction and verifies that it has been included in a
|
||||||
* validated ledger (or has errored/will not be included for some reason).
|
* validated ledger (or has errored/will not be included for some reason).
|
||||||
@@ -898,7 +995,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
* @param options.limit - Limit number of balances to return.
|
* @param options.limit - Limit number of balances to return.
|
||||||
* @returns An array of XRP/non-XRP balances for the given account.
|
* @returns An array of XRP/non-XRP balances for the given account.
|
||||||
*/
|
*/
|
||||||
// eslint-disable-next-line max-lines-per-function -- Longer definition is required for end users to see the definition.
|
/* eslint-disable max-lines-per-function -- getBalances requires more lines to implement logic */
|
||||||
public async getBalances(
|
public async getBalances(
|
||||||
address: string,
|
address: string,
|
||||||
options: {
|
options: {
|
||||||
@@ -946,6 +1043,7 @@ class Client extends EventEmitter<EventTypes> {
|
|||||||
)
|
)
|
||||||
return balances.slice(0, options.limit)
|
return balances.slice(0, options.limit)
|
||||||
}
|
}
|
||||||
|
/* eslint-enable max-lines-per-function */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fetch orderbook (buy/sell orders) between two currency pairs. This checks both sides of the orderbook
|
* Fetch orderbook (buy/sell orders) between two currency pairs. This checks both sides of the orderbook
|
||||||
|
|||||||
@@ -2,21 +2,37 @@ import BigNumber from 'bignumber.js'
|
|||||||
import { decode } from 'ripple-binary-codec'
|
import { decode } from 'ripple-binary-codec'
|
||||||
|
|
||||||
import type {
|
import type {
|
||||||
AccountTxResponse,
|
|
||||||
TransactionEntryResponse,
|
TransactionEntryResponse,
|
||||||
TransactionStream,
|
TransactionStream,
|
||||||
|
TransactionV1Stream,
|
||||||
TxResponse,
|
TxResponse,
|
||||||
} from '..'
|
} from '..'
|
||||||
import type { Amount } from '../models/common'
|
import type {
|
||||||
import type { RequestResponseMap } from '../models/methods'
|
Amount,
|
||||||
|
IssuedCurrency,
|
||||||
|
APIVersion,
|
||||||
|
DEFAULT_API_VERSION,
|
||||||
|
MPTAmount,
|
||||||
|
} from '../models/common'
|
||||||
|
import type {
|
||||||
|
AccountTxTransaction,
|
||||||
|
RequestResponseMap,
|
||||||
|
} from '../models/methods'
|
||||||
|
import { AccountTxVersionResponseMap } from '../models/methods/accountTx'
|
||||||
import { BaseRequest, BaseResponse } from '../models/methods/baseMethod'
|
import { BaseRequest, BaseResponse } from '../models/methods/baseMethod'
|
||||||
import { PaymentFlags, Transaction } from '../models/transactions'
|
import { PaymentFlags, Transaction, isMPTAmount } from '../models/transactions'
|
||||||
import type { TransactionMetadata } from '../models/transactions/metadata'
|
import type { TransactionMetadata } from '../models/transactions/metadata'
|
||||||
import { isFlagEnabled } from '../models/utils'
|
import { isFlagEnabled } from '../models/utils'
|
||||||
|
|
||||||
const WARN_PARTIAL_PAYMENT_CODE = 2001
|
const WARN_PARTIAL_PAYMENT_CODE = 2001
|
||||||
|
|
||||||
function amountsEqual(amt1: Amount, amt2: Amount): boolean {
|
/* eslint-disable complexity -- check different token types */
|
||||||
|
/* eslint-disable @typescript-eslint/consistent-type-assertions -- known currency type */
|
||||||
|
function amountsEqual(
|
||||||
|
amt1: Amount | MPTAmount,
|
||||||
|
amt2: Amount | MPTAmount,
|
||||||
|
): boolean {
|
||||||
|
// Compare XRP
|
||||||
if (typeof amt1 === 'string' && typeof amt2 === 'string') {
|
if (typeof amt1 === 'string' && typeof amt2 === 'string') {
|
||||||
return amt1 === amt2
|
return amt1 === amt2
|
||||||
}
|
}
|
||||||
@@ -25,15 +41,32 @@ function amountsEqual(amt1: Amount, amt2: Amount): boolean {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Compare MPTs
|
||||||
|
if (isMPTAmount(amt1) && isMPTAmount(amt2)) {
|
||||||
|
const aValue = new BigNumber(amt1.value)
|
||||||
|
const bValue = new BigNumber(amt2.value)
|
||||||
|
|
||||||
|
return (
|
||||||
|
amt1.mpt_issuance_id === amt2.mpt_issuance_id && aValue.isEqualTo(bValue)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isMPTAmount(amt1) || isMPTAmount(amt2)) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// Compare issued currency (IOU)
|
||||||
const aValue = new BigNumber(amt1.value)
|
const aValue = new BigNumber(amt1.value)
|
||||||
const bValue = new BigNumber(amt2.value)
|
const bValue = new BigNumber(amt2.value)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
amt1.currency === amt2.currency &&
|
(amt1 as IssuedCurrency).currency === (amt2 as IssuedCurrency).currency &&
|
||||||
amt1.issuer === amt2.issuer &&
|
(amt1 as IssuedCurrency).issuer === (amt2 as IssuedCurrency).issuer &&
|
||||||
aValue.isEqualTo(bValue)
|
aValue.isEqualTo(bValue)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
/* eslint-enable complexity */
|
||||||
|
/* eslint-enable @typescript-eslint/consistent-type-assertions */
|
||||||
|
|
||||||
function isPartialPayment(
|
function isPartialPayment(
|
||||||
tx?: Transaction,
|
tx?: Transaction,
|
||||||
@@ -63,7 +96,10 @@ function isPartialPayment(
|
|||||||
}
|
}
|
||||||
|
|
||||||
const delivered = meta.delivered_amount
|
const delivered = meta.delivered_amount
|
||||||
const amount = tx.Amount
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment -- DeliverMax is a valid field on Payment response
|
||||||
|
// @ts-expect-error -- DeliverMax is a valid field on Payment response
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unsafe-assignment -- DeliverMax is a valid field on Payment response
|
||||||
|
const amount = tx.DeliverMax
|
||||||
|
|
||||||
if (delivered === undefined) {
|
if (delivered === undefined) {
|
||||||
return false
|
return false
|
||||||
@@ -73,23 +109,36 @@ function isPartialPayment(
|
|||||||
}
|
}
|
||||||
|
|
||||||
function txHasPartialPayment(response: TxResponse): boolean {
|
function txHasPartialPayment(response: TxResponse): boolean {
|
||||||
return isPartialPayment(response.result, response.result.meta)
|
return isPartialPayment(response.result.tx_json, response.result.meta)
|
||||||
}
|
}
|
||||||
|
|
||||||
function txEntryHasPartialPayment(response: TransactionEntryResponse): boolean {
|
function txEntryHasPartialPayment(response: TransactionEntryResponse): boolean {
|
||||||
return isPartialPayment(response.result.tx_json, response.result.metadata)
|
return isPartialPayment(response.result.tx_json, response.result.metadata)
|
||||||
}
|
}
|
||||||
|
|
||||||
function accountTxHasPartialPayment(response: AccountTxResponse): boolean {
|
function accountTxHasPartialPayment<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
>(response: AccountTxVersionResponseMap<Version>): boolean {
|
||||||
const { transactions } = response.result
|
const { transactions } = response.result
|
||||||
const foo = transactions.some((tx) => isPartialPayment(tx.tx, tx.meta))
|
const foo = transactions.some((tx) => {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access -- required to check API version model
|
||||||
|
if (tx.tx_json != null) {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- use API v2 model
|
||||||
|
const transaction = tx as AccountTxTransaction
|
||||||
|
return isPartialPayment(transaction.tx_json, transaction.meta)
|
||||||
|
}
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- use API v1 model
|
||||||
|
const transaction = tx as AccountTxTransaction<1>
|
||||||
|
return isPartialPayment(transaction.tx, transaction.meta)
|
||||||
|
})
|
||||||
return foo
|
return foo
|
||||||
}
|
}
|
||||||
|
|
||||||
function hasPartialPayment<R extends BaseRequest, T = RequestResponseMap<R>>(
|
function hasPartialPayment<
|
||||||
command: string,
|
R extends BaseRequest,
|
||||||
response: T,
|
V extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
): boolean {
|
T = RequestResponseMap<R, V>,
|
||||||
|
>(command: string, response: T): boolean {
|
||||||
/* eslint-disable @typescript-eslint/consistent-type-assertions -- Request type is known at runtime from command */
|
/* eslint-disable @typescript-eslint/consistent-type-assertions -- Request type is known at runtime from command */
|
||||||
switch (command) {
|
switch (command) {
|
||||||
case 'tx':
|
case 'tx':
|
||||||
@@ -97,7 +146,9 @@ function hasPartialPayment<R extends BaseRequest, T = RequestResponseMap<R>>(
|
|||||||
case 'transaction_entry':
|
case 'transaction_entry':
|
||||||
return txEntryHasPartialPayment(response as TransactionEntryResponse)
|
return txEntryHasPartialPayment(response as TransactionEntryResponse)
|
||||||
case 'account_tx':
|
case 'account_tx':
|
||||||
return accountTxHasPartialPayment(response as AccountTxResponse)
|
return accountTxHasPartialPayment(
|
||||||
|
response as AccountTxVersionResponseMap<V>,
|
||||||
|
)
|
||||||
default:
|
default:
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
@@ -112,7 +163,7 @@ function hasPartialPayment<R extends BaseRequest, T = RequestResponseMap<R>>(
|
|||||||
*/
|
*/
|
||||||
export function handlePartialPayment<
|
export function handlePartialPayment<
|
||||||
R extends BaseRequest,
|
R extends BaseRequest,
|
||||||
T = RequestResponseMap<R>,
|
T = RequestResponseMap<R, APIVersion>,
|
||||||
>(command: string, response: T): void {
|
>(command: string, response: T): void {
|
||||||
if (hasPartialPayment(command, response)) {
|
if (hasPartialPayment(command, response)) {
|
||||||
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- We are checking dynamically and safely.
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- We are checking dynamically and safely.
|
||||||
@@ -138,10 +189,10 @@ export function handlePartialPayment<
|
|||||||
* @param log - The method used for logging by the connection (to report the partial payment).
|
* @param log - The method used for logging by the connection (to report the partial payment).
|
||||||
*/
|
*/
|
||||||
export function handleStreamPartialPayment(
|
export function handleStreamPartialPayment(
|
||||||
stream: TransactionStream,
|
stream: TransactionStream | TransactionV1Stream,
|
||||||
log: (id: string, message: string) => void,
|
log: (id: string, message: string) => void,
|
||||||
): void {
|
): void {
|
||||||
if (isPartialPayment(stream.transaction, stream.meta)) {
|
if (isPartialPayment(stream.tx_json ?? stream.transaction, stream.meta)) {
|
||||||
const warnings = stream.warnings ?? []
|
const warnings = stream.warnings ?? []
|
||||||
|
|
||||||
const warning = {
|
const warning = {
|
||||||
|
|||||||
@@ -1,3 +1,7 @@
|
|||||||
|
export const RIPPLED_API_V1 = 1
|
||||||
|
export const RIPPLED_API_V2 = 2
|
||||||
|
export const DEFAULT_API_VERSION = RIPPLED_API_V2
|
||||||
|
export type APIVersion = typeof RIPPLED_API_V1 | typeof RIPPLED_API_V2
|
||||||
export type LedgerIndex = number | ('validated' | 'closed' | 'current')
|
export type LedgerIndex = number | ('validated' | 'closed' | 'current')
|
||||||
|
|
||||||
export interface XRP {
|
export interface XRP {
|
||||||
@@ -16,6 +20,11 @@ export interface IssuedCurrencyAmount extends IssuedCurrency {
|
|||||||
value: string
|
value: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface MPTAmount {
|
||||||
|
mpt_issuance_id: string
|
||||||
|
value: string
|
||||||
|
}
|
||||||
|
|
||||||
export type Amount = IssuedCurrencyAmount | string
|
export type Amount = IssuedCurrencyAmount | string
|
||||||
|
|
||||||
export interface Balance {
|
export interface Balance {
|
||||||
@@ -104,6 +113,10 @@ export interface ResponseOnlyTxInfo {
|
|||||||
* The sequence number of the ledger that included this transaction.
|
* The sequence number of the ledger that included this transaction.
|
||||||
*/
|
*/
|
||||||
ledger_index?: number
|
ledger_index?: number
|
||||||
|
/**
|
||||||
|
* The hash of the ledger included this transaction.
|
||||||
|
*/
|
||||||
|
ledger_hash?: string
|
||||||
/**
|
/**
|
||||||
* @deprecated Alias for ledger_index.
|
* @deprecated Alias for ledger_index.
|
||||||
*/
|
*/
|
||||||
@@ -149,9 +162,52 @@ export interface AuthAccount {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface AuthorizeCredential {
|
||||||
|
Credential: {
|
||||||
|
/** The issuer of the credential. */
|
||||||
|
Issuer: string
|
||||||
|
|
||||||
|
/** A hex-encoded value to identify the type of credential from the issuer. */
|
||||||
|
CredentialType: string
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
export interface XChainBridge {
|
export interface XChainBridge {
|
||||||
LockingChainDoor: string
|
LockingChainDoor: string
|
||||||
LockingChainIssue: Currency
|
LockingChainIssue: Currency
|
||||||
IssuingChainDoor: string
|
IssuingChainDoor: string
|
||||||
IssuingChainIssue: Currency
|
IssuingChainIssue: Currency
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A PriceData object represents the price information for a token pair.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
export interface PriceData {
|
||||||
|
PriceData: {
|
||||||
|
/**
|
||||||
|
* The primary asset in a trading pair. Any valid identifier, such as a stock symbol, bond CUSIP, or currency code is allowed.
|
||||||
|
* For example, in the BTC/USD pair, BTC is the base asset; in 912810RR9/BTC, 912810RR9 is the base asset.
|
||||||
|
*/
|
||||||
|
BaseAsset: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The quote asset in a trading pair. The quote asset denotes the price of one unit of the base asset. For example, in the
|
||||||
|
* BTC/USD pair,BTC is the base asset; in 912810RR9/BTC, 912810RR9 is the base asset.
|
||||||
|
*/
|
||||||
|
QuoteAsset: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The asset price after applying the Scale precision level. It's not included if the last update transaction didn't include
|
||||||
|
* the BaseAsset/QuoteAsset pair.
|
||||||
|
*/
|
||||||
|
AssetPrice?: number | string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The scaling factor to apply to an asset price. For example, if Scale is 6 and original price is 0.155, then the scaled
|
||||||
|
* price is 155000. Valid scale ranges are 0-10. It's not included if the last update transaction didn't include the
|
||||||
|
* BaseAsset/QuoteAsset pair.
|
||||||
|
*/
|
||||||
|
Scale?: number
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -8,8 +8,10 @@
|
|||||||
*/
|
*/
|
||||||
export * as LedgerEntry from './ledger'
|
export * as LedgerEntry from './ledger'
|
||||||
export {
|
export {
|
||||||
setTransactionFlagsToNumber,
|
|
||||||
parseAccountRootFlags,
|
parseAccountRootFlags,
|
||||||
|
setTransactionFlagsToNumber,
|
||||||
|
convertTxFlagsToNumber,
|
||||||
|
parseTransactionFlags,
|
||||||
} from './utils/flags'
|
} from './utils/flags'
|
||||||
export * from './methods'
|
export * from './methods'
|
||||||
export * from './transactions'
|
export * from './transactions'
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { AuthAccount, Currency, IssuedCurrencyAmount } from '../common'
|
import { AuthAccount, Currency, IssuedCurrencyAmount } from '../common'
|
||||||
|
|
||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasOptionalPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
export interface VoteSlot {
|
export interface VoteSlot {
|
||||||
VoteEntry: {
|
VoteEntry: {
|
||||||
@@ -15,7 +15,7 @@ export interface VoteSlot {
|
|||||||
*
|
*
|
||||||
* @category Ledger Entries
|
* @category Ledger Entries
|
||||||
*/
|
*/
|
||||||
export default interface AMM extends BaseLedgerEntry, MissingPreviousTxnID {
|
export default interface AMM extends BaseLedgerEntry, HasOptionalPreviousTxnID {
|
||||||
LedgerEntryType: 'AMM'
|
LedgerEntryType: 'AMM'
|
||||||
/**
|
/**
|
||||||
* The address of the special account that holds this AMM's assets.
|
* The address of the special account that holds this AMM's assets.
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasOptionalPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The unique id for the Amendments object https://xrpl.org/amendments-object.html#amendments-id-format
|
* The unique id for the Amendments object https://xrpl.org/amendments-object.html#amendments-id-format
|
||||||
@@ -26,7 +26,7 @@ export interface Majority {
|
|||||||
*/
|
*/
|
||||||
export default interface Amendments
|
export default interface Amendments
|
||||||
extends BaseLedgerEntry,
|
extends BaseLedgerEntry,
|
||||||
MissingPreviousTxnID {
|
HasOptionalPreviousTxnID {
|
||||||
LedgerEntryType: 'Amendments'
|
LedgerEntryType: 'Amendments'
|
||||||
/**
|
/**
|
||||||
* Array of 256-bit amendment IDs for all currently-enabled amendments. If
|
* Array of 256-bit amendment IDs for all currently-enabled amendments. If
|
||||||
|
|||||||
@@ -15,13 +15,17 @@ export interface HasPreviousTxnID {
|
|||||||
PreviousTxnLgrSeq: number
|
PreviousTxnLgrSeq: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface MissingPreviousTxnID {
|
export interface HasOptionalPreviousTxnID {
|
||||||
/**
|
/**
|
||||||
* This field is missing on this object but is present on most other returned objects.
|
* The identifying hash of the transaction that most recently modified this
|
||||||
|
* object. This field was added in the `fixPreviousTxnID` amendment, so it
|
||||||
|
* may not be present in every object.
|
||||||
*/
|
*/
|
||||||
PreviousTxnID: never
|
PreviousTxnID?: string
|
||||||
/**
|
/**
|
||||||
* This field is missing on this object but is present on most other returned objects.
|
* The index of the ledger that contains the transaction that most recently
|
||||||
|
* modified this object. This field was added in the `fixPreviousTxnID`
|
||||||
|
* amendment, so it may not be present in every object.
|
||||||
*/
|
*/
|
||||||
PreviousTxnLgrSeq: never
|
PreviousTxnLgrSeq?: number
|
||||||
}
|
}
|
||||||
|
|||||||
47
packages/xrpl/src/models/ledger/Credential.ts
Normal file
47
packages/xrpl/src/models/ledger/Credential.ts
Normal file
@@ -0,0 +1,47 @@
|
|||||||
|
import { GlobalFlags } from '../transactions/common'
|
||||||
|
|
||||||
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
|
export interface CredentialFlags extends GlobalFlags {
|
||||||
|
lsfAccepted?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* A Credential object describes a credential, similar to a passport, which is an issuable identity verifier
|
||||||
|
* that can be used as a prerequisite for other transactions
|
||||||
|
*
|
||||||
|
* @category Ledger Entries
|
||||||
|
*/
|
||||||
|
export default interface Credential extends BaseLedgerEntry, HasPreviousTxnID {
|
||||||
|
LedgerEntryType: 'Credential'
|
||||||
|
/**
|
||||||
|
* A bit-map of boolean flags
|
||||||
|
*/
|
||||||
|
Flags: number | CredentialFlags
|
||||||
|
|
||||||
|
/** The account that the credential is for. */
|
||||||
|
Subject: string
|
||||||
|
|
||||||
|
/** The issuer of the credential. */
|
||||||
|
Issuer: string
|
||||||
|
|
||||||
|
/** A hex-encoded value to identify the type of credential from the issuer. */
|
||||||
|
CredentialType: string
|
||||||
|
|
||||||
|
/** A hint indicating which page of the subject's owner directory links to this object,
|
||||||
|
* in case the directory consists of multiple pages.
|
||||||
|
*/
|
||||||
|
SubjectNode: string
|
||||||
|
|
||||||
|
/** A hint indicating which page of the issuer's owner directory links to this object,
|
||||||
|
* in case the directory consists of multiple pages.
|
||||||
|
*/
|
||||||
|
IssuerNode: string
|
||||||
|
|
||||||
|
/** Credential expiration. */
|
||||||
|
Expiration?: number
|
||||||
|
|
||||||
|
/** Additional data about the credential (such as a link to the VC document). */
|
||||||
|
URI?: string
|
||||||
|
}
|
||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { AuthorizeCredential } from '../common'
|
||||||
|
|
||||||
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -12,8 +14,6 @@ export default interface DepositPreauth
|
|||||||
LedgerEntryType: 'DepositPreauth'
|
LedgerEntryType: 'DepositPreauth'
|
||||||
/** The account that granted the preauthorization. */
|
/** The account that granted the preauthorization. */
|
||||||
Account: string
|
Account: string
|
||||||
/** The account that received the preauthorization. */
|
|
||||||
Authorize: string
|
|
||||||
/**
|
/**
|
||||||
* A bit-map of boolean flags. No flags are defined for DepositPreauth
|
* A bit-map of boolean flags. No flags are defined for DepositPreauth
|
||||||
* objects, so this value is always 0.
|
* objects, so this value is always 0.
|
||||||
@@ -24,4 +24,8 @@ export default interface DepositPreauth
|
|||||||
* object, in case the directory consists of multiple pages.
|
* object, in case the directory consists of multiple pages.
|
||||||
*/
|
*/
|
||||||
OwnerNode: string
|
OwnerNode: string
|
||||||
|
/** The account that received the preauthorization. */
|
||||||
|
Authorize?: string
|
||||||
|
/** The credential(s) that received the preauthorization. */
|
||||||
|
AuthorizeCredentials?: AuthorizeCredential[]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasOptionalPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The DirectoryNode object type provides a list of links to other objects in
|
* The DirectoryNode object type provides a list of links to other objects in
|
||||||
@@ -8,7 +8,7 @@ import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
|||||||
*/
|
*/
|
||||||
export default interface DirectoryNode
|
export default interface DirectoryNode
|
||||||
extends BaseLedgerEntry,
|
extends BaseLedgerEntry,
|
||||||
MissingPreviousTxnID {
|
HasOptionalPreviousTxnID {
|
||||||
LedgerEntryType: 'DirectoryNode'
|
LedgerEntryType: 'DirectoryNode'
|
||||||
/**
|
/**
|
||||||
* A bit-map of boolean flags enabled for this directory. Currently, the
|
* A bit-map of boolean flags enabled for this directory. Currently, the
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasOptionalPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The unique id for the FeeSettings object https://xrpl.org/feesettings.html#feesettings-id-format
|
* The unique id for the FeeSettings object https://xrpl.org/feesettings.html#feesettings-id-format
|
||||||
@@ -26,7 +26,9 @@ export interface FeeSettingsPostAmendmentFields {
|
|||||||
ReserveIncrementDrops: string
|
ReserveIncrementDrops: string
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface FeeSettingsBase extends BaseLedgerEntry, MissingPreviousTxnID {
|
export interface FeeSettingsBase
|
||||||
|
extends BaseLedgerEntry,
|
||||||
|
HasOptionalPreviousTxnID {
|
||||||
LedgerEntryType: 'FeeSettings'
|
LedgerEntryType: 'FeeSettings'
|
||||||
/**
|
/**
|
||||||
* A bit-map of boolean flags for this object. No flags are defined for this type.
|
* A bit-map of boolean flags for this object. No flags are defined for this type.
|
||||||
|
|||||||
@@ -1,14 +1,14 @@
|
|||||||
|
import { APIVersion, DEFAULT_API_VERSION, RIPPLED_API_V1 } from '../common'
|
||||||
import { Transaction, TransactionMetadata } from '../transactions'
|
import { Transaction, TransactionMetadata } from '../transactions'
|
||||||
|
|
||||||
import { LedgerEntry } from './LedgerEntry'
|
import { LedgerEntry } from './LedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A ledger is a block of transactions and shared state data. It has a unique
|
* Common properties for ledger entries.
|
||||||
* header that describes its contents using cryptographic hashes.
|
|
||||||
*
|
*
|
||||||
* @category Ledger Entries
|
* @category Ledger Entries
|
||||||
*/
|
*/
|
||||||
export default interface Ledger {
|
interface BaseLedger {
|
||||||
/** The SHA-512Half of this ledger's state tree information. */
|
/** The SHA-512Half of this ledger's state tree information. */
|
||||||
account_hash: string
|
account_hash: string
|
||||||
/** All the state information in this ledger. Admin only. */
|
/** All the state information in this ledger. Admin only. */
|
||||||
@@ -31,6 +31,11 @@ export default interface Ledger {
|
|||||||
* by which the close_time could be rounded.
|
* by which the close_time could be rounded.
|
||||||
*/
|
*/
|
||||||
close_time_resolution: number
|
close_time_resolution: number
|
||||||
|
/**
|
||||||
|
* The approximate time this ledger was closed, in date time string format.
|
||||||
|
* Always uses the UTC time zone.
|
||||||
|
*/
|
||||||
|
close_time_iso: string
|
||||||
/** Whether or not this ledger has been closed. */
|
/** Whether or not this ledger has been closed. */
|
||||||
closed: boolean
|
closed: boolean
|
||||||
/**
|
/**
|
||||||
@@ -38,11 +43,6 @@ export default interface Ledger {
|
|||||||
* for this ledger and all its contents.
|
* for this ledger and all its contents.
|
||||||
*/
|
*/
|
||||||
ledger_hash: string
|
ledger_hash: string
|
||||||
/**
|
|
||||||
* The ledger index of the ledger. Some API methods display this as a quoted
|
|
||||||
* integer; some display it as a native JSON number.
|
|
||||||
*/
|
|
||||||
ledger_index: string
|
|
||||||
/** The approximate time at which the previous ledger was closed. */
|
/** The approximate time at which the previous ledger was closed. */
|
||||||
parent_close_time: number
|
parent_close_time: number
|
||||||
/**
|
/**
|
||||||
@@ -61,5 +61,47 @@ export default interface Ledger {
|
|||||||
* either JSON or binary depending on whether the request specified binary
|
* either JSON or binary depending on whether the request specified binary
|
||||||
* as true.
|
* as true.
|
||||||
*/
|
*/
|
||||||
transactions?: Array<Transaction & { metaData?: TransactionMetadata }>
|
transactions?: Array<
|
||||||
|
Transaction & {
|
||||||
|
hash: string
|
||||||
|
metaData?: TransactionMetadata
|
||||||
|
}
|
||||||
|
>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A ledger is a block of transactions and shared state data. It has a unique
|
||||||
|
* header that describes its contents using cryptographic hashes.
|
||||||
|
*
|
||||||
|
* @category Ledger Entries
|
||||||
|
*/
|
||||||
|
export interface Ledger extends BaseLedger {
|
||||||
|
/**
|
||||||
|
* The ledger index of the ledger. Represented as a number.
|
||||||
|
*/
|
||||||
|
ledger_index: number
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A ledger is a block of transactions and shared state data. It has a unique
|
||||||
|
* header that describes its contents using cryptographic hashes. This is used
|
||||||
|
* in api_version 1.
|
||||||
|
*
|
||||||
|
* @category Ledger Entries
|
||||||
|
*/
|
||||||
|
export interface LedgerV1 extends BaseLedger {
|
||||||
|
/**
|
||||||
|
* The ledger index of the ledger. Some API methods display this as a quoted
|
||||||
|
* integer; some display it as a number.
|
||||||
|
*/
|
||||||
|
ledger_index: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the Ledger type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type LedgerVersionMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1 ? LedgerV1 : Ledger
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import Amendments from './Amendments'
|
|||||||
import AMM from './AMM'
|
import AMM from './AMM'
|
||||||
import Bridge from './Bridge'
|
import Bridge from './Bridge'
|
||||||
import Check from './Check'
|
import Check from './Check'
|
||||||
|
import Credential from './Credential'
|
||||||
import DepositPreauth from './DepositPreauth'
|
import DepositPreauth from './DepositPreauth'
|
||||||
import DirectoryNode from './DirectoryNode'
|
import DirectoryNode from './DirectoryNode'
|
||||||
import Escrow from './Escrow'
|
import Escrow from './Escrow'
|
||||||
@@ -10,7 +11,9 @@ import FeeSettings from './FeeSettings'
|
|||||||
import LedgerHashes from './LedgerHashes'
|
import LedgerHashes from './LedgerHashes'
|
||||||
import NegativeUNL from './NegativeUNL'
|
import NegativeUNL from './NegativeUNL'
|
||||||
import Offer from './Offer'
|
import Offer from './Offer'
|
||||||
|
import Oracle from './Oracle'
|
||||||
import PayChannel from './PayChannel'
|
import PayChannel from './PayChannel'
|
||||||
|
import PermissionedDomain from './PermissionedDomain'
|
||||||
import RippleState from './RippleState'
|
import RippleState from './RippleState'
|
||||||
import SignerList from './SignerList'
|
import SignerList from './SignerList'
|
||||||
import Ticket from './Ticket'
|
import Ticket from './Ticket'
|
||||||
@@ -23,6 +26,7 @@ type LedgerEntry =
|
|||||||
| AMM
|
| AMM
|
||||||
| Bridge
|
| Bridge
|
||||||
| Check
|
| Check
|
||||||
|
| Credential
|
||||||
| DepositPreauth
|
| DepositPreauth
|
||||||
| DirectoryNode
|
| DirectoryNode
|
||||||
| Escrow
|
| Escrow
|
||||||
@@ -30,7 +34,9 @@ type LedgerEntry =
|
|||||||
| LedgerHashes
|
| LedgerHashes
|
||||||
| NegativeUNL
|
| NegativeUNL
|
||||||
| Offer
|
| Offer
|
||||||
|
| Oracle
|
||||||
| PayChannel
|
| PayChannel
|
||||||
|
| PermissionedDomain
|
||||||
| RippleState
|
| RippleState
|
||||||
| SignerList
|
| SignerList
|
||||||
| Ticket
|
| Ticket
|
||||||
@@ -43,16 +49,21 @@ type LedgerEntryFilter =
|
|||||||
| 'amm'
|
| 'amm'
|
||||||
| 'bridge'
|
| 'bridge'
|
||||||
| 'check'
|
| 'check'
|
||||||
|
| 'credential'
|
||||||
| 'deposit_preauth'
|
| 'deposit_preauth'
|
||||||
| 'did'
|
| 'did'
|
||||||
| 'directory'
|
| 'directory'
|
||||||
| 'escrow'
|
| 'escrow'
|
||||||
| 'fee'
|
| 'fee'
|
||||||
| 'hashes'
|
| 'hashes'
|
||||||
|
| 'mpt_issuance'
|
||||||
|
| 'mptoken'
|
||||||
| 'nft_offer'
|
| 'nft_offer'
|
||||||
| 'nft_page'
|
| 'nft_page'
|
||||||
| 'offer'
|
| 'offer'
|
||||||
|
| 'oracle'
|
||||||
| 'payment_channel'
|
| 'payment_channel'
|
||||||
|
| 'permissioned_domain'
|
||||||
| 'signer_list'
|
| 'signer_list'
|
||||||
| 'state'
|
| 'state'
|
||||||
| 'ticket'
|
| 'ticket'
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The LedgerHashes objects exist to make it possible to look up a previous
|
* The LedgerHashes objects exist to make it possible to look up a previous
|
||||||
@@ -7,9 +7,7 @@ import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
|||||||
*
|
*
|
||||||
* @category Ledger Entries
|
* @category Ledger Entries
|
||||||
*/
|
*/
|
||||||
export default interface LedgerHashes
|
export default interface LedgerHashes extends BaseLedgerEntry {
|
||||||
extends BaseLedgerEntry,
|
|
||||||
MissingPreviousTxnID {
|
|
||||||
LedgerEntryType: 'LedgerHashes'
|
LedgerEntryType: 'LedgerHashes'
|
||||||
/** The Ledger Index of the last entry in this object's Hashes array. */
|
/** The Ledger Index of the last entry in this object's Hashes array. */
|
||||||
LastLedgerSequence?: number
|
LastLedgerSequence?: number
|
||||||
|
|||||||
11
packages/xrpl/src/models/ledger/MPToken.ts
Normal file
11
packages/xrpl/src/models/ledger/MPToken.ts
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
import { MPTAmount } from '../common'
|
||||||
|
|
||||||
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
|
export interface MPToken extends BaseLedgerEntry, HasPreviousTxnID {
|
||||||
|
LedgerEntryType: 'MPToken'
|
||||||
|
MPTokenIssuanceID: string
|
||||||
|
MPTAmount?: MPTAmount
|
||||||
|
Flags: number
|
||||||
|
OwnerNode?: string
|
||||||
|
}
|
||||||
13
packages/xrpl/src/models/ledger/MPTokenIssuance.ts
Normal file
13
packages/xrpl/src/models/ledger/MPTokenIssuance.ts
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
|
export interface MPTokenIssuance extends BaseLedgerEntry, HasPreviousTxnID {
|
||||||
|
LedgerEntryType: 'MPTokenIssuance'
|
||||||
|
Flags: number
|
||||||
|
Issuer: string
|
||||||
|
AssetScale?: number
|
||||||
|
MaximumAmount?: string
|
||||||
|
OutstandingAmount: string
|
||||||
|
TransferFee?: number
|
||||||
|
MPTokenMetadata?: string
|
||||||
|
OwnerNode?: string
|
||||||
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { BaseLedgerEntry, MissingPreviousTxnID } from './BaseLedgerEntry'
|
import { BaseLedgerEntry, HasOptionalPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The unique id for the nUNL object https://xrpl.org/negativeunl.html#negativeunl-id-format
|
* The unique id for the nUNL object https://xrpl.org/negativeunl.html#negativeunl-id-format
|
||||||
@@ -14,7 +14,7 @@ export const NEGATIVE_UNL_ID =
|
|||||||
*/
|
*/
|
||||||
export default interface NegativeUNL
|
export default interface NegativeUNL
|
||||||
extends BaseLedgerEntry,
|
extends BaseLedgerEntry,
|
||||||
MissingPreviousTxnID {
|
HasOptionalPreviousTxnID {
|
||||||
LedgerEntryType: 'NegativeUNL'
|
LedgerEntryType: 'NegativeUNL'
|
||||||
/**
|
/**
|
||||||
* A list of trusted validators that are currently disabled.
|
* A list of trusted validators that are currently disabled.
|
||||||
|
|||||||
43
packages/xrpl/src/models/ledger/Oracle.ts
Normal file
43
packages/xrpl/src/models/ledger/Oracle.ts
Normal file
@@ -0,0 +1,43 @@
|
|||||||
|
import { PriceData } from '../common'
|
||||||
|
|
||||||
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The Oracle object type describes a single Price Oracle instance.
|
||||||
|
*
|
||||||
|
* @category Ledger Entries
|
||||||
|
*/
|
||||||
|
export default interface Oracle extends BaseLedgerEntry, HasPreviousTxnID {
|
||||||
|
LedgerEntryType: 'Oracle'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The time the data was last updated, represented as a unix timestamp in seconds.
|
||||||
|
*/
|
||||||
|
LastUpdateTime: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The XRPL account with update and delete privileges for the oracle.
|
||||||
|
*/
|
||||||
|
Owner: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Describes the type of asset, such as "currency", "commodity", or "index".
|
||||||
|
*/
|
||||||
|
AssetClass: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The oracle provider, such as Chainlink, Band, or DIA.
|
||||||
|
*/
|
||||||
|
Provider: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An array of up to 10 PriceData objects.
|
||||||
|
*/
|
||||||
|
PriceDataSeries: PriceData[]
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A bit-map of boolean flags. No flags are defined for the Oracle object
|
||||||
|
* type, so this value is always 0.
|
||||||
|
*/
|
||||||
|
Flags: 0
|
||||||
|
}
|
||||||
29
packages/xrpl/src/models/ledger/PermissionedDomain.ts
Normal file
29
packages/xrpl/src/models/ledger/PermissionedDomain.ts
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
import { AuthorizeCredential } from '../common'
|
||||||
|
|
||||||
|
import { BaseLedgerEntry, HasPreviousTxnID } from './BaseLedgerEntry'
|
||||||
|
|
||||||
|
export default interface PermissionedDomain
|
||||||
|
extends BaseLedgerEntry,
|
||||||
|
HasPreviousTxnID {
|
||||||
|
/* The ledger object's type (PermissionedDomain). */
|
||||||
|
LedgerEntryType: 'PermissionedDomain'
|
||||||
|
|
||||||
|
/* The account that controls the settings of the domain. */
|
||||||
|
Owner: string
|
||||||
|
|
||||||
|
/* The credentials that are accepted by the domain.
|
||||||
|
Ownership of one of these credentials automatically
|
||||||
|
makes you a member of the domain. */
|
||||||
|
AcceptedCredentials: AuthorizeCredential[]
|
||||||
|
|
||||||
|
/* Flag values associated with this object. */
|
||||||
|
Flags: 0
|
||||||
|
|
||||||
|
/* Owner account's directory page containing the PermissionedDomain object. */
|
||||||
|
OwnerNode: string
|
||||||
|
|
||||||
|
/* The Sequence value of the PermissionedDomainSet
|
||||||
|
transaction that created this domain. Used in combination
|
||||||
|
with the Account to identify this domain. */
|
||||||
|
Sequence: number
|
||||||
|
}
|
||||||
@@ -75,4 +75,10 @@ export enum RippleStateFlags {
|
|||||||
lsfLowFreeze = 0x00400000,
|
lsfLowFreeze = 0x00400000,
|
||||||
// True, high side has set freeze flag
|
// True, high side has set freeze flag
|
||||||
lsfHighFreeze = 0x00800000,
|
lsfHighFreeze = 0x00800000,
|
||||||
|
// True, trust line to AMM. Used by client apps to identify payments via AMM.
|
||||||
|
lsfAMMNode = 0x01000000,
|
||||||
|
// True, low side has set deep freeze flag
|
||||||
|
lsfLowDeepFreeze = 0x02000000,
|
||||||
|
// True, high side has set deep freeze flag
|
||||||
|
lsfHighDeepFreeze = 0x04000000,
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import Amendments, { Majority, AMENDMENTS_ID } from './Amendments'
|
|||||||
import AMM, { VoteSlot } from './AMM'
|
import AMM, { VoteSlot } from './AMM'
|
||||||
import Bridge from './Bridge'
|
import Bridge from './Bridge'
|
||||||
import Check from './Check'
|
import Check from './Check'
|
||||||
|
import Credential from './Credential'
|
||||||
import DepositPreauth from './DepositPreauth'
|
import DepositPreauth from './DepositPreauth'
|
||||||
import DID from './DID'
|
import DID from './DID'
|
||||||
import DirectoryNode from './DirectoryNode'
|
import DirectoryNode from './DirectoryNode'
|
||||||
@@ -15,13 +16,16 @@ import FeeSettings, {
|
|||||||
FeeSettingsPostAmendmentFields,
|
FeeSettingsPostAmendmentFields,
|
||||||
FEE_SETTINGS_ID,
|
FEE_SETTINGS_ID,
|
||||||
} from './FeeSettings'
|
} from './FeeSettings'
|
||||||
import Ledger from './Ledger'
|
import { Ledger, LedgerV1 } from './Ledger'
|
||||||
import { LedgerEntry, LedgerEntryFilter } from './LedgerEntry'
|
import { LedgerEntry, LedgerEntryFilter } from './LedgerEntry'
|
||||||
import LedgerHashes from './LedgerHashes'
|
import LedgerHashes from './LedgerHashes'
|
||||||
|
import { MPToken } from './MPToken'
|
||||||
|
import { MPTokenIssuance } from './MPTokenIssuance'
|
||||||
import NegativeUNL, { NEGATIVE_UNL_ID } from './NegativeUNL'
|
import NegativeUNL, { NEGATIVE_UNL_ID } from './NegativeUNL'
|
||||||
import { NFTokenOffer } from './NFTokenOffer'
|
import { NFTokenOffer } from './NFTokenOffer'
|
||||||
import { NFToken, NFTokenPage } from './NFTokenPage'
|
import { NFToken, NFTokenPage } from './NFTokenPage'
|
||||||
import Offer, { OfferFlags } from './Offer'
|
import Offer, { OfferFlags } from './Offer'
|
||||||
|
import Oracle from './Oracle'
|
||||||
import PayChannel from './PayChannel'
|
import PayChannel from './PayChannel'
|
||||||
import RippleState, { RippleStateFlags } from './RippleState'
|
import RippleState, { RippleStateFlags } from './RippleState'
|
||||||
import SignerList, { SignerListFlags } from './SignerList'
|
import SignerList, { SignerListFlags } from './SignerList'
|
||||||
@@ -38,6 +42,7 @@ export {
|
|||||||
AMM,
|
AMM,
|
||||||
Bridge,
|
Bridge,
|
||||||
Check,
|
Check,
|
||||||
|
Credential,
|
||||||
DepositPreauth,
|
DepositPreauth,
|
||||||
DirectoryNode,
|
DirectoryNode,
|
||||||
DID,
|
DID,
|
||||||
@@ -47,17 +52,21 @@ export {
|
|||||||
FeeSettingsPreAmendmentFields,
|
FeeSettingsPreAmendmentFields,
|
||||||
FeeSettingsPostAmendmentFields,
|
FeeSettingsPostAmendmentFields,
|
||||||
Ledger,
|
Ledger,
|
||||||
|
LedgerV1,
|
||||||
LedgerEntryFilter,
|
LedgerEntryFilter,
|
||||||
LedgerEntry,
|
LedgerEntry,
|
||||||
LedgerHashes,
|
LedgerHashes,
|
||||||
Majority,
|
Majority,
|
||||||
NEGATIVE_UNL_ID,
|
NEGATIVE_UNL_ID,
|
||||||
NegativeUNL,
|
NegativeUNL,
|
||||||
|
MPTokenIssuance,
|
||||||
|
MPToken,
|
||||||
NFTokenOffer,
|
NFTokenOffer,
|
||||||
NFTokenPage,
|
NFTokenPage,
|
||||||
NFToken,
|
NFToken,
|
||||||
Offer,
|
Offer,
|
||||||
OfferFlags,
|
OfferFlags,
|
||||||
|
Oracle,
|
||||||
PayChannel,
|
PayChannel,
|
||||||
RippleState,
|
RippleState,
|
||||||
RippleStateFlags,
|
RippleStateFlags,
|
||||||
|
|||||||
@@ -1,17 +1,80 @@
|
|||||||
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Represents a payment channel in the XRP Ledger.
|
||||||
|
*/
|
||||||
export interface Channel {
|
export interface Channel {
|
||||||
|
/** The owner of the channel, as an Address. */
|
||||||
account: string
|
account: string
|
||||||
|
|
||||||
|
/** The total amount of XRP, in drops allocated to this channel. */
|
||||||
amount: string
|
amount: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The total amount of XRP, in drops, paid out from this channel,
|
||||||
|
* as of the ledger version used. (You can calculate the amount of
|
||||||
|
* XRP left in the channel by subtracting balance from amount.)
|
||||||
|
*/
|
||||||
balance: string
|
balance: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A unique ID for this channel, as a 64-character hexadecimal string.
|
||||||
|
* This is also the ID of the channel object in the ledger's state data.
|
||||||
|
*/
|
||||||
channel_id: string
|
channel_id: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The destination account of the channel, as an Address.
|
||||||
|
* Only this account can receive the XRP in the channel while it is open.
|
||||||
|
*/
|
||||||
destination_account: string
|
destination_account: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The number of seconds the payment channel must stay open after the owner
|
||||||
|
* of the channel requests to close it.
|
||||||
|
*/
|
||||||
settle_delay: number
|
settle_delay: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The public key for the payment channel in the XRP Ledger's base58 format.
|
||||||
|
* Signed claims against this channel must be redeemed with the matching key pair.
|
||||||
|
*/
|
||||||
public_key?: string
|
public_key?: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The public key for the payment channel in hexadecimal format, if one was
|
||||||
|
* specified at channel creation. Signed claims against this channel must be
|
||||||
|
* redeemed with the matching key pair.
|
||||||
|
*/
|
||||||
public_key_hex?: string
|
public_key_hex?: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Time, in seconds since the Ripple Epoch, when this channel is set to expire.
|
||||||
|
* This expiration date is mutable. If this is before the close time of the most
|
||||||
|
* recent validated ledger, the channel is expired.
|
||||||
|
*/
|
||||||
expiration?: number
|
expiration?: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Time, in seconds since the Ripple Epoch, of this channel's immutable expiration,
|
||||||
|
* if one was specified at channel creation. If this is before the close time of the
|
||||||
|
* most recent validated ledger, the channel is expired.
|
||||||
|
*/
|
||||||
cancel_after?: number
|
cancel_after?: number
|
||||||
source_tab?: number
|
|
||||||
|
/**
|
||||||
|
* A 32-bit unsigned integer to use as a source tag for payments through this payment channel,
|
||||||
|
* if one was specified at channel creation. This indicates the payment channel's originator or
|
||||||
|
* other purpose at the source account. Conventionally, if you bounce payments from this channel,
|
||||||
|
* you should specify this value in the DestinationTag of the return payment.
|
||||||
|
*/
|
||||||
|
source_tag?: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A 32-bit unsigned integer to use as a destination tag for payments through this channel,
|
||||||
|
* if one was specified at channel creation. This indicates the payment channel's beneficiary
|
||||||
|
* or other purpose at the destination account.
|
||||||
|
*/
|
||||||
destination_tag?: number
|
destination_tag?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
import { APIVersion, DEFAULT_API_VERSION, RIPPLED_API_V1 } from '../common'
|
||||||
import { AccountRoot, SignerList } from '../ledger'
|
import { AccountRoot, SignerList } from '../ledger'
|
||||||
|
|
||||||
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
||||||
@@ -133,23 +134,13 @@ export interface AccountInfoAccountFlags {
|
|||||||
allowTrustLineClawback: boolean
|
allowTrustLineClawback: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
interface BaseAccountInfoResponse extends BaseResponse {
|
||||||
* Response expected from an {@link AccountInfoRequest}.
|
|
||||||
*
|
|
||||||
* @category Responses
|
|
||||||
*/
|
|
||||||
export interface AccountInfoResponse extends BaseResponse {
|
|
||||||
result: {
|
result: {
|
||||||
/**
|
/**
|
||||||
* The AccountRoot ledger object with this account's information, as stored
|
* The AccountRoot ledger object with this account's information, as stored
|
||||||
* in the ledger.
|
* in the ledger.
|
||||||
* If requested, also includes Array of SignerList ledger objects
|
|
||||||
* associated with this account for Multi-Signing. Since an account can own
|
|
||||||
* at most one SignerList, this array must have exactly one member if it is
|
|
||||||
* present.
|
|
||||||
*/
|
*/
|
||||||
account_data: AccountRoot & { signer_lists?: SignerList[] }
|
account_data: AccountRoot
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A map of account flags parsed out. This will only be available for rippled nodes 1.11.0 and higher.
|
* A map of account flags parsed out. This will only be available for rippled nodes 1.11.0 and higher.
|
||||||
*/
|
*/
|
||||||
@@ -180,3 +171,58 @@ export interface AccountInfoResponse extends BaseResponse {
|
|||||||
validated?: boolean
|
validated?: boolean
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from a {@link AccountInfoRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export interface AccountInfoResponse extends BaseAccountInfoResponse {
|
||||||
|
result: BaseAccountInfoResponse['result'] & {
|
||||||
|
/**
|
||||||
|
* If requested, array of SignerList ledger objects associated with this account for Multi-Signing.
|
||||||
|
* Since an account can own at most one SignerList, this array must have exactly one
|
||||||
|
* member if it is present.
|
||||||
|
*/
|
||||||
|
signer_lists?: SignerList[]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from a {@link AccountInfoRequest} using API version 1.
|
||||||
|
*
|
||||||
|
* @category ResponsesV1
|
||||||
|
*/
|
||||||
|
export interface AccountInfoV1Response extends BaseAccountInfoResponse {
|
||||||
|
result: BaseAccountInfoResponse['result'] & {
|
||||||
|
/**
|
||||||
|
* The AccountRoot ledger object with this account's information, as stored
|
||||||
|
* in the ledger.
|
||||||
|
* If requested, also includes Array of SignerList ledger objects
|
||||||
|
* associated with this account for Multi-Signing. Since an account can own
|
||||||
|
* at most one SignerList, this array must have exactly one member if it is
|
||||||
|
* present.
|
||||||
|
*/
|
||||||
|
account_data: BaseAccountInfoResponse['result']['account_data'] & {
|
||||||
|
/**
|
||||||
|
* Array of SignerList ledger objects associated with this account for Multi-Signing.
|
||||||
|
* Since an account can own at most one SignerList, this array must have exactly one
|
||||||
|
* member if it is present.
|
||||||
|
* Quirk: In API version 1, this field is nested under account_data. For this method,
|
||||||
|
* Clio implements the API version 2 behavior where is field is not nested under account_data.
|
||||||
|
*/
|
||||||
|
signer_lists?: SignerList[]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the response type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type AccountInfoVersionResponseMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1
|
||||||
|
? AccountInfoV1Response
|
||||||
|
: AccountInfoResponse
|
||||||
|
|||||||
@@ -1,4 +1,10 @@
|
|||||||
import { ResponseOnlyTxInfo } from '../common'
|
import {
|
||||||
|
APIVersion,
|
||||||
|
DEFAULT_API_VERSION,
|
||||||
|
RIPPLED_API_V1,
|
||||||
|
RIPPLED_API_V2,
|
||||||
|
ResponseOnlyTxInfo,
|
||||||
|
} from '../common'
|
||||||
import { Transaction, TransactionMetadata } from '../transactions'
|
import { Transaction, TransactionMetadata } from '../transactions'
|
||||||
|
|
||||||
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
||||||
@@ -49,7 +55,9 @@ export interface AccountTxRequest extends BaseRequest, LookupByLedgerRequest {
|
|||||||
marker?: unknown
|
marker?: unknown
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface AccountTxTransaction {
|
export interface AccountTxTransaction<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> {
|
||||||
/** The ledger index of the ledger version that included this transaction. */
|
/** The ledger index of the ledger version that included this transaction. */
|
||||||
ledger_index: number
|
ledger_index: number
|
||||||
/**
|
/**
|
||||||
@@ -58,7 +66,15 @@ export interface AccountTxTransaction {
|
|||||||
*/
|
*/
|
||||||
meta: string | TransactionMetadata
|
meta: string | TransactionMetadata
|
||||||
/** JSON object defining the transaction. */
|
/** JSON object defining the transaction. */
|
||||||
tx?: Transaction & ResponseOnlyTxInfo
|
tx_json?: Version extends typeof RIPPLED_API_V2
|
||||||
|
? Transaction & ResponseOnlyTxInfo
|
||||||
|
: never
|
||||||
|
/** JSON object defining the transaction in rippled API v1. */
|
||||||
|
tx?: Version extends typeof RIPPLED_API_V1
|
||||||
|
? Transaction & ResponseOnlyTxInfo
|
||||||
|
: never
|
||||||
|
/** The hash of the transaction. */
|
||||||
|
hash?: Version extends typeof RIPPLED_API_V2 ? string : never
|
||||||
/** Unique hashed String representing the transaction. */
|
/** Unique hashed String representing the transaction. */
|
||||||
tx_blob?: string
|
tx_blob?: string
|
||||||
/**
|
/**
|
||||||
@@ -69,11 +85,11 @@ export interface AccountTxTransaction {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Expected response from an {@link AccountTxRequest}.
|
* Base interface for account transaction responses.
|
||||||
*
|
|
||||||
* @category Responses
|
|
||||||
*/
|
*/
|
||||||
export interface AccountTxResponse extends BaseResponse {
|
interface AccountTxResponseBase<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> extends BaseResponse {
|
||||||
result: {
|
result: {
|
||||||
/** Unique Address identifying the related account. */
|
/** Unique Address identifying the related account. */
|
||||||
account: string
|
account: string
|
||||||
@@ -98,7 +114,7 @@ export interface AccountTxResponse extends BaseResponse {
|
|||||||
* Array of transactions matching the request's criteria, as explained
|
* Array of transactions matching the request's criteria, as explained
|
||||||
* below.
|
* below.
|
||||||
*/
|
*/
|
||||||
transactions: AccountTxTransaction[]
|
transactions: Array<AccountTxTransaction<Version>>
|
||||||
/**
|
/**
|
||||||
* If included and set to true, the information in this response comes from
|
* If included and set to true, the information in this response comes from
|
||||||
* a validated ledger version. Otherwise, the information is subject to
|
* a validated ledger version. Otherwise, the information is subject to
|
||||||
@@ -107,3 +123,28 @@ export interface AccountTxResponse extends BaseResponse {
|
|||||||
validated?: boolean
|
validated?: boolean
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Expected response from an {@link AccountTxRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type AccountTxResponse = AccountTxResponseBase
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Expected response from an {@link AccountTxRequest} with `api_version` set to 1.
|
||||||
|
*
|
||||||
|
* @category ResponsesV1
|
||||||
|
*/
|
||||||
|
export type AccountTxV1Response = AccountTxResponseBase<typeof RIPPLED_API_V1>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the response type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type AccountTxVersionResponseMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1
|
||||||
|
? AccountTxV1Response
|
||||||
|
: AccountTxResponse
|
||||||
|
|||||||
@@ -15,6 +15,12 @@ export interface DepositAuthorizedRequest
|
|||||||
source_account: string
|
source_account: string
|
||||||
/** The recipient of a possible payment. */
|
/** The recipient of a possible payment. */
|
||||||
destination_account: string
|
destination_account: string
|
||||||
|
/**
|
||||||
|
* The object IDs of Credential objects. If this field is included, then the
|
||||||
|
* credential will be taken into account when analyzing whether the sender can send
|
||||||
|
* funds to the destination.
|
||||||
|
*/
|
||||||
|
credentials?: string[]
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -52,5 +58,9 @@ export interface DepositAuthorizedResponse extends BaseResponse {
|
|||||||
source_account: string
|
source_account: string
|
||||||
/** If true, the information comes from a validated ledger version. */
|
/** If true, the information comes from a validated ledger version. */
|
||||||
validated?: boolean
|
validated?: boolean
|
||||||
|
/** The object IDs of `Credential` objects. If this field is included,
|
||||||
|
* then the credential will be taken into account when analyzing whether
|
||||||
|
* the sender can send funds to the destination. */
|
||||||
|
credentials?: string[]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
68
packages/xrpl/src/models/methods/feature.ts
Normal file
68
packages/xrpl/src/models/methods/feature.ts
Normal file
@@ -0,0 +1,68 @@
|
|||||||
|
import { BaseRequest, BaseResponse } from './baseMethod'
|
||||||
|
|
||||||
|
export interface FeatureAllRequest extends BaseRequest {
|
||||||
|
command: 'feature'
|
||||||
|
|
||||||
|
feature?: never
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface FeatureOneRequest extends BaseRequest {
|
||||||
|
command: 'feature'
|
||||||
|
|
||||||
|
feature: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The `feature` command returns information about amendments this server knows about, including whether they are enabled.
|
||||||
|
* Returns an {@link FeatureResponse}.
|
||||||
|
*
|
||||||
|
* @category Requests
|
||||||
|
*/
|
||||||
|
export type FeatureRequest = FeatureAllRequest | FeatureOneRequest
|
||||||
|
|
||||||
|
export interface FeatureAllResponse extends BaseResponse {
|
||||||
|
result: {
|
||||||
|
features: Record<
|
||||||
|
string,
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Whether this amendment is currently enabled in the latest ledger.
|
||||||
|
*/
|
||||||
|
enabled: boolean
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The human-readable name for this amendment, if known.
|
||||||
|
*/
|
||||||
|
name: string
|
||||||
|
|
||||||
|
supported: boolean
|
||||||
|
}
|
||||||
|
>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface FeatureOneResponse extends BaseResponse {
|
||||||
|
result: Record<
|
||||||
|
string,
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Whether this amendment is currently enabled in the latest ledger.
|
||||||
|
*/
|
||||||
|
enabled: boolean
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The human-readable name for this amendment, if known.
|
||||||
|
*/
|
||||||
|
name: string
|
||||||
|
|
||||||
|
supported: boolean
|
||||||
|
}
|
||||||
|
>
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from an {@link FeatureRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type FeatureResponse = FeatureAllResponse | FeatureOneResponse
|
||||||
119
packages/xrpl/src/models/methods/getAggregatePrice.ts
Normal file
119
packages/xrpl/src/models/methods/getAggregatePrice.ts
Normal file
@@ -0,0 +1,119 @@
|
|||||||
|
import { BaseRequest, BaseResponse } from './baseMethod'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The `get_aggregate_price` method retrieves the aggregate price of specified Oracle objects,
|
||||||
|
* returning three price statistics: mean, median, and trimmed mean.
|
||||||
|
* Returns an {@link GetAggregatePriceResponse}.
|
||||||
|
*
|
||||||
|
* @category Requests
|
||||||
|
*/
|
||||||
|
export interface GetAggregatePriceRequest extends BaseRequest {
|
||||||
|
command: 'get_aggregate_price'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The currency code of the asset to be priced.
|
||||||
|
*/
|
||||||
|
base_asset: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The currency code of the asset to quote the price of the base asset.
|
||||||
|
*/
|
||||||
|
quote_asset: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The oracle identifier.
|
||||||
|
*/
|
||||||
|
oracles: Array<{
|
||||||
|
/**
|
||||||
|
* The XRPL account that controls the Oracle object.
|
||||||
|
*/
|
||||||
|
account: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A unique identifier of the price oracle for the Account
|
||||||
|
*/
|
||||||
|
oracle_document_id: string | number
|
||||||
|
}>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The percentage of outliers to trim. Valid trim range is 1-25. If included, the API returns statistics for the trimmed mean.
|
||||||
|
*/
|
||||||
|
trim?: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Defines a time range in seconds for filtering out older price data. Default value is 0, which doesn't filter any data.
|
||||||
|
*/
|
||||||
|
trim_threshold?: number
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from an {@link GetAggregatePriceRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export interface GetAggregatePriceResponse extends BaseResponse {
|
||||||
|
result: {
|
||||||
|
/**
|
||||||
|
* The statistics from the collected oracle prices.
|
||||||
|
*/
|
||||||
|
entire_set: {
|
||||||
|
/**
|
||||||
|
* The simple mean.
|
||||||
|
*/
|
||||||
|
mean: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The size of the data set to calculate the mean.
|
||||||
|
*/
|
||||||
|
size: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The standard deviation.
|
||||||
|
*/
|
||||||
|
standard_deviation: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The trimmed statistics from the collected oracle prices. Only appears if the trim field was specified in the request.
|
||||||
|
*/
|
||||||
|
trimmed_set?: {
|
||||||
|
/**
|
||||||
|
* The simple mean of the trimmed data.
|
||||||
|
*/
|
||||||
|
mean: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The size of the data to calculate the trimmed mean.
|
||||||
|
*/
|
||||||
|
size: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The standard deviation of the trimmed data.
|
||||||
|
*/
|
||||||
|
standard_deviation: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The median of the collected oracle prices.
|
||||||
|
*/
|
||||||
|
median: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The most recent timestamp out of all LastUpdateTime values.
|
||||||
|
*/
|
||||||
|
time: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The ledger index of the ledger version that was used to generate this
|
||||||
|
* response.
|
||||||
|
*/
|
||||||
|
ledger_current_index: number
|
||||||
|
|
||||||
|
/**
|
||||||
|
* If included and set to true, the information in this response comes from
|
||||||
|
* a validated ledger version. Otherwise, the information is subject to
|
||||||
|
* change.
|
||||||
|
*/
|
||||||
|
validated: boolean
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,5 +1,7 @@
|
|||||||
/* eslint-disable no-inline-comments -- Necessary for important note */
|
/* eslint-disable no-inline-comments -- Necessary for important note */
|
||||||
/* eslint-disable max-lines -- There is a lot to export */
|
/* eslint-disable max-lines -- There is a lot to export */
|
||||||
|
import type { APIVersion, DEFAULT_API_VERSION } from '../common'
|
||||||
|
|
||||||
import {
|
import {
|
||||||
AccountChannelsRequest,
|
AccountChannelsRequest,
|
||||||
AccountChannelsResponse,
|
AccountChannelsResponse,
|
||||||
@@ -13,6 +15,8 @@ import {
|
|||||||
AccountInfoAccountFlags,
|
AccountInfoAccountFlags,
|
||||||
AccountInfoRequest,
|
AccountInfoRequest,
|
||||||
AccountInfoResponse,
|
AccountInfoResponse,
|
||||||
|
AccountInfoV1Response,
|
||||||
|
AccountInfoVersionResponseMap,
|
||||||
AccountQueueData,
|
AccountQueueData,
|
||||||
AccountQueueTransaction,
|
AccountQueueTransaction,
|
||||||
} from './accountInfo'
|
} from './accountInfo'
|
||||||
@@ -40,6 +44,8 @@ import {
|
|||||||
import {
|
import {
|
||||||
AccountTxRequest,
|
AccountTxRequest,
|
||||||
AccountTxResponse,
|
AccountTxResponse,
|
||||||
|
AccountTxV1Response,
|
||||||
|
AccountTxVersionResponseMap,
|
||||||
AccountTxTransaction,
|
AccountTxTransaction,
|
||||||
} from './accountTx'
|
} from './accountTx'
|
||||||
import { AMMInfoRequest, AMMInfoResponse } from './ammInfo'
|
import { AMMInfoRequest, AMMInfoResponse } from './ammInfo'
|
||||||
@@ -60,23 +66,37 @@ import {
|
|||||||
DepositAuthorizedRequest,
|
DepositAuthorizedRequest,
|
||||||
DepositAuthorizedResponse,
|
DepositAuthorizedResponse,
|
||||||
} from './depositAuthorized'
|
} from './depositAuthorized'
|
||||||
|
import {
|
||||||
|
FeatureAllRequest,
|
||||||
|
FeatureAllResponse,
|
||||||
|
FeatureOneRequest,
|
||||||
|
FeatureOneResponse,
|
||||||
|
FeatureRequest,
|
||||||
|
FeatureResponse,
|
||||||
|
} from './feature'
|
||||||
import { FeeRequest, FeeResponse } from './fee'
|
import { FeeRequest, FeeResponse } from './fee'
|
||||||
import {
|
import {
|
||||||
GatewayBalance,
|
GatewayBalance,
|
||||||
GatewayBalancesRequest,
|
GatewayBalancesRequest,
|
||||||
GatewayBalancesResponse,
|
GatewayBalancesResponse,
|
||||||
} from './gatewayBalances'
|
} from './gatewayBalances'
|
||||||
|
import {
|
||||||
|
GetAggregatePriceRequest,
|
||||||
|
GetAggregatePriceResponse,
|
||||||
|
} from './getAggregatePrice'
|
||||||
import {
|
import {
|
||||||
LedgerBinary,
|
LedgerBinary,
|
||||||
LedgerModifiedOfferCreateTransaction,
|
LedgerModifiedOfferCreateTransaction,
|
||||||
LedgerQueueData,
|
LedgerQueueData,
|
||||||
LedgerRequest,
|
LedgerRequest,
|
||||||
LedgerResponse,
|
LedgerResponse,
|
||||||
|
LedgerV1Response,
|
||||||
LedgerRequestExpandedTransactionsOnly,
|
LedgerRequestExpandedTransactionsOnly,
|
||||||
LedgerResponseExpanded,
|
LedgerResponseExpanded,
|
||||||
LedgerRequestExpandedAccountsAndTransactions,
|
LedgerRequestExpandedAccountsAndTransactions,
|
||||||
LedgerRequestExpandedAccountsOnly,
|
LedgerRequestExpandedAccountsOnly,
|
||||||
LedgerRequestExpandedTransactionsBinary,
|
LedgerRequestExpandedTransactionsBinary,
|
||||||
|
LedgerVersionResponseMap,
|
||||||
} from './ledger'
|
} from './ledger'
|
||||||
import { LedgerClosedRequest, LedgerClosedResponse } from './ledgerClosed'
|
import { LedgerClosedRequest, LedgerClosedResponse } from './ledgerClosed'
|
||||||
import { LedgerCurrentRequest, LedgerCurrentResponse } from './ledgerCurrent'
|
import { LedgerCurrentRequest, LedgerCurrentResponse } from './ledgerCurrent'
|
||||||
@@ -96,6 +116,7 @@ import {
|
|||||||
NFTHistoryTransaction,
|
NFTHistoryTransaction,
|
||||||
} from './nftHistory'
|
} from './nftHistory'
|
||||||
import { NFTInfoRequest, NFTInfoResponse } from './nftInfo'
|
import { NFTInfoRequest, NFTInfoResponse } from './nftInfo'
|
||||||
|
import { NFTsByIssuerRequest, NFTsByIssuerResponse } from './nftsByIssuer'
|
||||||
import { NFTSellOffersRequest, NFTSellOffersResponse } from './nftSellOffers'
|
import { NFTSellOffersRequest, NFTSellOffersResponse } from './nftSellOffers'
|
||||||
import { NoRippleCheckRequest, NoRippleCheckResponse } from './norippleCheck'
|
import { NoRippleCheckRequest, NoRippleCheckResponse } from './norippleCheck'
|
||||||
import {
|
import {
|
||||||
@@ -127,10 +148,20 @@ import {
|
|||||||
StateAccountingFinal,
|
StateAccountingFinal,
|
||||||
} from './serverInfo'
|
} from './serverInfo'
|
||||||
import { ServerStateRequest, ServerStateResponse } from './serverState'
|
import { ServerStateRequest, ServerStateResponse } from './serverState'
|
||||||
|
import {
|
||||||
|
SimulateBinaryRequest,
|
||||||
|
SimulateBinaryResponse,
|
||||||
|
SimulateJsonRequest,
|
||||||
|
SimulateJsonResponse,
|
||||||
|
SimulateRequest,
|
||||||
|
SimulateResponse,
|
||||||
|
} from './simulate'
|
||||||
import { SubmitRequest, SubmitResponse } from './submit'
|
import { SubmitRequest, SubmitResponse } from './submit'
|
||||||
import {
|
import {
|
||||||
SubmitMultisignedRequest,
|
SubmitMultisignedRequest,
|
||||||
SubmitMultisignedResponse,
|
SubmitMultisignedResponse,
|
||||||
|
SubmitMultisignedV1Response,
|
||||||
|
SubmitMultisignedVersionResponseMap,
|
||||||
} from './submitMultisigned'
|
} from './submitMultisigned'
|
||||||
import {
|
import {
|
||||||
BooksSnapshot,
|
BooksSnapshot,
|
||||||
@@ -145,13 +176,14 @@ import {
|
|||||||
SubscribeRequest,
|
SubscribeRequest,
|
||||||
SubscribeResponse,
|
SubscribeResponse,
|
||||||
TransactionStream,
|
TransactionStream,
|
||||||
|
TransactionV1Stream,
|
||||||
ValidationStream,
|
ValidationStream,
|
||||||
} from './subscribe'
|
} from './subscribe'
|
||||||
import {
|
import {
|
||||||
TransactionEntryRequest,
|
TransactionEntryRequest,
|
||||||
TransactionEntryResponse,
|
TransactionEntryResponse,
|
||||||
} from './transactionEntry'
|
} from './transactionEntry'
|
||||||
import { TxRequest, TxResponse } from './tx'
|
import { TxRequest, TxResponse, TxV1Response, TxVersionResponseMap } from './tx'
|
||||||
import {
|
import {
|
||||||
UnsubscribeBook,
|
UnsubscribeBook,
|
||||||
UnsubscribeRequest,
|
UnsubscribeRequest,
|
||||||
@@ -179,6 +211,7 @@ type Request =
|
|||||||
| LedgerDataRequest
|
| LedgerDataRequest
|
||||||
| LedgerEntryRequest
|
| LedgerEntryRequest
|
||||||
// transaction methods
|
// transaction methods
|
||||||
|
| SimulateRequest
|
||||||
| SubmitRequest
|
| SubmitRequest
|
||||||
| SubmitMultisignedRequest
|
| SubmitMultisignedRequest
|
||||||
| TransactionEntryRequest
|
| TransactionEntryRequest
|
||||||
@@ -199,6 +232,7 @@ type Request =
|
|||||||
| ServerDefinitionsRequest
|
| ServerDefinitionsRequest
|
||||||
| ServerInfoRequest
|
| ServerInfoRequest
|
||||||
| ServerStateRequest
|
| ServerStateRequest
|
||||||
|
| FeatureRequest
|
||||||
// utility methods
|
// utility methods
|
||||||
| PingRequest
|
| PingRequest
|
||||||
| RandomRequest
|
| RandomRequest
|
||||||
@@ -208,33 +242,37 @@ type Request =
|
|||||||
// clio only methods
|
// clio only methods
|
||||||
| NFTInfoRequest
|
| NFTInfoRequest
|
||||||
| NFTHistoryRequest
|
| NFTHistoryRequest
|
||||||
|
| NFTsByIssuerRequest
|
||||||
// AMM methods
|
// AMM methods
|
||||||
| AMMInfoRequest
|
| AMMInfoRequest
|
||||||
|
// Price Oracle methods
|
||||||
|
| GetAggregatePriceRequest
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @category Responses
|
* @category Responses
|
||||||
*/
|
*/
|
||||||
type Response =
|
type Response<Version extends APIVersion = typeof DEFAULT_API_VERSION> =
|
||||||
// account methods
|
// account methods
|
||||||
| AccountChannelsResponse
|
| AccountChannelsResponse
|
||||||
| AccountCurrenciesResponse
|
| AccountCurrenciesResponse
|
||||||
| AccountInfoResponse
|
| AccountInfoVersionResponseMap<Version>
|
||||||
| AccountLinesResponse
|
| AccountLinesResponse
|
||||||
| AccountNFTsResponse
|
| AccountNFTsResponse
|
||||||
| AccountObjectsResponse
|
| AccountObjectsResponse
|
||||||
| AccountOffersResponse
|
| AccountOffersResponse
|
||||||
| AccountTxResponse
|
| AccountTxVersionResponseMap<Version>
|
||||||
| GatewayBalancesResponse
|
| GatewayBalancesResponse
|
||||||
| NoRippleCheckResponse
|
| NoRippleCheckResponse
|
||||||
// ledger methods
|
// ledger methods
|
||||||
| LedgerResponse
|
| LedgerVersionResponseMap<Version>
|
||||||
| LedgerClosedResponse
|
| LedgerClosedResponse
|
||||||
| LedgerCurrentResponse
|
| LedgerCurrentResponse
|
||||||
| LedgerDataResponse
|
| LedgerDataResponse
|
||||||
| LedgerEntryResponse
|
| LedgerEntryResponse
|
||||||
// transaction methods
|
// transaction methods
|
||||||
|
| SimulateResponse
|
||||||
| SubmitResponse
|
| SubmitResponse
|
||||||
| SubmitMultisignedResponse
|
| SubmitMultisignedVersionResponseMap<Version>
|
||||||
| TransactionEntryResponse
|
| TransactionEntryResponse
|
||||||
| TxResponse
|
| TxResponse
|
||||||
// path and order book methods
|
// path and order book methods
|
||||||
@@ -253,6 +291,7 @@ type Response =
|
|||||||
| ServerDefinitionsResponse
|
| ServerDefinitionsResponse
|
||||||
| ServerInfoResponse
|
| ServerInfoResponse
|
||||||
| ServerStateResponse
|
| ServerStateResponse
|
||||||
|
| FeatureResponse
|
||||||
// utility methods
|
// utility methods
|
||||||
| PingResponse
|
| PingResponse
|
||||||
| RandomResponse
|
| RandomResponse
|
||||||
@@ -262,15 +301,21 @@ type Response =
|
|||||||
// clio only methods
|
// clio only methods
|
||||||
| NFTInfoResponse
|
| NFTInfoResponse
|
||||||
| NFTHistoryResponse
|
| NFTHistoryResponse
|
||||||
|
| NFTsByIssuerResponse
|
||||||
// AMM methods
|
// AMM methods
|
||||||
| AMMInfoResponse
|
| AMMInfoResponse
|
||||||
|
// Price Oracle methods
|
||||||
|
| GetAggregatePriceResponse
|
||||||
|
|
||||||
export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
export type RequestResponseMap<
|
||||||
|
T,
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = T extends AccountChannelsRequest
|
||||||
? AccountChannelsResponse
|
? AccountChannelsResponse
|
||||||
: T extends AccountCurrenciesRequest
|
: T extends AccountCurrenciesRequest
|
||||||
? AccountCurrenciesResponse
|
? AccountCurrenciesResponse
|
||||||
: T extends AccountInfoRequest
|
: T extends AccountInfoRequest
|
||||||
? AccountInfoResponse
|
? AccountInfoVersionResponseMap<Version>
|
||||||
: T extends AccountLinesRequest
|
: T extends AccountLinesRequest
|
||||||
? AccountLinesResponse
|
? AccountLinesResponse
|
||||||
: T extends AccountNFTsRequest
|
: T extends AccountNFTsRequest
|
||||||
@@ -280,11 +325,13 @@ export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
: T extends AccountOffersRequest
|
: T extends AccountOffersRequest
|
||||||
? AccountOffersResponse
|
? AccountOffersResponse
|
||||||
: T extends AccountTxRequest
|
: T extends AccountTxRequest
|
||||||
? AccountTxResponse
|
? AccountTxVersionResponseMap<Version>
|
||||||
: T extends AMMInfoRequest
|
: T extends AMMInfoRequest
|
||||||
? AMMInfoResponse
|
? AMMInfoResponse
|
||||||
: T extends GatewayBalancesRequest
|
: T extends GatewayBalancesRequest
|
||||||
? GatewayBalancesResponse
|
? GatewayBalancesResponse
|
||||||
|
: T extends GetAggregatePriceRequest
|
||||||
|
? GetAggregatePriceResponse
|
||||||
: T extends NoRippleCheckRequest
|
: T extends NoRippleCheckRequest
|
||||||
? NoRippleCheckResponse
|
? NoRippleCheckResponse
|
||||||
: // NOTE: The order of these LedgerRequest types is important
|
: // NOTE: The order of these LedgerRequest types is important
|
||||||
@@ -344,15 +391,15 @@ export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
// then we'd get the wrong response type, LedgerResponse, instead of
|
// then we'd get the wrong response type, LedgerResponse, instead of
|
||||||
// LedgerResponseExpanded.
|
// LedgerResponseExpanded.
|
||||||
T extends LedgerRequestExpandedTransactionsBinary
|
T extends LedgerRequestExpandedTransactionsBinary
|
||||||
? LedgerResponse
|
? LedgerVersionResponseMap<Version>
|
||||||
: T extends LedgerRequestExpandedAccountsAndTransactions
|
: T extends LedgerRequestExpandedAccountsAndTransactions
|
||||||
? LedgerResponseExpanded
|
? LedgerResponseExpanded<Version>
|
||||||
: T extends LedgerRequestExpandedTransactionsOnly
|
: T extends LedgerRequestExpandedTransactionsOnly
|
||||||
? LedgerResponseExpanded
|
? LedgerResponseExpanded<Version>
|
||||||
: T extends LedgerRequestExpandedAccountsOnly
|
: T extends LedgerRequestExpandedAccountsOnly
|
||||||
? LedgerResponseExpanded
|
? LedgerResponseExpanded<Version>
|
||||||
: T extends LedgerRequest
|
: T extends LedgerRequest
|
||||||
? LedgerResponse
|
? LedgerVersionResponseMap<Version>
|
||||||
: T extends LedgerClosedRequest
|
: T extends LedgerClosedRequest
|
||||||
? LedgerClosedResponse
|
? LedgerClosedResponse
|
||||||
: T extends LedgerCurrentRequest
|
: T extends LedgerCurrentRequest
|
||||||
@@ -361,14 +408,20 @@ export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
? LedgerDataResponse
|
? LedgerDataResponse
|
||||||
: T extends LedgerEntryRequest
|
: T extends LedgerEntryRequest
|
||||||
? LedgerEntryResponse
|
? LedgerEntryResponse
|
||||||
|
: T extends SimulateBinaryRequest
|
||||||
|
? SimulateBinaryResponse
|
||||||
|
: T extends SimulateJsonRequest
|
||||||
|
? SimulateJsonResponse
|
||||||
|
: T extends SimulateRequest
|
||||||
|
? SimulateJsonResponse
|
||||||
: T extends SubmitRequest
|
: T extends SubmitRequest
|
||||||
? SubmitResponse
|
? SubmitResponse
|
||||||
: T extends SubmitMultisignedRequest
|
: T extends SubmitMultisignedRequest
|
||||||
? SubmitMultisignedResponse
|
? SubmitMultisignedVersionResponseMap<Version>
|
||||||
: T extends TransactionEntryRequest
|
: T extends TransactionEntryRequest
|
||||||
? TransactionEntryResponse
|
? TransactionEntryResponse
|
||||||
: T extends TxRequest
|
: T extends TxRequest
|
||||||
? TxResponse
|
? TxVersionResponseMap<Version>
|
||||||
: T extends BookOffersRequest
|
: T extends BookOffersRequest
|
||||||
? BookOffersResponse
|
? BookOffersResponse
|
||||||
: T extends DepositAuthorizedRequest
|
: T extends DepositAuthorizedRequest
|
||||||
@@ -393,6 +446,10 @@ export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
? ServerStateResponse
|
? ServerStateResponse
|
||||||
: T extends ServerDefinitionsRequest
|
: T extends ServerDefinitionsRequest
|
||||||
? ServerDefinitionsResponse
|
? ServerDefinitionsResponse
|
||||||
|
: T extends FeatureAllRequest
|
||||||
|
? FeatureAllResponse
|
||||||
|
: T extends FeatureOneRequest
|
||||||
|
? FeatureOneResponse
|
||||||
: T extends PingRequest
|
: T extends PingRequest
|
||||||
? PingResponse
|
? PingResponse
|
||||||
: T extends RandomRequest
|
: T extends RandomRequest
|
||||||
@@ -403,22 +460,29 @@ export type RequestResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
? NFTSellOffersResponse
|
? NFTSellOffersResponse
|
||||||
: T extends NFTInfoRequest
|
: T extends NFTInfoRequest
|
||||||
? NFTInfoResponse
|
? NFTInfoResponse
|
||||||
|
: T extends NFTsByIssuerRequest
|
||||||
|
? NFTsByIssuerResponse
|
||||||
: T extends NFTHistoryRequest
|
: T extends NFTHistoryRequest
|
||||||
? NFTHistoryResponse
|
? NFTHistoryResponse
|
||||||
: Response
|
: Response<Version>
|
||||||
|
|
||||||
export type MarkerRequest = Request & {
|
export type MarkerRequest = Request & {
|
||||||
limit?: number
|
limit?: number
|
||||||
marker?: unknown
|
marker?: unknown
|
||||||
}
|
}
|
||||||
|
|
||||||
export type MarkerResponse = Response & {
|
export type MarkerResponse<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Response<Version> & {
|
||||||
result: {
|
result: {
|
||||||
marker?: unknown
|
marker?: unknown
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export type RequestAllResponseMap<T> = T extends AccountChannelsRequest
|
export type RequestAllResponseMap<
|
||||||
|
T,
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = T extends AccountChannelsRequest
|
||||||
? AccountChannelsResponse
|
? AccountChannelsResponse
|
||||||
: T extends AccountLinesRequest
|
: T extends AccountLinesRequest
|
||||||
? AccountLinesResponse
|
? AccountLinesResponse
|
||||||
@@ -427,14 +491,12 @@ export type RequestAllResponseMap<T> = T extends AccountChannelsRequest
|
|||||||
: T extends AccountOffersRequest
|
: T extends AccountOffersRequest
|
||||||
? AccountOffersResponse
|
? AccountOffersResponse
|
||||||
: T extends AccountTxRequest
|
: T extends AccountTxRequest
|
||||||
? AccountTxResponse
|
? AccountTxVersionResponseMap<Version>
|
||||||
: T extends LedgerDataRequest
|
: T extends LedgerDataRequest
|
||||||
? LedgerDataResponse
|
? LedgerDataResponse
|
||||||
: T extends AccountTxRequest
|
|
||||||
? AccountTxResponse
|
|
||||||
: T extends BookOffersRequest
|
: T extends BookOffersRequest
|
||||||
? BookOffersResponse
|
? BookOffersResponse
|
||||||
: MarkerResponse
|
: MarkerResponse<Version>
|
||||||
|
|
||||||
export {
|
export {
|
||||||
// Allow users to define their own requests and responses. This is useful for releasing experimental versions
|
// Allow users to define their own requests and responses. This is useful for releasing experimental versions
|
||||||
@@ -452,6 +514,7 @@ export {
|
|||||||
AccountInfoAccountFlags,
|
AccountInfoAccountFlags,
|
||||||
AccountInfoRequest,
|
AccountInfoRequest,
|
||||||
AccountInfoResponse,
|
AccountInfoResponse,
|
||||||
|
AccountInfoV1Response,
|
||||||
AccountQueueData,
|
AccountQueueData,
|
||||||
AccountQueueTransaction,
|
AccountQueueTransaction,
|
||||||
AccountLinesRequest,
|
AccountLinesRequest,
|
||||||
@@ -469,15 +532,19 @@ export {
|
|||||||
AccountOffersResponse,
|
AccountOffersResponse,
|
||||||
AccountTxRequest,
|
AccountTxRequest,
|
||||||
AccountTxResponse,
|
AccountTxResponse,
|
||||||
|
AccountTxV1Response,
|
||||||
AccountTxTransaction,
|
AccountTxTransaction,
|
||||||
GatewayBalance,
|
GatewayBalance,
|
||||||
GatewayBalancesRequest,
|
GatewayBalancesRequest,
|
||||||
GatewayBalancesResponse,
|
GatewayBalancesResponse,
|
||||||
|
GetAggregatePriceRequest,
|
||||||
|
GetAggregatePriceResponse,
|
||||||
NoRippleCheckRequest,
|
NoRippleCheckRequest,
|
||||||
NoRippleCheckResponse,
|
NoRippleCheckResponse,
|
||||||
// ledger methods
|
// ledger methods
|
||||||
LedgerRequest,
|
LedgerRequest,
|
||||||
LedgerResponse,
|
LedgerResponse,
|
||||||
|
LedgerV1Response,
|
||||||
LedgerQueueData,
|
LedgerQueueData,
|
||||||
LedgerBinary,
|
LedgerBinary,
|
||||||
LedgerModifiedOfferCreateTransaction,
|
LedgerModifiedOfferCreateTransaction,
|
||||||
@@ -493,14 +560,18 @@ export {
|
|||||||
LedgerEntryRequest,
|
LedgerEntryRequest,
|
||||||
LedgerEntryResponse,
|
LedgerEntryResponse,
|
||||||
// transaction methods with types
|
// transaction methods with types
|
||||||
|
SimulateRequest,
|
||||||
|
SimulateResponse,
|
||||||
SubmitRequest,
|
SubmitRequest,
|
||||||
SubmitResponse,
|
SubmitResponse,
|
||||||
SubmitMultisignedRequest,
|
SubmitMultisignedRequest,
|
||||||
SubmitMultisignedResponse,
|
SubmitMultisignedResponse,
|
||||||
|
SubmitMultisignedV1Response,
|
||||||
TransactionEntryRequest,
|
TransactionEntryRequest,
|
||||||
TransactionEntryResponse,
|
TransactionEntryResponse,
|
||||||
TxRequest,
|
TxRequest,
|
||||||
TxResponse,
|
TxResponse,
|
||||||
|
TxV1Response,
|
||||||
// path and order book methods with types
|
// path and order book methods with types
|
||||||
BookOffersRequest,
|
BookOffersRequest,
|
||||||
BookOffer,
|
BookOffer,
|
||||||
@@ -531,6 +602,7 @@ export {
|
|||||||
LedgerStreamResponse,
|
LedgerStreamResponse,
|
||||||
ValidationStream,
|
ValidationStream,
|
||||||
TransactionStream,
|
TransactionStream,
|
||||||
|
TransactionV1Stream,
|
||||||
PathFindStream,
|
PathFindStream,
|
||||||
PeerStatusStream,
|
PeerStatusStream,
|
||||||
OrderBookStream,
|
OrderBookStream,
|
||||||
@@ -553,6 +625,8 @@ export {
|
|||||||
ServerState,
|
ServerState,
|
||||||
StateAccountingFinal,
|
StateAccountingFinal,
|
||||||
StateAccounting,
|
StateAccounting,
|
||||||
|
FeatureRequest,
|
||||||
|
FeatureResponse,
|
||||||
// utility methods
|
// utility methods
|
||||||
PingRequest,
|
PingRequest,
|
||||||
PingResponse,
|
PingResponse,
|
||||||
@@ -570,6 +644,8 @@ export {
|
|||||||
NFTHistoryRequest,
|
NFTHistoryRequest,
|
||||||
NFTHistoryResponse,
|
NFTHistoryResponse,
|
||||||
NFTHistoryTransaction,
|
NFTHistoryTransaction,
|
||||||
|
NFTsByIssuerRequest,
|
||||||
|
NFTsByIssuerResponse,
|
||||||
// AMM methods
|
// AMM methods
|
||||||
AMMInfoRequest,
|
AMMInfoRequest,
|
||||||
AMMInfoResponse,
|
AMMInfoResponse,
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
import { Ledger } from '../ledger'
|
import { APIVersion, DEFAULT_API_VERSION, RIPPLED_API_V1 } from '../common'
|
||||||
|
import { Ledger, LedgerV1, LedgerVersionMap } from '../ledger/Ledger'
|
||||||
import { LedgerEntryFilter } from '../ledger/LedgerEntry'
|
import { LedgerEntryFilter } from '../ledger/LedgerEntry'
|
||||||
import { Transaction, TransactionAndMetadata } from '../transactions'
|
import { Transaction, TransactionAndMetadata } from '../transactions'
|
||||||
import { TransactionMetadata } from '../transactions/metadata'
|
import { TransactionMetadata } from '../transactions/metadata'
|
||||||
@@ -202,7 +203,13 @@ export interface LedgerQueueData {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface LedgerBinary
|
export interface LedgerBinary
|
||||||
extends Omit<Omit<Ledger, 'transactions'>, 'accountState'> {
|
extends Omit<Ledger, 'transactions' | 'accountState'> {
|
||||||
|
accountState?: string[]
|
||||||
|
transactions?: string[]
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface LedgerBinaryV1
|
||||||
|
extends Omit<LedgerV1, 'transactions' | 'accountState'> {
|
||||||
accountState?: string[]
|
accountState?: string[]
|
||||||
transactions?: string[]
|
transactions?: string[]
|
||||||
}
|
}
|
||||||
@@ -231,6 +238,11 @@ interface LedgerResponseResult extends LedgerResponseBase {
|
|||||||
ledger: LedgerBinary
|
ledger: LedgerBinary
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface LedgerV1ResponseResult extends LedgerResponseBase {
|
||||||
|
/** The complete header data of this {@link Ledger}. */
|
||||||
|
ledger: LedgerBinaryV1
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Response expected from a {@link LedgerRequest}.
|
* Response expected from a {@link LedgerRequest}.
|
||||||
* This is the default request response, triggered when `expand` and `binary` are both false.
|
* This is the default request response, triggered when `expand` and `binary` are both false.
|
||||||
@@ -241,9 +253,31 @@ export interface LedgerResponse extends BaseResponse {
|
|||||||
result: LedgerResponseResult
|
result: LedgerResponseResult
|
||||||
}
|
}
|
||||||
|
|
||||||
interface LedgerResponseExpandedResult extends LedgerResponseBase {
|
/**
|
||||||
|
* Response expected from a {@link LedgerRequest}.
|
||||||
|
* This is the default request response, triggered when `expand` and `binary` are both false.
|
||||||
|
* This is the response for API version 1.
|
||||||
|
*
|
||||||
|
* @category ResponsesV1
|
||||||
|
*/
|
||||||
|
export interface LedgerV1Response extends BaseResponse {
|
||||||
|
result: LedgerV1ResponseResult
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the response type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type LedgerVersionResponseMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1 ? LedgerV1Response : LedgerResponse
|
||||||
|
|
||||||
|
interface LedgerResponseExpandedResult<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> extends LedgerResponseBase {
|
||||||
/** The complete header data of this {@link Ledger}. */
|
/** The complete header data of this {@link Ledger}. */
|
||||||
ledger: Ledger
|
ledger: LedgerVersionMap<Version>
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -254,6 +288,8 @@ interface LedgerResponseExpandedResult extends LedgerResponseBase {
|
|||||||
*
|
*
|
||||||
* @category Responses
|
* @category Responses
|
||||||
*/
|
*/
|
||||||
export interface LedgerResponseExpanded extends BaseResponse {
|
export interface LedgerResponseExpanded<
|
||||||
result: LedgerResponseExpandedResult
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> extends BaseResponse {
|
||||||
|
result: LedgerResponseExpandedResult<Version>
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,6 +21,22 @@ import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
|||||||
*/
|
*/
|
||||||
export interface LedgerEntryRequest extends BaseRequest, LookupByLedgerRequest {
|
export interface LedgerEntryRequest extends BaseRequest, LookupByLedgerRequest {
|
||||||
command: 'ledger_entry'
|
command: 'ledger_entry'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve a MPTokenIssuance object from the ledger.
|
||||||
|
*/
|
||||||
|
mpt_issuance?: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve a MPToken object from the ledger.
|
||||||
|
*/
|
||||||
|
mptoken?:
|
||||||
|
| {
|
||||||
|
mpt_issuance_id: string
|
||||||
|
account: string
|
||||||
|
}
|
||||||
|
| string
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve an Automated Market Maker (AMM) object from the ledger.
|
* Retrieve an Automated Market Maker (AMM) object from the ledger.
|
||||||
* This is similar to amm_info method, but the ledger_entry version returns only the ledger entry as stored.
|
* This is similar to amm_info method, but the ledger_entry version returns only the ledger entry as stored.
|
||||||
@@ -35,7 +51,14 @@ export interface LedgerEntryRequest extends BaseRequest, LookupByLedgerRequest {
|
|||||||
issuer?: string
|
issuer?: string
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* (Optional) If set to true and the queried object has been deleted,
|
||||||
|
* return its complete data prior to its deletion.
|
||||||
|
* If set to false or not provided and the queried object has been deleted,
|
||||||
|
* return objectNotFound (current behavior).
|
||||||
|
* This parameter is supported only by Clio servers
|
||||||
|
*/
|
||||||
|
include_deleted?: boolean
|
||||||
/**
|
/**
|
||||||
* If true, return the requested ledger object's contents as a hex string in
|
* If true, return the requested ledger object's contents as a hex string in
|
||||||
* the XRP Ledger's binary format. Otherwise, return data in JSON format. The
|
* the XRP Ledger's binary format. Otherwise, return data in JSON format. The
|
||||||
@@ -60,6 +83,23 @@ export interface LedgerEntryRequest extends BaseRequest, LookupByLedgerRequest {
|
|||||||
/** The object ID of a Check object to retrieve. */
|
/** The object ID of a Check object to retrieve. */
|
||||||
check?: string
|
check?: string
|
||||||
|
|
||||||
|
/* Specify the Credential to retrieve. If a string, must be the ledger entry ID of
|
||||||
|
* the entry, as hexadecimal. If an object, requires subject, issuer, and
|
||||||
|
* credential_type sub-fields.
|
||||||
|
*/
|
||||||
|
credential?:
|
||||||
|
| {
|
||||||
|
/** The account that is the subject of the credential. */
|
||||||
|
subject: string
|
||||||
|
|
||||||
|
/** The account that issued the credential. */
|
||||||
|
issuer: string
|
||||||
|
|
||||||
|
/** The type of the credential, as issued. */
|
||||||
|
credentialType: string
|
||||||
|
}
|
||||||
|
| string
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Specify a DepositPreauth object to retrieve. If a string, must be the
|
* Specify a DepositPreauth object to retrieve. If a string, must be the
|
||||||
* object ID of the DepositPreauth object, as hexadecimal. If an object,
|
* object ID of the DepositPreauth object, as hexadecimal. If an object,
|
||||||
@@ -204,5 +244,9 @@ export interface LedgerEntryResponse<T = LedgerEntry> extends BaseResponse {
|
|||||||
/** The binary representation of the ledger object, as hexadecimal. */
|
/** The binary representation of the ledger object, as hexadecimal. */
|
||||||
node_binary?: string
|
node_binary?: string
|
||||||
validated?: boolean
|
validated?: boolean
|
||||||
|
/**
|
||||||
|
* (Optional) Indicates the ledger index at which the object was deleted.
|
||||||
|
*/
|
||||||
|
deleted_ledger_index?: number
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
68
packages/xrpl/src/models/methods/nftsByIssuer.ts
Normal file
68
packages/xrpl/src/models/methods/nftsByIssuer.ts
Normal file
@@ -0,0 +1,68 @@
|
|||||||
|
import { NFToken } from '../common'
|
||||||
|
|
||||||
|
import { BaseRequest, BaseResponse, LookupByLedgerRequest } from './baseMethod'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The nfts_by_issuer method returns a list of NFTokens issued by the account.
|
||||||
|
* The order of the NFTs is not associated with the date the NFTs were minted.
|
||||||
|
* Expects a response in the form of a {@link
|
||||||
|
* NFTsByIssuerResponse}.
|
||||||
|
*
|
||||||
|
* @category Requests
|
||||||
|
*/
|
||||||
|
export interface NFTsByIssuerRequest
|
||||||
|
extends BaseRequest,
|
||||||
|
LookupByLedgerRequest {
|
||||||
|
command: 'nfts_by_issuer'
|
||||||
|
/**
|
||||||
|
* A unique identifier for the account, most commonly the account's address
|
||||||
|
*/
|
||||||
|
issuer: string
|
||||||
|
/**
|
||||||
|
* Value from a previous paginated response. Resume retrieving data where
|
||||||
|
* that response left off. This value is stable even if there is a change in
|
||||||
|
* the server's range of available ledgers.
|
||||||
|
*/
|
||||||
|
marker?: unknown
|
||||||
|
/**
|
||||||
|
* Filter NFTs issued by this issuer that have this taxon.
|
||||||
|
*/
|
||||||
|
nft_taxon?: number
|
||||||
|
/**
|
||||||
|
* Default varies. Limit the number of transactions to retrieve. The server
|
||||||
|
* is not required to honor this value.
|
||||||
|
*/
|
||||||
|
limit?: number
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Expected response from an {@link NFTsByIssuerRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export interface NFTsByIssuerResponse extends BaseResponse {
|
||||||
|
result: {
|
||||||
|
/**
|
||||||
|
* The unique identifier for the account, most commonly the account's address
|
||||||
|
*/
|
||||||
|
issuer: string
|
||||||
|
/**
|
||||||
|
* A list of NFTs issued by the account.
|
||||||
|
* The order of the NFTs is not associated with the date the NFTs were minted.
|
||||||
|
*/
|
||||||
|
nfts: NFToken[]
|
||||||
|
/**
|
||||||
|
* Server-defined value indicating the response is paginated. Pass this
|
||||||
|
* to the next call to resume where this call left off.
|
||||||
|
*/
|
||||||
|
marker?: unknown
|
||||||
|
/**
|
||||||
|
* The limit value used in the request.
|
||||||
|
*/
|
||||||
|
limit?: number
|
||||||
|
/**
|
||||||
|
* Use to filter NFTs issued by this issuer that have this taxon.
|
||||||
|
*/
|
||||||
|
nft_taxon?: number
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -51,6 +51,7 @@ export interface ServerStateResponse extends BaseResponse {
|
|||||||
load_factor_fee_queue?: number
|
load_factor_fee_queue?: number
|
||||||
load_factor_fee_reference?: number
|
load_factor_fee_reference?: number
|
||||||
load_factor_server?: number
|
load_factor_server?: number
|
||||||
|
network_id: number
|
||||||
peer_disconnects?: string
|
peer_disconnects?: string
|
||||||
peer_disconnects_resources?: string
|
peer_disconnects_resources?: string
|
||||||
peers: number
|
peers: number
|
||||||
|
|||||||
88
packages/xrpl/src/models/methods/simulate.ts
Normal file
88
packages/xrpl/src/models/methods/simulate.ts
Normal file
@@ -0,0 +1,88 @@
|
|||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
Transaction,
|
||||||
|
TransactionMetadata,
|
||||||
|
} from '../transactions'
|
||||||
|
|
||||||
|
import { BaseRequest, BaseResponse } from './baseMethod'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The `simulate` method simulates a transaction without submitting it to the network.
|
||||||
|
* Returns a {@link SimulateResponse}.
|
||||||
|
*
|
||||||
|
* @category Requests
|
||||||
|
*/
|
||||||
|
export type SimulateRequest = BaseRequest & {
|
||||||
|
command: 'simulate'
|
||||||
|
|
||||||
|
binary?: boolean
|
||||||
|
} & (
|
||||||
|
| {
|
||||||
|
tx_blob: string
|
||||||
|
tx_json?: never
|
||||||
|
}
|
||||||
|
| {
|
||||||
|
tx_json: Transaction
|
||||||
|
tx_blob?: never
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
export type SimulateBinaryRequest = SimulateRequest & {
|
||||||
|
binary: true
|
||||||
|
}
|
||||||
|
|
||||||
|
export type SimulateJsonRequest = SimulateRequest & {
|
||||||
|
binary?: false
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from an {@link SimulateRequest}.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type SimulateResponse = SimulateJsonResponse | SimulateBinaryResponse
|
||||||
|
|
||||||
|
export interface SimulateBinaryResponse extends BaseResponse {
|
||||||
|
result: {
|
||||||
|
applied: false
|
||||||
|
|
||||||
|
engine_result: string
|
||||||
|
|
||||||
|
engine_result_code: number
|
||||||
|
|
||||||
|
engine_result_message: string
|
||||||
|
|
||||||
|
tx_blob: string
|
||||||
|
|
||||||
|
meta_blob: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The ledger index of the ledger version that was used to generate this
|
||||||
|
* response.
|
||||||
|
*/
|
||||||
|
ledger_index: number
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface SimulateJsonResponse<T extends BaseTransaction = Transaction>
|
||||||
|
extends BaseResponse {
|
||||||
|
result: {
|
||||||
|
applied: false
|
||||||
|
|
||||||
|
engine_result: string
|
||||||
|
|
||||||
|
engine_result_code: number
|
||||||
|
|
||||||
|
engine_result_message: string
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The ledger index of the ledger version that was used to generate this
|
||||||
|
* response.
|
||||||
|
*/
|
||||||
|
ledger_index: number
|
||||||
|
|
||||||
|
tx_json: T
|
||||||
|
|
||||||
|
meta?: TransactionMetadata<T>
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,3 +1,4 @@
|
|||||||
|
import { APIVersion, DEFAULT_API_VERSION, RIPPLED_API_V1 } from '../common'
|
||||||
import { Transaction } from '../transactions'
|
import { Transaction } from '../transactions'
|
||||||
|
|
||||||
import { BaseRequest, BaseResponse } from './baseMethod'
|
import { BaseRequest, BaseResponse } from './baseMethod'
|
||||||
@@ -24,28 +25,59 @@ export interface SubmitMultisignedRequest extends BaseRequest {
|
|||||||
fail_hard?: boolean
|
fail_hard?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Common properties for multisigned transaction responses.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
interface BaseSubmitMultisignedResult {
|
||||||
|
/**
|
||||||
|
* Code indicating the preliminary result of the transaction, for example.
|
||||||
|
* `tesSUCCESS`.
|
||||||
|
*/
|
||||||
|
engine_result: string
|
||||||
|
/**
|
||||||
|
* Numeric code indicating the preliminary result of the transaction,
|
||||||
|
* directly correlated to `engine_result`.
|
||||||
|
*/
|
||||||
|
engine_result_code: number
|
||||||
|
/** Human-readable explanation of the preliminary transaction result. */
|
||||||
|
engine_result_message: string
|
||||||
|
/** The complete transaction in hex string format. */
|
||||||
|
tx_blob: string
|
||||||
|
/** The complete transaction in JSON format. */
|
||||||
|
tx_json: Transaction
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Response expected from a {@link SubmitMultisignedRequest}.
|
* Response expected from a {@link SubmitMultisignedRequest}.
|
||||||
*
|
*
|
||||||
* @category Responses
|
* @category Responses
|
||||||
*/
|
*/
|
||||||
export interface SubmitMultisignedResponse extends BaseResponse {
|
export interface SubmitMultisignedResponse extends BaseResponse {
|
||||||
result: {
|
result: BaseSubmitMultisignedResult & {
|
||||||
/**
|
hash?: string
|
||||||
* Code indicating the preliminary result of the transaction, for example.
|
}
|
||||||
* `tesSUCCESS` .
|
}
|
||||||
*/
|
|
||||||
engine_result: string
|
/**
|
||||||
/**
|
* Response expected from a {@link SubmitMultisignedRequest} using api_version 1.
|
||||||
* Numeric code indicating the preliminary result of the transaction,
|
*
|
||||||
* directly correlated to `engine_result`.
|
* @category ResponsesV1
|
||||||
*/
|
*/
|
||||||
engine_result_code: number
|
export interface SubmitMultisignedV1Response extends BaseResponse {
|
||||||
/** Human-readable explanation of the preliminary transaction result. */
|
result: BaseSubmitMultisignedResult & {
|
||||||
engine_result_message: string
|
|
||||||
/** The complete transaction in hex string format. */
|
|
||||||
tx_blob: string
|
|
||||||
/** The complete transaction in JSON format. */
|
|
||||||
tx_json: Transaction & { hash?: string }
|
tx_json: Transaction & { hash?: string }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the response type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type SubmitMultisignedVersionResponseMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1
|
||||||
|
? SubmitMultisignedV1Response
|
||||||
|
: SubmitMultisignedResponse
|
||||||
|
|||||||
@@ -4,6 +4,10 @@ import type {
|
|||||||
Path,
|
Path,
|
||||||
StreamType,
|
StreamType,
|
||||||
ResponseOnlyTxInfo,
|
ResponseOnlyTxInfo,
|
||||||
|
APIVersion,
|
||||||
|
DEFAULT_API_VERSION,
|
||||||
|
RIPPLED_API_V1,
|
||||||
|
RIPPLED_API_V2,
|
||||||
} from '../common'
|
} from '../common'
|
||||||
import { Offer } from '../ledger'
|
import { Offer } from '../ledger'
|
||||||
import { OfferCreate, Transaction } from '../transactions'
|
import { OfferCreate, Transaction } from '../transactions'
|
||||||
@@ -262,9 +266,16 @@ export interface ValidationStream extends BaseStream {
|
|||||||
*
|
*
|
||||||
* @category Streams
|
* @category Streams
|
||||||
*/
|
*/
|
||||||
export interface TransactionStream extends BaseStream {
|
interface TransactionStreamBase<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> extends BaseStream {
|
||||||
status: string
|
status: string
|
||||||
type: 'transaction'
|
type: 'transaction'
|
||||||
|
/**
|
||||||
|
* The approximate time this ledger was closed, in date time string format.
|
||||||
|
* Always uses the UTC time zone.
|
||||||
|
*/
|
||||||
|
close_time_iso: string
|
||||||
/** String Transaction result code. */
|
/** String Transaction result code. */
|
||||||
engine_result: string
|
engine_result: string
|
||||||
/** Numeric transaction response code, if applicable. */
|
/** Numeric transaction response code, if applicable. */
|
||||||
@@ -285,8 +296,14 @@ export interface TransactionStream extends BaseStream {
|
|||||||
* in detail.
|
* in detail.
|
||||||
*/
|
*/
|
||||||
meta?: TransactionMetadata
|
meta?: TransactionMetadata
|
||||||
/** The definition of the transaction in JSON format. */
|
/** JSON object defining the transaction. */
|
||||||
transaction: Transaction & ResponseOnlyTxInfo
|
tx_json?: Version extends typeof RIPPLED_API_V2
|
||||||
|
? Transaction & ResponseOnlyTxInfo
|
||||||
|
: never
|
||||||
|
/** JSON object defining the transaction in rippled API v1. */
|
||||||
|
transaction?: Version extends typeof RIPPLED_API_V1
|
||||||
|
? Transaction & ResponseOnlyTxInfo
|
||||||
|
: never
|
||||||
/**
|
/**
|
||||||
* If true, this transaction is included in a validated ledger and its
|
* If true, this transaction is included in a validated ledger and its
|
||||||
* outcome is final. Responses from the transaction stream should always be
|
* outcome is final. Responses from the transaction stream should always be
|
||||||
@@ -296,6 +313,20 @@ export interface TransactionStream extends BaseStream {
|
|||||||
warnings?: Array<{ id: number; message: string }>
|
warnings?: Array<{ id: number; message: string }>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Expected response from an {@link AccountTxRequest}.
|
||||||
|
*
|
||||||
|
* @category Streams
|
||||||
|
*/
|
||||||
|
export type TransactionStream = TransactionStreamBase
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Expected response from an {@link AccountTxRequest} with `api_version` set to 1.
|
||||||
|
*
|
||||||
|
* @category Streams
|
||||||
|
*/
|
||||||
|
export type TransactionV1Stream = TransactionStreamBase<typeof RIPPLED_API_V1>
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The admin-only `peer_status` stream reports a large amount of information on
|
* The admin-only `peer_status` stream reports a large amount of information on
|
||||||
* the activities of other rippled servers to which this server is connected, in
|
* the activities of other rippled servers to which this server is connected, in
|
||||||
|
|||||||
@@ -1,3 +1,9 @@
|
|||||||
|
import {
|
||||||
|
APIVersion,
|
||||||
|
DEFAULT_API_VERSION,
|
||||||
|
RIPPLED_API_V1,
|
||||||
|
RIPPLED_API_V2,
|
||||||
|
} from '../common'
|
||||||
import { Transaction, TransactionMetadata } from '../transactions'
|
import { Transaction, TransactionMetadata } from '../transactions'
|
||||||
import { BaseTransaction } from '../transactions/common'
|
import { BaseTransaction } from '../transactions/common'
|
||||||
|
|
||||||
@@ -41,6 +47,47 @@ export interface TxRequest extends BaseRequest {
|
|||||||
max_ledger?: number
|
max_ledger?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Common properties of transaction responses.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
interface BaseTxResult<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
T extends BaseTransaction = Transaction,
|
||||||
|
> {
|
||||||
|
/** The SHA-512 hash of the transaction. */
|
||||||
|
hash: string
|
||||||
|
/**
|
||||||
|
* The Concise Transaction Identifier of the transaction (16-byte hex string)
|
||||||
|
*/
|
||||||
|
ctid?: string
|
||||||
|
/** The ledger index of the ledger that includes this transaction. */
|
||||||
|
ledger_index?: number
|
||||||
|
/** Unique hashed string Transaction metadata blob, which describes the results of the transaction.
|
||||||
|
* Can be undefined if a transaction has not been validated yet. This field is omitted if binary
|
||||||
|
* binary format is not requested. */
|
||||||
|
meta_blob?: Version extends typeof RIPPLED_API_V2
|
||||||
|
? TransactionMetadata<T> | string
|
||||||
|
: never
|
||||||
|
/** Transaction metadata, which describes the results of the transaction.
|
||||||
|
* Can be undefined if a transaction has not been validated yet. */
|
||||||
|
meta?: TransactionMetadata<T> | string
|
||||||
|
/**
|
||||||
|
* If true, this data comes from a validated ledger version; if omitted or.
|
||||||
|
* Set to false, this data is not final.
|
||||||
|
*/
|
||||||
|
validated?: boolean
|
||||||
|
/**
|
||||||
|
* The time the transaction was closed, in seconds since the Ripple Epoch.
|
||||||
|
*/
|
||||||
|
close_time_iso?: string
|
||||||
|
/**
|
||||||
|
* This number measures the number of seconds since the "Ripple Epoch" of January 1, 2000 (00:00 UTC)
|
||||||
|
*/
|
||||||
|
date?: number
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Response expected from a {@link TxRequest}.
|
* Response expected from a {@link TxRequest}.
|
||||||
*
|
*
|
||||||
@@ -48,28 +95,7 @@ export interface TxRequest extends BaseRequest {
|
|||||||
*/
|
*/
|
||||||
export interface TxResponse<T extends BaseTransaction = Transaction>
|
export interface TxResponse<T extends BaseTransaction = Transaction>
|
||||||
extends BaseResponse {
|
extends BaseResponse {
|
||||||
result: {
|
result: BaseTxResult<typeof RIPPLED_API_V2, T> & { tx_json: T }
|
||||||
/** The SHA-512 hash of the transaction. */
|
|
||||||
hash: string
|
|
||||||
/**
|
|
||||||
* The Concise Transaction Identifier of the transaction (16-byte hex string)
|
|
||||||
*/
|
|
||||||
ctid?: string
|
|
||||||
/** The ledger index of the ledger that includes this transaction. */
|
|
||||||
ledger_index?: number
|
|
||||||
/** Transaction metadata, which describes the results of the transaction.
|
|
||||||
* Can be undefined if a transaction has not been validated yet. */
|
|
||||||
meta?: TransactionMetadata<T> | string
|
|
||||||
/**
|
|
||||||
* If true, this data comes from a validated ledger version; if omitted or.
|
|
||||||
* Set to false, this data is not final.
|
|
||||||
*/
|
|
||||||
validated?: boolean
|
|
||||||
/**
|
|
||||||
* This number measures the number of seconds since the "Ripple Epoch" of January 1, 2000 (00:00 UTC)
|
|
||||||
*/
|
|
||||||
date?: number
|
|
||||||
} & T
|
|
||||||
/**
|
/**
|
||||||
* If true, the server was able to search all of the specified ledger
|
* If true, the server was able to search all of the specified ledger
|
||||||
* versions, and the transaction was in none of them. If false, the server did
|
* versions, and the transaction was in none of them. If false, the server did
|
||||||
@@ -78,3 +104,29 @@ export interface TxResponse<T extends BaseTransaction = Transaction>
|
|||||||
*/
|
*/
|
||||||
searched_all?: boolean
|
searched_all?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Response expected from a {@link TxRequest} using API version 1.
|
||||||
|
*
|
||||||
|
* @category ResponsesV1
|
||||||
|
*/
|
||||||
|
export interface TxV1Response<T extends BaseTransaction = Transaction>
|
||||||
|
extends BaseResponse {
|
||||||
|
result: BaseTxResult<typeof RIPPLED_API_V1, T> & T
|
||||||
|
/**
|
||||||
|
* If true, the server was able to search all of the specified ledger
|
||||||
|
* versions, and the transaction was in none of them. If false, the server did
|
||||||
|
* not have all of the specified ledger versions available, so it is not sure.
|
||||||
|
* If one of them might contain the transaction.
|
||||||
|
*/
|
||||||
|
searched_all?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Type to map between the API version and the response type.
|
||||||
|
*
|
||||||
|
* @category Responses
|
||||||
|
*/
|
||||||
|
export type TxVersionResponseMap<
|
||||||
|
Version extends APIVersion = typeof DEFAULT_API_VERSION,
|
||||||
|
> = Version extends typeof RIPPLED_API_V1 ? TxV1Response : TxResponse
|
||||||
|
|||||||
120
packages/xrpl/src/models/transactions/AMMClawback.ts
Normal file
120
packages/xrpl/src/models/transactions/AMMClawback.ts
Normal file
@@ -0,0 +1,120 @@
|
|||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
import { Currency, IssuedCurrency, IssuedCurrencyAmount } from '../common'
|
||||||
|
|
||||||
|
import {
|
||||||
|
Account,
|
||||||
|
BaseTransaction,
|
||||||
|
GlobalFlags,
|
||||||
|
isAccount,
|
||||||
|
isAmount,
|
||||||
|
isCurrency,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateOptionalField,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Enum representing values for AMMClawback Transaction Flags.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export enum AMMClawbackFlags {
|
||||||
|
tfClawTwoAssets = 0x00000001,
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map of flags to boolean values representing {@link AMMClawback} transaction
|
||||||
|
* flags.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export interface AMMClawbackFlagsInterface extends GlobalFlags {
|
||||||
|
tfClawTwoAssets?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Claw back tokens from a holder that has deposited your issued tokens into an AMM pool.
|
||||||
|
*
|
||||||
|
* Clawback is disabled by default. To use clawback, you must send an AccountSet transaction to enable the
|
||||||
|
* Allow Trust Line Clawback setting. An issuer with any existing tokens cannot enable clawback. You can
|
||||||
|
* only enable Allow Trust Line Clawback if you have a completely empty owner directory, meaning you must
|
||||||
|
* do so before you set up any trust lines, offers, escrows, payment channels, checks, or signer lists.
|
||||||
|
* After you enable clawback, it cannot reverted: the account permanently gains the ability to claw back
|
||||||
|
* issued assets on trust lines.
|
||||||
|
*/
|
||||||
|
export interface AMMClawback extends BaseTransaction {
|
||||||
|
TransactionType: 'AMMClawback'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The account holding the asset to be clawed back.
|
||||||
|
*/
|
||||||
|
Holder: Account
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Specifies the asset that the issuer wants to claw back from the AMM pool.
|
||||||
|
* In JSON, this is an object with currency and issuer fields. The issuer field must match with Account.
|
||||||
|
*/
|
||||||
|
Asset: IssuedCurrency
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Specifies the other asset in the AMM's pool. In JSON, this is an object with currency and
|
||||||
|
* issuer fields (omit issuer for XRP).
|
||||||
|
*/
|
||||||
|
Asset2: Currency
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The maximum amount to claw back from the AMM account. The currency and issuer subfields should match
|
||||||
|
* the Asset subfields. If this field isn't specified, or the value subfield exceeds the holder's available
|
||||||
|
* tokens in the AMM, all of the holder's tokens will be clawed back.
|
||||||
|
*/
|
||||||
|
Amount?: IssuedCurrencyAmount
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an AMMClawback at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An AMMClawback Transaction.
|
||||||
|
* @throws {ValidationError} When the transaction is malformed.
|
||||||
|
*/
|
||||||
|
export function validateAMMClawback(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Holder', isAccount)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Asset', isCurrency)
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- required
|
||||||
|
const asset = tx.Asset as IssuedCurrency
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- required
|
||||||
|
const amount = tx.Amount as IssuedCurrencyAmount
|
||||||
|
|
||||||
|
if (tx.Holder === asset.issuer) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'AMMClawback: Holder and Asset.issuer must be distinct',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tx.Account !== asset.issuer) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'AMMClawback: Account must be the same as Asset.issuer',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Asset2', isCurrency)
|
||||||
|
|
||||||
|
validateOptionalField(tx, 'Amount', isAmount)
|
||||||
|
|
||||||
|
if (tx.Amount != null) {
|
||||||
|
if (amount.currency !== asset.currency) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'AMMClawback: Amount.currency must match Asset.currency',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (amount.issuer !== asset.issuer) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'AMMClawback: Amount.issuer must match Amount.issuer',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -21,6 +21,7 @@ export enum AMMDepositFlags {
|
|||||||
tfTwoAsset = 0x00100000,
|
tfTwoAsset = 0x00100000,
|
||||||
tfOneAssetLPToken = 0x00200000,
|
tfOneAssetLPToken = 0x00200000,
|
||||||
tfLimitLPToken = 0x00400000,
|
tfLimitLPToken = 0x00400000,
|
||||||
|
tfTwoAssetIfEmpty = 0x00800000,
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface AMMDepositFlagsInterface extends GlobalFlags {
|
export interface AMMDepositFlagsInterface extends GlobalFlags {
|
||||||
@@ -29,6 +30,7 @@ export interface AMMDepositFlagsInterface extends GlobalFlags {
|
|||||||
tfTwoAsset?: boolean
|
tfTwoAsset?: boolean
|
||||||
tfOneAssetLPToken?: boolean
|
tfOneAssetLPToken?: boolean
|
||||||
tfLimitLPToken?: boolean
|
tfLimitLPToken?: boolean
|
||||||
|
tfTwoAssetIfEmpty?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
44
packages/xrpl/src/models/transactions/CredentialAccept.ts
Normal file
44
packages/xrpl/src/models/transactions/CredentialAccept.ts
Normal file
@@ -0,0 +1,44 @@
|
|||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateCredentialType,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Accepts a credential issued to the Account (i.e. the Account is the Subject of the Credential object).
|
||||||
|
* Credentials are represented in hex. Whilst they are allowed a maximum length of 64
|
||||||
|
* bytes, every byte requires 2 hex characters for representation.
|
||||||
|
* The credential is not considered valid until it has been transferred/accepted.
|
||||||
|
*
|
||||||
|
* @category Transaction Models
|
||||||
|
* */
|
||||||
|
export interface CredentialAccept extends BaseTransaction {
|
||||||
|
TransactionType: 'CredentialAccept'
|
||||||
|
|
||||||
|
/** The subject of the credential. */
|
||||||
|
Account: string
|
||||||
|
|
||||||
|
/** The issuer of the credential. */
|
||||||
|
Issuer: string
|
||||||
|
|
||||||
|
/** A hex-encoded value to identify the type of credential from the issuer. */
|
||||||
|
CredentialType: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of a CredentialAccept at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - A CredentialAccept Transaction.
|
||||||
|
* @throws When the CredentialAccept is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateCredentialAccept(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Account', isString)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Issuer', isString)
|
||||||
|
|
||||||
|
validateCredentialType(tx)
|
||||||
|
}
|
||||||
81
packages/xrpl/src/models/transactions/CredentialCreate.ts
Normal file
81
packages/xrpl/src/models/transactions/CredentialCreate.ts
Normal file
@@ -0,0 +1,81 @@
|
|||||||
|
import { HEX_REGEX } from '@xrplf/isomorphic/utils'
|
||||||
|
|
||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
|
||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isNumber,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateCredentialType,
|
||||||
|
validateOptionalField,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
const MAX_URI_LENGTH = 256
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a Credential object. It must be sent by the issuer.
|
||||||
|
*
|
||||||
|
* @category Transaction Models
|
||||||
|
* */
|
||||||
|
export interface CredentialCreate extends BaseTransaction {
|
||||||
|
TransactionType: 'CredentialCreate'
|
||||||
|
|
||||||
|
/** The issuer of the credential. */
|
||||||
|
Account: string
|
||||||
|
|
||||||
|
/** The subject of the credential. */
|
||||||
|
Subject: string
|
||||||
|
|
||||||
|
/** A hex-encoded value to identify the type of credential from the issuer. */
|
||||||
|
CredentialType: string
|
||||||
|
|
||||||
|
/** Credential expiration. */
|
||||||
|
Expiration?: number
|
||||||
|
|
||||||
|
/** Additional data about the credential (such as a link to the VC document). */
|
||||||
|
URI?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of a CredentialCreate at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - A CredentialCreate Transaction.
|
||||||
|
* @throws When the CredentialCreate is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateCredentialCreate(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Account', isString)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Subject', isString)
|
||||||
|
|
||||||
|
validateCredentialType(tx)
|
||||||
|
|
||||||
|
validateOptionalField(tx, 'Expiration', isNumber)
|
||||||
|
|
||||||
|
validateURI(tx.URI)
|
||||||
|
}
|
||||||
|
|
||||||
|
function validateURI(URI: unknown): void {
|
||||||
|
if (URI === undefined) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof URI !== 'string') {
|
||||||
|
throw new ValidationError('CredentialCreate: invalid field URI')
|
||||||
|
}
|
||||||
|
|
||||||
|
if (URI.length === 0) {
|
||||||
|
throw new ValidationError('CredentialCreate: URI cannot be an empty string')
|
||||||
|
} else if (URI.length > MAX_URI_LENGTH) {
|
||||||
|
throw new ValidationError(
|
||||||
|
`CredentialCreate: URI length must be <= ${MAX_URI_LENGTH}`,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!HEX_REGEX.test(URI)) {
|
||||||
|
throw new ValidationError('CredentialCreate: URI must be encoded in hex')
|
||||||
|
}
|
||||||
|
}
|
||||||
55
packages/xrpl/src/models/transactions/CredentialDelete.ts
Normal file
55
packages/xrpl/src/models/transactions/CredentialDelete.ts
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
|
||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateCredentialType,
|
||||||
|
validateOptionalField,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Deletes a Credential object.
|
||||||
|
*
|
||||||
|
* @category Transaction Models
|
||||||
|
* */
|
||||||
|
export interface CredentialDelete extends BaseTransaction {
|
||||||
|
TransactionType: 'CredentialDelete'
|
||||||
|
|
||||||
|
/** The transaction submitter. */
|
||||||
|
Account: string
|
||||||
|
|
||||||
|
/** A hex-encoded value to identify the type of credential from the issuer. */
|
||||||
|
CredentialType: string
|
||||||
|
|
||||||
|
/** The person that the credential is for. If omitted, Account is assumed to be the subject. */
|
||||||
|
Subject?: string
|
||||||
|
|
||||||
|
/** The issuer of the credential. If omitted, Account is assumed to be the issuer. */
|
||||||
|
Issuer?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of a CredentialDelete at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - A CredentialDelete Transaction.
|
||||||
|
* @throws When the CredentialDelete is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateCredentialDelete(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
|
||||||
|
if (!tx.Subject && !tx.Issuer) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'CredentialDelete: either `Issuer` or `Subject` must be provided',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'Account', isString)
|
||||||
|
|
||||||
|
validateCredentialType(tx)
|
||||||
|
|
||||||
|
validateOptionalField(tx, 'Subject', isString)
|
||||||
|
|
||||||
|
validateOptionalField(tx, 'Issuer', isString)
|
||||||
|
}
|
||||||
67
packages/xrpl/src/models/transactions/MPTokenAuthorize.ts
Normal file
67
packages/xrpl/src/models/transactions/MPTokenAuthorize.ts
Normal file
@@ -0,0 +1,67 @@
|
|||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateRequiredField,
|
||||||
|
Account,
|
||||||
|
validateOptionalField,
|
||||||
|
isAccount,
|
||||||
|
GlobalFlags,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Transaction Flags for an MPTokenAuthorize Transaction.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export enum MPTokenAuthorizeFlags {
|
||||||
|
/**
|
||||||
|
* If set and transaction is submitted by a holder, it indicates that the holder no
|
||||||
|
* longer wants to hold the MPToken, which will be deleted as a result. If the the holder's
|
||||||
|
* MPToken has non-zero balance while trying to set this flag, the transaction will fail. On
|
||||||
|
* the other hand, if set and transaction is submitted by an issuer, it would mean that the
|
||||||
|
* issuer wants to unauthorize the holder (only applicable for allow-listing),
|
||||||
|
* which would unset the lsfMPTAuthorized flag on the MPToken.
|
||||||
|
*/
|
||||||
|
tfMPTUnauthorize = 0x00000001,
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map of flags to boolean values representing {@link MPTokenAuthorize} transaction
|
||||||
|
* flags.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export interface MPTokenAuthorizeFlagsInterface extends GlobalFlags {
|
||||||
|
tfMPTUnauthorize?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The MPTokenAuthorize transaction is used to globally lock/unlock a MPTokenIssuance,
|
||||||
|
* or lock/unlock an individual's MPToken.
|
||||||
|
*/
|
||||||
|
export interface MPTokenAuthorize extends BaseTransaction {
|
||||||
|
TransactionType: 'MPTokenAuthorize'
|
||||||
|
/**
|
||||||
|
* Identifies the MPTokenIssuance
|
||||||
|
*/
|
||||||
|
MPTokenIssuanceID: string
|
||||||
|
/**
|
||||||
|
* An optional XRPL Address of an individual token holder balance to lock/unlock.
|
||||||
|
* If omitted, this transaction will apply to all any accounts holding MPTs.
|
||||||
|
*/
|
||||||
|
Holder?: Account
|
||||||
|
Flags?: number | MPTokenAuthorizeFlagsInterface
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an MPTokenAuthorize at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An MPTokenAuthorize Transaction.
|
||||||
|
* @throws When the MPTokenAuthorize is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateMPTokenAuthorize(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
validateRequiredField(tx, 'MPTokenIssuanceID', isString)
|
||||||
|
validateOptionalField(tx, 'Holder', isAccount)
|
||||||
|
}
|
||||||
179
packages/xrpl/src/models/transactions/MPTokenIssuanceCreate.ts
Normal file
179
packages/xrpl/src/models/transactions/MPTokenIssuanceCreate.ts
Normal file
@@ -0,0 +1,179 @@
|
|||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
import { isHex, INTEGER_SANITY_CHECK, isFlagEnabled } from '../utils'
|
||||||
|
|
||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
GlobalFlags,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateOptionalField,
|
||||||
|
isString,
|
||||||
|
isNumber,
|
||||||
|
} from './common'
|
||||||
|
import type { TransactionMetadataBase } from './metadata'
|
||||||
|
|
||||||
|
// 2^63 - 1
|
||||||
|
const MAX_AMT = '9223372036854775807'
|
||||||
|
const MAX_TRANSFER_FEE = 50000
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Transaction Flags for an MPTokenIssuanceCreate Transaction.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export enum MPTokenIssuanceCreateFlags {
|
||||||
|
/**
|
||||||
|
* If set, indicates that the MPT can be locked both individually and globally.
|
||||||
|
* If not set, the MPT cannot be locked in any way.
|
||||||
|
*/
|
||||||
|
tfMPTCanLock = 0x00000002,
|
||||||
|
/**
|
||||||
|
* If set, indicates that individual holders must be authorized.
|
||||||
|
* This enables issuers to limit who can hold their assets.
|
||||||
|
*/
|
||||||
|
tfMPTRequireAuth = 0x00000004,
|
||||||
|
/**
|
||||||
|
* If set, indicates that individual holders can place their balances into an escrow.
|
||||||
|
*/
|
||||||
|
tfMPTCanEscrow = 0x00000008,
|
||||||
|
/**
|
||||||
|
* If set, indicates that individual holders can trade their balances
|
||||||
|
* using the XRP Ledger DEX or AMM.
|
||||||
|
*/
|
||||||
|
tfMPTCanTrade = 0x00000010,
|
||||||
|
/**
|
||||||
|
* If set, indicates that tokens may be transferred to other accounts
|
||||||
|
* that are not the issuer.
|
||||||
|
*/
|
||||||
|
tfMPTCanTransfer = 0x00000020,
|
||||||
|
/**
|
||||||
|
* If set, indicates that the issuer may use the Clawback transaction
|
||||||
|
* to clawback value from individual holders.
|
||||||
|
*/
|
||||||
|
tfMPTCanClawback = 0x00000040,
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map of flags to boolean values representing {@link MPTokenIssuanceCreate} transaction
|
||||||
|
* flags.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export interface MPTokenIssuanceCreateFlagsInterface extends GlobalFlags {
|
||||||
|
tfMPTCanLock?: boolean
|
||||||
|
tfMPTRequireAuth?: boolean
|
||||||
|
tfMPTCanEscrow?: boolean
|
||||||
|
tfMPTCanTrade?: boolean
|
||||||
|
tfMPTCanTransfer?: boolean
|
||||||
|
tfMPTCanClawback?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The MPTokenIssuanceCreate transaction creates a MPTokenIssuance object
|
||||||
|
* and adds it to the relevant directory node of the creator account.
|
||||||
|
* This transaction is the only opportunity an issuer has to specify any token fields
|
||||||
|
* that are defined as immutable (e.g., MPT Flags). If the transaction is successful,
|
||||||
|
* the newly created token will be owned by the account (the creator account) which
|
||||||
|
* executed the transaction.
|
||||||
|
*/
|
||||||
|
export interface MPTokenIssuanceCreate extends BaseTransaction {
|
||||||
|
TransactionType: 'MPTokenIssuanceCreate'
|
||||||
|
/**
|
||||||
|
* An asset scale is the difference, in orders of magnitude, between a standard unit and
|
||||||
|
* a corresponding fractional unit. More formally, the asset scale is a non-negative integer
|
||||||
|
* (0, 1, 2, …) such that one standard unit equals 10^(-scale) of a corresponding
|
||||||
|
* fractional unit. If the fractional unit equals the standard unit, then the asset scale is 0.
|
||||||
|
* Note that this value is optional, and will default to 0 if not supplied.
|
||||||
|
*/
|
||||||
|
AssetScale?: number
|
||||||
|
/**
|
||||||
|
* Specifies the maximum asset amount of this token that should ever be issued.
|
||||||
|
* It is a non-negative integer string that can store a range of up to 63 bits. If not set, the max
|
||||||
|
* amount will default to the largest unsigned 63-bit integer (0x7FFFFFFFFFFFFFFF or 9223372036854775807)
|
||||||
|
*
|
||||||
|
* Example:
|
||||||
|
* ```
|
||||||
|
* MaximumAmount: '9223372036854775807'
|
||||||
|
* ```
|
||||||
|
*/
|
||||||
|
MaximumAmount?: string
|
||||||
|
/**
|
||||||
|
* Specifies the fee to charged by the issuer for secondary sales of the Token,
|
||||||
|
* if such sales are allowed. Valid values for this field are between 0 and 50,000 inclusive,
|
||||||
|
* allowing transfer rates of between 0.000% and 50.000% in increments of 0.001.
|
||||||
|
* The field must NOT be present if the `tfMPTCanTransfer` flag is not set.
|
||||||
|
*/
|
||||||
|
TransferFee?: number
|
||||||
|
/**
|
||||||
|
* Arbitrary metadata about this issuance, in hex format.
|
||||||
|
*/
|
||||||
|
MPTokenMetadata?: string | null
|
||||||
|
Flags?: number | MPTokenIssuanceCreateFlagsInterface
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface MPTokenIssuanceCreateMetadata extends TransactionMetadataBase {
|
||||||
|
mpt_issuance_id?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/* eslint-disable max-lines-per-function -- Not needed to reduce function */
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an MPTokenIssuanceCreate at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An MPTokenIssuanceCreate Transaction.
|
||||||
|
* @throws When the MPTokenIssuanceCreate is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateMPTokenIssuanceCreate(
|
||||||
|
tx: Record<string, unknown>,
|
||||||
|
): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
validateOptionalField(tx, 'MaximumAmount', isString)
|
||||||
|
validateOptionalField(tx, 'MPTokenMetadata', isString)
|
||||||
|
validateOptionalField(tx, 'TransferFee', isNumber)
|
||||||
|
validateOptionalField(tx, 'AssetScale', isNumber)
|
||||||
|
|
||||||
|
if (typeof tx.MPTokenMetadata === 'string' && tx.MPTokenMetadata === '') {
|
||||||
|
throw new ValidationError(
|
||||||
|
'MPTokenIssuanceCreate: MPTokenMetadata must not be empty string',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof tx.MPTokenMetadata === 'string' && !isHex(tx.MPTokenMetadata)) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'MPTokenIssuanceCreate: MPTokenMetadata must be in hex format',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof tx.MaximumAmount === 'string') {
|
||||||
|
if (!INTEGER_SANITY_CHECK.exec(tx.MaximumAmount)) {
|
||||||
|
throw new ValidationError('MPTokenIssuanceCreate: Invalid MaximumAmount')
|
||||||
|
} else if (
|
||||||
|
BigInt(tx.MaximumAmount) > BigInt(MAX_AMT) ||
|
||||||
|
BigInt(tx.MaximumAmount) < BigInt(`0`)
|
||||||
|
) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'MPTokenIssuanceCreate: MaximumAmount out of range',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof tx.TransferFee === 'number') {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Not necessary
|
||||||
|
const flags = tx.Flags as number | MPTokenIssuanceCreateFlagsInterface
|
||||||
|
const isTfMPTCanTransfer =
|
||||||
|
typeof flags === 'number'
|
||||||
|
? isFlagEnabled(flags, MPTokenIssuanceCreateFlags.tfMPTCanTransfer)
|
||||||
|
: flags.tfMPTCanTransfer ?? false
|
||||||
|
|
||||||
|
if (tx.TransferFee < 0 || tx.TransferFee > MAX_TRANSFER_FEE) {
|
||||||
|
throw new ValidationError(
|
||||||
|
`MPTokenIssuanceCreate: TransferFee must be between 0 and ${MAX_TRANSFER_FEE}`,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tx.TransferFee && !isTfMPTCanTransfer) {
|
||||||
|
throw new ValidationError(
|
||||||
|
'MPTokenIssuanceCreate: TransferFee cannot be provided without enabling tfMPTCanTransfer flag',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/* eslint-enable max-lines-per-function */
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The MPTokenIssuanceDestroy transaction is used to remove an MPTokenIssuance object
|
||||||
|
* from the directory node in which it is being held, effectively removing the token
|
||||||
|
* from the ledger. If this operation succeeds, the corresponding
|
||||||
|
* MPTokenIssuance is removed and the owner’s reserve requirement is reduced by one.
|
||||||
|
* This operation must fail if there are any holders who have non-zero balances.
|
||||||
|
*/
|
||||||
|
export interface MPTokenIssuanceDestroy extends BaseTransaction {
|
||||||
|
TransactionType: 'MPTokenIssuanceDestroy'
|
||||||
|
/**
|
||||||
|
* Identifies the MPTokenIssuance object to be removed by the transaction.
|
||||||
|
*/
|
||||||
|
MPTokenIssuanceID: string
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an MPTokenIssuanceDestroy at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An MPTokenIssuanceDestroy Transaction.
|
||||||
|
* @throws When the MPTokenIssuanceDestroy is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateMPTokenIssuanceDestroy(
|
||||||
|
tx: Record<string, unknown>,
|
||||||
|
): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
validateRequiredField(tx, 'MPTokenIssuanceID', isString)
|
||||||
|
}
|
||||||
86
packages/xrpl/src/models/transactions/MPTokenIssuanceSet.ts
Normal file
86
packages/xrpl/src/models/transactions/MPTokenIssuanceSet.ts
Normal file
@@ -0,0 +1,86 @@
|
|||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
import { isFlagEnabled } from '../utils'
|
||||||
|
|
||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
isString,
|
||||||
|
validateBaseTransaction,
|
||||||
|
validateRequiredField,
|
||||||
|
Account,
|
||||||
|
validateOptionalField,
|
||||||
|
isAccount,
|
||||||
|
GlobalFlags,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Transaction Flags for an MPTokenIssuanceSet Transaction.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export enum MPTokenIssuanceSetFlags {
|
||||||
|
/**
|
||||||
|
* If set, indicates that issuer locks the MPT
|
||||||
|
*/
|
||||||
|
tfMPTLock = 0x00000001,
|
||||||
|
/**
|
||||||
|
* If set, indicates that issuer unlocks the MPT
|
||||||
|
*/
|
||||||
|
tfMPTUnlock = 0x00000002,
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map of flags to boolean values representing {@link MPTokenIssuanceSet} transaction
|
||||||
|
* flags.
|
||||||
|
*
|
||||||
|
* @category Transaction Flags
|
||||||
|
*/
|
||||||
|
export interface MPTokenIssuanceSetFlagsInterface extends GlobalFlags {
|
||||||
|
tfMPTLock?: boolean
|
||||||
|
tfMPTUnlock?: boolean
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The MPTokenIssuanceSet transaction is used to globally lock/unlock a MPTokenIssuance,
|
||||||
|
* or lock/unlock an individual's MPToken.
|
||||||
|
*/
|
||||||
|
export interface MPTokenIssuanceSet extends BaseTransaction {
|
||||||
|
TransactionType: 'MPTokenIssuanceSet'
|
||||||
|
/**
|
||||||
|
* Identifies the MPTokenIssuance
|
||||||
|
*/
|
||||||
|
MPTokenIssuanceID: string
|
||||||
|
/**
|
||||||
|
* An optional XRPL Address of an individual token holder balance to lock/unlock.
|
||||||
|
* If omitted, this transaction will apply to all any accounts holding MPTs.
|
||||||
|
*/
|
||||||
|
Holder?: Account
|
||||||
|
Flags?: number | MPTokenIssuanceSetFlagsInterface
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an MPTokenIssuanceSet at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An MPTokenIssuanceSet Transaction.
|
||||||
|
* @throws When the MPTokenIssuanceSet is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateMPTokenIssuanceSet(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
validateRequiredField(tx, 'MPTokenIssuanceID', isString)
|
||||||
|
validateOptionalField(tx, 'Holder', isAccount)
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- Not necessary
|
||||||
|
const flags = tx.Flags as number | MPTokenIssuanceSetFlagsInterface
|
||||||
|
const isTfMPTLock =
|
||||||
|
typeof flags === 'number'
|
||||||
|
? isFlagEnabled(flags, MPTokenIssuanceSetFlags.tfMPTLock)
|
||||||
|
: flags.tfMPTLock ?? false
|
||||||
|
|
||||||
|
const isTfMPTUnlock =
|
||||||
|
typeof flags === 'number'
|
||||||
|
? isFlagEnabled(flags, MPTokenIssuanceSetFlags.tfMPTUnlock)
|
||||||
|
: flags.tfMPTUnlock ?? false
|
||||||
|
|
||||||
|
if (isTfMPTLock && isTfMPTUnlock) {
|
||||||
|
throw new ValidationError('MPTokenIssuanceSet: flag conflict')
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -38,6 +38,10 @@ export enum NFTokenMintFlags {
|
|||||||
* issuer.
|
* issuer.
|
||||||
*/
|
*/
|
||||||
tfTransferable = 0x00000008,
|
tfTransferable = 0x00000008,
|
||||||
|
/**
|
||||||
|
* If set, indicates that this NFT's URI can be modified.
|
||||||
|
*/
|
||||||
|
tfMutable = 0x00000010,
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -51,6 +55,7 @@ export interface NFTokenMintFlagsInterface extends GlobalFlags {
|
|||||||
tfOnlyXRP?: boolean
|
tfOnlyXRP?: boolean
|
||||||
tfTrustLine?: boolean
|
tfTrustLine?: boolean
|
||||||
tfTransferable?: boolean
|
tfTransferable?: boolean
|
||||||
|
tfMutable?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
67
packages/xrpl/src/models/transactions/NFTokenModify.ts
Normal file
67
packages/xrpl/src/models/transactions/NFTokenModify.ts
Normal file
@@ -0,0 +1,67 @@
|
|||||||
|
import { ValidationError } from '../../errors'
|
||||||
|
import { isHex } from '../utils'
|
||||||
|
|
||||||
|
import {
|
||||||
|
BaseTransaction,
|
||||||
|
validateBaseTransaction,
|
||||||
|
isAccount,
|
||||||
|
isString,
|
||||||
|
validateOptionalField,
|
||||||
|
Account,
|
||||||
|
validateRequiredField,
|
||||||
|
} from './common'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The NFTokenModify transaction modifies an NFToken's URI
|
||||||
|
* if its tfMutable is set to true.
|
||||||
|
*/
|
||||||
|
export interface NFTokenModify extends BaseTransaction {
|
||||||
|
TransactionType: 'NFTokenModify'
|
||||||
|
/**
|
||||||
|
* Identifies the NFTokenID of the NFToken object that the
|
||||||
|
* offer references.
|
||||||
|
*/
|
||||||
|
NFTokenID: string
|
||||||
|
/**
|
||||||
|
* Indicates the AccountID of the account that owns the corresponding NFToken.
|
||||||
|
* Can be omitted if the owner is the account submitting this transaction
|
||||||
|
*/
|
||||||
|
Owner?: Account
|
||||||
|
/**
|
||||||
|
* URI that points to the data and/or metadata associated with the NFT.
|
||||||
|
* This field need not be an HTTP or HTTPS URL; it could be an IPFS URI, a
|
||||||
|
* magnet link, immediate data encoded as an RFC2379 "data" URL, or even an
|
||||||
|
* opaque issuer-specific encoding. The URI is NOT checked for validity, but
|
||||||
|
* the field is limited to a maximum length of 256 bytes.
|
||||||
|
*
|
||||||
|
* This field must be hex-encoded. You can use `convertStringToHex` to
|
||||||
|
* convert this field to the proper encoding.
|
||||||
|
*
|
||||||
|
* This field must not be an empty string. Omit it from the transaction or
|
||||||
|
* set to `null` if you do not use it.
|
||||||
|
*/
|
||||||
|
URI?: string | null
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verify the form and type of an NFTokenModify at runtime.
|
||||||
|
*
|
||||||
|
* @param tx - An NFTokenModify Transaction.
|
||||||
|
* @throws When the NFTokenModify is Malformed.
|
||||||
|
*/
|
||||||
|
export function validateNFTokenModify(tx: Record<string, unknown>): void {
|
||||||
|
validateBaseTransaction(tx)
|
||||||
|
|
||||||
|
validateRequiredField(tx, 'NFTokenID', isString)
|
||||||
|
validateOptionalField(tx, 'Owner', isAccount)
|
||||||
|
validateOptionalField(tx, 'URI', isString)
|
||||||
|
|
||||||
|
if (tx.URI !== undefined && typeof tx.URI === 'string') {
|
||||||
|
if (tx.URI === '') {
|
||||||
|
throw new ValidationError('NFTokenModify: URI must not be empty string')
|
||||||
|
}
|
||||||
|
if (!isHex(tx.URI)) {
|
||||||
|
throw new ValidationError('NFTokenModify: URI must be in hex format')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -4,8 +4,10 @@ import {
|
|||||||
isAccount,
|
isAccount,
|
||||||
isNumber,
|
isNumber,
|
||||||
validateBaseTransaction,
|
validateBaseTransaction,
|
||||||
|
validateCredentialsList,
|
||||||
validateOptionalField,
|
validateOptionalField,
|
||||||
validateRequiredField,
|
validateRequiredField,
|
||||||
|
MAX_AUTHORIZED_CREDENTIALS,
|
||||||
} from './common'
|
} from './common'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -28,6 +30,12 @@ export interface AccountDelete extends BaseTransaction {
|
|||||||
* information for the recipient of the deleted account's leftover XRP.
|
* information for the recipient of the deleted account's leftover XRP.
|
||||||
*/
|
*/
|
||||||
DestinationTag?: number
|
DestinationTag?: number
|
||||||
|
/**
|
||||||
|
* Credentials associated with sender of this transaction. The credentials included
|
||||||
|
* must not be expired. The list must not be empty when specified and cannot contain
|
||||||
|
* more than 8 credentials.
|
||||||
|
*/
|
||||||
|
CredentialIDs?: string[]
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -41,4 +49,12 @@ export function validateAccountDelete(tx: Record<string, unknown>): void {
|
|||||||
|
|
||||||
validateRequiredField(tx, 'Destination', isAccount)
|
validateRequiredField(tx, 'Destination', isAccount)
|
||||||
validateOptionalField(tx, 'DestinationTag', isNumber)
|
validateOptionalField(tx, 'DestinationTag', isNumber)
|
||||||
|
|
||||||
|
validateCredentialsList(
|
||||||
|
tx.CredentialIDs,
|
||||||
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- known from base check
|
||||||
|
tx.TransactionType as string,
|
||||||
|
true,
|
||||||
|
MAX_AUTHORIZED_CREDENTIALS,
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,13 @@
|
|||||||
import { ValidationError } from '../../errors'
|
import { ValidationError } from '../../errors'
|
||||||
import { IssuedCurrencyAmount } from '../common'
|
import { IssuedCurrencyAmount, MPTAmount } from '../common'
|
||||||
|
|
||||||
import {
|
import {
|
||||||
BaseTransaction,
|
BaseTransaction,
|
||||||
validateBaseTransaction,
|
validateBaseTransaction,
|
||||||
isIssuedCurrency,
|
isIssuedCurrency,
|
||||||
|
isMPTAmount,
|
||||||
|
isAccount,
|
||||||
|
validateOptionalField,
|
||||||
} from './common'
|
} from './common'
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -15,15 +18,20 @@ export interface Clawback extends BaseTransaction {
|
|||||||
TransactionType: 'Clawback'
|
TransactionType: 'Clawback'
|
||||||
/**
|
/**
|
||||||
* Indicates the AccountID that submitted this transaction. The account MUST
|
* Indicates the AccountID that submitted this transaction. The account MUST
|
||||||
* be the issuer of the currency.
|
* be the issuer of the currency or MPT.
|
||||||
*/
|
*/
|
||||||
Account: string
|
Account: string
|
||||||
/**
|
/**
|
||||||
* The amount of currency to deliver, and it must be non-XRP. The nested field
|
* The amount of currency or MPT to clawback, and it must be non-XRP. The nested field
|
||||||
* names MUST be lower-case. The `issuer` field MUST be the holder's address,
|
* names MUST be lower-case. If the amount is IOU, the `issuer` field MUST be the holder's address,
|
||||||
* whom to be clawed back.
|
* whom to be clawed back.
|
||||||
*/
|
*/
|
||||||
Amount: IssuedCurrencyAmount
|
Amount: IssuedCurrencyAmount | MPTAmount
|
||||||
|
/**
|
||||||
|
* Indicates the AccountID that the issuer wants to clawback. This field is only valid for clawing back
|
||||||
|
* MPTs.
|
||||||
|
*/
|
||||||
|
Holder?: string
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -34,16 +42,29 @@ export interface Clawback extends BaseTransaction {
|
|||||||
*/
|
*/
|
||||||
export function validateClawback(tx: Record<string, unknown>): void {
|
export function validateClawback(tx: Record<string, unknown>): void {
|
||||||
validateBaseTransaction(tx)
|
validateBaseTransaction(tx)
|
||||||
|
validateOptionalField(tx, 'Holder', isAccount)
|
||||||
|
|
||||||
if (tx.Amount == null) {
|
if (tx.Amount == null) {
|
||||||
throw new ValidationError('Clawback: missing field Amount')
|
throw new ValidationError('Clawback: missing field Amount')
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isIssuedCurrency(tx.Amount)) {
|
if (!isIssuedCurrency(tx.Amount) && !isMPTAmount(tx.Amount)) {
|
||||||
throw new ValidationError('Clawback: invalid Amount')
|
throw new ValidationError('Clawback: invalid Amount')
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isIssuedCurrency(tx.Amount) && tx.Account === tx.Amount.issuer) {
|
if (isIssuedCurrency(tx.Amount) && tx.Account === tx.Amount.issuer) {
|
||||||
throw new ValidationError('Clawback: invalid holder Account')
|
throw new ValidationError('Clawback: invalid holder Account')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (isMPTAmount(tx.Amount) && tx.Account === tx.Holder) {
|
||||||
|
throw new ValidationError('Clawback: invalid holder Account')
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isIssuedCurrency(tx.Amount) && tx.Holder) {
|
||||||
|
throw new ValidationError('Clawback: cannot have Holder for currency')
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isMPTAmount(tx.Amount) && !tx.Holder) {
|
||||||
|
throw new ValidationError('Clawback: missing Holder')
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user