Connector framework for financial data — typed fetch, hybrid-search catalogs, distribute via Hugging Face Hub or S3.
Project description
parsimony
Typed, composable data connectors for Python. A small kernel; every data source is a separate package discovered through the entry-point contract.
Why parsimony
- Light kernel.
parsimonyships as a small package (primitives, discovery, conformance, scaffolding). Data sources are separate PyPI distributions that plug in through a public contract. - One calling convention.
await connectors["name"](params)across every data source. Parameters are Pydantic models; results carry provenance. - Install what you need.
pip install parsimony parsimony-fred parsimony-sdmx— the kernel composes whatever is installed. - Private connectors as a first-class path. Customer-private and vendor-published plugins use the same entry-point contract as official ones; the kernel cannot tell them apart.
- MCP-ready. Connectors are agent-addressable via the Model Context Protocol — the server lives in the separate
parsimony-mcpdistribution.
Install
Pick what you need. The kernel has no connectors of its own:
pip install parsimony-core # kernel only (tiny footprint)
pip install parsimony-core parsimony-fred # + FRED
pip install parsimony-core parsimony-sdmx # + SDMX (ECB, Eurostat, IMF, OECD, BIS, World Bank, ILO)
pip install 'parsimony-core[standard]' # + canonical Catalog (FAISS + BM25 + sentence-transformers, hf:// loader)
pip install 'parsimony-core[standard,litellm]' # + LiteLLMEmbeddingProvider (OpenAI, Gemini, Cohere, Voyage, Bedrock)
pip install parsimony-mcp # MCP server (separate distribution)
Imports are always
from parsimony import ...; the bareparsimonyPyPI name is squatted, so the distribution ships asparsimony-core.
Full list of officially-maintained connectors: ockham-sh/parsimony-connectors.
30-Second Example
Fetch US unemployment rate from FRED:
import asyncio
from parsimony_fred import CONNECTORS as FRED
async def main():
fred = FRED.bind_deps(api_key="your-fred-key")
result = await fred["fred_fetch"](series_id="UNRATE")
print(result.data.tail())
print(result.provenance)
asyncio.run(main())
Or compose everything configured in the environment:
from parsimony import build_connectors_from_env
connectors = build_connectors_from_env()
result = await connectors["fred_fetch"](series_id="UNRATE")
build_connectors_from_env() walks every installed parsimony.providers entry point, binds dependencies from environment variables, and returns a single flat Connectors surface.
Core Primitives
Three decorators, one runtime type:
@connector— typed fetch/search; the bread and butter.@enumerator— catalog population (KEY + TITLE + METADATA, no DATA).@loader— observation persistence into aDataStore.
Provenance on every result:
result.provenance # Provenance(source="fred", params={"series_id": "UNRATE"}, fetched_at=...)
The Plugin Contract
Every data source is a separate distribution implementing one contract:
# your-connector/pyproject.toml
[project]
name = "parsimony-yourname"
dependencies = ["parsimony-core>=0.1.0,<0.3", "pydantic"]
classifiers = ["Framework :: Parsimony :: Contract 1"]
[project.entry-points."parsimony.providers"]
yourname = "parsimony_yourname"
Your module exports CONNECTORS (required), plus optional ENV_VARS and PROVIDER_METADATA. The full spec is in docs/contract.md — it's the framework's load-bearing surface.
Building a private connector for your organisation? See docs/building-a-private-connector.md for the customer-private path.
Discovering Plugins
from parsimony.discovery import discovered_providers
for provider in discovered_providers():
print(provider.distribution_name, provider.version, provider.connectors.names())
Or from the command line:
parsimony list-plugins # what's installed
parsimony conformance verify <package> # validate against the contract
parsimony conformance verify is the release-gate tool for every connector package and the security-review artefact for regulated-finance customers.
Security
- Allow-list by default. Officially-maintained plugins (
parsimony-<name>from ockham-sh/parsimony-connectors) load without opt-in. Non-official plugins requirePARSIMONY_TRUST_PLUGINS=<name1>,<name2>to load, with a structured log entry for every decision. - ABI gate. The kernel reads each plugin's contract-version classifier before importing the module. Mismatches fail loudly rather than mid-fetch.
- Single trust root. Official plugins publish from one signed manifest (
OFFICIAL_PLUGINS.json) under one publishing identity.
See SECURITY.md for disclosure.
MCP Server
The MCP server is a separate distribution, parsimony-mcp:
pip install parsimony-mcp
parsimony-mcp
Every tool-tagged connector becomes an MCP tool.
Documentation
Full docs at docs.parsimony.dev:
Contributing
- Kernel changes (this repo) — see
CONTRIBUTING.md. - New or updated connectors — contribute to ockham-sh/parsimony-connectors. The conformance suite is the merge gate.
The kernel does not accept provider-specific code. That's structurally enforced (see tests/test_kernel_purity.py).
License
Apache 2.0.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file parsimony_core-0.2.0a1.tar.gz.
File metadata
- Download URL: parsimony_core-0.2.0a1.tar.gz
- Upload date:
- Size: 69.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b435075478801b62e955c689431aa29ce93927a3125f787a4cba79cf382aaaf3
|
|
| MD5 |
3bdbf8e18aad1da3d988cb0b146768a8
|
|
| BLAKE2b-256 |
b5033f2393933151a36f33755428a7440969f7f26eab7b65d0215dafd709a418
|
Provenance
The following attestation bundles were made for parsimony_core-0.2.0a1.tar.gz:
Publisher:
publish.yml on ockham-sh/parsimony
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
parsimony_core-0.2.0a1.tar.gz -
Subject digest:
b435075478801b62e955c689431aa29ce93927a3125f787a4cba79cf382aaaf3 - Sigstore transparency entry: 1342804020
- Sigstore integration time:
-
Permalink:
ockham-sh/parsimony@e390305dba8cd11e807a1f828d882a260e361f45 -
Branch / Tag:
refs/tags/v0.2.0a1 - Owner: https://github.com/ockham-sh
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@e390305dba8cd11e807a1f828d882a260e361f45 -
Trigger Event:
release
-
Statement type:
File details
Details for the file parsimony_core-0.2.0a1-py3-none-any.whl.
File metadata
- Download URL: parsimony_core-0.2.0a1-py3-none-any.whl
- Upload date:
- Size: 83.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d747eade7d2c81e0b06b94ac482d3b294d3a4047a2dbeeeae58c450e0f517d44
|
|
| MD5 |
e96b4e21bc0264d1924421bacd9ba242
|
|
| BLAKE2b-256 |
e7f32188e0473b2dfd792abc444c405ed54e9d1646c8721ab64f4b64b42fc5ab
|
Provenance
The following attestation bundles were made for parsimony_core-0.2.0a1-py3-none-any.whl:
Publisher:
publish.yml on ockham-sh/parsimony
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
parsimony_core-0.2.0a1-py3-none-any.whl -
Subject digest:
d747eade7d2c81e0b06b94ac482d3b294d3a4047a2dbeeeae58c450e0f517d44 - Sigstore transparency entry: 1342804039
- Sigstore integration time:
-
Permalink:
ockham-sh/parsimony@e390305dba8cd11e807a1f828d882a260e361f45 -
Branch / Tag:
refs/tags/v0.2.0a1 - Owner: https://github.com/ockham-sh
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@e390305dba8cd11e807a1f828d882a260e361f45 -
Trigger Event:
release
-
Statement type: