Exemple #1
0
class HWBalance(Base):
    """A Hot Wallet Balance, for internal use only"""
    id = sa.Column(sa.Integer, sa.Sequence('hwbalance_id_seq'), primary_key=True)
    available = sa.Column(LedgerAmount, nullable=False)
    total = sa.Column(LedgerAmount, nullable=False)
    currency = sa.Column(sa.String(4), nullable=False)  # i.e. BTC, DASH, USDT
    network = sa.Column(sa.String(64), nullable=False)  # i.e. Bitcoin, Dash, Crypto Capital
    time = sa.Column(sa.DateTime(), default=datetime.datetime.utcnow)

    def __init__(self, available, total, currency, network):
        self.available = available
        self.total = total
        self.currency = currency
        self.network = network
        self.load_commodities()

    @orm.reconstructor
    def load_commodities(self):
        """
        Load the commodities for Amounts in this object.
        """
        if isinstance(self.available, Amount):
            self.available = Amount("{0:.8f} {1}".format(self.available.to_double(), self.currency))
        else:
            self.available = Amount("{0:.8f} {1}".format(self.available, self.currency))
        if isinstance(self.total, Amount):
            self.total = Amount("{0:.8f} {1}".format(self.total.to_double(), self.currency))
        else:
            self.total = Amount("{0:.8f} {1}".format(self.total, self.currency))
Exemple #2
0
class Credit(Base):
    """A Credit, which adds tokens to a User's Balance."""
    id = sa.Column(sa.Integer, sa.Sequence('credit_id_seq'), primary_key=True)
    amount = sa.Column(LedgerAmount, nullable=False)
    address = sa.Column(sa.String(64),
                        nullable=False)  # i.e. 1PkzTWAyfR9yoFw2jptKQ3g6E5nKXPsy8r, XhwWxABXPVG5Z3ePyLVA3VixPRkARK6FKy
    currency = sa.Column(sa.String(4), nullable=False)  # i.e. BTC, DASH, USD
    network = sa.Column(sa.String(64), nullable=False)  # i.e. Bitcoin, Dash, Crypto Capital
    transaction_state = sa.Column(sa.Enum("unconfirmed", "complete", "error", "canceled", name='transaction_state'), nullable=False)
    reference = sa.Column(sa.String(256), nullable=True)  # i.e. invoice#1
    ref_id = sa.Column(sa.String(256), nullable=False,
                       unique=True)  # i.e. 4cef42f9ff334b9b11bffbd9da21da54176103d92c1c6e4442cbe28ca43540fd:0
    time = sa.Column(sa.DateTime(), nullable=False)

    # foreign key reference to the owner of this
    user_id = sa.Column(
        sa.Integer,
        sa.ForeignKey('user.id'),
        nullable=False)
    user = orm.relationship("User", foreign_keys=[user_id])

    def __init__(self, amount, address, currency, network, transaction_state, reference, ref_id, user_id, time):
        self.amount = amount
        self.address = address
        self.currency = currency
        self.network = network
        self.transaction_state = transaction_state
        self.reference = reference
        self.ref_id = ref_id
        self.user_id = user_id
        # self.time = pytz.utc.localize(time)
        self.time = time.replace(tzinfo=None)
        self.load_commodities()

    def __repr__(self):
        return "<Credit(amount=%s, address='%s', currency='%s', network='%s', transaction_state='%s', reference='%s', " \
               "ref_id='%s', time=%s)>" % (
                   self.amount, self.address, self.currency, self.network,
                   self.transaction_state, self.network, self.ref_id, datetime_rfc3339(self.time))

    def get_ledger_entry(self):
        date = self.time.strftime('%Y/%m/%d %H:%M:%S')
        ledger = "%s %s %s %s\n" % (date, self.reference, 'credit', self.currency)
        ledger += "    Assets:{0}:{1}:credit    {2}\n".format(self.network, self.currency, self.amount)
        ledger += "    Equity:Wallet:{0}:debit   {1}\n".format(self.currency, -self.amount)
        ledger += "\n"
        return ledger

    @orm.reconstructor
    def load_commodities(self):
        """
        Load the commodities for Amounts in this object.
        """
        if isinstance(self.amount, Amount):
            self.amount = Amount("{0:.8f} {1}".format(self.amount.to_double(), self.currency))
        else:
            self.amount = Amount("{0:.8f} {1}".format(self.amount, self.currency))
