rippled
Loading...
Searching...
No Matches
Transaction.h
1#pragma once
2
3#include <xrpl/basics/RangeSet.h>
4#include <xrpl/beast/utility/Journal.h>
5#include <xrpl/protocol/ErrorCodes.h>
6#include <xrpl/protocol/Protocol.h>
7#include <xrpl/protocol/STBase.h>
8#include <xrpl/protocol/STTx.h>
9#include <xrpl/protocol/TER.h>
10#include <xrpl/protocol/TxMeta.h>
11#include <xrpl/protocol/TxSearched.h>
12
13#include <optional>
14#include <variant>
15
16namespace xrpl {
17
18//
19// Transactions should be constructed in JSON with. Use STObject::parseJson to
20// obtain a binary version.
21//
22
23class Application;
24class Database;
25class Rules;
26
28 NEW = 0, // just received / generated
29 INVALID = 1, // no valid signature, insufficient funds
30 INCLUDED = 2, // added to the current ledger
31 CONFLICTED = 3, // losing to a conflicting transaction
32 COMMITTED = 4, // known to be in a ledger
33 HELD = 5, // not valid now, maybe later
34 REMOVED = 6, // taken out of a ledger
35 OBSOLETE = 7, // a compatible transaction has taken precedence
36 INCOMPLETE = 8 // needs more signatures
37};
38
39// This class is for constructing and examining transactions.
40// Transactions are static so manipulation functions are unnecessary.
41class Transaction : public std::enable_shared_from_this<Transaction>,
42 public CountedObject<Transaction>
43{
44public:
46 using ref = pointer const&;
47
49
50 // The two boost::optional parameters are because SOCI requires
51 // boost::optional (not std::optional) parameters.
54 boost::optional<std::uint64_t> const& ledgerSeq,
55 boost::optional<std::string> const& status,
56 Blob const& rawTxn,
57 Application& app);
58
59 // The boost::optional parameter is because SOCI requires
60 // boost::optional (not std::optional) parameters.
61 static TransStatus
62 sqlTransactionStatus(boost::optional<std::string> const& status);
63
66 {
67 return mTransaction;
68 }
69
70 uint256 const&
71 getID() const
72 {
73 return mTransactionID;
74 }
75
77 getLedger() const
78 {
79 return mLedgerIndex;
80 }
81
82 bool
84 {
85 return mLedgerIndex != 0;
86 }
87
89 getStatus() const
90 {
91 return mStatus;
92 }
93
94 TER
96 {
97 return mResult;
98 }
99
100 void
101 setResult(TER terResult)
102 {
103 mResult = terResult;
104 }
105
106 void
108 TransStatus status,
109 std::uint32_t ledgerSeq,
110 std::optional<uint32_t> transactionSeq = std::nullopt,
112
113 void
115 {
116 mStatus = status;
117 }
118
119 void
121 {
122 mLedgerIndex = ledger;
123 }
124
128 void
130 {
131 // Note that all access to mApplying are made by NetworkOPsImp, and must
132 // be done under that class's lock.
133 mApplying = true;
134 }
135
141 bool
143 {
144 // Note that all access to mApplying are made by NetworkOPsImp, and must
145 // be done under that class's lock.
146 return mApplying;
147 }
148
152 void
154 {
155 // Note that all access to mApplying are made by NetworkOPsImp, and must
156 // be done under that class's lock.
157 mApplying = false;
158 }
159
161 {
165 void
167 {
168 applied = false;
169 broadcast = false;
170 queued = false;
171 kept = false;
172 }
173
178 bool
179 any() const
180 {
181 return applied || broadcast || queued || kept;
182 }
183
184 bool applied = false;
185 bool broadcast = false;
186 bool queued = false;
187 bool kept = false;
188 };
189
196 {
197 return submitResult_;
198 }
199
203 void
208
212 void
214 {
215 submitResult_.applied = true;
216 }
217
221 void
223 {
224 submitResult_.queued = true;
225 }
226
230 void
232 {
234 }
235
239 void
241 {
242 submitResult_.kept = true;
243 }
244
266
273 {
274 return currentLedgerState_;
275 }
276
284 void
286 LedgerIndex validatedLedger,
287 XRPAmount fee,
288 std::uint32_t accountSeq,
289 std::uint32_t availableSeq)
290 {
291 currentLedgerState_.emplace(validatedLedger, fee, accountSeq, availableSeq);
292 }
293
295 getJson(JsonOptions options, bool binary = false) const;
296
297 // Information used to locate a transaction.
298 // Contains a nodestore hash and ledger sequence pair if the transaction was
299 // found. Otherwise, contains the range of ledgers present in the database
300 // at the time of search.
301 struct Locator
302 {
304
305 // @return true if transaction was found, false otherwise
306 //
307 // Call this function first to determine the type of the contained info.
308 // Calling the wrong getter function will throw an exception.
309 // See documentation for the getter functions for more details
310 bool
315
316 // @return key used to find transaction in nodestore
317 //
318 // Throws if isFound() returns false
319 uint256 const&
324
325 // @return sequence of ledger containing the transaction
326 //
327 // Throws is isFound() returns false
328 uint32_t
333
334 // @return range of ledgers searched
335 //
336 // Throws if isFound() returns true
342 };
343
344 static Locator
345 locate(uint256 const& id, Application& app);
346
347 static std::
349 load(uint256 const& id, Application& app, error_code_i& ec);
350
351 static std::
353 load(
354 uint256 const& id,
355 Application& app,
357 error_code_i& ec);
358
359private:
360 static std::
362 load(
363 uint256 const& id,
364 Application& app,
366 error_code_i& ec);
367
369
375 /* Note that all access to mApplying are made by NetworkOPsImp,
376 and must be done under that class's lock. This avoids the overhead of
377 taking a separate lock, and the consequences of a race condition are
378 nearly-zero.
379
380 1. If there is a race condition, and getApplying returns false when it
381 should be true, the transaction will be processed again. Not that
382 big a deal if it's a rare one-off. Most of the time, it'll get
383 tefALREADY or tefPAST_SEQ.
384 2. On the flip side, if it returns true, when it should be false, then
385 the transaction must have been attempted recently, so no big deal if
386 it doesn't immediately get tried right away.
387 3. If there's a race between setApplying and clearApplying, and the
388 flag ends up set, then a batch is about to try to process the
389 transaction and will call clearApplying later. If it ends up
390 cleared, then it might get attempted again later as is the case with
391 item 1.
392 */
393 bool mApplying = false;
394
397
399
403};
404
405} // namespace xrpl
Represents a JSON value.
Definition json_value.h:130
A generic endpoint for log messages.
Definition Journal.h:40
Tracks the number of instances of an object.
std::shared_ptr< STTx const > mTransaction
void setApplying()
Set this flag once added to a batch.
Application & mApp
std::optional< uint32_t > mTxnSeq
std::optional< CurrentLedgerState > getCurrentLedgerState() const
getCurrentLedgerState Get current ledger state of transaction
TransStatus mStatus
void setKept()
setKept Set this flag once was put to localtxns queue
LedgerIndex mLedgerIndex
LedgerIndex getLedger() const
Definition Transaction.h:77
void setQueued()
setQueued Set this flag once was put into held-txns queue
void clearSubmitResult()
clearSubmitResult Clear all flags in SubmitResult
void clearApplying()
Indicate that transaction application has been attempted.
void setApplied()
setApplied Set this flag once was applied to open ledger
void setStatus(TransStatus status, std::uint32_t ledgerSeq, std::optional< uint32_t > transactionSeq=std::nullopt, std::optional< uint32_t > networkID=std::nullopt)
SubmitResult getSubmitResult() const
getSubmitResult Return submit result
std::optional< uint32_t > mNetworkID
beast::Journal j_
SubmitResult submitResult_
different ways for transaction to be accepted
TransStatus getStatus() const
Definition Transaction.h:89
void setCurrentLedgerState(LedgerIndex validatedLedger, XRPAmount fee, std::uint32_t accountSeq, std::uint32_t availableSeq)
setCurrentLedgerState Set current ledger state of transaction
void setResult(TER terResult)
static Transaction::pointer transactionFromSQL(boost::optional< std::uint64_t > const &ledgerSeq, boost::optional< std::string > const &status, Blob const &rawTxn, Application &app)
std::optional< CurrentLedgerState > currentLedgerState_
void setStatus(TransStatus status)
void setBroadcast()
setBroadcast Set this flag once was broadcasted via network
uint256 const & getID() const
Definition Transaction.h:71
void setLedger(LedgerIndex ledger)
static std::variant< std::pair< std::shared_ptr< Transaction >, std::shared_ptr< TxMeta > >, TxSearched > load(uint256 const &id, Application &app, error_code_i &ec)
Json::Value getJson(JsonOptions options, bool binary=false) const
static Locator locate(uint256 const &id, Application &app)
std::shared_ptr< STTx const > const & getSTransaction()
Definition Transaction.h:65
static TransStatus sqlTransactionStatus(boost::optional< std::string > const &status)
bool isValidated() const
Definition Transaction.h:83
pointer const & ref
Definition Transaction.h:46
bool getApplying()
Detect if transaction is being batched.
T is_same_v
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition algorithm.h:5
TransStatus
Definition Transaction.h:27
@ REMOVED
Definition Transaction.h:34
@ INVALID
Definition Transaction.h:29
@ OBSOLETE
Definition Transaction.h:35
@ COMMITTED
Definition Transaction.h:32
@ CONFLICTED
Definition Transaction.h:31
@ INCOMPLETE
Definition Transaction.h:36
@ INCLUDED
Definition Transaction.h:30
ClosedInterval< T > range(T low, T high)
Create a closed range interval.
Definition RangeSet.h:34
boost::icl::closed_interval< T > ClosedInterval
A closed interval over the domain T.
Definition RangeSet.h:25
TxSearched
Definition TxSearched.h:5
@ temUNCERTAIN
Definition TER.h:103
error_code_i
Definition ErrorCodes.h:20
Note, should be treated as flags that can be | and &.
Definition STBase.h:17
CurrentLedgerState(LedgerIndex li, XRPAmount fee, std::uint32_t accSeqNext, std::uint32_t accSeqAvail)
uint256 const & getNodestoreHash()
ClosedInterval< uint32_t > const & getLedgerRangeSearched()
std::variant< std::pair< uint256, uint32_t >, ClosedInterval< uint32_t > > locator
bool any() const
any Get true of any state is true
void clear()
clear Clear all states