omserv 0.0.0.dev295__py3-none-any.whl → 0.0.0.dev296__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.
omserv/apps/routes.py CHANGED
@@ -6,6 +6,7 @@ TODO:
6
6
  import contextlib
7
7
  import dataclasses as dc
8
8
  import logging
9
+ import re
9
10
  import typing as ta
10
11
 
11
12
  from omlish import check
@@ -23,6 +24,9 @@ from .markers import append_app_marker
23
24
  from .markers import get_app_markers
24
25
 
25
26
 
27
+ PatOrStr: ta.TypeAlias = re.Pattern | str
28
+
29
+
26
30
  log = logging.getLogger(__name__)
27
31
 
28
32
 
@@ -31,22 +35,22 @@ log = logging.getLogger(__name__)
31
35
 
32
36
  class Route(ta.NamedTuple):
33
37
  method: str
34
- path: str
38
+ path: PatOrStr
35
39
 
36
40
  @classmethod
37
- def get(cls, path: str) -> 'Route':
41
+ def get(cls, path: PatOrStr) -> 'Route':
38
42
  return cls('GET', path)
39
43
 
40
44
  @classmethod
41
- def post(cls, path: str) -> 'Route':
45
+ def post(cls, path: PatOrStr) -> 'Route':
42
46
  return cls('POST', path)
43
47
 
44
48
  @classmethod
45
- def put(cls, path: str) -> 'Route':
49
+ def put(cls, path: PatOrStr) -> 'Route':
46
50
  return cls('PUT', path)
47
51
 
48
52
  @classmethod
49
- def delete(cls, path: str) -> 'Route':
53
+ def delete(cls, path: PatOrStr) -> 'Route':
50
54
  return cls('DELETE', path)
51
55
 
52
56
 