Exemple #3
0
class Balance(Base):
    """A user's balance in a single currency. Only the latest record is valid."""
    id = sa.Column(sa.Integer, sa.Sequence('balance_id_seq'), primary_key=True)
    total = sa.Column(LedgerAmount, nullable=False)
    available = sa.Column(LedgerAmount, nullable=False)
    currency = sa.Column(sa.String(4), nullable=False)  # i.e. BTC, DASH, USD
    time = sa.Column(sa.DateTime(), default=datetime.datetime.utcnow)
    reference = sa.Column(sa.String(256), nullable=True)

    # foreign key reference to the owner of this
    user_id = sa.Column(
        sa.Integer,
        sa.ForeignKey('user.id'),
        nullable=False)
    user = orm.relationship("User", foreign_keys=[user_id])

    def __init__(self, total, available, currency, reference, user_id, time=None):
        self.total = total
        self.available = available
        self.currency = currency
        self.reference = reference
        self.user_id = user_id
        self.time = time if time is not None else datetime.datetime.utcnow()
        self.load_commodities()

    def __repr__(self):
        return "<Balance(total=%s, available=%s, currency='%s', reference='%s', user_id=%s, time=%s)>" % (
                   self.total, self.available, self.currency,
                   self.reference, self.user_id, datetime_rfc3339(self.time))

    @orm.reconstructor
    def load_commodities(self):
        """
        Load the commodities for Amounts in this object.
        """
        if isinstance(self.available, Amount):
            self.available = Amount("{0:.8f} {1}".format(self.available.to_double(), self.currency))
        else:
            self.available = Amount("{0:.8f} {1}".format(self.available, self.currency))
        if isinstance(self.total, Amount):
            self.total = Amount("{0:.8f} {1}".format(self.total.to_double(), self.currency))
        else:
            self.total = Amount("{0:.8f} {1}".format(self.total, self.currency))
Exemple #4
0
def fib_fan(side, amount, ticker, session):
    def calc_price(sid, index, offset):
        if sid == 'ask':
            return index * (Amount("1 %s" % index.commodity) + Amount("%s %s" % (offset, index.commodity)) / 100)
        else:
            return index * (Amount("1 %s" % index.commodity) - Amount("%s %s" % (offset, index.commodity)) / 100)

    usdamount = get_usd_value(amount)
    if usdamount <= MINORDER:
        print "ignoring dusty order %s worth %s" % (usdamount, usdamount)
        return
    fibseq = [1, 2, 3, 5, 8, 13]
    index = ticker.calculate_index()
    base = ticker.market.split("_")[0]
    if usdamount / Amount("{0} USD".format(len(fibseq))) <= MINORDER:
        price = calc_price(side, index, fibseq[int(round(len(fibseq) / 2))])
        if side == 'bid':
            amount = Amount("{0:.8f} {1}".format(amount.to_double(), base)) / \
                     Amount("{0:.8f} {1}".format(index.to_double(), base))
        # usdval = get_usd_value(amount)
        # print "{0} {1} @ {2:0.6f} {3} worth ${4:0.2f})".format(side, amount, price.to_double(), ticker.market,
        #                                                        usdval.to_double())
        create_order(ticker.exchange, price=price, amount=amount, market=ticker.market, side=side, session=session)
    else:
        if side == 'bid':
            amount = Amount("{0:.8f} {1}".format((amount / len(fibseq)).to_double(), base)) / \
                     Amount("{0:.8f} {1}".format(index.to_double(), base))
        else:
            amount /= len(fibseq)
        for fib in fibseq:
            price = calc_price(side, index, fib)
            create_order(ticker.exchange, price=price, amount=amount, market=ticker.market, side=side, session=session)
            # usdval = get_usd_value(amount) * price / index
            # print "{0} {1} @ {2:0.6f} {3} worth ${4:0.2f})".format(side, amount, price.to_double(),
            #                                                        ticker.market, usdval.to_double())
    sync_balances(ticker.exchange)
