示例#1
0
    def get_exchange_rate(from_token, to_token):
        """
        eg if from USD to AUD, and 1 USD buys 2 AUD
        return AUD 2
        :param from_token:
        :param to_token:
        :return:
        """

        from_amount = 1

        exchange_contract = Exchange._find_exchange_contract(from_token, to_token)

        to_amount = bt.get_conversion_amount(
            exchange_contract=exchange_contract,
            from_token=from_token,
            to_token=to_token,
            from_amount=from_amount)

        return to_amount/from_amount
示例#2
0
    def exchange_from_amount(self,
                             user,
                             from_token,
                             to_token,
                             from_amount,
                             calculated_to_amount=None,
                             prior_task_uuids=None,
                             transfer_mode=None,
                             queue='high-priority'):
        self.user = user
        self.from_token = from_token
        self.to_token = to_token
        self.from_amount = from_amount

        self.exchange_contract = self._find_exchange_contract(
            from_token, to_token)

        self.from_transfer = server.models.credit_transfer.CreditTransfer(
            from_amount,
            from_token,
            sender_user=user,
            recipient_transfer_account=
            find_transfer_accounts_with_matching_token(self.exchange_contract,
                                                       from_token),
            transfer_type=TransferTypeEnum.EXCHANGE,
            transfer_mode=transfer_mode)

        db.session.add(self.from_transfer)

        signing_address = self.from_transfer.sender_transfer_account.blockchain_address

        prior = []

        # TODO: set these so they either only fire on the first use of the exchange, or entirely asyn
        # We need to approve all the tokens involved for spend by the exchange contract
        self.to_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=to_token,
            spender=self.exchange_contract.blockchain_address,
            amount=from_amount * 100000,
            prior_tasks=prior)

        self.reserve_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=self.exchange_contract.reserve_token,
            spender=self.exchange_contract.blockchain_address,
            amount=from_amount * 100000,
            prior_tasks=prior)

        self.from_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=from_token,
            spender=self.exchange_contract.blockchain_address,
            amount=from_amount * 100000,
            prior_tasks=prior)

        if calculated_to_amount:
            to_amount = calculated_to_amount
        else:
            to_amount = bt.get_conversion_amount(
                exchange_contract=self.exchange_contract,
                from_token=from_token,
                to_token=to_token,
                from_amount=from_amount,
                signing_address=signing_address)

        self.exchange_rate = to_amount / from_amount

        self.blockchain_task_uuid = str(uuid4())
        g.pending_transactions.append((self, queue))

        self.to_transfer = server.models.credit_transfer.CreditTransfer(
            to_amount,
            to_token,
            sender_transfer_account=find_transfer_accounts_with_matching_token(
                self.exchange_contract, to_token),
            recipient_user=user,
            transfer_type=TransferTypeEnum.EXCHANGE,
            transfer_mode=transfer_mode,
            require_sufficient_balance=False)

        db.session.add(self.to_transfer)

        self.from_transfer.blockchain_task_uuid = self.blockchain_task_uuid
        self.to_transfer.blockchain_task_uuid = self.blockchain_task_uuid

        self.from_transfer.resolve_as_complete()
        self.to_transfer.resolve_as_complete()
示例#3
0
    def exchange_from_amount(
            self, user, from_token, to_token, from_amount, calculated_to_amount=None, prior_task_uuids=None,
            transfer_mode=None
    ):
        self.user = user
        self.from_token = from_token
        self.to_token = to_token

        exchange_contract = self._find_exchange_contract(from_token, to_token)

        self.from_transfer = server.models.credit_transfer.CreditTransfer(
            from_amount,
            from_token,
            sender_user=user,
            recipient_transfer_account=find_transfer_accounts_with_matching_token(exchange_contract, from_token),
            transfer_type=TransferTypeEnum.EXCHANGE, transfer_mode=transfer_mode
        )

        if not self.from_transfer.check_sender_has_sufficient_balance():
            message = "Sender {} has insufficient balance".format(user)
            self.from_transfer.resolve_as_rejected(message)

            raise InsufficientBalanceError(message)

        db.session.add(self.from_transfer)

        signing_address = self.from_transfer.sender_transfer_account.blockchain_address

        prior = []

        # TODO: set these so they either only fire on the first use of the exchange, or entirely asyn
        # We need to approve all the tokens involved for spend by the exchange contract
        to_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=to_token,
            spender=exchange_contract.blockchain_address,
            amount=from_amount * 100000,
            prior_tasks=prior
        )

        reserve_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=exchange_contract.reserve_token,
            spender=exchange_contract.blockchain_address,
            amount=from_amount * 100000,
            prior_tasks=prior
        )

        from_approval_uuid = bt.make_approval(
            signing_address=signing_address,
            token=from_token,
            spender=exchange_contract.blockchain_address,
            amount=from_amount*100000,
            prior_tasks=prior
        )

        if calculated_to_amount:
            to_amount = calculated_to_amount
        else:
            to_amount = bt.get_conversion_amount(exchange_contract=exchange_contract,
                                              from_token=from_token,
                                              to_token=to_token,
                                              from_amount=from_amount,
                                              signing_address=signing_address)

        self.exchange_rate = to_amount/from_amount

        task_uuid = bt.make_liquid_token_exchange(
            signing_address=signing_address,
            exchange_contract=exchange_contract,
            from_token=from_token,
            to_token=to_token,
            reserve_token=exchange_contract.reserve_token,
            from_amount=from_amount,
            prior_tasks=[to_approval_uuid, reserve_approval_uuid, from_approval_uuid] + (prior_task_uuids or [])
        )

        self.to_transfer = server.models.credit_transfer.CreditTransfer(
            to_amount,
            to_token,
            sender_transfer_account=find_transfer_accounts_with_matching_token(exchange_contract, to_token),
            recipient_user=user,
            transfer_type=TransferTypeEnum.EXCHANGE, transfer_mode=transfer_mode
        )

        db.session.add(self.to_transfer)

        self.blockchain_task_uuid = task_uuid
        self.from_transfer.blockchain_task_uuid = task_uuid
        self.to_transfer.blockchain_task_uuid = task_uuid

        self.from_transfer.resolve_as_completed(existing_blockchain_txn=True)
        self.to_transfer.resolve_as_completed(existing_blockchain_txn=True)