def test_decode_bis_url_legacy(verbose=False):
    bis_url = "bis://pay/8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234///Bg#w)r%}J-4Ct__J|z#_"
    decoded = BismuthUtil.read_url(bis_url, legacy=True)
    if verbose:
        print(decoded)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == ""
    assert decoded['openfield'] == ""
    bis_url = "bis://pay/8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234/bZ={AZaQ>wVQzC~WpV/bY*jNIxz/>H!cQZ*|L=^XYba0XP&1"
    decoded = BismuthUtil.read_url(bis_url, legacy=True)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == "token:transfer"
    assert decoded['openfield'] == "test:1"
    # Now test a broken hash
    bis_url = "bis://pay/8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234///Ag#w)r%}J-4Ct__J|z#_"
    decoded = BismuthUtil.read_url(bis_url, legacy=True)
    if verbose:
        print(decoded)
    assert "Error" in decoded
    bis_url = "bis://pay/8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234/bZ={AZaQ>wVQzC~WpV/bY*jNIx#wXB28s;b75y?B03^eWpi{OZDn(FVP|C`eE/#04XIp(|p18$+t~x+8E0"
    decoded = BismuthUtil.read_url(bis_url, legacy=True)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == "token:transfer"
    assert decoded['openfield'] == 'test:1:{"Message":"Test message"}'
def test_decode_bis_url_new(verbose=False):
    bis_url = "bis://8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234///g2ietw=="
    decoded = BismuthUtil.read_url(bis_url, legacy=False)
    if verbose:
        print("new", decoded)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == ""
    assert decoded['openfield'] == ""
    bis_url = "bis://8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234/dG9rZW46dHJhbnNmZXI=/dGVzdDox/ldW-ig=="
    decoded = BismuthUtil.read_url(bis_url, legacy=False)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == "token:transfer"
    assert decoded['openfield'] == "test:1"
    # Now test a broken hash
    bis_url = "bis://8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234///g4ietw=="
    decoded = BismuthUtil.read_url(bis_url, legacy=False)
    if verbose:
        print("new", decoded)
    assert "Error" in decoded
    bis_url = "bis://pay/8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742/1.234/bZ={AZaQ>wVQzC~WpV/bY*jNIx#wXB28s;b75y?B03^eWpi{OZDn(FVP|C`eE/#04XIp(|p18$+t~x+8E0"
    decoded = BismuthUtil.read_url(bis_url, legacy=True)
    assert decoded[
        'recipient'] == "8342c1610de5d7aa026ca7ae6d21bd99b1b3a4654701751891f08742"
    assert decoded['amount'] == "1.234"
    assert decoded['operation'] == "token:transfer"
    assert decoded['openfield'] == 'test:1:{"Message":"Test message"}'
示例#3
0
    def execute(self, bot, update, args):
        if len(args) == 0:
            msg = f"Usage:\n{self.get_usage()}"
            update.message.reply_text(msg, parse_mode=ParseMode.MARKDOWN)
            return

        username = update.effective_user.username

        # Check if user has a wallet
        if not Bismuth.wallet_exists(username):
            msg = "Accept terms and create a wallet first with:\n/accept"
            update.message.reply_text(msg)
            return

        try:
            decode = BismuthUtil.read_url(args[0])
        except Exception as e:
            msg = f"{emo.ERROR} Does not look like a proper BIS URL"
            update.message.reply_text(msg, parse_mode=ParseMode.MARKDOWN)
            logging.error(f"{msg}: {e}")
            return

        amount = float(decode['amount'])
        address = decode['recipient']
        operation = decode['operation']
        message = decode['openfield']
        fees = BismuthUtil.fee_for_tx(message)

        # Check if provided address is valid
        if not BismuthUtil.valid_address(address):
            update.message.reply_text(
                text=f"{emo.ERROR} Provided address is not valid",
                parse_mode=ParseMode.MARKDOWN)
            return

        bisurl_id = self.unix_time()

        # Save transaction to database
        insert = self.get_resource("insert_bisurl.sql")
        self.execute_sql(insert, bisurl_id, username, address, amount,
                         operation, message)

        msg = "Execute following transaction?\n\n"
        msg += "▸ Recipient: {}\n".format(address)
        msg += "▸ Amount: {:.2f} BIS\n".format(amount)
        msg += "▸ Operation: {}\n".format(operation)
        msg += "▸ Message: {}\n".format(message)
        msg += "▸ Fees: {} BIS\n".format(fees)

        update.message.reply_text(msg, reply_markup=self._keyboard(bisurl_id))
