From 5a44fb69af8f6dbeaa4e68d83d6bf143d50e9dc6 Mon Sep 17 00:00:00 2001 From: didier Date: Fri, 21 May 2021 01:27:19 +0100 Subject: [PATCH] add contracts to government menu --- .../cryptocurrency/crypto_controller.py | 2 +- .../government/gov_controller.py | 44 +++- .../government/quiverquant_model.py | 29 +- .../government/quiverquant_view.py | 248 ++++++++++++++++++ 4 files changed, 303 insertions(+), 20 deletions(-) diff --git a/gamestonk_terminal/cryptocurrency/crypto_controller.py b/gamestonk_terminal/cryptocurrency/crypto_controller.py index 42908565b86..3849602db04 100644 --- a/gamestonk_terminal/cryptocurrency/crypto_controller.py +++ b/gamestonk_terminal/cryptocurrency/crypto_controller.py @@ -66,7 +66,7 @@ class CryptoController: print(" candle show candles") print(" balance show coin balance") print("") - print(" >ta technical analysis menu for") + print("> ta technical analysis menu for") print("") def switch(self, an_input: str): diff --git a/gamestonk_terminal/government/gov_controller.py b/gamestonk_terminal/government/gov_controller.py index 5702327a43f..70edad786dd 100644 --- a/gamestonk_terminal/government/gov_controller.py +++ b/gamestonk_terminal/government/gov_controller.py @@ -34,6 +34,10 @@ class GovController: "sell_house", "house", "raw_house", + "last_contracts", + "sum_contracts", + "raw_contracts", + "contracts", ] def __init__( @@ -58,24 +62,28 @@ class GovController: print("") print("Explore:") print(" last_congress last congress trading") - print(" buy_congress top buy congress tickers") - print(" sell_congress top sell congress tickers") + print(" buy_congress plot top buy congress tickers") + print(" sell_congress plot top sell congress tickers") print(" last_senate last senate trading") - print(" buy_senate top buy senate tickers") - print(" sell_senate top sell senate tickers") + print(" buy_senate plot top buy senate tickers") + print(" sell_senate plot top sell senate tickers") print(" last_house last house trading") - print(" buy_house top buy house tickers") - print(" sell_house top sell house tickers") + print(" buy_house plot top buy house tickers") + print(" sell_house plot top sell house tickers") + print(" last_contracts last government contracts") + print(" sum_contracts plot sum of last government contracts") print("") if self.ticker: print(f"Ticker: {self.ticker}") print(" raw_congress raw congress trades on the ticker") - print(" congress congress trades on the ticker") + print(" congress plot congress trades on the ticker") print(" raw_senate raw senate trades on the ticker") - print(" senate senate trades on the ticker") + print(" senate plot senate trades on the ticker") print(" raw_house raw house trades on the ticker") - print(" house house trades on the ticker") - print("") + print(" house plot house trades on the ticker") + print(" raw_contracts raw contracts on the ticker") + print(" contracts plot sum of contracts on the ticker") + print("") return def switch(self, an_input: str): @@ -166,6 +174,22 @@ class GovController: """Process house command""" quiverquant_view.government_trading(other_args, self.ticker, "house") + def call_last_contracts(self, other_args: List[str]): + """Process last_contracts command""" + quiverquant_view.last_contracts(other_args) + + def call_sum_contracts(self, other_args: List[str]): + """Process sum_contracts command""" + quiverquant_view.sum_contracts(other_args) + + def call_raw_contracts(self, other_args: List[str]): + """Process raw_contracts command""" + quiverquant_view.raw_contracts(other_args, self.ticker) + + def call_contracts(self, other_args: List[str]): + """Process contracts command""" + quiverquant_view.contracts(other_args, self.ticker) + def menu(ticker: str): """Government Menu""" diff --git a/gamestonk_terminal/government/quiverquant_model.py b/gamestonk_terminal/government/quiverquant_model.py index 597b432352e..7c625c71086 100644 --- a/gamestonk_terminal/government/quiverquant_model.py +++ b/gamestonk_terminal/government/quiverquant_model.py @@ -5,13 +5,13 @@ import pandas as pd API_QUIVERQUANT_KEY = "5cd2a65e96d0486efbe926a7cdbc1e8d8ab6c7b3" -def get_government_trading(type: str, ticker: str = "") -> pd.DataFrame: +def get_government_trading(gov_type: str, ticker: str = "") -> pd.DataFrame: """Returns the most recent transactions by members of government Parameters ---------- - type: str - Type of government data between: Congress, Senate and House + gov_type: str + Type of government data between: Congress, Senate, House and Contracts ticker : str Ticker to get congress trading data from @@ -21,7 +21,7 @@ def get_government_trading(type: str, ticker: str = "") -> pd.DataFrame: Most recent transactions by members of U.S. Congress """ - if type == "congress": + if gov_type == "congress": if ticker: url = ( f"https://api.quiverquant.com/beta/historical/congresstrading/{ticker}" @@ -29,18 +29,26 @@ def get_government_trading(type: str, ticker: str = "") -> pd.DataFrame: else: url = "https://api.quiverquant.com/beta/live/congresstrading" - elif type == "senate": + elif gov_type == "senate": if ticker: url = f"https://api.quiverquant.com/beta/historical/senatetrading/{ticker}" else: url = "https://api.quiverquant.com/beta/live/senatetrading" - elif type == "house": + elif gov_type == "house": if ticker: url = f"https://api.quiverquant.com/beta/historical/housetrading/{ticker}" else: url = "https://api.quiverquant.com/beta/live/housetrading" + elif gov_type == "contracts": + if ticker: + url = ( + f"https://api.quiverquant.com/beta/historical/govcontractsall/{ticker}" + ) + else: + url = "https://api.quiverquant.com/beta/live/govcontractsall" + else: return pd.DataFrame() @@ -51,8 +59,11 @@ def get_government_trading(type: str, ticker: str = "") -> pd.DataFrame: } response = requests.get(url, headers=headers) if response.status_code == 200: - return pd.DataFrame(response.json()).rename( - columns={"Date": "TransactionDate", "Senator": "Representative"} - ) + if gov_type in ["congress", "senate", "house"]: + return pd.DataFrame(response.json()).rename( + columns={"Date": "TransactionDate", "Senator": "Representative"} + ) + else: + return pd.DataFrame(response.json()) return pd.DataFrame() diff --git a/gamestonk_terminal/government/quiverquant_view.py b/gamestonk_terminal/government/quiverquant_view.py index 0fe07e59981..6bb0c866a4d 100644 --- a/gamestonk_terminal/government/quiverquant_view.py +++ b/gamestonk_terminal/government/quiverquant_view.py @@ -513,3 +513,251 @@ def raw_government(other_args: List[str], ticker: str, gov_type: str): except Exception as e: print(e, "\n") + + +def last_contracts(other_args: List[str]): + """Last contracts + + Parameters + ---------- + other_args : List[str] + Command line arguments to be processed with argparse + """ + parser = argparse.ArgumentParser( + add_help=False, + prog="last_contracts", + description="Last contracts. [Source: www.quiverquant.com]", + ) + parser.add_argument( + "-p", + "--past_transactions_days", + action="store", + dest="past_transactions_days", + type=check_positive, + default=2, + help="Past transaction days", + ) + parser.add_argument( + "-l", + "--limit", + action="store", + dest="limit_contracts", + type=check_positive, + default=20, + help="Limit of contracts to display", + ) + + try: + if other_args: + if "-" not in other_args[0]: + other_args.insert(0, "-p") + + ns_parser = parse_known_args_and_warn(parser, other_args) + if not ns_parser: + return + + df_contracts = quiverquant_model.get_government_trading("contracts") + + if df_contracts.empty: + print("No government contracts found\n") + return + + df_contracts.sort_values("Date", ascending=False) + + df_contracts["Date"] = pd.to_datetime(df_contracts["Date"]) + + df_contracts.drop_duplicates(inplace=True) + + df_contracts = df_contracts[ + df_contracts["Date"].isin( + df_contracts["Date"].unique()[: ns_parser.past_transactions_days] + ) + ] + + df_contracts = df_contracts[ + ["Date", "Ticker", "Amount", "Description", "Agency"] + ][: ns_parser.limit_contracts] + + print(df_contracts.to_string(index=False)) + print("") + + except Exception as e: + print(e, "\n") + + +def sum_contracts(other_args: List[str]): + """Sum contracts + + Parameters + ---------- + other_args : List[str] + Command line arguments to be processed with argparse + """ + parser = argparse.ArgumentParser( + add_help=False, + prog="sum_contracts", + description="Sum latest contracts. [Source: www.quiverquant.com]", + ) + + try: + if other_args: + if "-" not in other_args[0]: + other_args.insert(0, "-p") + + ns_parser = parse_known_args_and_warn(parser, other_args) + if not ns_parser: + return + + df_contracts = quiverquant_model.get_government_trading("contracts") + + if df_contracts.empty: + print("No government contracts found\n") + return + + df_contracts["Date"] = pd.to_datetime(df_contracts["Date"]).dt.date + + df_contracts.drop_duplicates(inplace=True) + + plt.figure(figsize=plot_autoscale(), dpi=PLOT_DPI) + + df_contracts.groupby("Date").sum().div(1000).plot( + kind="bar", rot=0, ax=plt.gca() + ) + plt.ylabel("Amount [1k $]") + plt.title("Sum of latest government contracts") + + if gtff.USE_ION: + plt.ion() + + plt.show() + print("") + + except Exception as e: + print(e, "\n") + + +def raw_contracts(other_args: List[str], ticker: str): + """Raw contracts + + Parameters + ---------- + other_args : List[str] + Command line arguments to be processed with argparse + ticker: str + Ticker to get congress trading data from + """ + parser = argparse.ArgumentParser( + add_help=False, + prog="raw_contracts", + description="Raw contracts. [Source: www.quiverquant.com]", + ) + parser.add_argument( + "-p", + "--past_transactions_days", + action="store", + dest="past_transactions_days", + type=check_positive, + default=10, + help="Past transaction days", + ) + + try: + if other_args: + if "-" not in other_args[0]: + other_args.insert(0, "-p") + + ns_parser = parse_known_args_and_warn(parser, other_args) + if not ns_parser: + return + + df_contracts = quiverquant_model.get_government_trading("contracts", ticker) + + if df_contracts.empty: + print("No government contracts found\n") + return + + df_contracts["Date"] = pd.to_datetime(df_contracts["Date"]).dt.date + + df_contracts.drop_duplicates(inplace=True) + + df_contracts = df_contracts[ + df_contracts["Date"].isin( + df_contracts["Date"].unique()[: ns_parser.past_transactions_days] + ) + ] + + df_contracts.drop_duplicates(inplace=True) + + print(df_contracts.to_string(index=False)) + print("") + + except Exception as e: + print(e, "\n") + + +def contracts(other_args: List[str], ticker: str): + """Contracts + + Parameters + ---------- + other_args : List[str] + Command line arguments to be processed with argparse + ticker: str + Ticker to get congress trading data from + """ + parser = argparse.ArgumentParser( + add_help=False, + prog="contracts", + description="Contracts associated with ticker. [Source: www.quiverquant.com]", + ) + parser.add_argument( + "-p", + "--past_transactions_days", + action="store", + dest="past_transactions_days", + type=check_positive, + default=10, + help="Past transaction days", + ) + + try: + if other_args: + if "-" not in other_args[0]: + other_args.insert(0, "-p") + + ns_parser = parse_known_args_and_warn(parser, other_args) + if not ns_parser: + return + + df_contracts = quiverquant_model.get_government_trading("contracts", ticker) + + if df_contracts.empty: + print("No government contracts found\n") + return + + df_contracts["Date"] = pd.to_datetime(df_contracts["Date"]).dt.date + + df_contracts = df_contracts[ + df_contracts["Date"].isin( + df_contracts["Date"].unique()[: ns_parser.past_transactions_days] + ) + ] + + df_contracts.drop_duplicates(inplace=True) + + plt.figure(figsize=plot_autoscale(), dpi=PLOT_DPI) + + df_contracts.groupby("Date").sum().div(1000).plot( + kind="bar", rot=0, ax=plt.gca() + ) + plt.ylabel("Amount [1k $]") + plt.title(f"Sum of latest government contracts to {ticker}") + + if gtff.USE_ION: + plt.ion() + + plt.show() + print("") + + except Exception as e: + print(e, "\n")