Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/spec-drift.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ jobs:
with:
persist-credentials: false
- name: Fetch latest spec
run: curl -sf https://api-staging.ionq.co/v0.4/api-docs -o /tmp/latest-spec.json
run: curl -sf https://api.ionq.co/v0.4/api-docs -o /tmp/latest-spec.json
- name: Check for drift
id: drift
run: |
Expand All @@ -34,6 +34,6 @@ jobs:
if [[ "$existing" == "0" ]]; then
gh issue create \
--title "OpenAPI spec has changed upstream" \
--body "The spec at api-staging.ionq.co/v0.4/api-docs has diverged from the vendored openapi.json. Fetch the new spec and regenerate the client." \
--body "The spec at api.ionq.co/v0.4/api-docs has diverged from the vendored openapi.json. Fetch the new spec and regenerate the client." \
--label spec-drift
fi
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ build/
htmlcov/
.coverage
docs/
.claude/
.DS_Store
.env
.idea/
Expand Down
15 changes: 15 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v6.0.0
hooks:
- id: trailing-whitespace
- id: end-of-file-fixer
- id: check-yaml
- id: check-added-large-files

- repo: https://github.com/astral-sh/ruff-pre-commit
rev: v0.15.11
hooks:
- id: ruff-check
args: [--fix]
- id: ruff-format
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## [0.1.0] - Unreleased
## [0.1.0] - 2026-04-22

### Added

Expand Down
2 changes: 1 addition & 1 deletion CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ Most of the code in `ionq_core/` is **auto-generated** from the IonQ OpenAPI spe
## Regenerating the client

```sh
curl -s https://api-staging.ionq.co/v0.4/api-docs -o openapi.json
curl -s https://api.ionq.co/v0.4/api-docs -o openapi.json

if [ -f openapi-overlay.yaml ]; then
uvx oas-patch==0.6.0 overlay openapi.json openapi-overlay.yaml -o /tmp/patched-spec.json
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -360,7 +360,7 @@ The client is generated from the vendored OpenAPI spec. To regenerate after API

```sh
# Fetch the latest spec
curl -s https://api-staging.ionq.co/v0.4/api-docs -o openapi.json
curl -s https://api.ionq.co/v0.4/api-docs -o openapi.json

# Apply overlay if present (patches spec issues that the generator can't handle)
if [ -f openapi-overlay.yaml ]; then
Expand Down
2 changes: 2 additions & 0 deletions custom-templates/package_init.py.jinja
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
{% from "helpers.jinja" import safe_docstring %}
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

{{ safe_docstring(package_description) }}
from ._exceptions import (
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""A client library for accessing IonQ Cloud Platform API"""

from ._exceptions import (
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_exceptions.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Structured exceptions for the IonQ API client."""


Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_extensions.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Extension API for downstream SDKs building on ionq-core."""

import logging
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_gates.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Pure-Python unitary matrices for IonQ native gates.

Phase parameters (phi, phi0, phi1) are in turns (fractions of 2*pi).
Expand Down
7 changes: 7 additions & 0 deletions ionq_core/_pagination.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Pagination helpers for cursor-based IonQ API endpoints."""

from __future__ import annotations
Expand Down Expand Up @@ -54,6 +57,7 @@ def iter_jobs(
submitter_id: str | Unset = UNSET,
limit: int | Unset = UNSET,
) -> Iterator[Job]:
"""Iterate over all jobs, automatically following pagination cursors."""
return _paginate(
get_jobs.sync,
"jobs",
Expand All @@ -75,6 +79,7 @@ def aiter_jobs(
submitter_id: str | Unset = UNSET,
limit: int | Unset = UNSET,
) -> AsyncIterator[Job]:
"""Async iterate over all jobs, automatically following pagination cursors."""
return _apaginate(
get_jobs.asyncio,
"jobs",
Expand All @@ -96,6 +101,7 @@ def iter_session_jobs(
submitter_id: str | Unset = UNSET,
limit: int | Unset = UNSET,
) -> Iterator[Job]:
"""Iterate over all jobs in a session, automatically following pagination cursors."""
return _paginate(
get_session_jobs.sync,
"session jobs",
Expand All @@ -117,6 +123,7 @@ def aiter_session_jobs(
submitter_id: str | Unset = UNSET,
limit: int | Unset = UNSET,
) -> AsyncIterator[Job]:
"""Async iterate over all jobs in a session, automatically following pagination cursors."""
return _apaginate(
get_session_jobs.asyncio,
"session jobs",
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_polling.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Job polling helpers for waiting on quantum job completion."""

from __future__ import annotations
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_session.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Session lifecycle manager for IonQ QPU sessions."""

from __future__ import annotations
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/_transport.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""Transport layer: retry via httpx-retries, error raising for IonQ API responses."""

import httpx
Expand Down
3 changes: 3 additions & 0 deletions ionq_core/ionq_client.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Copyright 2026 IonQ, Inc.
# SPDX-License-Identifier: Apache-2.0

"""IonQ-specific client convenience wrapper."""

import os
Expand Down
4 changes: 2 additions & 2 deletions tests/test_ionq_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,8 @@ def test_default_base_url(self):
assert IonQClient(api_key="key")._base_url == "https://api.ionq.co/v0.4"

def test_custom_base_url(self):
assert IonQClient(api_key="key", base_url="https://staging.ionq.co/v0.4")._base_url == (
"https://staging.ionq.co/v0.4"
assert IonQClient(api_key="key", base_url="https://staging.example.com/v0.4")._base_url == (
"https://staging.example.com/v0.4"
)

def test_auth_header_set_correctly(self):
Expand Down