← Files NimbleARCHIVED FILE
skills/nimble-web-expert/references/nimble-extract/parsing-schema.md
10 KB · Oct 5, 2026 · 18:08 UTC
---
name: nimble-parsing-schema-reference
description: |
Reference for --parser flag structured extraction. Load when markdown output lacks the specific fields needed.
Contains: schema and schema_list types, CSS/jsonpath/xpath selectors, text/attr/html extractors,
post-processors (regex, number, boolean, sequence), results in data.parsing.
---
# Parsing Schema
Docs: https://docs.nimbleway.com/nimble-sdk/web-tools/extract/features/parsing-schema
Structured data extraction using declarative selectors, extractors, and post-processors. Use when you need specific fields as clean structured output rather than free-form markdown.
## Table of Contents
- [CLI flags](#cli-flags)
- [Python SDK](#python-sdk)
- [Parser types](#parser-types)
- [Selector types](#selector-types)
- [Extractors](#extractors)
- [Post-processors](#post-processors)
- [Examples](#examples)
- [When to use structured parsing vs markdown](#when-to-use-structured-parsing-vs-markdown)
- [Notes](#notes)
---
## CLI flags
```bash
--parse # enable parsing
--parser '{"type": "schema", "fields": {...}}' # structured extraction schema
```
Without `--parser`, `--parse` returns cleaned markdown/HTML. With `--parser`, it returns structured JSON matching your schema.
## Python SDK
```python
from nimble_python import Nimble
nimble = Nimble()
resp = nimble.extract(
url="https://example.com/product",
render=True,
parse=True,
parser={
"type": "schema",
"fields": {
"title": {"type": "terminal", "selector": {"type": "css", "css_selector": "h1"}, "extractor": {"type": "text"}},
"price": {"type": "terminal", "selector": {"type": "css", "css_selector": ".price"}, "extractor": {"type": "text", "post_processor": {"type": "number"}}},
},
},
)
print(resp["data"]["parsing"])
# → {"title": "Product Name", "price": 49.99}
```
SDK uses underscores for keys (e.g. `post_processor`, `css_selector`). Pass the `parser` dict directly — no JSON serialization needed.
---
## Parser types
| Type | Output | Use for |
|------|--------|---------|
| `terminal` | Single value | One field |
| `terminal_list` | Array of values | List of same field (e.g. all image URLs) |
| `schema` | Object with named fields | Structured record (e.g. product) |
| `schema_list` | Array of objects | List of records (e.g. search results) |
| `or` | First non-null result | Fallback across multiple selectors |
| `and` | Merged object | Combine results from multiple schemas |
| `const` | Fixed value | Hardcode a field value |
---
## Selector types
| Type | Syntax | Use for |
|------|--------|---------|
| `css` | `{"type": "css", "css_selector": ".class"}` | Standard HTML elements |
| `xpath` | `{"type": "xpath", "path": "//element"}` | XML/HTML navigation, RSS feeds, namespaced XML |
| `json` | `{"type": "json", "path": "nested.key", "coercion_filter": "$[?...]"}` | Embedded JSON, LD+JSON |
| `sequence` | `{"type": "sequence", "sequence": [...]}` | Chain multiple selectors |
| `parent` | `{"type": "parent", "times": 2}` | Traverse DOM upward |
| `root` | `{"type": "root"}` | Access full response (needed for network_capture data) |
---
## Extractors
| Type | Description |
|------|-------------|
| `text` | Text content. Params: `strip` (bool, default true), `separator` (string) |
| `attr` | Attribute value (href, src, data-*, class, id) |
| `json` | JSONPath expression on JSON data |
| `raw` | Return element unchanged (default) |
---
## Post-processors
| Type | Description |
|------|-------------|
| `url` | Resolve relative URLs to absolute |
| `regex` | Pattern match. Params: `pattern`, `group` (capture group index) |
| `format` | String template using `{data}` placeholder |
| `date` | Normalize date format. Params: `format` (e.g. `"%d/%m/%y"`) |
| `boolean` | Convert to true/false via `contains`, `exists`, or `regex` condition. Use `not: true` to negate. |
| `number` | Coerce formatted numbers: "1.5M" → 1500000, "$1,299" → 1299. Params: `locale`, `force_type` ("int"/"float") |
| `country` | Map country name to ISO code |
| `sequence` | Chain multiple post-processors |
---
## Examples
### CLI
```bash
# Single product — extract specific fields
nimble extract --url "https://example.com/product/123" --parse \
--parser '{
"type": "schema",
"fields": {
"title": {"type": "terminal", "selector": {"type": "css", "css_selector": "h1.product-title"}, "extractor": {"type": "text"}},
"price": {"type": "terminal", "selector": {"type": "css", "css_selector": ".price"}, "extractor": {"type": "text", "post_processor": {"type": "number"}}},
"rating": {"type": "terminal", "selector": {"type": "css", "css_selector": ".rating-value"}, "extractor": {"type": "text"}}
}
}'
# List of products from search results
nimble extract --url "https://example.com/search?q=shoes" --parse \
--parser '{
"type": "schema_list",
"selector": {"type": "css", "css_selector": ".product-card"},
"fields": {
"title": {"type": "terminal", "selector": {"type": "css", "css_selector": ".title"}, "extractor": {"type": "text"}},
"price": {"type": "terminal", "selector": {"type": "css", "css_selector": ".price"}, "extractor": {"type": "text", "post_processor": {"type": "number"}}},
"url": {"type": "terminal", "selector": {"type": "css", "css_selector": "a"}, "extractor": {"type": "attr", "attr": "href", "post_processor": {"type": "url"}}}
}
}'
# Fallback — try two selectors, use first that works
nimble extract --url "https://example.com/product" --parse \
--parser '{
"type": "terminal",
"selector": {"type": "or", "selectors": [
{"type": "css", "css_selector": ".price-sale"},
{"type": "css", "css_selector": ".price-regular"}
]},
"extractor": {"type": "text", "post_processor": {"type": "number"}}
}'
# Extract all image URLs as a list
nimble extract --url "https://example.com/product" --parse \
--parser '{
"type": "terminal_list",
"selector": {"type": "css", "css_selector": "img.product-image"},
"extractor": {"type": "attr", "attr": "src", "post_processor": {"type": "url"}}
}'
# Extract embedded JSON-LD (schema.org)
nimble extract --url "https://example.com/product" --parse \
--parser '{
"type": "schema",
"selector": {"type": "css", "css_selector": "script[type=\"application/ld+json\"]"},
"fields": {
"name": {"type": "terminal", "extractor": {"type": "json", "path": "name"}},
"price": {"type": "terminal", "extractor": {"type": "json", "path": "offers.price", "post_processor": {"type": "number"}}}
}
}'
# Parse RSS feed with XPath
nimble extract --url "https://example.com/feed.xml" --parse \
--parser '{
"type": "schema_list",
"selector": {"type": "xpath", "path": "//item"},
"fields": {
"title": {"type": "terminal", "selector": {"type": "xpath", "path": ".//title"}, "extractor": {"type": "text"}},
"link": {"type": "terminal", "selector": {"type": "xpath", "path": ".//link"}, "extractor": {"type": "text"}},
"date": {"type": "terminal", "selector": {"type": "xpath", "path": ".//pubDate"}, "extractor": {"type": "text", "post_processor": {"type": "date"}}}
}
}'
# Extract data from network capture response
nimble extract --url "https://example.com/products" --render \
--network-capture '[{"url": {"type": "contains", "value": "/api/products"}}]' \
--parse --parser '{
"type": "terminal",
"selector": {"type": "sequence", "sequence": [
{"type": "root"},
{"type": "json", "path": "network_capture[0].response_body.data.products"}
]},
"extractor": {"type": "raw"}
}'
```
### Python SDK
```python
# Single product
resp = nimble.extract(
url="https://example.com/product/123",
parse=True,
parser={
"type": "schema",
"fields": {
"title": {"type": "terminal", "selector": {"type": "css", "css_selector": "h1.product-title"}, "extractor": {"type": "text"}},
"price": {"type": "terminal", "selector": {"type": "css", "css_selector": ".price"}, "extractor": {"type": "text", "post_processor": {"type": "number"}}},
"rating": {"type": "terminal", "selector": {"type": "css", "css_selector": ".rating-value"}, "extractor": {"type": "text"}},
},
},
)
print(resp["data"]["parsing"])
# List of products from search results
resp = nimble.extract(
url="https://example.com/search?q=shoes",
parse=True,
parser={
"type": "schema_list",
"selector": {"type": "css", "css_selector": ".product-card"},
"fields": {
"title": {"type": "terminal", "selector": {"type": "css", "css_selector": ".title"}, "extractor": {"type": "text"}},
"price": {"type": "terminal", "selector": {"type": "css", "css_selector": ".price"}, "extractor": {"type": "text", "post_processor": {"type": "number"}}},
"url": {"type": "terminal", "selector": {"type": "css", "css_selector": "a"}, "extractor": {"type": "attr", "attr": "href", "post_processor": {"type": "url"}}},
},
},
)
for item in resp["data"]["parsing"][:5]:
print(item)
# All image URLs as a list
resp = nimble.extract(
url="https://example.com/product",
parse=True,
parser={
"type": "terminal_list",
"selector": {"type": "css", "css_selector": "img.product-image"},
"extractor": {"type": "attr", "attr": "src", "post_processor": {"type": "url"}},
},
)
print(resp["data"]["parsing"])
```
---
## When to use structured parsing vs markdown
| Use `--parser` | Use `--format markdown` |
|-----------------|------------------------|
| Need specific fields | Need full page content |
| Extracting a list of items | Reading an article or docs |
| Data will be used programmatically | LLM needs to read and summarize |
| Building a dataset | One-off research |
---
## Notes
- Use `or` parser as fallback for pages with varying layouts or A/B tests
- Chain post-processors with `sequence` for multi-step transforms
- Use `root` selector to access `network_capture` data in the parser
- `number` post-processor handles "$1,299", "1.5M", "2,100" automatically
- Selectors break when page structure changes — monitor and update as needed
SHA-256: 628668286bf7de6bdb9923bf84768ef82117c4bbdcdf532e4753248a7d8ab813