def post_market_data(context: telegram.ext.CallbackContext): # connect to database log().info('post market data job started') total_users = 0 tickers = [] user_id = 0 db = DBEngine() row = db.custom_command('SELECT DISTINCT id FROM watchlist') # for each id for r in row: s = 'Here is your watchlist update for today:\n\n' user_id = r[0] rowx = db.custom_command('SELECT ticker FROM watchlist WHERE id=' + str(user_id)) # for each ticker that belongs to the user for x in rowx: tickers.append(x[0]) # print(tickers) for ticker in tickers: share = Share(ticker) s += '<b>' + share.name + ' (' + share.ticker + ')</b>\nOpen: ' + str(share.open) + \ '\nLow: ' + str(share.low) + '\nHigh: ' + str(share.high) + \ '\nClose: ' + str(share.price) + '\nPrev Close: ' + \ str(share.previous_close) + '\n50MA: ' + str(share.fifty_day_ma) + \ '\nVolume: ' + str(share.volume)+'\n\n' try: context.bot.send_message(chat_id=user_id, text=s, parse_mode='HTML') total_users += 1 tickers.clear() time.sleep(1) except TelegramError: tickers.clear() continue log().info('market data sent to ' + str(total_users) + ' users')
def __init__(self): self.config = BotConfig(dev=False) log().info('kubera version' + self.config.version + ' started') # db engine DBEngine() # loaded from config self.token = self.config.token # telegram api self.updater = Updater(self.token, use_context=True) # job queue self.job_queue = self.updater.job_queue # Get the dispatcher to register handlers self.dp = self.updater.dispatcher # error handling self.dp.add_error_handler(self.error) # controllers MainMenu(self.dp) DividendSummary(self.dp) UpdateWatchlist(self.dp) About(self.dp) # jobs # 5:15 PM singapore time (after market close) self.job_queue.run_daily(post_market_data, datetime.time(hour=9, minute=15), (0, 1, 2, 3, 4)) # start bot self.updater.start_polling() self.updater.idle()
def __remove_share_final(self, update, context): tickers = {} user = update.effective_user query = update.callback_query query.answer() # print(query.data) DBEngine().delete_item('watchlist', 'ticker', query.data) result = DBEngine().custom_command("SELECT ticker FROM watchlist WHERE id=" + str(user.id)) for result in result: my_share = Share(result[0]) tickers[my_share.ticker] = my_share.name s = "" for key, value in tickers.items(): s += value + " (" + key + ")" + "\n" update.callback_query.message.edit_text("Your watchlist has been updated.\n\n<b>Current watchlist:</b>\n" + s, parse_mode='HTML') return ConversationHandler.END
def main(): db = DBEngine('test.sqlite') # # setup table # db.setup() # # add single item to database # db.add_item('watchlist', ['id', 'ticker'], ['1234', 'v03']) # db.add_item('watchlist', ['id', 'ticker'], ['1234', 'u11']) # db.add_item('watchlist', ['id', 'ticker'], ['1234', 'c6l']) row = db.custom_command('SELECT DISTINCT id FROM watchlist ') # for each id for r in row: print(r[0]) rowx = db.custom_command('SELECT ticker FROM watchlist WHERE id=' + str(r[0])) # for each ticker that belongs to the user for x in rowx: print(x[0])
def __remove_share(self, update, context): query = update.callback_query query.answer() keyboard = [] user = update.effective_user result = DBEngine().custom_command("SELECT ticker FROM watchlist WHERE id=" + str(user.id)) for result in result: my_share = Share(result[0]) keyboard.append([InlineKeyboardButton(my_share.name + " (" + my_share.ticker + ")", callback_data=my_share.ticker)]) reply_markup = InlineKeyboardMarkup(keyboard) update.callback_query.message.edit_text("What would you like to remove?", reply_markup=reply_markup, parse_mode='HTML') return REMOVESHARE
def __add_share_final(self, update, context): tickers = {} user = update.effective_user # print(user.id) ticker = update.message.text share = Share(ticker) count = DBEngine().count("SELECT COUNT (*) FROM watchlist WHERE id=" + str(user.id)) result = DBEngine().custom_command("SELECT ticker FROM watchlist WHERE id=" + str(user.id)) # check for valid ticker if not share.is_valid: update.message.reply_text("Invalid ticker. Please use /start to go back to the main menu") return ConversationHandler.END # check if the user has hit watchlist limit if count >= 3: update.message.reply_text("You have reached your watchlist limit") return ConversationHandler.END # create dictionary of existing watchlist for result in result: my_share = Share(result[0]) tickers[my_share.ticker] = my_share.name # add the incoming entry before = len(tickers) tickers[share.ticker] = share.name after = len(tickers) if before == after: update.message.reply_text("This stock is already on your watchlist") return ConversationHandler.END DBEngine().add_item('watchlist', ['id', 'ticker'], [user.id, share.ticker]) s = "" for key, value in tickers.items(): s += value + " (" + key + ")" + "\n" update.message.reply_text("Your watchlist has been updated.\n\n<b>Current watchlist:</b>\n" + s, parse_mode='HTML') return ConversationHandler.END
def __yes(self, update, context): # send to users for user in DBEngine().get_items('users', 'id'): try: context.bot.send_message(chat_id=user[0], text=self.__message, parse_mode='HTML') log().info('Message has been sent to %s', user[0]) time.sleep(1) except TelegramError as e: log().warning(e) log().warning('User %s has blocked the bot', user[0]) # DBEngine().delete_item('users', 'id', user[0]) # log().info('User %s has been removed from the database', user[0]) continue # send message update.message.reply_text('Update sent to all users') return ConversationHandler.END
def __show_menu(self, update, context): tickers = {} first_name = update.effective_user.first_name user_id = update.effective_user.id s = "Hi " + first_name + ", what would you like to do?\n\n<b>Your watchlist:</b>\n" result = DBEngine().custom_command( "SELECT ticker FROM watchlist WHERE id=" + str(user_id)) for result in result: my_share = Share(result[0]) tickers[my_share.ticker] = my_share.name for key, value in tickers.items(): s += value + " (" + key + ")" + "\n" if len(tickers) == 0: s += "Empty! Update your watchlist to receive automatic alerts about your favourite stocks." keyboard = [ [ InlineKeyboardButton("Update my watchlist", callback_data=str(states.UPDATEWATCHLIST)) ], [ InlineKeyboardButton("Dividend history", callback_data=str(states.DIVIDENDINFO)) ], # [InlineKeyboardButton("Bot settings", # callback_data=str(states.SETTINGS))], [ InlineKeyboardButton("About this bot", callback_data=str(states.ABOUT)) ] # [InlineKeyboardButton("Cancel", # callback_data=str(states.MENUCANCEL))] ] reply_markup = InlineKeyboardMarkup(keyboard) # Send message with text and appended InlineKeyboard update.message.reply_text(s, reply_markup=reply_markup, parse_mode='HTML')
def post_market_analysis(context: telegram.ext.CallbackContext): # connect to database db = DBEngine() # fetch tickers tickers = db.get_items('stocks', 'ticker') # update values for ticker in tickers: share = Share(ticker[0]) # ignore tickers with missing volume information if share.volume == 'unavailable': continue # add volume to database db.update_item('stocks', 'volume', share.volume, 'ticker', ticker[0]) # add company name to database db.update_item('stocks', 'name', share.name, 'ticker', ticker[0]) # add change % to database db.update_item('stocks', 'change', share.change, 'ticker', ticker[0]) time.sleep(1) # get top 5 results from database sorted volume = db.custom_command('select name, volume from stocks order by volume desc limit 5') gainers = db.custom_command('select name, change from stocks order by change desc limit 5') losers = db.custom_command('select name, change from stocks order by change asc limit 5') # STI change sti_change_raw = Share('^STI').percent_changed # append '%' sti_change = str(sti_change_raw) + '%' # prepend '+' if the value is positive if sti_change_raw > 0: sti_change = '+' + sti_change # create string s = '<b>Market Statistics (' + datetime.today().strftime('%d %B %Y') + ')</b>\n\n' s += '<b>STI overall change: </b>' + sti_change + '\n\n' s += '<b>Highest volumes:</b>\n' for idx, row in enumerate(volume): s += '‣ ' + row[0] + ' [' + str(millify(row[1])) + ']\n' s += '\n' s += '<b>Top gainers:</b>\n' for idx, row in enumerate(gainers): s += '‣ ' + row[0] + ' [+' + str(row[1]) + ']' + '\n' s += '\n' s += '<b>Top losers:</b>\n' for idx, row in enumerate(losers): s += '‣ ' + row[0] + ' [' + str(row[1]) + ']' + '\n' total_users = 0 # send message to all users for user in DBEngine().get_items('users', 'id'): try: context.bot.send_message(chat_id=user[0], text=s, parse_mode='HTML') total_users += 1 time.sleep(1) except TelegramError: DBEngine().delete_item('users', 'id', user[0]) continue log().info('market statistics sent to ' + str(total_users) + ' users')