Files
OpenBB/openbb_platform/extensions/quantitative/openbb_quantitative/helpers.py
Danglewood cd7d602b8f [V5] openbb-quantitative: Refactor for V5 (#7506)
* refactor quantitative for v5

* add factors endpoint and add a few charts

---------

Co-authored-by: deeleeramone <>
2026-05-29 10:46:25 +03:00

59 lines
1.9 KiB
Python

"""Helper functions for the quantitative extension."""
from typing import TYPE_CHECKING
if TYPE_CHECKING:
from pandas import DataFrame, Series
_FAMA_FRENCH_FACTORS_URL = (
"https://mba.tuck.dartmouth.edu/pages/faculty/ken.french/ftp/"
"F-F_Research_Data_Factors_CSV.zip"
)
def get_fama_raw(start_date: str, end_date: str) -> "DataFrame":
"""Download the Fama-French research factors for a date range.
Returns a DataFrame indexed by date with the excess market return ('mkt_rf'),
size ('smb'), value ('hml'), and risk-free ('rf') factors as decimal fractions.
"""
from io import BytesIO
from urllib.request import urlopen
from zipfile import ZipFile
from pandas import read_csv, to_datetime, to_numeric
with (
urlopen(_FAMA_FRENCH_FACTORS_URL) as response, # noqa: S310
ZipFile(BytesIO(response.read())) as archive,
archive.open("F-F_Research_Data_Factors.csv") as handle,
):
df = read_csv(
handle,
header=0,
names=["date", "mkt_rf", "smb", "hml", "rf"],
skiprows=3,
)
df = df[df["date"].apply(lambda value: len(str(value).strip()) == 6)]
df["date"] = to_datetime(df["date"].astype(str) + "01", format="%Y%m%d")
for column in ("mkt_rf", "smb", "hml", "rf"):
df[column] = to_numeric(df[column], downcast="float") / 100
df = df.set_index("date")
if to_datetime(start_date) > df.index.max():
raise ValueError(
f"Start date '{start_date}' is after the last available Fama-French"
f" observation '{df.index.max().date()}'."
)
return df.loc[start_date:end_date]
def validate_window(input_data: "Series | DataFrame", window: int) -> None:
"""Raise a ValueError when the rolling window exceeds the data length."""
if window > len(input_data):
raise ValueError(
f"Window '{window}' is larger than the data length '{len(input_data)}'."
)