davidkhala.ai 0.0.7__py3-none-any.whl → 0.0.8__py3-none-any.whl

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.
@@ -1,10 +1,9 @@
1
1
  from enum import Enum
2
2
  from http import HTTPStatus
3
- from typing import List
4
3
 
5
- from dashscope import Generation, TextEmbedding
6
4
  from dashscope.api_entities.dashscope_response import DashScopeAPIResponse
7
5
 
6
+ from dashscope import Generation, TextEmbedding
8
7
  from davidkhala.ai.model import AbstractClient
9
8
 
10
9
 
@@ -58,7 +57,7 @@ class API(AbstractClient):
58
57
  )
59
58
  return API._on_response(r)
60
59
 
61
- def encode(self, *_input: str)-> List[List[float]]:
60
+ def encode(self, *_input: str)-> list[list[float]]:
62
61
  r= TextEmbedding.call(
63
62
  self.model,list(_input),
64
63
  api_key= self.api_key,
@@ -6,11 +6,12 @@ from davidkhala.utils.http_request import Request
6
6
  from davidkhala.ai.model import AbstractClient
7
7
 
8
8
 
9
- class API(AbstractClient):
9
+ class API(AbstractClient, Request):
10
10
  def __init__(self, api_key: str, base_url: str):
11
- self.api_key = api_key
11
+ super().__init__({
12
+ "bearer": api_key
13
+ })
12
14
  self.base_url = base_url + '/v1'
13
- self._ = Request({"bearer": api_key})
14
15
 
15
16
  @property
16
17
  @abstractmethod
@@ -31,7 +32,7 @@ class API(AbstractClient):
31
32
  **kwargs,
32
33
  }
33
34
 
34
- response = self._.request(f"{self.base_url}/chat/completions", "POST", json=json)
35
+ response = self.request(f"{self.base_url}/chat/completions", "POST", json=json)
35
36
 
36
37
  return {
37
38
  "data": list(map(lambda x: x['message']['content'], response['choices'])),
@@ -43,5 +44,5 @@ class API(AbstractClient):
43
44
  }
44
45
 
45
46
  def list_models(self):
46
- response = self._.request(f"{self.base_url}/models", "GET")
47
+ response = self.request(f"{self.base_url}/models", "GET")
47
48
  return response['data']
@@ -35,13 +35,24 @@ class OpenRouter(API):
35
35
  super().__init__(api_key, 'https://openrouter.ai/api')
36
36
 
37
37
  if 'leaderboard' in kwargs and type(kwargs['leaderboard']) is dict:
