multisign tutorial

This commit is contained in:
mDuo13
2015-09-29 18:28:04 -07:00
parent ffdb26db76
commit d04cdfc6de
27 changed files with 2068 additions and 225 deletions

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -157,9 +157,30 @@ After a transaction has been submitted, if it gets accepted into a validated led
### Multi-Signing ###
A multi-signature authorizes a transaction in place of a single-signature. To provide a multi-signature, an account must first have a SignerList associated with it, which it can do by sending a [SignerListSet](#signerlistset) transaction.
Multi-signing in Ripple is the act of authorizing transactions for the Ripple
Consensus Ledger by using a combination of multiple secret keys. Multi-signing
allows various use cases including:
* If you require keys from different devices, a malicious user must compromise multiple machines in order to send transactions on your behalf.
* If the keys to an account are in the custody of entirely different people, those people must collaborate in order to send transaction from that account.
* Delegate a group of others who can send transactions for you if you are unavailable or unable to sign normally.
* ... and more.
To set up multi-signing for an account, the process is straightforward:
1. Use a [SignerListSet transaction](#signerlistset) to define which accounts or keys can, together, authorize transactions for this account.
2. Optionally disable the master key with an [AccountSet transaction](#accountset) using the `asfDisableMaster` flag.
3. Optionally remove the existing regular key (if any) with a [SetRegularKey transaction](#setregularkey).
After an account has a SignerList associated with it, the process of submitting a multi-signed transaction is as follows:
1. Create the transaction to be signed as a JSON object
2. Generate a signature for each account using the [`sign_for` command](rippled-apis.html#sign-for).
3. Combine the signatures and submit using the [`submit_multisigned` command](rippled-apis.html#submit-multisigned).
Main article: [How to Multi-Sign](multisign.html)
<span class='draft-comment'>TODO: more detail on how to actually sign and submit a multi-signed transaction.</span>
### Reliable Transaction Submission ###

View File

@@ -0,0 +1,707 @@
Introduction to Multi-Signing
==================================================================
Multi-signing in Ripple is the act of authorizing transactions for the Ripple
Consensus Ledger by using a combination of multiple secret keys. After setting
up multi-signing for an account, you can put the master secret in cold storage,
or even disable the master key entirely. With multiple secret keys required to
authorize a multi-signature, you can improve security in several ways.
* If you keep an account's keys on different devices, a malicious user must compromise multiple machines in order to send transactions on your behalf.
* If the keys to an account are in the custody of entirely different people, those people must collaborate in order to send transaction from that account.
* You can use the SignerList as a backup, to delegate a group of others who can send transactions for you if you are unavailable or unable to sign using your regular key.
* Even more uses than can be described here.
Availability of Multi-Signing
-----------------------------------------------------------------
Multi-signing is due to be enabled by an **Amendment** to the Ripple Consensus
Protocol. This Amendment must be approved by a consensus of validators showing
consistent support for the feature over a period of time. For more information,
see Amendments (TODO: link).
You can test multi-signing by running `rippled` in stand-alone mode with the
feature enabled. In stand-alone mode, `rippled` does not communicate with the
rest of the Ripple peer-to-peer network, but you can perform most of the same
actions on your local server only. This way, you can be sure that you are ready
for multi-signing when it goes live.
How to Multi-Sign
=================================================================
The basic process of Multi-Signing a transaction is necessarily more
complex than the process of signing a transaction with a single master key or
regular key.
1. Download and build rippled with multi-sign
-----------------------------------------------------------------
Until a binary for `rippled` with multi-signing is available, the best you can do is build it from source.
$ git clone git@github.com:scottschurr/rippled.git (TODO: switch to a Ripple Labs repo when available)
$ git checkout fix-sign_for
$ scons
See [rippled build instructions](https://wiki.ripple.com/Rippled_build_instructions) for help building from source.
2. Configure rippled to enable MultiSign
-----------------------------------------------------------------
Add the following to the bottom of the config file:
[features]
MultiSign
Note that this stanza is case-sensitive.
3. Start rippled in stand-alone mode
-----------------------------------------------------------------
If you have previously synced to the network, you can have the server load the
latest ledger as a starting place for stand-alone mode using the `--load`
commandline option:
$ sudo ./build/rippled --conf=/home/mduo13/.config/ripple/rippled.cfg -a --load
If you'd rather start from scratch, you can use the `--start` commandline
option to create a fresh ledger. In this case, the root account holds all
100 billion XRP:
**Address:** `rHb9CJAWyB4rj91VRWn96DkukG4bwdtyTh`
**Secret:** `snoPBrXtMeMyMHUVTgbuqAfg1SUTb` ("masterpassphrase")
4. Generate keys for a new wallet
-----------------------------------------------------------------
This step is not strictly necessary. For this process, we generate the keys to
a new Ripple account and then set up multi-signing for that account. To set up
multi-signing on an existing Ripple account, just use the keys to that account.
$ build/rippled wallet_propose
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"account_id" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"key_type" : "secp256k1",
"master_key" : "NED MANA SPA BLUR HERS HEAT RED NIBS MAIN MELT NOB RARE",
"master_seed" : "shqZZy2Rzs9ZqWTCQAdqc3bKgxnYq",
"master_seed_hex" : "99C7F2DCD88218372B7509ADF7DC562B",
"public_key" : "aBPvx491i2ZPVzmxoAmAVq5qXAxAZgmjfxoMTxFCg9Xxf2xwVVLc",
"public_key_hex" : "0303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D",
"status" : "success"
}
}
As always, be sure that an account's secret key never gets transmitted to
anyone you don't trust with full control of that account, and certainly not
unencrypted over the network.
5. Fund the new account with an existing wallet
-----------------------------------------------------------------
Again, this step is only necessary if you are setting up a new account to use
multi-signing for this example.
$ build/rippled submit <your existing account secret> '{
> "TransactionType" : "Payment",
> "Account" : "<your existing account address>",
> "Destination" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
> "Amount" : "100000000",
> "Flags": 2147483648
> }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "1200002280000000240000001E614000000005F5E10068400000000000000A7321023693F15967AE357D0327974AD46FE3C127113B1110D6044FD41E723689F81CC67446304402207AB5D16F58E9E6ADBBDD24837CAB80D871860E47EB0840FE57403FB979755A6D022015FE7A8838BEE6C18962C246D6D27791B7EE34B93415AE3824D12564E7A886C6811493B89AFCAD4C8EAC2B131C1331FEF12AE1522BBE83142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rN7n7otQDd6FczFgLdSqtcsAUxDkw6fzRH",
"Amount" : "100000000",
"Destination" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "10",
"Flags" : 2147483648,
"Sequence" : 30,
"SigningPubKey" : "023693F15967AE357D0327974AD46FE3C127113B1110D6044FD41E723689F81CC6",
"TransactionType" : "Payment",
"TxnSignature" : "304402207AB5D16F58E9E6ADBBDD24837CAB80D871860E47EB0840FE57403FB979755A6D022015FE7A8838BEE6C18962C246D6D27791B7EE34B93415AE3824D12564E7A886C6",
"hash" : "8C7A4D35D71CE80DA4EDAC91D620B6A348B7691B78AA2896284135378E10E0C2"
}
}
}
6. Manually close the ledger
-----------------------------------------------------------------
In the live network, you would simply wait for the ledger to close
automatically as the result of consensus. However, a rippled node running in
stand-alone mode does not engage in consensus, so you must manually close the
ledger with the [`ledger_accept` command](rippled-apis.html#ledger-accept).
$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061437,
"status" : "success"
}
}
7. Create a SignerList on the new account with a SignerListSet transaction
-----------------------------------------------------------------
Before you can multi-sign transactions, you must associate a SignerList with
your account, so that RCL knows which keys can be used to sign for you. You do
this with a [SignerListSet transaction](transactions.html#signerlistset).
In this example, the SignerList has 3 members, with the weights and quorum set
up such that multi-signed transactions need a signature from
rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW plus at least one signature from the other
two members of the list. The `Account` values you use in your list can be
funded accounts that exist in the ledger or just unused addresses.
$ build/rippled submit shqZZy2Rzs9ZqWTCQAdqc3bKgxnYq '{
> "Flags": 0,
> "TransactionType": "SignerListSet",
> "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
> "Fee": "10000",
> "SignerQuorum": 3,
> "SignerEntries": [
> {
> "SignerEntry": {
> "Account": "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
> "SignerWeight": 2
> }
> },
> {
> "SignerEntry": {
> "Account": "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
> "SignerWeight": 1
> }
> },
> {
> "SignerEntry": {
> "Account": "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
> "SignerWeight": 1
> }
> }
> ]
> }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "12000C2200000000240000000120230000000368400000000000271073210303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D74473045022100BEDFA12502C66DDCB64521972E5356F4DB965F553853D53D4C69B4897F11B4780220595202D1E080345B65BAF8EBD6CA161C227F1B62C7E72EA5CA282B9434A6F04281142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1F4EB1300028114204288D2E47F8EF6C99BCC457966320D12409711E1EB13000181147908A7F0EDD48EA896C3580A399F0EE78611C8E3E1EB13000181143A4C02EA95AD6AC3BED92FA036E0BBFB712C030CE1F1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "10000",
"Flags" : 0,
"Sequence" : 1,
"SignerEntries" : [
{
"SignerEntry" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight" : 2
}
},
{
"SignerEntry" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight" : 1
}
},
{
"SignerEntry" : {
"Account" : "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight" : 1
}
}
],
"SignerQuorum" : 3,
"SigningPubKey" : "0303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D",
"TransactionType" : "SignerListSet",
"TxnSignature" : "3045022100BEDFA12502C66DDCB64521972E5356F4DB965F553853D53D4C69B4897F11B4780220595202D1E080345B65BAF8EBD6CA161C227F1B62C7E72EA5CA282B9434A6F042",
"hash" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756"
}
}
}
8. Manually close the ledger again
-----------------------------------------------------------------
As before, you would wait for the ledger to close on a live network. We use
the [`ledger_accept` command](rippled-apis.html#ledger-accept) to manually
close the ledger when running `rippled` in stand-alone mode.
$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061438,
"status" : "success"
}
}
9. Confirm the presence of the new signer list using account_objects
-----------------------------------------------------------------
Normally an account has lots of different types of objects, but for this new
account, the only thing we've done is add a SignerList, so it should be easy to
find in the results of the
[`account_objects` command](rippled-apis.html#account-objects).
$ build/rippled account_objects rnBFvgZphmN39GWzUJeUitaP22Fr9be75H
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"account_objects" : [
{
"Flags" : 0,
"LedgerEntryType" : "SignerList",
"OwnerNode" : "0000000000000000",
"PreviousTxnID" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756",
"PreviousTxnLgrSeq" : 16061437,
"SignerEntries" : [
{
"SignerEntry" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight" : 2
}
},
{
"SignerEntry" : {
"Account" : "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight" : 1
}
},
{
"SignerEntry" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight" : 1
}
}
],
"SignerListID" : 0,
"SignerQuorum" : 3,
"index" : "92373B9F1683001079764527F0BD553ED8656A9934FE641A7F0A0BF4DB230E0E"
}
],
"ledger_current_index" : 16061438,
"status" : "success",
"validated" : false
}
}
10. Create a new transaction that you plan to multi-sign
-----------------------------------------------------------------
You have to specify _everything_ about this transaction, including Fee and
Sequence. Also include the field `SigningPubKey` as an empty string -- this
indicates that the transaction is multi-signed.
Here's an example transaction we can send from our test account:
{
"TransactionType": "TrustSet",
"Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Flags": 262144,
"LimitAmount": {
"currency": "USD",
"issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value": "100"
},
"Sequence": 2,
"SigningPubKey":"",
"Fee": "12000"
}
(If you started from a fresh ledger, you first need to fund the account
specified by the `issuer` in this example, and then manually close the ledger.)
Keep in mind that the `Fee` for multi-signed transactions is significantly
higher than for regularly-signed transactions. It should be (N+1) times the
normal fee, where N is the number of signatures you plan to provide. Given that
it sometimes takes a while to collect signatures from multiple sources, you may
want to include additional buffer in case the load fee increases in that time.
11. Get a signature using the sign_for command
-----------------------------------------------------------------
$ build/rippled sign_for rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW <rsA2's secret> '{
> "TransactionType": "TrustSet",
> "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
> "Flags": 262144,
> "LimitAmount": {
> "currency": "USD",
> "issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
> "value": "100"
> },
> "Sequence": 2,
> "SigningPubKey":"",
> "Fee": "12000"
> }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
}
],
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "4622B2893AF3A70B4DB1FF86B25C10E92B71973895143E66029567A8541A8060"
}
}
}
The valuable part in the response is the `Signers` field. This is the part that
you're going to need later in order to construct the full, multi-signed
transaction.
The other parts, such as the `tx_blob`, are not very useful at this point,
unless you're "multi-signing" a transaction with only one signature.
12. Get additional signatures the same way
-----------------------------------------------------------------
If the accounts in your SignerList are funded accounts, the secret key you use
to sign for those accounts can come from the regular key (if they have one), or
the master key (unless it's disabled). For accounts that don't exist in the
ledger, you can only use the master secret associated with the address.
$ build/rippled sign_for rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v <rUpy's secret> '{
"TransactionType": "TrustSet",
"Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Flags": 262144,
"LimitAmount": {
"currency": "USD",
"issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value": "100"
},
"Sequence": 2,
"SigningPubKey":"",
"Fee": "12000"
}'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Signers" : [
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "4622B2893AF3A70B4DB1FF86B25C10E92B71973895143E66029567A8541A8060"
}
}
}
Depending on the SignerList you configured, you may need to repeat this step
several times in order to get signatures from all the necessary parties.
13. Combine the signatures and submit
-----------------------------------------------------------------
Take the contents of all the `Signers` arrays from all the responses, and
concatenate them in to a single `Signers` array field. The commandline syntax
for the [`submit_multisigned` command](rippled-apis.html#submit-multisigned)
takes a single JSON object with two elements: this combined `Signers` array;
and `tx_json`, which is the transaction JSON that they signed.
This command actually submits the transaction for inclusion in the ledger. In
online mode, this relays it to other members of the network.
$ build/rippled submit_multisigned ' {
> "Signers": [
> {
> "Signer" : {
> "Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
> "SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
> "TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
> }
> },
> {
> "Signer" : {
> "Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
> "SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
> "TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
> }
> }
> ],
> "tx_json": {
> "TransactionType": "TrustSet",
> "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
> "Flags": 262144,
> "LimitAmount": {
> "currency": "USD",
> "issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
> "value": "100"
> },
> "Sequence": 2,
> "SigningPubKey":"",
> "Fee": "12000"
> }
> }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1F3E010732102B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF7447304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE8114204288D2E47F8EF6C99BCC457966320D12409711E1E0107321028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B7446304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E181147908A7F0EDD48EA896C3580A399F0EE78611C8E3E1F1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
},
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78"
}
}
}
Take note of the `hash` value from the response (In this case, it's
`878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78`) so you can
check the results of the transaction later.
14. Manually close the ledger one last time
-----------------------------------------------------------------
Once again, you would wait for the ledger to close on a live network. We use
the [`ledger_accept` command](rippled-apis.html#ledger-accept) to manually
close the ledger when running `rippled` in stand-alone mode.
$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061439,
"status" : "success"
}
}
15. Confirm the results of the transaction
-----------------------------------------------------------------
Use the hash value from the response to the `submit_multisigned` command.
$ build/rippled tx 878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
},
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"date" : 496881900,
"hash" : "878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78",
"inLedger" : 16061438,
"ledger_index" : 16061438,
"meta" : {
"AffectedNodes" : [
{
"ModifiedNode" : {
"LedgerEntryType" : "AccountRoot",
"LedgerIndex" : "13F1A95D7AAB7108D5CE7EEAF504B2894B8C674E6D68499076441C4837282BF8",
"PreviousTxnID" : "6ECC8C16B76D9B9AB099CA96DD653D8A321C34F1E5972D5EE6DBA19418F4D0CC",
"PreviousTxnLgrSeq" : 16061436
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Flags" : 0,
"Owner" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"RootIndex" : "3B9C0CE77FCE7BCEE1A68F1E26AC467AF326239D0D816CE705E4A0E2DAD03F6D"
},
"LedgerEntryType" : "DirectoryNode",
"LedgerIndex" : "3B9C0CE77FCE7BCEE1A68F1E26AC467AF326239D0D816CE705E4A0E2DAD03F6D"
}
},
{
"CreatedNode" : {
"LedgerEntryType" : "RippleState",
"LedgerIndex" : "3C75A1F3DB61406AC2A9493038E8394A73F103C9229695AC7E57EB0F8AFC69E4",
"NewFields" : {
"Balance" : {
"currency" : "USD",
"issuer" : "rrrrrrrrrrrrrrrrrrrrBZbvji",
"value" : "0"
},
"Flags" : 65536,
"HighLimit" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "0"
},
"LowLimit" : {
"currency" : "USD",
"issuer" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"value" : "100"
}
}
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Balance" : "109978000",
"Flags" : 0,
"OwnerCount" : 6,
"Sequence" : 3
},
"LedgerEntryType" : "AccountRoot",
"LedgerIndex" : "3D728C1F82CFE419F2DC58707D1AD06E985A29217D21A991ADF154184B664F4F",
"PreviousFields" : {
"Balance" : "109990000",
"OwnerCount" : 5,
"Sequence" : 2
},
"PreviousTxnID" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756",
"PreviousTxnLgrSeq" : 16061437
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Flags" : 0,
"Owner" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"RootIndex" : "95DA402B4D58FBFF6BAA4CB84BBC21348CC273949B61FEBCE758410EF90D147D"
},
"LedgerEntryType" : "DirectoryNode",
"LedgerIndex" : "95DA402B4D58FBFF6BAA4CB84BBC21348CC273949B61FEBCE758410EF90D147D"
}
}
],
"TransactionIndex" : 0,
"TransactionResult" : "tesSUCCESS"
},
"status" : "success",
"validated" : true
}
}
In particular, check that the `TransactionResult` is the string `tesSUCCESS`.
On the live network, you must also confirm that the `validated` field is set to
the boolean `true`. If not, you might need to wait longer for the consensus
process to finish; or your transaction may be unable to be included in a ledger
for some reason. In stand-alone mode, the server automatically considers a
ledger to be `validated` if it has been manually closed.