@@ -147,10 +151,40 @@ def build_route_handler_map(
147
151
  ##
148
152
 
149
153
 
150
- @dc.dataclass(frozen=True)
151
154
  class RouteHandlerApp(asgi.App_):
152
- route_handlers: ta.Mapping[Route, asgi.App]
153
- base_server_url: BaseServerUrl | None = None
155
+ def __init__(
156
+ self,
157
+ route_handlers: ta.Mapping[Route, asgi.App],
158
+ base_server_url: BaseServerUrl | None = None,
159
+ ) -> None:
160
+ super().__init__()
161
+
162
+ self._route_handlers = route_handlers
163
+ self._base_server_url = base_server_url
164
+
165
+ pat_dct: dict[str, list[tuple[Route, asgi.App]]] = {}
166
+ for r, a in route_handlers.items():
167
+ if not isinstance(r.path, re.Pattern):
168
+ continue
169
+ pat_dct.setdefault(r.method, []).append((r, a))
170
+ self._pat_route_handlers_by_method = pat_dct
171
+
172
+ def _get_route_app(self, *, method: str, path: str) -> asgi.App | None:
173
+ try:
174
+ return self._route_handlers[Route(method, path)]
175
+ except KeyError:
176
+ pass
177
+
178
+ if (pat_rts := self._pat_route_handlers_by_method.get(method)) is not None:
179
+ pat_apps = [
180
+ a
181
+ for r, a in pat_rts
182
+ if check.isinstance(r, re.Pattern).fullmatch(path)
183
+ ]
184
+ if pat_apps:
185
+ return check.single(pat_apps)
186
+
187
+ return None
154
188
 
155
189
  URL_SCHEME_PORT_PAIRS: ta.ClassVar[ta.Collection[tuple[str, int]]] = (
156
190
  ('http', 80),
@@ -167,8 +201,8 @@ class RouteHandlerApp(asgi.App_):
167
201
  return
168
202
 
169
203
  case 'http':
170
- if self.base_server_url is not None:
171
- bsu = self.base_server_url
204
+ if self._base_server_url is not None:
205
+ bsu = self._base_server_url
172
206
  else:
173
207
  sch = scope['scheme']
174
208
  h, p = scope['server']
@@ -179,11 +213,13 @@ class RouteHandlerApp(asgi.App_):
179
213
  bsu = BaseServerUrl(f'{sch}://{h}{ps}/')
180
214
  es.enter_context(lang.context_var_setting(BASE_SERVER_URL, bsu)) # noqa
181
215
 
182
- route = Route(scope['method'], scope['raw_path'].decode())
183
- handler = self.route_handlers.get(route)
216
+ app = self._get_route_app(
217
+ method=scope['method'],
218
+ path=scope['raw_path'].decode(),
219
+ )
184
220
 
185
- if handler is not None:
186
- await handler(scope, recv, send)
221
+ if app is not None:
222
+ await app(scope, recv, send)
187
223
 
188
224
  else:
189
225
  await asgi.send_response(send, 404)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: omserv
3
- Version: 0.0.0.dev295
3
+ Version: 0.0.0.dev296
4
4
  Summary: omserv
5
5
  Author: wrmsr
6
6
  License: BSD-3-Clause
@@ -12,7 +12,7 @@ Classifier: Operating System :: OS Independent
12
12
  Classifier: Operating System :: POSIX
13
13
  Requires-Python: >=3.12
14
14
  License-File: LICENSE
15
- Requires-Dist: omlish==0.0.0.dev295
15
+ Requires-Dist: omlish==0.0.0.dev296
16
16
  Provides-Extra: all
17
17
  Requires-Dist: h11~=0.14; extra == "all"
18
18
  Requires-Dist: h2~=4.2; extra == "all"
@@ -5,7 +5,7 @@ omserv/apps/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
5
5
  omserv/apps/base.py,sha256=HYsWbDot7zOnsdSL8dF_ANrNXEYgWIGzlnBdCU7n8v8,376
6
6
  omserv/apps/inject.py,sha256=GxM-TT3Ln8YrYBedJF__wY-zs4G3ow7RlxT2afr0FDs,2416
7
7
  omserv/apps/markers.py,sha256=JE_px0vsJqoDIDRFu9xtXsKjtxYAshUsFB0aRsoeIcg,965
8
- omserv/apps/routes.py,sha256=GeP1fk-tdd8LQ2no_FO2bFi48gSqjmTXpLTtcpsvSa0,5096
8
+ omserv/apps/routes.py,sha256=2YAWnfC0XOsxud2LLDwC-s9raORe2ZCMLV-Iznj5UjY,6193
9
9
  omserv/apps/sessions.py,sha256=4HFHra43S0TaM2OcWUZ06eQwAqEaXuhjK5X5jlI0_44,1423
10
10
  omserv/apps/templates.py,sha256=PBRZHIF9UbnFnq-4EC6RmPeRkeH8lCBbpJkSdseHs6A,2125
11
11
  omserv/nginx/__init__.py,sha256=2d63LCGFA2qS7gdl2nCvNPmQWXNICu19wZIihQJPHCs,48
@@ -46,9 +46,9 @@ omserv/server/streams/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3h
46
46
  omserv/server/streams/httpstream.py,sha256=0DeiAPLGbEGNa0fHTs8lUpi_CFZs4M5_QB-TiS8mobQ,8015
47
47
  omserv/server/streams/utils.py,sha256=aMOrqWIg_Hht5W4kLg3y7oR5AEkVvMrZhyjzo6U5owE,1527
48
48
  omserv/server/streams/wsstream.py,sha256=3Vyzox7dCE1tDSXjb6xBubWo41ZF9d38Hrsrlj6h1J8,15482
49
- omserv-0.0.0.dev295.dist-info/licenses/LICENSE,sha256=B_hVtavaA8zCYDW99DYdcpDLKz1n3BBRjZrcbv8uG8c,1451
50
- omserv-0.0.0.dev295.dist-info/METADATA,sha256=3YlWW1f54794ixMeaMlCEqiYaaEhF5_XtqeRvNz6DNw,1005
51
- omserv-0.0.0.dev295.dist-info/WHEEL,sha256=pxyMxgL8-pra_rKaQ4drOZAegBVuX-G_4nRHjjgWbmo,91
52
- omserv-0.0.0.dev295.dist-info/entry_points.txt,sha256=ivSrdA_ahEbI-eVMu-XZS-z4VrnQISvpecIkOqC9zFM,35
53
- omserv-0.0.0.dev295.dist-info/top_level.txt,sha256=HXehpnxeKscKNULzKNzZ27oNawBrsh1PaNAirbX-XNA,7
54
- omserv-0.0.0.dev295.dist-info/RECORD,,
49
+ omserv-0.0.0.dev296.dist-info/licenses/LICENSE,sha256=B_hVtavaA8zCYDW99DYdcpDLKz1n3BBRjZrcbv8uG8c,1451
50
+ omserv-0.0.0.dev296.dist-info/METADATA,sha256=hIZqw1NS89uvk8-k_0Zt702K7CZvrssxll4rlIOcXRM,1005
51
+ omserv-0.0.0.dev296.dist-info/WHEEL,sha256=pxyMxgL8-pra_rKaQ4drOZAegBVuX-G_4nRHjjgWbmo,91
52
+ omserv-0.0.0.dev296.dist-info/entry_points.txt,sha256=ivSrdA_ahEbI-eVMu-XZS-z4VrnQISvpecIkOqC9zFM,35
53
+ omserv-0.0.0.dev296.dist-info/top_level.txt,sha256=HXehpnxeKscKNULzKNzZ27oNawBrsh1PaNAirbX-XNA,7
54
+ omserv-0.0.0.dev296.dist-info/RECORD,,