38
- self._.options["headers"]["HTTP-Referer"] = kwargs['leaderboard'][
38
+ self.options["headers"]["HTTP-Referer"] = kwargs['leaderboard'][
39
39
  'url'] # Site URL for rankings on openrouter.ai.
40
- self._.options["headers"]["X-Title"] = kwargs['leaderboard'][
40
+ self.options["headers"]["X-Title"] = kwargs['leaderboard'][
41
41
  'name'] # Site title for rankings on openrouter.ai.
42
42
  self.models = models
43
43
 
44
- self._.on_response = OpenRouter.on_response
44
+ self.on_response = OpenRouter.on_response
45
+ self.retry = True
46
+
47
+ def request(self, url, method: str, params=None, data=None, json=None) -> dict:
48
+ try:
49
+ return super().request(url, method, params, data, json)
50
+ except requests.HTTPError as e:
51
+ if e.response.status_code == 429 and self.retry: # 429: You are being rate limited
52
+ time.sleep(1)
53
+ return self.request(url, method, params, data, json)
54
+ else:
55
+ raise
45
56
 
46
57
  def chat(self, *user_prompt: str, **kwargs):
47
58
  if self.models:
@@ -49,13 +60,8 @@ class OpenRouter(API):
49
60
  else:
50
61
  kwargs["model"] = self.model
51
62
 
52
- try:
53
- r = super().chat(*user_prompt, **kwargs)
54
- except requests.HTTPError as e:
55
- if e.response.status_code == 429 and kwargs.get('retry'):
56
- time.sleep(1)
57
- return self.chat(*user_prompt, **kwargs)
58
- else: raise
63
+ r = super().chat(*user_prompt, **kwargs)
64
+
59
65
  if self.models:
60
66
  assert r['model'] in self.models
61
67
  return r
@@ -34,7 +34,16 @@ class SiliconFlow(API):
34
34
 
35
35
  def __init__(self, api_key: str):
36
36
  super().__init__(api_key, 'https://api.siliconflow.cn')
37
- self._.options['timeout'] = 50
37
+ self.options['timeout'] = 50
38
+
38
39
  def chat(self, *user_prompt: str, **kwargs):
39
40
  kwargs['model'] = self.model
40
- return super().chat(*user_prompt, **kwargs)
41
+ return super().chat(*user_prompt, **kwargs)
42
+
43
+ def encode(self, *_input: str) -> list[list[float]]:
44
+ json = {
45
+ 'input': _input,
46
+ 'model': self.model
47
+ }
48
+ response = self.request(f"{self.base_url}/embeddings", "POST", json=json)
49
+ return [_['embedding'] for _ in response['data']]
@@ -0,0 +1,10 @@
1
+ import os
2
+
3
+ from davidkhala.ai.huggingface import clone
4
+ from pathlib import Path
5
+
6
+ def bge_m3_path(git_dir: os.PathLike):
7
+ model_dir = clone(git_dir, repo_id="BAAI/bge-m3",allow_patterns=["onnx/*"])
8
+ onnx_path = Path(model_dir) / "onnx" / "model.onnx"
9
+ assert onnx_path.is_file() and onnx_path.exists()
10
+ return onnx_path
@@ -0,0 +1,21 @@
1
+ import os
2
+ from typing import Optional
3
+
4
+ from huggingface_hub import snapshot_download
5
+
6
+
7
+ def clone(git_dir: os.PathLike,
8
+ *,
9
+ owner: Optional[str] = None,
10
+ repository: Optional[str] = None,
11
+ repo_id: Optional[str] = None,
12
+ **kwargs
13
+ ) -> str:
14
+ if not repo_id:
15
+ repo_id = f"{owner}/{repository}"
16
+ return snapshot_download(
17
+ repo_id=repo_id,
18
+ local_dir=git_dir,
19
+ local_dir_use_symlinks=False,
20
+ **kwargs
21
+ )
davidkhala/ai/model.py CHANGED
@@ -1,5 +1,5 @@
1
1
  from abc import ABC
2
- from typing import Optional, List
2
+ from typing import Optional
3
3
 
4
4
 
5
5
  class AbstractClient(ABC):
@@ -19,7 +19,7 @@ class AbstractClient(ABC):
19
19
  def chat(self, *user_prompt, **kwargs):
20
20
  ...
21
21
 
22
- def encode(self, *_input: str) -> List[List[float]]:
22
+ def encode(self, *_input: str) -> list[list[float]]:
23
23
  ...
24
24
  def connect(self):
25
25
  ...
@@ -1,5 +1,5 @@
1
1
  import runpy
2
- from typing import Union, Literal, List
2
+ from typing import Union, Literal
3
3
 
4
4
  from openai import OpenAI, AsyncOpenAI
5
5
 
@@ -14,7 +14,7 @@ class Client(AbstractClient):
14
14
  def connect(self):
15
15
  self.client.models.list()
16
16
 
17
- def encode(self, *_input: str) -> List[List[float]]:
17
+ def encode(self, *_input: str) -> list[list[float]]:
18
18
  response = self.client.embeddings.create(
19
19
  model=self.model,
20
20
  input=list(_input),
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: davidkhala.ai
3
- Version: 0.0.7
3
+ Version: 0.0.8
4
4
  Summary: misc AI modules
5
5
  Requires-Python: >=3.13
6
6
  Provides-Extra: ali
@@ -12,6 +12,11 @@ Requires-Dist: openai; extra == 'azure'
12
12
  Provides-Extra: google
13
13
  Requires-Dist: google-adk; extra == 'google'
14
14
  Requires-Dist: google-genai; extra == 'google'
15
+ Provides-Extra: hf
16
+ Requires-Dist: hf-xet; extra == 'hf'
17
+ Requires-Dist: huggingface-hub; extra == 'hf'
18
+ Requires-Dist: onnx; extra == 'hf'
19
+ Requires-Dist: onnxruntime; extra == 'hf'
15
20
  Provides-Extra: langchain
16
21
  Requires-Dist: langchain; extra == 'langchain'
17
22
  Requires-Dist: langchain-openai; extra == 'langchain'
@@ -0,0 +1,21 @@
1
+ davidkhala/ai/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
+ davidkhala/ai/model.py,sha256=1wcXC8X8oqerMatlcPbZmuxZ-nJWdJKmaDSDgiGlUGw,647
3
+ davidkhala/ai/opik.py,sha256=YU1XuweMUAzUkhpjxhltt-SBBDBkR3z-PCNo0DqzBRs,39
4
+ davidkhala/ai/agent/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
5
+ davidkhala/ai/agent/langgraph.py,sha256=jrc_Yvgo7eJjd3y5UJn0t1FzpnObDGYscwgsuVl2O_I,1052
6
+ davidkhala/ai/ali/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
+ davidkhala/ai/ali/dashscope.py,sha256=SZIzRhVHlLx3s5I2RNUh2-u8OoSdrbvoN5e1k8Mh8N0,1943
8
+ davidkhala/ai/api/__init__.py,sha256=q2Ro5nhW5kJx2CYR1MRVamjTT5tTexPZwhrS2hwAvFM,1319
9
+ davidkhala/ai/api/openrouter.py,sha256=khccJr5cBnudFy6Jc2O3A1TNCuHH_5W6Q2tXrkwlUYE,2308
10
+ davidkhala/ai/api/siliconflow.py,sha256=LWRZ-or6zgdDSCRfPcOT8nJRqcAO3vQAmvS-3Xeo6IU,1652
11
+ davidkhala/ai/google/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
12
+ davidkhala/ai/google/adk.py,sha256=QwxYoOzT2Hol03V4NM0PF_HAzUGb4fB18VUAYacYbAY,657
13
+ davidkhala/ai/google/gemini.py,sha256=Xf4HDOOcK4-jEBERzuLnQNFsU61P2fFx4K0z-ijvNHE,214
14
+ davidkhala/ai/huggingface/BAAI.py,sha256=LZ9kp5Gfql4UzuTn4osyekI6VV1H3RIfED2IolXFj5c,341
15
+ davidkhala/ai/huggingface/__init__.py,sha256=FJyU8eOfWQWKAvkIa5qwubF9ghsSQ8C0e6p6DKyomgs,521
16
+ davidkhala/ai/openai/__init__.py,sha256=UalrIvniAFSbCAQeCrDgBVEWCFTCPxFnoOAGVnVWkkI,1864
17
+ davidkhala/ai/openai/azure.py,sha256=jAtZNW1d8ub3odhB_f1MXxM7MImg64MXDnqLm1-Idkk,828
18
+ davidkhala/ai/openai/native.py,sha256=-XuHn0KSQnuFdJ4jTwZla1ts5iOW2L2Hosfo8o8iip8,257
19
+ davidkhala_ai-0.0.8.dist-info/METADATA,sha256=0FhXLSp1itgKjftPfCFL3FO8i-snghKJR5R4jqIjU_Y,877
20
+ davidkhala_ai-0.0.8.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
21
+ davidkhala_ai-0.0.8.dist-info/RECORD,,
@@ -1,19 +0,0 @@
1
- davidkhala/ai/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
- davidkhala/ai/model.py,sha256=5rqnbb9sGJ9xDY31bRWx6O1d7nDqQjsYCeSDCm1Bv4A,653
3
- davidkhala/ai/opik.py,sha256=YU1XuweMUAzUkhpjxhltt-SBBDBkR3z-PCNo0DqzBRs,39
4
- davidkhala/ai/agent/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
5
- davidkhala/ai/agent/langgraph.py,sha256=jrc_Yvgo7eJjd3y5UJn0t1FzpnObDGYscwgsuVl2O_I,1052
6
- davidkhala/ai/ali/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
- davidkhala/ai/ali/dashscope.py,sha256=b49unSTVXhjHCA0F1Qt6_-Zs7zjSgEetIcVK5E2nDMQ,1968
8
- davidkhala/ai/api/__init__.py,sha256=XR0QpCzILpYTuFBw_S9doxMu9JNrZCa8Zi4ojbbqENA,1322
9
- davidkhala/ai/api/openrouter.py,sha256=FiThnZpS9teZRRix7C9nw5NiOkTQ5qiZfeGLJqciUIQ,2078
10
- davidkhala/ai/api/siliconflow.py,sha256=B5Zccpq1peNY5mQJS7duBEonj-aeQVxvmU7F7AVIN_s,1356
11
- davidkhala/ai/google/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
12
- davidkhala/ai/google/adk.py,sha256=QwxYoOzT2Hol03V4NM0PF_HAzUGb4fB18VUAYacYbAY,657
13
- davidkhala/ai/google/gemini.py,sha256=Xf4HDOOcK4-jEBERzuLnQNFsU61P2fFx4K0z-ijvNHE,214
14
- davidkhala/ai/openai/__init__.py,sha256=B0LG4h4cquK2sS4DqBywV-Kf6pwOVp8hU5H8hUp-pXA,1870
15
- davidkhala/ai/openai/azure.py,sha256=jAtZNW1d8ub3odhB_f1MXxM7MImg64MXDnqLm1-Idkk,828
16
- davidkhala/ai/openai/native.py,sha256=-XuHn0KSQnuFdJ4jTwZla1ts5iOW2L2Hosfo8o8iip8,257
17
- davidkhala_ai-0.0.7.dist-info/METADATA,sha256=RFYRmpi6zwy71-kX3kF_2OtpSUqYAkFbsyDDfbLuH54,698
18
- davidkhala_ai-0.0.7.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
19
- davidkhala_ai-0.0.7.dist-info/RECORD,,