11import asyncio
22import json
3+ import sys
34import warnings
45from abc import ABC , abstractmethod
56from datetime import date , datetime , time
67from enum import Enum
78from functools import cached_property , partial
89from types import MappingProxyType
9- from typing import Any , Literal , Optional , TypedDict , Union
10+ from typing import Any , Literal , Optional , Union
1011
1112from aiohttp import web
1213from aiohttp_security import check_permission , permits
13- from pydantic import Json , parse_obj_as
14+ from pydantic import Json
1415
15- from ..security import permissions_as_dict
16- from ..types import FieldState , InputState
16+ from ..security import check , permissions_as_dict
17+ from ..types import ComponentState , InputState
18+
19+ if sys .version_info >= (3 , 12 ):
20+ from typing import TypedDict
21+ else :
22+ from typing_extensions import TypedDict
1723
1824Record = dict [str , object ]
1925
@@ -93,7 +99,7 @@ class DeleteManyParams(_Params):
9399
94100class AbstractAdminResource (ABC ):
95101 name : str
96- fields : dict [str , FieldState ]
102+ fields : dict [str , ComponentState ]
97103 inputs : dict [str , InputState ]
98104 primary_key : str
99105 omit_fields : set [str ]
@@ -149,7 +155,7 @@ async def delete_many(self, params: DeleteManyParams) -> list[Union[int, str]]:
149155
150156 async def _get_list (self , request : web .Request ) -> web .Response :
151157 await check_permission (request , f"admin.{ self .name } .view" , context = (request , None ))
152- query = parse_obj_as (GetListParams , request .query )
158+ query = check (GetListParams , request .query )
153159
154160 # When sort order refers to "id", this should be translated to primary key.
155161 if query ["sort" ]["field" ] == "id" :
@@ -174,7 +180,7 @@ async def _get_list(self, request: web.Request) -> web.Response:
174180
175181 async def _get_one (self , request : web .Request ) -> web .Response :
176182 await check_permission (request , f"admin.{ self .name } .view" , context = (request , None ))
177- query = parse_obj_as (GetOneParams , request .query )
183+ query = check (GetOneParams , request .query )
178184
179185 result = await self .get_one (query )
180186 if not await permits (request , f"admin.{ self .name } .view" , context = (request , result )):
@@ -185,7 +191,7 @@ async def _get_one(self, request: web.Request) -> web.Response:
185191
186192 async def _get_many (self , request : web .Request ) -> web .Response :
187193 await check_permission (request , f"admin.{ self .name } .view" , context = (request , None ))
188- query = parse_obj_as (GetManyParams , request .query )
194+ query = check (GetManyParams , request .query )
189195
190196 results = await self .get_many (query )
191197 if not results :
@@ -198,12 +204,12 @@ async def _get_many(self, request: web.Request) -> web.Response:
198204 return json_response ({"data" : results })
199205
200206 async def _create (self , request : web .Request ) -> web .Response :
201- query = parse_obj_as (CreateParams , request .query )
207+ query = check (CreateParams , request .query )
202208 # TODO(Pydantic): Dissallow extra arguments
203209 for k in query ["data" ]:
204210 if k not in self .inputs and k != "id" :
205211 raise web .HTTPBadRequest (reason = f"Invalid field '{ k } '" )
206- query ["data" ] = parse_obj_as (self ._record_type , query ["data" ])
212+ query ["data" ] = check (self ._record_type , query ["data" ])
207213 await check_permission (request , f"admin.{ self .name } .add" , context = (request , query ["data" ]))
208214 for k , v in query ["data" ].items ():
209215 if v is not None :
@@ -217,13 +223,13 @@ async def _create(self, request: web.Request) -> web.Response:
217223
218224 async def _update (self , request : web .Request ) -> web .Response :
219225 await check_permission (request , f"admin.{ self .name } .edit" , context = (request , None ))
220- query = parse_obj_as (UpdateParams , request .query )
226+ query = check (UpdateParams , request .query )
221227 # TODO(Pydantic): Dissallow extra arguments
222228 for k in query ["data" ]:
223229 if k not in self .inputs and k != "id" :
224230 raise web .HTTPBadRequest (reason = f"Invalid field '{ k } '" )
225- query ["data" ] = parse_obj_as (self ._record_type , query ["data" ])
226- query ["previousData" ] = parse_obj_as (self ._record_type , query ["previousData" ])
231+ query ["data" ] = check (self ._record_type , query ["data" ])
232+ query ["previousData" ] = check (self ._record_type , query ["previousData" ])
227233
228234 if self .primary_key != "id" :
229235 query ["data" ].pop ("id" , None )
@@ -251,12 +257,12 @@ async def _update(self, request: web.Request) -> web.Response:
251257
252258 async def _update_many (self , request : web .Request ) -> web .Response :
253259 await check_permission (request , f"admin.{ self .name } .edit" , context = (request , None ))
254- query = parse_obj_as (UpdateManyParams , request .query )
260+ query = check (UpdateManyParams , request .query )
255261 # TODO(Pydantic): Dissallow extra arguments
256262 for k in query ["data" ]:
257263 if k not in self .inputs and k != "id" :
258264 raise web .HTTPBadRequest (reason = f"Invalid field '{ k } '" )
259- query ["data" ] = parse_obj_as (self ._record_type , query ["data" ])
265+ query ["data" ] = check (self ._record_type , query ["data" ])
260266
261267 # Check original records are allowed by permission filters.
262268 originals = await self .get_many ({"ids" : query ["ids" ]})
@@ -278,8 +284,8 @@ async def _update_many(self, request: web.Request) -> web.Response:
278284
279285 async def _delete (self , request : web .Request ) -> web .Response :
280286 await check_permission (request , f"admin.{ self .name } .delete" , context = (request , None ))
281- query = parse_obj_as (DeleteParams , request .query )
282- query ["previousData" ] = parse_obj_as (self ._record_type , query ["previousData" ])
287+ query = check (DeleteParams , request .query )
288+ query ["previousData" ] = check (self ._record_type , query ["previousData" ])
283289
284290 original = await self .get_one ({"id" : query ["id" ]})
285291 if not await permits (request , f"admin.{ self .name } .delete" , context = (request , original )):
@@ -292,7 +298,7 @@ async def _delete(self, request: web.Request) -> web.Response:
292298
293299 async def _delete_many (self , request : web .Request ) -> web .Response :
294300 await check_permission (request , f"admin.{ self .name } .delete" , context = (request , None ))
295- query = parse_obj_as (DeleteManyParams , request .query )
301+ query = check (DeleteManyParams , request .query )
296302
297303 originals = await self .get_many (query )
298304 allowed = await asyncio .gather (* (permits (request , f"admin.{ self .name } .delete" ,
0 commit comments