Repository navigation
OpenBB V5
OpenBB V5 Changelog
OpenBB V5 is the new major-version line of the kept packages under openbb_platform/ and cli/.
The openbb metapackage is now 5.0.0; the core, CLI, API, MCP server, routers and most providers are 2.0.0; exceptions include openbb-devtools (1.6.8 -> 2.0.1), openbb-charting (3.0.0 -> 4.0.0) and openbb-imf (2.1.3 -> 2.1.2 -> 3.0.0).
The repository license changed from AGPL-3.0-only to Apache-2.0 in #7677, in the root LICENSE, every pyproject.toml and the desktop app.
Eighteen directories present on develop are absent on v5 (sixteen provider packages, the openbb-regulators extension and the test-only extensions/famafrench tree); one provider, openbb-jodi 2.0.0, is new.
Headline changes: hatchling/uv packaging, the openbb-core[pandas] extra, ruff and ty, layered openbb.toml config, OBBStream streaming, decoupled charting, CLI 2.0 with .spec files and codegen, spec-driven platform-api and MCP proxies, provider-owned routers with conditional registration, 16 provider refactors plus the new openbb-jodi provider, package 2.0 releases, the openbb 5.0.0 metapackage, charting 4.0, refreshed extension catalogs and a root-package publishing workflow.
The root openbb metapackage was migrated from Poetry 4.7.3 to hatchling/PEP 621 version 5.0.0 in direct commit 6d8e44100ab; its dependencies now target the V5 package line, router extensions are grouped in the routers extra, poetry.lock was removed and uv.lock added.
Pull requests
Core and packaging
| PR | Merged | Author | Title |
|---|---|---|---|
| #7482 | 2026-04-28 | Danglewood | [Feature] OpenBB V5: Initial openbb-core Refactor |
| #7484 | 2026-04-30 | Danglewood | [V5] openbb-core: 100% Test Coverage |
| #7492 | 2026-05-07 | Danglewood | [V5] openbb-core: Add Backwards-Compatible Layered Config System (openbb.toml) |
| #7537 | 2026-06-18 | Danglewood | [V5] [BugFix] Fix for Breaking Changes in FastAPI 0.137+ |
| #7524 | 2026-06-22 | Danglewood | [V5] Refactor Shared Pass Through Router Extensions For Hatchling |
| #7264 | 2026-09-24 | Boris Li | Enterprise Flask Migration Toolkit |
| #7622 | 2026-09-25 | Dex Hunter | perf(core): vectorize the date conversion in basemodel_to_df |
| #7681 | 2026-09-26 | Danglewood | [Release] openbb-core-v2.0.0rc1: Testing Publish Pipeline |
CLI
| PR | Merged | Author | Title |
|---|---|---|---|
| #7433 | 2026-06-01 | Danglewood | [V5] CLI 2.0 - Pluggable Backends, Non-TTY Default, HTTP Dispatcher, Spec Files + Codegen |
| #7586 | 2026-07-14 | Dex | fix(cli): resolve modular OpenAPI references |
| #7589 | 2026-07-14 | Danglewood | [V5] openbb-cli: Modular OpenAPI Refs |
| #7597 | 2026-07-20 | Monte Hoover | Update generated tests to get python parameter names instead of raw API-provider parameter names. |
| #7598 | 2026-07-20 | Monte Hoover | Update the record-vs-envelope heuristic in the payload processing code to not treat a record that happens to have a list datatype as an entire envelope. |
| #7599 | 2026-07-20 | Monte Hoover | Update class generation code to handle empty data that php-style serialization emits as []. |
| #7606 | 2026-09-25 | Lucas Zimmermann | fix(cli): inherit path-item-level OpenAPI parameters |
API, MCP and streaming
| PR | Merged | Author | Title |
|---|---|---|---|
| #7494 | 2026-06-20 | Danglewood | [V5] openbb-platform-api: Refactor for V5 Spec, Config, Packaging, Test Coverage |
| #7530 | 2026-06-22 | Danglewood | add full support for AsyncIterator response type for streaming output |
| #7495 | 2026-09-24 | Danglewood | [V5] openbb-mcp-server: Refactor for v5 - Spec, Config, Packaging, Test Coverage |
Charting and toolkit extensions
| PR | Merged | Author | Title |
|---|---|---|---|
| #7507 | 2026-05-29 | Danglewood | [V5] openbb-news: Refactor News for V5 and Add Configurable RSS Endpoint |
| #7506 | 2026-05-29 | Danglewood | [V5] openbb-quantitative: Refactor for V5 |
| #7502 | 2026-05-29 | Danglewood | [V5] openbb-technical: Refactor for V5 & Add More Quick Win Endpoints |
| #7505 | 2026-06-01 | Danglewood | refactor econometrics for v5 |
| #7545 | 2026-07-01 | Danglewood | [V5] openbb-charting: Refactor for V5 and Decouple |
| #7602 | 2026-07-23 | Danglewood | add drugs.com and brutalist as news rss feeds |
Providers — refactors and additions
| PR | Merged | Author | Title |
|---|---|---|---|
| #7413 | 2026-05-15 | Danglewood | [V5] Refactor openbb-oecd for full SDMX 2 API Exposure and V5 Packaging |
| #7509 | 2026-05-25 | Danglewood | [V5] openbb-oecd: Rename oecd_utils as oecd |
| #7508 | 2026-05-29 | Danglewood | [V5] openbb-imf: Refactor for V5 |
| #7518 | 2026-06-01 | Danglewood | [V5] openbb-bls: Refactor for V5 + Add Many Endpoints |
| #7503 | 2026-06-01 | Danglewood | [V5] openbb-famafrench: Refactor for V5 |
| #7528 | 2026-06-08 | Danglewood | [V5] openbb-congress-gov: Refactor for V5 + Convert To Using Bulk Files Instead of api.congress.gov. |
| #7560 | 2026-09-23 | Danglewood | [V5] openbb-ecb: Refactor for V5 and Expand Coverage |
| #7561 | 2026-09-23 | Danglewood | [V5] openbb-federal-reserve: Refactor for V5 + FFIEC & Regional Fed Routers |
| #7584 | 2026-09-23 | Danglewood | [V5] openbb-eia: Refactor for V5 + Add Full API Implementation |
| #7604 | 2026-09-23 | Danglewood | [V5] openbb-government-us: Refactor for V5 + Move uscongress |
| #7593 | 2026-09-23 | Danglewood | [V5] Feature: Add JODI World Oil & Gas Database |
| #7615 | 2026-09-23 | Danglewood | [V5] openbb-cftc: Refactor for V5 + Add OIS, Forward Curve, and FX Trade Analysis |
| #7668 | 2026-09-23 | Danglewood | [V5] openbb-tmx: Refactor extension for V5 |
| #7670 | 2026-09-23 | Danglewood | [V5] openbb-nasdaq: Refactor provider for V5. |
| #7669 | 2026-09-23 | Danglewood | [V5] openbb-fred: Refactor as V5 extension. |
| #7617 | 2026-09-23 | Danglewood | [V5] openbb-cboe: Refactor for V5 + Add Payoff Diagrams |
| #7674 | 2026-09-23 | Danglewood | [V5] openbb-deribit: Refactor provider for V5 |
| #7525 | 2026-09-24 | Danglewood | [V5] openbb-sec: Refactor for V5 |
| #7676 | 2026-09-24 | Danglewood | [V5] openbb-finra: Refactor for V5 |
Provider removals
| PR | Merged | Author | Title |
|---|---|---|---|
| #7486 | 2026-05-29 | Danglewood | remove stockgrid provider |
| #7485 | 2026-05-29 | Danglewood | [V5] remove wsj provider and related code |
| #7523 | 2026-06-01 | Danglewood | delete biztoc |
| #7522 | 2026-06-01 | Danglewood | [V5] Remove openbb-alpha-vantage |
| #7521 | 2026-06-01 | Danglewood | [V5] Remove openbb-benzinga |
| #7570 | 2026-07-08 | Danglewood | remove seeking alpha provider |
| #7573 | 2026-07-08 | Danglewood | remove tradier provider |
| #7574 | 2026-07-08 | Danglewood | remove tiingo provider |
| #7575 | 2026-07-08 | Danglewood | remove intrinio provider |
| #7576 | 2026-07-08 | Danglewood | remove yfinance provider from repo |
| #7577 | 2026-09-14 | Danglewood | remove finviz |
| #7578 | 2026-09-14 | Danglewood | remove trading economics provider |
| #7610 | 2026-09-14 | Danglewood | remove openbb-multpl from repository |
| #7665 | 2026-09-14 | Danglewood | remove fmp provider extension from repository |
| #7675 | 2026-09-23 | Danglewood | remove openbb-econdb provider |
License and repository tooling
| PR | Merged | Author | Title |
|---|---|---|---|
| #7677 | 2026-09-24 | Danglewood | [V5] Update Repository License to Apache 2.0 |
Direct commits
Commits on v5 that are not squash-merged PRs, deduplicated across packages. Bodies are available with git log -1 --format=%B <sha>.
932a895a069fix cli renderer helper with figure object JSON (addsPackageBuilder._distribution_version, the CLI figure renderer and_display_dict_result)1fa72f80d72test coverageaba09afb1c5fixes for docstring generation (_normalize_code_annotations,ruff --fix-only, dev_install refinements,.build.lockgitignored)1cbb24d8b7abump devtools and repoint pyproject.toml (openbb-devtools 2.0.0 -> 2.0.1 across 35 consumer pyprojects; editable devtools path source removed from the CLI and router extensions)4fe1bbcb94ffix tag grouping in swagger docs (composite tags,x-tagGroups,docExpansion: none)35ce305fba9fix charting conftest and missing coverage in 3.1034716a17f38unpin ruff (also thread-safeSingletonMeta, reference.json regeneration)90d427c5a52restore test coverage to 100% in openbb_cored8fd8f06da4some ty items and add requests-types stubs for ty in devtoolscaf49e818cbFieldInfo import38d636a7a6flinter976a4fd098efix test driftf56a44ec0cebump dependenciese79623ceef0remove comment chatter3a2bfbcbafdunpack POST parameters from params: Modelb455cf240a3fix docstring generator and body param unwrapping70bbf37caaatest_system_settingsa18a2921311ruff UP0073a978b654caupdate for deprecated pydantic syntax (SystemSettingsinstance-modemodel_validator)f18493c293bmissing coveragef899588da97fix docstring generator for nested models73b05163667package builder fixes5f4dda273b8fix the figure font when rendered (strip_theme_colorsin the CLI)a07534cfa4afix ty check failures exposed by newer version2c14e26acfbfixes for ty99e5c8618e2fix new ty issues1ad72fd756aunused ty ignoredc71797e063fix lint errors (addsPLR0917to ruff ignores in several packages)d0090d60dcdfix lint errors (JsonDictannotations,list(...)choices in federal_reserve, bls, cftc, tmx, finra)478235ca196fix oecd lint error5b1bc33e579update pre-commit, noxfile, and uv locks (rewrote.pre-commit-config.yaml,noxfile.py,dev_install.py, the platform README and 35uv.lockfiles)ab707f2fe88refactor cookiecutter78ee668a2a2bump cookiecutter packagge version (0.6.0 -> 1.0.0)768e52c6358fix merge widgetsbf0cb48465fmarkdown linting2c81a8cbb10fix markdown lint errors9bbc49675d4consolidate lint job14c0042f784general lint setup0980d4f1e11fogot that file74d9b58623bgeneral-lintingc06074f1dd7workflow cleanup"04825708836remove v4 platform workflow5d376a44141remove that annoying labeler actionfd98854bf39also run integration test in CIb9730ad658aopenbb-core publish workflowb6c2c79a0f0actions39e85422fe7actionsfae87660088fix publish workflows (checkout refdevelop-> merge commit SHA in 29 publish workflows)9b0e799148fproject ty.toml fileb6b472a511dcodespell0ff1a54706ecodespell30f84a3e811charting pyproject version67ebf4a4652plotly 7 handling for mapbox namespace changea2a1456dbcafix for plotly 7 breaking change to schemasb59b2b18bd2add charting coveragefbcd512905eremove integration tests from extensions that were moved into the famafrench provider (deletesextensions/famafrench)89b8c00b338downgrade aiohttp in devtools for vcrpy (later reverted by21ed5fe3672)21ed5fe3672add httpx2 to devtools for starlette test client0aa60395322missing test coverage that appeared in famafrench..32b6d4a2802fix warnings raised by federal_reserve on some xlsx workbook parsing7a70de9b722fix sec test by adding fixture (XBRL linkbase retry and offline Apple 10-K fixtures)07bf0873ae5fix desktop environments testf0258c93366fix publish workflows with missing tag job, some tests and bump fastapi (adds a tag job to 31 publish workflows;fastapi>=0.136.3->>=0.137.2,aiohttp>=3.13.3->>=3.14.2;openbb-coredev group gainspandas,pycountry,bs4,polars; new coverage forextension_loader.py,ast_analysis.py/introspector.py/loader.py,build.py,update_country_data.py,update_exchange_data.py;OpenBBField.choicestyped asJsonValue;reference_generator.pyregex-match fix; version2.0.0rc1->2.0.0)4d5017ad4d9fix python 3.10 test failure in core (test_build.py: assertSystemExitinstead of mockingsys.exit, which Python 3.10's CI run didn't intercept)45feafe11a3actually fix python 3.10 test failure in core (test_build.py: reorders the@patch("builtins.__import__")/@patch("...subprocess.run")stack — on Python 3.10,unittest.mock's dotted-target resolver calls the bare__import__builtin, so with the wrong decorator order the already-patched__import__interceptedsubprocess.run's own target resolution and let the real subprocess execute; fixed on 3.14+ only becauseunittest.mockthere resolves targets viapkgutil.resolve_nameinstead)220ffb7798aMerge origin/develop into v5 (ours strategy: keep v5 as source of truth) — kept v5's copy ofopenbb_platform/pyproject.tomlanddesktop/package.json, discarding develop's pin bumps86e0787e595Merge develop into v5 (resolve conflicts in favor of v5)ba81abcbc0dmerge branch develop (conflict resolution raised the devtoolstyfloor from>=0.0.1a14to>=0.0.40)4fe1a41ed78,7007a878db1,7fd1d89d52c,074842ed4f9merge branch develop
Cross-cutting patterns
- Packaging: every package moved from Poetry to hatchling with a PEP 621
[project]table,[dependency-groups] dev = ["openbb-devtools>=2.0.1"], a committeduv.lockand nopoetry.lock. The follow-up release work removed localopenbb-coresource overrides so standalone package builds resolve core 2.0.0 from PyPI. Evidence: openbb-core, openbb-cli,
openbb-platform-api, openbb-mcp-server, openbb-technical, openbb-quantitative, openbb-econometrics, openbb-charting, the nine pass-through routers, openbb-news, openbb-devtools, all 17 providers, openbb-cookiecutter. - Core dependency floors: packages that use pandas declare
openbb-core[pandas]>=2.0.0(cli, technical, quantitative, econometrics, charting, news, bls, cboe, cftc, deribit, ecb, us-eia, famafrench, federal-reserve, finra, fred, government-us, imf, jodi, nasdaq, oecd, sec, tmx); the nine routers,
platform-api and mcp-server declare plainopenbb-core>=2.0.0.pandasitself is an optional extra of openbb-core andrequire_optional("pandas")raisesOpenBBErrorwith an install hint when absent. - Lint and type checking: ruff is the only formatter and linter (
select = ["D","E","W","F","S","UP","I","PLC","PLE","PLR","PLW","SIM","T20"],pydocstyle convention = "numpy",line-length = 88) andtythe only type checker ([tool.ty]per package, rootty.toml), with# ty: ignore[code]
replacing blanket# type: ignore..pylintrcis deleted and# pylint: disabledirectives were stripped from core, cli, platform-api, mcp-server, technical, econometrics, the routers, news, deribit, cftc, sec and most providers (leftovers:openbb_core/app/config/loader.py, quantitative
views/*.py, cboefutures_curve.py, 22 tmx model files,validate_corpus.pyin sec). - Docstrings: numpy style with
Parameters/Returns/Raisessections on public functions;PythonExexamples that named removed providers were dropped from quantitative and most econometrics commands. - Test conventions:
class TestXsuites in role-named files; real installable fixture extensions instead of mocks (openbb-fake-integrationin core's integration suite,openbb-cli-fakein the CLI conftest,openbb-mcp-fixturein mcp-server); offline unit suites driven by monkeypatched
transports or JSON fixtures (deribit, finra, nasdaq, tmx, jodi, bls, news); VCR cassettes kept where they still fit (fred, oecd, imf, ecb, famafrench, cftc, sec, us-eia, government-us); live checks moved tointegration/packages behind anintegrationmarker with an in-process uvicorn fixture
(technical, quantitative, econometrics, charting, news, cboe, cftc, deribit, ecb, famafrench, finra, jodi, nasdaq, oecd, tmx, government-us, fred). - 100% coverage gate:
pytest tests --cov=<pkg> --cov-fail-under=100in the 22test-unit-openbb-*.ymlprovider and extension workflows plustest-unit-mcp-server.yml(branch coverage there), with# pragma: no coverreserved for annotated unreachable branches; core, cli and platform-api have
per-package test workflows without the fail-under flag. - Per-package CI and release: a
test-unit-openbb-<pkg>.yml(build once withuv build --no-sources, ruff check, ruff format --check,ty check, a 9-cell Python 3.10-3.14 OS matrix) and apublish-openbb-<pkg>.ymlgated on a mergedrelease/openbb-<pkg>-v<version>branch whose name must match
[project].version, a PyPI existence check and trusted publishing; 35 publish workflows exist on v5, with none for openbb-devtools or openbb-cookiecutter. - Layered
openbb.tomlconfiguration: the core loader from #7492 (load_layered_config,load_config,.envfiles,OPENBB_*promotion) is reused by openbb-cli ([tool.openbb-cli],[specs.<ns>],[settings]), openbb-platform-api
(--config-file,[launcher],[env],[middleware],[spec]), openbb-mcp-server ([mcp],[mcp.spec],[mcp.auth],[mcp.middleware],[env]), openbb-news ([news.rss_feeds],[news.rss_providers]) and theopenbb-secconsole script (cache_directory). - Spec files: the CLI writes
.specdocuments (SPEC_VERSION = 5,content_sha256integrity hash); openbb-platform-api (--spec,[spec]) and openbb-mcp-server (--spec,[mcp.spec]) synthesize aiohttp-backed proxy FastAPI apps from them with the same integrity, header-injection and zero-time
date-trimming behavior;--generate-extensionturns a spec into an installable hatchling extension. - Streaming: core's
OBBStream,Fetcher.stream_data,text/event-streamroute registration andStreamingResponsewrapper (#7530); the CLI follows SSE streams in one-shot and REPL modes and generates streaming fetchers; the platform-api
widgets builder skips event-stream routes. - Charting decoupling (#7545): core resolves the engine through
ChartingManagerand theopenbb_charting_backend/openbb_charting_hooksentry-point groups, withcharting_extension/charting_backendsystem settings; views in the routers
loadopenbb_chartingthroughimportlib.import_moduleand technical moved its imports inside functions; openbb-charting is a dev-group dependency only for technical, quantitative and econometrics, an optional extra for the CLI, cboe and tmx; newopenbb_charting_extensionregistrations come
from openbb-quantitative (QuantitativeViews) and openbb-imf (ImfViews). - Provider-owned routers with conditional registration: providers ship an
openbb_core_extensionrouter (new on bls, cboe, deribit, ecb, us-eia, finra, fred, jodi, nasdaq, sec, tmx, government-us; replaced on federal-reserve; renamed on imf and oecd) and usefind_spec("openbb_<extension>")flags
so standard-model fetcher keys stay standard when the owning extension is installed and switch toProvider*aliases plus fallback commands when it is not (bls, cboe, deribit, ecb, federal-reserve, finra, fred, imf, nasdaq, oecd, sec, tmx); us-eia and government-us gate only the fallback commands and keep standard keys. - POST body models: data-processing commands take a single
params: XxxQueryParamsargument and return typedDatarows; core'sMethodDefinition.query_params_modelunpacks the model into kwargs for the static package andfilter_inputsrepacks it; every such QueryParams carries__category__
and__output_columns__(technical, quantitative, econometrics). - Request and response plumbing: on-disk
diskcachestores under the user cache directory withOPENBB_<PKG>_*overrides (cftc, ecb, federal-reserve, fred, government-us, sec, tmx) and a persisted static-asset proxy cache under<user cache>/eia_proxy/in us-eia; sharedaiohttp-client-cacheSQLite backends with per-URL TTLs and size sweeps (cboe, deribit, nasdaq,
tmx); per-event-loop pooled aiohttp sessions (deribit via aloop.closehook, tmx closed by the router lifespan); a sharedcurl_cffiChrome-impersonating session helper for bot-managed hosts (federal-reserve, government-us, tmx, us-eia); a process-wide EDGAR rate limiter (sec);AnnotatedResultmetadata for units,
sources and assessments (cftc, jodi, oecd, nasdaq, econometricsgarch). - Workspace metadata lives in code:
widget_config=on@router.command,x-widget_configinjson_schema_extra(endpoint-backed dropdowns,cellOnClick/groupBy,chartDataType),x-unit_measurement/x-frontend_multiplyon rate fields, and a bundledassets/apps.jsonserved at
/<provider>/apps.jsonwith widget-id rewriting when the owning extension is absent; committedwidgets.jsonfiles exist only in sec and federal-reserve. - Static assets are real files under
assets/loaded viaPath(__file__)with single-pass token substitution (clifigure.html, us-eiadata_browser.htmlandrss_feed.html, government-us HTML widgets, tmx screener builder, secfiling_viewer_app.html, ecb, federal-reserve and finra JSON
assets). - Build-time generated catalogs: hatch custom build hooks materialize generated assets from live APIs when absent (gitignored
bls_cache.zip,ecb_cache.json.xz,eia_catalog.json.xz,imf_cache.json.xz;oecd_cache.json.xz, claimed gitignored without a matching rule; finra's committedsecurity_types.json.gz) withgenerate-<pkg>-cache/generate-*console
scripts andOPENBB_<PKG>_FORCE_*_REBUILDenv flags; CI seeds the asset from the built wheel and caches it by the generator script hash. - MCP: openbb-mcp-server switched to stateless BM25 tool discovery with
search_tools/call_tooland arun_pipelinechaining tool; us-eia and sec ship per-extension FastMCP servers that run as subprocesses and are reverse-proxied through the provider router with aDepends-injected plain dict
instead of aRequest. - License:
license = { text = "Apache-2.0" }in everypyproject.toml,APISettings.license_name = "Apache-2.0", Apache text in the root and desktopLICENSEfiles.
Removals
Removed packages (present on develop, absent on v5):
| Package | Last develop version | Removed by | Where the functionality went |
|---|---|---|---|
| openbb-alpha-vantage | 1.6.1 | #7522 | none |
| openbb-benzinga | 1.6.1 | #7521 | none |
| openbb-biztoc | 1.6.1 | #7523 | none |
| openbb-congress-gov | 1.2.3 | #7604, after the in-place refactor in #7528 | openbb-government-us: openbb_government_us.congress, provider name congress_gov, router uscongress and command paths preserved; data now from GovInfo bulk files |
| openbb-econdb | 1.5.1 | #7675 | none |
| openbb-finviz | 1.5.1 | #7577 | none |
| openbb-fmp | 1.6.1 | #7665 | none |
| openbb-intrinio | 1.6.1 | #7575 | none |
| openbb-multpl | 1.3.1 | #7610 | none |
| openbb-regulators | 1.6.2 | #7525 | openbb-sec router: the eight obb.regulators.sec.* commands are now obb.sec.* / /api/v1/sec/* |
| openbb-seeking-alpha | 1.6.1 | #7570 | none |
| openbb-stockgrid | 1.6.1 | #7486 | none |
| openbb-tiingo | 1.6.1 | #7574 | none |
| openbb-tradier | 1.5.1 | #7573 | none |
| openbb-tradingeconomics | 1.6.1 | #7578 | none |
| openbb-wsj | 1.6.1 | #7485 | none; the etf.discovery sub-router it served was deleted with it |
| openbb-yfinance | 1.6.3 | #7576 | none |
extensions/famafrench (integration tests only, no pyproject) |
n/a | direct commit fbcd512905e, after #7503 |
providers/famafrench/integration/ (rewritten; test_famafrench_factor_choices dropped) |
The early removal PRs (wsj, stockgrid, benzinga, alpha-vantage, biztoc) also pruned assets/extensions/provider.json, dev_install.py, README rows and router examples; the later ones touched only their provider directory, so v5 still carries provider.json entries for eleven removed packages, all
seventeen removed distributions in openbb_platform/poetry.lock, fmp/econdb/congress-gov in the desktop installer's alwaysInclude list, a yfinance smoke test in build/pypi/openbb_platform/publish.py, and 164 router APIEx examples plus 395 integration-test parameter sets naming removed
providers, plus regulators references in the mcp_server README and platform_api test fixtures, removed-provider samples in core docs (core/README.md, config/loader.py), the examples/ tree, the mcp_server README, the use_openbb_cli skill, mcp_server help strings (cli_tools.py,
pipeline.py), the platform_api provider display-name map (utils/widgets.py) and PythonEx/docs examples in openbb-technical and openbb-charting.
Removed commands, models and modules inside kept packages:
- openbb-core: the
html5libdependency;Linters.black()(Linters.runacceptsLiteral["ruff"]only);LoggingSettings.user_id,user_email,user_primary_usageand the%(userId)slog-prefix field (nohub_sessionreference remains);integration/test_obbject.py;poetry.lock. - openbb-core standard models (from #7669):
BondIndicesDatalostsymbolandvalue;CommercialPaperDatalostsymbol,maturity,rate,title;MortgageIndicesDatalostsymbol,name,rate;SpotRateDatalostrate. Each now
carries onlydateplus one column per requested series. - openbb-cli:
Settings.HUB_URLandSettings.BASE_URL(and the--devrepointing);exe --urland the OpenBB Hub routine download path (ROUTINE_DEFAULT_FILES,ROUTINE_PERSONAL_FILES);record --public/-pandSESSION_RECORDED_PUBLIC; the module-levelPLATFORM_ROUTERSdict;pytz; every
directopenbb_chartingimport; rich-table row/column truncation and the "Allowed number of rows/columns exceeded" notices;MenuText._format_cmd_nametruncation; the top-levelsystemREPL command; thefastapi = "0.136.3"pin;poetry.lock. - openbb-platform-api: the bundled "Example BLS App" dashboard in
assets/default_apps.json(removed by #7518); the README tutorial sections (Markdown/Table/Metric Widget, Query Parameters, Easy Date Picker, Annotated Query Params, Annotated
Table Fields, Export apps.json, Installation, Usage, Launch Custom App); the pandas import inOmniWidgetResponseModel.validate_model. - openbb-mcp-server: the admin tools
activate_tools,deactivate_tools,activate_category;ToolInfo.active;CategoryIndex.has_tool(); settingscache_expiration_seconds,on_duplicate_tools,on_duplicate_resources,on_duplicate_prompts,resource_prefix_format,dependencies,
deprecation_warningsand their env aliases;TokenAuthProvider.authorize()and itsresource_server_url/authorization_url/token_url; the default exclusion ofeconometrics,quantitative,technicalfrommodule_exclusion_map;ProcessedRouteData.removed_routes(renamed
excluded_routes);key:valuedict parsing in the CLI parser; theEnv()instantiation inparse_args;tests/app/test_tool_execution.py,tests/utils/test_compress_schema.py,poetry.lock. - openbb-technical:
openbb_technical/technical_router.py(all 27 commands moved toindicators/,signals/,multi/);kc.mamodevalueswma,hma,zlma; theDMP_<n>/DMN_<n>columns ofadx(moved to the newdiendpoint);fibfieldsmin_date,max_date,min_pr,max_pr,
lvl_text; the forward-projectedspan_*rows ofichimoku; the string-formattedr^2/fit_coef/factorcolumns ofclenow;tests/test_technical_helpers.py;poetry.lock. - openbb-quantitative:
openbb_quantitative/quantitative_router.py; theperformance/,rolling/,stats/sub-router packages (now flat modules);openbb_quantitative/models.py(TestModel,NormalityModel,ADFTestModel,KPSSTestModel,UnitRootModel,OmegaModel,SummaryModel,
CAPMModel);openbb_quantitative/statistics.py(helpers moved to private_stats_helpers.py); the unusedpandas-ta-openbbdependency;unitroot_test(fuller_reg="nc"); allPythonExexamples;poetry.lock. - openbb-econometrics:
openbb_econometrics/econometrics_router.py; theOLSRegressionResultspydantic model; thepandas-ta-openbbdependency; six of ninePythonExexamples (kept oncorrelation_matrix,ols_regression,variance_inflation_factor);poetry.lock. - openbb-charting:
poetry.lock; the 29-test live-network API and Python integration suites (replaced by five deterministic in-process cases); the Examples/Methods docstring sections onCharting.to_chart,OpenBBFigureandPlotlyTA;Charting._extension_views(replaced by lazy
_get_extension_views()). - Pass-through routers:
obb.etf.discovery.gainers,obb.etf.discovery.losers,obb.etf.discovery.active(modelsETFGainers,ETFLosers,ETFActive, wsj-only) and theopenbb_etf.discoverysubpackage; the Python-sidetest_equity_shorts_short_volume; benzinga, stockgrid and alpha_vantage
examples and test cases; all# pylint:/# flake8:/# noqa: PLR0912directives;poetry.lockin all nine. - openbb-news:
obb.news.worldno longer resolves (no v5 provider implementsWorldNews, so core drops the route);obb.news.companykeeps only the tmx and nasdaq providers, both gated on openbb-news being installed; the benzinga examples; the developtest_news_world/test_news_company
integration tests;poetry.lock. - openbb-devtools:
pylint,mypy,black,poetry,pytest-freezegun; theruff<0.16ceiling;poetry.lock. - openbb-bls: the 27 static
assets/*_series.xz/*_codes.jsonfiles andbls_assets.json; helpersget_survey_asset,download_category_series_ids,open_asset,update_static_asset; theEIsurvey from thecpicategory (nowixp); thechoiceslist onBlsSearchQueryParams.category;
poetry.lock. - openbb-cboe: the module-level
ConstituentsEuLiteral inmodels/index_constituents.py; unconditionalEtfHistoricalregistration (now only when openbb-etf is installed);poetry.lock. - openbb-cftc: the
COT/COTSearchfetcher keys (renamedCftcCot/CftcCotSearch); the standard-model base classes of the COT models;CftcCotSearchData.__alias_dict__entriesunits/commodity; theHYPERLIQUIDspecial case; the/cftc/get_cot_choicesroute (now/cftc/cot_choices); the
startup lifespan prefetch;reports_dictinutils/__init__;openbb-platform-apias a runtime dependency;poetry.lock. - openbb-deribit:
DERIBIT_OPTIONS_SYMBOLS,OptionsSymbols,DERIBIT_FUTURES_CURVE_SYMBOLS,FuturesCurveSymbols,get_ticker_data,check_ohlc_symboland theasync_lruimport inutils/helpers.py; theasync-lrudependency; the five VCR cassettes andtests/test_deribit_fetchers.py;
every# pylint:directive;poetry.lock. - openbb-ecb:
utils/ecb_helpers.pyandget_series_data; all use of thedata-detail-apiendpoint; the aiohttp SQLite yield-curve cache; theassets_issuer_sector_mfi/_government/_otherportfolio-investment series;poetry.lock. - openbb-us-eia:
utils/total_energy_map.json; the README "OpenBB Hub" credentials section and hand-written WPSR/STEO tables; the hand-maintainedWpsrCategoryChoices/WpsrTableChoiceslists (now derived from the Literal types); every# pylint: disabledirective;poetry.lock. - openbb-famafrench: the misspelled
famafranchentry-point key;poetry.lock; thefactor_choicesintegration tests. - openbb-federal-reserve: fetcher keys
SvenssonYieldCurveandTotalFactorProductivity(TFP re-homed atsf/total_factor_productivity; theeconomyandfixedincomerouters still declare both models with no provider);openbb_federal_reserve/router.py; theopenbb-economyand
openbb-fixedincomedependencies; the "Svensson Yield Curve" and "Total Factor Productivity" apps.json tabs;poetry.lock. - openbb-finra:
utils/data_storage.py(sqlite short-volume cache); helpersget_finra_weeks,get_finra_data,get_full_data,aget_finra_weeks,aget_finra_data,aget_full_data,get_adjusted_date,get_short_interest_dates; the VCR cassettes andtests/test_finra_fetchers.py;
poetry.lock. - openbb-fred: the synchronous
Fredclient (utils/fred_base.py);utils/ice_bofa_indices.csvandget_ice_bofa_series_id;get_cp_series_id,get_cpi_options; theYIELD_CURVE_*constants exceptYIELD_CURVES;FREDCommercialPaperData.asset_type;FredBondIndicesData.maturity/title;
FREDSpotRateData.__alias_dict__andvalue_validate; the repo-levelproviders/fred/py.typed;poetry.lock. - openbb-government-us: the
government_usprovider and entry point; theGovernmentUs*/GovernmentUS*fetcher classes andopenbb_government_us.models;CommodityPsdReportparamscommodity/year/month;use_cacheon committee documents;bill_url/amendment_url(now
bill_id/amendment_id); the Congress.gov-API-only sections ofcommittee_infomarkdown; congress.gov URLs inamendment_text; six of the eight congress VCR cassettes;poetry.lock. - openbb-imf: the
imf_utilsentry point and every/imf_utils/*route; the HTML/rawmode ofpresentation_table; the pickledassets/imf_cache.pkl.gz; the monolithicutils/metadata.py; the hardopenbb-platform-apiandopenbb-economydependencies;integration/test_imf_utils_*.py;
poetry.lock. - openbb-nasdaq: the
TopRetailfetcher (the standard model now has no provider);openbb_nasdaq/app.pyand its routes;utils/query_params.py(DataLinkQueryParams); theapi_keycredential and Quandl instructions; thenasdaq-data-linkandopenbb-platform-apidependencies; all VCR
cassettes,tests/record/expected_*.json,tests/test_nasdaq_app.py,tests/test_nasdaq_fetchers.py; theNasdaqCalendarIpoDataalias dict and validators;poetry.lock. - openbb-oecd:
CustomHttpAdapter,get_legacy_session,fetch_data,oecd_xml_to_df,parse_url,check_cache_exists_and_valid,write_to_cache,query_dict_to_path,get_possibly_cached_data; everyCOUNTRY_TO_CODE_*/CODE_TO_COUNTRY_*map; thedefusedxmldependency; theCountries
Literal on the CLI query;poetry.lock. - openbb-sec: the
aiohttp-client-cache/aiosqlitedependencies and everyCachedSessionblock; the Form 4 SQLite cache and its helpers;FISCAL_PERIODS/FISCAL_PERIODS_DICT; thehmrc-dpltaxonomy choice;SecRssLitigationData.published/summary/link; the "No valid forms provided"
validation;poetry.lock. - openbb-tmx:
get_data_from_gql,get_random_agent,get_companies_backend,get_indices_backend,response_callback; the lowercase*_query/*_payloaddicts inutils/gql.py(includinggetIndexBySymbolandgetIndexPriceHistory); thebackendargument ofget_data_from_url; all 23 VCR
cassettes andtests/test_tmx_fetchers.py;poetry.lock. - Repository:
.pylintrc; the black, ruff-pre-commit, pydocstyle, mirrors-mypy, pylint and codespell-project pre-commit hooks;general-linting.yml(renamed and rewritten aslint-openbb-platform.yml);test-unit-platform.yml; the srvaroa labeler step and.github/labeler.yml;
publish-/test-unit-openbb-congress-gov.yml; cookiecutterpoetry.lock,MANIFEST.in,cookiecutter.jsonand the template's.coveragerc,.secrets.baseline,pytest.ini,ruff.toml,routers/depends.py,models/ohlc_example.py.
Breaking changes
Grouped by package. Packaging, license and dependency-floor changes are listed once per package; the per-package sections below carry the full detail.
openbb-core
- Poetry to hatchling/PEP 621 (1.6.13 -> 2.0.0);
pandasmoved to theopenbb-core[pandas]extra, soOBBject.to_dataframe/to_polars/to_numpy,basemodel_to_df,Metadata,Fetcher.testand pandas-backed validators raiseOpenBBErrorwith an install hint when pandas is absent. - Dependency floors: uvicorn
>=0.48.0, fastapi>=0.137.2(exact pin dropped; raised from the initial>=0.136.3byf0258c93366— core'sroute_iter.pyuses the private_IncludedRouter/.effective_route_contexts()API from FastAPI's 0.137.0 router-inclusion refactor), requests>=2.34.2, pyjwt>=2.13.0, pydantic>=2.12.3,<3.0.0, aiohttp>=3.14.2(raised from>=3.13.3by the same commit), python-multipart>=0.0.29, ruff>=0.15, plustomli>=2.0.0on Python <3.11;html5libdropped. - License AGPL-3.0-only -> Apache-2.0 and
APISettings.license_namedefault"AGPLv3"->"Apache-2.0"(visible in the served OpenAPI info block). OBBject.to_llm()is annotated-> strand returns"[]"for empty JSON;OBBject.to_polars()raisesOpenBBErrorinstead ofImportErrorwhen polars is missing.openbb_core/api/router/commands.pyno longer importsChartingfromopenbb_charting;Charting = ChartingManager.get_charting_class(); the missing-charting error text is now "No charting extension is installed. Installopenbb-chartingor setsystem_settings.charting_extensionto your
engine."Linters.run()accepts onlylinter: Literal["ruff"]; generated-package linting runsruff check --fix-only --unsafe-fixes.LoggingSettingslostuser_id,user_email,user_primary_usage; the log prefix format lost%(userId)s.SingletonMetais no longerGeneric[T];Credentials.show()now unmasks rawSecretStrvalues and prints only declared fields.- Standard models
BondIndicesData,CommercialPaperData,MortgageIndicesData,SpotRateDataaredate-only wide layouts (fields listed under Removals); seven standard-model fields became Optional (CompositeLeadingIndicatorData.value,CountryInterestRatesData.date/.value,
FuturesCurveData.price,GdpNominalData.country,GdpRealData.country,RetailPricesData.description,TipsYieldsData.value). - FastAPI 0.137+ route iteration:
CommandMap, coverage maps andadd_command_mapiterate throughiter_api_routes; exception handlers are registered withapp.add_exception_handler;FastAPI(strict_content_type=False);AppLoader.add_openapi_tagsandrest_apinow overrideapp.openapi. - The committed
openbb/assets/reference.jsonchanged from a 14-line stub to a 10,207-line snapshot of a developer's local build that referencesyfinanceandequity@1.6.1— reverted back to the clean 14-line stub byd377ba941e3(#7681).
openbb-cli
- Poetry to hatchling/PEP 621 (1.4.2 -> 2.0.0); runtime dependency
openbb[all]replaced byopenbb-core[pandas]>=2.0.0, sopip install openbb-cliinstalls no router extensions or providers;httpx,pyyaml,tomli(py<3.11) added;pywrymoved to theinteractiveextra; newchartingand
allextras. - Default mode is non-TTY one-shot:
openbb <command.path> --key valuedispatches once and prints a JSON line; the REPL needs-i/--interactive;main(argv=None) -> int; the legacyparse_args_and_runflags (-t,-m,-f,--HistoryManager.hist_file) are unreachable from theopenbbentry
point. Settings.USE_INTERACTIVE_DFdefaults to False; newSettings.OUTPUT_MODE(rich|json|tsv|html, defaulttsv, REPL commandoutput);-iflips both to interactive defaults.Sessionis lazy (_obb,prompt_session,backendproperties;_get_prompt_session->_build_prompt_session; newoutput_adapter,is_interactive); the backend class is resolved throughopenbb_core.app.charting.get_charting_backend_class()then
ChartingManager.get_charting_class().get_backend_class().CLIController.__init__gained keyword-onlybackend;CHOICES_COMMANDS/CHOICES_MENUSare per-instance (class lists areCHOICES_COMMANDS_BUILTIN/CHOICES_MENUS_BUILTIN = ["settings", "user", "feature"]);run_cli,main,launchacceptbackend=.PlatformControllerFactory.__init__(platform_router=None, *, backend=None, router_name=None, reference=None)raises withoutbackendorplatform_router;router_name/controller_nameare read-only properties;PlatformController.__init__gainedpathsand a changedValueErrormessage.ArgparseClassProcessor._build_pathslostdepthand no longer recurses ("subpath"only);Registry.allreturnsobbject.model_dump(exclude={"results"})socommand/register_keylive underextra;Registry.registeraccepts any OBBject whoseresults is not None.BaseController.check_pathaccepts digits,_and-;parse_inputprependshomefor inputs starting with/and protects-f/--filepaths;resultsgained-i/-kaliases anddb/sqlite/sqlite3export choices and renders throughoutput_adapter.- OBBject results in
PlatformControllerrender throughsession.output_adapter.display(...)andextract_dataframe(obbject);SettingsControllerenumeratessession.settings.__class__.model_fields. LocalBackend.routersskipsuser,system,accountand names starting with_(develop excluded anyobbattribute containing_), so routers with underscores now appear; thesystemcommand is gone anduseris a/user/menu.- The test workflow installs with
uv pip install --system -e ".[charting]" --group devon a 9-cell matrix; README moved to "ODP Command-Line Interface" and the docs link todocs.openbb.co/odp/cli.
openbb-platform-api
- Poetry to hatchling/PEP 621 (1.3.6 -> 2.0.0);
openbb-core>=2.0.0;tomli>=2.0on py<3.11; license Apache-2.0. The release cleanup removedpoetry.lock;uv.lockremains. main.pyis a thin bootstrap (--help/-hshort-circuit, TOML bootstrap,globals().updatere-export ofapp.app);utils/api.py,query_models.py,response_models.py,utils/merge_agents.py,utils/merge_apps.pyare lazy or re-export shims overapp/,models/,service/and
utils/network.py;check_for_platform_extensionsmoved toapp/bootstrap.py.- Route discovery uses
iter_api_routes(app)andgetattr(route, "original_route", route).endpointinstead ofisinstance(route, APIRoute);import_appinstalls the six exception handlers inline and applies CORS throughapply_cors_from_system_service; the defaultrest_api.appis imported
only when no--app/--specapp is supplied. - widgets.json generation:
format: "date"fields emitcellDataType: "dateString"(date-timekeeps"date"); adatecolumn gets"sort": "desc";fiscal_year,year,year_born,calendar_yearemitcellDataType: "text"withformatterFn: "none"; routes with a 2xxevent-stream
response are skipped; SSRM routes are auto-promoted tossrm_table. --specand--appare mutually exclusive (ValueErrorat startup).- The bootstrap pushes TOML
[system]/[user]ontoSystemService/UserServiceand applies.envandOPENBB_*promotion before the launcher imports.
openbb-mcp-server
- Poetry to hatchling/PEP 621 (1.4.1 -> 2.0.0);
openbb-core>=2.0.0,fastapi>=0.138.2,fastmcp>=4.0.9(was>=3.2.0),tomli>=2.0on py<3.11; license Apache-2.0. - Console script
openbb-mcptargetsopenbb_mcp_server.main:main;parse_args()moved toapp/args.pyand returns{app, transport, mcp_overrides, uvicorn_overrides}instead of anArgsobject;import_appmoved toapp/bootstrap.py;cl_docrenamedLAUNCH_SCRIPT_DESCRIPTION(lazy
aliases kept inutils/app_import.py). - Tool discovery is stateless: route tools stay enabled but hidden behind
OpenBBToolCatalog(search_tools/call_tool);default_tool_categoriesis ignored in that mode;mcp_config.enable: falseno longer disables a tool when discovery is on;available_toolsis synchronous and returns name
plus description only. allowed_tool_categoriesis now enforced (routes outside it are never registered);module_exclusion_map={}hides nothing;exclude_argsis applied to tool input schemas.create_mcp_server(auth=...)acceptsAuthProvider | tuple[str, str] | list[str] | Noneand raisesTypeErrorotherwise;TokenAuthProvidersubclasses fastmcpTokenVerifierand takes a(username, password)tuple;get_auth_provider(auth)no longer takes settings.- The three
on_duplicate_*settings collapsed intoon_duplicate(OPENBB_MCP_ON_DUPLICATE);--versionsetsMCPSettings.versioninstead of reaching uvicorn;write_to_fileomits a defaultdefault_skills_dir. - Non-GET tools on multi-method paths get a
_<method>suffix;output_schemaisNonefor routes without a JSON 2xx response;StaticPrompt.renderreturnsfastmcp.prompts.base.Messageobjects;execute_prompt(prompt_name=...)becameget_prompt(name=...). process_fastapi_routes_for_mcpno longer rewritesapp.router.routes; exclusions areMCPType.EXCLUDERouteMaps and routes are walked withfastapi.routing.iter_route_contexts.
openbb-technical
- Poetry to hatchling/PEP 621 (1.6.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0; new requiredscipy>=1.11,statsmodels>=0.14; entry pointopenbb_technical.router:router; license Apache-2.0; hard dependency onopenbb_core.app.route_iter.iter_api_routes. - Every command takes a single
params: XxxQueryParamsbody (all HTTP params move from the query string into the JSON body) and returns typedXxxDatarows containing onlydateplus renamed indicator columns; warm-up rows are dropped (.dropna()) for the pandas-ta backed indicators (exceptions:
demark,ichimoku,realized_volatilitywithclean=False,supertrend,pivot_points,clenow). - Defaults:
bbands.length50 -> 20,adx.length50 -> 14,kc.scalar20 -> 2.0;bbands.stdNonNegativeFloat->PositiveFloat;atr.drift,stochperiods,adx.drift,rsi/macd/aroon/sma/ema/wma/hma/zlmalengths ->PositiveInt;rsi/adx/aroon.scalar->PositiveFloat;
cones.trading_periods->PositiveInt | None. - Column renames:
bbands->lower, middle, upper, bandwidth, percent;kc/donchian->lower, middle, upper;macd->macd, signal, histogram;aroon->aroon_up, aroon_down, aroon_oscillator;ichimoku->tenkan_sen, kijun_sen, senkou_a, senkou_b, chikou_span;fisher->
fisher, signal;stoch->k, d;cones->lower/upper;fib->level/price;demarkrows aredate, up, down;clenowreturns per-bar float rows. - Signal endpoints live under
/technical/signals/*(obb.technical.signals.*);relative_rotationtakes a singleparamsmodel and is categorisedmulti.
openbb-quantitative
- Poetry to hatchling/PEP 621 (1.6.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0, explicitnumpy>=1.24,scipy>=1.11,statsmodels>=0.14; entry pointopenbb_quantitative.router:router; license Apache-2.0. - Every command takes a single
params: XxxQueryParams;normalityandunitroot_testresponses are flattened (kurtosis_statistic,adf_statistic,kpss_p_value_interpolatedand the other fields listed in the openbb-quantitative section);summarypercentiles renamedp25/p50/p75; rolling
columns lose the window suffix (skew,variance,stdev,kurtosis,mean,median/quantile);stats.*return a single typed record;sharpe_{window}->sharpe_ratio; the sortino column (formerly named after the target) ->sortino_ratio;dateis emitted as a literal key. rolling.quantileraisesKeyError('date')for a non-dateindex;quantile_pctis constrainedge=0.0, le=1.0;capmresamples to month-start closes and regresses onmkt_rfdirectly (no double risk-free subtraction);get_fama_rawcolumns aremkt_rf, smb, hml, rfon indexdate;
validate_windowmessage changed;CAPMModel->CapmDataand all non-list responses subclassData;OmegaModel->OmegaRatioDatawith abinsparameter.
openbb-econometrics
- Poetry to hatchling/PEP 621 (1.7.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0, directstatsmodels>=0.14,scipy>=1.11, open floorsarch>=7.2,linearmodels>=6; entry pointopenbb_econometrics.router:router; license Apache-2.0. - Every command takes a single
params: <X>QueryParamsand returns typedData:ols_regressionreturns coefficient rows;ols_regression_summaryreturnsOlsRegressionSummaryData;autocorrelation.score->durbin_watson;residual_autocorrelationkeys ->
lm_statistic/lm_p_value/f_statistic/f_p_value;cointegration->pair/c/gamma/alpha/adf_stat/p_valuerows;causality->test/statistic/p_value/lagrows;unit_rootkeys ->adf_stat/p_value/used_lag/nobs/ic_bestpluscritical_values; allpanel_*returnPanelRegressionData
coefficient rows;variance_inflation_factoris long-format;correlation_matrix.comp_toisstr. panel_fixednow fits without a constant and withentity_effects=Trueby default; integration tests no longer fetch from fmp/yfinance.
openbb-charting
- Version stays 3.0.0 on both branches, so the publish workflow will refuse a release if 3.0.0 is already on PyPI until
[project].versionis bumped. - Poetry to hatchling/PEP 621;
openbb-core[pandas]>=2.0.0;plotly>=6.3.1without an upper bound (Plotly 7 handled);pandas-ta-openbb>=0.4.24;pywryextra floor lowered to>=2.0.0; license Apache-2.0; entry point moved to[project.entry-points."openbb_obbject_extension"]. Charting._extension_views(eager class attribute) replaced by lazy_get_extension_views()with_extension_views_cache;create_line_chart/create_bar_chartalways return the figure;Charting.__init__builds the backend fromget_backend_class()(entry-point override or built-in
Backend).- Platform interfaces (core
commands.py, package builder, command runner, the CLI) resolve the engine throughChartingManagerinstead of importingopenbb_chartingby name; the missing-charting error text changed. - openbb-technical no longer imports
openbb_chartingat import time; openbb-cli no longer pulls openbb-charting transitively.
Pass-through router extensions
- Nine packages (commodity 1.5.2, crypto/currency/derivatives/economy/equity/etf/fixedincome/index 1.6.2) moved to 2.0.0 on hatchling/PEP 621 with
openbb-core>=2.0.0, entry points under[project.entry-points.*]and license Apache-2.0. EtfViewsreturn annotations becametuple[Any, dict[str, Any]]; the session-scopedobbfixture nowpytest.skips when integration tests are disabled; the eightobb.regulators.sec.*commands areobb.sec.*(a staleobb.regulators.sec.institutions_searchexample survives in
ownership_router.py).
openbb-news
- Poetry to hatchling/PEP 621 (1.6.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newfeedparser>=6.0,lxml>=5.0; entry pointopenbb_news.router:router; description "RSS news feeds extension for OpenBB"; license Apache-2.0. news.worldhas no provider on v5 andnews.companyis served only by tmx and nasdaq; the metapackage still pinsopenbb-news = "^1.6.2".
openbb-devtools
- Poetry to hatchling/PEP 621 (1.6.8 -> 2.0.1);
pylint,mypy,black,poetry,pytest-freezegundropped;ty>=0.0.40,httpx2>=2.0.0,types-requests,pytest-freezer>=0.4.9added;pytest-recorder>=1.0.0(whose deps are now ruff/ty/vcrpy 8.3.0);ruff>=0.15unbounded; license
Apache-2.0. - Consumers that no longer path-source devtools (cli, platform-api, mcp-server, the 13 router/toolkit extensions) resolve
openbb-devtools>=2.0.1from an index that nothing in the repo publishes.
openbb-bls
- Poetry to hatchling/PEP 621 (1.3.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newrequests,beautifulsoup4,lxml,openpyxl; license Apache-2.0; building needs network access to download.bls.gov (or an existingbls_cache.zip); the metapackage still pinsopenbb-bls = "^1.3.1", which does not admit 2.0.0. BlsSeriesdefault window is the earliestbegin_yearof the requested symbols (fallback 20 years) instead of 3 years; chunking is 50 symbols/20 years with a key and 25/10 without; newcategoryparam;BlsSeriesDatagained chart widget config andformatterFn: percenton percent-change
columns.BlsSearchgained a no-opsymbolparam, recency ordering, synthesized titles and theixpcategory (EI series leftcpi); several category display names changed./bls/search,/bls/series,/bls/calendarregister only when openbb-economy is absent; the calendar fetcher key switches betweenEconomicCalendarandBlsEconomicCalendar; searching without the shippedbls_cache.zipraisesKeyError.BlsSeriesstill lacksrequire_credentials = False, soobb.bls.seriesraises "Missing credential 'api_key'" through the command path although the README says no key is required.
openbb-cboe
- Poetry to hatchling/PEP 621 (1.6.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0,aiohttp-client-cache>=0.11,aiosqlite>=0.20; license Apache-2.0; newopenbb_core_extensionrouter at/cboe; the metapackage pinsopenbb-cboe ^1.6.0(develop^1.6.1), which cannot resolve 2.0.0. - Fetcher keys are conditional on openbb-equity/etf/index/derivatives (
Cboe*aliases otherwise);EtfHistoricalonly with openbb-etf. IndexConstituents.symbolisCONSTITUENTS_EU | CONSTITUENTS_AUwith a newsessionparam and many new fields;IndexSnapshots.regionaddsau, symbols lose the^prefix and gainname; percent columns and OHLC values are no longer rounded;EquityQuotedropsmultiple_items_allowed
(fetcher still splits on commas).- Daily index history comes from per-symbol
_History.csvfiles (novolume); multi-dateFuturesCurvereturns a wide shape andexpirationbecamestr | None; optionsdteis anchored to 16:00 ET; default dates use the New York session; caching is a shared per-loop backend with per-URL TTLs;
model imports instantiateSystemService()at import time.
openbb-cftc
- Poetry to hatchling/PEP 621 (1.4.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newxlrd,openpyxl,diskcache,pyarrow;openbb-platform-apidropped; license Apache-2.0. COT->CftcCot,COTSearch->CftcCotSearchfetcher keys and router models; the COT models no longer subclass the core standard models;querydefault""->None;/cftc/get_cot_choices->/cftc/cot_choices;apps.jsonmoved underassets/; the startup lifespan prefetch is gone;
reports_dictmoved toutils/constants; COT responses are disk-cached for one hour.
openbb-deribit
- Poetry to hatchling/PEP 621 (1.2.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0,aiohttp-client-cache>=0.11,aiosqlite>=0.20;async-lrudropped; license Apache-2.0; newopenbb_core_extensionrouter at/deribit. - The five standard keys (
FuturesCurve,FuturesHistorical,FuturesInfo,FuturesInstruments,OptionsChains) register only with openbb-derivatives installed (Deribit*aliases and/deribit/futures/*,/deribit/options/chainsotherwise). FuturesCurve.symbolis a plainstr(novalidate_symbol),hours_agoisstr | None, the curve is priced offmark_priceand excludes the perpetual;FuturesHistoricallost its query-time symbol validator andvolume_notionalis Optional;FuturesInfofields
best_bid_price/best_ask_price/best_bid_amount/best_ask_amount->bid/ask/bid_size/ask_sizeandchange_percentis no longer divided by 100.- Options chains: any listed root is accepted;
mark_iv,bid_iv,ask_iv,price_changeare no longer divided by 100 andinterest_rateis multiplied by 100;contract_sizecomes from the instrument spec; several list fields lost theirdefault_factory; websocket timeout 2 s -> 15 s. - Helper API:
get_instruments(currency="any", kind=None, expired=False); constants moved toutils/constants(Currenciesno longer includes"all");BASE_URLmoved toutils/clientand includes/api/v2.
openbb-ecb
- Poetry to hatchling/PEP 621 (1.6.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newrequests,defusedxml,diskcache,beautifulsoup4,markdownify; license Apache-2.0; a hatch build hook fetches the SDMX catalogue whenecb_cache.json.xzis absent; newopenbb_core_extensionrouter at
/ecb; the metapackage pinsopenbb-ecb ^1.6.0, which cannot resolve 2.0.0. BalanceOfPayments,CurrencyReferenceRates,YieldCurvekeys register only with openbb-economy/currency/fixedincome installed (Ecb*aliases otherwise).- The yield curve is fetched as one OR-joined SDMX key within a 14-day window per date (single-date misses raise
EmptyDataErrorinstead of resolving to the nearest earlier date);BalanceOfPaymentsgainedstart_date/end_date/use_cache,aextract_datareturns flat observation records,
series ids lost theBPS.prefix and several keys were renamed to the standard field names;CurrencyReferenceRates.extract_datareturns a{"time", "rates"}dict; importing the package loads the catalogue.
openbb-us-eia
- Poetry to hatchling/PEP 621 (1.3.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newcurl-cffi,fastmcp>=2.0,feedparser; license Apache-2.0; cold builds need an EIA key and network access; newopenbb_core_extensionroutereia(obb.eia). petroleum_status_reportandshort_term_energy_outlookregister underobb.eiaonly when openbb-commodity is absent; STEO periods are parsed with explicit formats;response_callbackraisesOpenBBErroron anyerrorenvelope.
openbb-famafrench
- Poetry to hatchling/PEP 621 (1.2.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0; the provider entry-point keyfamafranchcorrected tofamafrench; license Apache-2.0; integration tests moved into the provider and self-host uvicorn.
openbb-federal-reserve
- Poetry to hatchling/PEP 621 (1.6.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0,openbb-platform-api>=2.0.0, newdiskcache,defusedxml,curl-cffi,pdfplumber;openbb-economy/openbb-fixedincomedropped; license Apache-2.0. - Core-extension entry point moved to
openbb_federal_reserve.federal_reserve_router:router(an OpenBBRouter), creating theobb.federal_reservenamespace; the 11 surviving standard keys are conditional on openbb-economy/fixedincome (FederalReserve*aliases and fallback commands otherwise). MoneyMeasuresvalues are dollars (x1e9);PrimaryDealerFailsandPrimaryDealerPositioningdrop the standard bases and return wide per-date records;CentralBankHoldingslost its x1000 frontend-multiply metadata; caching moved todiskcache(OPENBB_FEDERAL_RESERVE_CACHE_DIR); FOMC document
lists refresh at the next FOMC date.
openbb-finra
- Poetry to hatchling/PEP 621 (1.6.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0; license Apache-2.0; newopenbb_core_extensionrouter at/finra; fetcher keys conditional on openbb-equity/fixedincome (Finra*aliases otherwise). - Short interest reads
otcMarket/consolidatedShortInterest(sqlite CSV cache gone), decodesmarket_class, sorts by(symbol, settlement_date)and raisesEmptyDataErrorwhen empty; OTC without a symbol returns only the latest week and with a symbol returns full history (no 52-week cap);
BondPricesrejectscountry,isin,lei,currency,issued_amount_min/maxand unfiltered MBS/CMO searches; empty results surface as HTTP 204.
openbb-fred
- Poetry to hatchling/PEP 621 (1.6.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0,diskcache>=5.6; license Apache-2.0; newopenbb_core_extensionrouterfred; 32 standard keys switch toFred*aliases when the owning extension is absent. - Percent values are no longer divided by 100 across roughly twenty models (Ameribor, BalanceOfPayments, BondIndices, CommercialPaper, ConsumerPriceIndex, EuroShortTermRate, FederalFundsRate, HighQualityMarketCorporateBond, ManufacturingOutlookNY/Texas, MortgageIndices, NonFarmPayrolls,
OvernightBankFundingRate, RetailPrices, SeniorLoanOfficerSurvey, SOFR, SurveyOfEconomicConditionsChicago, TipsYields, UniversityOfMichigan, YieldCurve). CommercialPaper,BondIndices,MortgageIndicesare wide (one column per series);SpotRaterows are{date, maturity, rate}; nine fetchers switched fromextract_datatoaextract_data; Chicago survey columns renamed to the standard names;fred_get_manyre-raises the first failure;
FederalFundsRatedefaultstart_datelogic changed;use_cacheadded to every model.
openbb-government-us
- Poetry to hatchling/PEP 621 (1.6.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newcurl-cffi,defusedxml,diskcache,httpx,openpyxl,xlrd; license Apache-2.0. - The single
government_usprovider is replaced bycongress_gov,us_treasuryandusdawith routersuscongress,ustreasury,usda;provider="government_us"no longer exists (the commodity and fixedincome routers still carry stalegovernment_usexamples); fetcher classes renamed
Us*/Usda*;openbb_congress_gov.*->openbb_government_us.congress.*. - Congress identifiers are
bill_id/amendment_id(119-hr-29,119-hamdt-2) instead of URLs; data comes from GovInfo bulk files, the API key is optional (fallback for Congresses before 108);CommodityPsdDatais pivoted wide with marketing-year columns;CommodityPsdReportis a POSTurls
download;TreasuryPricesgained a requireddate; theuscongressrouter warms an on-disk SQLite cache at API startup.
openbb-imf
- Poetry to hatchling/PEP 621; version 2.1.3 -> 2.1.2 (lower);
openbb-core[pandas]>=2.0.0,requests>=2.31;chartingextraopenbb-charting>=3.0.0;openbb-platform-apiandopenbb-economydropped; license Apache-2.0. - Core-extension entry point
imf_utils->imf: every/api/v1/imf_utils/*route andobb.imf_utils.*command is now/api/v1/imf/*/obb.imf.*;list_port_id_choicesmoved to/imf/portwatch/;presentation_tablereturns AG-Grid rows only (no HTML/raw),countryis single-select and
the category is "IMF Data". - Fetcher keys switch to
Imf*aliases without openbb-economy; the metadata cache is xz JSON (imf_cache.json.xz, gitignored, generated at build);utils/metadata.pybecame a mixin package; router commands take aDepends-injectedImfMetadataDependency;
ImfAvailableIndicatorsFetcher.extract_datais async; unknowndimension_valuesraiseValueError; CPIsymbolis the rawseries_idandcountrydefaults to"USA"; importingopenbb_imfloads the catalogue.
openbb-nasdaq
- Poetry to hatchling/PEP 621 (1.6.3 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newaiohttp-client-cache,aiosqlite,python-dateutil,data-linkextrapdfplumber;nasdaq-data-linkandopenbb-platform-apidropped; no credentials; license Apache-2.0; newopenbb_core_extensionrouter
nasdaq. - Fetcher keys are conditional on the owning extension (
Nasdaq*aliases otherwise);TopRetailis gone (theobb.equity.discovery.top_retailcommand has no provider);website/repr_namechanged. HistoricalDividends.symboldropsmultiple_items_allowedand resolves the asset class via the listing directory;EquityScreener.market_capandCalendarEarnings.market_caparefloat | None; the screener uses thedownload=trueendpoint; IPO calendar sorts per status and raises a
differently wordedEmptyDataError; the symbol directory is fetched over HTTPS;get_headers()drops theHostheader; JSON requests go through a SQLite HTTP cache.
openbb-oecd
- Poetry to hatchling/PEP 621 (1.6.1 -> 2.0.0);
openbb-core[pandas]>=2.0.0,requests>=2.31;defusedxmldropped; license Apache-2.0; core-extension entry pointoecd(renamed fromoecd_utilsin #7509); fetcher keys switch toOecd*
aliases without openbb-economy. - Country slugs were regenerated from SDMX constraints (
czech_republic->czechia,turkey->turkiye,south_korea->korea,oecd_total->oecd,slovakia->slovak_republic, and others); resultcountryvalues are OECD labels; validators normalize instead of rejecting; four
fetchers switched fromaextract_datato syncextract_data. - House price index
yoy/periodvalues are divided by 100 and the monthly-to-quarterly fallback triggers on any exception; CPI lost its CSV cache, usesTRANSFORMATIONcodes, accepts multipleexpenditurevalues and gained required fields; every migrated fetcher wraps failures inOpenBBError
soEmptyDataErrorno longer surfaces;oecd_date_to_python_datereturnsNoneinstead of raising.
openbb-sec
- Poetry to hatchling/PEP 621 (1.6.7 -> 2.0.0);
openbb-core[pandas]>=2.0.0,openbb-platform-api>=1.3.6,fastmcp>=3.2.0,diskcache>=5.6.3; license Apache-2.0; newopenbb_core_extensionroutersec. - All commands moved from
obb.regulators.sec.*//api/v1/regulators/sec/*toobb.sec.*//api/v1/sec/*; standard equity/ETF fetcher keys becomeSec*aliases (andobb.sec.*commands) when openbb-equity/openbb-etf are absent. compare_company_facts.fiscal_period->calendar_period(with derived standalone Q4 andcalendar_year/calendar_periodoutput fields);SecRssLitigationDatafieldspublished/summary/link->date/excerpt/urlplusbody,authorand alimitparam;SecBaseFiling->Filing(alias
kept);hmrc-dpl->frc-core/frc-dpl;urlparams arestr | Nonewith strict sec.gov host validation;use_cachenarrowed toboolon four query models; caching moved to onediskcachestore under<cache>/secwith a 9 req/s rate limiter.
openbb-tmx
- Poetry to hatchling/PEP 621 (1.5.2 -> 2.0.0);
openbb-core[pandas]>=2.0.0, newcurl-cffi,diskcache,lxml,pyarrow,tzdata,python-dateutil,pdfplumber; extrascharting,builder,all; license Apache-2.0; newopenbb_core_extensionroutertmx; every standard fetcher key is
conditional on the owning extension (Tmx*aliases otherwise). EquitySearchreads the QuoteMedia symbology with newcountry/symbol_only/limitparams (default 200 Canadian listings) and raisesEmptyDataErroron no match;IndexConstituentsuses GraphQL,market_valuealiasquotedmarketvalue->quotedMarketValue,aextract_datareturns a list;
EquityHistorical.high/loware Optional;CalendarEarningsraisesEmptyDataErroron empty windows;EtfSearch.div_freqwidened; options chains come from QuoteMedia with greeks;helpers.get_data_from_urllostbackend;utils/gql.pywas rewritten with uppercase constants;
normalize_symbolno longer strips.TSXVforPriceTargetConsensus.
Repository and tooling
- Root
LICENSEand every package are Apache-2.0;.pylintrcdeleted;ruff.tomlline-length 122 -> 88 (ruleQdropped,E501/D206/D300ignored,[format]section added);ty.tomladded; the pre-committyhook points at the untracked.github/scripts/ty_per_package.sh. dev_install.pyis a uv-based installer with a single--routersflag (-e/--extrasand-c/--cliare gone);noxfile.pyinstalls uv and callsdev_install.py --routers;test-unit-cli.ymland the platform lint workflow were rewritten;general-linting.ymlandtest-unit-platform.ymlare
gone.- openbb-cookiecutter 0.6.0 -> 1.0.0 on hatchling; the template generates hatchling projects with
openbb-core[pandas]>=2.0.0, entry points under[project.entry-points.*]and anobbject_namedefault oftemplate_ext. - At the initial inventory, the root
openbbmetapackage was still on Poetry and the legacybuild/publish/nightly scripts were incompatible with V5. The metapackage was migrated to hatchling/PEP 621 version 5.0.0 in direct commit6d8e44100ab;openbb_platform/poetry.lockand the obsolete scripts were removed, anduv.lockis now committed. - The desktop app's vite/vitest/esbuild bumps from develop were discarded by the same merge;
publish-openbb-jodi.ymlstill checks outbase.ref || 'develop'.
openbb-core
openbb-core 1.6.13 -> 2.0.0 is the V5 foundation. The packaging and lint migration, the package-builder split and the first coverage push came in #7482 and #7484;
the layered openbb.toml config loader in #7492; streaming in #7530; the engine-agnostic charting layer in #7545;
FastAPI 0.137+ route iteration in #7537; the Flask migration toolkit in #7264; the vectorized basemodel_to_df in #7622;
the license flip in #7677. #7485 pinned the dev group, #7669 reshaped four FRED-backed standard models, and
#7494/#7495 only regenerated openbb/assets/reference.json. Twenty-two direct commits (listed above) added POST-body unpacking, docstring-generator fixes, the swagger tag grouping and the
thread-safe singleton.
Removed
html5libdependency.Linters.black();Linters.run()acceptslinter: Literal["ruff"]only.LoggingSettings.user_id,user_email,user_primary_usage(read fromhub_session) and the%(userId)sfield ofFormatterWithExceptions.LOGPREFIXFORMAT; nothing in openbb_core referenceshub_sessionany more.- Standard-model fields
BondIndicesData.symbol/value,CommercialPaperData.symbol/maturity/rate/title,MortgageIndicesData.symbol/name/rate,SpotRateData.rate: every requested series is now its own column. integration/test_obbject.py(required real providers) andpoetry.lock.- Nearly every
# pylint: disabledirective (threeimport-outside-toplevellines survive inopenbb_core/app/config/loader.py).
Breaking
- Packaging:
[tool.poetry]->[project], build backendpoetry.core.masonry.api->hatchling.build, wheel packages["openbb_core", "openbb"],uv.lockreplacespoetry.lock; the sdist ships onlyopenbb_core,openbb,README.md,pyproject.toml. pandasis theopenbb-core[pandas]extra;require_optional("pandas")guardsOBBject.to_dataframe/to_polars/to_numpy,basemodel_to_df,Metadata,Fetcher.test,OptionsChainsProperties.dataframeand the pandas-backed standard-model validators.- Dependency floors: uvicorn
>=0.48.0, fastapi>=0.137.2(raised from>=0.136.3byf0258c93366), requests>=2.34.2, pyjwt>=2.13.0, pydantic>=2.12.3,<3.0.0, aiohttp>=3.14.2(raised from>=3.13.3by the same commit), python-multipart>=0.0.29, ruff>=0.15,tomli>=2.0.0; python_version<'3.11';requires-pythonstays>=3.10,<4. - License Apache-2.0;
APISettings.license_namedefault"Apache-2.0"; README license section rewritten. OBBject.to_llm() -> str(returns"[]"when empty);OBBject.to_polars()raisesOpenBBErrorwithpip install polars pyarrowwhen polars is missing.api/router/commands.pyusesCharting = ChartingManager.get_charting_class()andCHARTING_INSTALLED = Charting is not None;StaticCommandRunner._chartresolves the accessor viaChartingManager.accessor_name()with a new error message;PackageBuildercomputes
CHARTING_INSTALLED = ChartingManager.is_installed().SingletonMetais thread-safe and no longerGeneric[T].Credentials.show()iteratestype(self).model_fields, unmasks rawSecretStrvalues and no longer prints undeclared extra credentials.- The committed
openbb/assets/reference.jsonis a 10,207-line local-build snapshot listingequity@1.6.1,technical@2.0.0andyfinance@1.6.2— reverted back to a clean 14-line stub byd377ba941e3(#7681);openbb/package/__init__.pynow matches the builder's unchanged""" Autogenerated OpenBB module."""output.
New
- Layered configuration (
openbb_core.app.config:load_config,load_layered_config,apply_config_to_services,apply_settings_to_env,load_env_files,render_config_template). Resolution order: model defaults ->system_settings.json/user_settings.json->[tool.openbb]in the nearest
pyproject.toml->~/.openbb_platform/openbb.toml(or.openbb.toml) ->./openbb.tomlwalking up from CWD ->$OPENBB_CONFIG->.envfiles (~/.openbb_platform/.env,$OPENBB_ENV_FILE) ->OPENBB_*env vars.
[system]/[user]tables deep-merge and the top-level keysdebug-mode,test-mode,headless,logging-suppress,allow-mutable-extensions,allow-on-command-outputpromote onto[system]. openbb_core.app.model.aggrid:AgGridRowsRequest,AgGridRowsResponse[Row],AgSortColumn,AgFilterModel,AgGroupingModel; routes using them are auto-promoted tossrm_tablewidgets by the platform-api generator.- Streaming:
OBBStream(openbb_core/app/model/stream.py) withid(uuid7),provider,warnings,extra,media_type,async for,start(output=None, handler=None)on a background thread (stdout, path, file or socket sink),stop(),wait(),aiter(),aiter_bytes(),
OBBStream.from_query()and a module-levelstop_all()wired to atexit/SIGINT/SIGTERM. - Fetcher streaming contract:
Fetcher.stream_data(query, data, **kwargs)(async generator),Fetcher.is_streaming,_get_data_typeunwraps async/sync iterator containers,Fetcher.fetch_datareturnsstream_data(...)for streaming fetchers,Fetcher.testdelegates to_test_stream,
RegistryMap._get_results_typenormalizes async-iterator return types tolist. - Router/API streaming plumbing:
Router.commandsetsresponse_model=Noneand registers a200: text/event-streamresponse for-> OBBStreamendpoints; the API wrapper returns aStreamingResponsefromoutput.aiter_bytes()withX-OpenBB-Stream-Id,X-OpenBB-Provider,X-OpenBB-Warning
headers and passes raw StarletteResponses through;Container._runwraps abody_iteratorintoOBBStream; the docstring generator emitsget_OBBStream_descriptionandImportDefinitionmapstext/event-streamtoOBBStream. - Charting layer
openbb_core.app.charting:ChartingManager(get_extension,accessor_name,get_charting_class,is_installed,functions,has_chart),ChartingExtension/AbstractChartingBackendprotocols,get_charting_backend_class(entry-point groupopenbb_charting_backend), and
lifecycle hooks (ChartLifecycleresolve_data/pre_figure/post_figure/pre_render/post_render,HookContext,ChartingHook,ChartingHooksManager,get_hooks_manager, groupopenbb_charting_hooks). - System settings
charting_extensionandcharting_backend(envOPENBB_CHARTING_EXTENSION,OPENBB_CHARTING_BACKEND), added toSystemService's allowed keys. - Enterprise Flask Migration Toolkit: an
openbb_core_extensionentry point may reference a Flask app;ExtensionLoader.flask_objectsdetects them,rest_apicallsmount_flask_extensions(app, prefix)to mount each under{prefix}/{name}via a2wsgi'sWSGIMiddleware,
FlaskIntrospector/OpenAPISpecGeneratorintrospect routes into aFlaskMountRegistry, andmerge_flask_openapifolds the fragments into the schema; new extraopenbb-core[flask](flask>=3.1.2,a2wsgi>=1.10.10);openbb_core/app/utils.pybecame the packageopenbb_core/app/utils/. openbb_core.app.utils_optional:is_installed(module_name)andrequire_optional(*module_names)with install hints for pandas, numpy, polars, pyarrow, openbb_charting, pycountry, bs4, flask, a2wsgi.openbb_core/app/route_iter.py(iter_api_routes,iter_included_routers) expanding FastAPI's_IncludedRouter;AppLoader.deduplicate_router_event_handlers.- POST bodies as
params: Model: a command may declare a singleparams: XxxQueryParamsargument;MethodDefinition.query_params_modelflattens it into kwargs in the generated SDK method, docstring and reference, the generated body repacks them, andfilter_inputsconverts a nested"data"key
viaconvert_to_basemodel. - The 4340-line
openbb_core/app/static/package_builder.pyis now the packagepackage_builder/(builder.py,class_definition.py,docstring_generator.py,file_lock.py,import_definition.py,method_definition.py,module_builder.py,path_handler.py,reference_generator.py,
_indent.py) with every previously importable name re-exported from__init__.py. PackageBuilder._writepost-processes generated modules through_normalize_code_annotations(rewritestyping.XandListto builtins only outside strings and comments);PackageBuilder._distribution_versiontolerates entry-point distributions whose metadata raises.- OpenAPI tag grouping:
AppLoader.add_openapi_tagsoverridesapp.openapito collapse per-level route tags into a compositea/b/ctag, emitstagswith router descriptions andx-tagGroups(data extensions first); Swagger UI is served withdocExpansion: "none". pytest.inimarkersrequires_pandasandrequires_extensions.openbb_platform/core/README.mdrewritten to document the three entry-point groups, theon_command_output/immutable/results_onlyflags with theirOPENBB_ALLOW_ON_COMMAND_OUTPUT/OPENBB_ALLOW_MUTABLE_EXTENSIONSgates, theopenbb-buildconsole script and
uvicorn openbb_core.api.rest_api:app.
Patterns
[dependency-groups] dev = ["openbb-devtools>=2.0.1", "flask>=3.1.2", "a2wsgi>=1.10.10"]with[tool.uv.sources] openbb-devtools = { path = "../extensions/devtools", editable = true }; ruff and[tool.ty]config in the package pyproject ([tool.ty.environment] python-version = "3.10").# ty: ignore[code]replaces pylint directives, for exampleclass OpenBBField(FieldInfo): # ty: ignore[subclass-of-final-class]..github/workflows/test-openbb-core.yml: Python 3.10-3.14 (Linux full sweep, macOS/Windows min+max) withpip install -e ".[pandas,flask]",--cov-config=.coveragerc,OPENBB_ALLOW_ON_COMMAND_OUTPUT=True/OPENBB_ALLOW_MUTABLE_EXTENSIONS=True, and anintegrationjob instrumenting
subprocesses via a sitecustomize shim;publish-openbb-core.ymlbuilds withuv build --no-sources, tests the installed wheel afterrm -rf openbb_core openbb, aborts if the version exists on PyPI and publishes via trusted publishing from arelease/openbb-core-v<version>branch.- A new
.coveragerc(branch=False, parallel=True, omitsbuild.py, the twoupdate_*_data.pyscripts,tests/*,integration/*) and 47 newtest_*.pymodules plus 3 conftests (tests/app/model/test_stream.py,tests/provider/abstract/test_fetcher_streaming.py,
tests/app/config/test_loader.py,tests/app/charting/*,tests/app/test_flask_*.py,tests/app/static/package_builder/*). integration/conftest.pywrites a syntheticopenbb-fake-integrationdistribution (router, provider and OBBject accessor entry points), installs it withpip install --no-deps -e, triggers the real build withOPENBB_AUTO_BUILD=true, andintegration/test_built_package.pyasserts
obb.fake_integration.list_indicatorsdispatches through the realCommandRunner.- Standard models and core modules use ruff-isort ordering (
pydanticbeforeopenbb_core); roughly 150 standard-model files changed only by that reorder.
Fixes
CommandMap.get_provider_coverage/get_command_coverageskip routes whoseopenapi_extra["model"]is not inProviderInterface().map(if model and model in mapping), avoiding aKeyErrorfor models with no installed provider.OBBject.to_dataframe()checksisinstance(self.results, DataFrame)before the "Results not found" guard, avoiding pandas' ambiguous-truth-valueValueError.basemodel_to_dfparsesdatewith one vectorizedto_datetimecall and a vectorized midnight test, falling back to per-element parsing only for mixed-UTC-offset columns (8.92 ms -> 1.46 ms for 250 bars, 162 ms -> 12 ms for 5000 bars).SystemSettings.create_openbb_directoryis an instance-mode@model_validator(mode="after").APIExvalidation usesparameters.get("provider")instead of popping it, excludesproviderfrom the >3-parameter description requirement and single-quotes onlystrvalues.- Seven standard-model annotations corrected to
X | Nonewhere the default isNone. openbb/__init__.pyloadsopenbb.package.__extensions__viaimport_moduleand also catchesAttributeErrorwhen falling back to a bare app.combine_certificatesregistersPath(combined_cert).unlinkwithmissing_ok=True;amake_requestsasserts re-raised results areBaseException.- Instance-level
model_fieldsaccess (deprecated in pydantic 2.11) removed:_model_fieldshelpers inRegistryMap._extract_infoandcreate_combined_model, class-level access inParametersBuilder.validate_kwargs,Credentials.model_post_init,OptionsChainsData.model_serialize. OptionsChainsProperties._require_pandas()andMetadata(require_optional("numpy", "pandas")) raise a uniformOpenBBErrorinstall hint when pandas is absent.- FastAPI 0.137+:
CommandMap, coverage maps andadd_command_mapiterateiter_api_routes(wrapping theoriginal_routeleaf with the effective prefixed path); exception handlers registered withapp.add_exception_handler;FastAPI(strict_content_type=False).
openbb-cli
openbb-cli 1.4.2 -> 2.0.0 was rewritten in #7433 around a non-TTY default, a pluggable Dispatcher, precomputed .spec files and --generate-extension codegen.
OpenAPI ingestion was hardened by #7586 and #7589 (modular $ref bundling) and #7606 (path-item parameter inheritance, allOf merging,
safe identifiers);
codegen by #7597, #7598 and #7599. #7530 added SSE streaming,
#7545 decoupled it from openbb_charting,
#7537 refreshed the lock, and #7677 relicensed it. Direct commits 932a895a069 and 5f4dda273b8 added Plotly figure rendering and strip_theme_colors.
Removed
Settings.HUB_URLandSettings.BASE_URL;--devno longer repoints them.exe --urland the OpenBB Hub routine download path (ROUTINE_DEFAULT_FILES,ROUTINE_PERSONAL_FILES,default//personal/prefixes, therequestsimport).record --public/-pandSESSION_RECORDED_PUBLIC.- The module-level
PLATFORM_ROUTERSdict and the import-timefrom openbb import obbincli_controller.py; thesystemREPL command;useras a model-dump command (now the/user/menu). pytz(stdlibzoneinfoinstead).- Every direct
openbb_chartingimport (session.py,base_platform_controller.py,controllers/utils.py). print_rich_tabletruncation toALLOWED_NUMBER_OF_ROWS/ALLOWED_NUMBER_OF_COLUMNS(settings remain but are unused) andMenuText._format_cmd_nametruncation.poetry.lockand thefastapi = "0.136.3"pin.
Breaking
- Packaging: PEP 621 + hatchling;
openbb[all]->openbb-core[pandas]>=2.0.0;httpx>=0.28.0,<1.0.0,pyyaml>=6.0,tomli>=2.0(py<3.11) added;pywrymoved to theinteractiveextra; newcharting = ["openbb-charting>=3.0.0"]andallextras; license Apache-2.0. openbb <command.path> [--key value]dispatches once and prints a JSON line; the REPL requires-i/--interactive;main(argv=None) -> int,__main__handlesBrokenPipeError;-t,-m,-f,--HistoryManager.hist_fileare unreachable from the entry point.Settings.USE_INTERACTIVE_DFdefault False; newSettings.OUTPUT_MODE(rich|json|tsv|html, defaulttsv) andOutputModeenum;_apply_interactive_defaultsflips them under-i.Sessionis lazy (_obb,prompt_session,backend,output_adapter,is_interactiveproperties;_build_prompt_session;Style(directory=None)).CLIController.__init__(jobs_cmds=None, *, backend=None);CHOICES_COMMANDS_BUILTIN = ["record", "stop", "exe", "results"],CHOICES_MENUS_BUILTIN = ["settings", "user", "feature"];run_cli,main,launchacceptbackend=.PlatformControllerFactory.__init__(platform_router=None, *, backend=None, router_name=None, reference=None);create()injects_factory_backend,_factory_translators,_factory_paths;PlatformController.__init__gainedpathsand a newValueErrormessage.ArgparseClassProcessor._build_paths(target)no longer recurses ("subpath"only);Registry.allreturnsobbject.model_dump(exclude={"results"});Registry.registeracceptsresults is not None.BaseController.check_pathregex^[a-z0-9_\-/]*$;parse_inputprependshomefor/-prefixed input and protects-f/--filepaths (.db/.sqlite/.sqlite3);parse_and_split_inputdrops empty commands.resultsgained-i/-k,db/sqlite/sqlite3export choices and renders throughsession.output_adapter.display;PlatformControllerroutes OBBject results throughoutput_adapter.displayandextract_dataframe;SettingsControllerusessession.settings.__class__.model_fields.LocalBackend.routersskipsuser,system,accountand_-prefixed names only, so routers containing_now surface.- The test workflow runs
uv pip install --system -e ".[charting]" --group devwith coverage on ubuntu 3.10-3.14 plus macOS/Windows 3.10 and 3.14; README retitled "ODP Command-Line Interface" with docs atdocs.openbb.co/odp/cli.
New
- Mode flags (mutually exclusive):
-i/--interactive,--batch,--generate-spec,--generate-extension,--list-commands,--describe COMMAND[:PROVIDER],--print-config-template,--show-config. - Option flags:
--config PATH,--env-file PATH,--batch-concurrency N,--server URL,--spec [NAME=]PATH(repeatable),-o/--output PATH,--openapi-path PATH,--socrata-story URL_OR_PATH,-H/--header KEY=VALUE,--header-file PATH,-Q/--query-param KEY=VALUE,
--query-param-file PATH,--provider-name,--project-name,--package-name,--router-name,--include PATTERN,--exclude PATTERN, plus--dev/--debugand acommandREMAINDER positional. - Environment:
OPENBB_CLI_CONFIG,OPENBB_CLI_ENV_FILE,OPENBB_CLI_BATCH_CONCURRENCY,OPENBB_SERVER_URL,OPENBB_SPEC_PATH,OPENBB_HEADER_FILE,OPENBB_QUERY_PARAM_FILE, anyOPENBB_HTTP_QUERY_<NAME>becomes a?name=query param; TOML[settings]keys and
output-mode/flair/timezone/rich-stylepromote toOPENBB_<FIELD>. - Layered TOML config (
openbb_cli/config/loader.py):[tool.openbb-cli]in the nearestpyproject.toml->~/.openbb_platform/openbb.toml->./openbb.tomlwalking up ->--config/$OPENBB_CLI_CONFIG; keysserver,spec,openapi-path,header-file,query-param-file,output,
batch-concurrency,auth-hook,[headers],[query],[specs.<ns>],[settings];.envfiles (~/.openbb_platform/.env,--env-file) loaded before argparse withos.environ.setdefault. openbb_cli.dispatchers:Dispatcherprotocol,LocalDispatcher(in-processobb),HttpDispatcher(httpx against openbb-platform-api or any OpenAPI server),MultiSpecDispatcher(<ns>.<cmd>routing), NDJSON wire modelsRequest/Response/ResponseErrorwithextra="forbid".- Batch mode: NDJSON requests on stdin, concurrent responses (
asyncio.Semaphore, default 8); reserved__commands__and__schema__introspection commands implemented by the HTTP and multi-spec dispatchers only;--list-commands/--describeexit 2 without--specor--server. .specfiles (SPEC_VERSION = 5):--generate-specwrites a compact JSON spec stamped withcontent_sha256;load_specrejects version mismatches, schema violations (SpecDocument) and hash mismatches; specs carrybase_url,api_prefix,commands,routers,reference,generator,
source_url,api_version;--generate-specaccepts the output path as its first positional.- Spec-driven argument parsing (
parse_command_argv): per-provider narrowing,BooleanOptionalActionbooleans, JSON-typed body args, ISO datetime coercion, URL overload merging (url_templates, longest fully-satisfied template wins). - OpenAPI ingestion (
dispatchers/openapi_schema.py): JSON or YAML,--openapi-path, specs embedded in HTML landing pages, 3.1typearrays rewritten toanyOf(expand_type_arrays),apiKeysecurity schemes materialized as parameters, menu tree andobb.reference-shaped metadata
(build_router_map,build_reference,detect_api_prefix,url_to_command); same-origin external$refs bundled with document-count (512), byte (8 MiB), depth (128) and no-redirect limits;.in URL segments maps to_. - Socrata support:
--socrata-story(or/resource/{uid}//api/views/{uid}URLs) builds a spec fromdatasetUids, resolves categorical choices via SoQL$group, emitsstart_date/end_dateandlimit/offset->$limit/$offset; the HTTP dispatcher rewrites$where/$order, fetches
all pages forlimit=0and truncates to N most recent dates. - Auth hooks: an importable
module:attributecallable (AuthContext->AuthDecision(headers, query_params, allow, deny_reason), sync or async) configured globally or per[specs.<ns>]; a deny short-circuits withAccessDeniedand hides commands from introspection. --generate-extension(openbb_cli.codegen): a hatchlingpyproject.tomlwithopenbb_provider_extension/openbb_core_extensionentry points and a[tool.openbb-codegen]provenance block, oneRouterper namespace, oneQueryParams/Data/Fetchermodule per GET command, POST commands
under atoolsprovider, aProvider(...)module, README,utils.py,record_httptest modules with VCR redactions; output post-processed withruff check --fixandruff format; credential-looking params and required path-item headers/cookies are promoted intocredentials=[...].- Backend-pluggable REPL:
openbb_cli.backend(Backendprotocol,LocalBackend,SpecBackend,SpecTranslator) soopenbb -i --spec X.specoropenbb -i --server URLruns the full REPL withoutopenbbinstalled;openbb -i <command ...>seeds the queue. - Output adapters
openbb_cli.outputs:RichTableOutput,JsonOutput,TsvOutput,HtmlOutput,StdioOutput;Session.output_adapterfollowssettings.OUTPUT_MODE. - Plotly figure rendering:
is_plotly_figure,render_figure_htmlfromassets/figure.html(inlined plotly.js with CDN fallback),show_figure,strip_theme_colors; TSV mode prints the figure JSON; the HTTP dispatcher wraps figure payloads into anOBBjectwithChart(format="plotly"). load -f/--file PATH [--sheet-name NAME] [--register_key KEY]in every menu (CSV/JSON/XLSX/XLS/DB/SQLite) with a lazySQLiteTablewrapper and tab completion./feature/menu (FeatureController):list,select,info,view,query,colname,coltype,addcol,dropcol,renamecol,modifycol,join,copy,save,delete,results./user/menu (UserController) with one toggle or-v/--valuecommand perobb.user.preferencesfield and a/user/credentials/submenu (CredentialsController) with masked status; session-only.- SQLite export (
--export db|sqlite|sqlite3) viaDataFrame.to_sqlwith an overwrite/append/new-table prompt. - SSE streaming end to end:
_HttpSSESourcereturns anOBBStreamfortext/event-streamcommands, one-shot mode follows to stdout until end or Ctrl+C,PlatformController._follow_streamdoes the same, codegen emits streaming fetchers (aextract_data -> AsyncIterator[str],stream_data) and
OBBStream.from_querycommands. - The HTTP dispatcher coerces rows to the spec's column types, attaches
extra["results_metadata"]andextra["metadata"](Metadatawith duration and route) and returns a realOBBject. - Completion:
results --index/--keyfrom the live registry,load --filefrom the data directory, spec-mode flags and choices,complete_while_typing=True.
Patterns
[dependency-groups] dev = ["openbb-devtools>=2.0.1"],[tool.uv.sources]foropenbb-coreandopenbb-charting, committeduv.lock; ruff with numpy pydocstyle and[tool.ty](src.include = ["openbb_cli"]); targeted# ty: ignore[code]and# noqadirectives..coveragerc(source = openbb_cli,parallel = True, omitsopenbb_cli/cli.pyand assets) withcoverage combineof subprocess partials inconftest.py; 29# pragma: no covermarkers across 11 files.cli/conftest.pybuilds and installs a real hatchling extensionopenbb-cli-fakeexposingobb.cli_test.{echo,quote,bomb,rows}, triggersopenbb-buildin a fresh subprocess, snapshots/restoresopenbb/packageandopenbb/assets, and provides a session-widerun_in_obbworker.- Static HTML lives in
openbb_cli/assets/figure.htmlwith__TITLE__/__PLOTLYJS__/__FIGURE__tokens. lint-openbb-cli.yml(ruff format/check + ty on changedcli/**/*.py) replaces the sharedgeneral-linting.yml; theopenbb-clitest workflow runs a 9-way matrix; nopublish-openbb-cli.ymlexists.- Lazy imports of
openbb,openbb_coremodels andprompt_toolkit(inside functions orlru_cacheaccessors) so the CLI starts in about 50 ms against a.spec. - Docstrings normalized to numpy style;
# pylint: disablebanners, inline comments and TODOs stripped.
Fixes
- Path-item-level
parameters(in: path/in: query) are inherited by every operation with operation-level overrides on(name, in); required path-itemheader/cookieparams route through credential handling. allOfcompositions in response and request-body schemas collapse into one object schema (merge_allof);deref_schema/merge_allofskipdefault,example(s),enum,const,x-*.- Generated POST signatures use Python-safe identifiers (
from,REB-APIKEY), dedupe on the emitted identifier and key payloads by wire name. - Generated provider tests use
safe_field_namePython parameter names. unpack_responseonly unwraps when every list item is a dict or the list is the payload's only key;_envelope_inner_schemaskips scalar item schemas.- Generated pydantic classes coerce
[]toNoneon optional object-typed fields (PHP-style serializers). fetch_openapisurfaces the parse error from a 2xx non-OpenAPI response (_raise_fetch_failure) instead of silently re-fetching.strip_theme_colorsremovestemplateand every*colorlayout key beforesend_figure.ArgparseClassProcessor._custom_groups_from_referencematches routes by the flattenedclass_name_function_nameform;_get_action_typerecognizestypes.UnionType; custom-type flattening skips*args/**kwargs.__patch_controller_functionswraps itsyieldintry/finally;system_clearusessubprocess.run("cls"|"clear", shell=True, check=False); rich/html adapters fall back to the terminal table whensession.backendisNoneorsend_tableraises.- Sub-menu partitioning uses exact prefix matching (
f"{router}_{path}_" in f"{name}_",translator_name.startswith(sub_prefix)). BaseController.load_classrefreshes a cached controller's completer (update_completer(choices_default)) before re-entering its menu.
openbb-platform-api
openbb-platform-api 1.3.6 -> 2.0.0 is almost entirely #7494: hatchling packaging, the app/, models/, service/ split behind tested import shims, the layered openbb.toml bootstrap, --spec proxy mode and a 489-test suite.
#7677 flipped the license, #7518 trimmed default_apps.json, and direct commits 768e52c6358 (merge widgets), 1cbb24d8b7a, 5b1bc33e579 and bf0cb48465f followed. The metapackage still
pins openbb-platform-api = "^1.3.6".
Removed
- The "Example BLS App" dashboard (
economy_survey_bls_search_bls_obb,economy_survey_bls_series_bls_obb) fromassets/default_apps.json. - README sections Markdown Widget, Table Widget, Metric Widget, Query Parameters, Easy Date Picker, Annotated Query Params, Annotated Table Fields, Export apps.json, Installation, Usage, Launch Custom App (collapsed into
## Install, a launch sample and one "Example Application" block). - The pandas import in
OmniWidgetResponseModel.validate_model(MRO-based_is_pandas_dataframeandzip(..., strict=True)instead).
Breaking
- Packaging:
[project] version = "2.0.0", hatchling,[dependency-groups] dev = ["openbb-devtools>=2.0.1", "httpx>=0.28.0,<1.0.0"],uv.lockadded (poetry.lockstill committed);openbb-core>=2.0.0,deepdiff>=8.6.2,tomli>=2.0on py<3.11; license Apache-2.0 with a new README license
section. main.pyis a bootstrap:_short_circuit_on_help(),_bootstrap_config(), thenglobals().update(...)ofapp.app;uvicorn.runstill targetsopenbb_platform_api.main:appand theopenbb-apiscriptopenbb_platform_api.main:main.utils/api.pyis a lazy__getattr__shim (parse_args/LAUNCH_SCRIPT_DESCRIPTION->app/args.py,import_app->app/bootstrap.py,check_port/get_user_settings->utils/network.py,get_widgets_json/FIRST_RUN/PATH_WIDGETS/logger->service/widgets_service.py);
query_models.py,response_models.py,utils/merge_agents.py,utils/merge_apps.pyre-export frommodels/andservice/.- Route discovery uses
iter_api_routes(app)andgetattr(route, "original_route", route).endpoint, which is what makesinclude_routerroutes discoverable under FastAPI 0.137+. import_app(...) -> FastAPIinstalls the sixExceptionHandlersinline and adds CORS through the idempotentapply_cors_from_system_service(app); the defaultrest_api.appis imported only when no--app/--specapp was supplied; TOML[middleware] hooksare registered at import.- widgets.json:
format: "date"->cellDataType: "dateString"; adatefield with a date cell type gets"sort": "desc";fiscal_year/year/year_born/calendar_year->cellDataType: "text",formatterFn: "none"; routes with a 2xxevent-streamcontent type are skipped. --spec(or[spec]) and--appare mutually exclusive.
New
--spec <path>/[spec] path: anopenbb-cli.spec(version 5,content_sha256verified, optional deploy pin) becomes an aiohttp-backed proxy FastAPI app, one route per command at itsurl_path, with hop-by-hop headers filtered,{path}placeholders substituted andwire_namequery
rewriting.- Multi-spec mode: each
[spec.NAME]subtable (path,mount,base_url,content_sha256,[spec.NAME.headers],[spec.NAME.auth] hooks,[spec.NAME.middleware] hooks) mounts its own sub-app on a parent FastAPI (app.state.openbb_specs); mount collisions raise at startup. [spec.headers]/[spec.NAME.headers]inject static upstream headers with$VAR/${VAR}expansion (unresolved entries skipped with a warning; config headers override incoming ones).- Spec launches rewrite widget defaults (
source: [<spec filename>],mcp_tool.mcp_server, namespacedmcp_tool.tool_id) and trim uniformT00:00:00suffixes from date columns in proxied JSON (top-level lists andresults/data/rows/recordsenvelopes). --config-file <path>(orOPENBB_API_CONFIG/OPENBB_CONFIG) selects the explicit layer of the core cascade; a[launcher]table supplies defaults for any CLI flag (CLI wins); malformed explicit TOML raises at startup;[env]is pushed intoos.environwithout clobbering shell variables,
with chained$VARsubstitution.[middleware] hooks = ["module:async_callable", ...]registers Starlette-style HTTP middleware (validated at startup; first entry outermost); per-spec[spec.NAME.auth]/[spec.NAME.middleware]hooks are registered on the sub-app asBaseHTTPMiddleware.-has an alias of--help, handled before the openbb-core stack is imported.- SSRM auto-promotion: a route whose request body is (or
allOf-extends)AgGridRowsRequest, or whose 200 response isAgGridRowsResponse[...]/ has{rowData, rowCount}, is emitted astype: "ssrm_table"withrunButton: trueand an emptydataKey;get_data_schema_for_widgetfalls back to
the POST operation and descends intorowData.items. - Inline-schema fast paths in
get_data_schema_for_widget(results.items,rowData.items, bare object schema) and a defensivecomponents.schemaslookup for apps without acomponentsblock. apply_cors_from_system_service(app) -> bool(idempotent) applied to every app path including the spec proxy.- Package layout
app/(args,bootstrap,config,middleware,spec,app),models/(query,response),service/(widgets_service,apps_service,agents_service),utils/network.py;synthesize_openapi_from_spec(spec)helper (exercised only by tests); spec provenance on
app.state.openbb_spec_*. - README sections "Spec-driven proxy mode",
[spec]credential injection, "Custom HTTP middleware", "Single-file launch".
Patterns
- Ruff (numpy pydocstyle, per-file ignores for tests) and
[tool.ty](unresolved-import = "warn") in-package;# ty: ignore[...]in place of pylint disables (one# pylint: disable=import-outside-toplevelremains in a README sample). - Tests mirror the package (
tests/app,tests/models,tests/service,tests/utils,tests/test_compat_shims.py): 6 files / 61 tests on develop -> 16 files / 489 on v5,httpxin the dev group forTestClient,.coveragercwithshow_missing. .github/workflows/test-unit-platform-api.yml: PRs to develop/v5/feature/cli-2 touching platform_api, core or devtools, 9-cell matrix,uv pip install --system -e . --group dev,pytest tests --cov=openbb_platform_api --cov-config=.coveragerc; no publish workflow.- Config is loaded once into
_BOOTSTRAPPED_CONFIGvia core'sload_layered_config(the bootstrap call applies[system]/[user]and env promotion;parse_argsre-reads withapply_to_services=False, apply_to_env=False). tests/test_compat_shims.pyasserts every legacy import path resolves to the same V5 objects and that theutils.apiproxy reflects livewidgets_servicestate.check_for_platform_extensionslives inapp/bootstrap.py(lazySystemServiceimport);service/__init__.pyre-exportsFIRST_RUN/PATH_WIDGETSby value whileapp/app.pymutateswidgets_service.FIRST_RUN.
Fixes
get_additional_agentsno longer crashes onendpoints.startwith(path)/agents[k][v]["endpoints"][name]; the rewrite usesendpoint_path.startswith(path)and guards non-dict values.PdfResponseModel.validate_modelno longer raisesUnboundLocalErroron the url-only path.OmniWidgetInput._validate_promptrepairs trailing commas on the inputv(develop ran the regex on an empty placeholder) and passes non-string scalars through./widgets.jsonin--editablemode reloads from disk on every request including the first.fix_router_widgetsprefixes bare relative endpoints (endpoint,wsEndpoint,imgUrl, paramendpoint,optionsEndpoint) and keys merged widgets bywidgetId(768e52c6358).parse_argsjoins--agents-json/--widgets-json/--apps-jsondirectories withos.path.joinand detectsmodule:attrnotation soC:\path\file.pyis not mis-split.- Form-widget POST schemas are looked up on the form endpoint path;
OmniWidgetResponseModelguardscontent is not None and parse_as.
openbb-mcp-server
openbb-mcp-server 1.4.1 -> 2.0.0 (#7495, plus the relicense in #7677) is a ground-up rewrite on fastmcp>=4.0.9 and fastapi>=0.138.2:
stateless BM25 tool discovery, a layered openbb.toml launcher, --spec proxy mode, run_pipeline chaining, ChartArtifactMiddleware, optional openbb-cli dispatcher tools and a 100% branch-coverage gate. Direct commits aba09afb1c5 and bf0cb48465f added the serve_app conftest fixtures and
README lint.
Removed
- Admin tools
activate_tools,deactivate_tools,activate_category;ToolInfo.active;CategoryIndex.has_tool(). - Settings
cache_expiration_seconds,on_duplicate_tools,on_duplicate_resources,on_duplicate_prompts,resource_prefix_format,dependencies,deprecation_warningsand theirOPENBB_MCP_*aliases. TokenAuthProvider.authorize()and itsresource_server_url/authorization_url/token_urlattributes.econometrics,quantitative,technicalfrom the defaultmodule_exclusion_map(only{"coverage": "openbb_core"}remains).ProcessedRouteData.removed_routes(nowexcluded_routes);key:value,key:valuedict parsing inparse_args(env vars keep it); theEnv()instantiation inparse_args.poetry.lock,tests/app/test_tool_execution.py,tests/utils/test_compress_schema.py.
Breaking
- Packaging: hatchling/PEP 621,
[dependency-groups] dev = ["openbb-devtools>=2.0.1", "httpx>=0.28.0,<1.0.0", "openbb-cli>=2.0.0", "openbb-mcp-fixture"],uv.lock;openbb-core>=2.0.0,fastapi>=0.138.2,fastmcp>=4.0.9,tomli>=2.0(py<3.11); license Apache-2.0. openbb-mcp->openbb_mcp_server.main:main(app.app.mainis a shim; the launcher body islaunch_mcp());parse_args()inapp/args.pyreturns{app, transport, mcp_overrides, uvicorn_overrides};import_appinapp/bootstrap.py;cl_doc->LAUNCH_SCRIPT_DESCRIPTION(lazy aliases in
utils/app_import.py).create_mcp_server(auth=...)acceptsAuthProvider | tuple[str, str] | list[str] | None(TypeErrorotherwise);TokenAuthProvider(TokenVerifier)takes a(username, password)tuple;get_auth_provider(auth).- Discovery is stateless: with
enable_tool_discoveryroute tools stay enabled but hidden byOpenBBToolCatalog;default_tool_categoriesis ignored;mcp_config.enable: falseno longer disables a tool in that mode; without discovery all route tools are disabled and only_enabled_tools
re-enabled. available_toolsis synchronous and reports name plus description only; non-GET tools on multi-method paths get a_<method>suffix (demo_items_post);allowed_tool_categoriesis enforced ("Unknown tool" for anything outside it);module_exclusion_map={}hides nothing.output_schemaisNonefor routes without a JSON 2xx response; JSON routes get a compressed, description-trimmed schema with the OBBjectchartfield replaced by theClientArtifactschema.StaticPrompt.renderreturnslist[Message | str];execute_prompt(prompt_name=...)->get_prompt(name=...); route-prompt arguments are emitted in first-appearance order, tagged with the served path and only for routes exposing a method.on_duplicate_*collapsed intoon_duplicate(OPENBB_MCP_ON_DUPLICATE);--versionsetsMCPSettings.version;write_to_fileomits a defaultdefault_skills_dir.process_fastapi_routes_for_mcpexpresses exclusions asMCPType.EXCLUDERouteMaps and walks routes withfastapi.routing.iter_route_contexts;ProcessedRouteData.exposed_methodsadded.
New
--spec <path>and[mcp.spec]/[mcp.spec.NAME]tables: a.spec(version 5,content_sha256integrity plus optional operator pin) becomes a FastAPI proxy exposed as MCP tools, with per-mount headers ([mcp.spec.headers]with$VARsubstitution),wire_namequery rewriting, zero-time
date trimming and hooks;--specand--appare mutually exclusive.--config-file <path>($OPENBB_MCP_CONFIG/$OPENBB_API_CONFIG/$OPENBB_CONFIG) with[mcp]defaults for any CLI flag (CLI wins, TOML beats env) and[env]injection.[mcp.auth]and[mcp.middleware]hookslists ofmodule:attrasync callables wrapped asBaseHTTPMiddlewareon the HTTP/SSE transports, between CORS andSSEShutdownWrapper.run_pipeline(always registered):PipelineStepwithtool,arguments,id,inputsmapping an argument to an earlier step'sresults; ids, references andoutputsvalidated before any step runs.search_tools(BM25, max 5 results) andcall_toolfromOpenBBToolCatalog, which hides route tools fromlist_tools.- openbb-cli dispatcher tools
openbb_dispatch,openbb_batch_dispatch,openbb_list_commands,openbb_describe_command(registered whenopenbb-cliis importable andenable_cli_toolsis true, default True;cliextraopenbb-cli>=2.0.0). expose_choices: providerchoicesandx-widget_configoptions become anenumor a "Valid values" note;optionsEndpointbecomes a note naming the listing tool.ChartArtifactMiddleware: line/bar/scatter/pie/donut Plotly figures become WorkspaceClientArtifactchartartifacts withcontentrows andchart_params, everything else atableartifact; typed-arraybdatais decoded;artifact_output_schemarewrites the OBBjectchartoutput field.MCPConfigModeldeclaresname,tags,enable,describe_responses,mime_type;exclude_argsis applied;_trim_model_descriptionskeeps only the first paragraph of object descriptions.- Bundled skill
use_openbb_cli(skill://use_openbb_cli/SKILL.md); existing skills rewritten for stateless discovery,run_pipeline, chart artifacts anduv pip install -e . --group dev. openbb-mcp --help/-hprintsLAUNCH_SCRIPT_DESCRIPTIONbefore any bootstrap; unknown--key valuerouting (settings fields,--httpx-<option>, uvicorn) is documented.- Public helpers
strip_api_prefix,route_naming,tool_name_for_route; the installable test extensionopenbb-mcp-fixture(mcp_fixturerouter withecho,fail, POSTscale) auto-installed by conftest. - Workflows
publish-openbb-mcp-server.yml(release branch, PyPI check,uv build --no-sources, trusted publishing) andtest-unit-mcp-server.yml(ruff,ty check,--cov-branch --cov-fail-under=100on 3.10-3.14 across ubuntu/macos/windows).
Patterns
- ruff (numpy pydocstyle) and
tyin pyproject and CI;# pylint: disablestripped; numpy docstrings with Parameters/Returns/Raises. [tool.coverage.run] branch = true; pytestfilterwarnings = ["error", ...].- Layered
openbb.tomlvia coreload_layered_config; theisolated_configfixture patchesloader.USER_OPENBB_DIR. - Tests dispatch against the real installed fixture extension;
test_auth.py,test_cli_tools.py,test_spec.pyserve the app with uvicorn on a free loopback port viaserve_app. - Subpackage
__init__.pyfiles eagerly import a subset of modules; legacy paths stay alive through theutils/app_import.py__getattr__alias. - The spec proxy imports
aiohttpat call time without declaring it; it is satisfied transitively throughopenbb-core>=2.0.0.
Fixes
- Passing a FastMCP
AuthProvidertocreate_mcp_server(auth=...)works (develop silently dropped it); a(username, password)pair builds the verifier from the pair itself (develop readsettings.server_authand rejected every token when it wasNone). install_skillrejects names outside[a-z0-9][a-z0-9_-]*and files whose path escapes the skill directory.- Server-prompt arguments without a
descriptionare no longer dropped (validated_arg.get("description")). _load_settings_from_envrecognizes PEP 604 unions, soOPENBB_MCP_UVICORN_CONFIGandOPENBB_MCP_MODULE_EXCLUSION_MAPparse from env.TokenAuthProvider.verify_tokenuses strict base64, byte-wisesecrets.compare_digestandpartition(b":").get_httpx_kwargscopieshttpx_client_kwargsinstead of mutating it;SSEShutdownWrapper.safe_sendno longer re-sends a response start.- README:
--portdefault 8001, client URLs/mcp, prompt typos fixed; skills importmake_requestfromopenbb_core.provider.utils.helpers.
openbb-technical
openbb-technical 1.6.2 -> 2.0.0 (#7502) deleted the 1916-line technical_router.py and rebuilt the extension as indicators/, signals/ and multi/ sub-packages aggregated by openbb_technical/router.py, keeping all 27 V4 commands by name
and adding 32 endpoints for 59 routes.
#7537 adapted the catalog to FastAPI 0.137+ and #7677 relicensed it; ten direct commits touched locks, ty ignores and workflows.
Removed
openbb_technical/technical_router.py(importingopenbb_technical.technical_routerfails; a dead ImportError-guarded fallback remains inmulti/compose.py).kc.mamodevalueswma,hma,zlma; theDMP_<n>/DMN_<n>columns ofadx;fibfieldsmin_date,max_date,min_pr,max_pr,lvl_text; thespan_*forward cloud rows ofichimoku;clenow's string-formatted columns.poetry.lock;tests/test_technical_helpers.py(replaced bytests/test_helpers.pyand per-family test packages); every# pylint: disabledirective.
Breaking
- Packaging: hatchling/PEP 621,
openbb-core[pandas]>=2.0.0,pandas-ta-openbb>=0.4.23,scikit-learn>=1.6.0, newscipy>=1.11andstatsmodels>=0.14;[dependency-groups] dev = ["openbb-devtools>=2.0.1", "openbb-charting>=3.0.0"]; entry pointopenbb_technical.router:router; license
Apache-2.0;iter_api_routesrequired. - Every command takes
params: XxxQueryParams(HTTP params move to the JSON body) and returns typedXxxDatarows withdateplus renamed indicator columns; pandas-ta backed indicators drop warm-up rows. - Defaults and types:
bbands.length50 -> 20,bbands.stdPositiveFloat,adx.length50 -> 14,kc.scalar20 -> 2.0,atr.drift/stochperiods/adx.drift/rsi.driftand thersi,macd,aroon,sma,ema,wma,hma,zlmalengthsPositiveInt;rsi/adx/aroon.scalar
PositiveFloat;cones.trading_periodsPositiveInt | None. - Column renames:
bbands(lower, middle, upper, bandwidth, percent),kc/donchian(lower, middle, upper),macd(macd, signal, histogram),aroon(aroon_up, aroon_down, aroon_oscillator),ichimoku(tenkan_sen, kijun_sen, senkou_a, senkou_b, chikou_span),fisher
(fisher, signal),stoch(k, d),cones(lower,upper, integerwindow),fib(level,price),demark(date, up, down);clenowreturns per-barpredicted,r2,coefficient,annualized_coefficientfloats. - Signals are mounted under
/technical/signals/*;relative_rotation(params: RelativeRotationQueryParams)is categorisedmultiand its crypto example was dropped.
New
- Overlays
tema,dema,kama,frama(evenwindow, native numpy),vwma,supertrend(supertrend,direction,long_band,short_band). - Oscillators
williams_r,mfi,trix,ultimate_oscillator,awesome_oscillator; trenddi(plus_di,minus_di,dx) andchoppiness. - Volatility
realized_volatility(std,parkinson,garman_klass,hodges_tompkins,rogers_satchell,yang_zhang; defaultyang_zhang,window=30) andrealized_volatility_compare; structurepivot_points(classic/fibonacci/woodie/camarilla/demark, day/week/month). - Statistics
drawdown,returns_stats(mean/std/skew/kurtosis/Sharpe/Sortino/Calmar/max_drawdown/VaR95/CVaR95, summary or rolling),stationarity(ADF/KPSS),hurst(rs/dfa),autocorrelation(ACF/PACF with 95% bands). - Signals
signals.crossovers,signals.oscillator_signals,signals.divergences,signals.breakouts,signals.candlestick_patterns(doji, hammer, engulfing, marubozu, spinning_top),signals.regime. - Multi-symbol and utility endpoints
multi,correlation,correlation_matrix,screen(gt/gte/lt/lte/eq/between/crossed_above/crossed_below/made_high/made_low), and the introspectedindicatorscatalog filterable bycategory. - Every endpoint QueryParams declares
__category__and__output_columns__; adocs/tree (getting-started, four user guides, generatedapi-reference.md) and a README endpoint table; integration tests run against committed SPY CSV fixtures and an in-process uvicorn server. - Unit-test tree:
tests/conftest.py,tests/test_router.py,tests/test_helpers.py,tests/test_technical_views.py,tests/test_relative_rotation.py,tests/indicators/,tests/signals/,tests/multi/.
Patterns
- Hatchling with
[tool.uv.sources]for openbb-core and openbb-charting, committeduv.lock; ruff (numpy pydocstyle) andtywith# ty: ignore[code]; explicit sdist include list. test-unit-openbb-technical.ymlandpublish-openbb-technical.ymlwith--cov-fail-under=100(reasons on every# pragma: no cover); router composed viaRouter.include_routerwith per-module__all__;class TestXfiles with a shared OHLCV fixture; integration markedintegrationand
excluded frompytest tests.technical_views.pyimportsopenbb_chartinglazily inside functions; openbb-charting is a dev-group dependency only.
Fixes
RelativeRotationFetcher.transform_querycallsmodel_validate(params)instead of the invalidmodel_validate(**params).- Catalog introspection uses
iter_api_routes(family_router.api_router). technical_relative_rotationvalidatestail_intervalagainstday|week|month(fallbackweek).demarkhandles bothEXHC_UPa/EXHC_DNaandEXHC_UP/EXHC_DNcolumn spellings.stochhonours the user-supplied periods (V4 passedfast_k_period=/slow_d_period=/slow_k_period=which pandas-ta swallowed, always computing 14/3/3); V5 passesk,d,smooth_k.
openbb-quantitative
openbb-quantitative 1.6.2 -> 2.0.0 (#7506) keeps all 19 V4 commands under the same paths but rewrites each to