Пример #1
0
 def test_post_sequentially(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": "test_debit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "credit",
         "note": "test_credit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     d1 = self.export.post(post1)
     return self.export.post(post2)
Пример #2
0
 def test_post_results_agree(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": "debit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "credit",
         "note": "credit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     d1 = self.export.post(post1)
     d2 = self.export.post(post2)
     return self.assertEqual(self.successResultOf(d1), self.successResultOf(d2))
Пример #3
0
 def test_quantity_mismatch(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": "debit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 1,
         "direction": "credit",
         "note": "credit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
     }
     d1 = self.export.post(post1)
     d1.addErrback(lambda x: None)
     d2 = self.assertFailure(self.export.post(post2), LedgerException)
     self.flushLoggedErrors()
     return self.assertEqual(self.successResultOf(d2), ledger.QUANTITY_MISMATCH)
Пример #4
0
 def test_post_results_agree(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": 'debit',
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "credit",
         "note": "credit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     d1 = self.export.post(post1)
     d2 = self.export.post(post2)
     return self.assertEqual(self.successResultOf(d1),
                             self.successResultOf(d2))
Пример #5
0
 def test_post_sequentially(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": "test_debit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "credit",
         "note": "test_credit",
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     d1 = self.export.post(post1)
     return self.export.post(post2)
Пример #6
0
 def test_quantity_mismatch(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": 'debit',
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 1,
         "direction": "credit",
         "note": 'credit',
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     d1 = self.export.post(post1)
     d1.addErrback(lambda x: None)
     d2 = self.assertFailure(self.export.post(post2), LedgerException)
     self.flushLoggedErrors()
     return self.assertEqual(self.successResultOf(d2),
                             ledger.QUANTITY_MISMATCH)
Пример #7
0
    def load_contract(self, ticker):
        res = yield self.dbpool.runQuery("SELECT ticker, description, denominator, contract_type, full_description,"
                                         "tick_size, lot_size, margin_high, margin_low,"
                                         "denominated_contract_ticker, payout_contract_ticker, expiration "
                                         "FROM contracts WHERE ticker = %s", (ticker,))
        if len(res) < 1:
            raise PostgresException("No such contract: %s" % ticker)
        if len(res) > 1:
            raise PostgresException("Contract %s not unique" % ticker)
        r = res[0]
        contract = {"contract": r[0],
                    "description": r[1],
                    "denominator": r[2],
                    "contract_type": r[3],
                    "full_description": markdown.markdown(r[4].decode('utf-8'), extensions=["markdown.extensions.extra",
                                                                            "markdown.extensions.sane_lists",
                                                                            "markdown.extensions.nl2br"
                    ]),
                    "tick_size": r[5],
                    "lot_size": r[6],
                    "denominated_contract_ticker": r[9],
                    "payout_contract_ticker": r[10]}

        if contract['contract_type'] == 'futures':
            contract['margin_high'] = r[7]
            contract['margin_low'] = r[8]

        if contract['contract_type'] in ['futures', 'prediction']:
            contract['expiration'] = util.dt_to_timestamp(r[11])

        returnValue(contract)
Пример #8
0
 def authenticateWithAuthCode(self, code):
     self._log_call("authenticateWithAuthCode", code)
     expiry = datetime.utcnow() + timedelta(days=1)
     from sputnik import util
     return defer.succeed({
         'access_token': 'TOKEN',
         'expires_at': util.dt_to_timestamp(expiry) / 1e6
     })
Пример #9
0
    def get_transaction_history(self, start_timestamp=None, end_timestamp=None, username=None):

        """

        :param from_timestamp:
        :param to_timestamp:
        :returns: Deferred
        """

        if start_timestamp is None:
            start_timestamp = util.dt_to_timestamp(datetime.datetime.utcnow() -
                                                             datetime.timedelta(days=30))

        if end_timestamp is None:
            end_timestamp = util.dt_to_timestamp(datetime.datetime.utcnow())


        history = yield self.db.get_transaction_history(start_timestamp, end_timestamp, username)
        returnValue(history)
Пример #10
0
    def get_open_orders(self, username):

        results = yield self.dbpool.runQuery(
            'SELECT contracts.ticker, orders.price, orders.quantity, orders.quantity_left, '
            'orders.timestamp, orders.side, orders.id FROM orders, contracts '
            'WHERE orders.contract_id=contracts.id AND orders.username=%s '
            'AND orders.quantity_left > 0 '
            'AND orders.accepted=TRUE AND orders.is_cancelled=FALSE', (username,))
        returnValue({r[6]: {'contract': r[0], 'price': r[1], 'quantity': r[2], 'quantity_left': r[3],
                            'timestamp': util.dt_to_timestamp(r[4]), 'side': r[5], 'id': r[6], 'is_cancelled': False}
                     for r in results})
Пример #11
0
    def get_trade_history(self, contract, start_timestamp=None, end_timestamp=None):
        if contract not in self.markets:
            raise WebserverException("exceptions/webserver/no-such-ticker", contract)

        now = util.dt_to_timestamp(datetime.utcnow())
        start = start_timestamp or int(now - 3.6e9) # delta 1 hour
        end = end_timestamp or now
        
        history = yield succeed([entry for entry in self.trade_history.get(contract, []) \
                if start <= entry["timestamp"] <= end])
        returnValue(history)
Пример #12
0
    def get_transaction_history(self,
                                start_timestamp=None,
                                end_timestamp=None,
                                username=None):
        """

        :param from_timestamp:
        :param to_timestamp:
        :returns: Deferred
        """

        if start_timestamp is None:
            start_timestamp = util.dt_to_timestamp(datetime.datetime.utcnow() -
                                                   datetime.timedelta(days=30))

        if end_timestamp is None:
            end_timestamp = util.dt_to_timestamp(datetime.datetime.utcnow())

        history = yield self.db.get_transaction_history(
            start_timestamp, end_timestamp, username)
        returnValue(history)
Пример #13
0
    def place_order(self, order, username=None):
        order["timestamp"] = util.dt_to_timestamp(datetime.datetime.utcnow())
        order['username'] = username

        # Check for zero price or quantity
        if order["price"] == 0 or order["quantity"] == 0:
            raise WebserverException("exceptions/webserver/invalid_price_quantity")

        # check tick size and lot size in the accountant, not here

        result = yield self.accountant.proxy.place_order(username, order)
        returnValue(result)
Пример #14
0
    def get_trade_history(self, contract, start_timestamp=None, end_timestamp=None):
        if contract not in self.markets:
            raise WebserverException("exceptions/webserver/no-such-ticker", contract)

        now = util.dt_to_timestamp(datetime.utcnow())
        start = start_timestamp or int(now - 3.6e9)  # delta 1 hour
        end = end_timestamp or now

        history = yield succeed(
            [entry for entry in self.trade_history.get(contract, []) if start <= entry["timestamp"] <= end]
        )
        returnValue(history)
Пример #15
0
    def test_database_commit(self):
        post1 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "debit",
            "note": "debit",
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
        }
        post2 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "credit",
            "note": "credit",
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
        }
        d = self.export.post(post1, post2)

        def dbtest(arg):
            postings = self.session.query(models.Posting).all()
            self.assertEqual(len(postings), 2)
            journals = self.session.query(models.Journal).all()
            self.assertEqual(len(journals), 1)
            p1 = postings[0]
            p2 = postings[1]
            journal = journals[0]
            self.assertEqual(p1.journal_id, journal.id)
            self.assertEqual(p2.journal_id, journal.id)
            self.assertEqual(abs(p1.quantity), 5)
            self.assertEqual(p1.quantity + p2.quantity, 0)

        return d.addCallback(dbtest)
Пример #16
0
    def test_database_commit(self):
        post1 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "debit",
            "note": "debit",
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
        }
        post2 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "credit",
            "note": "credit",
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
        }
        d = self.export.post(post1, post2)

        def dbtest(arg):
            postings = self.session.query(models.Posting).all()
            self.assertEqual(len(postings), 2)
            journals = self.session.query(models.Journal).all()
            self.assertEqual(len(journals), 1)
            p1 = postings[0]
            p2 = postings[1]
            journal = journals[0]
            self.assertEqual(p1.journal_id, journal.id)
            self.assertEqual(p2.journal_id, journal.id)
            self.assertEqual(abs(p1.quantity), 5)
            self.assertEqual(p1.quantity + p2.quantity, 0)

        return d.addCallback(dbtest)
Пример #17
0
    def place_order(self, order, username=None):
        order["timestamp"] = util.dt_to_timestamp(datetime.datetime.utcnow())
        order['username'] = username

        # Check for zero price or quantity
        if order["price"] == 0 or order["quantity"] == 0:
            raise WebserverException(
                "exceptions/webserver/invalid_price_quantity")

        # check tick size and lot size in the accountant, not here

        result = yield self.accountant.proxy.place_order(username, order)
        returnValue(result)
Пример #18
0
 def test_post_simultaneously(self):
     post1 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "debit",
         "note": 'debit',
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     post2 = {
         "uid": "foo",
         "count": 2,
         "type": "Trade",
         "username": "******",
         "contract": "MXN",
         "quantity": 5,
         "direction": "credit",
         "note": 'credit',
         "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
     }
     return self.export.post(post1, post2)
Пример #19
0
    def get_ohlcv_history(self, contract, period=None, start_timestamp=None,
            end_timestamp=None):
        if contract not in self.markets:
            raise WebserverException("exceptions/webserver/no-such-ticker", contract)

        now = util.dt_to_timestamp(datetime.utcnow())
        start = start_timestamp or int(now - 5.184e12) # delta 60 days
        end = end_timestamp or now
        period = period or "day"
       
        data = self.ohlcv_history.get(contract, {}).get(period, {})
        ohlcv = yield succeed({key: value for key, value in data.iteritems() \
                if value["open_timestamp"] <= end and \
                start <= value["close_timestamp"]})

        returnValue(ohlcv)
Пример #20
0
    def get_trade_history(self, ticker):
        to_dt = datetime.datetime.utcnow()
        from_dt = to_dt - datetime.timedelta(days=60)
        start_dt_for_period = {
            'minute': to_dt - datetime.timedelta(minutes=60),
            'hour': to_dt - datetime.timedelta(hours=60),
            'day': to_dt - datetime.timedelta(days=60)
        }
        results = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, trades.timestamp, trades.price, trades.quantity FROM trades, contracts WHERE "
            "trades.contract_id=contracts.id AND contracts.ticker=%s AND trades.timestamp >= %s AND trades.posted IS TRUE",
            (ticker, from_dt))

        trades = [{'contract': r[0], 'price': r[2], 'quantity': r[3],
                   'timestamp': util.dt_to_timestamp(r[1])} for r in results]
        returnValue(trades)
