Merge pull request #41 from PR0M3TH3AN/codex/choose-policy-for-lagged_oil_unrate_chart

Clamp trailing UNRATE NaN
This commit is contained in:
thePR0M3TH3AN authored and GitHub committed 2025-06-01 11:09:00 -04:00
commit ae60c19ff7
2 files changed
+19 -24

No files matched your search

+8 -7
View File
@@ -133,10 +133,11 @@ What happens under the hood:
``` ```
(\[Real Python]\[1], \[Software Engineering Stack Exchange]\[2]) (\[Real Python]\[1], \[Software Engineering Stack Exchange]\[2])
3. Converts both series to month‐end indices, resamples oil to a monthly average, and aligns their date ranges. 3. Converts both series to month-end indices, resamples oil to a monthly average, and aligns their date ranges.
4. Validates that neither series is empty, contains `NaN`, or has no overlap (raising a `ValueError` if any issue). 4. Clamps both series to the last month where `UNRATE` has a value so any trailing NaN is removed.
5. Applies the specified lag (e.g., 18 months), then plots UNRATE on the left y‐axis and log‐scaled WTI on the right y‐axis. 5. Validates that neither series is empty, contains `NaN`, or has no overlap (raising a `ValueError` if any issue).
6. Saves the figure to `outputs/lagged_oil_unrate_chart_styled_<timestamp>.png` (unless `--output` is specified). (\[martinheinz.dev]\[4], \[Real Python]\[1]) 6. Applies the specified lag (e.g., 18 months), then plots UNRATE on the left y-axis and log-scaled WTI on the right y-axis.
7. Saves the figure to `outputs/lagged_oil_unrate_chart_styled_<timestamp>.png` (unless `--output` is specified). (\[martinheinz.dev]\[4], \[Real Python]\[1])
#### Customizing the UNRATE vs. Oil Chart #### Customizing the UNRATE vs. Oil Chart
@@ -315,9 +316,9 @@ python-dateutil>=2.8.1
* This indicates that the UNRATE DataFrame has missing (NaN) entries. Possible fixes: * This indicates that the UNRATE DataFrame has missing (NaN) entries. Possible fixes:
1. Drop nulls within SQL—e.g., run `refresh_data.py --end` using the last fully published month rather than “today” (\[devgem.io]\[7], \[pyOpenSci]\[8]) 1. Drop nulls within SQL—e.g., run `refresh_data.py --end` using the last fully published month rather than "today" ([devgem.io][7], [pyOpenSci][8])
2. Forward‐fill or backward‐fill missing UNRATE values in `common.py` before validation (if appropriate) (\[pyOpenSci]\[8], \[Real Python]\[1]) 2. Clamp both series to `UNRATE.last_valid_index()` before validation (the approach used in `lagged_oil_unrate_chart_styled.py`).
3. Comment out the strict null check in `validate_dataframe(...)` (not recommended for publication‐quality charts) (\[devgem.io]\[7], \[Real Python]\[1]) 3. Comment out the strict null check in `validate_dataframe(...)` (not recommended for publication-quality charts) ([devgem.io][7], [Real Python][1])
* **Database not found** * **Database not found**
+11 -17
View File
@@ -3,10 +3,10 @@
lagged_oil_unrate_chart_styled.py lagged_oil_unrate_chart_styled.py
--------------------------------- ---------------------------------
Offline version: reads UNRATE & WTI series from `data/fred.db` Offline version: reads UNRATE & WTI series from `data/fred.db`
(populated by `scripts/refresh_data.py`), forward‐fills any NaNs (populated by `scripts/refresh_data.py`), clamps both series to the
in the UNRATE series, drops remaining NaNs in both series to maintain last month where UNRATE has a valid value, validates that they contain
purity, validates that both series contain data for the requested period data for the requested period (overlap only), and plots them with a
(overlap only), and plots them with a configurable lag. configurable lag.
""" """
from __future__ import annotations from __future__ import annotations
@@ -269,22 +269,16 @@ def main(argv: list[str] | None = None) -> plt.Figure:
raise SystemExit(1) raise SystemExit(1)
# ─────────────────────────────────────────────────────────────────────── # ───────────────────────────────────────────────────────────────────────
# Fetch both UNRATE and oil; UNRATE may contain NaNs if the last # Fetch both UNRATE and OIL. If UNRATE has a trailing NaN for the most
# month’s data has not yet been published. We forward‐fill UNRATE # recent month, clamp both series to its last valid index so that
# (option B), then drop any remaining NaNs in both series. # validation works on officially published data only.
# ─────────────────────────────────────────────────────────────────────── # ───────────────────────────────────────────────────────────────────────
unrate, oil = fetch_series(start_dt, end_dt, args.db) unrate, oil = fetch_series(start_dt, end_dt, args.db)
# Forward‐fill UNRATE to propagate the last known value into any NaN gaps last_date = unrate.last_valid_index()
unrate["value"] = unrate["value"].ffill() if last_date is not None:
# Drop any rows where UNRATE is still NaN (e.g., if the entire series started after 'start') unrate = unrate.loc[:last_date]
unrate = unrate.dropna(subset=["value"]) oil = oil.loc[:last_date]
# Drop any rows in 'oil' where the value is NaN (ensures no Nulls remain)
oil = oil.dropna(subset=["value"])
# Align oil to only dates present in UNRATE after cleaning
oil = oil.loc[oil.index.isin(unrate.index)]
validate_series(unrate, oil) validate_series(unrate, oil)
fig = plot_lagged( fig = plot_lagged(