adds basic resolve_claims + test
This commit is contained in:
@@ -42,7 +42,7 @@ pub type ActionResult<R> = Result<R, diesel::result::Error>;
|
|||||||
/// x .sell_loot([players], [excluded_item_ids]) -> Success status (bool, player_share)
|
/// x .sell_loot([players], [excluded_item_ids]) -> Success status (bool, player_share)
|
||||||
/// // Claims should be resolved after a certain delay
|
/// // Claims should be resolved after a certain delay
|
||||||
/// x .set_claims_timeout()
|
/// x .set_claims_timeout()
|
||||||
/// x .resolve_claims()
|
/// v .resolve_claims()
|
||||||
/// v .add_player(player_data)
|
/// v .add_player(player_data)
|
||||||
/// ```
|
/// ```
|
||||||
///
|
///
|
||||||
@@ -126,7 +126,7 @@ impl<'q> AsPlayer<'q> {
|
|||||||
/// # Panics
|
/// # Panics
|
||||||
///
|
///
|
||||||
/// This currently panics if player wealth fails to be updated, as this is
|
/// This currently panics if player wealth fails to be updated, as this is
|
||||||
/// a serious error. TODO: handle deletion of bought item in case of wealth update failure.
|
/// a serious error.
|
||||||
pub fn buy<'a>(self, name: &'a str, price: i32) -> ActionResult<(i32, i32, i32, i32)> {
|
pub fn buy<'a>(self, name: &'a str, price: i32) -> ActionResult<(i32, i32, i32, i32)> {
|
||||||
self.conn.transaction(|| {
|
self.conn.transaction(|| {
|
||||||
let new_item = models::item::NewLoot::to_player(self.id, (name, price));
|
let new_item = models::item::NewLoot::to_player(self.id, (name, price));
|
||||||
@@ -146,31 +146,25 @@ impl<'q> AsPlayer<'q> {
|
|||||||
/// # Panics
|
/// # Panics
|
||||||
///
|
///
|
||||||
/// This currently panics if player wealth fails to be updated, as this is
|
/// This currently panics if player wealth fails to be updated, as this is
|
||||||
/// a serious error. TODO: handle restoring of sold item in case of wealth update failure.
|
/// a serious error.
|
||||||
pub fn sell(
|
pub fn sell(
|
||||||
self,
|
self,
|
||||||
loot_id: i32,
|
loot_id: i32,
|
||||||
_price_mod: Option<f32>,
|
_price_mod: Option<f32>,
|
||||||
) -> ActionResult<(i32, i32, i32, i32)> {
|
) -> ActionResult<(i32, i32, i32, i32)> {
|
||||||
// Check that the item belongs to player
|
|
||||||
let exists_and_owned: bool =
|
|
||||||
diesel::select(models::Loot::owns(self.id, loot_id)).get_result(self.conn)?;
|
|
||||||
if !exists_and_owned {
|
|
||||||
return Err(diesel::result::Error::NotFound);
|
|
||||||
}
|
|
||||||
self.conn.transaction(|| {
|
self.conn.transaction(|| {
|
||||||
use schema::looted::dsl::*;
|
use schema::looted::dsl::*;
|
||||||
let loot_value = looted
|
let loot = looted
|
||||||
.find(loot_id)
|
.find(loot_id)
|
||||||
.select(base_price)
|
.first::<models::Loot>(self.conn)?;
|
||||||
.first::<i32>(self.conn)?;
|
if loot.owner != self.id {
|
||||||
let sell_value = (loot_value / 2) as f32;
|
// If the item does not belong to player,
|
||||||
|
// it can't be what we're looking for
|
||||||
|
return Err(diesel::result::Error::NotFound);
|
||||||
|
}
|
||||||
|
let sell_value = (loot.base_price / 2) as f32;
|
||||||
let _deleted = diesel::delete(looted.find(loot_id))
|
let _deleted = diesel::delete(looted.find(loot_id))
|
||||||
.execute(self.conn)
|
.execute(self.conn)?;
|
||||||
.map(|rows_updated| match rows_updated {
|
|
||||||
1 => (),
|
|
||||||
_ => panic!("RuntimeError: Sell did not update DB as expected"),
|
|
||||||
})?;
|
|
||||||
self.update_wealth(sell_value)
|
self.update_wealth(sell_value)
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -271,10 +265,32 @@ impl<'q> AsAdmin<'q> {
|
|||||||
.grouped_by(&loot);
|
.grouped_by(&loot);
|
||||||
// For each claimed item
|
// For each claimed item
|
||||||
let data = loot.into_iter().zip(claims).collect::<Vec<_>>();
|
let data = loot.into_iter().zip(claims).collect::<Vec<_>>();
|
||||||
dbg!(data);
|
dbg!(&data);
|
||||||
// If mutiples claims -> find highest resolve, give to this player
|
|
||||||
// If only one claim -> give to claiming
|
for (loot, claims) in data {
|
||||||
Err(diesel::result::Error::NotFound)
|
match claims.len() {
|
||||||
|
1 => {
|
||||||
|
let claim = claims.get(0).unwrap();
|
||||||
|
let player_id = claim.player_id;
|
||||||
|
self.0.transaction(|| {
|
||||||
|
use schema::looted::dsl::*;
|
||||||
|
diesel::update(looted.find(claim.loot_id))
|
||||||
|
.set(owner_id.eq(player_id))
|
||||||
|
.execute(self.0)?;
|
||||||
|
diesel::delete(schema::claims::table.find(claim.id))
|
||||||
|
.execute(self.0)?;
|
||||||
|
{
|
||||||
|
use schema::players::dsl::*;
|
||||||
|
diesel::update(players.find(player_id))
|
||||||
|
.set(debt.eq(debt + (loot.base_price / 2)))
|
||||||
|
.execute(self.0)
|
||||||
|
}
|
||||||
|
})?;
|
||||||
|
},
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -304,7 +320,7 @@ mod tests {
|
|||||||
/// When migrations are run, a special player with id 0 and name "Groupe"
|
/// When migrations are run, a special player with id 0 and name "Groupe"
|
||||||
/// must be created.
|
/// must be created.
|
||||||
#[test]
|
#[test]
|
||||||
fn test_group_is_autocreated() {
|
fn global_group_is_autocreated() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
let players = DbApi::with_conn(&conn).fetch_players().unwrap();
|
let players = DbApi::with_conn(&conn).fetch_players().unwrap();
|
||||||
assert_eq!(players.len(), 1);
|
assert_eq!(players.len(), 1);
|
||||||
@@ -316,7 +332,7 @@ mod tests {
|
|||||||
/// When a player updates wealth, a difference is returned by API.
|
/// When a player updates wealth, a difference is returned by API.
|
||||||
/// Added to the previous amount of coins, it should equal the updated weath.
|
/// Added to the previous amount of coins, it should equal the updated weath.
|
||||||
#[test]
|
#[test]
|
||||||
fn test_player_updates_wealth() {
|
fn as_player_updates_wealth() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
DbApi::with_conn(&conn)
|
DbApi::with_conn(&conn)
|
||||||
.as_admin()
|
.as_admin()
|
||||||
@@ -339,7 +355,7 @@ mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_admin_add_player() {
|
fn as_admin_add_player() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
let result = DbApi::with_conn(&conn)
|
let result = DbApi::with_conn(&conn)
|
||||||
.as_admin()
|
.as_admin()
|
||||||
@@ -356,15 +372,35 @@ mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_admin_resolve_claims() {
|
fn as_admin_resolve_claims() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
let claims = DbApi::with_conn(&conn).fetch_claims().unwrap();
|
let claims = DbApi::with_conn(&conn).fetch_claims().unwrap();
|
||||||
assert_eq!(claims.len(), 0);
|
assert_eq!(claims.len(), 0);
|
||||||
assert_eq!(true, false); // Failing as test is not complete
|
|
||||||
|
// Add items
|
||||||
|
assert_eq!(DbApi::with_conn(&conn).as_admin().add_loot(vec![
|
||||||
|
("Épée", 40),
|
||||||
|
("Arc", 40),
|
||||||
|
]).is_ok(), true);
|
||||||
|
// Add players
|
||||||
|
DbApi::with_conn(&conn).as_admin().add_player("Player1".to_string(), 0.0).unwrap();
|
||||||
|
DbApi::with_conn(&conn).as_admin().add_player("Player2".to_string(), 0.0).unwrap();
|
||||||
|
// Put claims on one different item each
|
||||||
|
DbApi::with_conn(&conn).as_player(1).claim(1).unwrap();
|
||||||
|
DbApi::with_conn(&conn).as_player(2).claim(2).unwrap();
|
||||||
|
let result = DbApi::with_conn(&conn).as_admin().resolve_claims();
|
||||||
|
assert_eq!(result.is_ok(), true);
|
||||||
|
// Check that both players received an item
|
||||||
|
let players = DbApi::with_conn(&conn).fetch_players().unwrap();
|
||||||
|
for &i in [1, 2].into_iter() {
|
||||||
|
assert_eq!(DbApi::with_conn(&conn).as_player(i).loot().unwrap().len(), 1);
|
||||||
|
let player = players.get(i as usize).unwrap();
|
||||||
|
assert_eq!(player.debt, 20);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_player_claim_item() {
|
fn as_player_claim_item() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
DbApi::with_conn(&conn)
|
DbApi::with_conn(&conn)
|
||||||
.as_admin()
|
.as_admin()
|
||||||
@@ -388,7 +424,7 @@ mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_player_unclaim_item() {
|
fn as_player_unclaim_item() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
DbApi::with_conn(&conn)
|
DbApi::with_conn(&conn)
|
||||||
.as_admin()
|
.as_admin()
|
||||||
@@ -418,8 +454,9 @@ mod tests {
|
|||||||
///
|
///
|
||||||
/// Checks that player's chest and wealth are updated.
|
/// Checks that player's chest and wealth are updated.
|
||||||
/// Checks that items are sold at half their value.
|
/// Checks that items are sold at half their value.
|
||||||
|
/// Checks that a player cannot sell item he does not own.
|
||||||
#[test]
|
#[test]
|
||||||
fn test_buy_sell_simple() {
|
fn as_player_simple_buy_sell() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
DbApi::with_conn(&conn)
|
DbApi::with_conn(&conn)
|
||||||
.as_admin()
|
.as_admin()
|
||||||
@@ -438,10 +475,11 @@ mod tests {
|
|||||||
let players = DbApi::with_conn(&conn).fetch_players().unwrap();
|
let players = DbApi::with_conn(&conn).fetch_players().unwrap();
|
||||||
let player = players.get(1).unwrap();
|
let player = players.get(1).unwrap();
|
||||||
assert_eq!(player.pp, 2);
|
assert_eq!(player.pp, 2);
|
||||||
|
// A player cannot sell loot from an other's chest
|
||||||
|
let result = DbApi::with_conn(&conn).as_player(0).sell(loot.id, None);
|
||||||
|
assert_eq!(result.is_ok(), false);
|
||||||
// Sell back
|
// Sell back
|
||||||
let sold = DbApi::with_conn(&conn)
|
let sold = DbApi::with_conn(&conn).as_player(1).sell(loot.id, None);
|
||||||
.as_player(1)
|
|
||||||
.sell(loot.id, None);
|
|
||||||
assert_eq!(sold.ok(), Some((0, 0, 0, 4)));
|
assert_eq!(sold.ok(), Some((0, 0, 0, 4)));
|
||||||
let chest = DbApi::with_conn(&conn).as_player(1).loot().unwrap();
|
let chest = DbApi::with_conn(&conn).as_player(1).loot().unwrap();
|
||||||
assert_eq!(chest.len(), 0);
|
assert_eq!(chest.len(), 0);
|
||||||
@@ -451,7 +489,7 @@ mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_admin_add_loot() {
|
fn as_admin_add_loot() {
|
||||||
let conn = test_connection();
|
let conn = test_connection();
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
0,
|
0,
|
||||||
|
|||||||
@@ -35,8 +35,8 @@ type OwnedLoot = Filter<looted::table, WithOwner>;
|
|||||||
pub(crate) struct Loot {
|
pub(crate) struct Loot {
|
||||||
id: i32,
|
id: i32,
|
||||||
name: String,
|
name: String,
|
||||||
base_price: i32,
|
pub(crate) base_price: i32,
|
||||||
owner: i32,
|
pub(crate) owner: i32,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Loot {
|
impl Loot {
|
||||||
|
|||||||
Reference in New Issue
Block a user