Пример #21
0
    def get_new_api_credentials(self,
                                expiration=None,
                                totp=None,
                                username=None):
        if expiration is None:
            now = datetime.utcnow()
            expiration = util.dt_to_timestamp(now + timedelta(days=7))

        # Check totp
        totp_result = yield self.administrator.proxy.check_totp(username, totp)

        if totp_result:
            r = yield self.administrator.proxy.get_new_api_credentials(
                username, expiration)
            returnValue(r)
        else:
            raise WebserverException("exceptions/webserver/invalid_otp")
Пример #22
0
    def load_contract(self, ticker):
        res = yield self.dbpool.runQuery(
            "SELECT ticker, description, denominator, contract_type, full_description,"
            "tick_size, lot_size, margin_high, margin_low,"
            "denominated_contract_ticker, payout_contract_ticker, expiration "
            "FROM contracts WHERE ticker = %s", (ticker, ))
        if len(res) < 1:
            raise PostgresException("No such contract: %s" % ticker)
        if len(res) > 1:
            raise PostgresException("Contract %s not unique" % ticker)
        r = res[0]
        contract = {
            "contract":
            r[0],
            "description":
            r[1],
            "denominator":
            r[2],
            "contract_type":
            r[3],
            "full_description":
            markdown.markdown(r[4].decode('utf-8'),
                              extensions=[
                                  "markdown.extensions.extra",
                                  "markdown.extensions.sane_lists",
                                  "markdown.extensions.nl2br"
                              ]),
            "tick_size":
            r[5],
            "lot_size":
            r[6],
            "denominated_contract_ticker":
            r[9],
            "payout_contract_ticker":
            r[10]
        }

        if contract['contract_type'] == 'futures':
            contract['margin_high'] = r[7]
            contract['margin_low'] = r[8]

        if contract['contract_type'] in ['futures', 'prediction']:
            contract['expiration'] = util.dt_to_timestamp(r[11])

        returnValue(contract)
