mirror of
https://github.com/Xahau/xahaud.git
synced 2025-11-13 23:25:48 +00:00
Compare commits
5 Commits
fixPageCap
...
mongo-db
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
74ce9743a7 | ||
|
|
79d83bd424 | ||
|
|
1a4d54f9d9 | ||
|
|
26cd629d28 | ||
|
|
2fb93f874b |
2
.github/workflows/clang-format.yml
vendored
2
.github/workflows/clang-format.yml
vendored
@@ -30,7 +30,7 @@ jobs:
|
||||
git diff --exit-code | tee "clang-format.patch"
|
||||
- name: Upload patch
|
||||
if: failure() && steps.assert.outcome == 'failure'
|
||||
uses: actions/upload-artifact@v2
|
||||
uses: actions/upload-artifact@v3
|
||||
continue-on-error: true
|
||||
with:
|
||||
name: clang-format.patch
|
||||
|
||||
2
.github/workflows/levelization.yml
vendored
2
.github/workflows/levelization.yml
vendored
@@ -18,7 +18,7 @@ jobs:
|
||||
git diff --exit-code | tee "levelization.patch"
|
||||
- name: Upload patch
|
||||
if: failure() && steps.assert.outcome == 'failure'
|
||||
uses: actions/upload-artifact@v2
|
||||
uses: actions/upload-artifact@v3
|
||||
continue-on-error: true
|
||||
with:
|
||||
name: levelization.patch
|
||||
|
||||
@@ -145,6 +145,7 @@ target_link_libraries (xrpl_core
|
||||
OpenSSL::Crypto
|
||||
Ripple::boost
|
||||
NIH::WasmEdge
|
||||
NIH::MongoCxx
|
||||
Ripple::syslibs
|
||||
NIH::secp256k1
|
||||
NIH::ed25519-donna
|
||||
|
||||
100
Builds/CMake/deps/Mongo.cmake
Normal file
100
Builds/CMake/deps/Mongo.cmake
Normal file
@@ -0,0 +1,100 @@
|
||||
#[===================================================================[
|
||||
NIH dep: mongo: MongoDB C++ driver (bsoncxx and mongocxx).
|
||||
#]===================================================================]
|
||||
|
||||
include(FetchContent)
|
||||
|
||||
FetchContent_Declare(
|
||||
mongo_c_driver_src
|
||||
GIT_REPOSITORY https://github.com/mongodb/mongo-c-driver.git
|
||||
GIT_TAG 1.17.4
|
||||
)
|
||||
|
||||
FetchContent_GetProperties(mongo_c_driver_src)
|
||||
if(NOT mongo_c_driver_src_POPULATED)
|
||||
message(STATUS "Pausing to download MongoDB C driver...")
|
||||
FetchContent_Populate(mongo_c_driver_src)
|
||||
endif()
|
||||
|
||||
set(MONGO_C_DRIVER_BUILD_DIR "${mongo_c_driver_src_BINARY_DIR}")
|
||||
set(MONGO_C_DRIVER_INCLUDE_DIR "${mongo_c_driver_src_SOURCE_DIR}/src/libbson/src")
|
||||
set(MONGO_C_DRIVER_INSTALL_PREFIX "${CMAKE_CURRENT_BINARY_DIR}/mongo_c_install")
|
||||
|
||||
set(MONGO_C_DRIVER_CMAKE_ARGS
|
||||
-DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}
|
||||
-DENABLE_AUTOMATIC_INIT_AND_CLEANUP=OFF
|
||||
-DENABLE_STATIC=ON
|
||||
-DENABLE_SHARED=OFF
|
||||
-DCMAKE_INSTALL_PREFIX=${MONGO_C_DRIVER_INSTALL_PREFIX}
|
||||
)
|
||||
|
||||
ExternalProject_Add(mongo_c_driver
|
||||
PREFIX ${CMAKE_CURRENT_BINARY_DIR}/mongo_c
|
||||
SOURCE_DIR ${mongo_c_driver_src_SOURCE_DIR}
|
||||
CMAKE_ARGS ${MONGO_C_DRIVER_CMAKE_ARGS}
|
||||
BUILD_COMMAND ${CMAKE_COMMAND} --build . --config $<CONFIG>
|
||||
INSTALL_COMMAND ${CMAKE_COMMAND} --install .
|
||||
)
|
||||
|
||||
FetchContent_Declare(
|
||||
mongo_cxx_driver_src
|
||||
GIT_REPOSITORY https://github.com/mongodb/mongo-cxx-driver.git
|
||||
GIT_TAG r3.10.2
|
||||
)
|
||||
|
||||
FetchContent_GetProperties(mongo_cxx_driver_src)
|
||||
if(NOT mongo_cxx_driver_src_POPULATED)
|
||||
message(STATUS "Pausing to download MongoDB C++ driver...")
|
||||
FetchContent_Populate(mongo_cxx_driver_src)
|
||||
endif()
|
||||
|
||||
set(MONGO_CXX_DRIVER_BUILD_DIR "${mongo_cxx_driver_src_BINARY_DIR}")
|
||||
set(MONGO_CXX_DRIVER_INCLUDE_DIR "${mongo_cxx_driver_src_SOURCE_DIR}/include")
|
||||
set(MONGO_CXX_DRIVER_INSTALL_PREFIX "${CMAKE_CURRENT_BINARY_DIR}/mongo_cxx_install")
|
||||
|
||||
set(MONGO_CXX_DRIVER_CMAKE_ARGS
|
||||
-DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}
|
||||
-DBUILD_SHARED_AND_STATIC_LIBS=ON
|
||||
-DBSONCXX_ENABLE_MONGOC=ON
|
||||
-DCMAKE_INSTALL_PREFIX=${MONGO_CXX_DRIVER_INSTALL_PREFIX}
|
||||
-DCMAKE_PREFIX_PATH=${MONGO_C_DRIVER_INSTALL_PREFIX}
|
||||
)
|
||||
|
||||
ExternalProject_Add(mongo_cxx_driver
|
||||
PREFIX ${CMAKE_CURRENT_BINARY_DIR}/mongo_cxx
|
||||
SOURCE_DIR ${mongo_cxx_driver_src_SOURCE_DIR}
|
||||
CMAKE_ARGS ${MONGO_CXX_DRIVER_CMAKE_ARGS}
|
||||
BUILD_COMMAND ${CMAKE_COMMAND} --build . --config $<CONFIG>
|
||||
INSTALL_COMMAND ${CMAKE_COMMAND} --install .
|
||||
DEPENDS mongo_c_driver
|
||||
)
|
||||
|
||||
add_library(bsoncxx STATIC IMPORTED GLOBAL)
|
||||
add_library(mongocxx STATIC IMPORTED GLOBAL)
|
||||
add_dependencies(bsoncxx mongo_cxx_driver)
|
||||
add_dependencies(mongocxx mongo_cxx_driver)
|
||||
|
||||
ExternalProject_Get_Property(mongo_cxx_driver BINARY_DIR)
|
||||
execute_process(
|
||||
COMMAND
|
||||
mkdir -p "${BINARY_DIR}/include/bsoncxx/v_noabi"
|
||||
mkdir -p "${BINARY_DIR}/include/mongocxx/v_noabi"
|
||||
)
|
||||
|
||||
set_target_properties(bsoncxx PROPERTIES
|
||||
IMPORTED_LOCATION "${MONGO_CXX_DRIVER_INSTALL_PREFIX}/lib/libbsoncxx-static.a"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${MONGO_CXX_DRIVER_INSTALL_PREFIX}/include/bsoncxx/v_noabi"
|
||||
)
|
||||
|
||||
set_target_properties(mongocxx PROPERTIES
|
||||
IMPORTED_LOCATION "${MONGO_CXX_DRIVER_INSTALL_PREFIX}/lib/libmongocxx-static.a"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${MONGO_CXX_DRIVER_INSTALL_PREFIX}/include/mongocxx/v_noabi"
|
||||
)
|
||||
|
||||
# Link the C driver libraries
|
||||
find_library(BSON_LIB bson-1.0 PATHS ${MONGO_C_DRIVER_INSTALL_PREFIX}/lib)
|
||||
find_library(MONGOC_LIB mongoc-1.0 PATHS ${MONGO_C_DRIVER_INSTALL_PREFIX}/lib)
|
||||
|
||||
target_link_libraries(ripple_libs INTERFACE bsoncxx mongocxx ${BSON_LIB} ${MONGOC_LIB})
|
||||
|
||||
add_library(NIH::MongoCxx ALIAS mongocxx)
|
||||
@@ -75,6 +75,7 @@ include(deps/gRPC)
|
||||
include(deps/cassandra)
|
||||
include(deps/Postgres)
|
||||
include(deps/WasmEdge)
|
||||
include(deps/Mongo)
|
||||
|
||||
###
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
# Xahau
|
||||
# Xahau
|
||||
|
||||
**Note:** Throughout this README, references to "we" or "our" pertain to the community and contributors involved in the Xahau network. It does not imply a legal entity or a specific collection of individuals.
|
||||
|
||||
@@ -68,4 +68,4 @@ git-subtree. See those directories' README files for more details.
|
||||
- **Testnet & Faucet**: Test applications and obtain test XAH at [xahau-test.net](https://xahau-test.net) and use the testnet explorer at [explorer.xahau.network](https://explorer.xahau.network).
|
||||
- **Supporting Wallets**: A list of wallets that support XAH and Xahau-based assets.
|
||||
- [Xumm](https://xumm.app)
|
||||
- [Crossmark](https://crossmark.io)
|
||||
- [Crossmark](https://crossmark.io)
|
||||
|
||||
@@ -134,8 +134,12 @@ RCLConsensus::Adaptor::acquireLedger(LedgerHash const& hash)
|
||||
acquiringLedger_ = hash;
|
||||
|
||||
app_.getJobQueue().addJob(
|
||||
jtADVANCE, "getConsensusLedger", [id = hash, &app = app_]() {
|
||||
app.getInboundLedgers().acquire(
|
||||
jtADVANCE,
|
||||
"getConsensusLedger1",
|
||||
[id = hash, &app = app_, this]() {
|
||||
JLOG(j_.debug())
|
||||
<< "JOB advanceLedger getConsensusLedger1 started";
|
||||
app.getInboundLedgers().acquireAsync(
|
||||
id, 0, InboundLedger::Reason::CONSENSUS);
|
||||
});
|
||||
}
|
||||
|
||||
@@ -135,8 +135,10 @@ RCLValidationsAdaptor::acquire(LedgerHash const& hash)
|
||||
Application* pApp = &app_;
|
||||
|
||||
app_.getJobQueue().addJob(
|
||||
jtADVANCE, "getConsensusLedger", [pApp, hash]() {
|
||||
pApp->getInboundLedgers().acquire(
|
||||
jtADVANCE, "getConsensusLedger2", [pApp, hash, this]() {
|
||||
JLOG(j_.debug())
|
||||
<< "JOB advanceLedger getConsensusLedger2 started";
|
||||
pApp->getInboundLedgers().acquireAsync(
|
||||
hash, 0, InboundLedger::Reason::CONSENSUS);
|
||||
});
|
||||
return std::nullopt;
|
||||
@@ -152,7 +154,9 @@ void
|
||||
handleNewValidation(
|
||||
Application& app,
|
||||
std::shared_ptr<STValidation> const& val,
|
||||
std::string const& source)
|
||||
std::string const& source,
|
||||
BypassAccept const bypassAccept,
|
||||
std::optional<beast::Journal> j)
|
||||
{
|
||||
auto const& signingKey = val->getSignerPublic();
|
||||
auto const& hash = val->getLedgerHash();
|
||||
@@ -177,7 +181,23 @@ handleNewValidation(
|
||||
if (outcome == ValStatus::current)
|
||||
{
|
||||
if (val->isTrusted())
|
||||
app.getLedgerMaster().checkAccept(hash, seq);
|
||||
{
|
||||
// Was: app.getLedgerMaster().checkAccept(hash, seq);
|
||||
// https://github.com/XRPLF/rippled/commit/fbbea9e6e25795a8a6bd1bf64b780771933a9579
|
||||
if (bypassAccept == BypassAccept::yes)
|
||||
{
|
||||
assert(j.has_value());
|
||||
if (j.has_value())
|
||||
{
|
||||
JLOG(j->trace()) << "Bypassing checkAccept for validation "
|
||||
<< val->getLedgerHash();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
app.getLedgerMaster().checkAccept(hash, seq);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -25,12 +25,16 @@
|
||||
#include <ripple/protocol/Protocol.h>
|
||||
#include <ripple/protocol/RippleLedgerHash.h>
|
||||
#include <ripple/protocol/STValidation.h>
|
||||
#include <optional>
|
||||
#include <set>
|
||||
#include <vector>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
class Application;
|
||||
|
||||
enum class BypassAccept : bool { no = false, yes };
|
||||
|
||||
/** Wrapper over STValidation for generic Validation code
|
||||
|
||||
Wraps an STValidation for compatibility with the generic validation code.
|
||||
@@ -248,7 +252,9 @@ void
|
||||
handleNewValidation(
|
||||
Application& app,
|
||||
std::shared_ptr<STValidation> const& val,
|
||||
std::string const& source);
|
||||
std::string const& source,
|
||||
BypassAccept const bypassAccept = BypassAccept::no,
|
||||
std::optional<beast::Journal> j = std::nullopt);
|
||||
|
||||
} // namespace ripple
|
||||
|
||||
|
||||
@@ -38,10 +38,21 @@ public:
|
||||
virtual ~InboundLedgers() = default;
|
||||
|
||||
// VFALCO TODO Should this be called findOrAdd ?
|
||||
// Callers should use this if they possibly need an authoritative
|
||||
// response immediately.
|
||||
//
|
||||
virtual std::shared_ptr<Ledger const>
|
||||
acquire(uint256 const& hash, std::uint32_t seq, InboundLedger::Reason) = 0;
|
||||
|
||||
// Callers should use this if they are known to be executing on the Job
|
||||
// Queue. TODO review whether all callers of acquire() can use this
|
||||
// instead. Inbound ledger acquisition is asynchronous anyway.
|
||||
virtual void
|
||||
acquireAsync(
|
||||
uint256 const& hash,
|
||||
std::uint32_t seq,
|
||||
InboundLedger::Reason reason) = 0;
|
||||
|
||||
virtual std::shared_ptr<InboundLedger>
|
||||
find(LedgerHash const& hash) = 0;
|
||||
|
||||
|
||||
@@ -560,7 +560,7 @@ InboundLedger::trigger(std::shared_ptr<Peer> const& peer, TriggerReason reason)
|
||||
return;
|
||||
}
|
||||
|
||||
if (auto stream = journal_.trace())
|
||||
if (auto stream = journal_.debug())
|
||||
{
|
||||
if (peer)
|
||||
stream << "Trigger acquiring ledger " << hash_ << " from " << peer;
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <ripple/nodestore/DatabaseShard.h>
|
||||
#include <ripple/protocol/jss.h>
|
||||
#include <exception>
|
||||
#include <memory>
|
||||
#include <mutex>
|
||||
#include <vector>
|
||||
@@ -141,6 +142,37 @@ public:
|
||||
return inbound->getLedger();
|
||||
}
|
||||
|
||||
void
|
||||
acquireAsync(
|
||||
uint256 const& hash,
|
||||
std::uint32_t seq,
|
||||
InboundLedger::Reason reason) override
|
||||
{
|
||||
std::unique_lock lock(acquiresMutex_);
|
||||
try
|
||||
{
|
||||
if (pendingAcquires_.contains(hash))
|
||||
return;
|
||||
pendingAcquires_.insert(hash);
|
||||
lock.unlock();
|
||||
acquire(hash, seq, reason);
|
||||
}
|
||||
catch (std::exception const& e)
|
||||
{
|
||||
JLOG(j_.warn())
|
||||
<< "Exception thrown for acquiring new inbound ledger " << hash
|
||||
<< ": " << e.what();
|
||||
}
|
||||
catch (...)
|
||||
{
|
||||
JLOG(j_.warn())
|
||||
<< "Unknown exception thrown for acquiring new inbound ledger "
|
||||
<< hash;
|
||||
}
|
||||
lock.lock();
|
||||
pendingAcquires_.erase(hash);
|
||||
}
|
||||
|
||||
std::shared_ptr<InboundLedger>
|
||||
find(uint256 const& hash) override
|
||||
{
|
||||
@@ -426,6 +458,9 @@ private:
|
||||
beast::insight::Counter mCounter;
|
||||
|
||||
std::unique_ptr<PeerSetBuilder> mPeerSetBuilder;
|
||||
|
||||
std::set<uint256> pendingAcquires_;
|
||||
std::mutex acquiresMutex_;
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
@@ -70,7 +70,9 @@
|
||||
#include <boost/asio/ip/host_name.hpp>
|
||||
#include <boost/asio/steady_timer.hpp>
|
||||
|
||||
#include <exception>
|
||||
#include <mutex>
|
||||
#include <set>
|
||||
#include <string>
|
||||
#include <tuple>
|
||||
#include <unordered_map>
|
||||
@@ -776,6 +778,9 @@ private:
|
||||
|
||||
StateAccounting accounting_{};
|
||||
|
||||
std::set<uint256> pendingValidations_;
|
||||
std::mutex validationsMutex_;
|
||||
|
||||
private:
|
||||
struct Stats
|
||||
{
|
||||
@@ -1791,7 +1796,8 @@ NetworkOPsImp::checkLastClosedLedger(
|
||||
}
|
||||
|
||||
JLOG(m_journal.warn()) << "We are not running on the consensus ledger";
|
||||
JLOG(m_journal.info()) << "Our LCL: " << getJson({*ourClosed, {}});
|
||||
JLOG(m_journal.info()) << "Our LCL: " << ourClosed->info().hash
|
||||
<< getJson({*ourClosed, {}});
|
||||
JLOG(m_journal.info()) << "Net LCL " << closedLedger;
|
||||
|
||||
if ((mMode == OperatingMode::TRACKING) || (mMode == OperatingMode::FULL))
|
||||
@@ -2345,7 +2351,37 @@ NetworkOPsImp::recvValidation(
|
||||
JLOG(m_journal.trace())
|
||||
<< "recvValidation " << val->getLedgerHash() << " from " << source;
|
||||
|
||||
handleNewValidation(app_, val, source);
|
||||
// handleNewValidation(app_, val, source);
|
||||
// https://github.com/XRPLF/rippled/commit/fbbea9e6e25795a8a6bd1bf64b780771933a9579
|
||||
std::unique_lock lock(validationsMutex_);
|
||||
BypassAccept bypassAccept = BypassAccept::no;
|
||||
try
|
||||
{
|
||||
if (pendingValidations_.contains(val->getLedgerHash()))
|
||||
bypassAccept = BypassAccept::yes;
|
||||
else
|
||||
pendingValidations_.insert(val->getLedgerHash());
|
||||
lock.unlock();
|
||||
handleNewValidation(app_, val, source, bypassAccept, m_journal);
|
||||
}
|
||||
catch (std::exception const& e)
|
||||
{
|
||||
JLOG(m_journal.warn())
|
||||
<< "Exception thrown for handling new validation "
|
||||
<< val->getLedgerHash() << ": " << e.what();
|
||||
}
|
||||
catch (...)
|
||||
{
|
||||
JLOG(m_journal.warn())
|
||||
<< "Unknown exception thrown for handling new validation "
|
||||
<< val->getLedgerHash();
|
||||
}
|
||||
if (bypassAccept == BypassAccept::no)
|
||||
{
|
||||
lock.lock();
|
||||
pendingValidations_.erase(val->getLedgerHash());
|
||||
lock.unlock();
|
||||
}
|
||||
|
||||
pubValidation(val);
|
||||
|
||||
|
||||
@@ -1923,6 +1923,7 @@ Transactor::operator()()
|
||||
uint32_t lgrCur = view().seq();
|
||||
|
||||
bool const has240819 = view().rules().enabled(fix240819);
|
||||
bool const has240911 = view().rules().enabled(fix240911);
|
||||
|
||||
auto const& sfRewardFields =
|
||||
*(ripple::SField::knownCodeToField.at(917511 - has240819));
|
||||
@@ -1971,7 +1972,11 @@ Transactor::operator()()
|
||||
uint32_t lgrElapsed = lgrCur - lgrLast;
|
||||
|
||||
// overflow safety
|
||||
if (lgrElapsed > lgrCur || lgrElapsed > lgrLast || lgrElapsed == 0)
|
||||
if (!has240911 &&
|
||||
(lgrElapsed > lgrCur || lgrElapsed > lgrLast ||
|
||||
lgrElapsed == 0))
|
||||
continue;
|
||||
if (has240911 && (lgrElapsed > lgrCur || lgrElapsed == 0))
|
||||
continue;
|
||||
|
||||
uint64_t accum = sle->getFieldU64(sfRewardAccumulator);
|
||||
|
||||
@@ -74,7 +74,7 @@ namespace detail {
|
||||
// Feature.cpp. Because it's only used to reserve storage, and determine how
|
||||
// large to make the FeatureBitset, it MAY be larger. It MUST NOT be less than
|
||||
// the actual number of amendments. A LogicError on startup will verify this.
|
||||
static constexpr std::size_t numFeatures = 72;
|
||||
static constexpr std::size_t numFeatures = 73;
|
||||
|
||||
/** Amendments that this server supports and the default voting behavior.
|
||||
Whether they are enabled depends on the Rules defined in the validated
|
||||
@@ -360,6 +360,7 @@ extern uint256 const featureZeroB2M;
|
||||
extern uint256 const fixNSDelete;
|
||||
extern uint256 const fix240819;
|
||||
extern uint256 const fixPageCap;
|
||||
extern uint256 const fix240911;
|
||||
|
||||
} // namespace ripple
|
||||
|
||||
|
||||
@@ -466,6 +466,7 @@ REGISTER_FEATURE(ZeroB2M, Supported::yes, VoteBehavior::De
|
||||
REGISTER_FIX (fixNSDelete, Supported::yes, VoteBehavior::DefaultNo);
|
||||
REGISTER_FIX (fix240819, Supported::yes, VoteBehavior::DefaultYes);
|
||||
REGISTER_FIX (fixPageCap, Supported::yes, VoteBehavior::DefaultYes);
|
||||
REGISTER_FIX (fix240911, Supported::yes, VoteBehavior::DefaultYes);
|
||||
|
||||
// The following amendments are obsolete, but must remain supported
|
||||
// because they could potentially get enabled.
|
||||
|
||||
@@ -106,6 +106,14 @@ public:
|
||||
return {};
|
||||
}
|
||||
|
||||
virtual void
|
||||
acquireAsync(
|
||||
uint256 const& hash,
|
||||
std::uint32_t seq,
|
||||
InboundLedger::Reason reason) override
|
||||
{
|
||||
}
|
||||
|
||||
virtual std::shared_ptr<InboundLedger>
|
||||
find(LedgerHash const& hash) override
|
||||
{
|
||||
|
||||
@@ -5020,6 +5020,550 @@ struct XahauGenesis_test : public beast::unit_test::suite
|
||||
BEAST_EXPECT(asPercent == 4);
|
||||
}
|
||||
|
||||
void
|
||||
testDeposit(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test deposit");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
env(pay(alice, user, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
// close ledgers
|
||||
for (int i = 0; i < 10; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const has240819 = env.current()->rules().enabled(fix240819);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == (has240819 ? XRP(6.383333) : XRP(6.663333)));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
has240819 ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(
|
||||
postUser == (has240819 ? XRP(2005.383333) : XRP(2005.663333)));
|
||||
}
|
||||
|
||||
void
|
||||
testDepositWithdraw(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test deposit withdraw");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
env(pay(alice, user, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
env(pay(user, alice, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
// close ledgers
|
||||
for (int i = 0; i < 10; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const has240819 = env.current()->rules().enabled(fix240819);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == XRP(3.583333));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
has240819 ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(postUser == XRP(1002.583323));
|
||||
}
|
||||
|
||||
void
|
||||
testDepositLate(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test deposit late");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// close ledgers
|
||||
for (int i = 0; i < 10; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
env(pay(alice, user, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const has240819 = env.current()->rules().enabled(fix240819);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == (has240819 ? XRP(3.606666) : XRP(6.663333)));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
has240819 ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(
|
||||
postUser == (has240819 ? XRP(2002.606666) : XRP(2005.663333)));
|
||||
}
|
||||
|
||||
void
|
||||
testDepositWithdrawLate(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test deposit late withdraw");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// close ledgers
|
||||
for (int i = 0; i < 10; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
env(pay(alice, user, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
env(pay(user, alice, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const has240819 = env.current()->rules().enabled(fix240819);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == (has240819 ? XRP(3.583333) : XRP(6.149999)));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
has240819 ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(
|
||||
postUser == (has240819 ? XRP(1002.583323) : XRP(1005.149989)));
|
||||
}
|
||||
|
||||
void
|
||||
testNoClaim(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test no claim");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// close ledgers (2 cycles)
|
||||
for (int i = 0; i < 20; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const hasFix = env.current()->rules().enabled(fix240819) &&
|
||||
env.current()->rules().enabled(fix240911);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == (hasFix ? XRP(3.329999) : XRP(3.329999)));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
hasFix ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(
|
||||
postUser == (hasFix ? XRP(1002.329999) : XRP(1002.329999)));
|
||||
}
|
||||
|
||||
void
|
||||
testNoClaimLate(FeatureBitset features)
|
||||
{
|
||||
using namespace jtx;
|
||||
using namespace std::chrono_literals;
|
||||
testcase("test no claim late");
|
||||
|
||||
Env env{*this, envconfig(), features - featureXahauGenesis};
|
||||
|
||||
double const rateDrops = 0.00333333333 * 1'000'000;
|
||||
STAmount const feesXRP = XRP(1);
|
||||
|
||||
auto const user = Account("user");
|
||||
env.fund(XRP(1000), user);
|
||||
env.close();
|
||||
|
||||
// setup governance
|
||||
auto const alice = Account("alice");
|
||||
auto const bob = Account("bob");
|
||||
auto const carol = Account("carol");
|
||||
auto const david = Account("david");
|
||||
auto const edward = Account("edward");
|
||||
|
||||
env.fund(XRP(10000), alice, bob, carol, david, edward);
|
||||
env.close();
|
||||
|
||||
std::vector<AccountID> initial_members_ids{
|
||||
alice.id(), bob.id(), carol.id(), david.id(), edward.id()};
|
||||
|
||||
setupGov(env, initial_members_ids);
|
||||
|
||||
// update reward delay
|
||||
{
|
||||
// this will be the new reward delay
|
||||
// 100
|
||||
std::vector<uint8_t> vote_data{
|
||||
0x00U, 0x80U, 0xC6U, 0xA4U, 0x7EU, 0x8DU, 0x03U, 0x55U};
|
||||
|
||||
updateTopic(
|
||||
env, alice, bob, carol, david, edward, 'R', 'D', vote_data);
|
||||
}
|
||||
|
||||
// verify unl report does not exist
|
||||
BEAST_EXPECT(hasUNLReport(env) == false);
|
||||
|
||||
// opt in claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// close ledgers (2 cycles)
|
||||
for (int i = 0; i < 20; ++i)
|
||||
{
|
||||
env.close(10s);
|
||||
}
|
||||
|
||||
env(pay(alice, user, XRP(1000)));
|
||||
env.close();
|
||||
|
||||
// close claim ledger & time
|
||||
STAmount const preUser = env.balance(user);
|
||||
NetClock::time_point const preTime = lastClose(env);
|
||||
std::uint32_t const preLedger = env.current()->seq();
|
||||
auto const [acct, acctSle] = accountKeyAndSle(*env.current(), user);
|
||||
|
||||
// claim reward
|
||||
env(claimReward(user, env.master), fee(feesXRP), ter(tesSUCCESS));
|
||||
env.close();
|
||||
|
||||
// trigger emitted txn
|
||||
env.close();
|
||||
|
||||
// calculate rewards
|
||||
bool const hasFix = env.current()->rules().enabled(fix240819) &&
|
||||
env.current()->rules().enabled(fix240911);
|
||||
STAmount const netReward =
|
||||
rewardUserAmount(*acctSle, preLedger, rateDrops);
|
||||
BEAST_EXPECT(netReward == (hasFix ? XRP(3.479999) : XRP(6.663333)));
|
||||
|
||||
// validate account fields
|
||||
STAmount const postUser = preUser + netReward;
|
||||
BEAST_EXPECT(expectAccountFields(
|
||||
env,
|
||||
user,
|
||||
preLedger,
|
||||
preLedger + 1,
|
||||
hasFix ? (preUser - feesXRP) : postUser,
|
||||
preTime));
|
||||
BEAST_EXPECT(
|
||||
postUser == (hasFix ? XRP(2002.479999) : XRP(2005.663333)));
|
||||
}
|
||||
|
||||
void
|
||||
testRewardHookWithFeats(FeatureBitset features)
|
||||
{
|
||||
@@ -5038,6 +5582,12 @@ struct XahauGenesis_test : public beast::unit_test::suite
|
||||
testInvalidElapsed0(features);
|
||||
testInvalidElapsedNegative(features);
|
||||
testCompoundInterest(features);
|
||||
testDeposit(features);
|
||||
testDepositWithdraw(features);
|
||||
testDepositLate(features);
|
||||
testDepositWithdrawLate(features);
|
||||
testNoClaim(features);
|
||||
testNoClaimLate(features);
|
||||
}
|
||||
|
||||
void
|
||||
@@ -5056,8 +5606,9 @@ struct XahauGenesis_test : public beast::unit_test::suite
|
||||
using namespace test::jtx;
|
||||
auto const sa = supported_amendments();
|
||||
testGovernHookWithFeats(sa);
|
||||
testRewardHookWithFeats(sa - fix240819);
|
||||
testRewardHookWithFeats(sa);
|
||||
testRewardHookWithFeats(sa - fix240819);
|
||||
testRewardHookWithFeats(sa - fix240819 - fix240911);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user