mirror of
https://gitlab.com/simple-stock-bots/simple-telegram-stock-bot.git
synced 2025-06-16 15:06:53 +00:00
added stat command
This commit is contained in:
parent
e603c5345a
commit
6cfbbeb992
25
bot.py
25
bot.py
@ -48,7 +48,7 @@ def help(update, context):
|
|||||||
|
|
||||||
def symbol_detect(update, context):
|
def symbol_detect(update, context):
|
||||||
"""
|
"""
|
||||||
Runs on any message that doesn't have a command and searches for symbols, then returns the prices of any symbols found.
|
Runs on any message that doesn't have a command and searches for symbols, then returns the prices of any symbols found.
|
||||||
"""
|
"""
|
||||||
message = update.message.text
|
message = update.message.text
|
||||||
chat_id = update.message.chat_id
|
chat_id = update.message.chat_id
|
||||||
@ -165,10 +165,29 @@ def intra(update, context):
|
|||||||
buf.seek(0)
|
buf.seek(0)
|
||||||
|
|
||||||
update.message.reply_photo(
|
update.message.reply_photo(
|
||||||
photo=buf, caption=f"", parse_mode=telegram.ParseMode.MARKDOWN,
|
photo=buf,
|
||||||
|
caption=f"",
|
||||||
|
parse_mode=telegram.ParseMode.MARKDOWN,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def stat(update, context):
|
||||||
|
"""
|
||||||
|
https://iexcloud.io/docs/api/#key-stats
|
||||||
|
"""
|
||||||
|
message = update.message.text
|
||||||
|
chat_id = update.message.chat_id
|
||||||
|
symbols = s.find_symbols(message)
|
||||||
|
|
||||||
|
if symbols:
|
||||||
|
context.bot.send_chat_action(chat_id=chat_id, action=telegram.ChatAction.TYPING)
|
||||||
|
|
||||||
|
for reply in s.stat_reply(symbols).items():
|
||||||
|
update.message.reply_text(
|
||||||
|
text=reply[1], parse_mode=telegram.ParseMode.MARKDOWN
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
def inline_query(update, context):
|
def inline_query(update, context):
|
||||||
"""
|
"""
|
||||||
Handles inline query.
|
Handles inline query.
|
||||||
@ -232,6 +251,8 @@ def main():
|
|||||||
dp.add_handler(CommandHandler("div", dividend))
|
dp.add_handler(CommandHandler("div", dividend))
|
||||||
dp.add_handler(CommandHandler("news", news))
|
dp.add_handler(CommandHandler("news", news))
|
||||||
dp.add_handler(CommandHandler("info", info))
|
dp.add_handler(CommandHandler("info", info))
|
||||||
|
dp.add_handler(CommandHandler("stat", stat))
|
||||||
|
dp.add_handler(CommandHandler("stats", stat))
|
||||||
dp.add_handler(CommandHandler("search", search))
|
dp.add_handler(CommandHandler("search", search))
|
||||||
dp.add_handler(CommandHandler("intraday", intra))
|
dp.add_handler(CommandHandler("intraday", intra))
|
||||||
dp.add_handler(CommandHandler("intra", intra))
|
dp.add_handler(CommandHandler("intra", intra))
|
||||||
|
54
functions.py
54
functions.py
@ -44,10 +44,10 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
def get_symbol_list(self, return_df=False):
|
def get_symbol_list(self, return_df=False):
|
||||||
"""
|
"""
|
||||||
Fetches a list of stock market symbols from FINRA
|
Fetches a list of stock market symbols from FINRA
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
pd.DataFrame -- [DataFrame with columns: Symbol | Issue_Name | Primary_Listing_Mkt
|
pd.DataFrame -- [DataFrame with columns: Symbol | Issue_Name | Primary_Listing_Mkt
|
||||||
datetime -- The time when the list of symbols was fetched. The Symbol list is updated every open and close of every trading day.
|
datetime -- The time when the list of symbols was fetched. The Symbol list is updated every open and close of every trading day.
|
||||||
"""
|
"""
|
||||||
raw_symbols = r.get(
|
raw_symbols = r.get(
|
||||||
f"https://cloud.iexapis.com/stable/ref-data/symbols?token={self.IEX_TOKEN}"
|
f"https://cloud.iexapis.com/stable/ref-data/symbols?token={self.IEX_TOKEN}"
|
||||||
@ -62,10 +62,10 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
def search_symbols(self, search: str):
|
def search_symbols(self, search: str):
|
||||||
"""
|
"""
|
||||||
Performs a fuzzy search to find stock symbols closest to a search term.
|
Performs a fuzzy search to find stock symbols closest to a search term.
|
||||||
|
|
||||||
Arguments:
|
Arguments:
|
||||||
search {str} -- String used to search, could be a company name or something close to the companies stock ticker.
|
search {str} -- String used to search, could be a company name or something close to the companies stock ticker.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
List of Tuples -- A list tuples of every stock sorted in order of how well they match. Each tuple contains: (Symbol, Issue Name).
|
List of Tuples -- A list tuples of every stock sorted in order of how well they match. Each tuple contains: (Symbol, Issue Name).
|
||||||
"""
|
"""
|
||||||
@ -78,13 +78,15 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
|
|
||||||
symbols = self.symbol_list
|
symbols = self.symbol_list
|
||||||
symbols["Match"] = symbols.apply(
|
symbols["Match"] = symbols.apply(
|
||||||
lambda x: fuzz.ratio(search, f"{x['symbol']}".lower()), axis=1,
|
lambda x: fuzz.ratio(search, f"{x['symbol']}".lower()),
|
||||||
|
axis=1,
|
||||||
)
|
)
|
||||||
|
|
||||||
symbols.sort_values(by="Match", ascending=False, inplace=True)
|
symbols.sort_values(by="Match", ascending=False, inplace=True)
|
||||||
if symbols["Match"].head().sum() < 300:
|
if symbols["Match"].head().sum() < 300:
|
||||||
symbols["Match"] = symbols.apply(
|
symbols["Match"] = symbols.apply(
|
||||||
lambda x: fuzz.partial_ratio(search, x["name"].lower()), axis=1,
|
lambda x: fuzz.partial_ratio(search, x["name"].lower()),
|
||||||
|
axis=1,
|
||||||
)
|
)
|
||||||
|
|
||||||
symbols.sort_values(by="Match", ascending=False, inplace=True)
|
symbols.sort_values(by="Match", ascending=False, inplace=True)
|
||||||
@ -96,12 +98,12 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
def find_symbols(self, text: str):
|
def find_symbols(self, text: str):
|
||||||
"""
|
"""
|
||||||
Finds stock tickers starting with a dollar sign in a blob of text and returns them in a list. Only returns each match once. Example: Whats the price of $tsla? -> ['tsla']
|
Finds stock tickers starting with a dollar sign in a blob of text and returns them in a list. Only returns each match once. Example: Whats the price of $tsla? -> ['tsla']
|
||||||
|
|
||||||
Arguments:
|
Arguments:
|
||||||
text {str} -- Blob of text that might contain tickers with the format: $TICKER
|
text {str} -- Blob of text that might contain tickers with the format: $TICKER
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
list -- List of every found match without the dollar sign.
|
list -- List of every found match without the dollar sign.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
return list(set(re.findall(self.SYMBOL_REGEX, text)))
|
return list(set(re.findall(self.SYMBOL_REGEX, text)))
|
||||||
@ -109,10 +111,10 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
def price_reply(self, symbols: list):
|
def price_reply(self, symbols: list):
|
||||||
"""
|
"""
|
||||||
Takes a list of symbols and replies with Markdown formatted text about the symbols price change for the day.
|
Takes a list of symbols and replies with Markdown formatted text about the symbols price change for the day.
|
||||||
|
|
||||||
Arguments:
|
Arguments:
|
||||||
symbols {list} -- List of stock market symbols.
|
symbols {list} -- List of stock market symbols.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
dict -- Dictionary with keys of symbols and values of markdown formatted text example: {'tsla': 'The current stock price of Tesla Motors is $**420$$, the stock price is currently **up 42%**}
|
dict -- Dictionary with keys of symbols and values of markdown formatted text example: {'tsla': 'The current stock price of Tesla Motors is $**420$$, the stock price is currently **up 42%**}
|
||||||
"""
|
"""
|
||||||
@ -224,3 +226,33 @@ Market data is provided by [IEX Cloud](https://iexcloud.io)
|
|||||||
df["DT"] = pd.to_datetime(df["date"] + "T" + df["minute"])
|
df["DT"] = pd.to_datetime(df["date"] + "T" + df["minute"])
|
||||||
df = df.set_index("DT")
|
df = df.set_index("DT")
|
||||||
return df
|
return df
|
||||||
|
|
||||||
|
def stat_reply(self, symbols: list):
|
||||||
|
infoMessages = {}
|
||||||
|
|
||||||
|
for symbol in symbols:
|
||||||
|
IEXurl = f"https://cloud.iexapis.com/stable/stock/{symbol}/stats?token={self.IEX_TOKEN}"
|
||||||
|
response = r.get(IEXurl)
|
||||||
|
|
||||||
|
if response.status_code == 200:
|
||||||
|
data = response.json()
|
||||||
|
infoMessages[
|
||||||
|
symbol
|
||||||
|
] = f"""
|
||||||
|
Company Name: {data['companyName']}\n
|
||||||
|
Market Cap: {data['marketcap']}
|
||||||
|
52 Week (high-low):{data['week52high']}-{data['week52low']}
|
||||||
|
Number of Employees: {data['employees']}
|
||||||
|
Next Earnings Date: {data['nextEarningsDate']}
|
||||||
|
Dividend Info:
|
||||||
|
\tYield: {round(data['dividendYield'],4)*100}%
|
||||||
|
\tNext Date: {data['nextDividendDate']}
|
||||||
|
\tEx Date: {data['exDividendDate']}
|
||||||
|
"""
|
||||||
|
|
||||||
|
else:
|
||||||
|
infoMessages[
|
||||||
|
symbol
|
||||||
|
] = f"No information found for: {symbol}\nEither today is boring or the symbol does not exist."
|
||||||
|
|
||||||
|
return infoMessages
|
Loading…
x
Reference in New Issue
Block a user