Python SDK for OperRouter - DataSource and LLM operations
Project description
py-operrouter
Python SDK for OperRouter - A unified SDK for DataSource and LLM operations with multiple transport options.
Features
- โ Three Transport Layers: HTTP (JSON-RPC), gRPC (Protobuf), FFI (Direct Rust calls)
- ๐ DataSource Support: PostgreSQL, MySQL, MongoDB, Redis, Kafka
- ๐ค LLM Integration: OpenAI, Claude, Ollama
- โก Async/Await: Full async support with type hints
- ๐ก๏ธ Type Safe: Complete type definitions with dataclasses
- ๐ฆ Zero Dependencies: FFI client uses only Python stdlib (ctypes)
Installation
Basic Installation
# Install from source
cd sdks/py-operrouter
pip install -e .
Dependencies
- HTTP Client: Requires
httpx>=0.24.0 - gRPC Client: Requires
grpcio>=1.50.0,protobuf>=4.21.0 - FFI Client: No external dependencies (uses ctypes)
# Install with all transport layers
pip install -e ".[http,grpc]"
# Or install individually
pip install httpx # For HTTP client
pip install grpcio protobuf # For gRPC client
Building FFI Library (for FFI Client)
cd ../../bridges/operrouter-core-ffi
cargo build --release
The FFI client will automatically search for the library in common locations. You can also set OPERROUTER_FFI_PATH to specify the library path.
Quick Start
HTTP Client (JSON-RPC)
import asyncio
from py_operrouter import HTTPClient, DataSourceConfig
async def main():
# Create HTTP client
client = HTTPClient("http://localhost:8080")
# Test connection
ping_resp = await client.ping()
print(f"Server alive: {ping_resp.success}")
# Create datasource
config = DataSourceConfig(
driver="postgres",
host="localhost",
port=5432,
database="mydb",
username="user",
password="pass"
)
create_resp = await client.create_datasource("my_db", config)
# Query data
query_resp = await client.query_datasource("my_db", "SELECT * FROM users")
print(f"Found {len(query_resp.rows)} rows")
# Close connection
await client.close_datasource("my_db")
asyncio.run(main())
gRPC Client (High Performance)
import asyncio
from py_operrouter import GRPCClient, LLMConfig, ChatMessage
async def main():
# Create gRPC client
client = GRPCClient("localhost:50051")
try:
# Create LLM instance
config = LLMConfig(
provider="openai",
model="gpt-3.5-turbo",
api_key="sk-..."
)
await client.create_llm("my_llm", config)
# Chat with LLM
messages = [
ChatMessage(role="system", content="You are helpful."),
ChatMessage(role="user", content="Hello!")
]
chat_resp = await client.chat_llm("my_llm", messages)
print(f"Response: {chat_resp.text}")
# Cleanup
await client.close_llm("my_llm")
finally:
# Always close gRPC channel
await client.close()
asyncio.run(main())
FFI Client (Direct Rust Calls - Zero Overhead)
import asyncio
from py_operrouter import FFIClient, DataSourceConfig
async def main():
# Create FFI client (no network, direct Rust calls)
client = FFIClient()
# Test FFI connection
ping_resp = await client.ping()
print(f"FFI core alive: {ping_resp.success}")
# Create MongoDB datasource
config = DataSourceConfig(
driver="mongodb",
host="localhost",
port=27017,
database="testdb"
)
await client.create_datasource("my_mongo", config)
# Query MongoDB
query_resp = await client.query_datasource(
"my_mongo",
'{"find": "users", "limit": 10}'
)
print(f"Found {len(query_resp.rows)} documents")
asyncio.run(main())
API Reference
Client Classes
All three clients implement the same OperRouterClient protocol:
HTTPClient(base_url: str)- JSON-RPC 2.0 over HTTPGRPCClient(address: str)- gRPC with ProtobufFFIClient(lib_path: Optional[str] = None)- Direct Rust FFI calls
Core Methods
# Test connection
await client.ping() -> PingResponse
# Validate TOML config
await client.validate_config(config_str: str) -> ConfigResponse
# Load operator config
await client.load_config(config_str: str) -> ConfigResponse
# Get metadata
await client.get_metadata(name: str) -> Metadata
DataSource Methods
# Create datasource
await client.create_datasource(
name: str,
config: DataSourceConfig
) -> DataSourceResponse
# Query (SELECT)
await client.query_datasource(
name: str,
query: str
) -> DataSourceQueryResponse
# Execute (DDL/DML)
await client.execute_datasource(
name: str,
statement: str
) -> DataSourceResponse
# Insert row
await client.insert_datasource(
name: str,
data: Dict[str, Any]
) -> DataSourceResponse
# Check health
await client.ping_datasource(name: str) -> DataSourceResponse
# Close connection
await client.close_datasource(name: str) -> DataSourceResponse
LLM Methods
# Create LLM instance
await client.create_llm(
name: str,
config: LLMConfig
) -> LLMResponse
# Generate completion
await client.generate_llm(
name: str,
prompt: str
) -> LLMGenerateResponse
# Chat conversation
await client.chat_llm(
name: str,
messages: List[ChatMessage]
) -> LLMChatResponse
# Get embeddings
await client.embedding_llm(
name: str,
text: str
) -> LLMEmbeddingResponse
# Check health
await client.ping_llm(name: str) -> LLMResponse
# Close instance
await client.close_llm(name: str) -> LLMResponse
Configuration Types
DataSource Configuration
from py_operrouter import DataSourceConfig
config = DataSourceConfig(
driver="postgres", # postgres, mysql, mongodb, redis, kafka
host="localhost", # Database host
port=5432, # Database port
database="mydb", # Database name
username="user", # Optional username
password="pass", # Optional password
options={} # Optional driver-specific options
)
LLM Configuration
from py_operrouter import LLMConfig
config = LLMConfig(
provider="openai", # openai, claude, ollama
model="gpt-3.5-turbo", # Model name
api_key="sk-...", # API key (not needed for Ollama)
base_url=None, # Optional custom endpoint
options={} # Optional provider-specific options
)
Chat Messages
from py_operrouter import ChatMessage
messages = [
ChatMessage(role="system", content="You are helpful."),
ChatMessage(role="user", content="Hello!"),
ChatMessage(role="assistant", content="Hi there!"),
]
Transport Comparison
| Feature | HTTP | gRPC | FFI |
|---|---|---|---|
| Protocol | JSON-RPC 2.0 | Protobuf | Direct calls |
| Performance | Good | Better | Best |
| Network | Required | Required | Not needed |
| Setup | Easiest | Moderate | Complex |
| Use Case | Web services | Microservices | Embedded/CLI |
| Streaming | No | Yes (future) | No |
| Dependencies | httpx | grpcio, protobuf | None |
When to Use Each
- HTTP Client: Best for web applications, REST APIs, simple integrations
- gRPC Client: Best for microservices, high-performance RPC, future streaming support
- FFI Client: Best for CLI tools, embedded systems, maximum performance
Examples
See the examples/ directory for complete working examples:
datasource_http.py- PostgreSQL operations via HTTPdatasource_grpc.py- MySQL operations via gRPCdatasource_ffi.py- MongoDB operations via FFIllm_http.py- OpenAI integration via HTTPllm_grpc.py- Claude integration via gRPCllm_ffi.py- Ollama integration via FFI
Run any example:
# HTTP examples (requires server on localhost:8080)
python examples/datasource_http.py
export OPENAI_API_KEY='sk-...'
python examples/llm_http.py
# gRPC examples (requires server on localhost:50051)
python examples/datasource_grpc.py
export CLAUDE_API_KEY='sk-...'
python examples/llm_grpc.py
# FFI examples (requires built library, no server)
python examples/datasource_ffi.py
python examples/llm_ffi.py
Development
Running Tests
# Install dev dependencies
pip install -e ".[dev]"
# Run tests
pytest
# Run with coverage
pytest --cov=py_operrouter --cov-report=html
Code Quality
# Format code
black src/ examples/
# Type checking
mypy src/
# Linting
ruff check src/
Building
# Build wheel
python -m build
# Install locally
pip install dist/py_operrouter-*.whl
Troubleshooting
Import Errors
# Make sure SDK is installed
pip install -e .
# Verify installation
python -c "from py_operrouter import HTTPClient; print('OK')"
gRPC Proto Files Not Found
# Generate proto files
cd ../..
buf generate --path proto/operrouter.proto
# Verify proto files
ls sdks/py-operrouter/gen/proto/operrouter_pb2.py
FFI Library Not Found
# Build FFI library
cd ../../bridges/operrouter-core-ffi
cargo build --release
# Or set library path
export OPERROUTER_FFI_PATH="/path/to/liboperrouter_core_ffi.so"
# Check library exists
ls ../../bridges/operrouter-core-ffi/target/release/liboperrouter_core_ffi.*
Server Connection Errors
# Start HTTP server
cd ../../bridges/operrouter-core-http
cargo run --release # Runs on :8080
# Start gRPC server
cd ../../bridges/operrouter-core-grpc
cargo run --release # Runs on :50051
Architecture
py-operrouter/
โโโ src/py_operrouter/
โ โโโ __init__.py # Main exports
โ โโโ types.py # Type definitions (10 dataclasses)
โ โโโ client/
โ โโโ __init__.py # Client exports
โ โโโ http_client.py # HTTP JSON-RPC client (310 lines)
โ โโโ grpc_client.py # gRPC Protobuf client (420 lines)
โ โโโ ffi_client.py # FFI ctypes client (420 lines)
โโโ examples/
โ โโโ README.md # Examples documentation
โ โโโ datasource_http.py # HTTP DataSource demo
โ โโโ datasource_grpc.py # gRPC DataSource demo
โ โโโ datasource_ffi.py # FFI DataSource demo
โ โโโ llm_http.py # HTTP LLM demo
โ โโโ llm_grpc.py # gRPC LLM demo
โ โโโ llm_ffi.py # FFI LLM demo
โโโ gen/proto/ # Generated protobuf files
โโโ pyproject.toml # Modern Python packaging
โโโ README.md # This file
Contributing
Contributions are welcome! Please:
- Fork the repository
- Create a feature branch
- Write tests for new features
- Ensure code passes
black,mypy, andruff - Submit a pull request
License
See the main repository LICENSE file.
Related Projects
- js-operrouter - JavaScript/TypeScript SDK
- go-operrouter - Go SDK
- rust-operrouter - Rust SDK
- operrouter-core-http - HTTP server
- operrouter-core-grpc - gRPC server
- operrouter-core-ffi - FFI library
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file py_operrouter-0.1.0.tar.gz.
File metadata
- Download URL: py_operrouter-0.1.0.tar.gz
- Upload date:
- Size: 33.3 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9a3d182100e63fede8330598bebb4a3c2cfb99812426940873be0599d473e78d
|
|
| MD5 |
fa89fd94c3a93d736c26b97b64b5ffd9
|
|
| BLAKE2b-256 |
b002b3da8d5e258dc0eae6111c711e955888403e767f89cbad08c2688a12d42e
|
Provenance
The following attestation bundles were made for py_operrouter-0.1.0.tar.gz:
Publisher:
python-publish.yml on operrouter/py-operrouter
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
py_operrouter-0.1.0.tar.gz -
Subject digest:
9a3d182100e63fede8330598bebb4a3c2cfb99812426940873be0599d473e78d - Sigstore transparency entry: 644665532
- Sigstore integration time:
-
Permalink:
operrouter/py-operrouter@fc2eef9614e4c6a7539152cb77917b2dda31bee4 -
Branch / Tag:
refs/tags/0.1.0 - Owner: https://github.com/operrouter
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
python-publish.yml@fc2eef9614e4c6a7539152cb77917b2dda31bee4 -
Trigger Event:
release
-
Statement type:
File details
Details for the file py_operrouter-0.1.0-py3-none-any.whl.
File metadata
- Download URL: py_operrouter-0.1.0-py3-none-any.whl
- Upload date:
- Size: 14.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
90b8b86d34ad17857abfe50afba3592cd7be7d50fe572ae0ff255714d45ef067
|
|
| MD5 |
8128324a1efe3f5a70ac24778deb9509
|
|
| BLAKE2b-256 |
e1ea23c61443add1432e581537d45150bb3c4e438b0124e6dcea29a6288a7221
|
Provenance
The following attestation bundles were made for py_operrouter-0.1.0-py3-none-any.whl:
Publisher:
python-publish.yml on operrouter/py-operrouter
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
py_operrouter-0.1.0-py3-none-any.whl -
Subject digest:
90b8b86d34ad17857abfe50afba3592cd7be7d50fe572ae0ff255714d45ef067 - Sigstore transparency entry: 644665555
- Sigstore integration time:
-
Permalink:
operrouter/py-operrouter@fc2eef9614e4c6a7539152cb77917b2dda31bee4 -
Branch / Tag:
refs/tags/0.1.0 - Owner: https://github.com/operrouter
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
python-publish.yml@fc2eef9614e4c6a7539152cb77917b2dda31bee4 -
Trigger Event:
release
-
Statement type: