def create_or_import_account(self, name, get_key_cb, db_session=None): if type(name) not in (str, unicode) or len( name.encode('utf-8')) > ACCOUNT_NAME_LEN: raise InvalidAccountName(name) db = db_session if db_session is not None else connectionmanager.database_session( ) existing_account = db.query(Account).filter( Account.manager_id == self.manager.id, Account.user == name).first() if existing_account != None: raise AccountExistsException(name) account = Account() account.manager_id = self.manager.id account.user = name privkey, pubkeyhash = get_key_cb() account.private_key = privkey account.pubkeyhash = pubkeyhash db.add(account) db.flush() for coin in COINS: try: addresses = coin.get_addresses_for_pubkeyhash(pubkeyhash) coin_db = connectionmanager.database_session(coin) coin_daemon = connectionmanager.coindaemon(coin) for address_id in [ import_address(address, dbsession=coin_db, daemon=coin_daemon) for address in addresses ]: account_address = AccountAddress() account_address.account_id = account.id account_address.coin = coin.ticker account_address.address_id = address_id db.add(account_address) coin_db.commit() except Exception as e: print( 'Failed to import %s addresses for new account "%s": %s' % (coin.ticker, name, e)) coin_db.rollback() db.rollback() raise db.flush() db.commit() return WalletAccount(self, account)
def wrapper(*args, **kwargs): auth_header = request.headers.get('Authorization') if not auth_header: abort(401) auth_header = auth_header.split(' ') if len(auth_header) != 2 or auth_header[0] != 'Bearer': abort(401) try: token = b64decode(auth_header[1]) except TypeError: abort(401) if len(token) != AUTH_TOKEN_SIZE: abort(401) tokenhash = sha256(sha256(token).digest()).digest() dbsession = connectionmanager.database_session() manager = dbsession.query(WalletManager).filter( WalletManager.tokenhash == tokenhash).first() if manager == None: abort(401) kwargs['manager'] = manager return api_func(*args, **kwargs)
def send(manager, wallet, account, user): requestobj = SendRequest(request.get_json()) sender = account.addresses[requestobj.coin] requestobj.destination.set_context_info(wallet=wallet, coin=sender.coin) tx = sender.transaction(requestobj.destination.address, requestobj.amount, spend_unconfirmed=True, subsidized=requestobj.low_priority) txid = tx.broadcast() txid_raw = unhexlify(txid) sent = time() db = connectionmanager.database_session(coin=sender.coin) tx_internal_id = None while time() < sent + 10: db.rollback() txobj = db.query(Transaction).filter(Transaction.txid == txid_raw).first() if txobj != None: tx_internal_id = txobj.id break if tx_internal_id is None: raise APIException('Transaction created but not seen on network after 10 seconds') with QueryDataPostProcessor() as pp: return pp.process_raw({ 'error': None, 'destination': dict(requestobj.destination), 'transaction': { 'txid': txid, 'href': make_tx_ref(sender.coin, txid) } }).json()
def main(): STATE = { coin.ticker: CoinState() for coin in COINS } while True: sleep(10) try: for coin in COINS: state = STATE[coin.ticker] session = connectionmanager.database_session(coin=coin) lastblock = session.query(Block).order_by(Block.height.desc()).first() if lastblock.hash == state.lastblockhash: continue log_event('New', 'Blk', hexlify(lastblock.hash), 'chain = ' + coin.ticker) should_run = state.update(lastblock.hash) if not should_run: log_event('Ign', 'Blk', hexlify(lastblock.hash), 'too soon') continue txs_queued = len(connectionmanager.coindaemon(coin).getrawmempool()) max_work = MAX_QUEUED_TXS - txs_queued if max_work <= 0: log_event('Ign', 'Blk', hexlify(lastblock.hash), 'mempool full') continue log_event('Check', 'Chn', coin.ticker, '%d entries in mempool, max = %d' % (txs_queued, MAX_QUEUED_TXS)) run_background_tasks_for_coin(coin, session, max_work=max_work) log_event('Finish', 'Chn', coin.ticker) except KeyboardInterrupt: return
def wait_until_seen_on_network(self, timeout=10, check_interval=0.5): start_time = time() db = connectionmanager.database_session(coin=self.coin) while time() < start_time + timeout: sleep(check_interval) db.rollback() if self.is_seen_on_network(db): return raise TransactionBroadcastException( 'Transaction was broadcasted, but not seen on network after %d seconds' % timeout)
def get(cls, token, format='raw', dbsession=None): token = { 'raw': lambda x: x, 'base64': lambda x: b64decode(x), 'hex': lambda x: unhexlify(x) }[format](token) if dbsession is None: dbsession = connectionmanager.database_session() manager = dbsession.query(WalletManager).filter( WalletManager.token == token).first() if manager != None: return cls(manager)
def create_account(manager, wallet): user = get_value(request.get_json(), 'user') try: private_key = get_value(request.get_json(), 'privkey') except ValueError: private_key = None db_session = connectionmanager.database_session() if private_key is None: new_account = wallet.create_account(user, db_session=db_session) else: new_account = wallet.import_account(user, private_key, db_session=db_session) with QueryDataPostProcessor() as pp: return pp.process(new_account.model).json()
def current_coinbase_confirmation_height(self, dbsession=None): if dbsession is None: from connections import connectionmanager dbsession = connectionmanager.database_session(coin=self) return dbsession.query(Block.height).order_by(Block.height.desc()).first()[0] - 100
def _dbsession(self): return connectionmanager.database_session(coin=Coin.by_ticker(self.coin))
def __init__(self, account, coin): self.account = account self.coin = coin self.db = connectionmanager.database_session(coin=self.coin) self._addresses = None