Exemple #5
0
def test_money_cycle():
    fee = Amount("%s BTC" % CFG.get('internal', 'FEE'))
    amount = Amount("%s BTC" % 0.01)
    # Receive Internal to user
    addy = client.get_model('Address')(currency='BTC', network='Internal')
    address = client.address.createAddress(address=addy).result()
    internal_credit(address.address, amount + fee, session=ses)

    for i in range(0, 60):
        c = ses.query(wm.Credit).filter(wm.Credit.address == address.address).first()
        if c is not None:
            break
        else:
            time.sleep(1)
    assert c is not None
    assert c.address == address.address
    assert c.amount == amount + fee
    assert c.currency == 'BTC'
    assert c.network == 'Internal'
    assert len(c.ref_id) > 0
    # ses.close()
    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user.id).filter(wm.Balance.currency == 'BTC').first()
    assert bal.total > Amount("0 BTC")
    assert bal.available == Amount("0 BTC")
    bal.available = bal.available + c.amount
    ses.add(bal)
    try:
        ses.commit()
    except Exception as e:
        ses.rollback()
        print "skipping test"
        return
    ses.close()
    # send Internal internally to user 2
    addy = client2.get_model('Address')(currency='BTC', network='Internal')
    address = client2.address.createAddress(address=addy).result()

    debit = client.debit.sendMoney(debit={'amount': 0.01,
                                  'fee': fee.to_double(),
                                  'address': address.address,
                                  'currency': 'BTC',
                                  'network': 'Internal',
                                  'state': 'unconfirmed',
                                  'reference': 'test send money internal internal',
                                  'ref_id': ''}).result()
    assert debit.transaction_state == 'complete'
    assert debit.amount == 0.01
    assert debit.reference == 'test send money internal internal'
    assert debit.network == 'internal'

    for i in range(0, 60):
        c = ses.query(wm.Credit).filter(wm.Credit.address == address.address).first()
        if c is not None:
            break
        else:
            time.sleep(1)
    assert c is not None
    assert c.transaction_state == 'complete'
    assert c.amount == Amount("0.01 BTC")
    assert c.reference == 'test send money internal internal'
    assert c.network == 'internal'
    assert int(debit.ref_id) == c.id
    assert int(c.ref_id) == debit.id
    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user.id).filter(wm.Balance.currency == 'BTC').first()
    assert bal.total == Amount("0 BTC")
    assert bal.available == Amount("0 BTC")

    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user2.id).filter(wm.Balance.currency == 'BTC').first()
    assert bal.total == Amount("0.01 BTC")
    assert bal.available == Amount("0.01 BTC")
    ses.close()
    # send BTC internally to user 2
    addy = client2.get_model('Address')(currency='BTC', network='Internal')
    address = client2.address.createAddress(address=addy).result()

    debit = client2.debit.sendMoney(debit={'amount': 0.0099,
                                  'fee': CFG.get('internal', 'FEE'),
                                  'address': address.address,
                                  'currency': 'BTC',
                                  'network': 'Internal',
                                  'state': 'unconfirmed',
                                  'reference': 'test send money internal internal',
                                  'ref_id': ''}).result()
    assert debit.transaction_state == 'complete'
    assert debit.amount == 0.0099
    assert debit.reference == 'test send money internal internal'
    assert debit.network == 'internal'

    for i in range(0, 60):
        c = ses.query(wm.Credit).filter(wm.Credit.address == address.address).first()
        if c is not None:
            break
        else:
            time.sleep(1)
    assert c is not None
    assert c.transaction_state == 'complete'
    assert c.amount == Amount("0.0099 BTC")
    assert c.reference == 'test send money internal internal'
    assert c.network == 'internal'
    assert int(debit.ref_id) == c.id
    assert int(c.ref_id) == debit.id
    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user.id).filter(wm.Balance.currency == 'BTC').first()
    assert bal.total == Amount("0 BTC")
    assert bal.available == Amount("0 BTC")

    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user2.id).filter(wm.Balance.currency == 'BTC').first()
    assert bal.total == Amount("0.0099 BTC")
    assert bal.available == Amount("0.0099 BTC")
    ses.close()
    # Send Internal from user2
    addy = internal_address()
    debit = client2.debit.sendMoney(debit={'amount': 0.0098,
                                   'fee': CFG.get('internal', 'FEE'),
                                  'address': addy,
                                  'currency': 'BTC',
                                  'network': 'Internal',
                                  'state': 'unconfirmed',
                                  'reference': 'test send money internal',
                                  'ref_id': ''}).result()
    time.sleep(0.1)
    for i in range(0, 60):
        d = ses.query(wm.Debit).filter(wm.Debit.address == addy).first()
        if d is not None:
            break
        else:
            time.sleep(1)
    assert d is not None

    assert d.address == addy
    assert d.amount == Amount("0.0098 BTC")
    bal = ses.query(wm.Balance).filter(wm.Balance.user_id == user2.id).filter(wm.Balance.currency == 'BTC')
    assert bal.first().total == Amount("0 BTC")
    assert bal.first().available == Amount("0 BTC")