Пример #23
0
    def test_timeout(self):
        post1 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "debit",
            "note": 'debit',
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow())
        }
        d1 = self.assertFailure(self.export.post(post1), LedgerException)
        group = self.ledger.pending["foo"]
        group.callLater = self.clock.callLater
        group.setTimeout(1)
        self.clock.advance(2)

        return self.assertEqual(self.successResultOf(d1), ledger.GROUP_TIMEOUT)
Пример #24
0
    def get_ohlcv_history(self, contract, period=None, start_timestamp=None, end_timestamp=None):
        if contract not in self.markets:
            raise WebserverException("exceptions/webserver/no-such-ticker", contract)

        now = util.dt_to_timestamp(datetime.utcnow())
        start = start_timestamp or int(now - 5.184e12)  # delta 60 days
        end = end_timestamp or now
        period = period or "day"

        data = self.ohlcv_history.get(contract, {}).get(period, {})
        ohlcv = yield succeed(
            {
                key: value
                for key, value in data.iteritems()
                if value["open_timestamp"] <= end and start <= value["close_timestamp"]
            }
        )

        returnValue(ohlcv)
Пример #25
0
    def test_timeout(self):
        post1 = {
            "uid": "foo",
            "count": 2,
            "type": "Trade",
            "username": "******",
            "contract": "MXN",
            "quantity": 5,
            "direction": "debit",
            "note": "debit",
            "timestamp": util.dt_to_timestamp(datetime.datetime.utcnow()),
        }
        d1 = self.assertFailure(self.export.post(post1), LedgerException)
        group = self.ledger.pending["foo"]
        group.callLater = self.clock.callLater
        group.setTimeout(1)
        self.clock.advance(2)

        return self.assertEqual(self.successResultOf(d1), ledger.GROUP_TIMEOUT)
