This release is a pre-release and may not be stable for production use.
cqlib-tianyan
Python bindings for the Tianyan quantum cloud platform client.
Overview
This package provides synchronous Python access to the Tianyan quantum computing cloud platform, allowing users to:
- Authenticate with API keys
- Discover available quantum backends
- Submit quantum circuits (QCIS format)
- Retrieve execution results with readout error mitigation
All blocking operations release the GIL, making the library safe for use in multi-threaded Python applications.
Installation
From Source (Development)
# Install maturin if not already installed
pip install maturin
# Build and install the package
maturin develop
Production Build
maturin build --release
pip install target/wheels/*.whl
Quick Start
from cqlib_tianyan import TianyanPlatform
# Authenticate with your API key
platform = TianyanPlatform.login("your_api_key")
# List available backends
backends = platform.list_backends()
for backend in backends:
print(f"{backend.name}: {backend.status}")
# Get a specific backend
backend = platform.get_backend("tianyan-287")
print(f"Physical qubits: {backend.num_qubits()}")
# Submit a circuit
task = backend.run(["H Q1\nM Q1"], shots=1000)
# Wait for results
results = task.wait(timeout=120.0)
for result in results:
print(f"Task ID: {result.task_id}")
print(f"Counts: {result.counts}")
print(f"Probabilities: {result.probabilities}")
API Reference
Core Classes
TianyanPlatform
The main entry point for interacting with the Tianyan platform.
# Login with API key
platform = TianyanPlatform.login(
api_key="your_key",
domain="qc.zdxlz.com", # Optional
save_credentials=True, # Optional, default: True
auto_refresh=True, # Optional, default: True
)
# Load from saved credentials
platform = TianyanPlatform.from_credentials()
# List all backends
backends = platform.list_backends()
# Get specific backend
backend = platform.get_backend("device_name")
# Submit circuits directly
task = platform.submit(
circuits=["H Q1\nM Q1"],
shots=1000,
device_name="tianyan-287"
)
TianyanBackend
Represents a quantum computing backend.
Only superconducting devices and simulators can submit tasks. Photonic and ion-trap
devices fail before submission. Configuration access (device_config() and
num_qubits()) and readout calibration require a superconducting device.
In "auto" mode, simulators return raw counts without downloading configuration;
superconducting devices apply calibration when data is available and at most 14
qubits are measured. Explicit "enabled" mode fails before submission on any
non-superconducting device. "disabled" always returns raw counts.
# Backend properties
backend.name # Device identifier
backend.display_name # Human-readable name
backend.device_type # DeviceType enum
backend.status # DeviceStatus enum
backend.toll # DeviceToll enum (free/paid)
if backend.device_type == "superconducting":
backend.num_qubits() # Physical qubit count (loads config on first use)
# Check availability
if backend.is_available() and backend.device_type.value in ("superconducting", "simulator"):
# Submit circuits
task = backend.run(circuits=["H Q1\nM Q1"], shots=1000)
# Raw execution (no calibration)
task = backend.run(circuits=["H Q1\nM Q1"], shots=1000, calibration_mode="disabled")
# With explicit calibration mode
task = backend.run(
circuits=["H Q1\nM Q1"],
shots=1000,
calibration_mode="disabled" # "auto", "enabled", "disabled"
)
# Get device configuration
if backend.device_type == "superconducting":
device = backend.device_config() # Returns cqlib.device.Device
run(circuits, shots, *, calibration_mode="auto") accepts a string or a
CalibrationMode object. platform.submit() accepts the same keyword-only
option. Each call submits a new task. run_raw() and run_with_mode() remain
deprecated aliases and emit DeprecationWarning.
TaskHandle
Represents a batch of submitted circuits.
wait() and wait_raw() take timeout and poll_interval in seconds, with
defaults of 120.0 and 5.0. Both methods can be called without arguments.
# Task properties
task.task_ids # List of platform-assigned task IDs
task.device_name # Backend name
task.shots # Number of shots
task.submitted_at # ISO 8601 timestamp
# Non-blocking status check
results = task.status() # Returns completed results only
# Blocking wait for all results
results = task.wait(
timeout=120.0,
poll_interval=5.0
)
# Wait for raw results
results = task.wait_raw() # timeout=120.0, poll_interval=5.0 (seconds)
TianyanConfig
Configuration for the platform client.
config = TianyanConfig(
domain="qc.zdxlz.com",
save_credentials=True,
auto_refresh=True,
credentials_path="~/.cqlib/tianyan/credentials.json"
)
Enums
from cqlib_tianyan import DeviceStatus, DeviceToll, DeviceType, CalibrationMode
# DeviceStatus values: "running", "calibration", "under_maintenance", "offline", "upgrading", "unknown"
# DeviceToll values: "free", "paid", "unknown"
# DeviceType values: "superconducting", "photonic", "ion_trap", "simulator"
# CalibrationMode values: "auto", "enabled", "disabled"
Read backend.device_type.value, or compare directly with a string, such as
backend.device_type == "simulator".
| Device type | .value |
Devices |
|---|---|---|
| Simulator | simulator |
tianyan_sw, tianyan_s, tianyan_tn, tianyan_tnn, tianyan_sa, tianyan_swn |
| Photonic | photonic |
tianyan-p2000 |
| Superconducting | superconducting |
tianyan176, tianyan176-2, tianyan24, tianyan504, tianyan-287, tianyan-294 |
Exception Handling
from cqlib_tianyan import TianyanError
try:
platform = TianyanPlatform.login("invalid_key")
except Exception as e:
# Handle authentication failure
print(f"Login failed: {e}")
Note: In abi3 mode, TianyanError cannot be caught by type. Catch Exception instead.
Testing
Test Structure
tests/
├── conftest.py # Pytest configuration and fixtures
└── test_cqlib_tianyan.py # Main test file
Environment Variables
| Variable | Required | Description |
|---|---|---|
TIANYAN_API_KEY |
For integration tests | Your Tianyan platform API key |
TIANYAN_DOMAIN |
Optional | Custom domain (defaults to qc.zdxlz.com) |
TIANYAN_DEVICE |
Optional | Target device name (e.g., "tianyan-287") |
Running Tests
# Run all tests (requires API key)
TIANYAN_API_KEY="your_key" pytest tests/ -v
# Run with specific device
TIANYAN_API_KEY="your_key" TIANYAN_DEVICE="tianyan-287" pytest tests/ -v
# Run only unit tests (no API key required)
pytest tests/ -v -m "not integration"
# Run integration tests only
TIANYAN_API_KEY="your_key" pytest tests/ -v -m integration
# Include slow tests (long timeouts)
TIANYAN_API_KEY="your_key" pytest tests/ -v --run-slow
# Run specific test class
TIANYAN_API_KEY="your_key" pytest tests/test_cqlib_tianyan.py::TestCircuitSubmission -v
Test Markers
| Marker | Description |
|---|---|
integration |
Requires API access and network connectivity |
slow |
Long-running tests (waits for circuit execution) |
Technical Details
Architecture
This package is built with:
- PyO3: Rust-Python bindings
- Maturin: Build tool for Python-Rust hybrid projects
- abi3: Stable Python ABI (supports Python 3.10+)
Module Structure
crates/binding-python/
├── Cargo.toml # Rust package manifest
├── pyproject.toml # Python package configuration
├── src/
│ ├── lib.rs # Module initialization
│ ├── error.rs # Exception types
│ ├── config.rs # TianyanConfig bindings
│ ├── platform.rs # TianyanPlatform bindings
│ ├── backend.rs # TianyanBackend bindings
│ └── task.rs # TaskHandle bindings
├── cqlib_tianyan/
│ ├── __init__.py # Python package entry
│ ├── __init__.pyi # Type stubs
│ └── py.typed # PEP 561 marker
└── tests/
├── conftest.py # Pytest configuration
└── test_cqlib_tianyan.py # Test suite
Known Limitations
-
ABI3 Mode: Due to
abi3-py310feature:TianyanErrorcannot inherit fromRuntimeErrorTianyanErrorcannot be instantiated directly in Python- Exception catching must use
except Exception:instead ofexcept TianyanError:
-
GIL Release: Long-running operations (
wait(),wait_raw()) release the GIL to allow other Python threads to run.
Dependencies
- Python >= 3.10
- Optional extra
cqlib>=1.4.0b1(pip install cqlib-tianyan[cqlib]) fordevice_config()andExecutionResultconversion. Do not install classic PyPIcqlib 1.3.x; it does not providecqlib.deviceorcqlib.circuit. cqlib-core(Rust workspace / git dependency)cqlib-tianyan(Rust workspace dependency)
License
Licensed under the Apache License, Version 2.0.
Copyright (c) 2026 China Telecom Quantum Group
Metadata
Release files for cqlib-tianyan 0.1.0b1
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Built distributions (wheels)
| File | Reset | |||
|---|---|---|---|---|
| cqlib_tianyan-0.1.0b1-cp310-abi3-win_amd64.whl | CPython 3.10 | abi3 | Windows x86-64 | Details |
| cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_x86_64.whl | CPython 3.10 | abi3 | Linux glibc 2.28+ x86-64 | Details |
| cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_aarch64.whl | CPython 3.10 | abi3 | Linux glibc 2.28+ ARM64 | Details |
| cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_x86_64.whl | CPython 3.10 | abi3 | macOS 11.0+ x86-64 | Details |
| cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_arm64.whl | CPython 3.10 | abi3 | macOS 11.0+ ARM64 | Details |
Total release size: 10.6 MB
Release files / cqlib_tianyan-0.1.0b1-cp310-abi3-win_amd64.whl
| Download URL | cqlib_tianyan-0.1.0b1-cp310-abi3-win_amd64.whl |
|---|---|
| Size | 1.7 MB |
| Tags | CPython 3.10 Windows x86-64 abi3 |
|
SHA-256 checksum How to use checksums |
f776b527c62484e6d4f7384616d30a1d576a8a8788d4afd6476c62f46cc955c3
|
|
BLAKE2b-256 checksum How to use checksums |
c1b7ab107c033e1fa9e28e72bdf06e30fa66ba2ed8274da6f8e7d0be770be7fa
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.5
|
Release files / cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_x86_64.whl
| Download URL | cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_x86_64.whl |
|---|---|
| Size | 3.2 MB |
| Tags | CPython 3.10 Linux glibc 2.28+ x86-64 abi3 |
|
SHA-256 checksum How to use checksums |
c30e288d9ee712c2e8269eebf33ff279b27dc0b92074302685fe500efb522dff
|
|
BLAKE2b-256 checksum How to use checksums |
91c9d2aa6236ccf2be898d5e53384dfb5978f416b13b161660eb6dbb439c7b09
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.5
|
Release files / cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_aarch64.whl
| Download URL | cqlib_tianyan-0.1.0b1-cp310-abi3-manylinux_2_28_aarch64.whl |
|---|---|
| Size | 3.0 MB |
| Tags | CPython 3.10 Linux glibc 2.28+ ARM64 abi3 |
|
SHA-256 checksum How to use checksums |
521c37ee194f48651e0a6cf7b1d0d1513dbc498661c466faff0aa5abd34d8928
|
|
BLAKE2b-256 checksum How to use checksums |
6ee27cbeb96c6f0de0905adf11de09b41d8c762ce3e07e14db053e42b98c6d45
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.5
|
Release files / cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_x86_64.whl
| Download URL | cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_x86_64.whl |
|---|---|
| Size | 1.4 MB |
| Tags | CPython 3.10 abi3 macOS 11.0+ x86-64 |
|
SHA-256 checksum How to use checksums |
cf78dc265f22316d6f2bb767264a27048c3b2ec1408121b71ea0ef1672411e2a
|
|
BLAKE2b-256 checksum How to use checksums |
1a54673590f957e926fc2ae2b24de3e24df99264c483f2e8b4d751688f4264b1
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.5
|
Release files / cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_arm64.whl
| Download URL | cqlib_tianyan-0.1.0b1-cp310-abi3-macosx_11_0_arm64.whl |
|---|---|
| Size | 1.3 MB |
| Tags | CPython 3.10 abi3 macOS 11.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
4c59d1c3f3bb2c0b18e848b0fb9c08d8ac8f91024c869bbeb01358e88a1ece36
|
|
BLAKE2b-256 checksum How to use checksums |
ebae117797bc41b1d3e1cd7468afedbc023d8c74c949d1417fc9d6ef652d323a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.5
|