def test_order_filled_volume(fx_buy_order: Order, fx_session: Session): fx_buy_order.volume = decimal.Decimal('2000') fx_buy_order.remaining_volume = decimal.Decimal('1000') assert fx_buy_order.filled_volume == decimal.Decimal('1000') assert fx_session.query(Order.filled_volume).filter( Order.id == fx_buy_order.id, ).scalar() == decimal.Decimal('1000')
def test_order_canceled(fx_buy_order: Order, fx_session: Session): assert fx_buy_order.canceled_at is None assert not fx_buy_order.canceled assert fx_session.query(Order.canceled).filter( Order.id == fx_buy_order.id, ).scalar() is False fx_buy_order.cancel() fx_session.flush() assert isinstance(fx_buy_order.canceled_at, datetime.datetime) assert fx_buy_order.canceled assert fx_session.query(Order.canceled).filter( Order.id == fx_buy_order.id, ).scalar() is True
def fx_trades( fx_market: Market, fx_orders: Mapping[OrderSide, Sequence[Order]], fx_session: Session, fx_user: User, fx_utcnow: datetime.datetime, ) -> Sequence[Trade]: second = datetime.timedelta(seconds=1) trades = [ Trade( id=uuid.UUID(int=1), created_at=fx_utcnow - 1 * second, pair='BTC/USDT', buy_order=Order( side=OrderSide.buy, user=fx_user, market=fx_market, volume=decimal.Decimal('2'), remaining_volume=decimal.Decimal('2'), price=decimal.Decimal('10000'), ), sell_order=fx_orders[OrderSide.sell][0], side=OrderSide.buy, volume=decimal.Decimal('2'), price=decimal.Decimal('10000'), index=0, ), Trade( id=uuid.UUID(int=2), created_at=fx_utcnow - 1 * second, pair='BTC/USDT', buy_order=fx_orders[OrderSide.buy][0], sell_order=Order( side=OrderSide.sell, user=fx_user, market=fx_market, volume=decimal.Decimal('3'), remaining_volume=decimal.Decimal('3'), price=decimal.Decimal('8000'), ), side=OrderSide.sell, volume=decimal.Decimal('3'), price=decimal.Decimal('9000'), index=0, ), ] for trade in trades: trade.buy_order.remaining_volume -= trade.volume trade.sell_order.remaining_volume -= trade.volume fx_session.add_all(trades) fx_session.flush() return trades
def test_order_remaining_locked_amount( fx_buy_order: Order, fx_sell_order: Order, fx_session: Session, ): fx_buy_order.volume = decimal.Decimal('200') fx_buy_order.remaining_volume = decimal.Decimal('100') fx_sell_order.volume = decimal.Decimal('300') fx_sell_order.remaining_volume = decimal.Decimal('150') assert fx_buy_order.remaining_locked_amount == decimal.Decimal('900000') assert fx_sell_order.remaining_locked_amount == decimal.Decimal('150') assert fx_session.query(Order.remaining_locked_amount).filter( Order.id == fx_buy_order.id, ).scalar() == decimal.Decimal('900000') assert fx_session.query(Order.remaining_locked_amount).filter( Order.id == fx_sell_order.id, ).scalar() == decimal.Decimal('150')
def test_order_active(fx_buy_order: Order, fx_session: Session): assert not fx_buy_order.filled assert not fx_buy_order.canceled assert fx_buy_order.active assert fx_session.query(Order.active).filter( Order.id == fx_buy_order.id, ).scalar() is True fx_buy_order.remaining_volume = decimal.Decimal('0') fx_session.flush() assert not fx_buy_order.active assert fx_session.query(Order.active).filter( Order.id == fx_buy_order.id, ).scalar() is False fx_buy_order.filled_at = None fx_buy_order.remaining_volume = decimal.Decimal('1') fx_buy_order.cancel() fx_session.flush() assert not fx_buy_order.active assert fx_session.query(Order.active).filter( Order.id == fx_buy_order.id, ).scalar() is False
def test_order_filled(fx_buy_order: Order, fx_session: Session): assert fx_buy_order.filled_at is None assert not fx_buy_order.filled assert fx_session.query(Order.filled).filter( Order.id == fx_buy_order.id, ).scalar() is False fx_buy_order.remaining_volume = decimal.Decimal('0') fx_session.flush() assert isinstance(fx_buy_order.filled_at, datetime.datetime) assert fx_buy_order.filled assert fx_session.query(Order.filled).filter( Order.id == fx_buy_order.id, ).scalar() is True
def fx_orders( fx_market: Market, fx_session: Session, fx_user: User, fx_utcnow: datetime.datetime, ) -> Mapping[OrderSide, Sequence[Order]]: second = datetime.timedelta(seconds=1) order_map = { OrderSide.sell: [ Order( id=uuid.UUID(int=1), created_at=fx_utcnow - 60 * second, volume=decimal.Decimal('20'), remaining_volume=decimal.Decimal('20'), price=decimal.Decimal('10000'), ), Order( id=uuid.UUID(int=2), created_at=fx_utcnow - 50 * second, volume=decimal.Decimal('25'), remaining_volume=decimal.Decimal('25'), price=decimal.Decimal('10000'), ), Order( id=uuid.UUID(int=3), created_at=fx_utcnow - 40 * second, volume=decimal.Decimal('30'), remaining_volume=decimal.Decimal('30'), price=decimal.Decimal('11000'), ), ], OrderSide.buy: [ Order( id=uuid.UUID(int=4), created_at=fx_utcnow - 30 * second, volume=decimal.Decimal('15'), remaining_volume=decimal.Decimal('15'), price=decimal.Decimal('9000'), ), Order( id=uuid.UUID(int=5), created_at=fx_utcnow - 20 * second, volume=decimal.Decimal('10'), remaining_volume=decimal.Decimal('10'), price=decimal.Decimal('9000'), ), Order( id=uuid.UUID(int=6), created_at=fx_utcnow - 10 * second, volume=decimal.Decimal('5'), remaining_volume=decimal.Decimal('5'), price=decimal.Decimal('8000'), ), ], } for side, orders in order_map.items(): for order in orders: order.side = side order.user = fx_user order.market = fx_market fx_session.add_all(itertools.chain.from_iterable(order_map.values())) fx_session.flush() return order_map
def test_order_check_constraints( fx_buy_order: Order, fx_session: Session, fx_utcnow: datetime.datetime, ): fx_session.begin_nested() fx_buy_order.price = decimal.Decimal('0') with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_price_positive' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.volume = decimal.Decimal('0') with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_volume' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.remaining_volume = decimal.Decimal('-1') with raises(IntegrityError) as e: fx_session.flush() assert 'violates check constraint' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.volume = decimal.Decimal('100') fx_buy_order.remaining_volume = decimal.Decimal('101') with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_volume' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.pair = 'BTC/BTC' with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_currency' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.remaining_volume = decimal.Decimal('0') fx_buy_order.filled_at = None with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_filled' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.remaining_volume = decimal.Decimal('1') fx_buy_order.filled_at = fx_utcnow with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_filled' in str(e.value) fx_session.rollback() fx_session.begin_nested() fx_buy_order.remaining_volume = decimal.Decimal('0') fx_buy_order.cancel() with raises(IntegrityError) as e: fx_session.flush() assert 'ck_order_canceled' in str(e.value) fx_session.rollback()
def test_order_validate_remaining_volume(fx_buy_order: Order): assert not fx_buy_order.filled fx_buy_order.remaining_volume = decimal.Decimal('0') assert fx_buy_order.filled