Пример #26
0
    def get_trade_history(self, ticker):
        to_dt = datetime.datetime.utcnow()
        from_dt = to_dt - datetime.timedelta(days=60)
        start_dt_for_period = {
            'minute': to_dt - datetime.timedelta(minutes=60),
            'hour': to_dt - datetime.timedelta(hours=60),
            'day': to_dt - datetime.timedelta(days=60)
        }
        results = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, trades.timestamp, trades.price, trades.quantity FROM trades, contracts WHERE "
            "trades.contract_id=contracts.id AND contracts.ticker=%s AND trades.timestamp >= %s AND trades.posted IS TRUE",
            (ticker, from_dt))

        trades = [{
            'contract': r[0],
            'price': r[2],
            'quantity': r[3],
            'timestamp': util.dt_to_timestamp(r[1])
        } for r in results]
        returnValue(trades)
Пример #27
0
    def get_transaction_history(self, from_timestamp, to_timestamp, username):
        result = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, SUM(posting.quantity) FROM posting, journal, contracts "
            "WHERE posting.journal_id=journal.id AND posting.username=%s AND journal.timestamp<%s "
            "AND posting.contract_id=contracts.id GROUP BY contracts.ticker",
            (username, util.timestamp_to_dt(from_timestamp)))

        balances = collections.defaultdict(int)
        for row in result:
            balances[row[0]] = int(row[1])

        result = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, journal.timestamp, posting.quantity, journal.type, posting.note "
            "FROM posting, journal, contracts WHERE posting.journal_id=journal.id AND "
            "posting.username=%s AND journal.timestamp>=%s AND journal.timestamp<=%s "
            "AND posting.contract_id=contracts.id ORDER BY journal.timestamp",
            (username, util.timestamp_to_dt(from_timestamp),
             util.timestamp_to_dt(to_timestamp)))

        transactions = []
        for row in result:
            balances[row[0]] += row[2]
            quantity = abs(row[2])

            # Here we assume that the user is a Liability user
            if row[2] < 0:
                direction = 'debit'
            else:
                direction = 'credit'

            transactions.append({
                'contract': row[0],
                'timestamp': util.dt_to_timestamp(row[1]),
                'quantity': quantity,
                'type': row[3],
                'direction': direction,
                'balance': balances[row[0]],
                'note': row[4]
            })

        returnValue(transactions)
