diff --git a/tests/common/tournament_helper.cpp b/tests/common/tournament_helper.cpp index 9ad98626..4cb27b08 100644 --- a/tests/common/tournament_helper.cpp +++ b/tests/common/tournament_helper.cpp @@ -131,7 +131,7 @@ optional tournaments_helper::get_asset_dividend_account(const a { graphene::chain::database& db = df.db; optional result; - const asset_object& asset_obj = asset_id(db); + const asset_object& asset_obj = asset_id_type()(db); if (asset_obj.dividend_data_id.valid()) { @@ -270,7 +270,7 @@ void tournaments_helper::rps_throw(const game_id_type& game_id, match_object match_obj = game_obj.match_id(db); tournament_object tournament_obj = match_obj.tournament_id(db); rock_paper_scissors_game_options game_options = tournament_obj.options.game_options.get(); - assert((int)gesture < game_options.number_of_gestures); + FC_ASSERT( (int)gesture < game_options.number_of_gestures ); account_object player_account_obj = player_id(db); @@ -291,6 +291,7 @@ void tournaments_helper::rps_throw(const game_id_type& game_id, // store off the reveal for applying after both players commit committed_game_moves[commit_throw] = reveal_throw; + latest_committs[player_account_obj.id] = commit_throw; signed_transaction tx; game_move_operation move_operation; @@ -310,6 +311,33 @@ void tournaments_helper::rps_throw(const game_id_type& game_id, PUSH_TX(db, tx); } +void tournaments_helper::rps_reveal( const game_id_type& game_id, + const account_id_type& player_id, + rock_paper_scissors_gesture gesture, + const fc::ecc::private_key& sig_priv_key ) +{ + graphene::chain::database& db = df.db; + + FC_ASSERT( latest_committs.find(player_id) != latest_committs.end() ); + const auto& reveal = committed_game_moves.find( latest_committs[player_id] ); + FC_ASSERT( reveal != committed_game_moves.end() ); + FC_ASSERT( reveal->second.gesture == gesture ); + + game_move_operation move_operation; + move_operation.game_id = game_id; + move_operation.player_account_id = player_id; + move_operation.move = reveal->second; + + signed_transaction tx; + tx.operations.push_back( move_operation ); + const asset f = db.current_fee_schedule().set_fee( tx.operations[0] ); + players_fees[player_id][f.asset_id] -= f.amount; + tx.validate(); + test::set_expiration( db, tx ); + df.sign( tx, sig_priv_key ); + PUSH_TX(db, tx); +} + // spaghetti programming // walking through all tournaments, matches and games and throwing random moves // optionaly skip generting randomly selected moves diff --git a/tests/common/tournament_helper.hpp b/tests/common/tournament_helper.hpp index ee8c70f6..f9ff6282 100644 --- a/tests/common/tournament_helper.hpp +++ b/tests/common/tournament_helper.hpp @@ -51,9 +51,9 @@ public: dividend_asset_options new_options, const fc::ecc::private_key& sig_priv_key); - optional get_asset_dividend_account(const asset_id_type& asset_id)const; + optional get_asset_dividend_account( const asset_id_type& asset_id = asset_id_type() )const; - const tournament_id_type create_tournament (const account_id_type& creator, + const tournament_id_type create_tournament( const account_id_type& creator, const fc::ecc::private_key& sig_priv_key, asset buy_in, uint32_t number_of_players = 2, @@ -89,6 +89,11 @@ public: const fc::ecc::private_key& sig_priv_key ); + void rps_reveal( const game_id_type& game_id, + const account_id_type& player_id, + rock_paper_scissors_gesture gesture, + const fc::ecc::private_key& sig_priv_key ); + // spaghetti programming // walking through all tournaments, matches and games and throwing random moves // optionaly skip generting randomly selected moves @@ -113,4 +118,6 @@ private: std::map> players_fees; // store of commits and reveals std::map committed_game_moves; + // store of latest commits, for use by rps_reveal + std::map latest_committs; }; diff --git a/tests/tests/affiliate_tests.cpp b/tests/tests/affiliate_tests.cpp index 3b09a135..8926ec39 100644 --- a/tests/tests/affiliate_tests.cpp +++ b/tests/tests/affiliate_tests.cpp @@ -24,26 +24,13 @@ #include -#include -#include -#include -#include +#include "../common/tournament_helper.hpp" -#include -#include -#include -#include #include - -#include - -#include -#include -#include -#include "../common/database_fixture.hpp" - -#include -#include +#include +#include +#include +#include using namespace graphene::chain; using namespace graphene::db; @@ -328,4 +315,142 @@ BOOST_AUTO_TEST_CASE( affiliate_payout_helper_test ) } } +BOOST_AUTO_TEST_CASE( rps_tournament_payout_test ) +{ try { + ACTORS( (alice)(ann)(audrey)(martha) ); + + generate_blocks( HARDFORK_999_TIME ); + generate_block(); + + test::set_expiration( db, trx ); + trx.clear(); + + // Paula: 100% to Alice for Bookie / nothing for RPS + const fc::ecc::private_key paula_private_key = generate_private_key( "paula" ); + account_create_operation aco = make_account( "paula", paula_private_key.get_public_key() ); + aco.extensions.value.affiliate_distributions = affiliate_reward_distributions(); + aco.extensions.value.affiliate_distributions->_dists[bookie]._dist[alice_id] = GRAPHENE_100_PERCENT; + trx.operations.push_back( aco ); + + // Penny: For Bookie 60% to Alice + 40% to Ann / For RPS 20% to Alice, 30% to Ann, 50% to Audrey + const fc::ecc::private_key penny_private_key = generate_private_key( "penny" ); + aco = make_account( "penny", penny_private_key.get_public_key() ); + aco.extensions.value.affiliate_distributions = affiliate_reward_distributions(); + aco.extensions.value.affiliate_distributions->_dists[bookie]._dist[alice_id] = GRAPHENE_100_PERCENT * 3 / 5; + aco.extensions.value.affiliate_distributions->_dists[bookie]._dist[ann_id] = GRAPHENE_100_PERCENT + - aco.extensions.value.affiliate_distributions->_dists[bookie]._dist[alice_id]; + aco.extensions.value.affiliate_distributions->_dists[rps]._dist[alice_id] = GRAPHENE_100_PERCENT / 5; + aco.extensions.value.affiliate_distributions->_dists[rps]._dist[audrey_id] = GRAPHENE_100_PERCENT / 2; + aco.extensions.value.affiliate_distributions->_dists[rps]._dist[ann_id] = GRAPHENE_100_PERCENT + - aco.extensions.value.affiliate_distributions->_dists[rps]._dist[alice_id] + - aco.extensions.value.affiliate_distributions->_dists[rps]._dist[audrey_id]; + trx.operations.push_back( aco ); + + // Petra: nothing for Bookie / For RPS 10% to Ann, 90% to Audrey + const fc::ecc::private_key petra_private_key = generate_private_key( "petra" ); + aco = make_account( "petra", petra_private_key.get_public_key() ); + aco.extensions.value.affiliate_distributions = affiliate_reward_distributions(); + aco.extensions.value.affiliate_distributions->_dists[rps]._dist[ann_id] = GRAPHENE_100_PERCENT / 10; + aco.extensions.value.affiliate_distributions->_dists[rps]._dist[audrey_id] = GRAPHENE_100_PERCENT + - aco.extensions.value.affiliate_distributions->_dists[rps]._dist[ann_id]; + trx.operations.push_back( aco ); + processed_transaction result = db.push_transaction(trx, ~0); + trx.clear(); + + account_id_type paula_id = result.operation_results[0].get(); + account_id_type penny_id = result.operation_results[1].get(); + account_id_type petra_id = result.operation_results[2].get(); + + fund( martha_id(db), asset(1000000000) ); + fund( paula_id(db), asset(20000000) ); + fund( penny_id(db), asset(30000000) ); + fund( petra_id(db), asset(40000000) ); + + upgrade_to_lifetime_member( martha ); + + tournaments_helper helper(*this); + account_id_type dividend_id = *helper.get_asset_dividend_account(); + int64_t div_ppy = get_balance( dividend_id, asset_id_type() ); + const asset buy_in = asset(12000); + tournament_id_type tournament_id = helper.create_tournament( martha_id, martha_private_key, buy_in, 3, 3, 1, 1 ); + BOOST_REQUIRE(tournament_id == tournament_id_type()); + + helper.join_tournament( tournament_id, paula_id, paula_id, paula_private_key, buy_in); + helper.join_tournament( tournament_id, penny_id, penny_id, penny_private_key, buy_in); + helper.join_tournament( tournament_id, petra_id, petra_id, petra_private_key, buy_in); + + generate_block(); + const tournament_object& tournament = db.get( tournament_id ); + + BOOST_CHECK_EQUAL( 19988000, get_balance( paula_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 29988000, get_balance( penny_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 39988000, get_balance( petra_id, asset_id_type() ) ); + + const tournament_details_object& tournament_details = tournament.tournament_details_id(db); + BOOST_CHECK_EQUAL( 3, tournament_details.matches.size() ); + + { // 3 players, match 1 is a bye for penny + const match_object& match = tournament_details.matches[0](db); + BOOST_CHECK_EQUAL( int64_t(match_state::match_complete), int64_t(match.get_state()) ); + BOOST_CHECK_EQUAL( 1, match.players.size() ); + BOOST_CHECK_EQUAL( object_id_type(penny_id).instance(), object_id_type(match.players[0]).instance() ); + } + { // match 2 is paula vs. petra: paula wins + const match_object& match = tournament_details.matches[1](db); + BOOST_CHECK_EQUAL( int64_t(match_state::match_in_progress), int64_t(match.get_state()) ); + BOOST_CHECK_EQUAL( 2, match.players.size() ); + BOOST_CHECK_EQUAL( object_id_type(paula_id).instance(), object_id_type(match.players[0]).instance() ); + BOOST_CHECK_EQUAL( object_id_type(petra_id).instance(), object_id_type(match.players[1]).instance() ); + BOOST_CHECK_EQUAL( 1, match.games.size() ); + + const game_object& game = match.games[0](db); + BOOST_CHECK_EQUAL( int64_t(game_state::expecting_commit_moves), int64_t(game.get_state()) ); + helper.rps_throw( game.id, paula_id, rock_paper_scissors_gesture::paper, paula_private_key ); + helper.rps_throw( game.id, petra_id, rock_paper_scissors_gesture::rock, petra_private_key ); + + BOOST_CHECK_EQUAL( int64_t(game_state::expecting_reveal_moves), int64_t(game.get_state()) ); + helper.rps_reveal( game.id, paula_id, rock_paper_scissors_gesture::paper, paula_private_key ); + helper.rps_reveal( game.id, petra_id, rock_paper_scissors_gesture::rock, petra_private_key ); + + BOOST_CHECK_EQUAL( int64_t(game_state::game_complete), int64_t(game.get_state()) ); + BOOST_CHECK_EQUAL( 1, match.games.size() ); + BOOST_CHECK_EQUAL( int64_t(match_state::match_complete), int64_t(match.get_state()) ); + } + { // match 3 is penny vs. paula: penny wins + const match_object& match = tournament_details.matches[2](db); + BOOST_CHECK_EQUAL( int64_t(match_state::match_in_progress), int64_t(match.get_state()) ); + BOOST_CHECK_EQUAL( 2, match.players.size() ); + BOOST_CHECK_EQUAL( object_id_type(penny_id).instance(), object_id_type(match.players[0]).instance() ); + BOOST_CHECK_EQUAL( object_id_type(paula_id).instance(), object_id_type(match.players[1]).instance() ); + BOOST_CHECK_EQUAL( 1, match.games.size() ); + + const game_object& game = match.games[0](db); + BOOST_CHECK_EQUAL( int64_t(game_state::expecting_commit_moves), int64_t(game.get_state()) ); + helper.rps_throw( game.id, paula_id, rock_paper_scissors_gesture::paper, paula_private_key ); + helper.rps_throw( game.id, penny_id, rock_paper_scissors_gesture::scissors, penny_private_key ); + + BOOST_CHECK_EQUAL( int64_t(game_state::expecting_reveal_moves), int64_t(game.get_state()) ); + helper.rps_reveal( game.id, paula_id, rock_paper_scissors_gesture::paper, paula_private_key ); + helper.rps_reveal( game.id, penny_id, rock_paper_scissors_gesture::scissors, penny_private_key ); + + BOOST_CHECK_EQUAL( int64_t(game_state::game_complete), int64_t(game.get_state()) ); + BOOST_CHECK_EQUAL( int64_t(match_state::match_complete), int64_t(match.get_state()) ); + } + + BOOST_CHECK_EQUAL( 3*GRAPHENE_1_PERCENT, db.get_global_properties().parameters.rake_fee_percentage ); + // Penny wins net 3*buy_in minus rake = 36000 - 1080 = 34920 + BOOST_CHECK_EQUAL( 19988000, get_balance( paula_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 29988000 + 34920, get_balance( penny_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 39988000, get_balance( petra_id, asset_id_type() ) ); + + // Dividend account receives 80% of rake = 864 + BOOST_CHECK_EQUAL( div_ppy + 864, get_balance( dividend_id, asset_id_type() ) ); + + // 20% of rake = 216 is paid to Penny's affiliates: 43 to Alice, 64 to Ann, 109 to Audrey + BOOST_CHECK_EQUAL( 43, get_balance( alice_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 64, get_balance( ann_id, asset_id_type() ) ); + BOOST_CHECK_EQUAL( 109, get_balance( audrey_id, asset_id_type() ) ); + +} FC_LOG_AND_RETHROW() } + BOOST_AUTO_TEST_SUITE_END()