Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding GARCH #4815

Merged
merged 81 commits into from
May 10, 2023
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
Show all changes
81 commits
Select commit Hold shift + click to select a range
ab8ef27
Add GARCH
northern-64bit Apr 17, 2023
0e0a5b0
Linting
northern-64bit Apr 17, 2023
374b084
Rearrange the econometrics menu
northern-64bit Apr 17, 2023
2229a76
Add integration test
northern-64bit Apr 17, 2023
347171f
Merge branch 'develop' into feature/garch
jmaslek Apr 18, 2023
a1f41ba
Add ret command + fixes
northern-64bit Apr 20, 2023
4d93698
Merge branch 'develop' into feature/garch
northern-64bit Apr 20, 2023
bae2ac3
Fix linting
northern-64bit Apr 20, 2023
5c3657d
Merge branch 'feature/garch' of github.com:northern-64bit/GamestonkTe…
northern-64bit Apr 20, 2023
01b80b5
Fix linting
northern-64bit Apr 20, 2023
8a673fb
Fix pylint
northern-64bit Apr 21, 2023
02e16eb
Merge branch 'develop' into feature/garch
northern-64bit Apr 21, 2023
cce6c6b
Merge branch 'develop' into feature/garch
northern-64bit Apr 21, 2023
31119b1
Add logger to functions
northern-64bit Apr 22, 2023
38a8b81
Merge branch 'develop' into feature/garch
northern-64bit Apr 24, 2023
a8a394d
Merge branch 'develop' into feature/garch
northern-64bit Apr 24, 2023
b3efe60
Merge branch 'develop' into feature/garch
northern-64bit Apr 25, 2023
1e4737a
Merge branch 'develop' into feature/garch
northern-64bit Apr 25, 2023
33a1a6f
Merge branch 'develop' into feature/garch
northern-64bit Apr 25, 2023
90da4e2
Merge pull request #4899 from OpenBB-finance/release/3.0.0
jmaslek Apr 26, 2023
a00d6ef
bump pywry
tehcoderer Apr 26, 2023
7cba702
Merge pull request #4906 from tehcoderer/hotfix/pywry-merge-fix
jmaslek Apr 26, 2023
839638b
fix rm command (#4890)
montezdesousa Apr 26, 2023
e7b8b38
Fix `crypto/defi/anchor` (#4892)
montezdesousa Apr 26, 2023
2558f94
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek Apr 26, 2023
61dffa0
fix windows pyinstaller subprocess fail if space in path
tehcoderer Apr 26, 2023
30d5e58
remove API_IEX_TOKEN
tehcoderer Apr 26, 2023
915dd1f
remove API_SENTIMENTINVESTOR_TOKEN
tehcoderer Apr 26, 2023
94a31f0
Merge pull request #4910 from tehcoderer/hotfix/windows-installer
jmaslek Apr 26, 2023
a949fd2
Merge branch 'main' of https://github.com/OpenBB-finance/OpenBBTermin…
jmaslek Apr 26, 2023
3779110
Merge branch 'develop' into feature/garch
northern-64bit Apr 27, 2023
c570d0e
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek Apr 27, 2023
dc35f71
Merge branch 'develop' into feature/garch
northern-64bit Apr 27, 2023
dc55a43
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek Apr 27, 2023
964c673
Merge branch 'develop' into feature/garch
northern-64bit Apr 28, 2023
b0a9f7a
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek Apr 28, 2023
1c65986
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek Apr 28, 2023
72ea2a3
Merge branch 'develop' into feature/garch
northern-64bit Apr 29, 2023
9244878
Convert to latex + requested changes
northern-64bit Apr 29, 2023
e1862a5
Fix linting
northern-64bit Apr 29, 2023
b3fe93c
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 1, 2023
9b6a61f
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 2, 2023
611c914
Merge branch 'develop' into feature/garch
northern-64bit May 2, 2023
5916f5a
Remove unnecessary logger
jmaslek May 2, 2023
a3066c5
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 2, 2023
d6bbae3
Merge branch 'develop' into feature/garch
northern-64bit May 3, 2023
d007d0e
Merge branch 'develop' into feature/garch
northern-64bit May 3, 2023
9d6615a
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 3, 2023
424a9a9
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 3, 2023
0784b29
Merge branch 'develop' into feature/garch
northern-64bit May 3, 2023
103b1a8
Add example
northern-64bit May 3, 2023
c01af20
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 4, 2023
2bd426a
SDK updated
jmaslek May 4, 2023
485cfc8
Merge branch 'develop' into feature/garch
jmaslek May 4, 2023
562208b
Merge branch 'develop' into feature/garch
andrewkenreich May 4, 2023
80b1bfb
fix syntax on elite level math that I def know
andrewkenreich May 4, 2023
7d317ce
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 4, 2023
3c0450c
Fix docstring
northern-64bit May 4, 2023
1fec4de
Merge branch 'feature/garch' of github.com:northern-64bit/GamestonkTe…
northern-64bit May 4, 2023
187e7a2
Merge branch 'develop' into feature/garch
northern-64bit May 4, 2023
749d776
Fix example
northern-64bit May 4, 2023
e7e0304
Merge branch 'feature/garch' of github.com:northern-64bit/GamestonkTe…
northern-64bit May 4, 2023
2a38da1
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 5, 2023
2edf8e0
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 5, 2023
710a1ea
Merge branch 'develop' into feature/garch
northern-64bit May 5, 2023
1daaa09
Merge branch 'develop' into feature/garch
northern-64bit May 8, 2023
84d257e
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 8, 2023
8052cab
Merge branch 'develop' into feature/garch
northern-64bit May 8, 2023
cba34a5
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 8, 2023
69acfeb
Merge branch 'develop' into feature/garch
northern-64bit May 8, 2023
065a462
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 9, 2023
6339eae
Merge branch 'develop' into feature/garch
jmaslek May 9, 2023
4daac7c
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 9, 2023
3d3b409
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 9, 2023
53207ac
Fix
northern-64bit May 9, 2023
76adde9
Merge branch 'develop' into feature/garch
northern-64bit May 9, 2023
0c66f80
Merge branch 'feature/garch' of github.com:northern-64bit/GamestonkTe…
northern-64bit May 9, 2023
ab0450d
Linting
northern-64bit May 9, 2023
36cb1df
Merge branch 'develop' into feature/garch
jmaslek May 9, 2023
2cde40d
Merge branch 'develop' of https://github.com/OpenBB-finance/OpenBBTer…
jmaslek May 10, 2023
3e52b2d
Merge branch 'develop' into pr/northern-64bit/4815
jmaslek May 10, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions openbb_terminal/core/sdk/trail_map.csv
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,7 @@ econometrics.panel,econometrics_regression_model.get_regressions_results,econome
econometrics.pols,econometrics_regression_model.get_pols,
econometrics.re,econometrics_regression_model.get_re,
econometrics.root,econometrics_model.get_root,econometrics_view.display_root
econometrics.garch,econometrics_model.get_garch,econometrics_view.display_garch
economy.available_indices,economy_yfinance_model.get_available_indices,
economy.balance,economy_oecd_model.get_balance,economy_oecd_view.plot_balance
economy.bigmac,economy_nasdaq_model.get_big_mac_indices,economy_nasdaq_view.display_big_mac_index
Expand Down
127 changes: 122 additions & 5 deletions openbb_terminal/econometrics/econometrics_controller.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ class EconometricsController(BaseController):
"dwat",
"bgod",
"bpag",
"garch",
"granger",
"coint",
]
Expand Down Expand Up @@ -181,6 +182,7 @@ def __init__(self, queue: Optional[List[str]] = None):
"plot",
"norm",
"root",
"garch",
"granger",
"coint",
"corr",
Expand Down Expand Up @@ -217,6 +219,7 @@ def update_runtime_choices(self):
"ols",
"panel",
"delete",
"garch",
]:
self.choices[feature] = dataset_columns
for feature in [
Expand Down Expand Up @@ -281,16 +284,17 @@ def print_help(self):
mt.add_cmd("rename", self.files)
mt.add_cmd("lag", self.files)
mt.add_cmd("export", self.files)
mt.add_info("_tests_")
mt.add_info("time_series_")
mt.add_cmd("norm", self.files)
mt.add_cmd("root", self.files)
mt.add_cmd("ols", self.files)
mt.add_cmd("granger", self.files)
mt.add_cmd("root", self.files)
mt.add_cmd("coint", self.files)
mt.add_info("_regression_")
mt.add_cmd("ols", self.files)
mt.add_cmd("garch", self.files)
mt.add_info("_panel_")
mt.add_cmd("panel", self.files)
mt.add_cmd("compare", self.files)
mt.add_info("_regression_tests_")
mt.add_info("_residuals_")
mt.add_cmd("dwat", self.files and self.regression["OLS"]["model"])
mt.add_cmd("bgod", self.files and self.regression["OLS"]["model"])
mt.add_cmd("bpag", self.files and self.regression["OLS"]["model"])
Expand Down Expand Up @@ -1890,6 +1894,119 @@ def call_bpag(self, other_args):
self.regression["OLS"]["model"], ns_parser.export
)

