structx-sdk 0.2.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,20 @@
1
+ # Build outputs
2
+ dist/
3
+ build/
4
+ *.egg-info/
5
+
6
+ # Virtual envs
7
+ .venv/
8
+ venv/
9
+ env/
10
+
11
+ # Caches
12
+ __pycache__/
13
+ *.pyc
14
+ .pytest_cache/
15
+ .mypy_cache/
16
+ .ruff_cache/
17
+
18
+ # Editor
19
+ .vscode/
20
+ .idea/
@@ -0,0 +1,44 @@
1
+ # Changelog
2
+
3
+ All notable changes to the `structx-sdk` Python SDK are documented here.
4
+ This project follows [Semantic Versioning](https://semver.org/).
5
+
6
+ ## [0.2.0] — 2026-05-25
7
+
8
+ ### BREAKING
9
+ - Renamed the package from `structx` to `structx-sdk` on PyPI. Pre-existing unrelated package at `structx` on PyPI made coexistence impossible.
10
+ - Renamed the Python module from `structx` to `structx_sdk`. Update imports: `from structx_sdk import StructX, AsyncStructX, ...`
11
+ - Renamed the public classes to use capital `X`: `Structx` → `StructX`, `AsyncStructx` → `AsyncStructX`, `StructxError` → `StructXError`. Brand-consistent with marketing's "Struct-X" spelling.
12
+ - Env variables (`STRUCTX_API_KEY`, `STRUCTX_BASE_URL`) unchanged.
13
+ - User-Agent header prefix updated to `structx-sdk/<version>`.
14
+
15
+ ### Migration
16
+ Replace `from structx import Structx` with `from structx_sdk import StructX`. The class API is otherwise unchanged.
17
+
18
+ ## [0.1.1] - 2026-05-25
19
+
20
+ ### Security
21
+ - `ApiError.response_body` now has sensitive-key values redacted at exception-construction time (Phase 5.5 / rho). Closes a credential/PII leak that surfaced when customer code logged `repr(exc)` or routed exceptions to error trackers like Sentry. Redacted keys (case-insensitive): `x-api-key`, `authorization`, `apikey`, `api_key`, `password`, `token`, `secret`, `private_key`, `content`. Values become `<redacted N chars>` (length preserved for debugging).
22
+ - `ApiError.__repr__` now omits `response_body` entirely — second layer of defense against accidental `f"{exc!r}"` logging.
23
+ - Backward compatible: `.response_body` attribute is still accessible for programmatic inspection; only the values for sensitive keys are sentinelized.
24
+
25
+ ## [0.1.0] — 2026-05-24
26
+
27
+ Initial release.
28
+
29
+ ### Added
30
+ - `Structx` sync client + `AsyncStructx` async client (parallel surfaces).
31
+ - `extract(content, *, schema=None, template_slug=None, tier=..., options=...)`.
32
+ - `infer_schema(content, *, content_type=None, hints=None, ...)`.
33
+ - `list_templates()`, `list_models()`, `usage()`.
34
+ - Typed exception hierarchy: `StructxError → ApiError → {Authentication, PermissionDenied, NotFound, Validation, RateLimit, Server}Error`, plus `TransportError` for network failures.
35
+ - Typed Pydantic response models: `Extraction`, `FieldConfidence`, `TokenCounts`, `InferenceResult`, `InferredSchema`, `InferredField`, `Recommendation`, `Template`, `Model`, `Usage`. All accept extra fields silently for forward compatibility.
36
+ - `RetryPolicy` with read-vs-write retry differentiation — reads auto-retry on 5xx, writes only on transport errors (avoid double-billing).
37
+ - `STRUCTX_API_KEY` / `STRUCTX_BASE_URL` environment fallbacks, plus `Structx.from_env()`.
38
+ - Context-manager support (`with Structx(...)` closes the underlying httpx client).
39
+ - `py.typed` marker for full type-checker support.
40
+
41
+ ### Compatible with
42
+ - Python 3.10, 3.11, 3.12, 3.13.
43
+ - struct-x API v1.x.
44
+ - httpx 0.27 / 0.28; pydantic 2.5+.
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 struct-x
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,217 @@
1
+ Metadata-Version: 2.4
2
+ Name: structx-sdk
3
+ Version: 0.2.0
4
+ Summary: Official Python SDK (structx-sdk) for struct-x — agent-native structured extraction.
5
+ Project-URL: Homepage, https://structx.ai
6
+ Project-URL: Documentation, https://docs.structx.ai
7
+ Project-URL: Repository, https://github.com/struct-x-ai/struct-x
8
+ Project-URL: Issues, https://github.com/struct-x-ai/struct-x/issues
9
+ Project-URL: Changelog, https://github.com/struct-x-ai/struct-x/blob/main/sdk/python/CHANGELOG.md
10
+ Author-email: struct-x <support@structx.ai>
11
+ License: MIT
12
+ License-File: LICENSE
13
+ Keywords: agent,ai,extraction,json-schema,llm,mcp,structured-extraction
14
+ Classifier: Development Status :: 4 - Beta
15
+ Classifier: Intended Audience :: Developers
16
+ Classifier: License :: OSI Approved :: MIT License
17
+ Classifier: Programming Language :: Python
18
+ Classifier: Programming Language :: Python :: 3
19
+ Classifier: Programming Language :: Python :: 3.10
20
+ Classifier: Programming Language :: Python :: 3.11
21
+ Classifier: Programming Language :: Python :: 3.12
22
+ Classifier: Programming Language :: Python :: 3.13
23
+ Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
24
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
25
+ Classifier: Typing :: Typed
26
+ Requires-Python: >=3.10
27
+ Requires-Dist: httpx<0.29,>=0.27
28
+ Requires-Dist: pydantic<3.0,>=2.5
29
+ Provides-Extra: dev
30
+ Requires-Dist: mypy>=1.8; extra == 'dev'
31
+ Requires-Dist: pytest-asyncio>=0.23; extra == 'dev'
32
+ Requires-Dist: pytest>=8.0; extra == 'dev'
33
+ Requires-Dist: respx>=0.21; extra == 'dev'
34
+ Requires-Dist: ruff>=0.5; extra == 'dev'
35
+ Description-Content-Type: text/markdown
36
+
37
+ # structx-sdk — Python SDK for struct-x
38
+
39
+ [![PyPI](https://img.shields.io/pypi/v/structx-sdk.svg)](https://pypi.org/project/structx-sdk/)
40
+ [![Python](https://img.shields.io/pypi/pyversions/structx-sdk.svg)](https://pypi.org/project/structx-sdk/)
41
+ [![License](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)
42
+
43
+ Official Python client for **[struct-x](https://structx.ai)** — the agent-native structured-extraction API. Send raw content and a JSON Schema, get back validated, typed JSON with per-field confidence scores.
44
+
45
+ ## Install
46
+
47
+ ```bash
48
+ pip install structx-sdk
49
+ ```
50
+
51
+ ## Quickstart
52
+
53
+ ```python
54
+ from structx_sdk import StructX
55
+
56
+ client = StructX(api_key="sx_...")
57
+
58
+ result = client.extract(
59
+ content="<div><h1>Aeron Chair</h1><span>$1,795.00</span></div>",
60
+ schema={
61
+ "type": "object",
62
+ "required": ["title", "price_cents"],
63
+ "properties": {
64
+ "title": {"type": "string"},
65
+ "price_cents": {"type": "integer"},
66
+ },
67
+ },
68
+ )
69
+
70
+ print(result.data)
71
+ # {'title': 'Aeron Chair', 'price_cents': 179500}
72
+
73
+ print(result.field_confidences[0])
74
+ # FieldConfidence(field='title', confidence=0.96, source_snippet=None)
75
+ ```
76
+
77
+ ## Use a catalog template instead of an inline schema
78
+
79
+ ```python
80
+ result = client.extract(
81
+ content=stripe_webhook_payload,
82
+ template_slug="logs.stripe.event", # latest published version
83
+ )
84
+ ```
85
+
86
+ Pin to a specific template version with `family_slug@version`:
87
+
88
+ ```python
89
+ template_slug="logs.stripe.event@1.0.0"
90
+ ```
91
+
92
+ ## Don't have a schema yet? Let the API infer one
93
+
94
+ ```python
95
+ inference = client.infer_schema(
96
+ content="<html>… some product page …</html>",
97
+ content_type="html",
98
+ )
99
+
100
+ print(inference.inferred.json_schema) # ready to pass back to extract()
101
+ for f in inference.inferred.fields:
102
+ print(f"{f.name} ({f.type}) — {f.rationale}")
103
+
104
+ # Plus template recommendations, if any matched:
105
+ for r in inference.recommendations:
106
+ print(f"{r.slug} (score={r.score:.2f})")
107
+ ```
108
+
109
+ ## Async
110
+
111
+ Same surface, `await`-flavored:
112
+
113
+ ```python
114
+ import asyncio
115
+ from structx_sdk import AsyncStructX
116
+
117
+ async def main():
118
+ async with AsyncStructX(api_key="sx_...") as client:
119
+ result = await client.extract(content="…", schema={…})
120
+ print(result.data)
121
+
122
+ asyncio.run(main())
123
+ ```
124
+
125
+ ## Configuration
126
+
127
+ | Param | Default | Notes |
128
+ |----------------|-------------------------------|--------------------------------------------------------|
129
+ | `api_key` | `STRUCTX_API_KEY` env var | Required. |
130
+ | `base_url` | `STRUCTX_BASE_URL` env var, else `https://api.structx.ai` | Override for staging / self-hosted. |
131
+ | `timeout` | `30.0` seconds | Applied per request. |
132
+ | `retry` | `RetryPolicy(max_attempts=3, …)` | Tune via `RetryPolicy(...)`. |
133
+ | `default_headers` | `{}` | Merged into every request — e.g., for tracing IDs. |
134
+
135
+ Pick up credentials from the environment with `StructX.from_env()`:
136
+
137
+ ```python
138
+ import os
139
+ os.environ["STRUCTX_API_KEY"] = "sx_..."
140
+
141
+ from structx_sdk import StructX
142
+ client = StructX.from_env()
143
+ ```
144
+
145
+ ## Errors
146
+
147
+ All exceptions inherit from `StructXError`. Catch the specific class you care about:
148
+
149
+ ```python
150
+ from structx_sdk import RateLimitError, ValidationError, ServerError
151
+
152
+ try:
153
+ result = client.extract(content=…, schema=…)
154
+ except RateLimitError as e:
155
+ # 429 — back off; e.retry_after, e.credits_used, e.credits_remaining are populated
156
+ print(f"Sleep {e.retry_after}s. Used {e.credits_used}/{e.credits_used + e.credits_remaining}.")
157
+ except ValidationError as e:
158
+ # 400/422 — fix your input. e.code carries the machine-readable reason.
159
+ print(f"Bad input: {e.code} — {e.message}")
160
+ except ServerError as e:
161
+ # 5xx — retry or contact support; e.request_id is your handle.
162
+ print(f"Server error (request_id={e.request_id})")
163
+ ```
164
+
165
+ Full hierarchy:
166
+
167
+ ```
168
+ StructXError
169
+ ├── TransportError # network failure — request never reached the server
170
+ └── ApiError # server responded with an error status
171
+ ├── AuthenticationError # 401
172
+ ├── PermissionDeniedError # 403
173
+ ├── NotFoundError # 404
174
+ ├── ValidationError # 400, 422
175
+ ├── RateLimitError # 429 (carries retry_after, credits info)
176
+ └── ServerError # 5xx
177
+ ```
178
+
179
+ ## Retries
180
+
181
+ By default, **read** calls (`list_templates`, `list_models`, `usage`) auto-retry on transient 5xx and connection errors with exponential backoff.
182
+
183
+ **Write** calls (`extract`, `infer_schema`) retry ONLY on transport errors, never on 5xx — because a 5xx after a partial backend run may have already billed the call.
184
+
185
+ Customize via `RetryPolicy`:
186
+
187
+ ```python
188
+ from structx_sdk import StructX, RetryPolicy
189
+
190
+ client = StructX(
191
+ api_key="sx_...",
192
+ retry=RetryPolicy(
193
+ max_attempts=5,
194
+ initial_backoff=0.5,
195
+ max_backoff=60.0,
196
+ retry_on_5xx=True,
197
+ respect_retry_after=True,
198
+ ),
199
+ )
200
+ ```
201
+
202
+ ## Forward compatibility
203
+
204
+ Response models accept extra fields silently. When the API adds a new field, old SDK versions don't break — they just don't surface it as a typed attribute. Reach it via `result.model_dump()` or `result.__pydantic_extra__`.
205
+
206
+ ## Development
207
+
208
+ ```bash
209
+ git clone https://github.com/struct-x-ai/struct-x
210
+ cd struct-x/sdk/python
211
+ pip install -e ".[dev]"
212
+ pytest -q
213
+ ```
214
+
215
+ ## License
216
+
217
+ MIT — see [LICENSE](LICENSE).
@@ -0,0 +1,181 @@
1
+ # structx-sdk — Python SDK for struct-x
2
+
3
+ [![PyPI](https://img.shields.io/pypi/v/structx-sdk.svg)](https://pypi.org/project/structx-sdk/)
4
+ [![Python](https://img.shields.io/pypi/pyversions/structx-sdk.svg)](https://pypi.org/project/structx-sdk/)
5
+ [![License](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)
6
+
7
+ Official Python client for **[struct-x](https://structx.ai)** — the agent-native structured-extraction API. Send raw content and a JSON Schema, get back validated, typed JSON with per-field confidence scores.
8
+
9
+ ## Install
10
+
11
+ ```bash
12
+ pip install structx-sdk
13
+ ```
14
+
15
+ ## Quickstart
16
+
17
+ ```python
18
+ from structx_sdk import StructX
19
+
20
+ client = StructX(api_key="sx_...")
21
+
22
+ result = client.extract(
23
+ content="<div><h1>Aeron Chair</h1><span>$1,795.00</span></div>",
24
+ schema={
25
+ "type": "object",
26
+ "required": ["title", "price_cents"],
27
+ "properties": {
28
+ "title": {"type": "string"},
29
+ "price_cents": {"type": "integer"},
30
+ },
31
+ },
32
+ )
33
+
34
+ print(result.data)
35
+ # {'title': 'Aeron Chair', 'price_cents': 179500}
36
+
37
+ print(result.field_confidences[0])
38
+ # FieldConfidence(field='title', confidence=0.96, source_snippet=None)
39
+ ```
40
+
41
+ ## Use a catalog template instead of an inline schema
42
+
43
+ ```python
44
+ result = client.extract(
45
+ content=stripe_webhook_payload,
46
+ template_slug="logs.stripe.event", # latest published version
47
+ )
48
+ ```
49
+
50
+ Pin to a specific template version with `family_slug@version`:
51
+
52
+ ```python
53
+ template_slug="logs.stripe.event@1.0.0"
54
+ ```
55
+
56
+ ## Don't have a schema yet? Let the API infer one
57
+
58
+ ```python
59
+ inference = client.infer_schema(
60
+ content="<html>… some product page …</html>",
61
+ content_type="html",
62
+ )
63
+
64
+ print(inference.inferred.json_schema) # ready to pass back to extract()
65
+ for f in inference.inferred.fields:
66
+ print(f"{f.name} ({f.type}) — {f.rationale}")
67
+
68
+ # Plus template recommendations, if any matched:
69
+ for r in inference.recommendations:
70
+ print(f"{r.slug} (score={r.score:.2f})")
71
+ ```
72
+
73
+ ## Async
74
+
75
+ Same surface, `await`-flavored:
76
+
77
+ ```python
78
+ import asyncio
79
+ from structx_sdk import AsyncStructX
80
+
81
+ async def main():
82
+ async with AsyncStructX(api_key="sx_...") as client:
83
+ result = await client.extract(content="…", schema={…})
84
+ print(result.data)
85
+
86
+ asyncio.run(main())
87
+ ```
88
+
89
+ ## Configuration
90
+
91
+ | Param | Default | Notes |
92
+ |----------------|-------------------------------|--------------------------------------------------------|
93
+ | `api_key` | `STRUCTX_API_KEY` env var | Required. |
94
+ | `base_url` | `STRUCTX_BASE_URL` env var, else `https://api.structx.ai` | Override for staging / self-hosted. |
95
+ | `timeout` | `30.0` seconds | Applied per request. |
96
+ | `retry` | `RetryPolicy(max_attempts=3, …)` | Tune via `RetryPolicy(...)`. |
97
+ | `default_headers` | `{}` | Merged into every request — e.g., for tracing IDs. |
98
+
99
+ Pick up credentials from the environment with `StructX.from_env()`:
100
+
101
+ ```python
102
+ import os
103
+ os.environ["STRUCTX_API_KEY"] = "sx_..."
104
+
105
+ from structx_sdk import StructX
106
+ client = StructX.from_env()
107
+ ```
108
+
109
+ ## Errors
110
+
111
+ All exceptions inherit from `StructXError`. Catch the specific class you care about:
112
+
113
+ ```python
114
+ from structx_sdk import RateLimitError, ValidationError, ServerError
115
+
116
+ try:
117
+ result = client.extract(content=…, schema=…)
118
+ except RateLimitError as e:
119
+ # 429 — back off; e.retry_after, e.credits_used, e.credits_remaining are populated
120
+ print(f"Sleep {e.retry_after}s. Used {e.credits_used}/{e.credits_used + e.credits_remaining}.")
121
+ except ValidationError as e:
122
+ # 400/422 — fix your input. e.code carries the machine-readable reason.
123
+ print(f"Bad input: {e.code} — {e.message}")
124
+ except ServerError as e:
125
+ # 5xx — retry or contact support; e.request_id is your handle.
126
+ print(f"Server error (request_id={e.request_id})")
127
+ ```
128
+
129
+ Full hierarchy:
130
+
131
+ ```
132
+ StructXError
133
+ ├── TransportError # network failure — request never reached the server
134
+ └── ApiError # server responded with an error status
135
+ ├── AuthenticationError # 401
136
+ ├── PermissionDeniedError # 403
137
+ ├── NotFoundError # 404
138
+ ├── ValidationError # 400, 422
139
+ ├── RateLimitError # 429 (carries retry_after, credits info)
140
+ └── ServerError # 5xx
141
+ ```
142
+
143
+ ## Retries
144
+
145
+ By default, **read** calls (`list_templates`, `list_models`, `usage`) auto-retry on transient 5xx and connection errors with exponential backoff.
146
+
147
+ **Write** calls (`extract`, `infer_schema`) retry ONLY on transport errors, never on 5xx — because a 5xx after a partial backend run may have already billed the call.
148
+
149
+ Customize via `RetryPolicy`:
150
+
151
+ ```python
152
+ from structx_sdk import StructX, RetryPolicy
153
+
154
+ client = StructX(
155
+ api_key="sx_...",
156
+ retry=RetryPolicy(
157
+ max_attempts=5,
158
+ initial_backoff=0.5,
159
+ max_backoff=60.0,
160
+ retry_on_5xx=True,
161
+ respect_retry_after=True,
162
+ ),
163
+ )
164
+ ```
165
+
166
+ ## Forward compatibility
167
+
168
+ Response models accept extra fields silently. When the API adds a new field, old SDK versions don't break — they just don't surface it as a typed attribute. Reach it via `result.model_dump()` or `result.__pydantic_extra__`.
169
+
170
+ ## Development
171
+
172
+ ```bash
173
+ git clone https://github.com/struct-x-ai/struct-x
174
+ cd struct-x/sdk/python
175
+ pip install -e ".[dev]"
176
+ pytest -q
177
+ ```
178
+
179
+ ## License
180
+
181
+ MIT — see [LICENSE](LICENSE).
@@ -0,0 +1,90 @@
1
+ [build-system]
2
+ requires = ["hatchling>=1.18"]
3
+ build-backend = "hatchling.build"
4
+
5
+ [project]
6
+ name = "structx-sdk"
7
+ dynamic = ["version"]
8
+ description = "Official Python SDK (structx-sdk) for struct-x — agent-native structured extraction."
9
+ readme = "README.md"
10
+ requires-python = ">=3.10"
11
+ license = { text = "MIT" }
12
+ authors = [
13
+ { name = "struct-x", email = "support@structx.ai" },
14
+ ]
15
+ keywords = [
16
+ "structured-extraction",
17
+ "llm",
18
+ "json-schema",
19
+ "extraction",
20
+ "ai",
21
+ "agent",
22
+ "mcp",
23
+ ]
24
+ classifiers = [
25
+ "Development Status :: 4 - Beta",
26
+ "Intended Audience :: Developers",
27
+ "License :: OSI Approved :: MIT License",
28
+ "Programming Language :: Python",
29
+ "Programming Language :: Python :: 3",
30
+ "Programming Language :: Python :: 3.10",
31
+ "Programming Language :: Python :: 3.11",
32
+ "Programming Language :: Python :: 3.12",
33
+ "Programming Language :: Python :: 3.13",
34
+ "Topic :: Software Development :: Libraries :: Python Modules",
35
+ "Topic :: Scientific/Engineering :: Artificial Intelligence",
36
+ "Typing :: Typed",
37
+ ]
38
+ dependencies = [
39
+ "httpx>=0.27,<0.29",
40
+ "pydantic>=2.5,<3.0",
41
+ ]
42
+
43
+ [project.optional-dependencies]
44
+ dev = [
45
+ "pytest>=8.0",
46
+ "pytest-asyncio>=0.23",
47
+ "respx>=0.21",
48
+ "mypy>=1.8",
49
+ "ruff>=0.5",
50
+ ]
51
+
52
+ [project.urls]
53
+ Homepage = "https://structx.ai"
54
+ Documentation = "https://docs.structx.ai"
55
+ Repository = "https://github.com/struct-x-ai/struct-x"
56
+ Issues = "https://github.com/struct-x-ai/struct-x/issues"
57
+ Changelog = "https://github.com/struct-x-ai/struct-x/blob/main/sdk/python/CHANGELOG.md"
58
+
59
+ [tool.hatch.version]
60
+ path = "src/structx_sdk/_version.py"
61
+
62
+ [tool.hatch.build.targets.wheel]
63
+ packages = ["src/structx_sdk"]
64
+
65
+ [tool.hatch.build.targets.sdist]
66
+ include = [
67
+ "src/structx_sdk",
68
+ "README.md",
69
+ "CHANGELOG.md",
70
+ "LICENSE",
71
+ "pyproject.toml",
72
+ ]
73
+
74
+ [tool.pytest.ini_options]
75
+ testpaths = ["tests"]
76
+ asyncio_mode = "auto"
77
+ filterwarnings = ["error"]
78
+
79
+ [tool.ruff]
80
+ line-length = 100
81
+ target-version = "py310"
82
+
83
+ [tool.ruff.lint]
84
+ select = ["E", "F", "I", "B", "UP", "N"]
85
+ ignore = ["E501"]
86
+
87
+ [tool.mypy]
88
+ strict = true
89
+ python_version = "3.10"
90
+ files = ["src/structx_sdk"]
@@ -0,0 +1,82 @@
1
+ """struct-x Python SDK — official client for the structured-extraction API.
2
+
3
+ Quickstart:
4
+
5
+ from structx_sdk import StructX
6
+
7
+ client = StructX(api_key="sx_...")
8
+ result = client.extract(
9
+ content="<div>$99 Widget</div>",
10
+ schema={
11
+ "type": "object",
12
+ "properties": {
13
+ "price_cents": {"type": "integer"},
14
+ "title": {"type": "string"},
15
+ },
16
+ },
17
+ )
18
+ print(result.data) # {'price_cents': 9900, 'title': 'Widget'}
19
+ print(result.field_confidences) # [FieldConfidence(field='price_cents', ...)]
20
+
21
+ Async variant — same surface:
22
+
23
+ from structx_sdk import AsyncStructX
24
+
25
+ async with AsyncStructX(api_key="sx_...") as client:
26
+ result = await client.extract(content="...", schema={...})
27
+ """
28
+ from ._client import AsyncStructX, RetryPolicy, StructX
29
+ from ._exceptions import (
30
+ ApiError,
31
+ AuthenticationError,
32
+ NotFoundError,
33
+ PermissionDeniedError,
34
+ RateLimitError,
35
+ ServerError,
36
+ StructXError,
37
+ TransportError,
38
+ ValidationError,
39
+ )
40
+ from ._models import (
41
+ Extraction,
42
+ FieldConfidence,
43
+ InferenceResult,
44
+ InferredField,
45
+ InferredSchema,
46
+ Model,
47
+ Recommendation,
48
+ Template,
49
+ TokenCounts,
50
+ Usage,
51
+ )
52
+ from ._version import __version__
53
+
54
+ __all__ = [
55
+ # Clients
56
+ "StructX",
57
+ "AsyncStructX",
58
+ "RetryPolicy",
59
+ # Exceptions
60
+ "StructXError",
61
+ "TransportError",
62
+ "ApiError",
63
+ "AuthenticationError",
64
+ "PermissionDeniedError",
65
+ "NotFoundError",
66
+ "ValidationError",
67
+ "RateLimitError",
68
+ "ServerError",
69
+ # Models
70
+ "Extraction",
71
+ "FieldConfidence",
72
+ "TokenCounts",
73
+ "InferenceResult",
74
+ "InferredSchema",
75
+ "InferredField",
76
+ "Recommendation",
77
+ "Template",
78
+ "Model",
79
+ "Usage",
80
+ # Meta
81
+ "__version__",
82
+ ]