View File

@@ -46,6 +46,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -53,6 +53,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -137,6 +138,7 @@ Ripples distributed settlement network is built on open-source technology tha
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</div>
<div class="col-md-3">

190
multisign.html Normal file
View File

@@ -0,0 +1,190 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<meta name="viewport" content="width=device-width">
<title>How to Multi-Sign a Transaction - Ripple Developer Portal</title>
<!-- favicon -->
<link rel="icon" href="favicon.ico" type="image/x-icon">
<link rel="shortcut icon" href="favicon.ico" type="image/x-icon">
<!-- jQuery -->
<script src="vendor/jquery-1.11.1.min.js"></script>
<!-- Bootstrap -->
<link href="css/bootstrap.min.css" rel="stylesheet">
<script src="js/bootstrap.min.js"></script>
<!-- Flatdoc theme -->
<link href='vendor/flatdoc/v/0.8.0/theme-white/style.css' rel='stylesheet'>
<script src="vendor/flatdoc/v/0.8.0/theme-white/script.js"></script>
<!-- syntax highlighting -->
<link rel="stylesheet" href="vendor/docco.min.css">
<script src="vendor/highlight.min.js"></script>
<!-- syntax selection js -->
<script src="js/multicodetab.js"></script>
<!-- Code to load contents via Flatdoc -->
<script src="vendor/flatdoc/v/0.8.0/legacy.js"></script>
<script src="vendor/flatdoc/v/0.8.0/flatdoc.js"></script>
<script>
$(".flatdoc-content").empty();
$(".content-root .menubar .menu").empty();
Flatdoc.run({
fetcher: Flatdoc.file('content/multi-sign_howto.md')
});
$(document).on('flatdoc:ready', function() {
$().multicode_tabs();
hljs.initHighlighting();
});
</script>
<script src="js/expandcode.js"></script>
<script src="js/fixsidebarscroll.js"></script>
<!-- Custom Stylesheets -->
<link href="font/fonts.css" rel="stylesheet" type="text/css" />
<link href="css/main.css" rel="stylesheet" />
<link href="css/custom.css" rel="stylesheet" />
<link rel="shortcut icon" href="favicon.ico?v=2" type="image/x-icon" />
<link rel="icon" href="favicon.ico?v=2" type="image/x-icon" />
</head>
<body role='flatdoc' class='no-literate'>
<div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
<div class="container">
<div class="navbar-header">
<button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
<span class="sr-only">Toggle navigation</span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<a class="navbar-brand" href="./"><img class="small_logo" src="assets/img/ripple_logo_small.png"></a>
</div>
<div class="navbar-collapse collapse">
<ul class="nav navbar-nav">
<li class="dropdown">
<a href="./" class="dropdown-toggle" data-toggle="dropdown">Documentation <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="rippled-apis.html">rippled</a></li>
<li><a href="rippled-setup.html">rippled Setup</a></li>
<li><a href="ripple-rest.html">Ripple-REST</a></li>
<li><a href="transactions.html">Transactions</a></li>
<li><a href="ripple-ledger.html">The Ledger</a></li>
<li><a href="reliable_tx.html">Reliable Transaction Submission</a></li>
<li><a href="gateway_guide.html">Gateway Guide</a></li>
<li><a href="historical_data.html">Historical Data API</a></li>
<li><a href="charts_api.html">Ripple Charts API</a></li>
<li><a href="data_api_v2.html">Ripple Data API v2</a></li>
<li><a href="gateway_services.html">Gateway Services</a></li>
<li><a href="transfer_fees.html">Transfer Fees</a></li>
<li><a href="whitepapers.html">Whitepapers</a></li>
<li><a href="multisign.html">How to Multi-Sign a Transaction</a></li>
</ul>
</li>
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown">API Tools <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="rest-api-tool.html">Ripple-REST API Tool</a></li>
<li><a href="historicaldb-api-tool.html">Historical Database API Tool</a></li>
<li><a href="ripple-api-tool.html">WebSocket API Tool</a></li>
<li><a href="charts-api-tool.html">Charts API Tool</a></li>
<li><a href="data-api-v2-tool.html">Data API v2 Tool</a></li>
</ul>
</li>
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown">Resources <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="https://forum.ripple.com/viewforum.php?f=2">Forums</a></li>
<li><a href="https://www.bountysource.com/teams/ripple/bounties">Bounties</a></li>
<li><a href="https://ripplelabs.atlassian.net/">Bug Tracking</a></li>
<li><a href="https://ripple.com/category/dev-blog/">Dev Blog</a></li>
<li><a href="https://ripple.com/press-releases/">Press Center</a></li>
<li><a href="https://ripple.com/brand-guidelines/">Brand Guidelines</a></li>
</ul>
<li><a href="https://github.com/ripple/ripple-dev-portal" title="GitHub">Site Source</a></li>
</ul>
</div><!--/.nav-collapse -->
</div>
</div>
<script type="text/javascript">
if (window.location.host.indexOf("github.io") > -1) {
document.write("<div style='background-color:red; color:white; position:fixed; top: 50px; right: 150px; padding: 10px 20px;'>DRAFT</div>");
}
</script>
<div class='wrapper'>
<div class='content-root'>
<div class='menubar'>
<div class='menu section' role='flatdoc-menu'>
</div>
</div>
<div role='flatdoc-content' class='content'>
</div>
</div>
</div>
<footer class="footer">
<div class="container">
<div class="row">
<div class="col-md-3">
<h4>Documentation</h4>
<ul class="footer_links">
<li><a href="rippled-apis.html">rippled</a></li>
<li><a href="rippled-setup.html">rippled Setup</a></li>
<li><a href="ripple-rest.html">Ripple-REST</a></li>
<li><a href="transactions.html">Transactions</a></li>
<li><a href="ripple-ledger.html">The Ledger</a></li>
<li><a href="reliable_tx.html">Reliable Transaction Submission</a></li>
<li><a href="gateway_guide.html">Gateway Guide</a></li>
<li><a href="historical_data.html">Historical Data API</a></li>
<li><a href="charts_api.html">Ripple Charts API</a></li>
<li><a href="data_api_v2.html">Ripple Data API v2</a></li>
<li><a href="gateway_services.html">Gateway Services</a></li>
<li><a href="transfer_fees.html">Transfer Fees</a></li>
<li><a href="whitepapers.html">Whitepapers</a></li>
<li><a href="multisign.html">How to Multi-Sign a Transaction</a></li>
</ul>
</div>
<div class="col-md-3">
<h4>Resources</h4>
<ul class="footer_links">
<li><a href="https://ripple.com/press-releases/">Press Center</a></li>
<li><a href="https://ripple.com/brand-guidelines/">Brand Use and Guidelines</a></li>
<li><a href="https://forum.ripple.com/viewforum.php?f=2">Forums</a></li>
<li><a href="https://ripple.com/category/dev-blog/">Dev Blog</a></li>
</ul>
</div>
<div class="col-md-3">
<h4>Ripple Projects</h4>
<ul class="footer_links">
<li><a href="https://www.rippletrade.com">Ripple Trade</a>
<li><a href="https://www.ripplecharts.com">Ripple Charts</a>
<li><a href="https://ripple.com/graph">Ripple Graph</a>
<li><a href="http://codius.org/">Codius</a>
</ul>
</div>
<div class="col-md-3">
<h4>Ripple Labs</h4>
<ul class="footer_links">
<li><a href="https://www.ripplelabs.com/wp-content/uploads/2014/10/ripple_labs_bylaws.pdf">Corporate Bylaws</a></li>
<li><a href="https://www.ripplelabs.com/wp-content/uploads/2014/09/ripple_labs_code_of_conduct1.pdf">Code of Conduct</a></li>
<li><a href="https://www.ripplelabs.com/team/">Team</a></li>
<li><a href="https://www.ripplelabs.com/careers/">Careers</a></li>
<li><a href="https://www.ripplelabs.com/investors/">Investors</a></li>
<li><a href="https://www.ripplelabs.com/advisors/">Advisors</a></li>
<li><a href="https://www.ripplelabs.com/xrp-distribution/">XRP Distribution</a></li>
<li><a href="https://www.ripplelabs.com/contact/">Contact</a></li>
</ul>
</div>
</div>
</div>
</footer>
</body>
</html>

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -972,6 +973,119 @@
<li>The AccountID of the high account</li>
<li>The 160-bit currency code of the trust line(s)</li>
</ul>
<h2 id="signerlist">SignerList</h2>
<p><a href="https://github.com/ripple/rippled/blob/6d2e3da30696bd10e3bb11a5ff6d45d2c4dae90f/src/ripple/protocol/impl/LedgerFormats.cpp#L127" title="Source">[Source]<br/></a></p>
<p>The <code>SignerList</code> node type represents a list of parties that, as a group, are authorized to sign a transaction in place of an individual account.</p>
<p>Example SignerList node:</p>
<pre><code>{
"Flags": 0,
"LedgerEntryType": "SignerList",
"OwnerNode": "0000000000000000",
"PreviousTxnID": "5904C0DC72C58A83AEFED2FFC5386356AA83FCA6A88C89D00646E51E687CDBE4",
"PreviousTxnLgrSeq": 16061435,
"SignerEntries": [
{
"SignerEntry": {
"Account": "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight": 2
}
},
{
"SignerEntry": {
"Account": "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight": 1
}
},
{
"SignerEntry": {
"Account": "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight": 1
}
}
],
"SignerListID": 0,
"SignerQuorum": 3,
"index": "A9C28A28B85CD533217F5C0A0C7767666B093FA58A0F2D80026FCC4CD932DDC7"
}
</code></pre>
<p>A SignerList node has the following fields:</p>
<table>
<thead>
<tr>
<th>Name</th>
<th>JSON Type</th>
<th>Internal Type</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>OwnerNode</td>
<td>String</td>
<td>UInt64</td>
<td>A hint indicating which page of the owner directory links to this node, in case the directory consists of multiple nodes.</td>
</tr>
<tr>
<td>SignerQuorum</td>
<td>Number</td>
<td>UInt32</td>
<td>A target number for signer weights. To produce a valid signature for the owner of this SignerList, the signers must provide valid signatures whose weights sum to this value or more.</td>
</tr>
<tr>
<td>SignerEntries</td>
<td>Array</td>
<td>Array</td>
<td>An array of SignerEntry objects representing the parties who are part of this signer list.</td>
</tr>
<tr>
<td>SignerListID</td>
<td>Number</td>
<td>UInt32</td>
<td>An ID for this signer list. Currently always set to <code>0</code>. If a future update allows multiple signer lists for an account, this may change.</td>
</tr>
<tr>
<td>PreviousTxnID</td>
<td>String</td>
<td>Hash256</td>
<td>The identifying hash of the transaction that most recently modified this node.</td>
</tr>
<tr>
<td>PreviousTxnLgrSeq</td>
<td>Number</td>
<td>UInt32</td>
<td>The sequence number (<code>ledger_index</code>) of the ledger that contains the transaction that most recently modified this node.</td>
</tr>
</tbody>
</table>
<h3 id="signerentry-object">SignerEntry object</h3>
<p>Each member of the <code>SignerEntries</code> field is an object that describes that signer in the list. A SignerEntry has the following fields:</p>
<table>
<thead>
<tr>
<th>Name</th>
<th>JSON Type</th>
<th>Internal Type</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>Account</td>
<td>String</td>
<td>AccountID</td>
<td>An address whose signature contributes to the multi-signature. This does not need to be a funded Ripple account.</td>
</tr>
<tr>
<td>SignerWeight</td>
<td>Number</td>
<td>UInt16</td>
<td>The weight of signatures from this signer. A multi-signature is only valid of the sum weight of the signatures provided meets or exceeds the SignerList's <code>SignerQuorum</code> value.</td>
</tr>
</tbody>
</table>
<p>When processing a multi-signed transaction, the server dereferences the <code>Account</code> values with respect to the ledger at the time of transaction execution. If the address <em>does not</em> correspond to a funded <a href="#accountroot">AccountRoot node</a>, then only the master secret associated with that address can be used to produce a valid signature. If the account <em>does</em> exist in the ledger, then it depends on the state of that account. If the account has a Regular Key configured, the Regular Key can be used. The account's master key can only be used if it is not disabled. Even if the account has a SignerList configured, a multi-signature cannot be used as a valid component to another multi-signature. (In other words, "multi-level" multi-signing is disallowed.)</p>
<h3 id="signerlists-and-reserves">SignerLists and Reserves</h3>
<p>A SignerList contributes to the <a href="https://wiki.ripple.com/Reserves">Account Reserve</a>. The SignerList itself counts as two objects, and each member of the list counts as one, so that the total owner reserve associated with a SignerList is anywhere from 3 times to 10 times the reserve required by a single trust line (<a href="#ripplestate">RippleState</a>) or <a href="#offer">Offer</a> node in the ledger.</p>
</div>
</main>
</div>

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -478,7 +479,7 @@ Null method
<p>All methods can potentially return any of the following values for the <code>error</code> code:</p>
<ul>
<li><code>unknownCmd</code> - The request does not contain a <a href="#api-methods">command</a> that the <code>rippled</code> server recognizes.</li>
<li>`jsonInvalid1 - (WebSocket only) The request is not a proper JSON object. <ul>
<li><code>jsonInvalid</code> - (WebSocket only) The request is not a proper JSON object.<ul>
<li>JSON-RPC returns a 400 Bad Request HTTP error in this case instead.</li>
</ul>
</li>
@@ -1629,7 +1630,7 @@ rippled account_offers r9cZA1mLK5R5Am25ArfXFmqgNwjZgnfk59 current
</ul>
<h2 id="account-objects">account_objects</h2>
<p><a href="https://github.com/ripple/rippled/blob/399c43cae6e90a428e9ce6a988123972b0f03c99/src/ripple/rpc/handlers/AccountObjects.cpp" title="Source">[Source]<br/></a></p>
<p>The <code>account_objects</code> command returns the raw <a href="reference-ledger-format.html">ledger format</a> for all objects owned by an account, such as <a href="reference-transaction-format.html#lifecycle-of-an-offer">outstanding offers</a>, trust lines in non-default state, and tickets (which are part of forthcoming multi-sign code). For getting the balance of an account's trust lines, we recommend <a href="#account-lines"><code>account_lines</code></a> instead.</p>
<p>The <code>account_objects</code> command returns the raw <a href="reference-ledger-format.html">ledger format</a> for all objects owned by an account, such as <a href="reference-transaction-format.html#lifecycle-of-an-offer">outstanding offers</a>, trust lines in non-default state, and <a href="reference-transaction-format.html#multi-signing">signer lists</a>. For getting the balance of an account's trust lines, we recommend <a href="#account-lines"><code>account_lines</code></a> instead.</p>
<h4 id="request-format-4">Request Format</h4>
<p>An example of the request format:</p>
<div class="multicode">

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -151,8 +152,7 @@
</ul>
<h2 id="signing-and-sending-transactions">Signing and Sending Transactions</h2>
<p>Signing a transaction cryptographically proves that the person in charge of the account sending the transaction is authorized to do so. Only signed transactions can be submitted to the network and included in a validated ledger. A signed transaction is immutable: its contents cannot change, and the signature is not valid for any other transaction.</p>
<p>You can sign a transaction using a secret key: either the master secret, or a regular secret if the account has a regular key pair associated with it. (See <a href="#setregularkey">SetRegularKey</a> for details.)</p>
<p>Multi-signature transactions are <a href="https://wiki.ripple.com/Multisign">in development</a>.</p>
<p>You sign a transaction using a secret key: either the master secret, or a regular secret if the account has a regular key pair associated with it. (See <a href="#setregularkey">SetRegularKey</a> for details.) If your account has a SignerList associated with it, you can use a <a href="#multi-signing">multi-signature</a> instead.</p>
<p>Typically, you create a transaction in JSON format first. Here is an example of an unsigned Payment-type transaction in JSON:</p>
<pre><code>{
"TransactionType" : "Payment",
@@ -168,13 +168,13 @@
"Sequence": 2,
}
</code></pre>
<p>After doing that, you generate the signed binary format for the transaction. There are two ways to do this:</p>
<p>After doing that, you generate the signed binary format for the transaction. For transactions authorized by only a single signature, you have two options:</p>
<ol>
<li>Convert it to a binary blob and sign it offline. This is preferable, since it means that the account secret used for signing the transaction is never transmitted over any network connection.<ul>
<li>You can use <a href="reference-rippleapi.html#sign">RippleAPI</a> to perform offline signing.</li>
</ul>
</li>
<li>Have a <code>rippled</code> server sign the transaction for you. The <a href="reference-rippled.html#sign">sign command</a> takes a JSON-format transaction and secret and returns the signed binary transaction format ready for submission. (Transmitting your account secret is dangerous, so you should only do this from within a trusted and encrypted sub-net, to a server you control.)<ul>
<li>Have a <code>rippled</code> server sign the transaction for you. The <a href="reference-rippled.html#sign">sign command</a> takes a JSON-format transaction and secret and returns the signed binary transaction format ready for submission. (Transmitting your account secret is dangerous, so you should only do this from within a trusted and encrypted connection, or through a local connection, and only to a server you control.)<ul>
<li>As a shortcut, you can use the <a href="reference-rippled.html#submit">submit command</a> with a <code>tx_json</code> object to sign and submit a transaction all at once. This is only recommended for testing and development purposes.</li>
</ul>
</li>
@@ -273,6 +273,29 @@
}
}
</code></pre>
<h3 id="multi-signing">Multi-Signing</h3>
<p>Multi-signing in Ripple is the act of authorizing transactions for the Ripple
Consensus Ledger by using a combination of multiple secret keys. Multi-signing
allows various use cases including:</p>
<ul>
<li>If you require keys from different devices, a malicious user must compromise multiple machines in order to send transactions on your behalf.</li>
<li>If the keys to an account are in the custody of entirely different people, those people must collaborate in order to send transaction from that account.</li>
<li>Delegate a group of others who can send transactions for you if you are unavailable or unable to sign normally.</li>
<li>... and more.</li>
</ul>
<p>To set up multi-signing for an account, the process is straightforward:</p>
<ol>
<li>Use a <a href="#signerlistset">SignerListSet transaction</a> to define which accounts or keys can, together, authorize transactions for this account.</li>
<li>Optionally disable the master key with an <a href="#accountset">AccountSet transaction</a> using the <code>asfDisableMaster</code> flag.</li>
<li>Optionally remove the existing regular key (if any) with a <a href="#setregularkey">SetRegularKey transaction</a>.</li>
</ol>
<p>After an account has a SignerList associated with it, the process of submitting a multi-signed transaction is as follows:</p>
<ol>
<li>Create the transaction to be signed as a JSON object</li>
<li>Generate a signature for each account using the <a href="rippled-apis.html#sign-for"><code>sign_for</code> command</a>.</li>
<li>Combine the signatures and submit using the <a href="rippled-apis.html#submit-multisigned"><code>submit_multisigned</code> command</a>.</li>
</ol>
<p>Main article: <a href="multisign.html">How to Multi-Sign</a></p>
<h3 id="reliable-transaction-submission">Reliable Transaction Submission</h3>
<p>Reliably submitting transactions is the process of achieving both of the following:</p>
<ul>
@@ -349,7 +372,13 @@
<td>SigningPubKey</td>
<td>String</td>
<td>PubKey</td>
<td>(Automatically added when signing) Hex representation of the public key that corresponds to the private key used to sign this transaction.</td>
<td>(Automatically added when signing) Hex representation of the public key that corresponds to the private key used to sign this transaction. If an empty string, indicates a multi-signature is present in the <code>Signers</code> field instead.</td>
</tr>
<tr>
<td><a href="#signers-field">Signers</a></td>
<td>Array</td>
<td>Array</td>
<td>(Optional) Array of objects that represent a multi-signature which authorizes this transaction.</td>
</tr>
<tr>
<td>SourceTag</td>
@@ -361,7 +390,7 @@
<td>TransactionType</td>
<td>String</td>
<td>UInt16</td>
<td>The type of transaction. Valid types include: <code>Payment</code>, <code>OfferCreate</code>, <code>OfferCancel</code>, <code>TrustSet</code>, <code>AccountSet</code>, and <code>SetRegularKey</code>.</td>
<td>The type of transaction. Valid types include: <code>Payment</code>, <code>OfferCreate</code>, <code>OfferCancel</code>, <code>TrustSet</code>, <code>AccountSet</code>, <code>SetRegularKey</code>, and <code>SignerListSet</code>.</td>
</tr>
<tr>
<td>TxnSignature</td>
@@ -381,8 +410,9 @@
<p>For a production system, we recommend <em>not</em> leaving these fields to be filled by the server. For example, if transaction costs become high due to a temporary spike in network load, you may want to wait for the cost to decrease before sending some transactions, instead of paying the temporarily-high cost.</p>
<p>The <a href="#paths"><code>Paths</code> field</a> of the <a href="#payment">Payment</a> transaction type can also be automatically filled in.</p>
<h3 id="transaction-cost">Transaction Cost</h3>
<p>In order to protect the Ripple Consensus Ledger from being disrupted by spam and denial-of-service attacks, each transaction must destroy a small amount of XRP. This transaction cost is designed to increase along with the load on the network, making it very expensive to deliberately or inadvertently overload the network.</p>
<p>The <code>Fee</code> field specifies an amount, in <a href="reference-rippled.html#specifying-currency-amounts">drops of XRP</a>, to destroy as the cost for this transaction. If the transaction is included in a validated leger (whether or not it achieves its intended purpose), then the amount of XRP specified in the <code>Fee</code> parameter is destroyed forever. You can <a href="concept-transaction-cost.html#querying-the-transaction-cost">look up the transaction cost</a> in advance, or <a href="concept-transaction-cost.html#automatically-specifying-the-transaction-cost">let <code>rippled</code> set it automatically</a> when you sign a transaction.</p>
<p>In order to protect the Ripple Consensus Ledger from being disrupted by spam and denial-of-service attacks, each transaction must destroy a small amount of XRP. This <em><a href="concept-transaction-cost.html">transaction cost</a></em> is designed to increase along with the load on the network, making it very expensive to deliberately or inadvertently overload the network.</p>
<p>The <code>Fee</code> field specifies an amount, in <a href="reference-rippled.html#specifying-currency-amounts">drops of XRP</a>, to destroy as the cost for relaying this transaction. If the transaction is included in a validated ledger (whether or not it achieves its intended purpose), then the amount of XRP specified in the <code>Fee</code> parameter is destroyed forever. You can <a href="concept-transaction-cost.html#querying-the-transaction-cost">look up the transaction cost</a> in advance, or <a href="concept-transaction-cost.html#automatically-specifying-the-transaction-cost">let <code>rippled</code> set it automatically</a> when you sign a transaction.</p>
<p><strong>Note:</strong> <a href="#multi-signing">Multi-signed transactions</a> require additional fees to relay to the network.</p>
<h3 id="canceling-or-skipping-a-transaction">Canceling or Skipping a Transaction</h3>
<p>An important and intentional feature of the Ripple Network is that a transaction is final as soon as it has been incorporated in a validated ledger.</p>
<p>However, if a transaction has not yet been included in a validated ledger, you can effectively cancel it by rendering it invalid. Typically, this means sending another transaction with the same <code>Sequence</code> value from the same account. If you do not want to perform the same transaction again, you can perform an <a href="#accountset">AccountSet</a> transaction with no options.</p>
@@ -397,7 +427,7 @@
<p>One situation in which this is useful is if you have a primary system for submitting transactions and a passive backup system. If the passive backup system becomes disconnected from the primary, but the primary is not fully dead, and they both begin operating at the same time, you could potentially encounter serious problems like some transactions sending twice and others not at all. Chaining your transactions together with <code>AccountTxnID</code> ensures that, even if both systems are active, only one of them can submit valid transactions at a time.</p>
<p>In order to use AccountTxnID, you must first set the <a href="#accountset-flags">asfAccountTxnID</a> flag, so that the ledger keeps track of the ID for the account's previous transaction.</p>
<h3 id="memos">Memos</h3>
<p>The Memos field allows for arbitrary messaging data that can accompany the transaction. It is presented as an array of objects. Each object has only one field, <code>Memo</code>, which in turn contains another object with <em>one or more</em> of the following fields:</p>
<p>The <code>Memos</code> field allows for arbitrary messaging data that can accompany the transaction. It is presented as an array of objects. Each object has only one field, <code>Memo</code>, which in turn contains another object with <em>one or more</em> of the following fields:</p>
<table>
<thead>
<tr>
@@ -446,8 +476,42 @@
"Amount": "1"
}
</code></pre>
<h3 id="signers-field">Signers Field</h3>
<p>The <code>Signers</code> field contains a <a href="#multi-signing">multi-signature</a>, which has signatures from up to 8 key pairs, that together should authorize the transaction. The <code>Signers</code> list is an array of objects, each with one field, <code>Signer</code>. The <code>Signer</code> field has the following nested fields:</p>
<table>
<thead>
<tr>
<th>Field</th>
<th>Type</th>
<th><a href="https://wiki.ripple.com/Binary_Format">Internal Type</a></th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>Account</td>
<td>String</td>
<td>AccountID</td>
<td>The address associated with this signature, as it appears in the SignerList.</td>
</tr>
<tr>
<td>TxnSignature</td>
<td>String</td>
<td>Blob</td>
<td>A signature for this transaction, verifiable using the <code>SigningPubKey</code>.</td>
</tr>
<tr>
<td>SigningPubKey</td>
<td>String</td>
<td>PubKey</td>
<td>The public key used to create this signature.</td>
</tr>
</tbody>
</table>
<p>The <code>SigningPubKey</code> must be a key that is associated with the <code>Account</code> address. If the referenced <code>Account</code> is a funded account in the ledger, then the SigningPubKey can be that account's current Regular Key if one is set. It could also be that account's Master Key, unless the <a href="ripple-ledger.html#accountroot-flags">lsfDisableMaster</a> flag is enabled. If the referenced <code>Account</code> address is not a funded account in the ledger, then the <code>SigningPubKey</code> must be the master key associated with that address.</p>
<p>Because signature verification is a compute-intensive task, multi-signed transactions cost additional XRP to relay to the network. Each signature included in the multi-siganture increases the <code>Fee</code> required by the amount of the minimum transaction fee. For example, if the current minimum <code>Fee</code> value to relay a transaction to the network is <code>10000</code> drops, then a multi-signed transaction with 3 entries in the <code>Signers</code> array would cost <code>40000</code> drops to relay.</p>
<h3 id="flags">Flags</h3>
<p>The Flags field allows for additional boolean options regarding the behavior of a transaction. They are represented as binary values that can be combined with bitwise-or operations to set multiple flags at once.</p>
<p>The <code>Flags</code> field allows for additional boolean options regarding the behavior of a transaction. They are represented as binary values that can be combined with bitwise-or operations to set multiple flags at once.</p>
<p>Most flags only have meaning for a specific transaction type. The same bitwise value may be reused for flags on different transaction types, so it is important to pay attention to the <code>TransactionType</code> field when setting and reading flags.</p>
<p>The only flag that applies globally to all transactions is as follows:</p>
<table>
@@ -729,7 +793,7 @@
<tr>
<td>asfDisableMaster</td>
<td>4</td>
<td>Disallow use of the master key. Can only be enabled if the account has a <a href="#setregularkey">RegularKey</a> configured.</td>
<td>Disallow use of the master key. Can only be enabled if the account has configured another way to sign transactions, such as a <a href="#setregularkey">Regular Key</a> or a <a href="#signerlistset">Signer List</a>.</td>
<td>lsfDisableMaster</td>
</tr>
<tr>
@@ -844,9 +908,9 @@
</tr>
</tbody>
</table>
<p>Instead of using an account's master key to sign transactions, you can set an alternate key pair, called the "Regular Key". As long as the public key for this key pair is set in the <code>RegularKey</code> field of an account this way, then the secret of the Regular Key pair can be used to sign transactions. (The master secret can still be used, too, unless you set the <a href="#accountset-flags">asfDisableMaster account flag</a>.)</p>
<p>A Regular Key pair is generated in the same way as any other Ripple keys (for example, with <a href="reference-rippled.html#wallet-propose">wallet_propose</a>), but it can be changed. A Master Key pair is an intrinsic part of the account's identity (the address is derived from the master public key) so the Master Key cannot be changed. Therefore, using a Regular Key to sign transactions instead of the master key whenever possible is beneficial to security.</p>
<p>If your regular key is compromised, but the master key is not, you can use this method to regain control of your account. In some cases, you can even send a <a href="concept-transaction-cost.html#key-reset-transaction">key reset transaction</a> without paying the <a href="#transaction-cost">transaction cost</a>.</p>
<p>Instead of using an account's master key to sign transactions, you can set an alternate key pair, called the "Regular Key". As long as the public key for this key pair is set in the <code>RegularKey</code> field of an account this way, then the secret of the Regular Key pair can be used to sign transactions. (Other methods of signing transactions can also be used, including <a href="#multi-signing">multi-signing</a> or the master key.</p>
<p>A Regular Key pair is generated in the same way as any other Ripple keys (for example, with <a href="rippled-apis.html#wallet-propose">wallet_propose</a>), but it can be changed. A Master Key pair is an intrinsic part of the account's identity (the address is derived from the master public key). The Master Key can be <a href="#accountset-flags">disabled</a> but it cannot be changed. Therefore, it is beneficial to security sign transactions with a Regular Key instead of the master key whenever possible. For even greater security, you can use <a href="#multi-signing">multi-signing</a>, but multi-signing costs additional XRP in transaction fees and reserves.</p>
<p>If your regular key is compromised, but the master key is not, you can use a SetRegularKey transaction to regain control of your account. In some cases, you can even send a <a href="concept-transaction-cost.html#key-reset-transaction">key reset transaction</a> without paying the <a href="#transaction-cost">transaction cost</a>.</p>
<h2 id="offercreate">OfferCreate</h2>
<p><a href="https://github.com/ripple/rippled/blob/master/src/ripple/app/tx/impl/CreateOffer.cpp" title="Source">[Source]<br/></a></p>
<p>An OfferCreate transaction is effectively a <a href="http://en.wikipedia.org/wiki/limit_order">limit order</a>. It defines an intent to exchange currencies, and creates an Offer node in the Ripple Consensus Ledger if not completely fulfilled when placed. Offers can be partially fulfilled.</p>
@@ -1134,6 +1198,65 @@
</tr>
</tbody>
</table>
<h2 id="signerlistset">SignerListSet</h2>
<p><a href="https://github.com/ripple/rippled/blob/ef511282709a6a0721b504c6b7703f9de3eecf38/src/ripple/app/tx/impl/SetSignerList.cpp" title="Source">[Source]<br/></a></p>
<p>The SignerListSet transaction creates, modifies, or removes a list of signers that can be used to multi-sign a transaction.</p>
<p>Example SignerListSet:</p>
<pre><code>{
"Flags": 0,
"TransactionType": "SignerListSet",
"Account": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"Fee": "10000",
"SignerQuorum": 3,
"SignerEntries": [
{
"SignerEntry": {
"Account": "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight": 2
}
},
{
"SignerEntry": {
"Account": "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight": 1
}
},
{
"SignerEntry": {
"Account": "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight": 1
}
}
]
}
</code></pre>
<table>
<thead>
<tr>
<th>Field</th>
<th>JSON Type</th>
<th><a href="https://wiki.ripple.com/Binary_Format">Internal Type</a></th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>SignerQuorum</td>
<td>Number</td>
<td>UInt32</td>
<td>A target number for the signer weights. A multi-signature from this list is valid only if the sum weights of the signatures provided is equal or greater than this value. To delete a SignerList, use the value <code>0</code>.</td>
</tr>
<tr>
<td>SignerEntries</td>
<td>Array</td>
<td>Array</td>
<td>(Omitted when deleting) Array of <a href="ripple-ledger.html#signerentry-object">SignerEntry objects</a>, indicating the addresses and weights of signers in this list. A SignerList must have at least 1 member and no more than 8 members. No address may appear more than once in the list, nor may the <code>Account</code> submitting the transaction appear in the list.</td>
</tr>
</tbody>
</table>
<p>An account may not have more than one SignerList. A successful SignerListSet transaction replaces the existing SignerList, if one exists. To delete a SignerList, you must set <code>SignerQuorum</code> to <code>0</code> <em>and</em> omit the <code>SignerEntries</code> field. Otherwise, the transaction fails with the error <a href="#tem-codes">temMALFORMED</a>. A transaction to delete a SignerList is considered successful even if there was no SignerList to delete.</p>
<p>You cannot create a SignerList such that the SignerQuorum could never be met. The SignerQuorum must be greater than 0 but less than or equal to the sum of the <code>SignerWeight</code> values in the list. Otherwise, the transaction fails with the error <a href="#tem-codes">temMALFORMED</a>.</p>
<p>You cannot remove the last method of signing transactions from an account. If an account's master key is disabled (it has the <a href="ripple-ledger.html#accountroot-flags"><code>lsfDisableMaster</code> flag</a> enabled) and the account does not have a Regular Key configured, then you cannot delete the SignerList from the account. Instead, the transaction fails with the error <a href="#tec-codes">tecNO_ALTERNATIVE_KEY</a>.</p>
<h1 id="pseudo-transactions">Pseudo-Transactions</h1>
<p>Pseudo-Transactions are never submitted by users, nor propagated through the network. Instead, a server may choose to inject them in a proposed ledger directly. If enough servers inject an equivalent pseudo-transaction for it to pass consensus, then it becomes included in the ledger, and appears in ledger data thereafter.</p>
<p>Some of the fields that are mandatory for normal transactions do not make sense for pseudo-transactions. In those cases, the pseudo-transaction has the following default values:</p>
@@ -1586,6 +1709,18 @@
<td>temRIPPLE_EMPTY</td>
<td>The <a href="#payment">Payment</a> transaction includes an empty <code>Paths</code> field, but paths are necessary to complete this payment.</td>
</tr>
<tr>
<td>temBAD_WEIGHT</td>
<td>The <a href="#signerlistset">SignerListSet</a> transaction includes a <code>SignerWeight</code> that is invalid, for example a zero or negative value.</td>
</tr>
<tr>
<td>temBAD_SIGNER</td>
<td>The <a href="#signerlistset">SignerListSet</a> transaction includes a signer who is invalid: for example, it might be a duplicate, or it might be the account to which the SignerList belongs.</td>
</tr>
<tr>
<td>temBAD_QUORUM</td>
<td>The <a href="#signerlistset">SignerListSet</a> transaction has an invalid <code>SignerQuorum</code> value. Either the value is not greater than zero, or it is more than the sum of all signers in the list.</td>
</tr>
</tbody>
</table>
<h3 id="tef-codes">tef Codes</h3>
@@ -1650,6 +1785,22 @@
<td>tefMAX_LEDGER</td>
<td>The transaction included a <a href="#lastledgersequence"><code>LastLedgerSequence</code></a> parameter, but the current ledger's sequence number is already higher than the specified value.</td>
</tr>
<tr>
<td>tefBAD_SIGNATURE</td>
<td>The transaction was <a href="#multi-signing">multi-signed</a>, but contained a signature for an address not part of a SignerList associated with the sending account.</td>
</tr>
<tr>
<td>tefBAD_QUORUM</td>
<td>The transaction was <a href="#multi-signing">multi-signed</a>, but the total weights of all included signatures did not meet the quorum.</td>
</tr>
<tr>
<td>tefNOT_MULTI_SIGNING</td>
<td>The transaction was <a href="#multi-signing">multi-signed</a>, but the sending account has no SignerList defined.</td>
</tr>
<tr>
<td>tefBAD_AUTH_MASTER</td>
<td><span class="draft-comment">(something to do with the key not being the right one for this account)</span></td>
</tr>
</tbody>
</table>
<h3 id="ter-codes">ter Codes</h3>
@@ -1807,9 +1958,9 @@
<td><strong>DEPRECATED.</strong> Replaced by tecUNFUNDED_OFFER and tecUNFUNDED_PAYMENT.</td>
</tr>
<tr>
<td>tecMASTER_DISABLED</td>
<td>tecNO_ALTERNATIVE_KEY</td>
<td>130</td>
<td>The <a href="#setregularkey">SetRegularKey transaction</a> tried to unset the Regular Key, but the account has the <code>lsfDisableMaster</code> flag enabled. (Unsetting the Regular Key while also leaving the Master Key disabled would make the account unusable.)</td>
<td>The transaction tried to remove the only available method of signing transactions. This could be a <a href="#setregularkey">SetRegularKey transaction</a> to remove the Regular Key, a <a href="#signerlistset">SignerListSet transaction</a> to delete a SignerList, or an <a href="#accountset">AccountSet transaction</a> to disable the Master Key. (Prior to <a href="https://github.com/ripple/rippled/releases/tag/0.30.0">rippled 0.30.0</a>, this was called <code>tecMASTER_DISABLED</code> instead.)</td>
</tr>
<tr>
<td>tecNO_REGULAR_KEY</td>
@@ -1837,11 +1988,6 @@
<td>The <code>TakerPays</code> field of the <a href="#offercreate">OfferCreate transaction</a> specifies an asset whose issuer has <code>lsfRequireAuth</code> enabled, and the account making the offer does not have a trust line for that asset. (Normally, making an offer implicitly creates a trust line if necessary, but in this case it does not bother because you cannot hold the asset without authorization.) If the trust line exists, but is not authorized, tecNO_AUTH occurs instead.</td>
</tr>
<tr>
<td>tecINSUFF_FEE</td>
<td>136</td>
<td>The account sending the transaction does not possess enough XRP to pay the specified <code>Fee</code>. This error only occurs if the transaction has already been propagated through the network to achieve consensus,</td>
</tr>
<tr>
<td>tecFROZEN</td>
<td>137</td>
<td>The <a href="#offercreate">OfferCreate transaction</a> failed because one or both of the assets involved are subject to a <a href="concept-freeze.html">global freeze</a>.</td>
@@ -1849,22 +1995,22 @@
<tr>
<td>tecNO_TARGET</td>
<td>138</td>
<td><strong>FORTHCOMING</strong> Part of multi-signature transactions.</td>
<td><strong>FORTHCOMING</strong> Reserved for future features.</td>
</tr>
<tr>
<td>tecNO_PERMISSION</td>
<td>139</td>
<td><strong>FORTHCOMING</strong> Part of multi-signature transactions.</td>
<td><strong>FORTHCOMING</strong> Reserved for future features.</td>
</tr>
<tr>
<td>tecNO_ENTRY</td>
<td>140</td>
<td><strong>FORTHCOMING</strong> Part of multi-signature transactions.</td>
<td><strong>FORTHCOMING</strong> Reserved for future features.</td>
</tr>
<tr>
<td>tecINSUFFICIENT_RESERVE</td>
<td>141</td>
<td><strong>FORTHCOMING</strong> Part of multi-signature transactions. (Code may change; see <a href="https://ripplelabs.atlassian.net/browse/RIPD-743">RIPD-743</a> for status.)</td>
<td>The <a href="#signerlistset">SignerListSet</a> or other transaction would increase the <a href="concept-reserves.html">reserve requirement</a> higher than the sending account's balance. See <a href="ripple-ledger.html#signerlists-and-reserves">SignerLists and Reserves</a> for more information.</td>
</tr>
<tr>
<td>tecNEED_MASTER_KEY</td>

View File

@@ -46,6 +46,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -46,6 +46,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

View File

@@ -107,6 +107,13 @@ pages:
ripple.com: https://ripple.com/build/reliable-transaction-submission/
sidebar: true
- name: Multi-Signing Transactions
category: Tutorials
html: tutorial-multisign.html
md: tutorial-multisign.md
ripple.com: https://wiki.ripple.com/Multisign
sidebar: true
# Concepts are introductions that explain a topic.
# In the Dev Portal, these are mostly summaries of RCL features.
- name: Paths

View File

@@ -1,162 +0,0 @@
[
{
"name": "Overview",
"template":"template-index.html",
"html": "index.html",
"targets": ["local", "ripple.com"],
"sidebar": false
},
{
"name": "Ripple Developer Resources",
"template":"template-pdf_intro.html",
"html": "pdf_intro.html",
"targets": ["pdf"]
},
{
"name": "Paths",
"md":"paths.md",
"html":"paths.html",
"ripple.com": "https://ripple.com/build/paths/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Fees (Disambiguation)",
"md": "fees.md",
"html": "fees.html",
"ripple.com": "https://ripple.com/knowledge_center/fees-disambiguation/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Transfer Fees",
"md":"transferrate.md",
"html":"transfer_fees.html",
"ripple.com": "https://ripple.com/knowledge_center/transfer-fees/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Transaction Cost",
"md": "tx-cost.md",
"html": "tx-cost.html",
"ripple.com": "https://ripple.com/build/transaction-cost/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Fee Voting",
"md": "fee-voting.md",
"html": "fee-voting.html",
"ripple.com": "https://ripple.com/build/fee-voting/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Reserves",
"md": "reserves.md",
"html": "reserves.html",
"ripple.com": "https://ripple.com/build/reserves/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "Freeze",
"md": "freeze.md",
"html": "freeze.html",
"ripple.com": "https://ripple.com/build/freeze/",
"category": "Concepts",
"sidebar": "category-toc"
},
{
"name": "RippleAPI Quick Start Guide",
"md": "rippleapi_quickstart.md",
"html": "rippleapi_quickstart.html",
"category": "Tutorials",
"sidebar": "page-toc"
},
{
"name": "rippled",
"md":"rippled.md",
"html":"rippled-apis.html",
"ripple.com": "https://ripple.com/build/rippled-apis/",
"category": "References",
"sidebar": "page-toc"
},
{
"name": "rippled Setup",
"md":"rippled-setup.md",
"html":"rippled-setup.html",
"ripple.com": "https://ripple.com/build/rippled-setup/",
"category": "Tutorials",
"sidebar": "page-toc"
},
{
"name": "Transactions",
"md":"tx_format.md",
"html":"transactions.html",
"ripple.com": "https://ripple.com/build/transactions/",
"category": "References",
"sidebar": "page-toc"
},
{
"name": "Ledger Format",
"md":"ledger_format.md",
"html":"ripple-ledger.html",
"ripple.com": "https://ripple.com/build/ledger-format/",
"category": "References",
"sidebar": "page-toc"
},
{
"name": "Reliable Transaction Submission",
"md":"reliable_tx.md",
"html":"reliable_tx.html",
"ripple.com": "https://ripple.com/build/reliable-transaction-submission/",
"category": "Tutorials",
"sidebar": "page-toc"
},
{
"name": "Gateway Guide",
"md":"gateway_guide.md",
"html":"gateway_guide.html",
"ripple.com": "https://ripple.com/build/gateway-guide/",
"category": "Tutorials",
"sidebar": "page-toc"
},
{
"name": "Ripple Data API v2",
"md": "data_v2.md",
"html": "data_api_v2.html",
"ripple.com": "https://ripple.com/build/data-api-v2/",
"category": "References",
"sidebar": "page-toc"
},
{
"name": "RippleAPI",
"md": "https://raw.githubusercontent.com/ripple/ripple-lib/0.16.7/docs/index.md",
"html": "rippleapi.html",
"ripple.com": "https://ripple.com/build/rippleapi/",
"category": "References",
"sidebar": "page-toc"
},
{
"name": "WebSocket API Tool",
"template":"template-ripple-api-tool.html",
"category": "API Tools",
"ripple.com": "https://ripple.com/build/websocket-tool/",
"html": "ripple-api-tool.html",
"targets": ["local","ripple.com"],
"sidebar": "custom"
},
{
"name": "Data API v2 Tool",
"template":"template-rest-api-tool.html",
"methods_js": "js/apitool-methods-data_v2.js",
"category": "API Tools",
"rest_host": "https://data.ripple.com",
"html": "data-api-v2-tool.html",
"targets": ["local","ripple.com"],
"sidebar": "custom"
}
]

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">

797
tutorial-multisign.html Normal file
View File

@@ -0,0 +1,797 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta content="IE=edge,chrome=1" http-equiv="X-UA-Compatible">
<meta content="width=device-width" name="viewport">
<title>Multi-Signing Transactions - Ripple Developer Portal</title>
<!-- favicon -->
<link href="favicon.ico" rel="icon" type="image/x-icon">
<link href="favicon.ico" rel="shortcut icon" type="image/x-icon">
<!-- jQuery -->
<script src="assets/vendor/jquery-1.11.1.min.js"></script>
<!-- Custom Stylesheets. ripple.css includes bootstrap, font stuff -->
<link href="assets/css/ripple.css" rel="stylesheet"/>
<link href="assets/css/devportal.css" rel="stylesheet"/>
<!-- Bootstrap JS -->
<script src="assets/vendor/bootstrap.min.js"></script>
<!-- syntax highlighting -->
<link href="assets/vendor/docco.min.css" rel="stylesheet">
<script src="assets/vendor/highlight.min.js"></script>
<!-- syntax selection js -->
<script src="assets/js/multicodetab.js"></script>
<script>
$(document).ready(function() {
$().multicode_tabs();
hljs.initHighlighting();
make_code_expandable();
});
</script>
<script src="assets/js/expandcode.js"></script>
<script src="assets/js/fixsidebarscroll.js"></script>
</link></link></link></meta></meta></meta></head>
<body class="page page-template page-template-template-dev-portal page-template-template-dev-portal-php sidebar-primary wpb-js-composer js-comp-ver-3.6.2 vc_responsive">
<header class="banner navbar navbar-default navbar-fixed-top initial_header" role="banner">
<div class="container">
<div class="navbar-header">
<a class="navbar-brand" href="index.html"><img class="logo" src="assets/img/ripple-logo-color.png"/></a>
</div><!-- /.navbar-header -->
<div class="nav">
<div class="draft-warning">DRAFT PAGE</div>
</div><!-- /.nav -->
</div><!-- /.container -->
<div class="subnav dev_nav">
<div class="container">
<ul class="menu" id="menu-dev-menu">
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">References <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="reference-rippled.html">rippled</a></li>
<li><a href="reference-transaction-format.html">Transaction Format</a></li>
<li><a href="reference-ledger-format.html">Ledger Format</a></li>
<li><a href="reference-rippleapi.html">RippleAPI</a></li>
<li><a href="reference-data-api.html">Ripple Data API v2</a></li>
</ul>
</li>
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">Tutorials <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">Concepts <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="concept-paths.html">Paths</a></li>
<li><a href="concept-fees.html">Fees (Disambiguation)</a></li>
<li><a href="concept-transfer-fees.html">Transfer Fees</a></li>
<li><a href="concept-transaction-cost.html">Transaction Cost</a></li>
<li><a href="concept-fee-voting.html">Fee Voting</a></li>
<li><a href="concept-reserves.html">Reserves</a></li>
<li><a href="concept-freeze.html">Freeze</a></li>
</ul>
</li>
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">Best Practices <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="concept-issuing-and-operational-addresses.html">Issuing and Operational Addresses</a></li>
<li><a href="tutorial-gateway-guide.html">Gateway Guide</a></li>
</ul>
</li>
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">API Tools <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="ripple-api-tool.html">WebSocket API Tool</a></li>
<li><a href="data-api-v2-tool.html">Data API v2 Tool</a></li>
<li><a href="tool-jsonrpc.html">rippled JSON-RPC Tool</a></li>
</ul>
</li>
<li class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">Resources <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li><a href="https://forum.ripple.com/viewforum.php?f=2">Forums</a></li>
<li><a href="https://www.bountysource.com/teams/ripple/bounties">Bounties</a></li>
<li><a href="https://ripplelabs.atlassian.net/">Bug Tracking</a></li>
<li><a href="https://ripple.com/category/dev-blog/">Dev Blog</a></li>
<li><a href="https://ripple.com/press-releases/">Press Center</a></li>
<li><a href="https://ripple.com/brand-guidelines/">Brand Guidelines</a></li>
</ul>
<li><a href="https://github.com/ripple/ripple-dev-portal" title="GitHub">Site Source</a></li>
</li></ul><!-- /#dev-menu -->
</div><!-- /.subnav .container -->
</div><!-- /.subnav -->
</header>
<div class="wrap container" role="document">
<aside class="sidebar" role="complementary">
<div class="dev_nav_wrapper">
<div id="cont">
<ul class="dev_nav_sidebar">
<li class="level-1"><a href="index.html">Category: Tutorials</a></li>
<li class="level-2"><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li class="level-2"><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li class="level-2"><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li class="level-2"><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
<hr/>
<h5>In this page:</h5>
</div>
<script src="assets/js/jquery.gensidebar.js" type="text/javascript"></script>
</div>
</aside>
<main class="main" role="main">
<div class="content">
<h1 id="introduction-to-multi-signing">Introduction to Multi-Signing</h1>
<p>Multi-signing in Ripple is the act of authorizing transactions for the Ripple
Consensus Ledger by using a combination of multiple secret keys. After setting
up multi-signing for an account, you can put the master secret in cold storage,
or even disable the master key entirely. With multiple secret keys required to
authorize a multi-signature, you can improve security in several ways.</p>
<ul>
<li>If you keep an account's keys on different devices, a malicious user must compromise multiple machines in order to send transactions on your behalf.</li>
<li>If the keys to an account are in the custody of entirely different people, those people must collaborate in order to send transaction from that account.</li>
<li>You can use the SignerList as a backup, to delegate a group of others who can send transactions for you if you are unavailable or unable to sign using your regular key.</li>
<li>Even more uses than can be described here.</li>
</ul>
<h2 id="availability-of-multi-signing">Availability of Multi-Signing</h2>
<p>Multi-signing is due to be enabled by an <strong>Amendment</strong> to the Ripple Consensus
Protocol. This Amendment must be approved by a consensus of validators showing
consistent support for the feature over a period of time. For more information,
see Amendments (TODO: link).</p>
<p>You can test multi-signing by running <code>rippled</code> in stand-alone mode with the
feature enabled. In stand-alone mode, <code>rippled</code> does not communicate with the
rest of the Ripple peer-to-peer network, but you can perform most of the same
actions on your local server only. This way, you can be sure that you are ready
for multi-signing when it goes live.</p>
<h1 id="how-to-multi-sign">How to Multi-Sign</h1>
<p>The basic process of Multi-Signing a transaction is necessarily more
complex than the process of signing a transaction with a single master key or
regular key. </p>
<h2 id="1-download-and-build-rippled-with-multi-sign">1. Download and build rippled with multi-sign</h2>
<p>Until a binary for <code>rippled</code> with multi-signing is available, the best you can do is build it from source.</p>
<pre><code>$ git clone git@github.com:scottschurr/rippled.git (TODO: switch to a Ripple Labs repo when available)
$ git checkout fix-sign_for
$ scons
</code></pre>
<p>See <a href="https://wiki.ripple.com/Rippled_build_instructions">rippled build instructions</a> for help building from source.</p>
<h2 id="2-configure-rippled-to-enable-multisign">2. Configure rippled to enable MultiSign</h2>
<p>Add the following to the bottom of the config file:</p>
<pre><code>[features]
MultiSign
</code></pre>
<p>Note that this stanza is case-sensitive.</p>
<h2 id="3-start-rippled-in-stand-alone-mode">3. Start rippled in stand-alone mode</h2>
<p>If you have previously synced to the network, you can have the server load the
latest ledger as a starting place for stand-alone mode using the <code>--load</code>
commandline option:</p>
<pre><code>$ sudo ./build/rippled --conf=/home/mduo13/.config/ripple/rippled.cfg -a --load
</code></pre>
<p>If you'd rather start from scratch, you can use the <code>--start</code> commandline
option to create a fresh ledger. In this case, the root account holds all
100 billion XRP:</p>
<p><strong>Address:</strong> <code>rHb9CJAWyB4rj91VRWn96DkukG4bwdtyTh</code></p>
<p><strong>Secret:</strong> <code>snoPBrXtMeMyMHUVTgbuqAfg1SUTb</code> ("masterpassphrase")</p>
<h2 id="4-generate-keys-for-a-new-wallet">4. Generate keys for a new wallet</h2>
<p>This step is not strictly necessary. For this process, we generate the keys to
a new Ripple account and then set up multi-signing for that account. To set up
multi-signing on an existing Ripple account, just use the keys to that account.</p>
<pre><code>$ build/rippled wallet_propose
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"account_id" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"key_type" : "secp256k1",
"master_key" : "NED MANA SPA BLUR HERS HEAT RED NIBS MAIN MELT NOB RARE",
"master_seed" : "shqZZy2Rzs9ZqWTCQAdqc3bKgxnYq",
"master_seed_hex" : "99C7F2DCD88218372B7509ADF7DC562B",
"public_key" : "aBPvx491i2ZPVzmxoAmAVq5qXAxAZgmjfxoMTxFCg9Xxf2xwVVLc",
"public_key_hex" : "0303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D",
"status" : "success"
}
}
</code></pre>
<p>As always, be sure that an account's secret key never gets transmitted to
anyone you don't trust with full control of that account, and certainly not
unencrypted over the network.</p>
<h2 id="5-fund-the-new-account-with-an-existing-wallet">5. Fund the new account with an existing wallet</h2>
<p>Again, this step is only necessary if you are setting up a new account to use
multi-signing for this example.</p>
<pre><code>$ build/rippled submit &lt;your existing account secret&gt; '{
&gt; "TransactionType" : "Payment",
&gt; "Account" : "&lt;your existing account address&gt;",
&gt; "Destination" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
&gt; "Amount" : "100000000",
&gt; "Flags": 2147483648
&gt; }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "1200002280000000240000001E614000000005F5E10068400000000000000A7321023693F15967AE357D0327974AD46FE3C127113B1110D6044FD41E723689F81CC67446304402207AB5D16F58E9E6ADBBDD24837CAB80D871860E47EB0840FE57403FB979755A6D022015FE7A8838BEE6C18962C246D6D27791B7EE34B93415AE3824D12564E7A886C6811493B89AFCAD4C8EAC2B131C1331FEF12AE1522BBE83142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rN7n7otQDd6FczFgLdSqtcsAUxDkw6fzRH",
"Amount" : "100000000",
"Destination" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "10",
"Flags" : 2147483648,
"Sequence" : 30,
"SigningPubKey" : "023693F15967AE357D0327974AD46FE3C127113B1110D6044FD41E723689F81CC6",
"TransactionType" : "Payment",
"TxnSignature" : "304402207AB5D16F58E9E6ADBBDD24837CAB80D871860E47EB0840FE57403FB979755A6D022015FE7A8838BEE6C18962C246D6D27791B7EE34B93415AE3824D12564E7A886C6",
"hash" : "8C7A4D35D71CE80DA4EDAC91D620B6A348B7691B78AA2896284135378E10E0C2"
}
}
}
</code></pre>
<h2 id="6-manually-close-the-ledger">6. Manually close the ledger</h2>
<p>In the live network, you would simply wait for the ledger to close
automatically as the result of consensus. However, a rippled node running in
stand-alone mode does not engage in consensus, so you must manually close the
ledger with the <a href="rippled-apis.html#ledger-accept"><code>ledger_accept</code> command</a>.</p>
<pre><code>$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061437,
"status" : "success"
}
}
</code></pre>
<h2 id="7-create-a-signerlist-on-the-new-account-with-a-signerlistset-transaction">7. Create a SignerList on the new account with a SignerListSet transaction</h2>
<p>Before you can multi-sign transactions, you must associate a SignerList with
your account, so that RCL knows which keys can be used to sign for you. You do
this with a <a href="transactions.html#signerlistset">SignerListSet transaction</a>.</p>
<p>In this example, the SignerList has 3 members, with the weights and quorum set
up such that multi-signed transactions need a signature from
rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW plus at least one signature from the other
two members of the list. The <code>Account</code> values you use in your list can be
funded accounts that exist in the ledger or just unused addresses.</p>
<pre><code>$ build/rippled submit shqZZy2Rzs9ZqWTCQAdqc3bKgxnYq '{
&gt; "Flags": 0,
&gt; "TransactionType": "SignerListSet",
&gt; "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
&gt; "Fee": "10000",
&gt; "SignerQuorum": 3,
&gt; "SignerEntries": [
&gt; {
&gt; "SignerEntry": {
&gt; "Account": "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
&gt; "SignerWeight": 2
&gt; }
&gt; },
&gt; {
&gt; "SignerEntry": {
&gt; "Account": "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
&gt; "SignerWeight": 1
&gt; }
&gt; },
&gt; {
&gt; "SignerEntry": {
&gt; "Account": "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
&gt; "SignerWeight": 1
&gt; }
&gt; }
&gt; ]
&gt; }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "12000C2200000000240000000120230000000368400000000000271073210303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D74473045022100BEDFA12502C66DDCB64521972E5356F4DB965F553853D53D4C69B4897F11B4780220595202D1E080345B65BAF8EBD6CA161C227F1B62C7E72EA5CA282B9434A6F04281142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1F4EB1300028114204288D2E47F8EF6C99BCC457966320D12409711E1EB13000181147908A7F0EDD48EA896C3580A399F0EE78611C8E3E1EB13000181143A4C02EA95AD6AC3BED92FA036E0BBFB712C030CE1F1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "10000",
"Flags" : 0,
"Sequence" : 1,
"SignerEntries" : [
{
"SignerEntry" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight" : 2
}
},
{
"SignerEntry" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight" : 1
}
},
{
"SignerEntry" : {
"Account" : "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight" : 1
}
}
],
"SignerQuorum" : 3,
"SigningPubKey" : "0303E20EC6B4A39A629815AE02C0A1393B9225E3B890CAE45B59F42FA29BE9668D",
"TransactionType" : "SignerListSet",
"TxnSignature" : "3045022100BEDFA12502C66DDCB64521972E5356F4DB965F553853D53D4C69B4897F11B4780220595202D1E080345B65BAF8EBD6CA161C227F1B62C7E72EA5CA282B9434A6F042",
"hash" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756"
}
}
}
</code></pre>
<h2 id="8-manually-close-the-ledger-again">8. Manually close the ledger again</h2>
<p>As before, you would wait for the ledger to close on a live network. We use
the <a href="rippled-apis.html#ledger-accept"><code>ledger_accept</code> command</a> to manually
close the ledger when running <code>rippled</code> in stand-alone mode.</p>
<pre><code>$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061438,
"status" : "success"
}
}
</code></pre>
<h2 id="9-confirm-the-presence-of-the-new-signer-list-using-account-objects">9. Confirm the presence of the new signer list using account_objects</h2>
<p>Normally an account has lots of different types of objects, but for this new
account, the only thing we've done is add a SignerList, so it should be easy to
find in the results of the
<a href="rippled-apis.html#account-objects"><code>account_objects</code> command</a>.</p>
<pre><code>$ build/rippled account_objects rnBFvgZphmN39GWzUJeUitaP22Fr9be75H
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"account_objects" : [
{
"Flags" : 0,
"LedgerEntryType" : "SignerList",
"OwnerNode" : "0000000000000000",
"PreviousTxnID" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756",
"PreviousTxnLgrSeq" : 16061437,
"SignerEntries" : [
{
"SignerEntry" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SignerWeight" : 2
}
},
{
"SignerEntry" : {
"Account" : "raKEEVSGnKSD9Zyvxu4z6Pqpm4ABH8FS6n",
"SignerWeight" : 1
}
},
{
"SignerEntry" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SignerWeight" : 1
}
}
],
"SignerListID" : 0,
"SignerQuorum" : 3,
"index" : "92373B9F1683001079764527F0BD553ED8656A9934FE641A7F0A0BF4DB230E0E"
}
],
"ledger_current_index" : 16061438,
"status" : "success",
"validated" : false
}
}
</code></pre>
<h2 id="10-create-a-new-transaction-that-you-plan-to-multi-sign">10. Create a new transaction that you plan to multi-sign</h2>
<p>You have to specify <em>everything</em> about this transaction, including Fee and
Sequence. Also include the field <code>SigningPubKey</code> as an empty string -- this
indicates that the transaction is multi-signed.</p>
<p>Here's an example transaction we can send from our test account:</p>
<pre><code>{
"TransactionType": "TrustSet",
"Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Flags": 262144,
"LimitAmount": {
"currency": "USD",
"issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value": "100"
},
"Sequence": 2,
"SigningPubKey":"",
"Fee": "12000"
}
</code></pre>
<p>(If you started from a fresh ledger, you first need to fund the account
specified by the <code>issuer</code> in this example, and then manually close the ledger.)</p>
<p>Keep in mind that the <code>Fee</code> for multi-signed transactions is significantly
higher than for regularly-signed transactions. It should be (N+1) times the
normal fee, where N is the number of signatures you plan to provide. Given that
it sometimes takes a while to collect signatures from multiple sources, you may
want to include additional buffer in case the load fee increases in that time.</p>
<h2 id="11-get-a-signature-using-the-sign-for-command">11. Get a signature using the sign_for command</h2>
<pre><code>$ build/rippled sign_for rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW &lt;rsA2's secret&gt; '{
&gt; "TransactionType": "TrustSet",
&gt; "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
&gt; "Flags": 262144,
&gt; "LimitAmount": {
&gt; "currency": "USD",
&gt; "issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
&gt; "value": "100"
&gt; },
&gt; "Sequence": 2,
&gt; "SigningPubKey":"",
&gt; "Fee": "12000"
&gt; }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
}
],
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "4622B2893AF3A70B4DB1FF86B25C10E92B71973895143E66029567A8541A8060"
}
}
}
</code></pre>
<p>The valuable part in the response is the <code>Signers</code> field. This is the part that
you're going to need later in order to construct the full, multi-signed
transaction.</p>
<p>The other parts, such as the <code>tx_blob</code>, are not very useful at this point,
unless you're "multi-signing" a transaction with only one signature.</p>
<h2 id="12-get-additional-signatures-the-same-way">12. Get additional signatures the same way</h2>
<p>If the accounts in your SignerList are funded accounts, the secret key you use
to sign for those accounts can come from the regular key (if they have one), or
the master key (unless it's disabled). For accounts that don't exist in the
ledger, you can only use the master secret associated with the address.</p>
<pre><code>$ build/rippled sign_for rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v &lt;rUpy's secret&gt; '{
"TransactionType": "TrustSet",
"Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Flags": 262144,
"LimitAmount": {
"currency": "USD",
"issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value": "100"
},
"Sequence": 2,
"SigningPubKey":"",
"Fee": "12000"
}'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Signers" : [
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "4622B2893AF3A70B4DB1FF86B25C10E92B71973895143E66029567A8541A8060"
}
}
}
</code></pre>
<p>Depending on the SignerList you configured, you may need to repeat this step
several times in order to get signatures from all the necessary parties.</p>
<h2 id="13-combine-the-signatures-and-submit">13. Combine the signatures and submit</h2>
<p>Take the contents of all the <code>Signers</code> arrays from all the responses, and
concatenate them in to a single <code>Signers</code> array field. The commandline syntax
for the <a href="rippled-apis.html#submit-multisigned"><code>submit_multisigned</code> command</a>
takes a single JSON object with two elements: this combined <code>Signers</code> array;
and <code>tx_json</code>, which is the transaction JSON that they signed.</p>
<p>This command actually submits the transaction for inclusion in the ledger. In
online mode, this relays it to other members of the network.</p>
<pre><code>$ build/rippled submit_multisigned ' {
&gt; "Signers": [
&gt; {
&gt; "Signer" : {
&gt; "Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
&gt; "SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
&gt; "TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
&gt; }
&gt; },
&gt; {
&gt; "Signer" : {
&gt; "Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
&gt; "SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
&gt; "TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
&gt; }
&gt; }
&gt; ],
&gt; "tx_json": {
&gt; "TransactionType": "TrustSet",
&gt; "Account": "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
&gt; "Flags": 262144,
&gt; "LimitAmount": {
&gt; "currency": "USD",
&gt; "issuer": "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
&gt; "value": "100"
&gt; },
&gt; "Sequence": 2,
&gt; "SigningPubKey":"",
&gt; "Fee": "12000"
&gt; }
&gt; }'
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"engine_result" : "tesSUCCESS",
"engine_result_code" : 0,
"engine_result_message" : "The transaction was applied. Only final in a validated ledger.",
"status" : "success",
"tx_blob" : "1200142200040000240000000263D5038D7EA4C6800000000000000000000000000055534400000000004B4E9C06F24296074F7BC48F92A97916C6DC5EA9684000000000002EE0730081142DECAB42CA805119A9BA2FF305C9AFA12F0B86A1F3E010732102B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF7447304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE8114204288D2E47F8EF6C99BCC457966320D12409711E1E0107321028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B7446304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E181147908A7F0EDD48EA896C3580A399F0EE78611C8E3E1F1",
"tx_json" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
},
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"hash" : "878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78"
}
}
}
</code></pre>
<p>Take note of the <code>hash</code> value from the response (In this case, it's
<code>878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78</code>) so you can
check the results of the transaction later.</p>
<h2 id="14-manually-close-the-ledger-one-last-time">14. Manually close the ledger one last time</h2>
<p>Once again, you would wait for the ledger to close on a live network. We use
the <a href="rippled-apis.html#ledger-accept"><code>ledger_accept</code> command</a> to manually
close the ledger when running <code>rippled</code> in stand-alone mode.</p>
<pre><code>$ build/rippled ledger_accept
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"ledger_current_index" : 16061439,
"status" : "success"
}
}
</code></pre>
<h2 id="15-confirm-the-results-of-the-transaction">15. Confirm the results of the transaction</h2>
<p>Use the hash value from the response to the <code>submit_multisigned</code> command.</p>
<pre><code>$ build/rippled tx 878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78
Loading: "/home/mduo13/.config/ripple/rippled.cfg"
Connecting to 127.0.0.1:5005
{
"result" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Fee" : "12000",
"Flags" : 262144,
"LimitAmount" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "100"
},
"Sequence" : 2,
"Signers" : [
{
"Signer" : {
"Account" : "rsA2LpzuawewSBQXkiju3YQTMzW13pAAdW",
"SigningPubKey" : "02B3EC4E5DD96029A647CFA20DA07FE1F85296505552CCAC114087E66B46BD77DF",
"TxnSignature" : "304502210093EED0F75190385282C6369EE3C5C0FCC65227917F545EC8848B94E17105BC3D022073B3FB14452056FF8E966736150E2D75F3B7460AD7DEF6E2932ECD6690B6C3FE"
}
},
{
"Signer" : {
"Account" : "rUpy3eEg8rqjqfUoLeBnZkscbKbFsKXC3v",
"SigningPubKey" : "028FFB276505F9AC3F57E8D5242B386A597EF6C40A7999F37F1948636FD484E25B",
"TxnSignature" : "304402204C1A4FFE1628A4BBEA4E8BEDE7C7080B94299704207479D1334096721629DB9802206BB07EBAB23EA288D5714CF7D3231D041BBB2AFD973D24ED693197C4881DC2E1"
}
}
],
"SigningPubKey" : "",
"TransactionType" : "TrustSet",
"date" : 496881900,
"hash" : "878C1C988305D87070F3E961FC27AC9D02C46FFDD92FC7EBB74E962344E58C78",
"inLedger" : 16061438,
"ledger_index" : 16061438,
"meta" : {
"AffectedNodes" : [
{
"ModifiedNode" : {
"LedgerEntryType" : "AccountRoot",
"LedgerIndex" : "13F1A95D7AAB7108D5CE7EEAF504B2894B8C674E6D68499076441C4837282BF8",
"PreviousTxnID" : "6ECC8C16B76D9B9AB099CA96DD653D8A321C34F1E5972D5EE6DBA19418F4D0CC",
"PreviousTxnLgrSeq" : 16061436
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Flags" : 0,
"Owner" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"RootIndex" : "3B9C0CE77FCE7BCEE1A68F1E26AC467AF326239D0D816CE705E4A0E2DAD03F6D"
},
"LedgerEntryType" : "DirectoryNode",
"LedgerIndex" : "3B9C0CE77FCE7BCEE1A68F1E26AC467AF326239D0D816CE705E4A0E2DAD03F6D"
}
},
{
"CreatedNode" : {
"LedgerEntryType" : "RippleState",
"LedgerIndex" : "3C75A1F3DB61406AC2A9493038E8394A73F103C9229695AC7E57EB0F8AFC69E4",
"NewFields" : {
"Balance" : {
"currency" : "USD",
"issuer" : "rrrrrrrrrrrrrrrrrrrrBZbvji",
"value" : "0"
},
"Flags" : 65536,
"HighLimit" : {
"currency" : "USD",
"issuer" : "rf1BiGeXwwQoi8Z2ueFYTEXSwuJYfV2Jpn",
"value" : "0"
},
"LowLimit" : {
"currency" : "USD",
"issuer" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"value" : "100"
}
}
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Account" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"Balance" : "109978000",
"Flags" : 0,
"OwnerCount" : 6,
"Sequence" : 3
},
"LedgerEntryType" : "AccountRoot",
"LedgerIndex" : "3D728C1F82CFE419F2DC58707D1AD06E985A29217D21A991ADF154184B664F4F",
"PreviousFields" : {
"Balance" : "109990000",
"OwnerCount" : 5,
"Sequence" : 2
},
"PreviousTxnID" : "3950D98AD20DA52EBB1F3937EF32F382D74092A4C8DF9A0B1A06ED25200B5756",
"PreviousTxnLgrSeq" : 16061437
}
},
{
"ModifiedNode" : {
"FinalFields" : {
"Flags" : 0,
"Owner" : "rnBFvgZphmN39GWzUJeUitaP22Fr9be75H",
"RootIndex" : "95DA402B4D58FBFF6BAA4CB84BBC21348CC273949B61FEBCE758410EF90D147D"
},
"LedgerEntryType" : "DirectoryNode",
"LedgerIndex" : "95DA402B4D58FBFF6BAA4CB84BBC21348CC273949B61FEBCE758410EF90D147D"
}
}
],
"TransactionIndex" : 0,
"TransactionResult" : "tesSUCCESS"
},
"status" : "success",
"validated" : true
}
}
</code></pre>
<p>In particular, check that the <code>TransactionResult</code> is the string <code>tesSUCCESS</code>. </p>
<p>On the live network, you must also confirm that the <code>validated</code> field is set to
the boolean <code>true</code>. If not, you might need to wait longer for the consensus
process to finish; or your transaction may be unable to be included in a ledger
for some reason. In stand-alone mode, the server automatically considers a
ledger to be <code>validated</code> if it has been manually closed.</p>
</div>
</main>
</div>
<footer class="content-info" role="contentinfo">
<div class="container">
<div class="row">
<section class="col-sm-3 widget nav_menu-3 widget_nav_menu">
<h4>Resources<hr/></h4>
<ul class="menu" id="menu-resources">
<li class="menu-insights"><a href="https://ripple.com/insights/">Insights</a></li>
<li class="menu-press-center"><a href="https://ripple.com/press-center/">Press Center</a></li>
<li class="menu-media-resources"><a href="https://ripple.com/media-resources/">Media Resources</a></li>
<li class="menu-videos"><a href="https://ripple.com/videos/">Videos</a></li>
<li class="menu-whitepapers-reports"><a href="https://ripple.com/whitepapers-reports/">Whitepapers &amp; Reports</a></li>
<li class="menu-xrp-portal"><a href="https://ripple.com/xrp-portal/">XRP Portal</a></li>
</ul>
</section>
<section class="col-sm-3 widget nav_menu-5 widget_nav_menu">
<h4>Regulators<hr/></h4>
<ul class="menu" id="menu-compliance-regulatory-relations"><li class="menu-compliance"><a href="https://ripple.com/compliance/">Compliance</a></li>
<li class="menu-policy-framework"><a href="https://ripple.com/policy-framework/">Policy Framework</a></li>
</ul>
</section>
<section class="col-sm-3 widget nav_menu-4 widget_nav_menu">
<h4>Support<hr/></h4>
<ul class="menu" id="menu-dev-footer-menu">
<li class="menu-contact-us"><a href="https://ripple.com/contact/">Contact Us</a></li>
<li class="active menu-developer-center"><a href="https://ripple.com/build/">Developer Center</a></li>
<li class="menu-knowledge-center"><a href="https://ripple.com/learn/">Knowledge Center</a></li>
<li class="menu-ripple-forum"><a href="https://forum.ripple.com/" target="_blank">Ripple Forum</a></li>
</ul>
</section>
<section class="col-sm-3 widget nav_menu-2 widget_nav_menu">
<h4>About<hr/></h4>
<ul class="menu" id="menu-company-footer">
<li class="menu-our-company"><a href="https://ripple.com/company/">Our Company</a></li>
<li class="menu-careers"><a href="https://ripple.com/company/careers/">Careers</a></li>
</ul>
</section>
<div class="col-sm-12 absolute_bottom_footer">
<div class="col-sm-8">
<span>© 2013-2015 Ripple Labs, Inc. All Rights Reserved.</span>
<span><a href="https://ripple.com/terms-of-use/">Terms</a></span>
<span><a href="https://ripple.com/privacy-policy/">Privacy</a></span>
</div>
</div><!-- /.absolute_bottom_footer -->
</div><!-- /.row -->
</div><!-- /.container -->
</footer>
</body>
</html>

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -113,6 +114,7 @@
<li class="level-2"><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li class="level-2"><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li class="level-2"><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li class="level-2"><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
<hr/>
<h5>In this page:</h5>

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -113,6 +114,7 @@
<li class="level-2"><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li class="level-2"><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li class="level-2"><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li class="level-2"><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
<hr/>
<h5>In this page:</h5>

View File

@@ -60,6 +60,7 @@
<li><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
</li>
<li class="dropdown">
@@ -113,6 +114,7 @@
<li class="level-2"><a href="tutorial-rippleapi-beginners-guide.html">RippleAPI Beginners Guide</a></li>
<li class="level-2"><a href="tutorial-rippled-setup.html">rippled Setup</a></li>
<li class="level-2"><a href="tutorial-reliable-transaction-submission.html">Reliable Transaction Submission</a></li>
<li class="level-2"><a href="tutorial-multisign.html">Multi-Signing Transactions</a></li>
</ul>
<hr/>
<h5>In this page:</h5>