Merge branch 'develop' into feature/son-for-hive-voting
This commit is contained in:
commit
d39f3f309a
6 changed files with 232 additions and 9 deletions
|
|
@ -2102,18 +2102,11 @@ void database::perform_son_tasks()
|
|||
|
||||
void update_son_params(database& db)
|
||||
{
|
||||
if( db.head_block_time() >= HARDFORK_SON2_TIME )
|
||||
if( (db.head_block_time() >= HARDFORK_SON2_TIME) && (db.head_block_time() < HARDFORK_SON3_TIME) )
|
||||
{
|
||||
const auto& gpo = db.get_global_properties();
|
||||
const asset_object& btc_asset = gpo.parameters.btc_asset()(db);
|
||||
if( btc_asset.is_transfer_restricted() ) {
|
||||
db.modify( btc_asset, []( asset_object& ao ) {
|
||||
ao.options.flags = asset_issuer_permission_flags::charge_market_fee |
|
||||
asset_issuer_permission_flags::override_authority;
|
||||
});
|
||||
}
|
||||
db.modify( gpo, []( global_property_object& gpo ) {
|
||||
gpo.parameters.extensions.value.maximum_son_count = 7;
|
||||
gpo.parameters.extensions.value.maximum_son_count = 7;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
|||
7
libraries/chain/hardfork.d/SON3.hf
Normal file
7
libraries/chain/hardfork.d/SON3.hf
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
#ifndef HARDFORK_SON3_TIME
|
||||
#ifdef BUILD_PEERPLAYS_TESTNET
|
||||
#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-05-31T00:00:00"))
|
||||
#else
|
||||
#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-05-31T00:00:00"))
|
||||
#endif
|
||||
#endif
|
||||
|
|
@ -1567,6 +1567,28 @@ class wallet_api
|
|||
sidechain_type sidechain,
|
||||
bool broadcast = false);
|
||||
|
||||
/** Broadcast signed transaction for manually sidechain withdrawal
|
||||
* @param son_name_or_id ID or name of the son account
|
||||
* @param sidechain Sidechain type (bitcoin, HIVE, etc)
|
||||
* @param peerplays_uid peerplays_uid
|
||||
* @param transaction_id ID of transaction
|
||||
* @param peerplays_from Sidechain address transaction from
|
||||
* @param withdraw_sidechain Withdraw sidechain
|
||||
* @param withdraw_address Withdraw address
|
||||
* @param withdraw_currency Withdraw currency
|
||||
* @param withdraw_amount Withdraw amount
|
||||
* @returns the signed transaction.
|
||||
*/
|
||||
signed_transaction sidechain_withdrawal_transaction(const string &son_name_or_id,
|
||||
const sidechain_type& sidechain,
|
||||
const std::string &peerplays_uid,
|
||||
const std::string &peerplays_transaction_id,
|
||||
const chain::account_id_type &peerplays_from,
|
||||
const sidechain_type& withdraw_sidechain,
|
||||
const std::string &withdraw_address,
|
||||
const std::string &withdraw_currency,
|
||||
const string &withdraw_amount);
|
||||
|
||||
/** Retrieves all sidechain addresses owned by given account.
|
||||
*
|
||||
* @param account the name or id of the account who owns the address
|
||||
|
|
@ -2728,6 +2750,7 @@ FC_API( graphene::wallet::wallet_api,
|
|||
(get_son_wallets)
|
||||
(add_sidechain_address)
|
||||
(delete_sidechain_address)
|
||||
(sidechain_withdrawal_transaction)
|
||||
(get_sidechain_addresses_by_account)
|
||||
(get_sidechain_addresses_by_sidechain)
|
||||
(get_sidechain_address_by_account_and_sidechain)
|
||||
|
|
|
|||
|
|
@ -2361,6 +2361,63 @@ public:
|
|||
|
||||
} FC_CAPTURE_AND_RETHROW() }
|
||||
|
||||
signed_transaction sidechain_withdrawal_transaction(const string &son_name_or_id,
|
||||
const sidechain_type& sidechain,
|
||||
const std::string &peerplays_uid,
|
||||
const std::string &peerplays_transaction_id,
|
||||
const chain::account_id_type &peerplays_from,
|
||||
const sidechain_type& withdraw_sidechain,
|
||||
const std::string &withdraw_address,
|
||||
const std::string &withdraw_currency,
|
||||
const string &withdraw_amount)
|
||||
{ try{
|
||||
const global_property_object& gpo = get_global_properties();
|
||||
const auto dynamic_props = get_dynamic_global_properties();
|
||||
const auto son_obj = get_son(son_name_or_id);
|
||||
|
||||
fc::optional<asset_object> peerplays_asset = get_asset(withdraw_currency);
|
||||
FC_ASSERT(peerplays_asset, "Could not find asset matching ${asset}", ("asset", peerplays_asset));
|
||||
const auto asset_val = peerplays_asset->amount_from_string(withdraw_amount);
|
||||
const auto asset_price = peerplays_asset->options.core_exchange_rate;
|
||||
|
||||
price withdraw_currency_price = {};
|
||||
if ("BTC" == withdraw_currency) {
|
||||
fc::optional<asset_object> a = get_asset( gpo.parameters.btc_asset());
|
||||
withdraw_currency_price = a->options.core_exchange_rate;
|
||||
} else
|
||||
if ("HBD" == withdraw_currency) {
|
||||
fc::optional<asset_object> a = get_asset( gpo.parameters.hbd_asset());
|
||||
withdraw_currency_price = a->options.core_exchange_rate;
|
||||
} else
|
||||
if ("HIVE" == withdraw_currency) {
|
||||
fc::optional<asset_object> a = get_asset( gpo.parameters.hive_asset());
|
||||
withdraw_currency_price = a->options.core_exchange_rate;
|
||||
} else {
|
||||
FC_THROW("withdraw_currency ${withdraw_currency}", ("withdraw_currency", withdraw_currency));
|
||||
}
|
||||
|
||||
//! Create transaction
|
||||
signed_transaction son_wallet_withdraw_create_transaction;
|
||||
son_wallet_withdraw_create_operation op;
|
||||
op.payer = son_obj.son_account;
|
||||
op.son_id = son_obj.id;
|
||||
op.timestamp = dynamic_props.time;
|
||||
op.block_num = dynamic_props.head_block_number;
|
||||
op.sidechain = sidechain;
|
||||
op.peerplays_uid = peerplays_uid;
|
||||
op.peerplays_transaction_id = peerplays_transaction_id;
|
||||
op.peerplays_from = peerplays_from;
|
||||
op.peerplays_asset = asset(asset_val.amount * asset_price.base.amount / asset_price.quote.amount);
|
||||
op.withdraw_sidechain = withdraw_sidechain;
|
||||
op.withdraw_address = withdraw_address;
|
||||
op.withdraw_currency = withdraw_currency;
|
||||
op.withdraw_amount = asset_val.amount;
|
||||
|
||||
son_wallet_withdraw_create_transaction.operations.push_back(op);
|
||||
|
||||
return sign_transaction(son_wallet_withdraw_create_transaction, true);
|
||||
} FC_CAPTURE_AND_RETHROW( (withdraw_currency) ) }
|
||||
|
||||
signed_transaction create_witness(string owner_account,
|
||||
string url,
|
||||
bool broadcast /* = false */)
|
||||
|
|
@ -5313,6 +5370,27 @@ signed_transaction wallet_api::delete_sidechain_address(string account,
|
|||
return my->delete_sidechain_address(account, sidechain, broadcast);
|
||||
}
|
||||
|
||||
signed_transaction wallet_api::sidechain_withdrawal_transaction(const string &son_name_or_id,
|
||||
const sidechain_type& sidechain,
|
||||
const std::string &peerplays_uid,
|
||||
const std::string &peerplays_transaction_id,
|
||||
const chain::account_id_type &peerplays_from,
|
||||
const sidechain_type& withdraw_sidechain,
|
||||
const std::string &withdraw_address,
|
||||
const std::string &withdraw_currency,
|
||||
const string &withdraw_amount)
|
||||
{
|
||||
return my->sidechain_withdrawal_transaction(son_name_or_id,
|
||||
sidechain,
|
||||
peerplays_uid,
|
||||
peerplays_transaction_id,
|
||||
peerplays_from,
|
||||
withdraw_sidechain,
|
||||
withdraw_address,
|
||||
withdraw_currency,
|
||||
withdraw_amount);
|
||||
}
|
||||
|
||||
vector<optional<sidechain_address_object>> wallet_api::get_sidechain_addresses_by_account(string account)
|
||||
{
|
||||
account_id_type account_id = get_account_id(account);
|
||||
|
|
|
|||
|
|
@ -868,6 +868,87 @@ BOOST_AUTO_TEST_CASE( sidechain_deposit_transaction_test )
|
|||
BOOST_TEST_MESSAGE("SON sidechain_deposit_transaction_test cli wallet tests end");
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE( sidechain_withdraw_transaction_test )
|
||||
{
|
||||
BOOST_TEST_MESSAGE("SON sidechain_withdraw_transaction_test cli wallet tests begin");
|
||||
son_test_helper sth(*this);
|
||||
|
||||
std::string name("sonaccount1");
|
||||
|
||||
global_property_object gpo;
|
||||
gpo = con.wallet_api_ptr->get_global_properties();
|
||||
unsigned int son_number = gpo.parameters.maximum_son_count();
|
||||
|
||||
flat_map<sidechain_type, string> sidechain_public_keys;
|
||||
|
||||
// create son accounts
|
||||
for(unsigned int i = 0; i < son_number + 1; i++)
|
||||
{
|
||||
sidechain_public_keys.clear();
|
||||
sidechain_public_keys[sidechain_type::bitcoin] = "bitcoin_address " + fc::to_pretty_string(i);
|
||||
sidechain_public_keys[sidechain_type::hive] = "hive account " + fc::to_pretty_string(i);
|
||||
sth.create_son("sonaccount" + fc::to_pretty_string(i),
|
||||
"http://son" + fc::to_pretty_string(i),
|
||||
sidechain_public_keys,
|
||||
false);
|
||||
}
|
||||
BOOST_CHECK(generate_maintenance_block());
|
||||
|
||||
BOOST_TEST_MESSAGE("Voting for SONs");
|
||||
for(unsigned int i = 1; i < son_number + 1; i++)
|
||||
{
|
||||
con.wallet_api_ptr->transfer(
|
||||
"nathan", "sonaccount" + fc::to_pretty_string(i), "1000", "1.3.0", "Here are some CORE tokens for your new account", true );
|
||||
con.wallet_api_ptr->create_vesting_balance("sonaccount" + fc::to_pretty_string(i), "500", "1.3.0", vesting_balance_type::gpos, true);
|
||||
con.wallet_api_ptr->vote_for_son("sonaccount" + fc::to_pretty_string(i), name, true, true);
|
||||
}
|
||||
BOOST_CHECK(generate_maintenance_block());
|
||||
|
||||
son_object son_obj = con.wallet_api_ptr->get_son(name);
|
||||
BOOST_CHECK(son_obj.status == son_status::active);
|
||||
|
||||
// create son account
|
||||
std::string account_name("peerplaystest");
|
||||
graphene::wallet::brain_key_info bki = con.wallet_api_ptr->suggest_brain_key();
|
||||
BOOST_CHECK(!bki.brain_priv_key.empty());
|
||||
signed_transaction create_tx = con.wallet_api_ptr->create_account_with_brain_key(bki.brain_priv_key, account_name, "nathan", "nathan", true);
|
||||
|
||||
generate_block();
|
||||
|
||||
// Deposit
|
||||
//BOOST_TEST_MESSAGE("Deposit");
|
||||
//signed_transaction deposit_tx = con.wallet_api_ptr->transfer("nathan", account_name, "5", "BTC", "", true);
|
||||
//generate_block();
|
||||
|
||||
// Withdraw
|
||||
BOOST_TEST_MESSAGE("Withdraw");
|
||||
signed_transaction withdraw_tx = con.wallet_api_ptr->transfer(account_name, "son-acount", "1", "BTC", "", true);
|
||||
generate_block();
|
||||
BOOST_TEST_MESSAGE("Withdraw done");
|
||||
|
||||
graphene::chain::transaction_id_type trx_id_type = con.wallet_api_ptr->get_transaction_id(withdraw_tx);
|
||||
std::string peerplays_transaction_id = trx_id_type.str();
|
||||
|
||||
std::string peerplays_transaction_id_str = "peerplays_transaction_id = " + peerplays_transaction_id;
|
||||
BOOST_TEST_MESSAGE(peerplays_transaction_id_str);
|
||||
|
||||
std::string peerplays_uid = "peerplays-" + peerplays_transaction_id + "0";
|
||||
graphene::chain::account_id_type peerplays_from = con.wallet_api_ptr->get_account(account_name).id;
|
||||
std::string withdraw_address = "2MtTPtraZawsvNGc8eCdx98hXbi4gaYy8L6";
|
||||
|
||||
signed_transaction txs = con.wallet_api_ptr->sidechain_withdrawal_transaction(account_name, sidechain_type::peerplays,
|
||||
peerplays_uid,
|
||||
peerplays_transaction_id,
|
||||
peerplays_from,
|
||||
sidechain_type::bitcoin,
|
||||
withdraw_address,
|
||||
"BTC",
|
||||
"1");
|
||||
|
||||
|
||||
BOOST_TEST_MESSAGE("SON sidechain_withdraw_transaction_test cli wallet tests end");
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_SUITE_END()
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1012,6 +1012,47 @@ BOOST_FIXTURE_TEST_CASE( prevent_missconfiguration_blockchain_param, database_fi
|
|||
|
||||
} FC_LOG_AND_RETHROW() }
|
||||
|
||||
BOOST_FIXTURE_TEST_CASE( hardfork_son2_time, database_fixture )
|
||||
{ try {
|
||||
|
||||
db.modify(db.get_global_properties(), [](global_property_object& p) {
|
||||
p.parameters.committee_proposal_review_period = fc::hours(1).to_seconds();
|
||||
});
|
||||
|
||||
generate_block();
|
||||
// check that maximum_son_count are not yet updated on 7, it should
|
||||
// be updated on HARDFORK_SON2_TIME
|
||||
BOOST_CHECK_EQUAL(db.get_global_properties().parameters.maximum_son_count(), GRAPHENE_DEFAULT_MAX_SONS);
|
||||
|
||||
generate_blocks(HARDFORK_SON2_TIME);
|
||||
|
||||
// check that flags for assets are set after hardfork_son2_time
|
||||
asset_object btc_asset = get_asset("BTC");
|
||||
uint16_t check_flags{0};
|
||||
check_flags |= asset_issuer_permission_flags::charge_market_fee | asset_issuer_permission_flags::override_authority;
|
||||
uint16_t result = btc_asset.options.flags & check_flags;
|
||||
BOOST_CHECK_EQUAL( result, check_flags);
|
||||
|
||||
// move on next maintenance interval and check that maximum_son_count is updated to 7
|
||||
generate_blocks(db.get_dynamic_global_properties().next_maintenance_time);
|
||||
generate_block(); // get the maintenance skip slots out of the way*/
|
||||
BOOST_CHECK_EQUAL(db.get_global_properties().parameters.maximum_son_count(), 7);
|
||||
|
||||
generate_blocks(HARDFORK_SON3_TIME);
|
||||
// after this hardfork maximum son account should not reset the value
|
||||
// on 7 after maintenance interval anymore. So change the global parameters
|
||||
// and check the value after maintenance interval
|
||||
db.modify(db.get_global_properties(), [](global_property_object& p) {
|
||||
p.parameters.extensions.value.maximum_son_count = 13;
|
||||
});
|
||||
|
||||
generate_blocks(db.get_dynamic_global_properties().next_maintenance_time);
|
||||
generate_block();
|
||||
|
||||
BOOST_CHECK_EQUAL(db.get_global_properties().parameters.maximum_son_count(), 13);
|
||||
|
||||
} FC_LOG_AND_RETHROW() }
|
||||
|
||||
BOOST_FIXTURE_TEST_CASE( pop_block_twice, database_fixture )
|
||||
{
|
||||
try
|
||||
|
|
|
|||
Loading…
Reference in a new issue