示例#4
0
    async def bisurl(self, ctx, bisurl: str, send: str = 'NO'):
        """Decode a transaction from a BIS URL. Append SEND to effectively send the tx."""
        # TODO: too much code in common with withdraw, factorize somehow.
        try:
            try:
                decode = BismuthUtil.read_url(bisurl)
            except Exception as e:
                await ctx.message.add_reaction('😢')  # Crying
                await ctx.send("Does not look like a proper BIS URL")
                return
            amount = float(decode['amount'])
            address = decode['recipient']
            operation = decode['operation']
            message = decode['openfield']
            fees = BismuthUtil.fee_for_tx(message)

            decoded = "▸ Recipient: {}\n".format(address)
            decoded += "▸ Amount: {:.2f} $BIS\n".format(amount)
            decoded += "▸ Operation: {}\n".format(operation)
            decoded += "▸ Message: {}\n".format(message)
            decoded += "▸ Fees: {} $BIS\n".format(fees)
            if send == 'SEND':
                title = "Decoded BIS URL:"
                em = discord.Embed(description=decoded,
                                   colour=discord.Colour.green())
                em.set_author(name=title)
                await ctx.send(embed=em)
            else:
                title = "Decoded BIS URL: (**not** sent)"
                decoded += " \nPaste this command again and append ` SEND` if you want to send that transaction.\n"
                em = discord.Embed(description=decoded,
                                   colour=discord.Colour.green())
                em.set_author(name=title)
                await ctx.send(embed=em)
                return

            user = User(ctx.author.id)
            user_info = user.info()
            # Check the address looks ok
            if not BismuthUtil.valid_address(decode['recipient']):
                print("address error")
                await ctx.message.add_reaction('😟')
                await ctx.send(
                    "Address does not look ok. Command is `Pawer operation <operation> <address> <amount> [message]`"
                )
                return

            if user_info and user_info['address']:
                # User exists and validated the terms, has an address
                # Make sure balance is enough
                balance = float(user.balance())
                msg = "{} withdraw {}, balance is {} ".format(
                    ctx.author.display_name, amount, balance)
                fees = BismuthUtil.fee_for_tx(message)
                print(msg)
                if balance < amount + 0.01:
                    print("balance too low")
                    await ctx.message.add_reaction('😟')
                    await ctx.send(
                        "Not enough balance to cover amount + fee ({} Fees)".
                        format(fees))
                    return
                send = user.send_bis_to(amount,
                                        address,
                                        data=message,
                                        operation=operation)
                txid = send['txid']
                print("txid", txid)
                if txid:
                    # answer by reaction not to pollute
                    await ctx.message.add_reaction('👍')  # Thumb up
                    await ctx.send("Done, txid is {}.".format(txid))
                else:
                    await ctx.message.add_reaction('👎')  # Thumb down
                    await ctx.send("Error {}".format(send['error']))
                return
            # Depending on channel, say or send PM
            em = discord.Embed(description=DISCLAIMER,
                               colour=discord.Colour.red())
            em.set_author(name="You have to create your address first:")
            await ctx.send(embed=em)
        except Exception as e:
            print(str(e))
            # Send a PM to the sender or answer if dedicated channel
            await ctx.message.add_reaction('👎')  # Thumb down
            await ctx.send("Error {}".format(e))
示例#5
0
    async def send_pop(self, params=None):
        # TODO: factorize, common code with send.
        _ = self.locale.translate
        self.settings["page_title"] = _("Send BIS")

        if not self.bismuth_vars["address"]:
            await self.message(
                _("Error:") + " " + _("No Wallet"),
                _("Load your wallet first"),
                "danger",
            )
            return
        # print(self.bismuth.wallet())
        if self.bismuth._wallet._locked:
            self.message(
                _("Error:") + " " + _("Encrypted wallet"),
                _("You have to unlock your wallet first"),
                "danger",
            )
            return
        if self.get_argument("url", False):
            # print("url", self.get_argument('url'))
            # We have an url param, confirm once decoded
            self.settings["page_title"] = _("Send BIS: Confirmation")
            type = "warning"  # Do not translate
            title = _("Please confirm this transaction")
            message = _(
                'Check this is what you intended to do and hit the "confirm" button'
            )
            # self.bismuth_vars['recipient'] operation data amount
            decoded = BismuthUtil.read_url(self.get_argument("url"))
            if decoded.get("Error", False):
                self.message_pop(_("Error:"), _(decoded["Error"]), "warning")
                return
            # print(decoded)
            self.bismuth_vars["params"]["recipient"] = decoded["recipient"]
            self.bismuth_vars["params"]["amount"] = decoded["amount"]
            self.bismuth_vars["params"]["operation"] = decoded["operation"]
            self.bismuth_vars["params"]["data"] = decoded["openfield"]
            if self.bismuth_vars["params"][
                "data"
            ] == "" and self.bismuth.reject_empty_message_for(
                self.bismuth_vars["params"]["recipient"]
            ):
                await self.message_pop(
                    _("Error:") + " " + _("No message"),
                    _("Sending to this recipient needs a proper message"),
                    "danger",
                )
                return
            # TODO: address ok?
            # todo: amount ok
            # todo: enough balance?
            self.render(
                "transactions_sendpop_confirm.html",
                bismuth=self.bismuth_vars,
                type=type,
                title=title,
                message=message,
            )
        elif self.get_argument("recipient", False):
            # We have an address param, it's a confirmation
            self.settings["page_title"] = _("Send BIS: Confirmation")
            type = "warning"  # Do not translate
            title = _("Please confirm this transaction")
            message = _(
                'Check this is what you intended to do and hit the "confirm" button'
            )

            self.bismuth_vars["params"]["recipient"] = self.get_argument("recipient")
            self.bismuth_vars["params"]["amount"] = self.get_argument(
                "amount", "0.00000000"
            )
            self.bismuth_vars["params"]["operation"] = self.get_argument(
                "operation", ""
            )
            self.bismuth_vars["params"]["data"] = self.get_argument("data", "")
            if self.bismuth_vars["params"][
                "data"
            ] == "" and self.bismuth.reject_empty_message_for(
                self.bismuth_vars["params"]["recipient"]
            ):
                await self.message_pop(
                    _("Error:") + " " + _("No message"),
                    _("Sending to this recipient needs a proper message"),
                    "danger",
                )
                return

            # TODO: address ok?
            # todo: amount ok
            # todo: enough balance?
            self.render(
                "transactions_sendpop_confirm.html",
                bismuth=self.bismuth_vars,
                type=type,
                title=title,
                message=message,
            )
        else:
            self.message(_("Error:"), "No recipient", "warning")