add yahoofinance most shorted & undervalued screener (#688)

* add yahoofinance most shorted & undervalued screener

* .

* .

* (#688) follow up

* .

* followup (#688)
This commit is contained in:
devwolff
2021-08-22 00:37:59 +10:00
committed by GitHub
parent c7e784af71
commit 1e1767dc15
8 changed files with 225 additions and 17 deletions

View File

@@ -16,9 +16,11 @@ from gamestonk_terminal.helper_funcs import (
parse_known_args_and_warn,
check_positive,
valid_date,
check_int_range,
)
from gamestonk_terminal.stocks.stocks_helper import load
from gamestonk_terminal.stocks.dark_pool_shorts import (
yahoofinance_view,
stockgrid_view,
shortinterest_view,
quandl_view,
@@ -41,6 +43,7 @@ class DarkPoolShortsController:
]
CHOICES_COMMANDS = [
"shorted",
"hsi",
"prom",
"pos",
@@ -80,7 +83,9 @@ Dark Pool Shorts:
quit quit to abandon program
load load a specific stock ticker for analysis
shortinterest.com
Yahoo Finance:
shorted show most shorted stocks
shortinterest.com:
hsi show top high short interest stocks of over 20% ratio
FINRA:
prom promising tickers based on dark pool shares regression
@@ -149,6 +154,48 @@ Quandl/Stockgrid:
other_args, self.ticker, self.start, "1440min", self.stock
)
def call_shorted(self, other_args: List[str]):
"""Process shorted command"""
parser = argparse.ArgumentParser(
add_help=False,
formatter_class=argparse.ArgumentDefaultsHelpFormatter,
prog="shorted",
description="Print up to 25 top ticker most shorted. [Source: Yahoo Finance]",
)
parser.add_argument(
"-n",
"--num",
action="store",
dest="num",
type=check_int_range(1, 25),
default=5,
help="Number of the most shorted stocks to retrieve.",
)
parser.add_argument(
"--export",
choices=["csv", "json", "xlsx"],
default="",
type=str,
dest="export",
help="Export dataframe data to csv,json,xlsx file",
)
try:
if other_args:
if "-" not in other_args[0]:
other_args.insert(0, "-n")
ns_parser = parse_known_args_and_warn(parser, other_args)
if not ns_parser:
return
yahoofinance_view.display_most_shorted(
num_stocks=ns_parser.num,
export=ns_parser.export,
)
except Exception as e:
print(e, "\n")
def call_hsi(self, other_args: List[str]):
"""Process hsi command"""
parser = argparse.ArgumentParser(

View File

@@ -0,0 +1,20 @@
""" Yahoo Finance Model """
__docformat__ = "numpy"
import pandas as pd
import requests
def get_most_shorted() -> pd.DataFrame:
"""Get most shorted stock screener [Source: Yahoo Finance]
Returns
-------
pd.DataFrame
Most Shorted Stocks
"""
url = "https://finance.yahoo.com/screener/predefined/most_shorted_stocks"
data = pd.read_html(requests.get(url).text)[0]
data = data.iloc[:, :-1]
return data

View File

@@ -0,0 +1,43 @@
""" Yahoo Finance View """
__docformat__ = "numpy"
import os
from tabulate import tabulate
from gamestonk_terminal.helper_funcs import export_data
from gamestonk_terminal.stocks.dark_pool_shorts import yahoofinance_model
def display_most_shorted(num_stocks: int, export: str):
"""Display most shorted stocks screener. [Source: Yahoo Finance]
Parameters
----------
num_stocks: int
Number of stocks to display
export : str
Export dataframe data to csv,json,xlsx file
"""
df = yahoofinance_model.get_most_shorted().head(num_stocks)
df.dropna(how="all", axis=1, inplace=True)
df = df.replace(float("NaN"), "")
if df.empty:
print("No data found.")
else:
print(
tabulate(
df,
headers=df.columns,
floatfmt=".2f",
showindex=False,
tablefmt="fancy_grid",
)
)
print("")
export_data(
export,
os.path.dirname(os.path.abspath(__file__)),
"shorted",
df,
)

View File

@@ -44,6 +44,7 @@ class DiscoveryController:
"fipo",
"gainers",
"losers",
"under",
"ford",
"arkord",
"upcoming",
@@ -79,6 +80,7 @@ Finnhub:
Yahoo Finance:
gainers show latest top gainers
losers show latest top losers
under undervalued growth stocks
Fidelity:
ford orders by Fidelity Customers
cathiesark.com:
@@ -308,6 +310,48 @@ pennystockflow.com
except Exception as e:
print(e, "\n")
def call_under(self, other_args: List[str]):
"""Process under command"""
parser = argparse.ArgumentParser(
add_help=False,
formatter_class=argparse.ArgumentDefaultsHelpFormatter,
prog="under",
description="Print up to 25 top ticker losers. [Source: Yahoo Finance]",
)
parser.add_argument(
"-n",
"--num",
action="store",
dest="num",
type=check_int_range(1, 25),
default=5,
help="Number of the undervalued stocks to retrieve.",
)
parser.add_argument(
"--export",
choices=["csv", "json", "xlsx"],
default="",
type=str,
dest="export",
help="Export dataframe data to csv,json,xlsx file",
)
try:
if other_args:
if "-" not in other_args[0]:
other_args.insert(0, "-n")
ns_parser = parse_known_args_and_warn(parser, other_args)
if not ns_parser:
return
yahoofinance_view.display_undervalued(
num_stocks=ns_parser.num,
export=ns_parser.export,
)
except Exception as e:
print(e, "\n")
def call_ford(self, other_args: List[str]):
"""Process ford command"""
parser = argparse.ArgumentParser(

View File

@@ -29,3 +29,18 @@ def get_losers() -> pd.DataFrame:
url_losers = "https://finance.yahoo.com/screener/predefined/day_losers"
return pd.read_html(requests.get(url_losers).text)[0]
def get_undervalued() -> pd.DataFrame:
"""Get Yahoo Finance undervalued growth stocks
Returns
-------
pd.DataFrame
Undervalued stocks
"""
url = "https://finance.yahoo.com/screener/predefined/undervalued_growth_stocks"
data = pd.read_html(requests.get(url).text)[0]
data = data.iloc[:, :-1]
return data

View File

@@ -17,7 +17,7 @@ def display_gainers(num_stocks: int, export: str):
export : str
Export dataframe data to csv,json,xlsx file
"""
df_gainers = yahoofinance_model.get_gainers().head(num_stocks)
df_gainers = yahoofinance_model.get_gainers()
df_gainers.dropna(how="all", axis=1, inplace=True)
df_gainers = df_gainers.replace(float("NaN"), "")
@@ -26,7 +26,7 @@ def display_gainers(num_stocks: int, export: str):
else:
print(
tabulate(
df_gainers,
df_gainers.head(num_stocks),
headers=df_gainers.columns,
floatfmt=".2f",
showindex=False,
@@ -53,7 +53,7 @@ def display_losers(num_stocks: int, export: str):
export : str
Export dataframe data to csv,json,xlsx file
"""
df_losers = yahoofinance_model.get_losers().head(num_stocks)
df_losers = yahoofinance_model.get_losers()
df_losers.dropna(how="all", axis=1, inplace=True)
df_losers = df_losers.replace(float("NaN"), "")
@@ -62,7 +62,7 @@ def display_losers(num_stocks: int, export: str):
else:
print(
tabulate(
df_losers,
df_losers.head(num_stocks),
headers=df_losers.columns,
floatfmt=".2f",
showindex=False,
@@ -77,3 +77,39 @@ def display_losers(num_stocks: int, export: str):
"losers",
df_losers,
)
def display_undervalued(num_stocks: int, export: str):
"""Display most undervalued growth stock. [Source: Yahoo Finance]
Parameters
----------
num_stocks: int
Number of stocks to display
export : str
Export dataframe data to csv,json,xlsx file
"""
df = yahoofinance_model.get_undervalued()
df.dropna(how="all", axis=1, inplace=True)
df = df.replace(float("NaN"), "")
if df.empty:
print("No data found.")
else:
print(
tabulate(
df.head(num_stocks),
headers=df.columns,
floatfmt=".2f",
showindex=False,
tablefmt="fancy_grid",
)
)
print("")
export_data(
export,
os.path.dirname(os.path.abspath(__file__)),
"undervalued",
df,
)

View File

@@ -1,21 +1,21 @@
"""Screener Controller Module"""
__docformat__ = "numpy"
import os
import argparse
import configparser
import os
from typing import List
import matplotlib.pyplot as plt
from prompt_toolkit.completion import NestedCompleter
from gamestonk_terminal.helper_funcs import get_flair
from gamestonk_terminal.menu import session
from gamestonk_terminal import feature_flags as gtff
from gamestonk_terminal.helper_funcs import (
get_flair,
parse_known_args_and_warn,
)
from gamestonk_terminal.stocks.screener import finviz_view
from gamestonk_terminal.stocks.screener import yahoo_finance_view
from gamestonk_terminal.menu import session
from gamestonk_terminal.portfolio.portfolio_optimization import po_controller
from gamestonk_terminal.stocks.screener import finviz_view, yahoofinance_view
presets_path = os.path.join(os.path.abspath(os.path.dirname(__file__)), "presets/")
@@ -253,7 +253,7 @@ class ScreenerController:
def call_historical(self, other_args: List[str]):
"""Process historical command"""
self.screen_tickers = yahoo_finance_view.historical(other_args, self.preset)
self.screen_tickers = yahoofinance_view.historical(other_args, self.preset)
def call_overview(self, other_args: List[str]):
"""Process overview command"""

View File

@@ -1,21 +1,24 @@
import os
"""Yahoo Finance View"""
__docformat__ = "numpy"
import argparse
from typing import List
import random
import datetime
import configparser
import datetime
import os
import random
from typing import List
from pandas.plotting import register_matplotlib_converters
import matplotlib.pyplot as plt
import yfinance as yf
from finvizfinance.screener import ticker
from gamestonk_terminal.stocks.screener import finviz_view
from gamestonk_terminal import feature_flags as gtff
from gamestonk_terminal.config_plot import PLOT_DPI
from gamestonk_terminal.helper_funcs import (
parse_known_args_and_warn,
plot_autoscale,
valid_date,
)
from gamestonk_terminal.config_plot import PLOT_DPI
from gamestonk_terminal.stocks.screener import finviz_view
register_matplotlib_converters()