Ctx Langextract¶
ctx_langextract — mvp.ctx_langextract
Cluster: Context & Retrieval | Type: component | MCP Tools: 26
Overview¶
Structured information extractor that pulls typed field values from free-form text using a backend-aware strategy: google/langextract is attempted when available, and regex heuristics provide the dependency-free fallback. Within regex extraction, caller-supplied patterns take priority, then built-in heuristics cover common types (email, URL, date, phone, currency amount, number, person name, ZIP code, IP address), and finally a field_name: value label-colon pattern catches anything else. Returns a flat dict of extracted values alongside the source text and a canonical degradation envelope.
Pilot-readiness caveat
ctx_langextract is pilot-ready for local MCP workflows and first-user demos, especially when schemas use built-in fields or explicit regex patterns. Do not present the regex fallback as high-accuracy general NLP. When google/langextract or the G6 LLM path falls back to regex, outputs are marked completion_state: qualified-draft with degraded, degradation_reason, warning_card, evidence, backend_attempted, and backend_used. Arbitrary domain fields need custom patterns, templates, or a configured LLM backend, and results should be reviewed before use in regulated, paid-customer, or unattended production workflows.
Capabilities: info exposes source_capabilities for regex_heuristic, google_langextract, G6 LLM, SQLite persistence, search backend, returned-set rerank status, and the degradation taxonomy.
Quality: evaluate_quality reports quality_method: exact_match. It compares strings exactly with no semantic normalization, so date-format variants or synonyms can fail even when a human would consider them equivalent.
When to use:
- Parsing structured fields (emails, dates, amounts) from unstructured documents or LLM outputs
- Lightweight extraction where a full NLP pipeline would be overkill
- Post-processing scraped or converted text to populate a schema
Example:
from mvp.ctx_langextract import CtxLangExtractBlock, ExtractInput
block = CtxLangExtractBlock(name="extract")
result = block.infer(ExtractInput(
text="Invoice date: 2026-01-15. Contact: [email protected]. Total: $1,200.00",
schema_fields=["date", "email", "amount"],
))
# result.value.extracted → {"date": "2026-01-15", "email": "[email protected]", "amount": "$1,200.00"}
Works well with: ctx_markitdown, ctx_scrapling, align_specs
Public API¶
LangExtractRerankDecision¶
Validated advisory rerank verdict over a returned search-record set.
| Field | Type | Default |
|---|---|---|
ordered_indices | tuple[int, ...] | required |
dropped_indices | tuple[int, ...] | () |
rationale | str | '' |
eligible_fingerprint | str | '' |
confidence | float | 0.0 |
degraded | bool | False |
raw_response | str | '' |
LLMLangExtractRerankRuntime¶
Provider-neutral search-result-rerank runtime backed by G6's LLM caller.
Constructor:
| Parameter | Type | Default |
|---|---|---|
llm | LLMCaller \| None | None |
Methods:
rerank(query: str, records: list[Any]) -> LangExtractRerankDecision¶
CtxLangExtractRerankPatternRuntime¶
Stateless, load-bearing returned-set-ceiling enforcement.
Methods:
enforce_eligibility(decision: LangExtractRerankDecision, records: list[Any]) -> tuple[list[Any], bool, bool]¶
CtxLangExtractPlanner¶
Runtime-first advisory result-rerank facade with returned-order fallback.
Constructor:
| Parameter | Type | Default |
|---|---|---|
runtime | LangExtractRerankRuntime \| None | None |
pattern_runtime | CtxLangExtractRerankPatternRuntime \| None | None |
Methods:
rerank(query: str, records: list[Any]) -> list[Any]¶
CtxLangExtractBlock(AIBlock[ExtractInput, ExtractOutput, None])¶
Structured extraction from free text.
| Field | Type | Default |
|---|---|---|
name | str | 'ctx_langextract' |
resource_bounds | ResourceBounds \| None | None |
usage | ResourceUsage | field(default_factory=ResourceUsage) |
Methods:
infer(data: ExtractInput) -> Result[ExtractOutput]¶
capabilities() -> dict[str, Any]¶
bias() -> dict¶
ExtractInput(BaseModel)¶
Input to CtxLangExtractBlock.
| Field | Type | Default |
|---|---|---|
text | str | required |
schema_fields | list[str] | required |
patterns | dict[str, str] | Field(default_factory=dict) |
run_mode | Literal['beta', 'production'] | 'beta' |
reviewer_signature | str | '' |
ExtractOutput(BaseModel)¶
Output from CtxLangExtractBlock.
| Field | Type | Default |
|---|---|---|
extracted | dict[str, str] | required |
text | str | required |
n_fields_found | int | required |
extractor | str | 'regex_heuristic' |
source_grounding | list[dict] | Field(default_factory=list) |
model_used | str | '' |
degraded | bool | False |
degradation_reason | str \| None | None |
completion_state | Literal['verified', 'qualified-draft', 'blocked-escalated'] | 'qualified-draft' |
warning_card | str | '' |
evidence | list[dict[str, Any]] | Field(default_factory=list) |
request_id | str | '' |
task_id | str | '' |
run_id | str | '' |
backend_attempted | str | '' |
backend_used | str | '' |
CtxLangExtractMCPBlock(AIBlock[MCPLangExtractInput, MCPLangExtractOutput, dict])¶
Full-featured extraction block with SQLite persistence.
| Field | Type | Default |
|---|---|---|
name | str | 'ctx_langextract_mcp' |
state | dict \| None | None |
db_path | str | ':memory:' |
resource_bounds | ResourceBounds \| None | None |
usage | ResourceUsage | field(default_factory=ResourceUsage) |
agentic_planner | CtxLangExtractPlanner \| None | None |
Methods:
infer(data: MCPLangExtractInput) -> Result[MCPLangExtractOutput]¶
MCPLangExtractRecord(BaseModel)¶
| Field | Type | Default |
|---|---|---|
id | str | required |
record_type | str | required |
key | str | required |
value | str | required |
tags | list[str] | Field(default_factory=list) |
timestamp | str | required |
metadata | dict[str, Any] | Field(default_factory=dict) |
MCPLangExtractInput(BaseModel)¶
| Field | Type | Default |
|---|---|---|
op | Literal['extract', 'batch_extract', 'add_pattern', 'list_patterns', 'validate_pattern', 'create_schema', 'get_schema', 'list_schemas', 'delete_schema', 'save_session', 'load_session', 'list_sessions', 'delete_session', 'record_extraction', 'query_extractions', 'summarize_extractions', 'store_template', 'retrieve_template', 'list_templates', 'llm_extract', 'llm_batch', 'search', 'info', 'evaluate_quality', 'get_field_stats', 'agentic_patterns'] | required |
text | str | '' |
texts_json | str | '' |
schema_fields | list[str] | Field(default_factory=list) |
patterns_json | str | '{}' |
field_name | str | '' |
pattern | str | '' |
test_text | str | '' |
name | str | '' |
description | str | '' |
query | str | '' |
limit | int | 50 |
top_k | int | 5 |
tags | list[str] | Field(default_factory=list) |
source | str | '' |
fields_json | str | '[]' |
session_name | str | '' |
state_json | str | '{}' |
schema_name | str | '' |
extracted_json | str | '{}' |
n_fields_found | int | 0 |
n_fields_total | int | 0 |
extraction_id | str | '' |
ground_truth_json | str | '{}' |
agentic_rerank | bool \| None | None |
run_mode | Literal['beta', 'production'] | 'beta' |
reviewer_signature | str | '' |
MCPLangExtractOutput(BaseModel)¶
| Field | Type | Default |
|---|---|---|
op | str | required |
key | str | '' |
value | str | '' |
found | bool | False |
count | int | 0 |
records | list[MCPLangExtractRecord] | Field(default_factory=list) |
retrieved | list[str] | Field(default_factory=list) |
scores | list[float] | Field(default_factory=list) |
summary | str | '' |
message | str | '' |
extracted | dict[str, str] | Field(default_factory=dict) |
batch_results | list[dict[str, Any]] | Field(default_factory=list) |
patterns | dict[str, str] | Field(default_factory=dict) |
metadata | dict[str, Any] | Field(default_factory=dict) |
degraded | bool | False |
degradation_reason | str | '' |
completion_state | Literal['verified', 'qualified-draft', 'blocked-escalated'] | 'qualified-draft' |
warning_card | str | '' |
evidence | list[dict[str, Any]] | Field(default_factory=list) |
request_id | str | '' |
task_id | str | '' |
run_id | str | '' |
backend_attempted | str | '' |
backend_used | str | '' |
quality_method | str | '' |
agentic_evidence | dict[str, Any] | Field(default_factory=dict) |
LangExtractStore¶
Sync SQLite store with 6 tables.
Constructor:
| Parameter | Type | Default |
|---|---|---|
db_path | str | ':memory:' |
Methods:
upsert_schema(name: str, fields_json: str, patterns_json: str, description: str) -> str¶
get_schema(name: str) -> dict[str, Any] | None¶
list_schemas(limit: int = 50) -> list[dict[str, Any]]¶
delete_schema(name: str) -> bool¶
upsert_session(name: str, state_json: str) -> str¶
get_session(name: str) -> dict[str, Any] | None¶
list_sessions(limit: int = 50) -> list[dict[str, Any]]¶
delete_session(name: str) -> bool¶
add_extraction(schema_name: str, text: str, extracted_json: str, n_fields_found: int, n_fields_total: int, source: str) -> str¶
query_extractions(schema_name: str = '', source: str = '', limit: int = 50) -> list[dict[str, Any]]¶
upsert_template(name: str, fields_json: str, patterns_json: str, description: str, tags: list[str]) -> str¶
get_template(name: str) -> dict[str, Any] | None¶
list_templates(limit: int = 50) -> list[dict[str, Any]]¶
add_quality_eval(extraction_id: str, ground_truth_json: str, field_scores_json: str, overall_score: float) -> str¶
query_quality_evals(extraction_id: str = '', limit: int = 50) -> list[dict[str, Any]]¶
upsert_pattern(field_name: str, pattern: str, description: str) -> str¶
get_pattern(field_name: str) -> dict[str, Any] | None¶
list_patterns(limit: int = 100) -> list[dict[str, Any]]¶
text_search(query: str, top_k: int = 5) -> list[dict[str, Any]]¶
TF-IDF search across schemas, templates, extractions, and custom patterns.
count_all() -> dict[str, int]¶
Functions¶
agentic_planner_enabled(default_enabled: bool) -> bool¶
Decide whether the agentic search-result-rerank planner should be used.
eligible_fingerprint(records: list[Any]) -> str¶
sha256 over the returned record texts (order-sensitive).
validate_langextract_rerank_decision(decision: LangExtractRerankDecision, n_eligible: int, expected_fingerprint: str) -> None¶
Returned-set / anti-injection guard for a search-result-rerank decision.
planner_is_llm_trusted(planner: Any) -> bool¶
Whether the BLOCK may report
llm_used=Trueforplanner.
MCP Tools¶
| Operation | Source |
|---|---|
extract | langextract_mcp |
batch_extract | langextract_mcp |
add_pattern | langextract_mcp |
list_patterns | langextract_mcp |
validate_pattern | langextract_mcp |
create_schema | langextract_mcp |
get_schema | langextract_mcp |
list_schemas | langextract_mcp |
delete_schema | langextract_mcp |
save_session | langextract_mcp |
load_session | langextract_mcp |
list_sessions | langextract_mcp |
delete_session | langextract_mcp |
record_extraction | langextract_mcp |
query_extractions | langextract_mcp |
summarize_extractions | langextract_mcp |
store_template | langextract_mcp |
retrieve_template | langextract_mcp |
list_templates | langextract_mcp |
llm_extract | langextract_mcp |
llm_batch | langextract_mcp |
search | langextract_mcp |
info | langextract_mcp |
evaluate_quality | langextract_mcp |
get_field_stats | langextract_mcp |
agentic_patterns | langextract_mcp |