@log_start_end(log=logger)
def call_garch(self, other_args: List[str]):
"""Process garch command"""
parser = argparse.ArgumentParser(
add_help=False,
formatter_class=argparse.ArgumentDefaultsHelpFormatter,
prog="gach",
northern-64bit marked this conversation as resolved.
Show resolved Hide resolved
description="""Calculates annualized volatility forecasts based on GARCH.
GARCH (Generalized autoregressive conditional heteroskedasticity) is stochastic model for time series, which is for
instance used to model volatility clusters, stock return and inflation. It is a generalisation of the ARCH models.

GARCH(p, q): = (1 - alpha - beta) sigma_l + SUM(alpha u_{t-1} ^ 2) + SUM(beta sigma_{t-1} ^ 2) [1]

The GARCH-model assumes that the variance estimate consists of 3 components:
- sigma_l; the long term component, which is unrelated to the current market conditions
- u_t; the innovation/discovery through current market price changes
- simgma_t; the last estimate

GARCH can be understood as a model, which allows to optimize these 3 variance components to the time series.
This is done assigning weights to variance components: (1 - alpha - beta) for sigma_l, alpha for u_t and
beta for sigma_t. [2]

The weights can be estimated by iterating over different values of (1 - alpha - beta) sigma_l which we will call omega, alpha and beta, while
maximizing: SUM(-ln(v_i) - (u_i ^ 2) / v_i). With the constraints:
- alpha > 0
- beta > 0
- alpha + beta < 1
Note that there is no restriction on omega.

Another method used for estimation is "variance targeting", where one first sets omega
equal to the variance of the time series. This method nearly as effective as the previously mentioned and is less
computationally effective.

One can measure the fit of the time series to the GARCH method by using the Ljung-Box statistic. [3]

See the sources below for reference and for greater detail.

Sources:
[1] Generalized Autoregressive Conditional Heteroskedasticity, by Tim Bollerslev
[2] Finance Compact Plus Band 1, by Yvonne Seler Zimmerman and Heinz Zimmerman; ISBN: 978-3-907291-31-1
[3] Options, Futures & other Derivates, by John C. Hull; ISBN: 0-13-022444-8""",
)
parser.add_argument(
"-v",
"--value",
type=str,
choices=self.choices["garch"],
dest="column",
help="The column and name of the database you want to estimate volatility for",
required="-h" not in other_args,
)
parser.add_argument(
"-p",
help="The lag order of the symmetric innovation",
dest="p",
type=int,
default=1,
)
parser.add_argument(
"-o",
help="The lag order of the asymmetric innovation",
dest="o",
type=int,
default=0,
)
parser.add_argument(
"-q",
help="The lag order of lagged volatility or equivalent",
dest="q",
type=int,
default=1,
)
parser.add_argument(
"-m",
"--mean",
help="Choose mean model",
choices=["LS", "AR", "ARX", "HAR", "HARX", "constant", "zero"],
default="constant",
type=str,
dest="mean",
)
parser.add_argument(
"-l",
"--length",
help="The length of the estimate",
dest="horizon",
type=int,
default=100,
)
parser.add_argument(
"-d",
"--detailed",
help="Display the details about the parameter fit, for instance the confidence interval",
dest="detailed",
action="store_true",
default=False,
)
ns_parser = self.parse_known_args_and_warn(
parser, other_args, EXPORT_BOTH_RAW_DATA_AND_FIGURES
)
if ns_parser:
dataset, column = ns_parser.column.split(".")
econometrics_view.display_garch(
self.datasets[dataset],
column,
ns_parser.p,
ns_parser.o,
ns_parser.q,
ns_parser.mean,
ns_parser.horizon,
ns_parser.detailed,
)

@log_start_end(log=logger)
def call_granger(self, other_args: List[str]):
"""Process granger command"""
Expand Down
70 changes: 70 additions & 0 deletions openbb_terminal/econometrics/econometrics_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
from itertools import combinations
from typing import Any, Dict, Optional, Tuple, Union

from arch import arch_model
import numpy as np
import pandas as pd
import statsmodels.api as sm
from scipy import stats
Expand Down Expand Up @@ -326,6 +328,74 @@ def get_coint_df(
return pd.DataFrame()


def get_garch(
data: pd.Series,
p: int = 1,
o: int = 0,
q: int = 1,
mean: str = "constant",
horizon: int = 100,
):
northern-64bit marked this conversation as resolved.
Show resolved Hide resolved
"""Calculates annualized volatility forecasts based on GARCH.

GARCH (Generalized autoregressive conditional heteroskedasticity) is stochastic model for time series, which is for
instance used to model volatility clusters, stock return and inflation. It is a generalisation of the ARCH models.

GARCH(p, q): = (1 - alpha - beta) sigma_l + SUM(alpha u_{t-1} ^ 2) + SUM(beta sigma_{t-1} ^ 2) [1]

The GARCH-model assumes that the variance estimate consists of 3 components:
- sigma_l; the long term component, which is unrelated to the current market conditions
- u_t; the innovation/discovery through current market price changes
- simgma_t; the last estimate

GARCH can be understood as a model, which allows to optimize these 3 variance components to the time series.
This is done assigning weights to variance components: (1 - alpha - beta) for sigma_l, alpha for u_t and
beta for sigma_t. [2]

The weights can be estimated by iterating over different values of (1 - alpha - beta) sigma_l which we will call omega, alpha and beta, while
maximizing: SUM(-ln(v_i) - (u_i ^ 2) / v_i). With the constraints:
- alpha > 0
- beta > 0
- alpha + beta < 1
Note that there is no restriction on omega.

Another method used for estimation is "variance targeting", where one first sets omega
equal to the variance of the time series. This method nearly as effective as the previously mentioned and is less
computationally effective.

One can measure the fit of the time series to the GARCH method by using the Ljung-Box statistic. [3]

See the sources below for reference and for greater detail.

Sources:
[1] Generalized Autoregressive Conditional Heteroskedasticity, by Tim Bollerslev
[2] Finance Compact Plus Band 1, by Yvonne Seler Zimmerman and Heinz Zimmerman; ISBN: 978-3-907291-31-1
[3] Options, Futures & other Derivates, by John C. Hull; ISBN: 0-13-022444-8

Parameters
----------
data: pd.Series
The time series to estimate volatility from
p: int
Lag order of the symmetric innovation
o: int
Lag order of the asymmetric innovation
q: int
Lag order of lagged volatility or equivalent
mean: str
The name of the mean model
horizon: int
The horizon of the forecast
"""
model = arch_model(
100 * data.pct_change().dropna(), vol="GARCH", p=p, o=o, q=q, mean=mean
northern-64bit marked this conversation as resolved.
Show resolved Hide resolved
)
model_fit = model.fit(disp="off")
pred = model_fit.forecast(horizon=horizon, reindex=False)

return pred.variance.values[-1, :] * np.sqrt(252), model_fit
northern-64bit marked this conversation as resolved.
Show resolved Hide resolved


def get_engle_granger_two_step_cointegration_test(
dependent_series: pd.Series, independent_series: pd.Series
) -> Tuple[float, float, float, pd.Series, float, float]:
Expand Down
71 changes: 71 additions & 0 deletions openbb_terminal/econometrics/econometrics_view.py
Original file line number Diff line number Diff line change
Expand Up @@ -386,6 +386,77 @@ def display_root(
)


@log_start_end(log=logger)
def display_garch(
dataset: pd.DataFrame,
column: str,
p: int = 1,
o: int = 0,
q: int = 1,
mean: str = "constant",
horizon: int = 1,
detailed: bool = False,
export: str = "",
external_axes: bool = False,
) -> Union[OpenBBFigure, None]:
"""Plots the annualized volatility forecasts based on GARCH

Parameters
----------
dataset: pd.DataFrame
The dataframe to use
column: str
The column of the dataframe to use
p: int
Lag order of the symmetric innovation
o: int
Lag order of the asymmetric innovation
q: int
Lag order of lagged volatility or equivalent
mean: str
The name of the mean model
horizon: int
The horizon of the forecast
detailed: bool
Whether to display the details about the parameter fit, for instance the confidence interval
export: str
Format to export data
external_axes: bool
Whether to return the figure object or not, by default False
"""
data = dataset[column]
result, garch_fit = econometrics_model.get_garch(data, p, o, q, mean, horizon)

fig = OpenBBFigure()

fig.add_scatter(x=list(range(1, horizon + 1)), y=result)
fig.set_title(
f"{f'GARCH({p}, {o}, {q})' if o != 0 else f'GARCH({p}, {q})'} annualized volatility forecast"
)

if fig.is_image_export(export):
export_data(
export,
os.path.dirname(os.path.abspath(__file__)),
f"{column}_{dataset}_GARCH({p},{q})",
result,
figure=fig,
)

if not detailed:
print_rich_table(
garch_fit.params.to_frame(),
headers=["Values"],
show_index=True,
index_name="Parameters",
title=f"GARCH({p}, {o}, {q})" if o != 0 else f"GARCH({p}, {q})",
export=bool(export),
)
else:
console.print(garch_fit)
return fig.show(external=external_axes)


@log_start_end(log=logger)
def display_granger(
dependent_series: pd.Series,
Expand Down
7 changes: 4 additions & 3 deletions openbb_terminal/miscellaneous/i18n/en.yml
Original file line number Diff line number Diff line change
Expand Up @@ -968,19 +968,20 @@ en:
econometrics/combine: Combine columns from different datasets
econometrics/rename: Rename column from dataset
econometrics/lag: Add lag to a variable by shifting a column
econometrics/_regression_: Regression
econometrics/_regression_tests_: Regression Tests
econometrics/_panel_: Panel
econometrics/_residuals_: Residuals
econometrics/ols: fit a (multi) linear regression model
econometrics/norm: perform normality tests on a column of a dataset
econometrics/root: perform unitroot tests (ADF & KPSS) on a column of a dataset
econometrics/panel: estimate model based on various regression techniques
econometrics/compare: compare results of all estimated models
econometrics/_tests_: Tests
econometrics/_time_series_: Time Series
econometrics/dwat: Durbin-Watson autocorrelation test on the residuals of the regression
econometrics/bgod: Breusch-Godfrey autocorrelation tests with lags on the residuals of the regression
econometrics/bpag: Breusch-Pagan heteroscedasticity test on the residuals of the regression
econometrics/granger: Granger causality tests on two columns
econometrics/coint: co-integration test on a multitude of columns
econometrics/garch: estimate future volatility with GARCH
portfolio/bro: brokers holdings, supports robinhood, ally, degiro, coinbase
portfolio/po: portfolio optimization, optimize your portfolio weights efficiently
portfolio/load: load transactions into the portfolio (use load --example for an example)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ econometrics
## Exploration

load nile
garch -v nile.volume
desc nile
load nile -a nile_2
eval double_volume = volume * 2
Expand Down
1 change: 1 addition & 0 deletions requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ altair==4.2.2 ; python_version >= "3.8" and python_full_version != "3.9.7" and p
ansiwrap==0.8.4 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
anyio==3.6.2 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
appdirs==1.4.4 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
arch==5.3.1 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
appnope==0.1.3 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11" and sys_platform == "darwin" or python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11" and platform_system == "Darwin"
argon2-cffi-bindings==21.2.0 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
argon2-cffi==21.3.0 ; python_version >= "3.8" and python_full_version != "3.9.7" and python_version < "3.11"
Expand Down