libentry 1.24.6__py3-none-any.whl → 1.24.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.
libentry/mcp/api.py CHANGED
@@ -2,6 +2,7 @@
2
2
 
3
3
  __author__ = "xi"
4
4
  __all__ = [
5
+ "HasRequestPath",
5
6
  "APIInfo",
6
7
  "api",
7
8
  "route",
@@ -12,8 +13,9 @@ __all__ = [
12
13
  "list_api_info",
13
14
  ]
14
15
 
16
+ import re
15
17
  from functools import partial
16
- from typing import Callable, List, Literal, Optional, Tuple
18
+ from typing import Any, Callable, List, Literal, Optional, Tuple, Type, Union
17
19
 
18
20
  from pydantic import BaseModel, ConfigDict
19
21
 
@@ -26,6 +28,34 @@ TAG_TOOL = "tool"
26
28
  TAG_RESOURCE = "resource"
27
29
 
28
30
 
31
+ class HasRequestPath:
32
+ """The object has a request path.
33
+ A request path is a snake named string starts with "/".
34
+ """
35
+
36
+ __request_name__ = None
37
+
38
+ @classmethod
39
+ def get_request_path(cls) -> str:
40
+ name = cls.__request_name__
41
+ if name:
42
+ if name.startswith("/"):
43
+ return name
44
+ else:
45
+ return "/" + name
46
+ else:
47
+ name = cls.__name__
48
+ if name.endswith("Request"):
49
+ name = name[:-7]
50
+ return "/" + cls._camel_to_snake(name)
51
+
52
+ @staticmethod
53
+ def _camel_to_snake(name: str) -> str:
54
+ s1 = re.sub(r"(.)([A-Z][a-z]+)", r"\1_\2", name)
55
+ s2 = re.sub(r"([a-z0-9])([A-Z])", r"\1_\2", s1)
56
+ return s2.lower()
57
+
58
+
29
59
  class APIInfo(BaseModel):
30
60
  path: str
31
61
  methods: List[Literal["GET", "POST"]]
@@ -37,7 +67,7 @@ class APIInfo(BaseModel):
37
67
 
38
68
 
39
69
  def api(
40
- path: Optional[str] = None,
70
+ path: Optional[Union[str, Type[HasRequestPath], HasRequestPath, Any]] = None,
41
71
  methods: List[Literal["GET", "POST"]] = ("GET", "POST"),
42
72
  name: Optional[str] = None,
43
73
  description: Optional[str] = None,
@@ -50,8 +80,19 @@ def api(
50
80
  fn_name = getattr(fn, "__name__")
51
81
  fn_doc = getattr(fn, "__doc__")
52
82
 
83
+ if path:
84
+ if hasattr(path, "get_request_path"):
85
+ _path = path.get_request_path()
86
+ else:
87
+ _path = path
88
+ else:
89
+ _path = f"/{fn_name}"
90
+
91
+ if not isinstance(_path, str):
92
+ raise TypeError(f"\"path\" should be instance of str or HasRequestPath.")
93
+
53
94
  api_info = APIInfo(
54
- path=path or f"/{fn_name}",
95
+ path=_path,
55
96
  methods=methods,
56
97
  name=name or fn_name,
57
98
  description=description or fn_doc,
libentry/mcp/client.py CHANGED
@@ -8,19 +8,18 @@ from queue import Queue
8
8
  from threading import Semaphore, Thread
9
9
  from time import sleep
10
10
  from types import GeneratorType
11
- from typing import Any, Dict, Iterable, List, Optional, Tuple, Union
11
+ from typing import Any, Dict, Iterable, List, Optional, Tuple, Type, Union
12
12
  from urllib.parse import urlencode, urljoin
13
13
 
14
14
  import httpx
15
15
  from pydantic import BaseModel, TypeAdapter
16
16
 
17
17
  from libentry import json
18
+ from libentry.mcp.api import HasRequestPath
18
19
  from libentry.mcp.types import CallToolRequestParams, CallToolResult, ClientCapabilities, HTTPOptions, HTTPRequest, \
19
20
  HTTPResponse, Implementation, InitializeRequestParams, InitializeResult, JSONObject, JSONRPCError, \
20
- JSONRPCNotification, \
21
- JSONRPCRequest, \
22
- JSONRPCResponse, JSONType, ListResourcesResult, ListToolsResult, MIME, ReadResourceRequestParams, \
23
- ReadResourceResult, SSE, SubroutineError, SubroutineResponse
21
+ JSONRPCNotification, JSONRPCRequest, JSONRPCResponse, JSONType, ListResourcesResult, ListToolsResult, MIME, \
22
+ ReadResourceRequestParams, ReadResourceResult, SSE, SubroutineError, SubroutineResponse
24
23
 
25
24
 
26
25
  class ServiceError(RuntimeError):
@@ -122,16 +121,16 @@ class SubroutineMixIn(abc.ABC):
122
121
  @abc.abstractmethod
123
122
  def subroutine_request(
124
123
  self,
125
- path: str,
126
- params: Dict[str, Any],
124
+ path: Union[str, Type[HasRequestPath], HasRequestPath, Any],
125
+ params: Optional[Union[JSONObject, BaseModel]] = None,
127
126
  options: Optional[HTTPOptions] = None
128
127
  ) -> Union[SubroutineResponse, Iterable[SubroutineResponse]]:
129
128
  raise NotImplementedError()
130
129
 
131
130
  def request(
132
131
  self,
133
- path: str,
134
- params: Optional[JSONObject] = None,
132
+ path: Union[str, Type[HasRequestPath], HasRequestPath, Any],
133
+ params: Optional[Union[JSONObject, BaseModel]] = None,
135
134
  options: Optional[HTTPOptions] = None
136
135
  ) -> Union[JSONType, Iterable[JSONType]]:
137
136
  response = self.subroutine_request(path, params, options)
@@ -153,7 +152,7 @@ class SubroutineMixIn(abc.ABC):
153
152
 
154
153
  def get(
155
154
  self,
156
- path: str,
155
+ path: Union[str, Type[HasRequestPath], HasRequestPath, Any],
157
156
  options: Optional[HTTPOptions] = None
158
157
  ) -> Union[JSONType, Iterable[JSONType]]:
159
158
  if options is None:
@@ -164,8 +163,8 @@ class SubroutineMixIn(abc.ABC):
164
163
 
165
164
  def post(
166
165
  self,
167
- path: str,
168
- params: Optional[JSONObject] = None,
166
+ path: Union[str, Type[HasRequestPath], HasRequestPath, Any],
167
+ params: Optional[Union[JSONObject, BaseModel]] = None,
169
168
  options: Optional[HTTPOptions] = None
170
169
  ) -> Union[JSONType, Iterable[JSONType]]:
171
170
  if options is None:
@@ -462,13 +461,19 @@ class APIClient(SubroutineMixIn, MCPMixIn):
462
461
 
463
462
  def subroutine_request(
464
463
  self,
465
- path: str,
466
- params: Dict[str, Any],
464
+ path: Union[str, Type[HasRequestPath], HasRequestPath, Any],
465
+ params: Optional[Union[JSONObject, BaseModel]] = None,
467
466
  options: Optional[HTTPOptions] = None
468
467
  ) -> Union[SubroutineResponse, Iterable[SubroutineResponse]]:
468
+ if isinstance(path, BaseModel):
469
+ if params is None:
470
+ params = path
469
471
  if isinstance(params, BaseModel):
470
472
  params = params.model_dump(exclude_none=True)
471
473
 
474
+ if hasattr(path, "get_request_path"):
475
+ path = path.get_request_path()
476
+
472
477
  json_request = HTTPRequest(
473
478
  path=path,
474
479
  json_obj=params,
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: libentry
3
- Version: 1.24.6
3
+ Version: 1.24.8
4
4
  Summary: Entries for experimental utilities.
5
5
  Home-page: https://github.com/XoriieInpottn/libentry
6
6
  Author: xi
@@ -11,8 +11,8 @@ libentry/schema.py,sha256=40SOhCF_eytWOF47MWKCRHKHl_lCaQVetx1Af62PkiI,10439
11
11
  libentry/test_api.py,sha256=Xw7B7sH6g1iCTV5sFzyBF3JAJzeOr9xg0AyezTNsnIk,4452
12
12
  libentry/utils.py,sha256=O7P6GadtUIjq0N2IZH7PhHZDUM3NebzcqyDqytet7CM,683
13
13
  libentry/mcp/__init__.py,sha256=1oLL20yLB1GL9IbFiZD8OReDqiCpFr-yetIR6x1cNkI,23
14
- libentry/mcp/api.py,sha256=KSvz6_TNGKQQoFJPNH1XIc8CMji0I2_CqC9VCSOPRfc,2491
15
- libentry/mcp/client.py,sha256=tEJbMpXiMKQ0qDgLGyavE2A4jpoXliqbrVj_TMfOGXI,22488
14
+ libentry/mcp/api.py,sha256=GDErVCz_hh_ZeMxLS8bTPyBUhCTHw3Mm-nGFMV2W2yo,3669
15
+ libentry/mcp/client.py,sha256=3HmKAsFenPlDk1lfSdXL9GJwfCSU92uQS04zvZGeJfQ,23065
16
16
  libentry/mcp/service.py,sha256=qA6I9Mi-eudRYwVGhff1_aAImK424bhASlsWaHP8XNI,34971
17
17
  libentry/mcp/types.py,sha256=aAoVO4jjqEvDzNneuZapmRYonLLnGsbcLoypVyRNNYg,12389
18
18
  libentry/service/__init__.py,sha256=1oLL20yLB1GL9IbFiZD8OReDqiCpFr-yetIR6x1cNkI,23
@@ -22,10 +22,10 @@ libentry/service/list.py,sha256=ElHWhTgShGOhaxMUEwVbMXos0NQKjHsODboiQ-3AMwE,1397
22
22
  libentry/service/running.py,sha256=FrPJoJX6wYxcHIysoatAxhW3LajCCm0Gx6l7__6sULQ,5105
23
23
  libentry/service/start.py,sha256=mZT7b9rVULvzy9GTZwxWnciCHgv9dbGN2JbxM60OMn4,1270
24
24
  libentry/service/stop.py,sha256=wOpwZgrEJ7QirntfvibGq-XsTC6b3ELhzRW2zezh-0s,1187
25
- libentry-1.24.6.dist-info/LICENSE,sha256=xx0jnfkXJvxRnG63LTGOxlggYnIysveWIZ6H3PNdCrQ,11357
26
- libentry-1.24.6.dist-info/METADATA,sha256=uA1bcL68bf5Seq6xOAqVkF7EBPSy1OYVsN9Og7mKVig,1135
27
- libentry-1.24.6.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
28
- libentry-1.24.6.dist-info/entry_points.txt,sha256=1v_nLVDsjvVJp9SWhl4ef2zZrsLTBtFWgrYFgqvQBgc,61
29
- libentry-1.24.6.dist-info/top_level.txt,sha256=u2uF6-X5fn2Erf9PYXOg_6tntPqTpyT-yzUZrltEd6I,9
30
- libentry-1.24.6.dist-info/zip-safe,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1
31
- libentry-1.24.6.dist-info/RECORD,,
25
+ libentry-1.24.8.dist-info/LICENSE,sha256=xx0jnfkXJvxRnG63LTGOxlggYnIysveWIZ6H3PNdCrQ,11357
26
+ libentry-1.24.8.dist-info/METADATA,sha256=xTdFiobksHW7BiQG0DgyOd3d46as22zSv3q2uxz5jKM,1135
27
+ libentry-1.24.8.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
28
+ libentry-1.24.8.dist-info/entry_points.txt,sha256=1v_nLVDsjvVJp9SWhl4ef2zZrsLTBtFWgrYFgqvQBgc,61
29
+ libentry-1.24.8.dist-info/top_level.txt,sha256=u2uF6-X5fn2Erf9PYXOg_6tntPqTpyT-yzUZrltEd6I,9
30
+ libentry-1.24.8.dist-info/zip-safe,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1
31
+ libentry-1.24.8.dist-info/RECORD,,