def get_db_session(): """Dependency that create database session with pool of connections""" session = Session() try: yield session finally: session.close()
def sell_position(user_id: str, username: str, symbol: str, amount: int, price: float): # TODO: maybe add cash attr for users session = Session() sold_price, currency = Stock(symbol).get_live() if currency not in ["USD", "CAD"]: raise NotAmerican sold_price = price if price else sold_price try: symbol = get_symbol_or_create(session, symbol) symbol_id = symbol[0].symbol_id user = get_user_or_create(session, user_id=user_id, username=username) user_id = user[0].id existing = get_existing_position( session=session, user_id=user_id, symbol_id=symbol_id ) if existing: ex_total, ex_amount = existing.total_price, existing.amount if ex_amount < amount: raise NotEnoughPositionsToSell elif ex_amount == amount: session.delete(existing) return sold_price, currency new_amount = ex_amount - amount existing.total_price = ex_total - sold_price * new_amount existing.amount = new_amount return sold_price, currency else: raise NotEnoughPositionsToSell finally: session.commit() session.close()
def db(prepare_db): from src.database import Session session = Session() session.begin_nested() try: yield session finally: session.rollback() session.close()
def login_user(login, password, ip, user_agent): pass_hash = hash_password(login, password) current_user = User.query.filter_by(login=login, pass_hash=pass_hash).first() if not current_user: raise ValueError("No such user") current_session = Session.query.filter_by(user=current_user, user_agent=user_agent, ip=ip).first() if current_session: return current_session.id, current_session.token new_session = Session(user=current_user, user_agent=user_agent, ip=ip) db.session.add(new_session) db.session.commit() return new_session.id, new_session.token
async def portfolio(ctx, mobile=""): if mobile and mobile not in ("m", "mobile"): raise discord.ext.commands.BadArgument session = Session() user_id = ctx.author.id username = ctx.author.name mobile = bool(mobile) portfolio_complete = get_portfolio(session=session, user_id=user_id, username=username, mobile=mobile) if portfolio_complete and mobile: await ctx.send(embed=portfolio_complete[0]) await ctx.send(embed=portfolio_complete[1]) else: await ctx.send(f"""```{portfolio_complete[0]}```""") await ctx.send(f"""```{portfolio_complete[1]}```""") if not portfolio_complete: await ctx.send(Embedder.error(""))
def buy_position(user_id: str, username: str, symbol: str, amount: int, price: float): session = Session() bought_price, currency = Stock(ticker=symbol).get_live() if currency not in ["USD", "CAD"]: raise NotAmerican bought_price = price if price else bought_price try: symbol = get_symbol_or_create(session, symbol) symbol_id = symbol[0].symbol_id user = get_user_or_create(session, user_id=user_id, username=username) user_id = user[0].id ex_total, ex_amount = 0, 0 existing = get_existing_position( session=session, user_id=user_id, symbol_id=symbol_id ) if existing: ex_total, ex_amount = existing.total_price, existing.amount new_total_price = float(ex_total + bought_price * amount) new_amount = ex_amount + amount new_average_price = new_total_price / new_amount if existing: existing.total_price = new_total_price existing.amount = new_amount existing.average_price = new_average_price else: position_row = db.Positions( user_id=user_id, symbol_id=symbol_id, total_price=new_total_price, average_price=new_average_price, amount=new_amount, ) session.add(position_row) return bought_price, currency finally: session.commit() session.close()
async def sell(ctx, ticker: str, amount: int, price: float = None): session = Session() ticker_price, total, currency = calculate_total(ticker=ticker, amount=amount, price=price) ticker = ticker.upper() user_id = str(ctx.message.author.id) username = ctx.message.author.name sell_complete = sell_position(session=session, user_id=user_id, username=username, symbol=ticker, amount=amount, price=ticker_price) if sell_complete: embed = Embedder.embed( title=f"Successfully Sold ${ticker}", message=f"{ticker} x {amount} @{ticker_price} {currency}\n" f"`Total: ${'{:.2f}'.format(total)} {currency}`") else: embed = Embedder.error("Check if you have enough positions to sell!") await ctx.send(embed=embed)
async def buy(ctx, ticker: str, amount: int, price: float = None): session = Session() ticker_price, total, currency = calculate_total(ticker=ticker, amount=amount, price=price) ticker = ticker.upper() is_usd = True if currency == "USD" else False user_id = str(ctx.message.author.id) username = ctx.message.author.name buy_complete = buy_position(session=session, user_id=user_id, username=username, symbol=ticker, amount=amount, price=ticker_price, is_usd=is_usd) if buy_complete: embed = Embedder.embed( title=f"Successfully bought ${ticker}", message=f"{ticker} x {amount} @{ticker_price} {currency}\n" f"`Total: ${'{:.2f}'.format(total)} {currency}`") else: embed = Embedder.error("Something went wrong.") await ctx.send(embed=embed)
import alembic.config print() print("Running Alembic migrations...") print() alembic_args = ["--raiseerr", "upgrade", "head"] alembic.config.main(argv=alembic_args) print() print("Migrations finished successfully!") print() from src.models import SimpleModel print("Loaded model: SimpleModel") from src.database import Session db = Session() print('Loaded session. It is accessible as "db" variable.')
def get_portfolio(user_id: str, username: str, mobile: bool): session = Session() try: user = get_user_or_create(session=session, user_id=user_id, username=username) user_id = user[0].id positions = session.query(db.Positions).filter_by(user_id=user_id).all() if not positions: raise NoPositionsException pf_list = ( list() if not mobile else discord.Embed( title=f"{username}'s Portfolio", colour=discord.Colour.green() ) ) currency_wallet = CurrencyWallet() pos_group = Group() pos_dict = dict() for item in positions: symbol = ( session.query(db.Symbols) .filter_by(symbol_id=item.symbol_id) .one() .symbol ) pos_group.add_ticker(symbol) pos_dict[symbol] = dict( book_value=item.total_price, average=item.average_price, amount=item.amount, ) handle_positions( pos_group=pos_group, pos_dict=pos_dict, currency_wallet=currency_wallet, format_type=pf_list, ) if mobile: portfolio_table = pf_list else: headers = [ "Symbol", "Amount", "Average Price", "Live Price", "Book Value", "Current Total", "P/L (%)", "Currency", ] pf_len = len(pf_list) if pf_len > 10: chunking = pf_len // 10 if pf_len % 10: chunking += 1 else: chunking = 1 portfolio_table = [] for _ in range(chunking): chunk = pf_list[:10] portfolio_table.append( tabulate( chunk, headers=headers, disable_numparse=True, ) ) del pf_list[:10] wallet_summary = currency_wallet.summary() if mobile: summary = discord.Embed( title=f"{username}'s Portfolio Summary", colour=discord.Colour.green() ) summary_handler(wallet_summary, summary) else: summary = [] summary_handler(wallet_summary, summary) summary = tabulate( summary, headers=["Currency", "Book Value", "Current Total", "P/L(%)"], stralign="left", disable_numparse=True, ) return portfolio_table, summary finally: session.close()
async def parse(url, current_depth=1, max_depth=4, from_page_id=None): """ Recursive function for saving links """ if current_depth <= max_depth: links = await _get_links_from_url(url) logging.debug("deep: {}, links: {}, url: {}".format( current_depth, len(links), url)) session = Session() if from_page_id is None: from_page = Pages(URL=url, request_depth=current_depth) session.add(from_page) session.flush() from_page_id = from_page.id session.commit() tasks = [] for link in links: # save url to page table to_page = Pages(URL=link, request_depth=current_depth) session.add(to_page) session.flush() # save dependencies values session.add( Dependencies(from_page_id=from_page_id, link_id=to_page.id)) session.flush() # generate new async tasks task = asyncio.create_task( parse(link, max_depth=max_depth, current_depth=current_depth + 1, from_page_id=to_page.id)) tasks.append(task) session.commit() session.close() return await asyncio.gather(*tasks)