Пример #28
0
    def get_open_orders(self, username):

        results = yield self.dbpool.runQuery(
            'SELECT contracts.ticker, orders.price, orders.quantity, orders.quantity_left, '
            'orders.timestamp, orders.side, orders.id FROM orders, contracts '
            'WHERE orders.contract_id=contracts.id AND orders.username=%s '
            'AND orders.quantity_left > 0 '
            'AND orders.accepted=TRUE AND orders.is_cancelled=FALSE',
            (username, ))
        returnValue({
            r[6]: {
                'contract': r[0],
                'price': r[1],
                'quantity': r[2],
                'quantity_left': r[3],
                'timestamp': util.dt_to_timestamp(r[4]),
                'side': r[5],
                'id': r[6],
                'is_cancelled': False
            }
            for r in results
        })
Пример #29
0
    def get_transaction_history(self, from_timestamp, to_timestamp, username):
        result = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, SUM(posting.quantity) FROM posting, journal, contracts "
            "WHERE posting.journal_id=journal.id AND posting.username=%s AND journal.timestamp<%s "
            "AND posting.contract_id=contracts.id GROUP BY contracts.ticker",
            (username, util.timestamp_to_dt(from_timestamp)))

        balances = collections.defaultdict(int)
        for row in result:
            balances[row[0]] = int(row[1])

        result = yield self.dbpool.runQuery(
            "SELECT contracts.ticker, journal.timestamp, posting.quantity, journal.type, posting.note "
            "FROM posting, journal, contracts WHERE posting.journal_id=journal.id AND "
            "posting.username=%s AND journal.timestamp>=%s AND journal.timestamp<=%s "
            "AND posting.contract_id=contracts.id ORDER BY journal.timestamp",
            (username, util.timestamp_to_dt(from_timestamp), util.timestamp_to_dt(to_timestamp)))

        transactions = []
        for row in result:
            balances[row[0]] += row[2]
            quantity = abs(row[2])

            # Here we assume that the user is a Liability user
            if row[2] < 0:
                direction = 'debit'
            else:
                direction = 'credit'

            transactions.append({'contract': row[0],
                                 'timestamp': util.dt_to_timestamp(row[1]),
                                 'quantity': quantity,
                                 'type': row[3],
                                 'direction': direction,
                                 'balance': balances[row[0]],
                                 'note': row[4]})

        returnValue(transactions)
Пример #30
0
 def authenticateWithAuthCode(self, code):
     self._log_call("authenticateWithAuthCode", code)
     expiry = datetime.utcnow() + timedelta(days=1)
     from sputnik import util
     return defer.succeed({'access_token': 'TOKEN',
                           'expires_at': util.dt_to_timestamp(expiry)/1e6})