django-ninja-aio-crud 0.6.0__py3-none-any.whl → 0.6.1__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.
- {django_ninja_aio_crud-0.6.0.dist-info → django_ninja_aio_crud-0.6.1.dist-info}/METADATA +3 -3
- django_ninja_aio_crud-0.6.1.dist-info/RECORD +13 -0
- ninja_aio/__init__.py +1 -1
- ninja_aio/exceptions.py +16 -0
- ninja_aio/models.py +4 -1
- ninja_aio/views.py +13 -5
- django_ninja_aio_crud-0.6.0.dist-info/RECORD +0 -13
- {django_ninja_aio_crud-0.6.0.dist-info → django_ninja_aio_crud-0.6.1.dist-info}/WHEEL +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.3
|
|
2
2
|
Name: django-ninja-aio-crud
|
|
3
|
-
Version: 0.6.
|
|
3
|
+
Version: 0.6.1
|
|
4
4
|
Summary: Django Ninja AIO CRUD - Rest Framework
|
|
5
5
|
Author: Giuseppe Casillo
|
|
6
6
|
Requires-Python: >=3.10
|
|
@@ -157,7 +157,7 @@ class Foo(ModelSerializer):
|
|
|
157
157
|
optionals = [("bar", str), ("active", bool)]
|
|
158
158
|
|
|
159
159
|
class UpdateSerializer:
|
|
160
|
-
optionals = [
|
|
160
|
+
optionals = [("bar", str), ("active", bool)]
|
|
161
161
|
```
|
|
162
162
|
|
|
163
163
|
- Instead of declaring your fields maybe you want to exclude some of them. Declaring "excludes" attribute into serializers will exclude the given fields. (You can declare only one between "fields" and "excludes").
|
|
@@ -182,7 +182,7 @@ class Foo(ModelSerializer):
|
|
|
182
182
|
|
|
183
183
|
class UpdateSerializer:
|
|
184
184
|
excludes = ["id", "name"]
|
|
185
|
-
optionals = [
|
|
185
|
+
optionals = [("bar", str), ("active", bool)]
|
|
186
186
|
```
|
|
187
187
|
|
|
188
188
|
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
ninja_aio/__init__.py,sha256=VSJ4PO3jZ-Z_NF8y2IrjsTc6MSqxlJ_b7TtAvZW4f28,119
|
|
2
|
+
ninja_aio/api.py,sha256=Fe6l3YCy7MW5TY4-Lbl80CFuK2NT2Y7tHfmqPk6Mqak,1735
|
|
3
|
+
ninja_aio/auth.py,sha256=z9gniLIgT8SjRqhGN7ZI0AGHjsALwgU6eyr2m46fwFY,1389
|
|
4
|
+
ninja_aio/exceptions.py,sha256=Lg0nUJe6kWEf0qvXpQ9FqQ8sCFBFH-lP4xovvY-YfiY,1922
|
|
5
|
+
ninja_aio/models.py,sha256=lplwxtZKweoppJEi0ERPSHRtsq5UwQaGK3NtR_I-FBw,15213
|
|
6
|
+
ninja_aio/parsers.py,sha256=e_4lGCPV7zs-HTqtdJTc8yQD2KPAn9njbL8nF_Mmgkc,153
|
|
7
|
+
ninja_aio/renders.py,sha256=mHeKNJtmDhZmgFpS9B6SPn5uZFcyVXrsoMhr149LeW8,1555
|
|
8
|
+
ninja_aio/schemas.py,sha256=EgRkfhnzZqwGvdBmqlZixMtMcoD1ZxV_qzJ3fmaAy20,113
|
|
9
|
+
ninja_aio/types.py,sha256=EHznS-6KWLwSX5hLeXbAi7qHWla09_rGeQraiLpH-aY,491
|
|
10
|
+
ninja_aio/views.py,sha256=z820mKzfbvh9SZ4cALQVKMfc64kx74t8xWGWaUBzHfs,9270
|
|
11
|
+
django_ninja_aio_crud-0.6.1.dist-info/WHEEL,sha256=CpUCUxeHQbRN5UGRQHYRJorO5Af-Qy_fHMctcQ8DSGI,82
|
|
12
|
+
django_ninja_aio_crud-0.6.1.dist-info/METADATA,sha256=4nH4p3l9UUIUGilQ4C_fDM1Uv-WiF6FveqrG25JosQk,13076
|
|
13
|
+
django_ninja_aio_crud-0.6.1.dist-info/RECORD,,
|
ninja_aio/__init__.py
CHANGED
ninja_aio/exceptions.py
CHANGED
|
@@ -3,6 +3,7 @@ from functools import partial
|
|
|
3
3
|
from joserfc.errors import JoseError
|
|
4
4
|
from ninja import NinjaAPI
|
|
5
5
|
from django.http import HttpRequest, HttpResponse
|
|
6
|
+
from pydantic import ValidationError
|
|
6
7
|
|
|
7
8
|
|
|
8
9
|
class BaseException(Exception):
|
|
@@ -34,14 +35,29 @@ class AuthError(BaseException):
|
|
|
34
35
|
pass
|
|
35
36
|
|
|
36
37
|
|
|
38
|
+
class PydanticValidationError(BaseException):
|
|
39
|
+
def __init__(self, details=None):
|
|
40
|
+
super().__init__("Validation Error", 400, details)
|
|
41
|
+
|
|
42
|
+
|
|
37
43
|
def _default_error(
|
|
38
44
|
request: HttpRequest, exc: BaseException, api: type[NinjaAPI]
|
|
39
45
|
) -> HttpResponse:
|
|
40
46
|
return api.create_response(request, exc.error, status=exc.status_code)
|
|
41
47
|
|
|
42
48
|
|
|
49
|
+
def _pydantic_validation_error(
|
|
50
|
+
request: HttpRequest, exc: ValidationError, api: type[NinjaAPI]
|
|
51
|
+
) -> HttpResponse:
|
|
52
|
+
error = PydanticValidationError(exc.errors(include_input=False))
|
|
53
|
+
return api.create_response(request, error.error, status=error.status_code)
|
|
54
|
+
|
|
55
|
+
|
|
43
56
|
def set_api_exception_handlers(api: type[NinjaAPI]) -> None:
|
|
44
57
|
api.add_exception_handler(BaseException, partial(_default_error, api=api))
|
|
58
|
+
api.add_exception_handler(
|
|
59
|
+
ValidationError, partial(_pydantic_validation_error, api=api)
|
|
60
|
+
)
|
|
45
61
|
|
|
46
62
|
|
|
47
63
|
def parse_jose_error(jose_exc: JoseError) -> dict:
|
ninja_aio/models.py
CHANGED
|
@@ -269,8 +269,11 @@ class ModelSerializer(models.Model, metaclass=ModelSerializerMeta):
|
|
|
269
269
|
exclude=excludes,
|
|
270
270
|
)
|
|
271
271
|
fields = cls.get_fields(s_type)
|
|
272
|
-
|
|
272
|
+
optionals = cls.get_optional_fields(s_type)
|
|
273
|
+
customs = cls.get_custom_fields(s_type) + optionals
|
|
273
274
|
excludes = cls.get_excluded_fields(s_type)
|
|
275
|
+
if not fields and not excludes:
|
|
276
|
+
fields = [f[0] for f in optionals]
|
|
274
277
|
return (
|
|
275
278
|
create_schema(
|
|
276
279
|
model=cls,
|
ninja_aio/views.py
CHANGED
|
@@ -112,6 +112,9 @@ class APIViewSet:
|
|
|
112
112
|
def _generate_filters_schema(self):
|
|
113
113
|
return self._generate_schema(self.query_params, "FiltersSchema")
|
|
114
114
|
|
|
115
|
+
def _get_pk(self, data: Schema):
|
|
116
|
+
return data.model_dump()[self.model_util.model_pk_name]
|
|
117
|
+
|
|
115
118
|
def get_schemas(self):
|
|
116
119
|
if isinstance(self.model, ModelSerializerMeta):
|
|
117
120
|
return (
|
|
@@ -153,14 +156,17 @@ class APIViewSet:
|
|
|
153
156
|
},
|
|
154
157
|
)
|
|
155
158
|
@paginate(self.pagination_class)
|
|
156
|
-
async def list(
|
|
159
|
+
async def list(
|
|
160
|
+
request: HttpRequest, filters: Query[self.filters_schema] = None
|
|
161
|
+
):
|
|
157
162
|
qs = self.model.objects.select_related()
|
|
158
163
|
if isinstance(self.model, ModelSerializerMeta):
|
|
159
164
|
qs = await self.model.queryset_request(request)
|
|
160
165
|
rels = self.model_util.get_reverse_relations()
|
|
161
166
|
if len(rels) > 0:
|
|
162
167
|
qs = qs.prefetch_related(*rels)
|
|
163
|
-
|
|
168
|
+
if filters is not None:
|
|
169
|
+
qs = await self.query_params_handler(qs, filters.model_dump())
|
|
164
170
|
objs = [
|
|
165
171
|
await self.model_util.read_s(request, obj, self.schema_out)
|
|
166
172
|
async for obj in qs.all()
|
|
@@ -177,7 +183,7 @@ class APIViewSet:
|
|
|
177
183
|
response={200: self.schema_out, self.error_codes: GenericMessageSchema},
|
|
178
184
|
)
|
|
179
185
|
async def retrieve(request: HttpRequest, pk: Path[self.path_schema]):
|
|
180
|
-
obj = await self.model_util.get_object(request, pk)
|
|
186
|
+
obj = await self.model_util.get_object(request, self._get_pk(pk))
|
|
181
187
|
return await self.model_util.read_s(request, obj, self.schema_out)
|
|
182
188
|
|
|
183
189
|
retrieve.__name__ = f"retrieve_{self.model_util.model_name}"
|
|
@@ -192,7 +198,9 @@ class APIViewSet:
|
|
|
192
198
|
async def update(
|
|
193
199
|
request: HttpRequest, data: self.schema_update, pk: Path[self.path_schema]
|
|
194
200
|
):
|
|
195
|
-
return await self.model_util.update_s(
|
|
201
|
+
return await self.model_util.update_s(
|
|
202
|
+
request, data, self._get_pk(pk), self.schema_out
|
|
203
|
+
)
|
|
196
204
|
|
|
197
205
|
update.__name__ = f"update_{self.model_util.model_name}"
|
|
198
206
|
return update
|
|
@@ -204,7 +212,7 @@ class APIViewSet:
|
|
|
204
212
|
response={204: None, self.error_codes: GenericMessageSchema},
|
|
205
213
|
)
|
|
206
214
|
async def delete(request: HttpRequest, pk: Path[self.path_schema]):
|
|
207
|
-
return 204, await self.model_util.delete_s(request, pk)
|
|
215
|
+
return 204, await self.model_util.delete_s(request, self._get_pk(pk))
|
|
208
216
|
|
|
209
217
|
delete.__name__ = f"delete_{self.model_util.model_name}"
|
|
210
218
|
return delete
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
ninja_aio/__init__.py,sha256=-m_l3-9_2Q1-PvkjWqAfSmu2jt2ILNb490jT2yC4sbk,119
|
|
2
|
-
ninja_aio/api.py,sha256=Fe6l3YCy7MW5TY4-Lbl80CFuK2NT2Y7tHfmqPk6Mqak,1735
|
|
3
|
-
ninja_aio/auth.py,sha256=z9gniLIgT8SjRqhGN7ZI0AGHjsALwgU6eyr2m46fwFY,1389
|
|
4
|
-
ninja_aio/exceptions.py,sha256=JGUvZyYevGnFYFk2JYnNqng1e9ilG8l325wA5YC1RUA,1364
|
|
5
|
-
ninja_aio/models.py,sha256=ddV2QGzWSJzwZ4vt-AJ9rRdiQCVSEtl6Bj3mxroSiQE,15096
|
|
6
|
-
ninja_aio/parsers.py,sha256=e_4lGCPV7zs-HTqtdJTc8yQD2KPAn9njbL8nF_Mmgkc,153
|
|
7
|
-
ninja_aio/renders.py,sha256=mHeKNJtmDhZmgFpS9B6SPn5uZFcyVXrsoMhr149LeW8,1555
|
|
8
|
-
ninja_aio/schemas.py,sha256=EgRkfhnzZqwGvdBmqlZixMtMcoD1ZxV_qzJ3fmaAy20,113
|
|
9
|
-
ninja_aio/types.py,sha256=EHznS-6KWLwSX5hLeXbAi7qHWla09_rGeQraiLpH-aY,491
|
|
10
|
-
ninja_aio/views.py,sha256=b-KLPkNhfMXsTx4egfi-nKeuKqYEUOLXJFNt0fYariE,9027
|
|
11
|
-
django_ninja_aio_crud-0.6.0.dist-info/WHEEL,sha256=CpUCUxeHQbRN5UGRQHYRJorO5Af-Qy_fHMctcQ8DSGI,82
|
|
12
|
-
django_ninja_aio_crud-0.6.0.dist-info/METADATA,sha256=aRvvPaOFsyvqGwg_wCpoQJ0PiQJfo0obaBPlovRlXeA,13078
|
|
13
|
-
django_ninja_aio_crud-0.6.0.dist-info/RECORD,,
|
|
File without changes
|