proxyllm-sdk 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,24 @@
1
+ Metadata-Version: 2.4
2
+ Name: proxyllm-sdk
3
+ Version: 0.1.0
4
+ Summary: Python client for the ProxyLLM OpenAI-compatible gateway.
5
+ Author: ProxyLLM
6
+ License: MIT
7
+ Keywords: proxyllm,openai,llm
8
+ Requires-Python: >=3.9
9
+ Description-Content-Type: text/markdown
10
+
11
+ # ProxyLLM Python SDK
12
+
13
+ ```python
14
+ from proxyllm import ProxyLLMClient
15
+
16
+ client = ProxyLLMClient(api_key="pk_...")
17
+
18
+ completion = client.chat.completions.create(
19
+ model="gpt-4o-mini",
20
+ messages=[{"role": "user", "content": "Say hello."}],
21
+ )
22
+ ```
23
+
24
+ Set `PROXYLLM_BASE_URL` to override the default `https://proxyllm.ericslab.ai/v1`.
@@ -0,0 +1,14 @@
1
+ # ProxyLLM Python SDK
2
+
3
+ ```python
4
+ from proxyllm import ProxyLLMClient
5
+
6
+ client = ProxyLLMClient(api_key="pk_...")
7
+
8
+ completion = client.chat.completions.create(
9
+ model="gpt-4o-mini",
10
+ messages=[{"role": "user", "content": "Say hello."}],
11
+ )
12
+ ```
13
+
14
+ Set `PROXYLLM_BASE_URL` to override the default `https://proxyllm.ericslab.ai/v1`.
@@ -0,0 +1,3 @@
1
+ from .client import ProxyLLMClient, ProxyLLMError
2
+
3
+ __all__ = ["ProxyLLMClient", "ProxyLLMError"]
@@ -0,0 +1,104 @@
1
+ from __future__ import annotations
2
+
3
+ import json
4
+ import os
5
+ from dataclasses import dataclass
6
+ from typing import Any, Dict, Iterable, Mapping, Optional
7
+ from urllib.error import HTTPError
8
+ from urllib.request import Request, urlopen
9
+
10
+
11
+ class ProxyLLMError(Exception):
12
+ def __init__(self, message: str, status_code: int, body: Any):
13
+ super().__init__(message)
14
+ self.status_code = status_code
15
+ self.body = body
16
+
17
+
18
+ @dataclass
19
+ class _ChatCompletions:
20
+ client: "ProxyLLMClient"
21
+
22
+ def create(self, **params: Any) -> Any:
23
+ return self.client.post("/chat/completions", params)
24
+
25
+
26
+ @dataclass
27
+ class _Chat:
28
+ client: "ProxyLLMClient"
29
+
30
+ def __post_init__(self) -> None:
31
+ self.completions = _ChatCompletions(self.client)
32
+
33
+
34
+ @dataclass
35
+ class _Models:
36
+ client: "ProxyLLMClient"
37
+
38
+ def list(self) -> Any:
39
+ return self.client.get("/models")
40
+
41
+
42
+ class ProxyLLMClient:
43
+ def __init__(
44
+ self,
45
+ api_key: Optional[str] = None,
46
+ base_url: Optional[str] = None,
47
+ default_headers: Optional[Mapping[str, str]] = None,
48
+ timeout: float = 60,
49
+ ) -> None:
50
+ key = api_key or os.getenv("PROXYLLM_API_KEY")
51
+ if not key:
52
+ raise ValueError("ProxyLLM API key required. Pass api_key or set PROXYLLM_API_KEY.")
53
+ self.api_key = key
54
+ self.base_url = (base_url or os.getenv("PROXYLLM_BASE_URL") or "https://proxyllm.ericslab.ai/v1").rstrip("/")
55
+ self.default_headers = dict(default_headers or {})
56
+ self.timeout = timeout
57
+ self.chat = _Chat(self)
58
+ self.models = _Models(self)
59
+
60
+ def get(self, path: str) -> Any:
61
+ return self.request("GET", path)
62
+
63
+ def post(self, path: str, body: Mapping[str, Any]) -> Any:
64
+ return self.request("POST", path, body)
65
+
66
+ def request(self, method: str, path: str, body: Optional[Mapping[str, Any]] = None) -> Any:
67
+ payload = None if body is None else json.dumps(body).encode("utf-8")
68
+ headers = {
69
+ "Authorization": f"Bearer {self.api_key}",
70
+ "Content-Type": "application/json",
71
+ **self.default_headers,
72
+ }
73
+ req = Request(f"{self.base_url}{path}", data=payload, method=method, headers=headers)
74
+ try:
75
+ with urlopen(req, timeout=self.timeout) as res:
76
+ return _decode(res.read())
77
+ except HTTPError as exc:
78
+ raw = exc.read()
79
+ body_obj = _decode(raw)
80
+ raise ProxyLLMError(_error_message(body_obj, exc.reason), exc.code, body_obj) from exc
81
+
82
+
83
+ def _decode(raw: bytes) -> Any:
84
+ if not raw:
85
+ return {}
86
+ text = raw.decode("utf-8")
87
+ try:
88
+ return json.loads(text)
89
+ except json.JSONDecodeError:
90
+ return text
91
+
92
+
93
+ def _error_message(body: Any, fallback: str) -> str:
94
+ if isinstance(body, dict):
95
+ error = body.get("error")
96
+ if isinstance(error, dict) and error.get("message"):
97
+ return str(error["message"])
98
+ if error:
99
+ return str(error)
100
+ if body.get("message"):
101
+ return str(body["message"])
102
+ if isinstance(body, str) and body:
103
+ return body
104
+ return fallback
@@ -0,0 +1,24 @@
1
+ Metadata-Version: 2.4
2
+ Name: proxyllm-sdk
3
+ Version: 0.1.0
4
+ Summary: Python client for the ProxyLLM OpenAI-compatible gateway.
5
+ Author: ProxyLLM
6
+ License: MIT
7
+ Keywords: proxyllm,openai,llm
8
+ Requires-Python: >=3.9
9
+ Description-Content-Type: text/markdown
10
+
11
+ # ProxyLLM Python SDK
12
+
13
+ ```python
14
+ from proxyllm import ProxyLLMClient
15
+
16
+ client = ProxyLLMClient(api_key="pk_...")
17
+
18
+ completion = client.chat.completions.create(
19
+ model="gpt-4o-mini",
20
+ messages=[{"role": "user", "content": "Say hello."}],
21
+ )
22
+ ```
23
+
24
+ Set `PROXYLLM_BASE_URL` to override the default `https://proxyllm.ericslab.ai/v1`.
@@ -0,0 +1,8 @@
1
+ README.md
2
+ pyproject.toml
3
+ proxyllm/__init__.py
4
+ proxyllm/client.py
5
+ proxyllm_sdk.egg-info/PKG-INFO
6
+ proxyllm_sdk.egg-info/SOURCES.txt
7
+ proxyllm_sdk.egg-info/dependency_links.txt
8
+ proxyllm_sdk.egg-info/top_level.txt
@@ -0,0 +1 @@
1
+ proxyllm
@@ -0,0 +1,17 @@
1
+ [build-system]
2
+ requires = ["setuptools>=69", "wheel"]
3
+ build-backend = "setuptools.build_meta"
4
+
5
+ [project]
6
+ name = "proxyllm-sdk"
7
+ version = "0.1.0"
8
+ description = "Python client for the ProxyLLM OpenAI-compatible gateway."
9
+ readme = "README.md"
10
+ requires-python = ">=3.9"
11
+ license = { text = "MIT" }
12
+ authors = [{ name = "ProxyLLM" }]
13
+ keywords = ["proxyllm", "openai", "llm"]
14
+
15
+ [tool.setuptools.packages.find]
16
+ where = ["."]
17
+ include = ["proxyllm*"]
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+