diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 3e02389..d500ed1 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -37,18 +37,20 @@ jobs: - name: Install locked dependencies run: uv sync --locked --extra dev - name: Check formatting - run: uv run ruff format --check . + run: uv run --locked --no-sync --no-build ruff format --check . - name: Build distributions run: uv build + - name: Smoke-check built distributions + run: uv run --locked --no-sync --no-build python scripts/check_distribution.py - name: Lint - run: uv run ruff check . + run: uv run --locked --no-sync --no-build ruff check . - name: Type check - run: uv run mypy --strict + run: uv run --locked --no-sync --no-build mypy --strict - name: Test transport and models - run: uv run python -m pytest tests/test_client.py + run: uv run --locked --no-sync --no-build python -m pytest tests/test_client.py - name: Run mocked examples - run: uv run python -m pytest tests/test_examples.py + run: uv run --locked --no-sync --no-build python -m pytest tests/test_examples.py - name: Execute README examples - run: uv run python -m pytest tests/test_docs.py + run: uv run --locked --no-sync --no-build python -m pytest tests/test_docs.py - name: Check API contract - run: uv run python scripts/check_contracts.py + run: uv run --locked --no-sync --no-build python scripts/check_contracts.py diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 8b2f57a..25fefd1 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -39,17 +39,19 @@ jobs: - name: Install locked dependencies run: uv sync --locked --extra dev - name: Check formatting - run: uv run ruff format --check . + run: uv run --locked --no-sync --no-build ruff format --check . - name: Build distributions run: uv build + - name: Smoke-check built distributions + run: uv run --locked --no-sync --no-build python scripts/check_distribution.py - name: Lint - run: uv run ruff check . + run: uv run --locked --no-sync --no-build ruff check . - name: Type check - run: uv run mypy --strict + run: uv run --locked --no-sync --no-build mypy --strict - name: Test sync, async, examples, and docs - run: uv run python -m pytest + run: uv run --locked --no-sync --no-build python -m pytest - name: Check API contract - run: uv run python scripts/check_contracts.py + run: uv run --locked --no-sync --no-build python scripts/check_contracts.py - name: Generate SBOM uses: anchore/sbom-action@66cbf4bc1f1c0d2edc94016e65bc221b6bb0ad6c # v0.24.3 with: diff --git a/CHANGELOG.md b/CHANGELOG.md index fa0a272..0a5c962 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,9 +4,22 @@ All notable changes to this SDK are recorded here. -## 1.0.0 (2026-10-08) +## 1.0.0 (2026-10-09) + +### Breaking changes + +- Use resource-oriented method names and semantic path parameters. +- Distinguish omitted request bodies from JSON `null` and `{}`. Omitting `body` now sends no body. ### Features -- Release the unified Python 1.0 SDK with synchronous and asynchronous clients, all 370 catalogued operations, typed AI text generation and embeddings, fluent agent and workflow builders, Pydantic v2 request models, offline HTTPX tests, and PyPI trusted publishing. -- Add sync and async AI tool registry helpers, plus agent configuration, approval predicate, and run completion polling helpers. +- Provide synchronous and asynchronous clients, all 370 catalogued operations, + typed AI helpers, and fluent agent and workflow builders. +- Add `FrontalError.transient` and `FrontalError.safe_to_retry` to separate temporary failures from safe replay. +- Add jitter to client-generated retry delays and enforce asynchronous polling deadlines. +- Add agent configuration, approval predicates, and run completion polling. + +### Bug fixes + +- Preserve server-sent event IDs across events that omit a new ID. +- Retain details from non-standard JSON error responses and validate pagination limits. diff --git a/README.md b/README.md index f572850..472c3fc 100644 --- a/README.md +++ b/README.md @@ -58,14 +58,24 @@ environment header, and debug logging. The SDK does not load `.env` files. - HTTPX sync and async transports with bounded GET retries, request IDs, pagination helpers, polling, raw bytes, multipart uploads, and SSE streams. - Pydantic v2 request models and validation for JSON-compatible payloads. -- A structured error hierarchy with status, code, request ID, and retryability. +- A structured error hierarchy with status, code, request ID, transient status, + and an explicit `safe_to_retry` signal. - Inline package typing, including `py.typed`. +Streaming POST requests default to no retries because a connection failure can +occur after the server has accepted the request. Pass an explicit retry count +only when replaying that operation is safe. If you provide an `httpx.Client` or +`httpx.AsyncClient`, you retain ownership of its lifecycle and timeout settings. +For JSON writes, omitting `body` sends no request body; pass `body=None` to send +the JSON value `null`, and `body={}` to send an empty JSON object. + The OpenAPI snapshots define the operation inventory but do not include service-specific request and response schemas for most endpoints. The SDK does not guess those payload shapes; define request models with `APIModel` and use `PageResult[T]` for paginated responses where applicable. +The SDK uses resource-oriented names and semantic path arguments. + ## Development Install the locked development environment with `uv`: diff --git a/docs/ARCHITECTURE.md b/docs/ARCHITECTURE.md index f1a7926..9fd94b2 100644 --- a/docs/ARCHITECTURE.md +++ b/docs/ARCHITECTURE.md @@ -30,13 +30,19 @@ request IDs, timeouts, bounded retries with backoff, Pydantic JSON validation, structured errors, multipart uploads, raw bytes, and server-sent events. Safe GET requests are retryable. Stream retries are limited to the period before the first event is delivered, so an already-consumed stream is never replayed. +Streaming POST requests default to zero retries because a request may have been +accepted before a connection failure is visible to the client. Retrying one is +opt-in through its `max_retries` argument and is appropriate only when replay is +safe. The server's `Retry-After` value is honored up to five seconds. Debug +request logs include the path but omit query values. `core/pagination.py` and `core/polling.py` provide sync and async cursor iteration and polling helpers. The clients default to `https://api.frontal.dev/v1`, a 30 second timeout, and three transport retries. Pass `base_url`, `timeout`, `max_retries`, `environment`, or `debug` to override those defaults. Both clients are context -managers and close their HTTPX connection pools on exit. +managers and close SDK-owned HTTPX connection pools on exit. If an HTTPX client +is injected, the caller owns it and its timeout configuration. ## Request flow diff --git a/docs/ENTERPRISE_READINESS.md b/docs/ENTERPRISE_READINESS.md index a713969..2076fb7 100644 --- a/docs/ENTERPRISE_READINESS.md +++ b/docs/ENTERPRISE_READINESS.md @@ -1,7 +1,7 @@ # Enterprise readiness -The Python SDK includes sync and async HTTPX transports, validated client configuration, structured API errors, bounded GET retries, Pydantic boundary models, and methods for the complete endpoint inventory. Remaining release operations are: +The Python SDK includes sync and async HTTPX transports, validated client configuration, structured API errors, bounded GET retries, Pydantic boundary models, and methods for the complete endpoint inventory. The repository also contains a GitHub OIDC PyPI publishing workflow with SBOM generation and build provenance attestation. Remaining readiness work is: -- Generate operation-specific request and response models when the API publishes complete schemas. -- Configure the PyPI trusted publisher for this repository, workflow, and `pypi` environment. +- Obtain verified operation-specific request and response schemas from API owners. The committed API snapshot has no request-body schemas and uses generic object schemas for successful responses; the AI snapshot has no operation response schemas. +- Configure the PyPI trusted publisher for this repository, the `publish.yml` workflow, and the `pypi` environment in the PyPI project settings. - Review security controls, supported authentication flows, and service-specific operational guidance during release review. diff --git a/docs/RESOURCES.md b/docs/RESOURCES.md index 19dc6a3..ff3f152 100644 --- a/docs/RESOURCES.md +++ b/docs/RESOURCES.md @@ -59,7 +59,7 @@ an execution, list executions, and poll one to a terminal state. The same accessors work with `AsyncFrontal`; await their results and use `async for` for streams. -## Raw endpoint methods +## Endpoint methods Each service also exposes methods corresponding to the committed inventory. For example: @@ -68,15 +68,16 @@ For example: from frontal_sdk import Frontal with Frontal() as client: - agent = client.agents.get_agents_by_param_1("agent_123") - page = client.agents.get_agents(query={"limit": 20}) + agent = client.agents.get(id="agent_123") + page = client.agents.list(query={"limit": 20}) ``` -Raw method names include the HTTP verb and route segments. Since the inventory -does not preserve path parameter names, placeholders appear as `param_1`, -`param_2`, and so on in route order. Use `query=` for query parameters, -`body=` for JSON writes, `parts=` for multipart uploads, and `data=` with -`content_type=` for raw request bodies. Raw streaming methods return +The `agents` collection exposes concise `get(id=...)` and `list(query=...)` +methods, with runs and versions under `client.agents.runs` and +`client.agents.versions`. Other service namespaces continue to expose their +current resource-oriented operation names. Across them, use `query=` for query +parameters, `body=` for JSON writes, `parts=` for multipart uploads, and `data=` +with `content_type=` for raw request bodies. Streaming methods return `ServerEvent` iterators; raw response-body methods return bytes. Pydantic models cover shared and high-level boundaries. Raw operation payloads @@ -84,3 +85,54 @@ use `JSONValue` where the OpenAPI snapshots do not define operation-specific schemas. The endpoint inventory and OpenAPI snapshots remain authoritative; the contract gate checks that endpoint methods do not drift. Run `python scripts/check_contracts.py` after changing inventory-backed methods. + +The SDK uses resource-oriented names and semantic path arguments. + +If you inject an `httpx.Client` or `httpx.AsyncClient`, set its timeout on that +HTTPX instance. The SDK uses the injected instance as-is and leaves closing it +to your application: + +```python +import httpx +from frontal_sdk import Frontal + +http = httpx.Client(timeout=httpx.Timeout(10.0, connect=2.0)) +with Frontal(http_client=http) as client: + agents = client.agents.list() +http.close() +``` + +## Pagination and errors + +The endpoint inventory does not assign a response model to every collection. +Validate the documented page envelope at the call site, then use the shared +cursor helper: + +```python +from frontal_sdk import Frontal, PageResult, RateLimitError, paginate +from frontal_sdk.models import JSONValue + +with Frontal() as client: + + def fetch_agents(query): + response = client.agents.list(query=query) + return PageResult[dict[str, JSONValue]].model_validate(response) + + try: + agent_rows = list(paginate(fetch_agents, query={"limit": 50})) + except RateLimitError as error: + print(error.request_id, error.retry_after) +``` + +Each fetch callback receives the original query plus the cursor returned by the +prior page. Configure `timeout` on the client as well as on polling helpers: a +polling deadline cannot interrupt a blocking synchronous fetch. + +## Request bodies and retry safety + +Write methods distinguish an omitted body from JSON values. Omitting `body` +sends no request body; `body=None` sends JSON `null`, and `body={}` sends an +empty JSON object. API errors expose `transient` for temporary failures and +`safe_to_retry` for operations that can be replayed safely. A transient error +from a write may still represent an operation the server accepted, so inspect +`safe_to_retry` before replaying it. diff --git a/docs/ROADMAP.md b/docs/ROADMAP.md index 393392b..0c38bdb 100644 --- a/docs/ROADMAP.md +++ b/docs/ROADMAP.md @@ -4,7 +4,9 @@ - [x] Add the shared API contract snapshots and Python coverage placeholder. - [x] Implement the core client, transport, configuration, and error model. - [x] Generate typed resource methods for all endpoint inventory operations. -- [ ] Add operation-specific request and response models when complete API schemas are available. +- [ ] Acquire verified operation-specific request and response schemas; keep unknown payloads as explicit JSON boundaries until confirmed. - [x] Add contract conformance checks and local HTTP integration tests. - [x] Add offline runnable examples for sync and async AI, agent definitions, and workflows. -- [ ] Configure protected PyPI releases. +- [x] Add a tag-triggered PyPI publishing workflow with GitHub OIDC, SBOM, and provenance attestation. +- [ ] Configure the account-side PyPI trusted publisher and environment protections. +- [x] Establish the resource-oriented SDK API as the canonical initial interface. diff --git a/examples/SDKS_GUIDE.md b/examples/SDKS_GUIDE.md index c925f8d..a143d51 100644 --- a/examples/SDKS_GUIDE.md +++ b/examples/SDKS_GUIDE.md @@ -53,13 +53,13 @@ define a workflow with `client.workflows.define(name).manual().task(...).create( Then use the returned identifier with `client.agents.use(id)` or `client.workflows.use(id)` to message, inspect, trigger, or poll runs. -Raw operations use method names that include the HTTP verb and route. Path -parameters are named `param_1`, `param_2`, and so on in route order. Pass query -parameters as `query=`, JSON request values as `body=`, multipart uploads as -`parts=`, and raw request bodies as `data=` plus `content_type=`. Most raw -operations return JSON values because the OpenAPI snapshot does not define a -specific response schema for each operation. See [API resources](../docs/RESOURCES.md) -for details and [examples](./README.md) for runnable scripts. +SDK operations use resource-oriented method names and semantic path +arguments where the contract provides them. Pass query parameters as `query=`, +JSON request values as `body=`, multipart uploads as `parts=`, and raw request +bodies as `data=` plus `content_type=`. Most operations return JSON values +because the OpenAPI snapshot does not define a specific response schema for +each operation. See [API resources](../docs/RESOURCES.md) and +[examples](./README.md). Sync streams use `for`; async streams use `async for`. AI `stream_text()` yields typed text and lifecycle parts. Agent `watch(run_id)` yields raw diff --git a/frontal_sdk/__init__.py b/frontal_sdk/__init__.py index 8b748cd..6f0a600 100644 --- a/frontal_sdk/__init__.py +++ b/frontal_sdk/__init__.py @@ -16,6 +16,7 @@ from frontal_sdk.core.pagination import async_paginate, paginate from frontal_sdk.core.polling import async_poll_until, poll_until from frontal_sdk.models import ( + UNSET, Agent, AgentDefinition, AgentExecution, @@ -43,8 +44,8 @@ PageResult, PaginationMeta, QueryParams, - RegisteredTool, RequestBody, + RequestBodyInput, RerankOptions, RerankResult, ServerEvent, @@ -54,6 +55,7 @@ ToolDefinition, TranscriptionOptions, TranscriptionResult, + Unset, Workflow, WorkflowDefinition, WorkflowExecution, @@ -110,9 +112,9 @@ "PaginationMeta", "poll_until", "QueryParams", - "RegisteredTool", "RateLimitError", "RequestBody", + "RequestBodyInput", "RerankOptions", "RerankResult", "ServerError", @@ -131,5 +133,7 @@ "WorkflowExecution", "StepDefinition", "tool", + "UNSET", + "Unset", "__version__", ] diff --git a/frontal_sdk/client.py b/frontal_sdk/client.py index e0c96dc..ea5ca8c 100644 --- a/frontal_sdk/client.py +++ b/frontal_sdk/client.py @@ -82,7 +82,8 @@ class Frontal: ``api_key`` defaults to ``FRONTAL_API_KEY``. The base URL, environment, and debug setting also read ``FRONTAL_API_URL``, ``FRONTAL_ENV``, and - ``FRONTAL_DEBUG`` when their matching arguments are omitted. + ``FRONTAL_DEBUG`` when their matching arguments are omitted. A supplied + ``http_client`` remains caller-owned and keeps its own timeout configuration. """ def __init__( @@ -153,7 +154,11 @@ def __exit__(self, *_: object) -> None: class AsyncFrontal: - """Asynchronous API client with the same typed service namespaces.""" + """Async client with matching typed services. + + A supplied ``http_client`` remains caller-owned and keeps its own timeout + configuration. + """ def __init__( self, diff --git a/frontal_sdk/core/config.py b/frontal_sdk/core/config.py index 1bf3343..0055b18 100644 --- a/frontal_sdk/core/config.py +++ b/frontal_sdk/core/config.py @@ -12,6 +12,55 @@ _API_KEY_PATTERN = re.compile(r"frt_[A-Za-z0-9_-]+") +def _validate_api_key(api_key: str) -> None: + if len(api_key) < 9 or _API_KEY_PATTERN.fullmatch(api_key) is None: + raise ValueError( + "api_key must start with 'frt_' and contain base64url characters" + ) + + +def _validate_base_url(base_url: str) -> None: + parsed = urlsplit(base_url) + if ( + parsed.scheme not in {"http", "https"} + or not parsed.netloc + or parsed.username is not None + or parsed.password is not None + or parsed.query + or parsed.fragment + ): + raise ValueError( + "base_url must be an absolute HTTP(S) URL without credentials, " + "query, or fragment" + ) + + +def _validate_retries(max_retries: int) -> None: + if isinstance(max_retries, bool) or not isinstance(max_retries, int): + raise TypeError("max_retries must be an integer") + if not 0 <= max_retries <= 10: + raise ValueError("max_retries must be between 0 and 10") + + +def _validate_headers(headers: Mapping[str, str]) -> None: + reserved_headers = { + "authorization", + "x-request-id", + "x-frontal-environment", + } + for name, value in headers.items(): + if not isinstance(name, str) or not isinstance(value, str): + raise TypeError("header names and values must be strings") + if not name or any(char in name for char in "\r\n:"): + raise ValueError( + "header names must be non-empty and contain no colon or newline" + ) + if "\r" in value or "\n" in value: + raise ValueError("header values must not contain newlines") + if name.lower() in reserved_headers: + raise ValueError(f"{name} is managed by the SDK and cannot be overridden") + + @dataclass(frozen=True) class ClientConfig: api_key: str @@ -23,37 +72,13 @@ class ClientConfig: debug: bool = False def __post_init__(self) -> None: - parsed = urlsplit(self.base_url) - if len(self.api_key) < 9 or _API_KEY_PATTERN.fullmatch(self.api_key) is None: - raise ValueError( - "api_key must start with 'frt_' and contain base64url characters" - ) - if ( - parsed.scheme not in {"http", "https"} - or not parsed.netloc - or parsed.username is not None - or parsed.password is not None - or parsed.query - or parsed.fragment - ): - raise ValueError( - "base_url must be an absolute HTTP(S) URL without credentials, " - "query, or fragment" - ) + _validate_api_key(self.api_key) + _validate_base_url(self.base_url) if not isfinite(self.timeout) or self.timeout <= 0: raise ValueError("timeout must be a finite positive number") - if isinstance(self.max_retries, bool) or not isinstance(self.max_retries, int): - raise TypeError("max_retries must be an integer") - if not 0 <= self.max_retries <= 10: - raise ValueError("max_retries must be between 0 and 10") + _validate_retries(self.max_retries) if not self.environment.strip(): raise ValueError("environment must not be empty") - for name, value in self.headers.items(): - if not name or any(char in name for char in "\r\n:"): - raise ValueError( - "header names must be non-empty and contain no colon or newline" - ) - if "\r" in value or "\n" in value: - raise ValueError("header values must not contain newlines") + _validate_headers(self.headers) object.__setattr__(self, "base_url", self.base_url.rstrip("/")) object.__setattr__(self, "headers", MappingProxyType(dict(self.headers))) diff --git a/frontal_sdk/core/errors.py b/frontal_sdk/core/errors.py index 46cd29d..86ac980 100644 --- a/frontal_sdk/core/errors.py +++ b/frontal_sdk/core/errors.py @@ -15,6 +15,7 @@ class _ErrorContext(TypedDict, total=False): status_code: int | None details: JSONValue fields: list[ErrorField] | None + safe_to_retry: bool class FrontalError(Exception): @@ -27,7 +28,8 @@ def __init__( code: str | None = None, request_id: str | None = None, status_code: int | None = None, - retryable: bool | None = None, + transient: bool | None = None, + safe_to_retry: bool = False, details: JSONValue = None, fields: list[ErrorField] | None = None, ) -> None: @@ -35,9 +37,10 @@ def __init__( self.code = code or "FRONTAL_ERROR" self.request_id = request_id self.status_code = status_code - self.retryable = ( - status_code in _RETRYABLE_STATUS if retryable is None else retryable + self.transient = ( + status_code in _RETRYABLE_STATUS if transient is None else transient ) + self.safe_to_retry = safe_to_retry self.details = details self.fields = fields or [] @@ -67,13 +70,15 @@ def __init__( status_code: int | None = 429, details: JSONValue = None, fields: list[ErrorField] | None = None, + safe_to_retry: bool = False, ) -> None: super().__init__( message, code=code, request_id=request_id, status_code=status_code, - retryable=True, + transient=True, + safe_to_retry=safe_to_retry, details=details, fields=fields, ) @@ -99,13 +104,15 @@ def __init__( request_id: str | None = None, status_code: int | None = None, details: JSONValue = None, + safe_to_retry: bool = False, ) -> None: super().__init__( message, code=code, request_id=request_id, status_code=status_code, - retryable=True, + transient=True, + safe_to_retry=safe_to_retry, details=details, ) @@ -123,6 +130,7 @@ def error_for_status( details: JSONValue = None, fields: list[ErrorField] | None = None, retry_after: float | None = None, + safe_to_retry: bool = False, ) -> FrontalError: """Create the public error subtype corresponding to an HTTP status.""" arguments: _ErrorContext = { @@ -131,6 +139,7 @@ def error_for_status( "status_code": status_code, "details": details, "fields": fields, + "safe_to_retry": safe_to_retry, } if status_code in {401, 403}: return AuthenticationError(message, **arguments) diff --git a/frontal_sdk/core/http.py b/frontal_sdk/core/http.py index 0d208e1..e560eca 100644 --- a/frontal_sdk/core/http.py +++ b/frontal_sdk/core/http.py @@ -4,6 +4,7 @@ import json import logging +import random from collections.abc import AsyncIterator, Coroutine, Iterator, Mapping, Sequence from datetime import datetime, timezone from email.utils import parsedate_to_datetime @@ -33,9 +34,11 @@ QueryParams, ) from frontal_sdk.models.http import ServerEvent -from frontal_sdk.models.requests import RequestBody +from frontal_sdk.models.requests import UNSET, RequestBody, RequestBodyInput, Unset _RETRYABLE_STATUS = {408, 425, 429, 500, 502, 503, 504} +_EVENT_STREAM_CONTENT_TYPE = "text/event-stream" +_EVENT_STREAM_ERROR = "The API did not return an event stream" _JSON_ADAPTER: TypeAdapter[JSONValue] = TypeAdapter(JSONValue) _LOGGER = logging.getLogger("frontal_sdk.http") @@ -72,6 +75,17 @@ def _json_body(body: RequestBody) -> JSONValue: raise ValueError("request body must contain JSON-compatible values") from error +def _json_body_bytes(body: RequestBody) -> bytes: + """Serialize a JSON value, including the valid top-level value ``null``.""" + return _JSON_ADAPTER.dump_json(_json_body(body)) + + +def _request_body_bytes(body: RequestBodyInput) -> bytes | None: + if isinstance(body, Unset): + return None + return _json_body_bytes(body) + + def _headers( config: ClientConfig, extra: Mapping[str, str] | None = None ) -> dict[str, str]: @@ -81,37 +95,77 @@ def _headers( "User-Agent": "frontal-python-sdk/1.0.0", "X-Request-ID": str(uuid4()), "X-Frontal-Environment": config.environment, - **config.headers, - **(extra or {}), } + # Header names are case-insensitive; normalize before merging to avoid + # duplicate wire headers when callers vary the casing. + for source in (config.headers, extra or {}): + for name, value in source.items(): + existing = next( + (key for key in values if key.lower() == name.lower()), None + ) + if existing is not None: + del values[existing] + values[name] = value return values -def _api_error(response: httpx.Response) -> FrontalError: - request_id = response.headers.get("x-request-id") +def _decode_error_body(response: httpx.Response) -> Any: + try: + return response.json() + except ValueError: + return None + + +_ERROR_FIELDS = { + "code", + "message", + "requestId", + "request_id", + "docs", + "fields", + "details", +} + + +def _error_envelope( + decoded: dict[str, Any], response: httpx.Response, request_id: str | None +) -> tuple[str | None, str, str | None, JSONValue, list[ErrorField]]: code: str | None = None message = f"Frontal API request failed with HTTP {response.status_code}" details: JSONValue = None fields: list[ErrorField] = [] try: - decoded = response.json() - except (ValueError, UnicodeDecodeError): - decoded = None - if isinstance(decoded, dict): - try: - envelope = ErrorResponse.model_validate(decoded) - except PydanticValidationError: - pass - else: - code = envelope.code - message = envelope.message - request_id = envelope.request_id or request_id - details = envelope.details - fields = envelope.fields - else: - fields = [] - if response.content: - details = response.text[:2048] + envelope = ErrorResponse.model_validate(decoded) + except PydanticValidationError: + return code, message, request_id, response.text[:2048], fields + + code = envelope.code + message = envelope.message + request_id = envelope.request_id or request_id + details = envelope.details + fields = envelope.fields + if details is None: + extra = { + key: value for key, value in decoded.items() if key not in _ERROR_FIELDS + } + if extra: + details = cast(JSONValue, extra) + return code, message, request_id, details, fields + + +def _api_error(response: httpx.Response, method: str) -> FrontalError: + request_id = response.headers.get("x-request-id") + code: str | None = None + message = f"Frontal API request failed with HTTP {response.status_code}" + details: JSONValue = None + fields: list[ErrorField] = [] + decoded = _decode_error_body(response) + if isinstance(decoded, dict) and _ERROR_FIELDS.intersection(decoded): + code, message, request_id, details, fields = _error_envelope( + decoded, response, request_id + ) + elif response.content: + details = decoded if isinstance(decoded, (dict, list)) else response.text[:2048] return error_for_status( response.status_code, @@ -121,6 +175,7 @@ def _api_error(response: httpx.Response) -> FrontalError: details=details, fields=fields, retry_after=_parse_retry_after(response.headers.get("retry-after")), + safe_to_retry=method in {"GET", "HEAD", "OPTIONS", "PUT", "DELETE"}, ) @@ -166,7 +221,8 @@ def _parse_retry_after(value: str | None) -> float | None: def _retry_delay(attempt: int, retry_after: float | None) -> float: if retry_after is not None: return retry_after - return float(min(0.1 * (2**attempt), 2.0)) + ceiling = float(min(0.1 * (2**attempt), 2.0)) + return random.uniform(0.0, ceiling) def _event(event: str, event_id: str | None, lines: list[str]) -> ServerEvent: @@ -186,7 +242,8 @@ def _parse_event_line( ) -> tuple[str, str | None, list[str], ServerEvent | None]: if not line: parsed_event = _event(event, event_id, data_lines) if data_lines else None - return "message", None, [], parsed_event + # SSE's last-event-ID buffer persists until another non-empty id field. + return "message", event_id, [], parsed_event if line.startswith(":"): return event, event_id, data_lines, None if ":" not in line: @@ -204,6 +261,92 @@ def _parse_event_line( return event, event_id, data_lines, None +def _stream_retry_count(operation: Operation, max_retries: int | None) -> int: + if operation.method != "POST": + raise ValueError("stream_request() requires a POST operation") + retries = 0 if max_retries is None else max_retries + if isinstance(retries, bool) or not isinstance(retries, int): + raise TypeError("max_retries must be an integer") + if not 0 <= retries <= 10: + raise ValueError("max_retries must be between 0 and 10") + return retries + + +def _stream_response_retry_delay( + response: httpx.Response, attempt: int, retries: int +) -> float | None: + if response.status_code not in _RETRYABLE_STATUS or attempt >= retries: + return None + return _retry_delay( + attempt, _parse_retry_after(response.headers.get("retry-after")) + ) + + +def _check_stream_response(response: httpx.Response) -> None: + if response.is_error: + raise _api_error(response, "POST") + if response.headers.get("content-type", "").startswith(_EVENT_STREAM_CONTENT_TYPE): + return + raise FrontalError( + _EVENT_STREAM_ERROR, + request_id=response.headers.get("x-request-id"), + status_code=response.status_code, + ) + + +def _stream_events(response: httpx.Response) -> Iterator[ServerEvent]: + _check_stream_response(response) + event = "message" + event_id: str | None = None + data_lines: list[str] = [] + for line in response.iter_lines(): + event, event_id, data_lines, parsed = _parse_event_line( + line, event, event_id, data_lines + ) + if parsed is not None: + yield parsed + if data_lines: + yield _event(event, event_id, data_lines) + + +async def _async_stream_events(response: httpx.Response) -> AsyncIterator[ServerEvent]: + _check_stream_response(response) + event = "message" + event_id: str | None = None + data_lines: list[str] = [] + async for line in response.aiter_lines(): + event, event_id, data_lines, parsed = _parse_event_line( + line, event, event_id, data_lines + ) + if parsed is not None: + yield parsed + if data_lines: + yield _event(event, event_id, data_lines) + + +def _can_retry_stream_error( + error: FrontalError | httpx.RequestError | httpx.TimeoutException, + emitted: bool, + attempt: int, + retries: int, +) -> bool: + if emitted or attempt >= retries: + return False + if isinstance(error, FrontalError): + return error.transient + return True + + +def _raise_stream_error( + error: FrontalError | httpx.RequestError | httpx.TimeoutException, +) -> None: + if isinstance(error, FrontalError): + raise error + if isinstance(error, httpx.TimeoutException): + raise TimeoutError(f"Stream request timed out: {error}") from error + raise NetworkError(f"Stream request failed: {error}") from error + + class HttpClient: """Synchronous HTTPX transport shared by every service on a client.""" @@ -220,7 +363,7 @@ def request( *, path_params: Sequence[str] = (), query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONValue: """Call one catalogued operation and validate the JSON response.""" if operation.method in {"GETRAW", "STREAM", "POSTFORMDATA", "POSTRAW"}: @@ -228,13 +371,7 @@ def request( "use request_bytes(), stream(), request_multipart(), or request_raw()" ) url = _request_url(self._config.base_url, operation, path_params, query) - content = ( - _json_body(body) - if body is not None - else {} - if operation.method in {"POST", "PUT", "PATCH", "DELETE"} - else None - ) + content = _request_body_bytes(body) headers = _headers( self._config, {"Content-Type": "application/json"} if content is not None else None, @@ -243,7 +380,7 @@ def request( operation.method, url, headers=headers, - json=content, + content=content, ) response = self._send(request, operation.method) return _decode_json(response) @@ -327,7 +464,9 @@ def stream( with self._client.stream( "GET", url, - headers=_headers(self._config, {"Accept": "text/event-stream"}), + headers=_headers( + self._config, {"Accept": _EVENT_STREAM_CONTENT_TYPE} + ), ) as response: if ( response.status_code in _RETRYABLE_STATUS @@ -341,12 +480,12 @@ def stream( attempt += 1 continue if response.is_error: - raise _api_error(response) + raise _api_error(response, "GET") if not response.headers.get("content-type", "").startswith( - "text/event-stream" + _EVENT_STREAM_CONTENT_TYPE ): raise FrontalError( - "The API did not return an event stream", + _EVENT_STREAM_ERROR, request_id=response.headers.get("x-request-id"), status_code=response.status_code, ) @@ -369,13 +508,17 @@ def stream( time_sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise TimeoutError(f"Stream request timed out: {error}") from error + raise TimeoutError( + f"Stream request timed out: {error}", safe_to_retry=True + ) from error except httpx.RequestError as error: if not emitted and attempt < self._config.max_retries: time_sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise NetworkError(f"Stream request failed: {error}") from error + raise NetworkError( + f"Stream request failed: {error}", safe_to_retry=True + ) from error def stream_request( self, @@ -384,13 +527,13 @@ def stream_request( body: RequestBody, max_retries: int | None = None, ) -> Iterator[ServerEvent]: - """Send a JSON POST and yield SSE events, retrying before the first event.""" - if operation.method != "POST": - raise ValueError("stream_request() requires a POST operation") - retries = self._config.max_retries if max_retries is None else max_retries - if not 0 <= retries <= 10: - raise ValueError("max_retries must be between 0 and 10") - content = _json_body(body) + """Send a JSON POST and yield SSE events. + + Retries default to zero because a failed connection may follow server + acceptance. Set ``max_retries`` only when replaying is safe. + """ + retries = _stream_retry_count(operation, max_retries) + content = _json_body_bytes(body) url = _request_url(self._config.base_url, operation, (), None) attempt = 0 emitted = False @@ -402,63 +545,27 @@ def stream_request( headers=_headers( self._config, { - "Accept": "text/event-stream", + "Accept": _EVENT_STREAM_CONTENT_TYPE, "Content-Type": "application/json", }, ), - json=content, + content=content, ) as response: - if response.status_code in _RETRYABLE_STATUS and attempt < retries: - time_sleep( - _retry_delay( - attempt, - _parse_retry_after(response.headers.get("retry-after")), - ) - ) + delay = _stream_response_retry_delay(response, attempt, retries) + if delay is not None: + time_sleep(delay) attempt += 1 continue - if response.is_error: - raise _api_error(response) - if not response.headers.get("content-type", "").startswith( - "text/event-stream" - ): - raise FrontalError( - "The API did not return an event stream", - request_id=response.headers.get("x-request-id"), - status_code=response.status_code, - ) - event = "message" - event_id: str | None = None - data_lines: list[str] = [] - for line in response.iter_lines(): - event, event_id, data_lines, parsed = _parse_event_line( - line, event, event_id, data_lines - ) - if parsed is not None: - emitted = True - yield parsed - if data_lines: + for event in _stream_events(response): emitted = True - yield _event(event, event_id, data_lines) + yield event return - except FrontalError as error: - if error.retryable and not emitted and attempt < retries: - time_sleep(_retry_delay(attempt, None)) - attempt += 1 - continue - raise - except httpx.TimeoutException as error: - if not emitted and attempt < retries: - time_sleep(_retry_delay(attempt, None)) - attempt += 1 - continue - raise TimeoutError(f"Stream request timed out: {error}") from error - except httpx.RequestError as error: - if not emitted and attempt < retries: + except (FrontalError, httpx.TimeoutException, httpx.RequestError) as error: + if _can_retry_stream_error(error, emitted, attempt, retries): time_sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise NetworkError(f"Stream request failed: {error}") from error + _raise_stream_error(error) def close(self) -> None: """Close the connection pool if this transport created it.""" @@ -476,7 +583,9 @@ def _send(self, request: httpx.Request, method: str) -> httpx.Response: while True: try: if self._config.debug: - _LOGGER.debug("Frontal request %s %s", request.method, request.url) + _LOGGER.debug( + "Frontal request %s %s", request.method, request.url.path + ) response = self._client.send(request) if ( method == "GET" @@ -498,20 +607,26 @@ def _send(self, request: httpx.Request, method: str) -> httpx.Response: response.headers.get("x-request-id"), ) if response.is_error: - raise _api_error(response) + raise _api_error(response, method) return response except httpx.TimeoutException as error: if method == "GET" and attempt < self._config.max_retries: time_sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise TimeoutError(f"Request timed out: {error}") from error + raise TimeoutError( + f"Request timed out: {error}", + safe_to_retry=method in {"GET", "HEAD", "OPTIONS", "PUT", "DELETE"}, + ) from error except httpx.RequestError as error: if method == "GET" and attempt < self._config.max_retries: time_sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise NetworkError(f"Request failed: {error}") from error + raise NetworkError( + f"Request failed: {error}", + safe_to_retry=method in {"GET", "HEAD", "OPTIONS", "PUT", "DELETE"}, + ) from error def time_sleep(delay: float) -> None: @@ -539,7 +654,7 @@ def request( *, path_params: Sequence[str] = (), query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> Coroutine[Any, Any, JSONValue]: """Call one catalogued operation and validate the JSON response.""" return self._request(operation, path_params=path_params, query=query, body=body) @@ -550,19 +665,13 @@ async def _request( *, path_params: Sequence[str], query: QueryParams | None, - body: RequestBody, + body: RequestBodyInput, ) -> JSONValue: if operation.method in {"GETRAW", "STREAM", "POSTFORMDATA", "POSTRAW"}: raise ValueError( "use request_bytes(), stream(), request_multipart(), or request_raw()" ) - content = ( - _json_body(body) - if body is not None - else {} - if operation.method in {"POST", "PUT", "PATCH", "DELETE"} - else None - ) + content = _request_body_bytes(body) headers = _headers( self._config, {"Content-Type": "application/json"} if content is not None else None, @@ -571,7 +680,7 @@ async def _request( operation.method, _request_url(self._config.base_url, operation, path_params, query), headers=headers, - json=content, + content=content, ) response = await self._send(request, operation.method) return _decode_json(response) @@ -693,7 +802,9 @@ async def stream( async with self._client.stream( "GET", url, - headers=_headers(self._config, {"Accept": "text/event-stream"}), + headers=_headers( + self._config, {"Accept": _EVENT_STREAM_CONTENT_TYPE} + ), ) as response: if ( response.status_code in _RETRYABLE_STATUS @@ -708,12 +819,12 @@ async def stream( attempt += 1 continue if response.is_error: - raise _api_error(response) + raise _api_error(response, "GET") if not response.headers.get("content-type", "").startswith( - "text/event-stream" + _EVENT_STREAM_CONTENT_TYPE ): raise FrontalError( - "The API did not return an event stream", + _EVENT_STREAM_ERROR, request_id=response.headers.get("x-request-id"), status_code=response.status_code, ) @@ -736,13 +847,17 @@ async def stream( await anyio.sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise TimeoutError(f"Stream request timed out: {error}") from error + raise TimeoutError( + f"Stream request timed out: {error}", safe_to_retry=True + ) from error except httpx.RequestError as error: if not emitted and attempt < self._config.max_retries: await anyio.sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise NetworkError(f"Stream request failed: {error}") from error + raise NetworkError( + f"Stream request failed: {error}", safe_to_retry=True + ) from error async def stream_request( self, @@ -751,13 +866,13 @@ async def stream_request( body: RequestBody, max_retries: int | None = None, ) -> AsyncIterator[ServerEvent]: - """Send a JSON POST and asynchronously yield SSE events.""" - if operation.method != "POST": - raise ValueError("stream_request() requires a POST operation") - retries = self._config.max_retries if max_retries is None else max_retries - if not 0 <= retries <= 10: - raise ValueError("max_retries must be between 0 and 10") - content = _json_body(body) + """Send a JSON POST and asynchronously yield SSE events. + + Retries default to zero because a failed connection may follow server + acceptance. Set ``max_retries`` only when replaying is safe. + """ + retries = _stream_retry_count(operation, max_retries) + content = _json_body_bytes(body) url = _request_url(self._config.base_url, operation, (), None) attempt = 0 emitted = False @@ -769,63 +884,27 @@ async def stream_request( headers=_headers( self._config, { - "Accept": "text/event-stream", + "Accept": _EVENT_STREAM_CONTENT_TYPE, "Content-Type": "application/json", }, ), - json=content, + content=content, ) as response: - if response.status_code in _RETRYABLE_STATUS and attempt < retries: - await anyio.sleep( - _retry_delay( - attempt, - _parse_retry_after(response.headers.get("retry-after")), - ) - ) + delay = _stream_response_retry_delay(response, attempt, retries) + if delay is not None: + await anyio.sleep(delay) attempt += 1 continue - if response.is_error: - raise _api_error(response) - if not response.headers.get("content-type", "").startswith( - "text/event-stream" - ): - raise FrontalError( - "The API did not return an event stream", - request_id=response.headers.get("x-request-id"), - status_code=response.status_code, - ) - event = "message" - event_id: str | None = None - data_lines: list[str] = [] - async for line in response.aiter_lines(): - event, event_id, data_lines, parsed = _parse_event_line( - line, event, event_id, data_lines - ) - if parsed is not None: - emitted = True - yield parsed - if data_lines: + async for event in _async_stream_events(response): emitted = True - yield _event(event, event_id, data_lines) + yield event return - except FrontalError as error: - if error.retryable and not emitted and attempt < retries: - await anyio.sleep(_retry_delay(attempt, None)) - attempt += 1 - continue - raise - except httpx.TimeoutException as error: - if not emitted and attempt < retries: + except (FrontalError, httpx.TimeoutException, httpx.RequestError) as error: + if _can_retry_stream_error(error, emitted, attempt, retries): await anyio.sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise TimeoutError(f"Stream request timed out: {error}") from error - except httpx.RequestError as error: - if not emitted and attempt < retries: - await anyio.sleep(_retry_delay(attempt, None)) - attempt += 1 - continue - raise NetworkError(f"Stream request failed: {error}") from error + _raise_stream_error(error) async def aclose(self) -> None: """Close the connection pool if this transport created it.""" @@ -843,7 +922,9 @@ async def _send(self, request: httpx.Request, method: str) -> httpx.Response: while True: try: if self._config.debug: - _LOGGER.debug("Frontal request %s %s", request.method, request.url) + _LOGGER.debug( + "Frontal request %s %s", request.method, request.url.path + ) response = await self._client.send(request) if ( method == "GET" @@ -865,20 +946,26 @@ async def _send(self, request: httpx.Request, method: str) -> httpx.Response: response.headers.get("x-request-id"), ) if response.is_error: - raise _api_error(response) + raise _api_error(response, method) return response except httpx.TimeoutException as error: if method == "GET" and attempt < self._config.max_retries: await anyio.sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise TimeoutError(f"Request timed out: {error}") from error + raise TimeoutError( + f"Request timed out: {error}", + safe_to_retry=method in {"GET", "HEAD", "OPTIONS", "PUT", "DELETE"}, + ) from error except httpx.RequestError as error: if method == "GET" and attempt < self._config.max_retries: await anyio.sleep(_retry_delay(attempt, None)) attempt += 1 continue - raise NetworkError(f"Request failed: {error}") from error + raise NetworkError( + f"Request failed: {error}", + safe_to_retry=method in {"GET", "HEAD", "OPTIONS", "PUT", "DELETE"}, + ) from error __all__ = ["AsyncHttpClient", "HttpClient"] diff --git a/frontal_sdk/core/pagination.py b/frontal_sdk/core/pagination.py index b39b186..689cefc 100644 --- a/frontal_sdk/core/pagination.py +++ b/frontal_sdk/core/pagination.py @@ -73,7 +73,10 @@ async def async_paginate( def _validate_pagination(cursor_param: str, max_pages: int | None) -> None: - if not cursor_param: + if not isinstance(cursor_param, str) or not cursor_param.strip(): raise ValueError("cursor_param must not be empty") - if max_pages is not None and max_pages < 1: - raise ValueError("max_pages must be positive") + if max_pages is not None: + if isinstance(max_pages, bool) or not isinstance(max_pages, int): + raise TypeError("max_pages must be an integer") + if max_pages < 1: + raise ValueError("max_pages must be positive") diff --git a/frontal_sdk/core/polling.py b/frontal_sdk/core/polling.py index 59b48b7..f103d90 100644 --- a/frontal_sdk/core/polling.py +++ b/frontal_sdk/core/polling.py @@ -23,13 +23,19 @@ def poll_until( timeout: float = 300.0, backoff: Backoff = "constant", ) -> ResultT: - """Call ``fetch`` until its result satisfies ``until`` or times out.""" + """Call ``fetch`` until its result satisfies ``until`` or the loop times out. + + ``timeout`` cannot interrupt a blocking ``fetch``. Configure the underlying + HTTP request timeout too. + """ _validate_polling(interval, timeout, backoff) - predicate = until or bool + predicate = until if until is not None else bool started = time.monotonic() attempt = 0 while True: result = fetch() + if time.monotonic() - started >= timeout: + raise TimeoutError(f"Polling timed out after {timeout:g} seconds") if predicate(result): return result remaining = timeout - (time.monotonic() - started) @@ -47,13 +53,23 @@ async def async_poll_until( timeout: float = 300.0, backoff: Backoff = "constant", ) -> ResultT: - """Asynchronously poll until a result matches or the timeout expires.""" + """Poll until a result matches or the loop timeout expires. + + ``timeout`` may expire while ``fetch`` is awaiting. Configure the underlying + HTTP request timeout too. + """ _validate_polling(interval, timeout, backoff) - predicate = until or bool + predicate = until if until is not None else bool started = time.monotonic() attempt = 0 while True: - result = await fetch() + remaining = timeout - (time.monotonic() - started) + if remaining <= 0: + raise TimeoutError(f"Polling timed out after {timeout:g} seconds") + with anyio.move_on_after(remaining) as scope: + result = await fetch() + if scope.cancel_called: + raise TimeoutError(f"Polling timed out after {timeout:g} seconds") if predicate(result): return result remaining = timeout - (time.monotonic() - started) diff --git a/frontal_sdk/models/__init__.py b/frontal_sdk/models/__init__.py index e87a59b..c1ee5a4 100644 --- a/frontal_sdk/models/__init__.py +++ b/frontal_sdk/models/__init__.py @@ -41,7 +41,6 @@ ModerationResult, Prompt, PromptChain, - RegisteredTool, RerankDocument, RerankOptions, RerankResult, @@ -61,7 +60,14 @@ ) from frontal_sdk.models.http import MultipartPart, ServerEvent from frontal_sdk.models.pagination import PageResult, PaginationMeta -from frontal_sdk.models.requests import QueryParams, QueryValue, RequestBody +from frontal_sdk.models.requests import ( + UNSET, + QueryParams, + QueryValue, + RequestBody, + RequestBodyInput, + Unset, +) from frontal_sdk.models.types import ( APIModel, ErrorField, @@ -163,13 +169,15 @@ "PageResult", "Prompt", "PromptChain", - "RegisteredTool", "ParallelStep", "ParallelStepConfig", "PaginationMeta", "QueryParams", "QueryValue", "RequestBody", + "RequestBodyInput", + "UNSET", + "Unset", "RerankDocument", "RerankOptions", "RerankResult", diff --git a/frontal_sdk/models/ai.py b/frontal_sdk/models/ai.py index 74b54c8..50ba22f 100644 --- a/frontal_sdk/models/ai.py +++ b/frontal_sdk/models/ai.py @@ -85,16 +85,6 @@ class ToolDefinition(Generic[ToolInputT, ToolOutputT]): execute: Callable[[ToolInputT], ToolOutputT] -@dataclass(frozen=True) -class RegisteredTool(Generic[ToolInputT, ToolOutputT]): - """A named tool in the process-local compatibility registry.""" - - name: str - description: str - parameters: type[ToolInputT] | TypeAdapter[ToolInputT] | dict[str, JSONValue] - execute: Callable[[ToolInputT], ToolOutputT] - - class GenerateTextOptions(AIModel): """Validated inputs for :meth:`AI.generate_text`.""" @@ -105,7 +95,7 @@ class GenerateTextOptions(AIModel): model: str prompt: str | list[Message] messages: list[Message] | None = None - max_tokens: float | None = Field(default=None, alias="maxTokens") + max_tokens: int | None = Field(default=None, alias="maxTokens", ge=1) temperature: float | None = None top_p: float | None = Field(default=None, alias="topP") frequency_penalty: float | None = Field(default=None, alias="frequencyPenalty") @@ -199,13 +189,13 @@ class ChatCompletionRequest(AIModel): n: int | None = None stream: bool | None = None stop: str | list[str] | None = None - max_tokens: float | None = Field(default=None, alias="maxTokens") + max_tokens: int | None = Field(default=None, alias="maxTokens", ge=1) presence_penalty: float | None = Field(default=None, alias="presencePenalty") frequency_penalty: float | None = Field(default=None, alias="frequencyPenalty") logit_bias: dict[str, float] | None = Field(default=None, alias="logitBias") user: str | None = None response_format: dict[str, str] | None = Field(default=None, alias="responseFormat") - seed: float | None = None + seed: int | None = None tools: list[JSONValue] | None = None tool_choice: JSONValue = Field(default=None, alias="toolChoice") diff --git a/frontal_sdk/models/requests.py b/frontal_sdk/models/requests.py index 5c79236..58adcdd 100644 --- a/frontal_sdk/models/requests.py +++ b/frontal_sdk/models/requests.py @@ -11,4 +11,24 @@ QueryParams = Mapping[str, QueryValue] RequestBody = Union[JSONValue, BaseModel] -__all__ = ["QueryParams", "QueryValue", "RequestBody"] + +class Unset: + """Sentinel type for an omitted JSON request body.""" + + __slots__ = () + + def __repr__(self) -> str: + return "UNSET" + + +UNSET = Unset() +RequestBodyInput = Union[RequestBody, Unset] + +__all__ = [ + "QueryParams", + "QueryValue", + "RequestBody", + "RequestBodyInput", + "UNSET", + "Unset", +] diff --git a/frontal_sdk/resources/_base.py b/frontal_sdk/resources/_base.py index 96b60f3..47044f0 100644 --- a/frontal_sdk/resources/_base.py +++ b/frontal_sdk/resources/_base.py @@ -7,6 +7,7 @@ from frontal_sdk.core.operation import Operation from frontal_sdk.models import MultipartPart, QueryParams, RequestBody +from frontal_sdk.models.requests import UNSET, RequestBodyInput JSONResultT = TypeVar("JSONResultT", covariant=True) BytesResultT = TypeVar("BytesResultT", covariant=True) @@ -22,7 +23,7 @@ def request( *, path_params: Sequence[str] = (), query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: ... def request_multipart( @@ -84,7 +85,7 @@ def _request( *, path_params: Sequence[str] = (), query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: return self._http.request( operation, path_params=path_params, query=query, body=body diff --git a/frontal_sdk/resources/agents.py b/frontal_sdk/resources/agents.py index 3c1fc0d..8be3831 100644 --- a/frontal_sdk/resources/agents.py +++ b/frontal_sdk/resources/agents.py @@ -21,12 +21,13 @@ JSONValue, MemoryConfig, QueryParams, - RequestBody, RetryConfig, ) +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, + HTTPTransport, JSONResultT, StreamResultT, ) @@ -38,17 +39,24 @@ class Agents( ): """Methods for the agents API endpoints.""" - def delete_agents_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def __init__( + self, http: HTTPTransport[JSONResultT, BytesResultT, StreamResultT] + ) -> None: + super().__init__(http) + self.runs = AgentRuns(self) + self.versions = AgentVersions(self) + + def _delete_agent( + self, agent_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /agents/{param}.""" return self._request( Operation("DELETE", "/agents/{param}"), - path_params=(param_1,), + path_params=(agent_id,), query=query, ) - def get_agents(self, *, query: QueryParams | None = None) -> JSONResultT: + def _list_agents(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /agents.""" return self._request( Operation("GET", "/agents"), @@ -56,37 +64,37 @@ def get_agents(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_agents_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def _get_agent( + self, agent_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /agents/{param}.""" return self._request( Operation("GET", "/agents/{param}"), - path_params=(param_1,), + path_params=(agent_id,), query=query, ) - def get_agents_by_param_1_runs( - self, param_1: str, *, query: QueryParams | None = None + def _list_agent_runs( + self, agent_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /agents/{param}/runs.""" return self._request( Operation("GET", "/agents/{param}/runs"), - path_params=(param_1,), + path_params=(agent_id,), query=query, ) - def get_agents_by_param_1_versions( - self, param_1: str, *, query: QueryParams | None = None + def _list_agent_versions( + self, agent_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /agents/{param}/versions.""" return self._request( Operation("GET", "/agents/{param}/versions"), - path_params=(param_1,), + path_params=(agent_id,), query=query, ) - def get_agents_health(self, *, query: QueryParams | None = None) -> JSONResultT: + def _get_agents_health(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /agents/health.""" return self._request( Operation("GET", "/agents/health"), @@ -94,28 +102,26 @@ def get_agents_health(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_agents_runs_by_param_1( - self, param_1: str, *, query: QueryParams | None = None - ) -> JSONResultT: + def _get_run(self, run_id: str, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /agents/runs/{param}.""" return self._request( Operation("GET", "/agents/runs/{param}"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) - def get_agents_runs_by_param_1_conversation( - self, param_1: str, *, query: QueryParams | None = None + def _get_run_conversation( + self, run_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /agents/runs/{param}/conversation.""" return self._request( Operation("GET", "/agents/runs/{param}/conversation"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) - def post_agents( - self, *, query: QueryParams | None = None, body: RequestBody = None + def _create_agent( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /agents.""" return self._request( @@ -125,58 +131,58 @@ def post_agents( body=body, ) - def post_agents_by_param_1_rollback( + def _rollback_agent( self, - param_1: str, + agent_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /agents/{param}/rollback.""" return self._request( Operation("POST", "/agents/{param}/rollback"), - path_params=(param_1,), + path_params=(agent_id,), query=query, body=body, ) - def post_agents_by_param_1_runs( + def _create_run_for_agent( self, - param_1: str, + agent_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /agents/{param}/runs.""" return self._request( Operation("POST", "/agents/{param}/runs"), - path_params=(param_1,), + path_params=(agent_id,), query=query, body=body, ) - def put_agents_by_param_1( + def _update_agent( self, - param_1: str, + agent_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /agents/{param}.""" return self._request( Operation("PUT", "/agents/{param}"), - path_params=(param_1,), + path_params=(agent_id,), query=query, body=body, ) - def stream_agents_runs_by_param_1_stream( - self, param_1: str, *, query: QueryParams | None = None + def _stream_run( + self, run_id: str, *, query: QueryParams | None = None ) -> StreamResultT: """Call STREAM /agents/runs/{param}/stream.""" return self._stream( Operation("STREAM", "/agents/runs/{param}/stream"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) @@ -201,43 +207,97 @@ def use( """Create an accessor for one agent and its runs.""" return AgentAccessor(self, agent_id, approve_when, approvers) - def list( + def get(self, id: str, *, query: QueryParams | None = None) -> JSONResultT: + """Retrieve one agent.""" + return self._get_agent(id, query=query) + + def list(self, *, query: QueryParams | None = None) -> JSONResultT: + """List agents using the endpoint's query parameters.""" + return self._list_agents(query=query) + + def create( self, *, - status: str | None = None, - trigger: str | None = None, - limit: int | None = None, - cursor: str | None = None, + body: RequestBodyInput = UNSET, + query: QueryParams | None = None, ) -> JSONResultT: - """List agents with the filters and cursor used by the TypeScript SDK.""" - query: dict[str, str | int] = {} - if status is not None: - query["status"] = status - if trigger is not None: - query["trigger"] = trigger - if limit is not None: - query["limit"] = limit - if cursor is not None: - query["cursor"] = cursor - return self.get_agents(query=query) + """Create one agent, serializing an AgentDefinition when provided.""" + if isinstance(body, AgentDefinition): + body = cast( + JSONValue, + body.model_dump(mode="json", by_alias=True, exclude_none=True), + ) + return self._create_agent(body=body, query=query) - def create( - self, definition: AgentDefinition | Mapping[str, JSONValue] + def update( + self, + id: str, + *, + body: RequestBodyInput = UNSET, + query: QueryParams | None = None, ) -> JSONResultT: - """Validate and create an agent definition.""" - model = ( - definition - if isinstance(definition, AgentDefinition) - else AgentDefinition.model_validate(definition) - ) - body = cast( - JSONValue, model.model_dump(mode="json", by_alias=True, exclude_none=True) - ) - return self.post_agents(body=body) + """Replace an agent definition.""" + return self._update_agent(id, body=body, query=query) + + def delete(self, id: str, *, query: QueryParams | None = None) -> JSONResultT: + """Delete one agent.""" + return self._delete_agent(id, query=query) + + def rollback( + self, + id: str, + *, + body: RequestBodyInput = UNSET, + query: QueryParams | None = None, + ) -> JSONResultT: + """Roll back an agent to a prior version.""" + return self._rollback_agent(id, body=body, query=query) def health(self) -> JSONResultT: """Check the agent service health.""" - return self.get_agents_health() + return self._get_agents_health() + + +class AgentRuns(Generic[JSONResultT, BytesResultT, StreamResultT]): + """Run operations scoped under ``client.agents.runs``.""" + + def __init__( + self, agents: Agents[JSONResultT, BytesResultT, StreamResultT] + ) -> None: + self._agents = agents + + def list(self, *, agent_id: str, query: QueryParams | None = None) -> JSONResultT: + return self._agents._list_agent_runs(agent_id, query=query) + + def create( + self, + *, + agent_id: str, + body: RequestBodyInput = UNSET, + query: QueryParams | None = None, + ) -> JSONResultT: + return self._agents._create_run_for_agent(agent_id, body=body, query=query) + + def get(self, id: str, *, query: QueryParams | None = None) -> JSONResultT: + return self._agents._get_run(id, query=query) + + def conversation(self, id: str, *, query: QueryParams | None = None) -> JSONResultT: + return self._agents._get_run_conversation(id, query=query) + + def stream(self, id: str, *, query: QueryParams | None = None) -> StreamResultT: + return self._agents._stream_run(id, query=query) + + +class AgentVersions(Generic[JSONResultT, BytesResultT, StreamResultT]): + """Version operations scoped under ``client.agents.versions``.""" + + def __init__( + self, agents: Agents[JSONResultT, BytesResultT, StreamResultT] + ) -> None: + self._agents = agents + + def list(self, *, agent_id: str, query: QueryParams | None = None) -> JSONResultT: + return self._agents._list_agent_versions(agent_id, query=query) class AgentBuilder(Generic[JSONResultT, BytesResultT, StreamResultT]): @@ -443,7 +503,7 @@ def to_json(self) -> dict[str, JSONValue]: def create(self) -> JSONResultT: """Validate and create the agent on the configured client.""" - return self._agents.create(self.to_model()) + return self._agents.create(body=self.to_model()) class AgentAccessor(Generic[JSONResultT, BytesResultT, StreamResultT]): @@ -466,19 +526,19 @@ def requires_approval(self, state: JSONValue) -> bool: return self._approve_when(state) if self._approve_when is not None else False def get(self) -> JSONResultT: - return self._agents.get_agents_by_param_1(self.id) + return self._agents.get(id=self.id) def update(self, definition: Mapping[str, JSONValue]) -> JSONResultT: - return self._agents.put_agents_by_param_1(self.id, body=dict(definition)) + return self._agents.update(id=self.id, body=dict(definition)) def delete(self) -> JSONResultT: - return self._agents.delete_agents_by_param_1(self.id) + return self._agents.delete(id=self.id) def rollback(self, *, to_version: int | None = None) -> JSONResultT: body: dict[str, JSONValue] = {} if to_version is not None: body["toVersion"] = to_version - return self._agents.post_agents_by_param_1_rollback(self.id, body=body) + return self._agents.rollback(self.id, body=body) def versions( self, *, limit: int | None = None, cursor: str | None = None @@ -488,7 +548,7 @@ def versions( query["limit"] = limit if cursor is not None: query["cursor"] = cursor - return self._agents.get_agents_by_param_1_versions(self.id, query=query) + return self._agents.versions.list(agent_id=self.id, query=query) def runs( self, @@ -509,10 +569,10 @@ def runs( ): if value is not None: query[key] = value - return self._agents.get_agents_by_param_1_runs(self.id, query=query) + return self._agents.runs.list(agent_id=self.id, query=query) def run(self, run_id: str) -> JSONResultT: - return self._agents.get_agents_runs_by_param_1(run_id) + return self._agents.runs.get(run_id) def wait_for_completion( self, @@ -555,15 +615,15 @@ async def wait_async(initial: Awaitable[JSONValue]) -> JSONValue: return cast(JSONResultT, current) def conversation(self, run_id: str) -> JSONResultT: - return self._agents.get_agents_runs_by_param_1_conversation(run_id) + return self._agents.runs.conversation(run_id) def message(self, event: str, payload: Mapping[str, JSONValue]) -> JSONResultT: body: dict[str, JSONValue] = {"event": event, "payload": dict(payload)} - return self._agents.post_agents_by_param_1_runs(self.id, body=body) + return self._agents.runs.create(agent_id=self.id, body=body) def watch(self, run_id: str) -> StreamResultT: """Watch a run as a sync iterator or async iterator of server events.""" - return self._agents.stream_agents_runs_by_param_1_stream(run_id) + return self._agents.runs.stream(run_id) def _terminal_run(value: JSONValue) -> bool: diff --git a/frontal_sdk/resources/ai.py b/frontal_sdk/resources/ai.py index af526a1..85d3a59 100644 --- a/frontal_sdk/resources/ai.py +++ b/frontal_sdk/resources/ai.py @@ -49,8 +49,6 @@ Prompt, PromptChain, QueryParams, - RegisteredTool, - RequestBody, RerankOptions, RerankResult, StreamErrorPart, @@ -68,6 +66,7 @@ VariableDefinition, ) from frontal_sdk.models.http import ServerEvent +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -80,6 +79,27 @@ OutputT = TypeVar("OutputT") +def _generate_object_result( + raw_response: JSONValue, + schema: type[BaseModel] | TypeAdapter[Any] | Mapping[str, JSONValue], +) -> GenerateObjectResult[Any]: + response = ChatCompletionResponse.model_validate(raw_response) + content = response.choices[0].message.content if response.choices else None + if not content: + raise ValueError("No content generated") + value = _validate_object(schema, json.loads(content)) + return GenerateObjectResult[Any]( + object=value, usage=_response_usage(response.usage) + ) + + +def _validate_generation_retries(max_retries: int) -> None: + if isinstance(max_retries, bool) or not isinstance(max_retries, int): + raise TypeError("max_retries must be an integer") + if not 0 <= max_retries <= 10: + raise ValueError("max_retries must be between 0 and 10") + + class AI( APIResource[JSONResultT, BytesResultT, StreamResultT], Generic[JSONResultT, BytesResultT, StreamResultT], @@ -92,63 +112,11 @@ def __init__( super().__init__(http) self._prompts: dict[str, Prompt] = {} self._current_step = 0 - self._tools: dict[str, RegisteredTool[Any, Any]] = {} def health(self) -> JSONResultT: """Check the AI gateway health.""" return self.get_health() - def define_tool( - self, - name: str, - *, - description: str, - parameters: type[InputT] | TypeAdapter[InputT] | dict[str, JSONValue], - execute: Callable[[InputT], OutputT], - ) -> RegisteredTool[InputT, OutputT]: - """Define a named tool for the deprecated in-memory registry. - - Prefer :func:`tool` and pass the tool in ``generate_text`` or - ``stream_text`` options. - """ - return RegisteredTool( - name=name, - description=description, - parameters=parameters, - execute=execute, - ) - - def register_tool(self, registered: RegisteredTool[Any, Any]) -> None: - """Register a tool for later use with :meth:`execute_tool`.""" - self._tools[registered.name] = registered - - def get_tools(self) -> list[RegisteredTool[Any, Any]]: - """Return the process-local compatibility tool registry.""" - return list(self._tools.values()) - - def _registered_tool(self, name: str) -> RegisteredTool[Any, Any]: - try: - return self._tools[name] - except KeyError as error: - raise ValueError(f"Tool not found: {name}") from error - - def execute_tool(self, name: str, params: object) -> object: - """Execute a registered synchronous tool after validating its input.""" - registered = self._registered_tool(name) - definition = ToolDefinition( - description=registered.description, - parameters=registered.parameters, - execute=registered.execute, - ) - result = registered.execute(_tool_input(definition, cast(JSONValue, params))) - if inspect.isawaitable(result): - if inspect.iscoroutine(result): - result.close() - raise TypeError( - "async registered tools require AsyncFrontal.ai.execute_tool()" - ) - return result - def get_health(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /health.""" return self._request( @@ -157,7 +125,7 @@ def get_health(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_internal_models(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_model_records(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /internal/models.""" return self._request( Operation("GET", "/internal/models"), @@ -165,9 +133,7 @@ def get_internal_models(self, *, query: QueryParams | None = None) -> JSONResult query=query, ) - def get_internal_models_defaults( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_defaults(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /internal/models/defaults.""" return self._request( Operation("GET", "/internal/models/defaults"), @@ -175,8 +141,8 @@ def get_internal_models_defaults( query=query, ) - def post_ai_chat_completions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_completion( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ai/chat/completions.""" return self._request( @@ -186,8 +152,8 @@ def post_ai_chat_completions( body=body, ) - def post_internal_embeddings( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_embedding( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /internal/embeddings.""" return self._request( @@ -197,8 +163,8 @@ def post_internal_embeddings( body=body, ) - def post_internal_predictions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_prediction( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /internal/predictions.""" return self._request( @@ -209,7 +175,7 @@ def post_internal_predictions( ) def post_internal_rerank( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /internal/rerank.""" return self._request( @@ -790,7 +756,7 @@ def generate_text( request.model_dump(mode="json", by_alias=True, exclude_none=True), ) response = ChatCompletionResponse.model_validate( - self.post_ai_chat_completions(body=body) + self.create_completion(body=body) ) result = _generate_text_result(response) total_usage = _combined_usage(total_usage, result.usage) @@ -856,9 +822,7 @@ def embed(self, model: str, input: str | list[str]) -> EmbedResult: """Create text embeddings and normalize the vector response.""" request = EmbeddingsRequest(model=model, input=input) body = cast(JSONValue, request.model_dump(mode="json", by_alias=True)) - response = EmbeddingsResponse.model_validate( - self.post_internal_embeddings(body=body) - ) + response = EmbeddingsResponse.model_validate(self.create_embedding(body=body)) return EmbedResult( embeddings=[item.embedding for item in response.data], usage=EmbedUsage(totalTokens=response.usage.total_tokens), @@ -866,7 +830,7 @@ def embed(self, model: str, input: str | list[str]) -> EmbedResult: def list_models(self) -> list[str]: """List model IDs advertised by the AI gateway.""" - response = self.get_internal_models() + response = self.list_model_records() if isinstance(response, dict): data = response.get("data") if isinstance(data, list) and data: @@ -884,7 +848,7 @@ def list_models(self) -> list[str]: def get_default_models(self) -> dict[str, str]: """Return the gateway's model ID for each supported capability.""" - response = self.get_internal_models_defaults() + response = self.list_defaults() if isinstance(response, dict): return { key: value for key, value in response.items() if isinstance(value, str) @@ -896,10 +860,18 @@ def count_tokens(self, text: str) -> int: return (len(text) + 3) // 4 def estimate_cost(self, model: str, input_tokens: int, output_tokens: int) -> float: - """Estimate cost using the SDK's documented placeholder rates.""" - input_rate, output_rate = ( - (0.000001, 0.000002) if model == "frontal-ai-fast" else (0.00001, 0.00003) - ) + """Estimate cost using the documented placeholder rate for one model. + + This is a rough planning estimate, not billing data. Other model IDs + require an application-owned pricing table and are rejected. + """ + if input_tokens < 0 or output_tokens < 0: + raise ValueError("token counts must be non-negative") + if model != "frontal-ai-fast": + raise ValueError( + "estimate_cost only has a placeholder rate for frontal-ai-fast" + ) + input_rate, output_rate = (0.000001, 0.000002) return input_tokens * input_rate + output_tokens * output_rate def generate_object( @@ -911,30 +883,23 @@ def generate_object( temperature: float | None = None, max_retries: int = 0, ) -> GenerateObjectResult[Any]: - """Generate JSON and validate it with a Pydantic model or adapter.""" - if max_retries < 0: - raise ValueError("max_retries must be non-negative") + """Generate JSON and validate it with a Pydantic model or adapter. + + Each retry issues the generation POST again and may incur additional + work or cost; use retries only when that replay is acceptable. + """ + _validate_generation_retries(max_retries) body = _object_request(model, prompt, schema, temperature) last_error: Exception | None = None for attempt in range(max_retries + 1): if attempt: time.sleep(0.5) try: - response = ChatCompletionResponse.model_validate( - self.post_ai_chat_completions(body=body) - ) - content = ( - response.choices[0].message.content if response.choices else None - ) - if not content: - raise ValueError("No content generated") - value = _validate_object(schema, json.loads(content)) - return GenerateObjectResult[Any]( - object=value, - usage=_response_usage(response.usage), + return _generate_object_result( + self.create_completion(body=body), schema ) except FrontalError as error: - if not error.retryable: + if not error.transient: raise last_error = error except (ValueError, PydanticValidationError) as error: @@ -982,7 +947,7 @@ def generate_image( body["quality"] = values.quality if values.style is not None: body["style"] = values.style - return _image_result(self.post_internal_predictions(body=body)) + return _image_result(self.create_prediction(body=body)) def generate_video( self, options: GenerateVideoOptions | Mapping[str, JSONValue] @@ -996,9 +961,7 @@ def generate_video( JSONValue, values.model_dump(mode="json", by_alias=True, exclude_none=True), ) - return GenerateVideoResult.model_validate( - self.post_internal_predictions(body=body) - ) + return GenerateVideoResult.model_validate(self.create_prediction(body=body)) def transcribe( self, options: TranscriptionOptions | Mapping[str, object] @@ -1036,9 +999,7 @@ def moderate( "input": cast(JSONValue, values.input), "model": values.model or "text-moderation-latest", } - return ModerationResult.model_validate( - self.post_internal_predictions(body=body) - ) + return ModerationResult.model_validate(self.create_prediction(body=body)) def rerank(self, options: RerankOptions | Mapping[str, JSONValue]) -> RerankResult: values = ( @@ -1060,19 +1021,6 @@ class AsyncAI( ): """Asynchronous high-level AI helpers plus every raw AI endpoint.""" - async def execute_tool(self, name: str, params: object) -> object: - """Execute a registered tool, awaiting its result when needed.""" - registered = self._registered_tool(name) - definition = ToolDefinition( - description=registered.description, - parameters=registered.parameters, - execute=registered.execute, - ) - result = registered.execute(_tool_input(definition, cast(JSONValue, params))) - if inspect.isawaitable(result): - return await result - return result - async def stream_text( self, options: StreamTextOptions | Mapping[str, object] ) -> AsyncIterator[TextStreamPart]: @@ -1118,7 +1066,7 @@ async def generate_text( request.model_dump(mode="json", by_alias=True, exclude_none=True), ) response = ChatCompletionResponse.model_validate( - await self.post_ai_chat_completions(body=body) + await self.create_completion(body=body) ) result = _generate_text_result(response) total_usage = _combined_usage(total_usage, result.usage) @@ -1183,7 +1131,7 @@ async def embed(self, model: str, input: str | list[str]) -> EmbedResult: request = EmbeddingsRequest(model=model, input=input) body = cast(JSONValue, request.model_dump(mode="json", by_alias=True)) response = EmbeddingsResponse.model_validate( - await self.post_internal_embeddings(body=body) + await self.create_embedding(body=body) ) return EmbedResult( embeddings=[item.embedding for item in response.data], @@ -1192,7 +1140,7 @@ async def embed(self, model: str, input: str | list[str]) -> EmbedResult: async def list_models(self) -> list[str]: """List model IDs advertised by the AI gateway.""" - response = await self.get_internal_models() + response = await self.list_model_records() if isinstance(response, dict): data = response.get("data") if isinstance(data, list) and data: @@ -1210,7 +1158,7 @@ async def list_models(self) -> list[str]: async def get_default_models(self) -> dict[str, str]: """Return the gateway's model ID for each supported capability.""" - response = await self.get_internal_models_defaults() + response = await self.list_defaults() if isinstance(response, dict): return { key: value for key, value in response.items() if isinstance(value, str) @@ -1222,10 +1170,18 @@ def count_tokens(self, text: str) -> int: return (len(text) + 3) // 4 def estimate_cost(self, model: str, input_tokens: int, output_tokens: int) -> float: - """Estimate cost using the SDK's documented placeholder rates.""" - input_rate, output_rate = ( - (0.000001, 0.000002) if model == "frontal-ai-fast" else (0.00001, 0.00003) - ) + """Estimate cost using the documented placeholder rate for one model. + + This is a rough planning estimate, not billing data. Other model IDs + require an application-owned pricing table and are rejected. + """ + if input_tokens < 0 or output_tokens < 0: + raise ValueError("token counts must be non-negative") + if model != "frontal-ai-fast": + raise ValueError( + "estimate_cost only has a placeholder rate for frontal-ai-fast" + ) + input_rate, output_rate = (0.000001, 0.000002) return input_tokens * input_rate + output_tokens * output_rate async def generate_object( @@ -1237,30 +1193,23 @@ async def generate_object( temperature: float | None = None, max_retries: int = 0, ) -> GenerateObjectResult[Any]: - """Generate JSON and validate it with a Pydantic model or adapter.""" - if max_retries < 0: - raise ValueError("max_retries must be non-negative") + """Generate JSON and validate it with a Pydantic model or adapter. + + Each retry issues the generation POST again and may incur additional + work or cost; use retries only when that replay is acceptable. + """ + _validate_generation_retries(max_retries) body = _object_request(model, prompt, schema, temperature) last_error: Exception | None = None for attempt in range(max_retries + 1): if attempt: await anyio.sleep(0.5) try: - response = ChatCompletionResponse.model_validate( - await self.post_ai_chat_completions(body=body) - ) - content = ( - response.choices[0].message.content if response.choices else None - ) - if not content: - raise ValueError("No content generated") - value = _validate_object(schema, json.loads(content)) - return GenerateObjectResult[Any]( - object=value, - usage=_response_usage(response.usage), + return _generate_object_result( + await self.create_completion(body=body), schema ) except FrontalError as error: - if not error.retryable: + if not error.transient: raise last_error = error except (ValueError, PydanticValidationError) as error: @@ -1307,7 +1256,7 @@ async def generate_image( body["quality"] = values.quality if values.style is not None: body["style"] = values.style - return _image_result(await self.post_internal_predictions(body=body)) + return _image_result(await self.create_prediction(body=body)) async def generate_video( self, options: GenerateVideoOptions | Mapping[str, JSONValue] @@ -1321,7 +1270,7 @@ async def generate_video( JSONValue, values.model_dump(mode="json", by_alias=True, exclude_none=True), ) - response = await self.post_internal_predictions(body=body) + response = await self.create_prediction(body=body) return GenerateVideoResult.model_validate(response) async def transcribe( @@ -1360,7 +1309,7 @@ async def moderate( "input": cast(JSONValue, values.input), "model": values.model or "text-moderation-latest", } - response = await self.post_internal_predictions(body=body) + response = await self.create_prediction(body=body) return ModerationResult.model_validate(response) async def rerank( diff --git a/frontal_sdk/resources/audit.py b/frontal_sdk/resources/audit.py index 8e4e4d7..a0d94a6 100644 --- a/frontal_sdk/resources/audit.py +++ b/frontal_sdk/resources/audit.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,7 +21,7 @@ class Audit( ): """Methods for the audit API endpoints.""" - def get_audit_events(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_events(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /audit/events.""" return self._request( Operation("GET", "/audit/events"), @@ -28,18 +29,18 @@ def get_audit_events(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_audit_events_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_event( + self, event_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /audit/events/{param}.""" return self._request( Operation("GET", "/audit/events/{param}"), - path_params=(param_1,), + path_params=(event_id,), query=query, ) - def post_audit_events( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_event( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /audit/events.""" return self._request( @@ -50,7 +51,7 @@ def post_audit_events( ) def post_audit_events_batch( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /audit/events/batch.""" return self._request( diff --git a/frontal_sdk/resources/auth.py b/frontal_sdk/resources/auth.py index 071df24..d94687c 100644 --- a/frontal_sdk/resources/auth.py +++ b/frontal_sdk/resources/auth.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,13 +21,13 @@ class Auth( ): """Methods for the auth API endpoints.""" - def delete_auth_account_mfa_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_mfa( + self, mfa_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/account/mfa/{param}.""" return self._request( Operation("DELETE", "/auth/account/mfa/{param}"), - path_params=(param_1,), + path_params=(mfa_id,), query=query, ) @@ -40,73 +41,73 @@ def delete_auth_account_profile( query=query, ) - def delete_auth_account_security_api_keys_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_api_key( + self, api_key_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/account/security/api-keys/{param}.""" return self._request( Operation("DELETE", "/auth/account/security/api-keys/{param}"), - path_params=(param_1,), + path_params=(api_key_id,), query=query, ) - def delete_auth_account_security_devices_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_device( + self, device_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/account/security/devices/{param}.""" return self._request( Operation("DELETE", "/auth/account/security/devices/{param}"), - path_params=(param_1,), + path_params=(device_id,), query=query, ) - def delete_auth_account_sessions_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_session( + self, session_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/account/sessions/{param}.""" return self._request( Operation("DELETE", "/auth/account/sessions/{param}"), - path_params=(param_1,), + path_params=(session_id,), query=query, ) - def delete_auth_admin_users_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_user( + self, user_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/admin/users/{param}.""" return self._request( Operation("DELETE", "/auth/admin/users/{param}"), - path_params=(param_1,), + path_params=(user_id,), query=query, ) - def delete_auth_admin_users_by_param_1_factors_by_param_2( - self, param_1: str, param_2: str, *, query: QueryParams | None = None + def delete_factor_for_user( + self, user_id: str, factor_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/admin/users/{param}/factors/{param}.""" return self._request( Operation("DELETE", "/auth/admin/users/{param}/factors/{param}"), - path_params=(param_1, param_2), + path_params=(user_id, factor_id), query=query, ) - def delete_auth_factors_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_factor( + self, factor_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/factors/{param}.""" return self._request( Operation("DELETE", "/auth/factors/{param}"), - path_params=(param_1,), + path_params=(factor_id,), query=query, ) - def delete_auth_user_identities_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_identity( + self, identity_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /auth/user/identities/{param}.""" return self._request( Operation("DELETE", "/auth/user/identities/{param}"), - path_params=(param_1,), + path_params=(identity_id,), query=query, ) @@ -128,13 +129,11 @@ def get_auth_account_mfa(self, *, query: QueryParams | None = None) -> JSONResul query=query, ) - def get_auth_account_mfa_by_param_1( - self, param_1: str, *, query: QueryParams | None = None - ) -> JSONResultT: + def get_mfa(self, mfa_id: str, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/account/mfa/{param}.""" return self._request( Operation("GET", "/auth/account/mfa/{param}"), - path_params=(param_1,), + path_params=(mfa_id,), query=query, ) @@ -148,9 +147,7 @@ def get_auth_account_profile( query=query, ) - def get_auth_account_security_api_keys( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_api_keys(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/account/security/api-keys.""" return self._request( Operation("GET", "/auth/account/security/api-keys"), @@ -158,19 +155,17 @@ def get_auth_account_security_api_keys( query=query, ) - def get_auth_account_security_api_keys_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_api_key( + self, api_key_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /auth/account/security/api-keys/{param}.""" return self._request( Operation("GET", "/auth/account/security/api-keys/{param}"), - path_params=(param_1,), + path_params=(api_key_id,), query=query, ) - def get_auth_account_security_devices( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_devices(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/account/security/devices.""" return self._request( Operation("GET", "/auth/account/security/devices"), @@ -178,19 +173,17 @@ def get_auth_account_security_devices( query=query, ) - def get_auth_account_security_devices_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_device( + self, device_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /auth/account/security/devices/{param}.""" return self._request( Operation("GET", "/auth/account/security/devices/{param}"), - path_params=(param_1,), + path_params=(device_id,), query=query, ) - def get_auth_account_sessions( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_sessions(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/account/sessions.""" return self._request( Operation("GET", "/auth/account/sessions"), @@ -198,7 +191,7 @@ def get_auth_account_sessions( query=query, ) - def get_auth_admin_users(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_users(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/admin/users.""" return self._request( Operation("GET", "/auth/admin/users"), @@ -206,23 +199,23 @@ def get_auth_admin_users(self, *, query: QueryParams | None = None) -> JSONResul query=query, ) - def get_auth_admin_users_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_user( + self, user_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /auth/admin/users/{param}.""" return self._request( Operation("GET", "/auth/admin/users/{param}"), - path_params=(param_1,), + path_params=(user_id,), query=query, ) - def get_auth_admin_users_by_param_1_factors( - self, param_1: str, *, query: QueryParams | None = None + def list_user_factors( + self, user_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /auth/admin/users/{param}/factors.""" return self._request( Operation("GET", "/auth/admin/users/{param}/factors"), - path_params=(param_1,), + path_params=(user_id,), query=query, ) @@ -234,7 +227,7 @@ def get_auth_auth_session(self, *, query: QueryParams | None = None) -> JSONResu query=query, ) - def get_auth_factors(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_factors(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/factors.""" return self._request( Operation("GET", "/auth/factors"), @@ -250,9 +243,7 @@ def get_auth_user(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_auth_user_identities( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_identities(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /auth/user/identities.""" return self._request( Operation("GET", "/auth/user/identities"), @@ -261,7 +252,7 @@ def get_auth_user_identities( ) def post_auth_account_mfa( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/account/mfa.""" return self._request( @@ -271,38 +262,38 @@ def post_auth_account_mfa( body=body, ) - def post_auth_account_mfa_by_param_1_challenge( + def challenge_mfa( self, - param_1: str, + mfa_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/account/mfa/{param}/challenge.""" return self._request( Operation("POST", "/auth/account/mfa/{param}/challenge"), - path_params=(param_1,), + path_params=(mfa_id,), query=query, body=body, ) - def post_auth_account_mfa_by_param_1_verify( + def verify_mfa( self, - param_1: str, + mfa_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/account/mfa/{param}/verify.""" return self._request( Operation("POST", "/auth/account/mfa/{param}/verify"), - path_params=(param_1,), + path_params=(mfa_id,), query=query, body=body, ) def post_auth_account_password( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/account/password.""" return self._request( @@ -312,8 +303,8 @@ def post_auth_account_password( body=body, ) - def post_auth_account_security_api_keys( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_api_key( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/account/security/api-keys.""" return self._request( @@ -323,8 +314,8 @@ def post_auth_account_security_api_keys( body=body, ) - def post_auth_account_security_devices( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_device( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/account/security/devices.""" return self._request( @@ -334,38 +325,38 @@ def post_auth_account_security_devices( body=body, ) - def post_auth_account_security_devices_by_param_1_trust( + def trust_device( self, - param_1: str, + device_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/account/security/devices/{param}/trust.""" return self._request( Operation("POST", "/auth/account/security/devices/{param}/trust"), - path_params=(param_1,), + path_params=(device_id,), query=query, body=body, ) - def post_auth_account_sessions_by_param_1_extend( + def extend_session( self, - param_1: str, + session_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/account/sessions/{param}/extend.""" return self._request( Operation("POST", "/auth/account/sessions/{param}/extend"), - path_params=(param_1,), + path_params=(session_id,), query=query, body=body, ) def post_auth_admin_generate_link( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/admin/generate_link.""" return self._request( @@ -376,7 +367,7 @@ def post_auth_admin_generate_link( ) def post_auth_admin_logout( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/admin/logout.""" return self._request( @@ -386,8 +377,8 @@ def post_auth_admin_logout( body=body, ) - def post_auth_admin_users( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_user( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/admin/users.""" return self._request( @@ -398,7 +389,7 @@ def post_auth_admin_users( ) def post_auth_auth_session( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/auth/session.""" return self._request( @@ -409,7 +400,7 @@ def post_auth_auth_session( ) def post_auth_authorize( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/authorize.""" return self._request( @@ -419,8 +410,8 @@ def post_auth_authorize( body=body, ) - def post_auth_factors( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_factor( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/factors.""" return self._request( @@ -430,38 +421,38 @@ def post_auth_factors( body=body, ) - def post_auth_factors_by_param_1_challenge( + def challenge_factor( self, - param_1: str, + factor_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/factors/{param}/challenge.""" return self._request( Operation("POST", "/auth/factors/{param}/challenge"), - path_params=(param_1,), + path_params=(factor_id,), query=query, body=body, ) - def post_auth_factors_by_param_1_verify( + def verify_factor( self, - param_1: str, + factor_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /auth/factors/{param}/verify.""" return self._request( Operation("POST", "/auth/factors/{param}/verify"), - path_params=(param_1,), + path_params=(factor_id,), query=query, body=body, ) def post_auth_invite( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/invite.""" return self._request( @@ -472,7 +463,7 @@ def post_auth_invite( ) def post_auth_logout( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/logout.""" return self._request( @@ -483,7 +474,7 @@ def post_auth_logout( ) def post_auth_otp( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/otp.""" return self._request( @@ -494,7 +485,7 @@ def post_auth_otp( ) def post_auth_reauthenticate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/reauthenticate.""" return self._request( @@ -505,7 +496,7 @@ def post_auth_reauthenticate( ) def post_auth_recover( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/recover.""" return self._request( @@ -516,7 +507,7 @@ def post_auth_recover( ) def post_auth_resend( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/resend.""" return self._request( @@ -527,7 +518,7 @@ def post_auth_resend( ) def post_auth_signup( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/signup.""" return self._request( @@ -538,7 +529,7 @@ def post_auth_signup( ) def post_auth_sso( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/sso.""" return self._request( @@ -549,7 +540,7 @@ def post_auth_sso( ) def post_auth_token_query_grant_type_id_token( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/token?grant_type=id_token.""" return self._request( @@ -560,7 +551,7 @@ def post_auth_token_query_grant_type_id_token( ) def post_auth_token_query_grant_type_password( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/token?grant_type=password.""" return self._request( @@ -571,7 +562,7 @@ def post_auth_token_query_grant_type_password( ) def post_auth_token_query_grant_type_pkce( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/token?grant_type=pkce.""" return self._request( @@ -582,7 +573,7 @@ def post_auth_token_query_grant_type_pkce( ) def post_auth_token_query_grant_type_refresh_token( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/token?grant_type=refresh_token.""" return self._request( @@ -592,8 +583,8 @@ def post_auth_token_query_grant_type_refresh_token( body=body, ) - def post_auth_user_identities( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_identity( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/user/identities.""" return self._request( @@ -604,7 +595,7 @@ def post_auth_user_identities( ) def post_auth_verify( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /auth/verify.""" return self._request( @@ -615,7 +606,7 @@ def post_auth_verify( ) def put_auth_account_profile( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call PUT /auth/account/profile.""" return self._request( @@ -625,38 +616,38 @@ def put_auth_account_profile( body=body, ) - def put_auth_account_security_api_keys_by_param_1( + def update_api_key( self, - param_1: str, + api_key_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /auth/account/security/api-keys/{param}.""" return self._request( Operation("PUT", "/auth/account/security/api-keys/{param}"), - path_params=(param_1,), + path_params=(api_key_id,), query=query, body=body, ) - def put_auth_admin_users_by_param_1( + def update_user( self, - param_1: str, + user_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /auth/admin/users/{param}.""" return self._request( Operation("PUT", "/auth/admin/users/{param}"), - path_params=(param_1,), + path_params=(user_id,), query=query, body=body, ) def put_auth_user( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call PUT /auth/user.""" return self._request( diff --git a/frontal_sdk/resources/billing.py b/frontal_sdk/resources/billing.py index 5d8a10d..6ff18bc 100644 --- a/frontal_sdk/resources/billing.py +++ b/frontal_sdk/resources/billing.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,158 +21,158 @@ class Billing( ): """Methods for the billing API endpoints.""" - def get_billing_addons_by_param_1_entitlements( - self, param_1: str, *, query: QueryParams | None = None + def list_addon_entitlements( + self, addon_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/addons/{param}/entitlements.""" return self._request( Operation("GET", "/billing/addons/{param}/entitlements"), - path_params=(param_1,), + path_params=(addon_id,), query=query, ) - def get_billing_customers_by_param_1_entitlements( - self, param_1: str, *, query: QueryParams | None = None + def list_customer_entitlements( + self, customer_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/customers/{param}/entitlements.""" return self._request( Operation("GET", "/billing/customers/{param}/entitlements"), - path_params=(param_1,), + path_params=(customer_id,), query=query, ) - def get_billing_customers_by_param_1_invoices_summary( - self, param_1: str, *, query: QueryParams | None = None + def get_customer_invoices_summary( + self, customer_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/customers/{param}/invoices/summary.""" return self._request( Operation("GET", "/billing/customers/{param}/invoices/summary"), - path_params=(param_1,), + path_params=(customer_id,), query=query, ) - def get_billing_customers_by_param_1_usage( - self, param_1: str, *, query: QueryParams | None = None + def get_customer_usage( + self, customer_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/customers/{param}/usage.""" return self._request( Operation("GET", "/billing/customers/{param}/usage"), - path_params=(param_1,), + path_params=(customer_id,), query=query, ) - def get_billing_customers_by_param_1_wallets( - self, param_1: str, *, query: QueryParams | None = None + def list_customer_wallets( + self, customer_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/customers/{param}/wallets.""" return self._request( Operation("GET", "/billing/customers/{param}/wallets"), - path_params=(param_1,), + path_params=(customer_id,), query=query, ) - def get_billing_customers_portal_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_portal( + self, portal_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/customers/portal/{param}.""" return self._request( Operation("GET", "/billing/customers/portal/{param}"), - path_params=(param_1,), + path_params=(portal_id,), query=query, ) - def get_billing_plans_by_param_1_entitlements( - self, param_1: str, *, query: QueryParams | None = None + def list_plan_entitlements( + self, plan_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/plans/{param}/entitlements.""" return self._request( Operation("GET", "/billing/plans/{param}/entitlements"), - path_params=(param_1,), + path_params=(plan_id,), query=query, ) - def get_billing_prices_lookup_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_lookup( + self, lookup_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/prices/lookup/{param}.""" return self._request( Operation("GET", "/billing/prices/lookup/{param}"), - path_params=(param_1,), + path_params=(lookup_id,), query=query, ) - def get_billing_subscriptions_by_param_1_entitlements( - self, param_1: str, *, query: QueryParams | None = None + def list_subscription_entitlements( + self, subscription_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/subscriptions/{param}/entitlements.""" return self._request( Operation("GET", "/billing/subscriptions/{param}/entitlements"), - path_params=(param_1,), + path_params=(subscription_id,), query=query, ) - def get_billing_wallets_by_param_1_balance_real_time( - self, param_1: str, *, query: QueryParams | None = None + def get_wallet_balance_real_time( + self, wallet_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/wallets/{param}/balance/real-time.""" return self._request( Operation("GET", "/billing/wallets/{param}/balance/real-time"), - path_params=(param_1,), + path_params=(wallet_id,), query=query, ) - def get_billing_wallets_by_param_1_transactions( - self, param_1: str, *, query: QueryParams | None = None + def list_wallet_transactions( + self, wallet_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /billing/wallets/{param}/transactions.""" return self._request( Operation("GET", "/billing/wallets/{param}/transactions"), - path_params=(param_1,), + path_params=(wallet_id,), query=query, ) - def download_billing_invoices_by_param_1_pdf( - self, param_1: str, *, query: QueryParams | None = None + def download_invoice_pdf( + self, invoice_id: str, *, query: QueryParams | None = None ) -> BytesResultT: """Call GETRAW /billing/invoices/{param}/pdf.""" return self._request_bytes( Operation("GETRAW", "/billing/invoices/{param}/pdf"), - path_params=(param_1,), + path_params=(invoice_id,), query=query, ) - def post_billing_invoices_by_param_1_finalize( + def finalize_invoice( self, - param_1: str, + invoice_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/invoices/{param}/finalize.""" return self._request( Operation("POST", "/billing/invoices/{param}/finalize"), - path_params=(param_1,), + path_params=(invoice_id,), query=query, body=body, ) - def post_billing_invoices_by_param_1_void( + def void_invoice( self, - param_1: str, + invoice_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/invoices/{param}/void.""" return self._request( Operation("POST", "/billing/invoices/{param}/void"), - path_params=(param_1,), + path_params=(invoice_id,), query=query, body=body, ) def post_billing_invoices_preview( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /billing/invoices/preview.""" return self._request( @@ -181,122 +182,122 @@ def post_billing_invoices_preview( body=body, ) - def post_billing_meters_by_param_1_disable( + def disable_meter( self, - param_1: str, + meter_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/meters/{param}/disable.""" return self._request( Operation("POST", "/billing/meters/{param}/disable"), - path_params=(param_1,), + path_params=(meter_id,), query=query, body=body, ) - def post_billing_plans_by_param_1_clone( + def clone_plan( self, - param_1: str, + plan_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/plans/{param}/clone.""" return self._request( Operation("POST", "/billing/plans/{param}/clone"), - path_params=(param_1,), + path_params=(plan_id,), query=query, body=body, ) - def post_billing_subscriptions_by_param_1_activate( + def activate_subscription( self, - param_1: str, + subscription_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/subscriptions/{param}/activate.""" return self._request( Operation("POST", "/billing/subscriptions/{param}/activate"), - path_params=(param_1,), + path_params=(subscription_id,), query=query, body=body, ) - def post_billing_subscriptions_by_param_1_cancel( + def cancel_subscription( self, - param_1: str, + subscription_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/subscriptions/{param}/cancel.""" return self._request( Operation("POST", "/billing/subscriptions/{param}/cancel"), - path_params=(param_1,), + path_params=(subscription_id,), query=query, body=body, ) - def post_billing_subscriptions_by_param_1_pause( + def pause_subscription( self, - param_1: str, + subscription_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/subscriptions/{param}/pause.""" return self._request( Operation("POST", "/billing/subscriptions/{param}/pause"), - path_params=(param_1,), + path_params=(subscription_id,), query=query, body=body, ) - def post_billing_subscriptions_by_param_1_resume( + def resume_subscription( self, - param_1: str, + subscription_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/subscriptions/{param}/resume.""" return self._request( Operation("POST", "/billing/subscriptions/{param}/resume"), - path_params=(param_1,), + path_params=(subscription_id,), query=query, body=body, ) - def post_billing_wallets_by_param_1_terminate( + def terminate_wallet( self, - param_1: str, + wallet_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/wallets/{param}/terminate.""" return self._request( Operation("POST", "/billing/wallets/{param}/terminate"), - path_params=(param_1,), + path_params=(wallet_id,), query=query, body=body, ) - def post_billing_wallets_by_param_1_top_up( + def top_up_wallet( self, - param_1: str, + wallet_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /billing/wallets/{param}/top-up.""" return self._request( Operation("POST", "/billing/wallets/{param}/top-up"), - path_params=(param_1,), + path_params=(wallet_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/blob.py b/frontal_sdk/resources/blob.py index 343624b..a0f78eb 100644 --- a/frontal_sdk/resources/blob.py +++ b/frontal_sdk/resources/blob.py @@ -6,7 +6,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import MultipartPart, QueryParams, RequestBody +from frontal_sdk.models import MultipartPart, QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -21,38 +22,38 @@ class Blob( ): """Methods for the blob API endpoints.""" - def delete_blob_object_by_param_1_by_param_2( - self, param_1: str, param_2: str, *, query: QueryParams | None = None + def delete_object( + self, container: str, object_key: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /blob/object/{param}/{param}.""" return self._request( Operation("DELETE", "/blob/object/{param}/{param}"), - path_params=(param_1, param_2), + path_params=(container, object_key), query=query, ) - def get_blob_object_info_by_param_1_by_param_2( - self, param_1: str, param_2: str, *, query: QueryParams | None = None + def get_object_info( + self, container: str, object_key: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /blob/object/info/{param}/{param}.""" return self._request( Operation("GET", "/blob/object/info/{param}/{param}"), - path_params=(param_1, param_2), + path_params=(container, object_key), query=query, ) - def get_blob_object_by_param_1_by_param_2( - self, param_1: str, param_2: str, *, query: QueryParams | None = None + def get_object( + self, container: str, object_key: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /blob/object/{param}/{param}.""" return self._request( Operation("GET", "/blob/object/{param}/{param}"), - path_params=(param_1, param_2), + path_params=(container, object_key), query=query, ) def post_blob_object_copy( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /blob/object/copy.""" return self._request( @@ -62,23 +63,23 @@ def post_blob_object_copy( body=body, ) - def post_blob_object_list_by_param_1( + def post_blob_object_list_by_list_id( self, - param_1: str, + list_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /blob/object/list/{param}.""" return self._request( Operation("POST", "/blob/object/list/{param}"), - path_params=(param_1,), + path_params=(list_id,), query=query, body=body, ) def post_blob_object_move( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /blob/object/move.""" return self._request( @@ -88,26 +89,26 @@ def post_blob_object_move( body=body, ) - def post_blob_object_sign_by_param_1_by_param_2( + def sign_object( self, - param_1: str, - param_2: str, + container: str, + object_key: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /blob/object/sign/{param}/{param}.""" return self._request( Operation("POST", "/blob/object/sign/{param}/{param}"), - path_params=(param_1, param_2), + path_params=(container, object_key), query=query, body=body, ) - def upload_blob_object_by_param_1_by_param_2( + def upload_object( self, - param_1: str, - param_2: str, + container: str, + object_key: str, parts: Sequence[MultipartPart], *, fields: Mapping[str, str] | None = None, @@ -116,6 +117,6 @@ def upload_blob_object_by_param_1_by_param_2( return self._upload( Operation("POSTFORMDATA", "/blob/object/{param}/{param}"), parts, - path_params=(param_1, param_2), + path_params=(container, object_key), fields=fields, ) diff --git a/frontal_sdk/resources/connectors.py b/frontal_sdk/resources/connectors.py index da53b2d..4040298 100644 --- a/frontal_sdk/resources/connectors.py +++ b/frontal_sdk/resources/connectors.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,13 +21,13 @@ class Connectors( ): """Methods for the connectors API endpoints.""" - def delete_connectors_installations_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_installation( + self, installation_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /connectors/installations/{param}.""" return self._request( Operation("DELETE", "/connectors/installations/{param}"), - path_params=(param_1,), + path_params=(installation_id,), query=query, ) @@ -40,29 +41,27 @@ def get_connectors_catalog( query=query, ) - def get_connectors_catalog_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_catalog( + self, catalog_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /connectors/catalog/{param}.""" return self._request( Operation("GET", "/connectors/catalog/{param}"), - path_params=(param_1,), + path_params=(catalog_id,), query=query, ) - def get_connectors_connection_tests_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_connection_test( + self, connection_test_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /connectors/connection-tests/{param}.""" return self._request( Operation("GET", "/connectors/connection-tests/{param}"), - path_params=(param_1,), + path_params=(connection_test_id,), query=query, ) - def get_connectors_installations( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_installations(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /connectors/installations.""" return self._request( Operation("GET", "/connectors/installations"), @@ -70,17 +69,17 @@ def get_connectors_installations( query=query, ) - def get_connectors_installations_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_installation( + self, installation_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /connectors/installations/{param}.""" return self._request( Operation("GET", "/connectors/installations/{param}"), - path_params=(param_1,), + path_params=(installation_id,), query=query, ) - def get_diagnostics(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_diagnostics(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /diagnostics.""" return self._request( Operation("GET", "/diagnostics"), @@ -88,23 +87,23 @@ def get_diagnostics(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def patch_connectors_installations_by_param_1( + def update_installation( self, - param_1: str, + installation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PATCH /connectors/installations/{param}.""" return self._request( Operation("PATCH", "/connectors/installations/{param}"), - path_params=(param_1,), + path_params=(installation_id,), query=query, body=body, ) - def post_connectors_installations( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_installation( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /connectors/installations.""" return self._request( @@ -114,47 +113,47 @@ def post_connectors_installations( body=body, ) - def post_connectors_installations_by_param_1_pause( + def pause_installation( self, - param_1: str, + installation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /connectors/installations/{param}/pause.""" return self._request( Operation("POST", "/connectors/installations/{param}/pause"), - path_params=(param_1,), + path_params=(installation_id,), query=query, body=body, ) - def post_connectors_installations_by_param_1_resume( + def resume_installation( self, - param_1: str, + installation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /connectors/installations/{param}/resume.""" return self._request( Operation("POST", "/connectors/installations/{param}/resume"), - path_params=(param_1,), + path_params=(installation_id,), query=query, body=body, ) - def post_connectors_sync_runs_by_param_1_replay( + def replay_sync_run( self, - param_1: str, + sync_run_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /connectors/sync-runs/{param}/replay.""" return self._request( Operation("POST", "/connectors/sync-runs/{param}/replay"), - path_params=(param_1,), + path_params=(sync_run_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/data.py b/frontal_sdk/resources/data.py index dd02f08..95aa24b 100644 --- a/frontal_sdk/resources/data.py +++ b/frontal_sdk/resources/data.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,9 +21,7 @@ class Data( ): """Methods for the data API endpoints.""" - def get_data_aggregations_aggregations( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_aggregations(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/aggregations/aggregations.""" return self._request( Operation("GET", "/data/aggregations/aggregations"), @@ -30,19 +29,17 @@ def get_data_aggregations_aggregations( query=query, ) - def get_data_aggregations_aggregations_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_aggregation( + self, aggregation_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/aggregations/aggregations/{param}.""" return self._request( Operation("GET", "/data/aggregations/aggregations/{param}"), - path_params=(param_1,), + path_params=(aggregation_id,), query=query, ) - def get_data_archival_archival_policies( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_policies(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/archival/archival/policies.""" return self._request( Operation("GET", "/data/archival/archival/policies"), @@ -50,17 +47,17 @@ def get_data_archival_archival_policies( query=query, ) - def get_data_archival_archival_policies_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_policy( + self, policy_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/archival/archival/policies/{param}.""" return self._request( Operation("GET", "/data/archival/archival/policies/{param}"), - path_params=(param_1,), + path_params=(policy_id,), query=query, ) - def get_data_enrichment_enrichment_profiles( + def list_enrichment_profiles( self, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/enrichment/enrichment/profiles.""" @@ -70,19 +67,17 @@ def get_data_enrichment_enrichment_profiles( query=query, ) - def get_data_enrichment_enrichment_profiles_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_enrichment_profile( + self, profile_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/enrichment/enrichment/profiles/{param}.""" return self._request( Operation("GET", "/data/enrichment/enrichment/profiles/{param}"), - path_params=(param_1,), + path_params=(profile_id,), query=query, ) - def get_data_exports_exports( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_exports(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/exports/exports.""" return self._request( Operation("GET", "/data/exports/exports"), @@ -90,17 +85,17 @@ def get_data_exports_exports( query=query, ) - def get_data_exports_exports_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_export( + self, export_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/exports/exports/{param}.""" return self._request( Operation("GET", "/data/exports/exports/{param}"), - path_params=(param_1,), + path_params=(export_id,), query=query, ) - def get_data_normalization_normalization_profiles( + def list_normalization_profiles( self, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/normalization/normalization/profiles.""" @@ -110,19 +105,17 @@ def get_data_normalization_normalization_profiles( query=query, ) - def get_data_normalization_normalization_profiles_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_normalization_profile( + self, profile_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/normalization/normalization/profiles/{param}.""" return self._request( Operation("GET", "/data/normalization/normalization/profiles/{param}"), - path_params=(param_1,), + path_params=(profile_id,), query=query, ) - def get_data_quality_quality_rulesets( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_rulesets(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/quality/quality/rulesets.""" return self._request( Operation("GET", "/data/quality/quality/rulesets"), @@ -130,19 +123,17 @@ def get_data_quality_quality_rulesets( query=query, ) - def get_data_quality_quality_rulesets_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_ruleset( + self, ruleset_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/quality/quality/rulesets/{param}.""" return self._request( Operation("GET", "/data/quality/quality/rulesets/{param}"), - path_params=(param_1,), + path_params=(ruleset_id,), query=query, ) - def get_data_schemas_schemas( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_schemas(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/schemas/schemas.""" return self._request( Operation("GET", "/data/schemas/schemas"), @@ -150,19 +141,17 @@ def get_data_schemas_schemas( query=query, ) - def get_data_schemas_schemas_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_schema_ref( + self, schema_ref: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/schemas/schemas/{param}.""" return self._request( Operation("GET", "/data/schemas/schemas/{param}"), - path_params=(param_1,), + path_params=(schema_ref,), query=query, ) - def get_data_serving_serving_products( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_products(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/serving/serving/products.""" return self._request( Operation("GET", "/data/serving/serving/products"), @@ -170,19 +159,17 @@ def get_data_serving_serving_products( query=query, ) - def get_data_serving_serving_products_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_product( + self, product_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/serving/serving/products/{param}.""" return self._request( Operation("GET", "/data/serving/serving/products/{param}"), - path_params=(param_1,), + path_params=(product_id,), query=query, ) - def get_data_streams_streams( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_streams(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/streams/streams.""" return self._request( Operation("GET", "/data/streams/streams"), @@ -190,19 +177,17 @@ def get_data_streams_streams( query=query, ) - def get_data_streams_streams_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_stream( + self, stream_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/streams/streams/{param}.""" return self._request( Operation("GET", "/data/streams/streams/{param}"), - path_params=(param_1,), + path_params=(stream_id,), query=query, ) - def get_data_sync_sync_jobs( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_jobs(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/sync/sync/jobs.""" return self._request( Operation("GET", "/data/sync/sync/jobs"), @@ -210,19 +195,15 @@ def get_data_sync_sync_jobs( query=query, ) - def get_data_sync_sync_jobs_by_param_1( - self, param_1: str, *, query: QueryParams | None = None - ) -> JSONResultT: + def get_job(self, job_id: str, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/sync/sync/jobs/{param}.""" return self._request( Operation("GET", "/data/sync/sync/jobs/{param}"), - path_params=(param_1,), + path_params=(job_id,), query=query, ) - def get_data_transformations_transformations( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_transformations(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/transformations/transformations.""" return self._request( Operation("GET", "/data/transformations/transformations"), @@ -230,18 +211,18 @@ def get_data_transformations_transformations( query=query, ) - def get_data_transformations_transformations_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_transformation( + self, transformation_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/transformations/transformations/{param}.""" return self._request( Operation("GET", "/data/transformations/transformations/{param}"), - path_params=(param_1,), + path_params=(transformation_id,), query=query, ) - def post_data_aggregations_aggregations( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_aggregation( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/aggregations/aggregations.""" return self._request( @@ -251,23 +232,23 @@ def post_data_aggregations_aggregations( body=body, ) - def post_data_aggregations_aggregations_by_param_1_executions( + def create_execution_for_aggregation( self, - param_1: str, + aggregation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/aggregations/aggregations/{param}/executions.""" return self._request( Operation("POST", "/data/aggregations/aggregations/{param}/executions"), - path_params=(param_1,), + path_params=(aggregation_id,), query=query, body=body, ) - def post_data_archival_archival_policies( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_policy( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/archival/archival/policies.""" return self._request( @@ -277,23 +258,23 @@ def post_data_archival_archival_policies( body=body, ) - def post_data_archival_archival_policies_by_param_1_executions( + def create_execution_for_policy( self, - param_1: str, + policy_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/archival/archival/policies/{param}/executions.""" return self._request( Operation("POST", "/data/archival/archival/policies/{param}/executions"), - path_params=(param_1,), + path_params=(policy_id,), query=query, body=body, ) - def post_data_enrichment_enrichment_profiles( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_enrichment_profile( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/enrichment/enrichment/profiles.""" return self._request( @@ -303,25 +284,25 @@ def post_data_enrichment_enrichment_profiles( body=body, ) - def post_data_enrichment_enrichment_profiles_by_param_1_executions( + def create_execution_for_enrichment_profile( self, - param_1: str, + profile_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/enrichment/enrichment/profiles/{param}/executions.""" return self._request( Operation( "POST", "/data/enrichment/enrichment/profiles/{param}/executions" ), - path_params=(param_1,), + path_params=(profile_id,), query=query, body=body, ) - def post_data_exports_exports( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_export( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/exports/exports.""" return self._request( @@ -331,23 +312,23 @@ def post_data_exports_exports( body=body, ) - def post_data_exports_exports_by_param_1_executions( + def create_execution_for_export( self, - param_1: str, + export_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/exports/exports/{param}/executions.""" return self._request( Operation("POST", "/data/exports/exports/{param}/executions"), - path_params=(param_1,), + path_params=(export_id,), query=query, body=body, ) - def post_data_normalization_normalization_profiles( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_normalization_profile( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/normalization/normalization/profiles.""" return self._request( @@ -357,25 +338,25 @@ def post_data_normalization_normalization_profiles( body=body, ) - def post_data_normalization_normalization_profiles_by_param_1_executions( + def create_execution_for_normalization_profile( self, - param_1: str, + profile_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/normalization/normalization/profiles/{param}/executions.""" return self._request( Operation( "POST", "/data/normalization/normalization/profiles/{param}/executions" ), - path_params=(param_1,), + path_params=(profile_id,), query=query, body=body, ) - def post_data_quality_quality_rulesets( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_ruleset( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/quality/quality/rulesets.""" return self._request( @@ -385,23 +366,23 @@ def post_data_quality_quality_rulesets( body=body, ) - def post_data_quality_quality_rulesets_by_param_1_evaluations( + def create_evaluation_for_ruleset( self, - param_1: str, + ruleset_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/quality/quality/rulesets/{param}/evaluations.""" return self._request( Operation("POST", "/data/quality/quality/rulesets/{param}/evaluations"), - path_params=(param_1,), + path_params=(ruleset_id,), query=query, body=body, ) def post_data_query_query_federated( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/query/query/federated.""" return self._request( @@ -411,8 +392,8 @@ def post_data_query_query_federated( body=body, ) - def post_data_schemas_schemas( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_schema( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/schemas/schemas.""" return self._request( @@ -423,7 +404,7 @@ def post_data_schemas_schemas( ) def post_data_schemas_schemas_resolve( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/schemas/schemas/resolve.""" return self._request( @@ -433,8 +414,8 @@ def post_data_schemas_schemas_resolve( body=body, ) - def post_data_serving_serving_products( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_product( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/serving/serving/products.""" return self._request( @@ -444,23 +425,23 @@ def post_data_serving_serving_products( body=body, ) - def post_data_serving_serving_products_by_param_1_refreshes( + def create_refresh_for_product( self, - param_1: str, + product_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/serving/serving/products/{param}/refreshes.""" return self._request( Operation("POST", "/data/serving/serving/products/{param}/refreshes"), - path_params=(param_1,), + path_params=(product_id,), query=query, body=body, ) - def post_data_streams_streams( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_stream( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/streams/streams.""" return self._request( @@ -470,23 +451,23 @@ def post_data_streams_streams( body=body, ) - def post_data_streams_streams_by_param_1_deliveries( + def create_delivery_for_stream( self, - param_1: str, + stream_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/streams/streams/{param}/deliveries.""" return self._request( Operation("POST", "/data/streams/streams/{param}/deliveries"), - path_params=(param_1,), + path_params=(stream_id,), query=query, body=body, ) - def post_data_sync_sync_jobs( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_job( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/sync/sync/jobs.""" return self._request( @@ -496,23 +477,23 @@ def post_data_sync_sync_jobs( body=body, ) - def post_data_sync_sync_jobs_by_param_1_executions( + def create_execution_for_job( self, - param_1: str, + job_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/sync/sync/jobs/{param}/executions.""" return self._request( Operation("POST", "/data/sync/sync/jobs/{param}/executions"), - path_params=(param_1,), + path_params=(job_id,), query=query, body=body, ) - def post_data_transformations_transformations( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_transformation( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/transformations/transformations.""" return self._request( @@ -522,19 +503,19 @@ def post_data_transformations_transformations( body=body, ) - def post_data_transformations_transformations_by_param_1_executions( + def create_execution_for_transformation( self, - param_1: str, + transformation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /data/transformations/transformations/{param}/executions.""" return self._request( Operation( "POST", "/data/transformations/transformations/{param}/executions" ), - path_params=(param_1,), + path_params=(transformation_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/governance.py b/frontal_sdk/resources/governance.py index a1945c8..8c59fad 100644 --- a/frontal_sdk/resources/governance.py +++ b/frontal_sdk/resources/governance.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,29 +21,27 @@ class Governance( ): """Methods for the governance API endpoints.""" - def delete_policies_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_policy( + self, policy_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /policies/{param}.""" return self._request( Operation("DELETE", "/policies/{param}"), - path_params=(param_1,), + path_params=(policy_id,), query=query, ) - def delete_roles_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_role( + self, role_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /roles/{param}.""" return self._request( Operation("DELETE", "/roles/{param}"), - path_params=(param_1,), + path_params=(role_id,), query=query, ) - def get_compliance_assessments( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_assessments(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /compliance/assessments.""" return self._request( Operation("GET", "/compliance/assessments"), @@ -50,19 +49,17 @@ def get_compliance_assessments( query=query, ) - def get_compliance_assessments_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_assessment( + self, assessment_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /compliance/assessments/{param}.""" return self._request( Operation("GET", "/compliance/assessments/{param}"), - path_params=(param_1,), + path_params=(assessment_id,), query=query, ) - def get_compliance_frameworks( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_frameworks(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /compliance/frameworks.""" return self._request( Operation("GET", "/compliance/frameworks"), @@ -78,9 +75,7 @@ def get_compliance_score(self, *, query: QueryParams | None = None) -> JSONResul query=query, ) - def get_compliance_violations( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_violations(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /compliance/violations.""" return self._request( Operation("GET", "/compliance/violations"), @@ -88,7 +83,7 @@ def get_compliance_violations( query=query, ) - def get_permissions(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_permissions(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /permissions.""" return self._request( Operation("GET", "/permissions"), @@ -96,17 +91,17 @@ def get_permissions(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_permissions_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_permission( + self, permission_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /permissions/{param}.""" return self._request( Operation("GET", "/permissions/{param}"), - path_params=(param_1,), + path_params=(permission_id,), query=query, ) - def get_policies(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_policies(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /policies.""" return self._request( Operation("GET", "/policies"), @@ -114,29 +109,27 @@ def get_policies(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_policies_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_policy( + self, policy_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /policies/{param}.""" return self._request( Operation("GET", "/policies/{param}"), - path_params=(param_1,), + path_params=(policy_id,), query=query, ) - def get_policies_by_param_1_versions( - self, param_1: str, *, query: QueryParams | None = None + def list_policy_versions( + self, policy_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /policies/{param}/versions.""" return self._request( Operation("GET", "/policies/{param}/versions"), - path_params=(param_1,), + path_params=(policy_id,), query=query, ) - def get_policies_templates( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_templates(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /policies/templates.""" return self._request( Operation("GET", "/policies/templates"), @@ -144,7 +137,7 @@ def get_policies_templates( query=query, ) - def get_roles(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_roles(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /roles.""" return self._request( Operation("GET", "/roles"), @@ -152,18 +145,18 @@ def get_roles(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_roles_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_role( + self, role_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /roles/{param}.""" return self._request( Operation("GET", "/roles/{param}"), - path_params=(param_1,), + path_params=(role_id,), query=query, ) def post_access_check( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /access/check.""" return self._request( @@ -173,8 +166,8 @@ def post_access_check( body=body, ) - def post_compliance_assessments( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_assessment( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /compliance/assessments.""" return self._request( @@ -184,23 +177,23 @@ def post_compliance_assessments( body=body, ) - def post_compliance_violations_by_param_1_resolve( + def resolve_violation( self, - param_1: str, + violation_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /compliance/violations/{param}/resolve.""" return self._request( Operation("POST", "/compliance/violations/{param}/resolve"), - path_params=(param_1,), + path_params=(violation_id,), query=query, body=body, ) - def post_permissions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_permission( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /permissions.""" return self._request( @@ -210,8 +203,8 @@ def post_permissions( body=body, ) - def post_policies( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_policy( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /policies.""" return self._request( @@ -222,7 +215,7 @@ def post_policies( ) def post_policies_from_template( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /policies/from-template.""" return self._request( @@ -233,7 +226,7 @@ def post_policies_from_template( ) def post_policies_validate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /policies/validate.""" return self._request( @@ -243,8 +236,8 @@ def post_policies_validate( body=body, ) - def post_roles( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_role( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /roles.""" return self._request( @@ -254,17 +247,17 @@ def post_roles( body=body, ) - def put_policies_by_param_1( + def update_policy( self, - param_1: str, + policy_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /policies/{param}.""" return self._request( Operation("PUT", "/policies/{param}"), - path_params=(param_1,), + path_params=(policy_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/lineage.py b/frontal_sdk/resources/lineage.py index e501657..13aafc4 100644 --- a/frontal_sdk/resources/lineage.py +++ b/frontal_sdk/resources/lineage.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,7 +21,7 @@ class Lineage( ): """Methods for the lineage API endpoints.""" - def get_lineage_edges(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_edges(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /lineage/edges.""" return self._request( Operation("GET", "/lineage/edges"), @@ -28,13 +29,13 @@ def get_lineage_edges(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_lineage_edges_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_edge( + self, edge_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /lineage/edges/{param}.""" return self._request( Operation("GET", "/lineage/edges/{param}"), - path_params=(param_1,), + path_params=(edge_id,), query=query, ) @@ -46,7 +47,7 @@ def get_lineage_graph(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_lineage_nodes(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_nodes(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /lineage/nodes.""" return self._request( Operation("GET", "/lineage/nodes"), @@ -54,28 +55,28 @@ def get_lineage_nodes(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_lineage_nodes_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_node( + self, node_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /lineage/nodes/{param}.""" return self._request( Operation("GET", "/lineage/nodes/{param}"), - path_params=(param_1,), + path_params=(node_id,), query=query, ) - def get_lineage_nodes_by_param_1_trace( - self, param_1: str, *, query: QueryParams | None = None + def get_node_trace( + self, node_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /lineage/nodes/{param}/trace.""" return self._request( Operation("GET", "/lineage/nodes/{param}/trace"), - path_params=(param_1,), + path_params=(node_id,), query=query, ) def post_lineage_impact( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /lineage/impact.""" return self._request( diff --git a/frontal_sdk/resources/observability.py b/frontal_sdk/resources/observability.py index 1f95577..83311fb 100644 --- a/frontal_sdk/resources/observability.py +++ b/frontal_sdk/resources/observability.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,29 +21,27 @@ class Observability( ): """Methods for the observability API endpoints.""" - def delete_observability_alerts_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_alert( + self, alert_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /observability/alerts/{param}.""" return self._request( Operation("DELETE", "/observability/alerts/{param}"), - path_params=(param_1,), + path_params=(alert_id,), query=query, ) - def delete_observability_dashboards_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_dashboard( + self, dashboard_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /observability/dashboards/{param}.""" return self._request( Operation("DELETE", "/observability/dashboards/{param}"), - path_params=(param_1,), + path_params=(dashboard_id,), query=query, ) - def get_observability_alerts( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_alerts(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/alerts.""" return self._request( Operation("GET", "/observability/alerts"), @@ -50,9 +49,7 @@ def get_observability_alerts( query=query, ) - def get_observability_alerts_incidents( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_incidents(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/alerts/incidents.""" return self._request( Operation("GET", "/observability/alerts/incidents"), @@ -60,9 +57,7 @@ def get_observability_alerts_incidents( query=query, ) - def get_observability_dashboards( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_dashboards(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/dashboards.""" return self._request( Operation("GET", "/observability/dashboards"), @@ -70,19 +65,17 @@ def get_observability_dashboards( query=query, ) - def get_observability_dashboards_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_dashboard( + self, dashboard_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /observability/dashboards/{param}.""" return self._request( Operation("GET", "/observability/dashboards/{param}"), - path_params=(param_1,), + path_params=(dashboard_id,), query=query, ) - def get_observability_events_stats( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_stats(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/events/stats.""" return self._request( Operation("GET", "/observability/events/stats"), @@ -90,9 +83,7 @@ def get_observability_events_stats( query=query, ) - def get_observability_metrics( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_metrics(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/metrics.""" return self._request( Operation("GET", "/observability/metrics"), @@ -110,9 +101,7 @@ def get_observability_metrics_list( query=query, ) - def get_observability_traces( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_traces(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /observability/traces.""" return self._request( Operation("GET", "/observability/traces"), @@ -120,18 +109,18 @@ def get_observability_traces( query=query, ) - def get_observability_traces_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_trace( + self, trace_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /observability/traces/{param}.""" return self._request( Operation("GET", "/observability/traces/{param}"), - path_params=(param_1,), + path_params=(trace_id,), query=query, ) - def post_observability_alerts( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_alert( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/alerts.""" return self._request( @@ -141,38 +130,38 @@ def post_observability_alerts( body=body, ) - def post_observability_alerts_by_param_1_disable( + def disable_alert( self, - param_1: str, + alert_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /observability/alerts/{param}/disable.""" return self._request( Operation("POST", "/observability/alerts/{param}/disable"), - path_params=(param_1,), + path_params=(alert_id,), query=query, body=body, ) - def post_observability_alerts_by_param_1_enable( + def enable_alert( self, - param_1: str, + alert_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /observability/alerts/{param}/enable.""" return self._request( Operation("POST", "/observability/alerts/{param}/enable"), - path_params=(param_1,), + path_params=(alert_id,), query=query, body=body, ) - def post_observability_dashboards( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_dashboard( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/dashboards.""" return self._request( @@ -182,23 +171,23 @@ def post_observability_dashboards( body=body, ) - def post_observability_dashboards_by_param_1_share( + def share_dashboard( self, - param_1: str, + dashboard_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /observability/dashboards/{param}/share.""" return self._request( Operation("POST", "/observability/dashboards/{param}/share"), - path_params=(param_1,), + path_params=(dashboard_id,), query=query, body=body, ) - def post_observability_events( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_event( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/events.""" return self._request( @@ -209,7 +198,7 @@ def post_observability_events( ) def post_observability_events_batch( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/events/batch.""" return self._request( @@ -220,7 +209,7 @@ def post_observability_events_batch( ) def post_observability_logs_ingest( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/logs/ingest.""" return self._request( @@ -231,7 +220,7 @@ def post_observability_logs_ingest( ) def post_observability_logs_query( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/logs/query.""" return self._request( @@ -242,7 +231,7 @@ def post_observability_logs_query( ) def post_observability_metrics_ingest( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/metrics/ingest.""" return self._request( @@ -253,7 +242,7 @@ def post_observability_metrics_ingest( ) def post_observability_traces_query( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /observability/traces/query.""" return self._request( @@ -263,32 +252,32 @@ def post_observability_traces_query( body=body, ) - def put_observability_alerts_by_param_1( + def update_alert( self, - param_1: str, + alert_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /observability/alerts/{param}.""" return self._request( Operation("PUT", "/observability/alerts/{param}"), - path_params=(param_1,), + path_params=(alert_id,), query=query, body=body, ) - def put_observability_dashboards_by_param_1( + def update_dashboard( self, - param_1: str, + dashboard_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /observability/dashboards/{param}.""" return self._request( Operation("PUT", "/observability/dashboards/{param}"), - path_params=(param_1,), + path_params=(dashboard_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/ontology.py b/frontal_sdk/resources/ontology.py index b17c6ec..7e99d99 100644 --- a/frontal_sdk/resources/ontology.py +++ b/frontal_sdk/resources/ontology.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,109 +21,107 @@ class Ontology( ): """Methods for the ontology API endpoints.""" - def delete_ontology_objects_object_types_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_object_type( + self, object_type_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/objects/object-types/{param}.""" return self._request( Operation("DELETE", "/ontology/objects/object-types/{param}"), - path_params=(param_1,), + path_params=(object_type_id,), query=query, ) - def delete_ontology_objects_objects_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_object( + self, object_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/objects/objects/{param}.""" return self._request( Operation("DELETE", "/ontology/objects/objects/{param}"), - path_params=(param_1,), + path_params=(object_id,), query=query, ) - def delete_ontology_reasoning_rules_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_reasoning_rule( + self, rule_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/reasoning/rules/{param}.""" return self._request( Operation("DELETE", "/ontology/reasoning/rules/{param}"), - path_params=(param_1,), + path_params=(rule_id,), query=query, ) - def delete_ontology_relationships_relationship_types_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_relationship_type( + self, relationship_type_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/relationships/relationship-types/{param}.""" return self._request( Operation("DELETE", "/ontology/relationships/relationship-types/{param}"), - path_params=(param_1,), + path_params=(relationship_type_id,), query=query, ) - def delete_ontology_relationships_relationships_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_relationship( + self, relationship_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/relationships/relationships/{param}.""" return self._request( Operation("DELETE", "/ontology/relationships/relationships/{param}"), - path_params=(param_1,), + path_params=(relationship_id,), query=query, ) - def delete_ontology_rollouts_rollouts_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_rollout( + self, rollout_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/rollouts/rollouts/{param}.""" return self._request( Operation("DELETE", "/ontology/rollouts/rollouts/{param}"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, ) - def delete_ontology_rollups_rollups_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_rollup( + self, rollup_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/rollups/rollups/{param}.""" return self._request( Operation("DELETE", "/ontology/rollups/rollups/{param}"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, ) - def delete_ontology_schemas_schemas_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_schema( + self, schema_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/schemas/schemas/{param}.""" return self._request( Operation("DELETE", "/ontology/schemas/schemas/{param}"), - path_params=(param_1,), + path_params=(schema_id,), query=query, ) - def delete_ontology_validation_rules_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_validation_rule( + self, rule_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/validation/rules/{param}.""" return self._request( Operation("DELETE", "/ontology/validation/rules/{param}"), - path_params=(param_1,), + path_params=(rule_id,), query=query, ) - def delete_ontology_versions_versions_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_version( + self, version_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /ontology/versions/versions/{param}.""" return self._request( Operation("DELETE", "/ontology/versions/versions/{param}"), - path_params=(param_1,), + path_params=(version_id,), query=query, ) - def get_ontology_events_events( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_events(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/events/events.""" return self._request( Operation("GET", "/ontology/events/events"), @@ -130,29 +129,27 @@ def get_ontology_events_events( query=query, ) - def get_ontology_events_events_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_event( + self, event_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/events/events/{param}.""" return self._request( Operation("GET", "/ontology/events/events/{param}"), - path_params=(param_1,), + path_params=(event_id,), query=query, ) - def get_ontology_events_events_checkpoints_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_consumer( + self, consumer: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/events/events/checkpoints/{param}.""" return self._request( Operation("GET", "/ontology/events/events/checkpoints/{param}"), - path_params=(param_1,), + path_params=(consumer,), query=query, ) - def get_ontology_objects_object_types( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_object_types(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/objects/object-types.""" return self._request( Operation("GET", "/ontology/objects/object-types"), @@ -160,19 +157,17 @@ def get_ontology_objects_object_types( query=query, ) - def get_ontology_objects_object_types_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_object_type( + self, object_type_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/objects/object-types/{param}.""" return self._request( Operation("GET", "/ontology/objects/object-types/{param}"), - path_params=(param_1,), + path_params=(object_type_id,), query=query, ) - def get_ontology_objects_objects( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_objects(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/objects/objects.""" return self._request( Operation("GET", "/ontology/objects/objects"), @@ -180,19 +175,17 @@ def get_ontology_objects_objects( query=query, ) - def get_ontology_objects_objects_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_object( + self, object_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/objects/objects/{param}.""" return self._request( Operation("GET", "/ontology/objects/objects/{param}"), - path_params=(param_1,), + path_params=(object_id,), query=query, ) - def get_ontology_reasoning_rules( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_reasoning_rules(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/reasoning/rules.""" return self._request( Operation("GET", "/ontology/reasoning/rules"), @@ -200,7 +193,7 @@ def get_ontology_reasoning_rules( query=query, ) - def get_ontology_relationships_relationship_types( + def list_relationship_types( self, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/relationships/relationship-types.""" @@ -210,9 +203,7 @@ def get_ontology_relationships_relationship_types( query=query, ) - def get_ontology_relationships_relationships( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_relationships(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/relationships/relationships.""" return self._request( Operation("GET", "/ontology/relationships/relationships"), @@ -220,19 +211,17 @@ def get_ontology_relationships_relationships( query=query, ) - def get_ontology_relationships_relationships_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_relationship( + self, relationship_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/relationships/relationships/{param}.""" return self._request( Operation("GET", "/ontology/relationships/relationships/{param}"), - path_params=(param_1,), + path_params=(relationship_id,), query=query, ) - def get_ontology_rollouts_rollouts( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_rollouts(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/rollouts/rollouts.""" return self._request( Operation("GET", "/ontology/rollouts/rollouts"), @@ -240,39 +229,37 @@ def get_ontology_rollouts_rollouts( query=query, ) - def get_ontology_rollouts_rollouts_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_rollout( + self, rollout_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/rollouts/rollouts/{param}.""" return self._request( Operation("GET", "/ontology/rollouts/rollouts/{param}"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, ) - def get_ontology_rollouts_rollouts_by_param_1_status( - self, param_1: str, *, query: QueryParams | None = None + def list_rollout_status( + self, rollout_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/rollouts/rollouts/{param}/status.""" return self._request( Operation("GET", "/ontology/rollouts/rollouts/{param}/status"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, ) - def get_ontology_rollups_rollup_results_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_execution( + self, execution_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/rollups/rollup-results/{param}.""" return self._request( Operation("GET", "/ontology/rollups/rollup-results/{param}"), - path_params=(param_1,), + path_params=(execution_id,), query=query, ) - def get_ontology_rollups_rollups( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_rollups(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/rollups/rollups.""" return self._request( Operation("GET", "/ontology/rollups/rollups"), @@ -280,29 +267,27 @@ def get_ontology_rollups_rollups( query=query, ) - def get_ontology_rollups_rollups_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_rollup( + self, rollup_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/rollups/rollups/{param}.""" return self._request( Operation("GET", "/ontology/rollups/rollups/{param}"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, ) - def get_ontology_rollups_rollups_by_param_1_result( - self, param_1: str, *, query: QueryParams | None = None + def get_rollup_result( + self, rollup_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/rollups/rollups/{param}/result.""" return self._request( Operation("GET", "/ontology/rollups/rollups/{param}/result"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, ) - def get_ontology_schemas_schemas( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_schemas(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/schemas/schemas.""" return self._request( Operation("GET", "/ontology/schemas/schemas"), @@ -310,19 +295,17 @@ def get_ontology_schemas_schemas( query=query, ) - def get_ontology_schemas_schemas_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_schema( + self, schema_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/schemas/schemas/{param}.""" return self._request( Operation("GET", "/ontology/schemas/schemas/{param}"), - path_params=(param_1,), + path_params=(schema_id,), query=query, ) - def get_ontology_validation_rules( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_validation_rules(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/validation/rules.""" return self._request( Operation("GET", "/ontology/validation/rules"), @@ -330,19 +313,17 @@ def get_ontology_validation_rules( query=query, ) - def get_ontology_validation_rules_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_rule( + self, rule_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/validation/rules/{param}.""" return self._request( Operation("GET", "/ontology/validation/rules/{param}"), - path_params=(param_1,), + path_params=(rule_id,), query=query, ) - def get_ontology_versions_release_bundles( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_release_bundles(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /ontology/versions/release-bundles.""" return self._request( Operation("GET", "/ontology/versions/release-bundles"), @@ -350,28 +331,28 @@ def get_ontology_versions_release_bundles( query=query, ) - def get_ontology_versions_release_bundles_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_bundle( + self, bundle_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/versions/release-bundles/{param}.""" return self._request( Operation("GET", "/ontology/versions/release-bundles/{param}"), - path_params=(param_1,), + path_params=(bundle_id,), query=query, ) - def get_ontology_versions_versions_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_version( + self, version_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /ontology/versions/versions/{param}.""" return self._request( Operation("GET", "/ontology/versions/versions/{param}"), - path_params=(param_1,), + path_params=(version_id,), query=query, ) - def post_ontology_engine_ontologies_compare_versions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_compare_version( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/compare-versions.""" return self._request( @@ -382,7 +363,7 @@ def post_ontology_engine_ontologies_compare_versions( ) def post_ontology_engine_ontologies_export( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/export.""" return self._request( @@ -393,7 +374,7 @@ def post_ontology_engine_ontologies_export( ) def post_ontology_engine_ontologies_export_shacl( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/export-shacl.""" return self._request( @@ -404,7 +385,7 @@ def post_ontology_engine_ontologies_export_shacl( ) def post_ontology_engine_ontologies_generate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/generate.""" return self._request( @@ -414,8 +395,8 @@ def post_ontology_engine_ontologies_generate( body=body, ) - def post_ontology_engine_ontologies_infer_classes( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_infer_class( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/infer-classes.""" return self._request( @@ -425,8 +406,8 @@ def post_ontology_engine_ontologies_infer_classes( body=body, ) - def post_ontology_engine_ontologies_infer_properties( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_infer_property( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/infer-properties.""" return self._request( @@ -437,7 +418,7 @@ def post_ontology_engine_ontologies_infer_properties( ) def post_ontology_engine_ontologies_validate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/engine/ontologies/validate.""" return self._request( @@ -447,8 +428,8 @@ def post_ontology_engine_ontologies_validate( body=body, ) - def post_ontology_events_events( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_event( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/events/events.""" return self._request( @@ -458,8 +439,8 @@ def post_ontology_events_events( body=body, ) - def post_ontology_events_events_checkpoints( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_checkpoint( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/events/events/checkpoints.""" return self._request( @@ -470,7 +451,7 @@ def post_ontology_events_events_checkpoints( ) def post_ontology_events_events_leases_acknowledge( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/events/events/leases/acknowledge.""" return self._request( @@ -481,7 +462,7 @@ def post_ontology_events_events_leases_acknowledge( ) def post_ontology_events_events_leases_acquire( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/events/events/leases/acquire.""" return self._request( @@ -492,7 +473,7 @@ def post_ontology_events_events_leases_acquire( ) def post_ontology_extract_extract_analyze( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/analyze.""" return self._request( @@ -503,7 +484,7 @@ def post_ontology_extract_extract_analyze( ) def post_ontology_extract_extract_architecture( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/architecture.""" return self._request( @@ -513,8 +494,8 @@ def post_ontology_extract_extract_architecture( body=body, ) - def post_ontology_extract_extract_coreferences( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_coreference( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/coreferences.""" return self._request( @@ -524,8 +505,8 @@ def post_ontology_extract_extract_coreferences( body=body, ) - def post_ontology_extract_extract_entities( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_entity( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/entities.""" return self._request( @@ -535,8 +516,8 @@ def post_ontology_extract_extract_entities( body=body, ) - def post_ontology_extract_extract_events( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_extract_event( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/events.""" return self._request( @@ -546,8 +527,8 @@ def post_ontology_extract_extract_events( body=body, ) - def post_ontology_extract_extract_relations( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_relation( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/relations.""" return self._request( @@ -557,8 +538,8 @@ def post_ontology_extract_extract_relations( body=body, ) - def post_ontology_extract_extract_triplets( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_triplet( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/extract/extract/triplets.""" return self._request( @@ -569,7 +550,7 @@ def post_ontology_extract_extract_triplets( ) def post_ontology_reasoning_explain( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/explain.""" return self._request( @@ -579,8 +560,8 @@ def post_ontology_reasoning_explain( body=body, ) - def post_ontology_reasoning_facts( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_fact( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/facts.""" return self._request( @@ -591,7 +572,7 @@ def post_ontology_reasoning_facts( ) def post_ontology_reasoning_facts_load_graph( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/facts/load-graph.""" return self._request( @@ -602,7 +583,7 @@ def post_ontology_reasoning_facts_load_graph( ) def post_ontology_reasoning_reason_backward( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/reason/backward.""" return self._request( @@ -613,7 +594,7 @@ def post_ontology_reasoning_reason_backward( ) def post_ontology_reasoning_reason_forward( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/reason/forward.""" return self._request( @@ -623,8 +604,8 @@ def post_ontology_reasoning_reason_forward( body=body, ) - def post_ontology_reasoning_rules( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_reasoning_rule( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/reasoning/rules.""" return self._request( @@ -634,8 +615,8 @@ def post_ontology_reasoning_rules( body=body, ) - def post_ontology_rollouts_rollouts( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_rollout( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/rollouts/rollouts.""" return self._request( @@ -645,68 +626,68 @@ def post_ontology_rollouts_rollouts( body=body, ) - def post_ontology_rollouts_rollouts_by_param_1_pause( + def pause_rollout( self, - param_1: str, + rollout_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollouts/rollouts/{param}/pause.""" return self._request( Operation("POST", "/ontology/rollouts/rollouts/{param}/pause"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, body=body, ) - def post_ontology_rollouts_rollouts_by_param_1_resume( + def resume_rollout( self, - param_1: str, + rollout_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollouts/rollouts/{param}/resume.""" return self._request( Operation("POST", "/ontology/rollouts/rollouts/{param}/resume"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, body=body, ) - def post_ontology_rollouts_rollouts_by_param_1_rollback( + def rollback_rollout( self, - param_1: str, + rollout_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollouts/rollouts/{param}/rollback.""" return self._request( Operation("POST", "/ontology/rollouts/rollouts/{param}/rollback"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, body=body, ) - def post_ontology_rollouts_rollouts_by_param_1_start( + def start_rollout( self, - param_1: str, + rollout_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollouts/rollouts/{param}/start.""" return self._request( Operation("POST", "/ontology/rollouts/rollouts/{param}/start"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, body=body, ) - def post_ontology_rollups_rollups( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_rollup( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/rollups/rollups.""" return self._request( @@ -716,38 +697,38 @@ def post_ontology_rollups_rollups( body=body, ) - def post_ontology_rollups_rollups_by_param_1_execute( + def execute_rollup( self, - param_1: str, + rollup_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollups/rollups/{param}/execute.""" return self._request( Operation("POST", "/ontology/rollups/rollups/{param}/execute"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, body=body, ) - def post_ontology_rollups_rollups_by_param_1_preview( + def preview_rollup( self, - param_1: str, + rollup_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /ontology/rollups/rollups/{param}/preview.""" return self._request( Operation("POST", "/ontology/rollups/rollups/{param}/preview"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, body=body, ) - def post_ontology_schemas_schemas( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_schema( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/schemas/schemas.""" return self._request( @@ -758,7 +739,7 @@ def post_ontology_schemas_schemas( ) def post_ontology_schemas_schemas_validate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/schemas/schemas/validate.""" return self._request( @@ -768,8 +749,8 @@ def post_ontology_schemas_schemas_validate( body=body, ) - def post_ontology_transformations_transformations( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_transformation( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/transformations/transformations.""" return self._request( @@ -780,7 +761,7 @@ def post_ontology_transformations_transformations( ) def post_ontology_validation_payloads_validate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/validation/payloads/validate.""" return self._request( @@ -790,8 +771,8 @@ def post_ontology_validation_payloads_validate( body=body, ) - def post_ontology_validation_rules( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_validation_rule( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/validation/rules.""" return self._request( @@ -802,7 +783,7 @@ def post_ontology_validation_rules( ) def post_ontology_versions_audit_verify( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/versions/audit/verify.""" return self._request( @@ -812,8 +793,8 @@ def post_ontology_versions_audit_verify( body=body, ) - def post_ontology_versions_release_bundles( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_release_bundle( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/versions/release-bundles.""" return self._request( @@ -823,8 +804,8 @@ def post_ontology_versions_release_bundles( body=body, ) - def post_ontology_versions_versions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_version( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/versions/versions.""" return self._request( @@ -835,7 +816,7 @@ def post_ontology_versions_versions( ) def post_ontology_versions_versions_compare( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /ontology/versions/versions/compare.""" return self._request( @@ -845,92 +826,92 @@ def post_ontology_versions_versions_compare( body=body, ) - def put_ontology_objects_object_types_by_param_1( + def update_object_type( self, - param_1: str, + object_type_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/objects/object-types/{param}.""" return self._request( Operation("PUT", "/ontology/objects/object-types/{param}"), - path_params=(param_1,), + path_params=(object_type_id,), query=query, body=body, ) - def put_ontology_objects_objects_by_param_1( + def update_object( self, - param_1: str, + object_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/objects/objects/{param}.""" return self._request( Operation("PUT", "/ontology/objects/objects/{param}"), - path_params=(param_1,), + path_params=(object_id,), query=query, body=body, ) - def put_ontology_reasoning_rules_by_param_1( + def update_rule( self, - param_1: str, + rule_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/reasoning/rules/{param}.""" return self._request( Operation("PUT", "/ontology/reasoning/rules/{param}"), - path_params=(param_1,), + path_params=(rule_id,), query=query, body=body, ) - def put_ontology_relationships_relationships_by_param_1( + def update_relationship( self, - param_1: str, + relationship_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/relationships/relationships/{param}.""" return self._request( Operation("PUT", "/ontology/relationships/relationships/{param}"), - path_params=(param_1,), + path_params=(relationship_id,), query=query, body=body, ) - def put_ontology_rollouts_rollouts_by_param_1( + def update_rollout( self, - param_1: str, + rollout_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/rollouts/rollouts/{param}.""" return self._request( Operation("PUT", "/ontology/rollouts/rollouts/{param}"), - path_params=(param_1,), + path_params=(rollout_id,), query=query, body=body, ) - def put_ontology_rollups_rollups_by_param_1( + def update_rollup( self, - param_1: str, + rollup_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /ontology/rollups/rollups/{param}.""" return self._request( Operation("PUT", "/ontology/rollups/rollups/{param}"), - path_params=(param_1,), + path_params=(rollup_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/pipelines.py b/frontal_sdk/resources/pipelines.py index 4431dc8..a88fb9c 100644 --- a/frontal_sdk/resources/pipelines.py +++ b/frontal_sdk/resources/pipelines.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,9 +21,7 @@ class Pipelines( ): """Methods for the pipelines API endpoints.""" - def get_data_pipelines_capabilities( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_capabilities(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/pipelines/capabilities.""" return self._request( Operation("GET", "/data/pipelines/capabilities"), @@ -50,9 +49,7 @@ def get_data_pipelines_info( query=query, ) - def get_data_pipelines_pipeline_runs( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_pipeline_runs(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/pipelines/pipeline-runs.""" return self._request( Operation("GET", "/data/pipelines/pipeline-runs"), @@ -60,19 +57,15 @@ def get_data_pipelines_pipeline_runs( query=query, ) - def get_data_pipelines_pipeline_runs_by_param_1( - self, param_1: str, *, query: QueryParams | None = None - ) -> JSONResultT: + def get_run(self, run_id: str, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/pipelines/pipeline-runs/{param}.""" return self._request( Operation("GET", "/data/pipelines/pipeline-runs/{param}"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) - def get_data_pipelines_pipelines( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_pipelines(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/pipelines/pipelines.""" return self._request( Operation("GET", "/data/pipelines/pipelines"), @@ -80,19 +73,17 @@ def get_data_pipelines_pipelines( query=query, ) - def get_data_pipelines_pipelines_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_definition( + self, definition_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /data/pipelines/pipelines/{param}.""" return self._request( Operation("GET", "/data/pipelines/pipelines/{param}"), - path_params=(param_1,), + path_params=(definition_id,), query=query, ) - def get_data_pipelines_runs( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_runs(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /data/pipelines/runs.""" return self._request( Operation("GET", "/data/pipelines/runs"), @@ -100,8 +91,8 @@ def get_data_pipelines_runs( query=query, ) - def post_data_pipelines_pipelines( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_pipeline( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/pipelines/pipelines.""" return self._request( @@ -111,8 +102,8 @@ def post_data_pipelines_pipelines( body=body, ) - def post_data_pipelines_runs( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_run( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /data/pipelines/runs.""" return self._request( @@ -122,12 +113,12 @@ def post_data_pipelines_runs( body=body, ) - def stream_data_pipelines_pipeline_runs_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def stream_data_pipelines_pipeline_runs_by_run_id( + self, run_id: str, *, query: QueryParams | None = None ) -> StreamResultT: """Call STREAM /data/pipelines/pipeline-runs/{param}.""" return self._stream( Operation("STREAM", "/data/pipelines/pipeline-runs/{param}"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) diff --git a/frontal_sdk/resources/sandbox.py b/frontal_sdk/resources/sandbox.py index c4eec41..63e7de3 100644 --- a/frontal_sdk/resources/sandbox.py +++ b/frontal_sdk/resources/sandbox.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,7 +21,7 @@ class Sandbox( ): """Methods for the sandbox API endpoints.""" - def get_sandbox_languages(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_languages(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /sandbox/languages.""" return self._request( Operation("GET", "/sandbox/languages"), @@ -29,7 +30,7 @@ def get_sandbox_languages(self, *, query: QueryParams | None = None) -> JSONResu ) def post_sandbox_self_test( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /sandbox/self-test.""" return self._request( @@ -40,7 +41,7 @@ def post_sandbox_self_test( ) def post_sandbox_submit( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /sandbox/submit.""" return self._request( diff --git a/frontal_sdk/resources/schedules.py b/frontal_sdk/resources/schedules.py index 16ac590..b1ca0cc 100644 --- a/frontal_sdk/resources/schedules.py +++ b/frontal_sdk/resources/schedules.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,19 +21,17 @@ class Schedules( ): """Methods for the schedules API endpoints.""" - def delete_workflows_schedules_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_schedule( + self, schedule_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /workflows/schedules/{param}.""" return self._request( Operation("DELETE", "/workflows/schedules/{param}"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, ) - def get_workflows_schedules( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_schedules(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /workflows/schedules.""" return self._request( Operation("GET", "/workflows/schedules"), @@ -40,33 +39,33 @@ def get_workflows_schedules( query=query, ) - def get_workflows_schedules_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_schedule( + self, schedule_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/schedules/{param}.""" return self._request( Operation("GET", "/workflows/schedules/{param}"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, ) - def patch_workflows_schedules_by_param_1( + def update_schedule( self, - param_1: str, + schedule_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PATCH /workflows/schedules/{param}.""" return self._request( Operation("PATCH", "/workflows/schedules/{param}"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, body=body, ) def post_workflows_cron_parse( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows/cron/parse.""" return self._request( @@ -77,7 +76,7 @@ def post_workflows_cron_parse( ) def post_workflows_cron_validate( - self, *, query: QueryParams | None = None, body: RequestBody = None + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows/cron/validate.""" return self._request( @@ -87,8 +86,8 @@ def post_workflows_cron_validate( body=body, ) - def post_workflows_schedules( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_schedule( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows/schedules.""" return self._request( @@ -98,47 +97,47 @@ def post_workflows_schedules( body=body, ) - def post_workflows_schedules_by_param_1_pause( + def pause_schedule( self, - param_1: str, + schedule_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/schedules/{param}/pause.""" return self._request( Operation("POST", "/workflows/schedules/{param}/pause"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, body=body, ) - def post_workflows_schedules_by_param_1_resume( + def resume_schedule( self, - param_1: str, + schedule_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/schedules/{param}/resume.""" return self._request( Operation("POST", "/workflows/schedules/{param}/resume"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, body=body, ) - def post_workflows_schedules_by_param_1_trigger( + def trigger_schedule( self, - param_1: str, + schedule_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/schedules/{param}/trigger.""" return self._request( Operation("POST", "/workflows/schedules/{param}/trigger"), - path_params=(param_1,), + path_params=(schedule_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/webhooks.py b/frontal_sdk/resources/webhooks.py index 07fc417..bf3c7df 100644 --- a/frontal_sdk/resources/webhooks.py +++ b/frontal_sdk/resources/webhooks.py @@ -5,7 +5,8 @@ from typing import Generic from frontal_sdk.core.operation import Operation -from frontal_sdk.models import QueryParams, RequestBody +from frontal_sdk.models import QueryParams +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -20,17 +21,17 @@ class Webhooks( ): """Methods for the webhooks API endpoints.""" - def delete_webhooks_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_webhook( + self, webhook_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /webhooks/{param}.""" return self._request( Operation("DELETE", "/webhooks/{param}"), - path_params=(param_1,), + path_params=(webhook_id,), query=query, ) - def get_webhooks(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_webhooks(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /webhooks.""" return self._request( Operation("GET", "/webhooks"), @@ -38,19 +39,17 @@ def get_webhooks(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_webhooks_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_webhook( + self, webhook_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /webhooks/{param}.""" return self._request( Operation("GET", "/webhooks/{param}"), - path_params=(param_1,), + path_params=(webhook_id,), query=query, ) - def get_webhooks_deliveries( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_deliveries(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /webhooks/deliveries.""" return self._request( Operation("GET", "/webhooks/deliveries"), @@ -58,17 +57,17 @@ def get_webhooks_deliveries( query=query, ) - def get_webhooks_deliveries_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_delivery( + self, delivery_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /webhooks/deliveries/{param}.""" return self._request( Operation("GET", "/webhooks/deliveries/{param}"), - path_params=(param_1,), + path_params=(delivery_id,), query=query, ) - def get_webhooks_stats(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_stats(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /webhooks/stats.""" return self._request( Operation("GET", "/webhooks/stats"), @@ -76,8 +75,8 @@ def get_webhooks_stats(self, *, query: QueryParams | None = None) -> JSONResultT query=query, ) - def post_webhooks( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_webhook( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /webhooks.""" return self._request( @@ -87,47 +86,47 @@ def post_webhooks( body=body, ) - def post_webhooks_by_param_1_rotate_secret( + def rotate_secret_webhook( self, - param_1: str, + webhook_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /webhooks/{param}/rotate-secret.""" return self._request( Operation("POST", "/webhooks/{param}/rotate-secret"), - path_params=(param_1,), + path_params=(webhook_id,), query=query, body=body, ) - def post_webhooks_deliveries_by_param_1_retry( + def retry_delivery( self, - param_1: str, + delivery_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /webhooks/deliveries/{param}/retry.""" return self._request( Operation("POST", "/webhooks/deliveries/{param}/retry"), - path_params=(param_1,), + path_params=(delivery_id,), query=query, body=body, ) - def put_webhooks_by_param_1( + def update_webhook( self, - param_1: str, + webhook_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PUT /webhooks/{param}.""" return self._request( Operation("PUT", "/webhooks/{param}"), - path_params=(param_1,), + path_params=(webhook_id,), query=query, body=body, ) diff --git a/frontal_sdk/resources/workflows.py b/frontal_sdk/resources/workflows.py index 8b848f1..bd78b57 100644 --- a/frontal_sdk/resources/workflows.py +++ b/frontal_sdk/resources/workflows.py @@ -13,12 +13,12 @@ from frontal_sdk.models import ( JSONValue, QueryParams, - RequestBody, Workflow, WorkflowDefinition, WorkflowStep, WorkflowTrigger, ) +from frontal_sdk.models.requests import UNSET, RequestBodyInput from frontal_sdk.resources._base import ( APIResource, BytesResultT, @@ -44,17 +44,17 @@ def __init__( self.steps = WorkflowSteps(self) self.templates = WorkflowTemplates(self) - def delete_workflows_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def delete_workflow( + self, workflow_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call DELETE /workflows/{param}.""" return self._request( Operation("DELETE", "/workflows/{param}"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, ) - def get_workflows(self, *, query: QueryParams | None = None) -> JSONResultT: + def list_workflows(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /workflows.""" return self._request( Operation("GET", "/workflows"), @@ -62,19 +62,17 @@ def get_workflows(self, *, query: QueryParams | None = None) -> JSONResultT: query=query, ) - def get_workflows_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_workflow( + self, workflow_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/{param}.""" return self._request( Operation("GET", "/workflows/{param}"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, ) - def get_workflows_approvals( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_approvals(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /workflows/approvals.""" return self._request( Operation("GET", "/workflows/approvals"), @@ -82,19 +80,17 @@ def get_workflows_approvals( query=query, ) - def get_workflows_approvals_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_approval( + self, approval_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/approvals/{param}.""" return self._request( Operation("GET", "/workflows/approvals/{param}"), - path_params=(param_1,), + path_params=(approval_id,), query=query, ) - def get_workflows_executions( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_executions(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /workflows/executions.""" return self._request( Operation("GET", "/workflows/executions"), @@ -102,49 +98,47 @@ def get_workflows_executions( query=query, ) - def get_workflows_executions_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_execution( + self, execution_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/executions/{param}.""" return self._request( Operation("GET", "/workflows/executions/{param}"), - path_params=(param_1,), + path_params=(execution_id,), query=query, ) - def get_workflows_executions_by_param_1_tasks( - self, param_1: str, *, query: QueryParams | None = None + def list_execution_tasks( + self, execution_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/executions/{param}/tasks.""" return self._request( Operation("GET", "/workflows/executions/{param}/tasks"), - path_params=(param_1,), + path_params=(execution_id,), query=query, ) - def get_workflows_runs_by_param_1_steps( - self, param_1: str, *, query: QueryParams | None = None + def list_run_steps( + self, run_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/runs/{param}/steps.""" return self._request( Operation("GET", "/workflows/runs/{param}/steps"), - path_params=(param_1,), + path_params=(run_id,), query=query, ) - def get_workflows_tasks_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_task( + self, task_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/tasks/{param}.""" return self._request( Operation("GET", "/workflows/tasks/{param}"), - path_params=(param_1,), + path_params=(task_id,), query=query, ) - def get_workflows_templates( - self, *, query: QueryParams | None = None - ) -> JSONResultT: + def list_templates(self, *, query: QueryParams | None = None) -> JSONResultT: """Call GET /workflows/templates.""" return self._request( Operation("GET", "/workflows/templates"), @@ -152,33 +146,33 @@ def get_workflows_templates( query=query, ) - def get_workflows_templates_by_param_1( - self, param_1: str, *, query: QueryParams | None = None + def get_template( + self, template_id: str, *, query: QueryParams | None = None ) -> JSONResultT: """Call GET /workflows/templates/{param}.""" return self._request( Operation("GET", "/workflows/templates/{param}"), - path_params=(param_1,), + path_params=(template_id,), query=query, ) - def patch_workflows_by_param_1( + def update_workflow( self, - param_1: str, + workflow_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call PATCH /workflows/{param}.""" return self._request( Operation("PATCH", "/workflows/{param}"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, body=body, ) - def post_workflows( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_workflow( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows.""" return self._request( @@ -188,98 +182,98 @@ def post_workflows( body=body, ) - def post_workflows_by_param_1_archive( + def archive_workflow( self, - param_1: str, + workflow_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/{param}/archive.""" return self._request( Operation("POST", "/workflows/{param}/archive"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, body=body, ) - def post_workflows_by_param_1_publish( + def publish_workflow( self, - param_1: str, + workflow_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/{param}/publish.""" return self._request( Operation("POST", "/workflows/{param}/publish"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, body=body, ) - def post_workflows_by_param_1_restore( + def restore_workflow( self, - param_1: str, + workflow_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/{param}/restore.""" return self._request( Operation("POST", "/workflows/{param}/restore"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, body=body, ) - def post_workflows_by_param_1_versions( + def create_version_for_workflow( self, - param_1: str, + workflow_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/{param}/versions.""" return self._request( Operation("POST", "/workflows/{param}/versions"), - path_params=(param_1,), + path_params=(workflow_id,), query=query, body=body, ) - def post_workflows_approvals_by_param_1_approve( + def approve_approval( self, - param_1: str, + approval_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/approvals/{param}/approve.""" return self._request( Operation("POST", "/workflows/approvals/{param}/approve"), - path_params=(param_1,), + path_params=(approval_id,), query=query, body=body, ) - def post_workflows_approvals_by_param_1_reject( + def reject_approval( self, - param_1: str, + approval_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/approvals/{param}/reject.""" return self._request( Operation("POST", "/workflows/approvals/{param}/reject"), - path_params=(param_1,), + path_params=(approval_id,), query=query, body=body, ) - def post_workflows_executions( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_execution( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows/executions.""" return self._request( @@ -289,38 +283,38 @@ def post_workflows_executions( body=body, ) - def post_workflows_tasks_by_param_1_cancel( + def cancel_task( self, - param_1: str, + task_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/tasks/{param}/cancel.""" return self._request( Operation("POST", "/workflows/tasks/{param}/cancel"), - path_params=(param_1,), + path_params=(task_id,), query=query, body=body, ) - def post_workflows_tasks_by_param_1_retry( + def retry_task( self, - param_1: str, + task_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/tasks/{param}/retry.""" return self._request( Operation("POST", "/workflows/tasks/{param}/retry"), - path_params=(param_1,), + path_params=(task_id,), query=query, body=body, ) - def post_workflows_templates( - self, *, query: QueryParams | None = None, body: RequestBody = None + def create_template( + self, *, query: QueryParams | None = None, body: RequestBodyInput = UNSET ) -> JSONResultT: """Call POST /workflows/templates.""" return self._request( @@ -330,17 +324,17 @@ def post_workflows_templates( body=body, ) - def post_workflows_templates_by_param_1_instantiate( + def instantiate_template( self, - param_1: str, + template_id: str, *, query: QueryParams | None = None, - body: RequestBody = None, + body: RequestBodyInput = UNSET, ) -> JSONResultT: """Call POST /workflows/templates/{param}/instantiate.""" return self._request( Operation("POST", "/workflows/templates/{param}/instantiate"), - path_params=(param_1,), + path_params=(template_id,), query=query, body=body, ) @@ -372,7 +366,7 @@ def list( query["pageSize"] = limit if cursor is not None: query["pageToken"] = cursor - return self.get_workflows(query=query) + return self.list_workflows(query=query) def create( self, definition: WorkflowDefinition | Mapping[str, JSONValue] @@ -388,7 +382,7 @@ def create( } if model.description is not None: base["description"] = model.description - created = self.post_workflows(body=base) + created = self.create_workflow(body=base) return _flat_map( created, lambda raw: self._create_version(raw, model, payload), @@ -402,7 +396,7 @@ def _create_version( ) -> JSONResultT: workflow_data = _unwrap_record(created, "workflow") workflow_id = _resource_id(workflow_data, "workflowId") - version_result = self.post_workflows_by_param_1_versions( + version_result = self.create_version_for_workflow( workflow_id, body={"spec": payload} ) return _map_result( @@ -417,7 +411,7 @@ def _create_version( def _activate_created(self, created: JSONValue) -> JSONResultT: workflow_data = _unwrap_record(created, "workflow") workflow_id = _resource_id(workflow_data, "workflowId") - return self.post_workflows_by_param_1_publish(workflow_id, body={}) + return self.publish_workflow(workflow_id, body={}) def _workflow_definition( @@ -733,24 +727,22 @@ def __init__( self.id = workflow_id def get(self) -> JSONResultT: - return self._workflows.get_workflows_by_param_1(self.id) + return self._workflows.get_workflow(self.id) def update(self, definition: Mapping[str, JSONValue]) -> JSONResultT: - return self._workflows.patch_workflows_by_param_1( - self.id, body=dict(definition) - ) + return self._workflows.update_workflow(self.id, body=dict(definition)) def delete(self) -> JSONResultT: - return self._workflows.delete_workflows_by_param_1(self.id) + return self._workflows.delete_workflow(self.id) def activate(self) -> JSONResultT: - return self._workflows.post_workflows_by_param_1_publish(self.id, body={}) + return self._workflows.publish_workflow(self.id, body={}) def archive(self) -> JSONResultT: - return self._workflows.post_workflows_by_param_1_archive(self.id, body={}) + return self._workflows.archive_workflow(self.id, body={}) def restore(self) -> JSONResultT: - return self._workflows.post_workflows_by_param_1_restore(self.id, body={}) + return self._workflows.restore_workflow(self.id, body={}) def executions( self, @@ -761,13 +753,13 @@ def executions( ) -> JSONResultT: query = _page_query(status=status, limit=limit, cursor=cursor) query["workflowId"] = self.id - return self._workflows.get_workflows_executions(query=query) + return self._workflows.list_executions(query=query) def execution(self, execution_id: str) -> JSONResultT: - return self._workflows.get_workflows_executions_by_param_1(execution_id) + return self._workflows.get_execution(execution_id) def trigger(self, input: Mapping[str, JSONValue] | None = None) -> JSONResultT: - return self._workflows.post_workflows_executions( + return self._workflows.create_execution( body={"workflowId": self.id, "input": dict(input or {})} ) @@ -851,24 +843,20 @@ def list( limit: int | None = None, cursor: str | None = None, ) -> JSONResultT: - return self._workflows.get_workflows_approvals( + return self._workflows.list_approvals( query=_page_query(status=status, limit=limit, cursor=cursor) ) def get(self, approval_id: str) -> JSONResultT: - return self._workflows.get_workflows_approvals_by_param_1(approval_id) + return self._workflows.get_approval(approval_id) def approve(self, approval_id: str, comment: str | None = None) -> JSONResultT: body: dict[str, JSONValue] = {} if comment is None else {"comment": comment} - return self._workflows.post_workflows_approvals_by_param_1_approve( - approval_id, body=body - ) + return self._workflows.approve_approval(approval_id, body=body) def reject(self, approval_id: str, comment: str | None = None) -> JSONResultT: body: dict[str, JSONValue] = {} if comment is None else {"comment": comment} - return self._workflows.post_workflows_approvals_by_param_1_reject( - approval_id, body=body - ) + return self._workflows.reject_approval(approval_id, body=body) class WorkflowSteps(Generic[JSONResultT, BytesResultT, StreamResultT]): @@ -887,21 +875,19 @@ def list_tasks( limit: int | None = None, cursor: str | None = None, ) -> JSONResultT: - return self._workflows.get_workflows_executions_by_param_1_tasks( + return self._workflows.list_execution_tasks( execution_id, query=_page_query(status=status, limit=limit, cursor=cursor) ) def get_task(self, task_id: str) -> JSONResultT: - return self._workflows.get_workflows_tasks_by_param_1(task_id) + return self._workflows.get_task(task_id) def retry_task(self, task_id: str) -> JSONResultT: - return self._workflows.post_workflows_tasks_by_param_1_retry(task_id, body={}) + return self._workflows.retry_task(task_id, body={}) def cancel_task(self, task_id: str, reason: str | None = None) -> JSONResultT: body: dict[str, JSONValue] = {} if reason is None else {"reason": reason} - return self._workflows.post_workflows_tasks_by_param_1_cancel( - task_id, body=body - ) + return self._workflows.cancel_task(task_id, body=body) def list_run_steps( self, @@ -911,7 +897,7 @@ def list_run_steps( limit: int | None = None, cursor: str | None = None, ) -> JSONResultT: - return self._workflows.get_workflows_runs_by_param_1_steps( + return self._workflows.list_run_steps( run_id, query=_page_query(status=status, limit=limit, cursor=cursor) ) @@ -934,10 +920,10 @@ def list( query = _page_query(limit=limit, cursor=cursor) if category is not None: query["category"] = category - return self._workflows.get_workflows_templates(query=query) + return self._workflows.list_templates(query=query) def get(self, template_id: str) -> JSONResultT: - return self._workflows.get_workflows_templates_by_param_1(template_id) + return self._workflows.get_template(template_id) def create( self, @@ -959,12 +945,10 @@ def create( body["description"] = description if category is not None: body["category"] = category - return self._workflows.post_workflows_templates(body=body) + return self._workflows.create_template(body=body) def use(self, template_id: str, name: str) -> JSONResultT: - return self._workflows.post_workflows_templates_by_param_1_instantiate( - template_id, body={"name": name} - ) + return self._workflows.instantiate_template(template_id, body={"name": name}) __all__ = [ diff --git a/scripts/README.md b/scripts/README.md index 0b5c594..effa315 100644 --- a/scripts/README.md +++ b/scripts/README.md @@ -6,6 +6,14 @@ documentation and writes `docs/mcp.json` plus the root `mcp.json`. Both are repository maintenance utilities written in Python 3's standard library; they do not affect the SDK runtime or package dependencies. +`check_distribution.py` validates built wheel metadata, the `py.typed` marker, +and importability from the wheel. `benchmark_transport.py` measures mocked JSON +request overhead without network latency: + +```bash +python scripts/benchmark_transport.py --iterations 1000 +``` + Run them directly: ```bash diff --git a/scripts/benchmark_transport.py b/scripts/benchmark_transport.py new file mode 100644 index 0000000..610cce2 --- /dev/null +++ b/scripts/benchmark_transport.py @@ -0,0 +1,63 @@ +#!/usr/bin/env python3 +"""Measure local JSON transport overhead without network variability.""" + +from __future__ import annotations + +import argparse +import asyncio +import time + +import httpx +from frontal_sdk import AsyncFrontal, Frontal +from frontal_sdk.core import Operation + + +def response(request: httpx.Request) -> httpx.Response: + return httpx.Response(200, json={"ok": True}) + + +def benchmark_sync(iterations: int) -> float: + http = httpx.Client(transport=httpx.MockTransport(response)) + client = Frontal("frt_benchmark_key", http_client=http, max_retries=0) + operation = Operation("GET", "/health") + started = time.perf_counter() + for _ in range(iterations): + client._http.request(operation) + elapsed = time.perf_counter() - started + http.close() + return elapsed + + +async def benchmark_async(iterations: int) -> float: + http = httpx.AsyncClient(transport=httpx.MockTransport(response)) + client = AsyncFrontal("frt_benchmark_key", http_client=http, max_retries=0) + operation = Operation("GET", "/health") + started = time.perf_counter() + for _ in range(iterations): + await client._http.request(operation) + elapsed = time.perf_counter() - started + await http.aclose() + return elapsed + + +def main() -> None: + parser = argparse.ArgumentParser(description=__doc__) + parser.add_argument("--iterations", type=int, default=1000) + arguments = parser.parse_args() + if arguments.iterations < 1: + parser.error("--iterations must be positive") + + sync_elapsed = benchmark_sync(arguments.iterations) + async_elapsed = asyncio.run(benchmark_async(arguments.iterations)) + print( + f"sync: {arguments.iterations / sync_elapsed:.0f} mocked JSON requests/s " + f"({sync_elapsed:.3f}s total)" + ) + print( + f"async: {arguments.iterations / async_elapsed:.0f} mocked JSON requests/s " + f"({async_elapsed:.3f}s total)" + ) + + +if __name__ == "__main__": + main() diff --git a/scripts/check_contracts.py b/scripts/check_contracts.py index c813b71..688c1cc 100644 --- a/scripts/check_contracts.py +++ b/scripts/check_contracts.py @@ -70,6 +70,41 @@ def documented_operation(function: ast.FunctionDef) -> tuple[str, str] | None: return parts[1], parts[2][:-1] +def class_operations( + path: Path, resource: ast.ClassDef +) -> tuple[set[tuple[str, str]], list[str]]: + operations: set[tuple[str, str]] = set() + errors: list[str] = [] + for function in resource.body: + if not isinstance(function, ast.FunctionDef): + continue + documented = documented_operation(function) + if documented is None: + continue + if "by_param_" in function.name or any( + re.fullmatch(r"param_\d+", argument.arg) for argument in function.args.args + ): + errors.append( + f"{path.relative_to(ROOT)}:{function.name} uses a generic " + "path parameter name" + ) + actual = operation_calls(function) + if len(actual) != 1: + errors.append( + f"{path.relative_to(ROOT)}:{function.name} must call exactly " + "one Operation descriptor" + ) + continue + operation = next(iter(actual)) + if operation != documented: + errors.append( + f"{path.relative_to(ROOT)}:{function.name} documents " + f"{documented} but calls {operation}" + ) + operations.add(operation) + return operations, errors + + def resource_operations(path: Path) -> tuple[set[tuple[str, str]], list[str]]: tree = ast.parse(path.read_text(encoding="utf-8")) operations: set[tuple[str, str]] = set() @@ -77,29 +112,36 @@ def resource_operations(path: Path) -> tuple[set[tuple[str, str]], list[str]]: for resource in tree.body: if not isinstance(resource, ast.ClassDef): continue - for function in resource.body: - if not isinstance(function, ast.FunctionDef): - continue - documented = documented_operation(function) - if documented is None: - continue - actual = operation_calls(function) - if len(actual) != 1: - errors.append( - f"{path.relative_to(ROOT)}:{function.name} must call exactly " - "one Operation descriptor" - ) - continue - operation = next(iter(actual)) - if operation != documented: - errors.append( - f"{path.relative_to(ROOT)}:{function.name} documents " - f"{documented} but calls {operation}" - ) - operations.add(operation) + resource_ops, resource_errors = class_operations(path, resource) + operations.update(resource_ops) + errors.extend(resource_errors) return operations, errors +def resource_endpoint_names(path: Path) -> set[str]: + tree = ast.parse(path.read_text(encoding="utf-8")) + return { + function.name + for resource in tree.body + if isinstance(resource, ast.ClassDef) + for function in resource.body + if isinstance(function, ast.FunctionDef) + and documented_operation(function) is not None + } + + +def resource_public_method_names(path: Path) -> set[str]: + tree = ast.parse(path.read_text(encoding="utf-8")) + return { + function.name + for resource in tree.body + if isinstance(resource, ast.ClassDef) + for function in resource.body + if isinstance(function, (ast.FunctionDef, ast.AsyncFunctionDef)) + and not function.name.startswith("_") + } + + def parse_openapi(path: Path) -> set[tuple[str, str]]: document = load_json(path) paths = document.get("paths") diff --git a/scripts/check_distribution.py b/scripts/check_distribution.py new file mode 100644 index 0000000..e287422 --- /dev/null +++ b/scripts/check_distribution.py @@ -0,0 +1,68 @@ +#!/usr/bin/env python3 +"""Smoke-check the built wheel and source distribution.""" + +from __future__ import annotations + +import os +import subprocess +import sys +import tarfile +import tempfile +import zipfile +from pathlib import Path + +ROOT = Path(__file__).resolve().parents[1] +DIST = ROOT / "dist" +VERSION = "1.0.0" + + +def main() -> None: + wheels = list(DIST.glob("frontal-*.whl")) + sdists = list(DIST.glob("frontal-*.tar.gz")) + if len(wheels) != 1 or len(sdists) != 1: + raise SystemExit( + "expected one frontal wheel and one source distribution in dist/" + ) + + wheel = wheels[0] + with zipfile.ZipFile(wheel) as archive: + names = set(archive.namelist()) + metadata_path = next( + (name for name in names if name.endswith(".dist-info/METADATA")), None + ) + if metadata_path is None: + raise SystemExit("wheel is missing distribution metadata") + metadata = archive.read(metadata_path).decode("utf-8") + if f"Version: {VERSION}\n" not in metadata: + raise SystemExit(f"wheel metadata does not declare version {VERSION}") + if "frontal_sdk/py.typed" not in names: + raise SystemExit("wheel is missing frontal_sdk/py.typed") + + with tempfile.TemporaryDirectory(prefix="frontal-wheel-smoke-") as temp_dir: + environment = os.environ.copy() + environment["PYTHONPATH"] = os.pathsep.join( + [str(wheel), environment.get("PYTHONPATH", "")] + ) + subprocess.run( + [ + sys.executable, + "-c", + "import frontal_sdk; assert frontal_sdk.__version__ == '1.0.0'", + ], + cwd=temp_dir, + env=environment, + check=True, + ) + + with tarfile.open(sdists[0], "r:gz") as archive: + if not any( + name.startswith(f"frontal-{VERSION}/frontal_sdk/") + for name in archive.getnames() + ): + raise SystemExit("source distribution is missing the SDK package") + + print(f"validated built frontal {VERSION} wheel and source distribution") + + +if __name__ == "__main__": + main() diff --git a/templates/async-client/src/frontal_async/__main__.py b/templates/async-client/src/frontal_async/__main__.py index 4ad154c..c8a1e2f 100644 --- a/templates/async-client/src/frontal_async/__main__.py +++ b/templates/async-client/src/frontal_async/__main__.py @@ -20,7 +20,7 @@ async def fetch_agent( """Run one native asynchronous SDK request.""" async with semaphore: try: - result = await client.agents.get_agents_by_param_1(agent_id) + result = await client.agents.get(id=agent_id) except FrontalError as error: return agent_id, error return agent_id, result diff --git a/templates/batch-job/src/frontal_batch/__main__.py b/templates/batch-job/src/frontal_batch/__main__.py index c98df83..5e9c662 100644 --- a/templates/batch-job/src/frontal_batch/__main__.py +++ b/templates/batch-job/src/frontal_batch/__main__.py @@ -25,7 +25,7 @@ def process_agent_ids( if not normalized_id: continue try: - result = client.agents.get_agents_by_param_1(normalized_id) + result = client.agents.get(id=normalized_id) except FrontalError as error: failures += 1 logger.error("agent lookup failed for %s: %s", normalized_id, error) diff --git a/templates/cli/src/frontal_cli/__main__.py b/templates/cli/src/frontal_cli/__main__.py index a94a99a..2cd118e 100644 --- a/templates/cli/src/frontal_cli/__main__.py +++ b/templates/cli/src/frontal_cli/__main__.py @@ -29,9 +29,9 @@ def main(argv: Sequence[str] | None = None) -> int: if args.command == "health": result = client.ai.health() elif args.command == "agents": - result = client.agents.get_agents() + result = client.agents.list() else: - result = client.agents.get_agents_by_param_1(args.agent_id) + result = client.agents.get(id=args.agent_id) except FrontalError as error: print(f"Frontal API request failed: {error}", file=sys.stderr) return 1 diff --git a/tests/test_client.py b/tests/test_client.py index 6c5b525..d993cb1 100644 --- a/tests/test_client.py +++ b/tests/test_client.py @@ -3,9 +3,11 @@ from __future__ import annotations import json +import time from collections.abc import AsyncIterator, Iterator from typing import Any +import anyio import httpx import pytest import respx @@ -22,6 +24,7 @@ NetworkError, PageResult, RateLimitError, + ServerError, ServerEvent, ValidationError, async_paginate, @@ -30,6 +33,9 @@ poll_until, tool, ) +from frontal_sdk import ( + TimeoutError as FrontalTimeoutError, +) from frontal_sdk.core import ClientConfig, HttpClient, Operation from pydantic import Field @@ -94,9 +100,7 @@ def test_sync_request_auth_query_request_id_and_encoded_path( ).mock(return_value=httpx.Response(200, json={"ok": True})) client = Frontal("frt_local_key", max_retries=0) - response = client.agents.get_agents_by_param_1( - "agent/one", query={"include_runs": True} - ) + response = client.agents.get(id="agent/one", query={"include_runs": True}) request = route.calls.last.request assert response == {"ok": True} @@ -108,6 +112,147 @@ def test_sync_request_auth_query_request_id_and_encoded_path( client.close() +def test_workflow_and_schedule_getters_accept_resource_id_keywords( + respx_mock: respx.Router, +) -> None: + routes = [ + respx_mock.get(f"{API_URL}/workflows/approvals/approval_1").mock( + return_value=httpx.Response(200, json={"id": "approval_1"}) + ), + respx_mock.get(f"{API_URL}/workflows/executions/execution_1").mock( + return_value=httpx.Response(200, json={"id": "execution_1"}) + ), + respx_mock.get(f"{API_URL}/workflows/tasks/task_1").mock( + return_value=httpx.Response(200, json={"id": "task_1"}) + ), + respx_mock.get(f"{API_URL}/workflows/templates/template_1").mock( + return_value=httpx.Response(200, json={"id": "template_1"}) + ), + respx_mock.get(f"{API_URL}/workflows/schedules/schedule_1").mock( + return_value=httpx.Response(200, json={"id": "schedule_1"}) + ), + ] + client = Frontal("frt_local_key", max_retries=0) + + client.workflows.get_approval(approval_id="approval_1") + client.workflows.get_execution(execution_id="execution_1") + client.workflows.get_task(task_id="task_1") + client.workflows.get_template(template_id="template_1") + client.schedules.get_schedule(schedule_id="schedule_1") + + assert [route.call_count for route in routes] == [1, 1, 1, 1, 1] + client.close() + + +def test_sync_write_distinguishes_omitted_null_and_empty_json_body( + respx_mock: respx.Router, +) -> None: + routes = [ + respx_mock.post(f"{API_URL}/body/omitted").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + respx_mock.post(f"{API_URL}/body/null").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + respx_mock.post(f"{API_URL}/body/empty").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + ] + client = Frontal("frt_local_key", max_retries=0) + client._http.request(Operation("POST", "/body/omitted")) + client._http.request(Operation("POST", "/body/null"), body=None) + client._http.request(Operation("POST", "/body/empty"), body={}) + + assert routes[0].calls.last.request.content == b"" + assert routes[0].calls.last.request.headers.get("content-type") is None + assert routes[1].calls.last.request.content == b"null" + assert routes[2].calls.last.request.content == b"{}" + client.close() + + +def test_sse_last_event_id_persists_between_events() -> None: + from frontal_sdk.core.http import _parse_event_line + + event, event_id, data, parsed = _parse_event_line( + "id: cursor-1", "message", None, [] + ) + assert parsed is None + event, event_id, data, parsed = _parse_event_line( + 'data: {"n":1}', event, event_id, data + ) + assert parsed is None + event, event_id, data, parsed = _parse_event_line("", event, event_id, data) + assert parsed == ServerEvent("message", {"n": 1}, "cursor-1") + assert event_id == "cursor-1" + event, event_id, data, parsed = _parse_event_line( + 'data: {"n":2}', event, event_id, data + ) + assert parsed is None + _, _, _, parsed = _parse_event_line("", event, event_id, data) + assert parsed == ServerEvent("message", {"n": 2}, "cursor-1") + + +def test_nonstandard_error_json_is_preserved(respx_mock: respx.Router) -> None: + respx_mock.get(f"{API_URL}/failure").mock( + return_value=httpx.Response( + 400, json={"error": "invalid input", "field": "name"} + ) + ) + client = Frontal("frt_local_key", max_retries=0) + operation = Operation("GET", "/failure") + + with pytest.raises(FrontalError) as raised: + client._http.request(operation) + + assert raised.value.details == {"error": "invalid input", "field": "name"} + client.close() + + +def test_http_errors_distinguish_transient_from_safe_replay( + respx_mock: respx.Router, +) -> None: + respx_mock.get(f"{API_URL}/read").mock( + return_value=httpx.Response(503, json={"message": "temporary"}) + ) + respx_mock.post(f"{API_URL}/write").mock( + return_value=httpx.Response(503, json={"message": "temporary"}) + ) + client = Frontal("frt_local_key", max_retries=0) + read_operation = Operation("GET", "/read") + write_operation = Operation("POST", "/write") + + with pytest.raises(ServerError) as read_error: + client._http.request(read_operation) + with pytest.raises(ServerError) as write_error: + client._http.request(write_operation, body={}) + + assert read_error.value.transient is True + assert read_error.value.safe_to_retry is True + assert write_error.value.transient is True + assert write_error.value.safe_to_retry is False + client.close() + + +def test_sync_poll_rejects_a_result_returned_after_deadline() -> None: + def slow_fetch() -> str: + time.sleep(0.02) + return "ready" + + with pytest.raises(FrontalTimeoutError): + poll_until(slow_fetch, timeout=0.01) + + +def test_pagination_limit_requires_positive_integer() -> None: + def fetch_page(query: object) -> PageResult[str]: + raise AssertionError("invalid pagination arguments must fail before fetch") + + for value in (True, 1.5): + with pytest.raises(TypeError, match="max_pages must be an integer"): + list(paginate(fetch_page, max_pages=value)) # type: ignore[arg-type] + with pytest.raises(ValueError, match="max_pages must be positive"): + list(paginate(fetch_page, max_pages=0)) + + def test_sync_generate_text_uses_typed_chat_models( respx_mock: respx.Router, ) -> None: @@ -668,41 +813,6 @@ def test_agent_configure_json_and_approval_predicate( client.close() -def test_sync_ai_legacy_tool_registry_validates_input() -> None: - client = Frontal("frt_local_key", max_retries=0) - registered = client.ai.define_tool( - "double", - description="Double an integer", - parameters=ToolInput, - execute=lambda value: value.value * 2, - ) - client.ai.register_tool(registered) - - assert client.ai.get_tools() == [registered] - assert client.ai.execute_tool("double", {"value": "4"}) == 8 - with pytest.raises(ValueError, match="Tool not found"): - client.ai.execute_tool("missing", {}) - client.close() - - -@pytest.mark.anyio -async def test_async_ai_legacy_tool_registry_awaits_result() -> None: - async with AsyncFrontal("frt_local_key", max_retries=0) as client: - - async def double(value: ToolInput) -> int: - return value.value * 2 - - registered = client.ai.define_tool( - "double", - description="Double an integer", - parameters=ToolInput, - execute=double, - ) - client.ai.register_tool(registered) - - assert await client.ai.execute_tool("double", {"value": 5}) == 10 - - def test_sync_agent_wait_for_completion_polls_until_terminal( respx_mock: respx.Router, ) -> None: @@ -826,13 +936,25 @@ def test_pydantic_request_model_serializes_aliases(respx_mock: respx.Router) -> ) client = Frontal("frt_local_key", max_retries=0) - response = client.agents.post_agents(body=CreateAgent(display_name="sample")) + response = client.agents.create(body=CreateAgent(display_name="sample")) assert response == {"id": "agent_1"} assert json.loads(route.calls.last.request.content) == {"displayName": "sample"} client.close() +def test_agent_create_accepts_partial_json_mapping(respx_mock: respx.Router) -> None: + route = respx_mock.post(f"{API_URL}/agents").mock( + return_value=httpx.Response(201, json={"id": "agent_1"}) + ) + client = Frontal("frt_local_key", max_retries=0) + + client.agents.create(body={"name": "partial"}) + + assert json.loads(route.calls.last.request.content) == {"name": "partial"} + client.close() + + def test_sync_get_retries_transient_server_errors(respx_mock: respx.Router) -> None: route = respx_mock.get(f"{API_URL}/agents").mock( side_effect=[ @@ -842,7 +964,7 @@ def test_sync_get_retries_transient_server_errors(respx_mock: respx.Router) -> N ) client = Frontal("frt_local_key", max_retries=1) - assert client.agents.get_agents() == {"data": []} + assert client.agents.list() == {"data": []} assert route.call_count == 2 client.close() @@ -866,11 +988,11 @@ def test_sync_error_categories_include_request_id( client = Frontal("frt_local_key", max_retries=0) with pytest.raises(error_type) as raised: - client.agents.get_agents() + client.agents.list() assert raised.value.status_code == status assert raised.value.request_id == "req_123" - assert raised.value.retryable is False + assert raised.value.transient is False client.close() @@ -885,9 +1007,9 @@ def test_rate_limit_error_parses_retry_after(respx_mock: respx.Router) -> None: client = Frontal("frt_local_key", max_retries=0) with pytest.raises(RateLimitError) as raised: - client.agents.get_agents() + client.agents.list() - assert raised.value.retryable is True + assert raised.value.transient is True assert raised.value.retry_after == 5.0 client.close() @@ -901,7 +1023,7 @@ def test_multipart_and_raw_response(respx_mock: respx.Router) -> None: ) client = Frontal("frt_local_key", max_retries=0) - result = client.blob.upload_blob_object_by_param_1_by_param_2( + result = client.blob.upload_object( "reports", "report.txt", [ @@ -942,7 +1064,7 @@ def test_sync_sse_stream(respx_mock: respx.Router) -> None: ) client = Frontal("frt_local_key", max_retries=0) - events = list(client.agents.stream_agents_runs_by_param_1_stream("run_1")) + events = list(client.agents.runs.stream("run_1")) assert [(item.event, item.id, item.data) for item in events] == [ ("state", "evt_1", {"ready": True}) @@ -962,7 +1084,7 @@ def test_sync_sse_stream_does_not_retry_after_yielding_an_event( ) ) client = Frontal("frt_local_key", max_retries=2) - events = client.agents.stream_agents_runs_by_param_1_stream("run_1") + events = client.agents.runs.stream("run_1") assert next(events) == ServerEvent("message", {"step": 1}, None) with pytest.raises(NetworkError, match="Stream request failed"): @@ -982,6 +1104,42 @@ async def test_async_request_and_retry(respx_mock: respx.Router) -> None: assert route.call_count == 2 +@pytest.mark.anyio +async def test_async_write_distinguishes_omitted_null_and_empty_json_body( + respx_mock: respx.Router, +) -> None: + routes = [ + respx_mock.post(f"{API_URL}/body/omitted").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + respx_mock.post(f"{API_URL}/body/null").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + respx_mock.post(f"{API_URL}/body/empty").mock( + return_value=httpx.Response(200, json={"ok": True}) + ), + ] + async with AsyncFrontal("frt_local_key", max_retries=0) as client: + await client._http.request(Operation("POST", "/body/omitted")) + await client._http.request(Operation("POST", "/body/null"), body=None) + await client._http.request(Operation("POST", "/body/empty"), body={}) + + assert routes[0].calls.last.request.content == b"" + assert routes[0].calls.last.request.headers.get("content-type") is None + assert routes[1].calls.last.request.content == b"null" + assert routes[2].calls.last.request.content == b"{}" + + +@pytest.mark.anyio +async def test_async_poll_cancels_fetch_at_deadline() -> None: + async def slow_fetch() -> str: + await anyio.sleep(0.1) + return "ready" + + with pytest.raises(FrontalTimeoutError): + await async_poll_until(slow_fetch, timeout=0.01) + + @pytest.mark.anyio async def test_async_generate_text_uses_typed_chat_models( respx_mock: respx.Router, @@ -1052,13 +1210,8 @@ async def test_async_error_mapping_and_sse(respx_mock: respx.Router) -> None: ) async with AsyncFrontal("frt_local_key", max_retries=0) as client: with pytest.raises(AuthenticationError) as raised: - await client.agents.get_agents() - events = [ - event - async for event in client.agents.stream_agents_runs_by_param_1_stream( - "run_2" - ) - ] + await client.agents.list() + events = [event async for event in client.agents.runs.stream("run_2")] assert raised.value.request_id == "req_async" assert events == [ServerEvent("message", {"step": 1}, None)] @@ -1077,7 +1230,7 @@ async def test_async_sse_stream_does_not_retry_after_yielding_an_event( ) ) async with AsyncFrontal("frt_local_key", max_retries=2) as client: - events = client.agents.stream_agents_runs_by_param_1_stream("run_2") + events = client.agents.runs.stream("run_2") assert await events.__anext__() == ServerEvent("message", {"step": 1}, None) with pytest.raises(NetworkError, match="Stream request failed"): await events.__anext__()