示例#1
0
def cover_order(order: Order):
    base_currency = Currency[order.base_currency]

    quote = LpClient().get_quote(
        CurrencyPair(base=base_currency, quote=INVENTORY_COVER_CURRENCY),
        amount=order.amount,
    )

    update_order(
        order_id=OrderId(UUID(order.id)),
        quote_id=str(quote.quote_id),
        quote_expiration=quote.expires_at,
        rate=quote.rate.rate,
        cover_status=CoverStatus.PendingCoverWithQuote,
    )

    covered = False
    if Direction[order.direction] == Direction.Sell:
        covered = _cover_sell(order, quote)

    elif Direction[order.direction] == Direction.Buy:
        covered = _cover_buy(order, quote)

    if covered:
        update_order(order_id=OrderId(UUID(order.id)), cover_status=CoverStatus.Covered)
示例#2
0
def cover_order(order_id: OrderId):
    order = get_order(order_id)

    if order.order_type == OrderType.DirectConvert.value:
        update_order(order_id=order_id, cover_status=CoverStatus.Covered)
        return

    inventory.cover_order(order)
示例#3
0
def test_update_order(clean_db: None) -> None:
    user_id, order_id = OneUserWithOneOrder().run(db_session)

    update_order(OrderId(UUID(order_id)),
                 order_status=OrderStatus.FailedCredit)

    order = get_order(order_id)

    assert order.order_status == OrderStatus.FailedCredit.value
示例#4
0
def order_expired(order_id: OrderId):
    order = get_order(order_id)

    is_expired = datetime.utcnow() > order.order_expiration

    if is_expired:
        update_order(order_id=order_id, order_status=OrderStatus.Expired)
        return True

    return False
示例#5
0
def execute_convert(order: Order) -> ConvertResult:
    inventory_account = get_account(account_name=INVENTORY_ACCOUNT_NAME).id
    user_account = get_user(order.user_id).account.id
    order_id = typing.cast(OrderId, order.id)

    from_amount = order.amount
    from_diem_currency = DiemCurrency[order.base_currency]
    to_amount = order.exchange_amount
    to_diem_currency = DiemCurrency[order.quote_currency]

    if not validate_balance(sender_id=user_account,
                            amount=from_amount,
                            currency=from_diem_currency):
        return ConvertResult.InsufficientBalance

    if not validate_balance(sender_id=inventory_account,
                            amount=to_amount,
                            currency=to_diem_currency):
        return ConvertResult.InsufficientInventoryBalance

    try:
        to_inventory_tx = internal_transaction(
            sender_id=user_account,
            receiver_id=inventory_account,
            amount=from_amount,
            currency=from_diem_currency,
            payment_type=TransactionType.INTERNAL,
        )
        from_inventory_tx = internal_transaction(
            sender_id=inventory_account,
            receiver_id=user_account,
            amount=to_amount,
            currency=to_diem_currency,
            payment_type=TransactionType.INTERNAL,
        )
        update_order(
            order_id=order_id,
            internal_ledger_tx=to_inventory_tx.id,
            correlated_tx=from_inventory_tx.id,
            order_status=OrderStatus.Executed,
        )
        return ConvertResult.Success
    except Exception:
        logging.exception("execute convert")
        update_order(order_id=order_id, order_status=OrderStatus.FailedExecute)
        return ConvertResult.TransferFailure
示例#6
0
def process_order_payment(order_id, payment_method,
                          action: PaymentMethodAction):
    order = get_order(order_id)

    time.sleep(PAYMENT_PROCESSING_DUMMY_SLEEP_TIME)
    charge_token = process_payment_method(payment_method,
                                          order.exchange_amount, action)

    if charge_token:
        update_order(
            order_id=order_id,
            charge_token=charge_token,
            order_status=OrderStatus.Charged.value,
            payment_method=payment_method,
        )
    else:
        update_order(
            order_id=order_id,
            order_status=OrderStatus.FailedCharge.value if action
            == PaymentMethodAction.Charge else OrderStatus.FailedCredit,
            payment_method=payment_method,
        )

    return charge_token
示例#7
0
def execute_trade(order: Order):
    inventory_account_id = get_account(account_name=INVENTORY_ACCOUNT_NAME).id
    user_account_id = get_user(order.user_id).account.id
    order_id = typing.cast(OrderId, order.id)

    base_diem_currency = DiemCurrency[order.base_currency]

    if Direction[order.direction] == Direction.Buy:
        sender_id = inventory_account_id
        receiver_id = user_account_id

        if not validate_balance(sender_id, order.amount, base_diem_currency):
            buy_funds(CurrencyPairs[
                f"{base_diem_currency}_{INVENTORY_COVER_CURRENCY}"])
    else:
        sender_id = user_account_id
        receiver_id = inventory_account_id

    try:
        transaction = internal_transaction(
            sender_id=sender_id,
            receiver_id=receiver_id,
            amount=order.amount,
            currency=base_diem_currency,
            payment_type=TransactionType.INTERNAL,
        )
        update_order(
            order_id=order_id,
            internal_ledger_tx=transaction.id,
            order_status=OrderStatus.Executed,
        )
        return True
    except BalanceError:
        logging.exception("execute trade")
        update_order(order_id=order_id, order_status=OrderStatus.FailedExecute)
        return False
示例#8
0
def _cover_sell(order: Order, quote: QuoteData) -> bool:
    transfer_to_lp_blockchain_version = _transfer_funds_to_lp(order)

    if transfer_to_lp_blockchain_version == -1:
        update_order(
            order_id=OrderId(UUID(order.id)),
            cover_status=CoverStatus.FailedCoverTransactionError,
        )
        return False

    trade_info = LpClient().trade_and_execute(
        quote_id=quote.quote_id,
        direction=Direction[order.direction],
        tx_version=transfer_to_lp_blockchain_version,
    )

    if not trade_info:
        update_order(
            order_id=OrderId(UUID(order.id)),
            cover_status=CoverStatus.FailedCoverLPTradeError,
        )
        return False

    return True
示例#9
0
def _cover_buy(order: Order, quote: QuoteData) -> bool:
    deposit_address = get_inventory_deposit_address()
    trade_id = LpClient().trade_and_execute(
        quote_id=quote.quote_id,
        direction=Direction[order.direction],
        diem_deposit_address=deposit_address,
    )
    trade_info = _wait_for_trade(order=order, trade_id=trade_id)

    if not trade_info:
        update_order(
            order_id=OrderId(UUID(order.id)),
            cover_status=CoverStatus.FailedCoverLPTradeError,
        )
        return False

    update_order(
        order_id=OrderId(UUID(order.id)),
        cover_status=CoverStatus.PendingCoverValidation,
    )

    vasp_address, internal_subaddress = decode_account(
        deposit_address, context.get().config.diem_address_hrp()
    )
    if not _validate_blockchain_transaction(
        blockchain_version=trade_info.tx_version,
        vasp_address=utils.account_address_hex(vasp_address),
        internal_subaddress=internal_subaddress.hex(),
        amount=round(trade_info.amount),
    ):
        update_order(
            order_id=OrderId(UUID(order.id)),
            cover_status=CoverStatus.FailedCoverTransactionError,
        )
        return False

    return True