fastgenerateapi 1.1.20__tar.gz → 1.1.24__tar.gz
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.
Potentially problematic release.
This version of fastgenerateapi might be problematic. Click here for more details.
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/PKG-INFO +1 -1
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/__version__.py +1 -1
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/base_view.py +29 -2
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/create_view.py +15 -7
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/delete_filter_view.py +15 -5
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/delete_tree_view.py +13 -5
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/delete_view.py +13 -5
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/get_all_view.py +21 -16
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/get_one_view.py +9 -15
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/get_relation_view.py +8 -3
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/get_tree_view.py +8 -3
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/switch_view.py +2 -5
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/update_relation_view.py +9 -2
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/update_view.py +12 -5
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/get_all_schema_factory.py +32 -28
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/__init__.py +1 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/all_settings.py +34 -24
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/db_settings.py +1 -1
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/etcd_settings.py +7 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi.egg-info/PKG-INFO +1 -1
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/LICENSE +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/README.md +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/api_view.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/base_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/dbmodel_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/get_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/response_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/save_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/tool_mixin.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/docx_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/file_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/pdf_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/xlsx_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/zip_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/sql_get_view.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/cache/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/cache/cache_decorator.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/cache/key_builder.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/channel/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/channel/connection_manager.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/channel/consumer.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/channel/websocket_view.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/filter_controller.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/router_controller.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/rpc_controller.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/search_controller.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/ws_controller.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/data_type/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/data_type/data_type.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/data_type/mysql_data_type.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/deps/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/deps/filter_params_deps.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/deps/paginator_deps.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/deps/tree_params_deps.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/example/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/example/models.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/example/routers.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/example/schemas.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/example/views.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/all.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/param_utils.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/response_utils.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/model/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/model/base_model.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/aes_field.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/enum_field.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/pk_field.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/pwd_field.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/soft_delete_field.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/validator.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/base_model.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/base_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/json_encoders.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/common_function.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/common_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/create_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/filter_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/get_one_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/get_relation_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/get_tree_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/response_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/sql_get_all_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/update_schema_factory.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/app_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/file_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/jwt_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/otlp_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/redis_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/sms_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/system_settings.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/aes.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/auto_discover.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/exception.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/file_utils.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/pwd_utils.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/ramdom_utils.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/snowflake.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/str_util.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/utils/swagger_to_js.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi.egg-info/SOURCES.txt +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi.egg-info/dependency_links.txt +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi.egg-info/top_level.txt +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/script/__init__.py +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/setup.cfg +0 -0
- {fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/setup.py +0 -0
|
@@ -15,6 +15,7 @@ from fastgenerateapi.api_view.mixin.base_mixin import BaseMixin
|
|
|
15
15
|
from fastgenerateapi.api_view.mixin.dbmodel_mixin import DBModelMixin
|
|
16
16
|
from fastgenerateapi.api_view.mixin.response_mixin import ResponseMixin
|
|
17
17
|
from fastgenerateapi.api_view.mixin.tool_mixin import ToolMixin
|
|
18
|
+
from fastgenerateapi.schemas_factory import get_one_schema_factory, response_factory
|
|
18
19
|
from fastgenerateapi.settings.all_settings import settings
|
|
19
20
|
from fastgenerateapi.utils.exception import NOT_FOUND
|
|
20
21
|
|
|
@@ -24,7 +25,7 @@ class BaseView(BaseMixin, ResponseMixin, ToolMixin, DBModelMixin):
|
|
|
24
25
|
prefix: Optional[str] = None # 路由追加后缀
|
|
25
26
|
model_class: Optional[Type[Model]] = None # 数据库模型
|
|
26
27
|
prefetch_related_fields: Union[None, dict] = None
|
|
27
|
-
schema: Optional[Type[BaseModel]] = None # 返回序列化
|
|
28
|
+
schema: Optional[Type[BaseModel]] = None # 返回序列化[未使用]
|
|
28
29
|
dependencies: Optional[Sequence[params.Depends]] = None
|
|
29
30
|
tags: Optional[List[str]] = None # swagger标签
|
|
30
31
|
router_args: Dict[str, any] = None
|
|
@@ -161,7 +162,7 @@ class BaseView(BaseMixin, ResponseMixin, ToolMixin, DBModelMixin):
|
|
|
161
162
|
model_class: Type[Model], # 数据库模型
|
|
162
163
|
model: Union[Model, None] = None
|
|
163
164
|
):
|
|
164
|
-
check_unique_fields = cls._get_unique_fields(model_class)
|
|
165
|
+
check_unique_fields = cls._get_unique_fields(model_class)
|
|
165
166
|
check_unique_together_fields = cls._get_unique_together_fields(model_class)
|
|
166
167
|
for unique_field in check_unique_fields:
|
|
167
168
|
if hasattr(request_data, unique_field):
|
|
@@ -225,5 +226,31 @@ class BaseView(BaseMixin, ResponseMixin, ToolMixin, DBModelMixin):
|
|
|
225
226
|
result[key] = val[0]
|
|
226
227
|
return result
|
|
227
228
|
|
|
229
|
+
def gen_get_one_response_schema(self):
|
|
230
|
+
if not hasattr(self, "get_one_schema"):
|
|
231
|
+
get_one_schema_include = []
|
|
232
|
+
if hasattr(self, "is_with_prefetch") and self.is_with_prefetch and self.prefetch_related_fields:
|
|
233
|
+
for key, value in self.prefetch_related_fields.items():
|
|
234
|
+
if value and type(value) in [list, tuple, set]:
|
|
235
|
+
for val in value:
|
|
236
|
+
val_str = val
|
|
237
|
+
if type(val) in [list, tuple, set]:
|
|
238
|
+
val_str = val[0]
|
|
239
|
+
get_one_schema_include.append(key + "__" + val_str)
|
|
240
|
+
self.get_one_schema = get_one_schema_factory(model_class=self.model_class, include=get_one_schema_include)
|
|
241
|
+
|
|
242
|
+
return self.get_one_schema
|
|
243
|
+
|
|
244
|
+
def gen_get_one_response_schema_factory(self):
|
|
245
|
+
"""
|
|
246
|
+
如果get_one_response_schema不存在,则生成
|
|
247
|
+
:return:
|
|
248
|
+
"""
|
|
249
|
+
self.gen_get_one_response_schema()
|
|
250
|
+
if not hasattr(self, "get_one_response_schema"):
|
|
251
|
+
self.get_one_response_schema_factory = response_factory(self.get_one_schema, name="GetOne")
|
|
252
|
+
|
|
253
|
+
return self.get_one_response_schema_factory
|
|
254
|
+
|
|
228
255
|
|
|
229
256
|
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Optional, Type, Union, Any
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends
|
|
@@ -18,16 +19,18 @@ from fastgenerateapi.settings.all_settings import settings
|
|
|
18
19
|
|
|
19
20
|
class CreateView(BaseView, SaveMixin):
|
|
20
21
|
|
|
21
|
-
create_schema: Optional[Type[BaseModel]] = None
|
|
22
22
|
create_route: Union[bool, DEPENDENCIES] = True
|
|
23
|
+
create_schema: Optional[Type[BaseModel]] = None
|
|
24
|
+
create_response_schema: Optional[Type[BaseModel]] = None
|
|
23
25
|
"""
|
|
26
|
+
create_route: 创建路由开关,可以放依赖函数列表
|
|
24
27
|
create_schema: 创建请求模型;
|
|
25
28
|
优先级:
|
|
26
29
|
- create_schema:参数传入
|
|
27
30
|
- create_schema_factory:数据库模型自动生成
|
|
28
31
|
- 优选模型层[include, exclude, create_include, create_exclude](同时存在交集)
|
|
29
32
|
- 无include和exclude默认模型层所有字段
|
|
30
|
-
|
|
33
|
+
create_response_schema: 创建返回模型
|
|
31
34
|
"""
|
|
32
35
|
|
|
33
36
|
@atomic()
|
|
@@ -91,10 +94,15 @@ class CreateView(BaseView, SaveMixin):
|
|
|
91
94
|
if not self.create_route:
|
|
92
95
|
return
|
|
93
96
|
self.create_schema = self.create_schema or create_schema_factory(self.model_class)
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
if not
|
|
97
|
-
self.
|
|
97
|
+
|
|
98
|
+
func_type = inspect.signature(self.create).return_annotation
|
|
99
|
+
if func_type != inspect._empty and func_type is not None:
|
|
100
|
+
self.create_response_schema = func_type
|
|
101
|
+
if self.create_response_schema:
|
|
102
|
+
self.create_response_schema_factory = response_factory(self.create_response_schema, name="Create")
|
|
103
|
+
else:
|
|
104
|
+
self.create_response_schema_factory = self.gen_get_one_response_schema_factory()
|
|
105
|
+
|
|
98
106
|
doc = self.create.__doc__
|
|
99
107
|
summary = doc.strip().split("\n")[0] if doc else f"Create"
|
|
100
108
|
path = f"/{settings.app_settings.ROUTER_CREATE_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -102,7 +110,7 @@ class CreateView(BaseView, SaveMixin):
|
|
|
102
110
|
path=path,
|
|
103
111
|
endpoint=self._create_decorator(),
|
|
104
112
|
methods=["POST"],
|
|
105
|
-
response_model=self.
|
|
113
|
+
response_model=self.create_response_schema_factory, # type: ignore
|
|
106
114
|
summary=summary,
|
|
107
115
|
dependencies=self.create_route,
|
|
108
116
|
)
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/delete_filter_view.py
RENAMED
|
@@ -1,8 +1,10 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Optional, Type, Any, Union
|
|
2
3
|
|
|
3
4
|
from fastapi import Query, Depends
|
|
4
5
|
from fastapi.security import OAuth2PasswordBearer
|
|
5
6
|
from fastapi.types import DecoratedCallable
|
|
7
|
+
from pydantic import BaseModel
|
|
6
8
|
from starlette.requests import Request
|
|
7
9
|
from starlette.responses import JSONResponse
|
|
8
10
|
from tortoise.transactions import atomic
|
|
@@ -17,9 +19,12 @@ from fastgenerateapi.settings.all_settings import settings
|
|
|
17
19
|
class DeleteFilterView(BaseView):
|
|
18
20
|
|
|
19
21
|
delete_filter_route: Union[bool, DEPENDENCIES] = True
|
|
22
|
+
delete_filter_response_schema: Optional[Type[BaseModel]] = None
|
|
20
23
|
"""
|
|
21
24
|
必须继承 GetAllView 才能使用
|
|
22
25
|
与 GetAllView 同步的筛选条件
|
|
26
|
+
delete_filter_route: 删除路由开关,可以放依赖函数列表
|
|
27
|
+
delete_filter_response_schema: 删除返回模型
|
|
23
28
|
"""
|
|
24
29
|
|
|
25
30
|
@atomic()
|
|
@@ -50,10 +55,15 @@ class DeleteFilterView(BaseView):
|
|
|
50
55
|
def _handler_destroy_filter_settings(self):
|
|
51
56
|
if self.delete_filter_route:
|
|
52
57
|
return
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
if not
|
|
56
|
-
self.
|
|
58
|
+
|
|
59
|
+
func_type = inspect.signature(self.destroy_filter).return_annotation
|
|
60
|
+
if func_type != inspect._empty and func_type is not None:
|
|
61
|
+
self.delete_filter_response_schema = func_type
|
|
62
|
+
if self.delete_filter_response_schema:
|
|
63
|
+
self.delete_filter_response_schema_factory = response_factory(self.delete_filter_response_schema, name="DeleteFilter")
|
|
64
|
+
else:
|
|
65
|
+
self.delete_filter_response_schema_factory = self.gen_get_one_response_schema_factory()
|
|
66
|
+
|
|
57
67
|
doc = self.destroy_filter.__doc__
|
|
58
68
|
summary = doc.strip().split("\n")[0] if doc else "Delete Filter"
|
|
59
69
|
path = f"/{settings.app_settings.ROUTER_FILTER_DELETE_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -61,7 +71,7 @@ class DeleteFilterView(BaseView):
|
|
|
61
71
|
path=path,
|
|
62
72
|
endpoint=self._delete_filter_decorator(),
|
|
63
73
|
methods=["DELETE"],
|
|
64
|
-
response_model=Optional[self.
|
|
74
|
+
response_model=Optional[self.delete_filter_response_schema_factory],
|
|
65
75
|
summary=summary,
|
|
66
76
|
dependencies=self.delete_filter_route,
|
|
67
77
|
)
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/delete_tree_view.py
RENAMED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
import time
|
|
2
3
|
from typing import Optional, Type, Any, Union
|
|
3
4
|
|
|
@@ -20,9 +21,11 @@ class DeleteTreeView(BaseView):
|
|
|
20
21
|
|
|
21
22
|
delete_tree_route: Union[bool, DEPENDENCIES] = True
|
|
22
23
|
delete_tree_schema: Optional[Type[BaseModel]] = IdList
|
|
24
|
+
delete_tree_response_schema: Optional[Type[BaseModel]] = None
|
|
23
25
|
"""
|
|
24
26
|
delete_route: 删除路由开关,可以放依赖函数列表
|
|
25
27
|
delete_schema: 删除请求模型
|
|
28
|
+
delete_tree_response_schema: 删除返回模型
|
|
26
29
|
"""
|
|
27
30
|
|
|
28
31
|
@atomic()
|
|
@@ -77,10 +80,15 @@ class DeleteTreeView(BaseView):
|
|
|
77
80
|
def _handler_delete_tree_settings(self):
|
|
78
81
|
if self.delete_tree_route:
|
|
79
82
|
return
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
if not
|
|
83
|
-
self.
|
|
83
|
+
|
|
84
|
+
func_type = inspect.signature(self.destroy_tree).return_annotation
|
|
85
|
+
if func_type != inspect._empty and func_type is not None:
|
|
86
|
+
self.delete_tree_response_schema = func_type
|
|
87
|
+
if self.delete_tree_response_schema:
|
|
88
|
+
self.delete_tree_response_schema_factory = response_factory(self.delete_tree_response_schema, name="DeleteTree")
|
|
89
|
+
else:
|
|
90
|
+
self.delete_tree_response_schema_factory = self.gen_get_one_response_schema_factory()
|
|
91
|
+
|
|
84
92
|
doc = self.destroy_tree.__doc__
|
|
85
93
|
summary = doc.strip().split("\n")[0] if doc else "Delete Tree"
|
|
86
94
|
path = f"/{settings.app_settings.ROUTER_RECURSION_DELETE_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -88,7 +96,7 @@ class DeleteTreeView(BaseView):
|
|
|
88
96
|
path=path,
|
|
89
97
|
endpoint=self._delete_tree_decorator(),
|
|
90
98
|
methods=["DELETE"],
|
|
91
|
-
response_model=Optional[self.
|
|
99
|
+
response_model=Optional[self.delete_tree_response_schema_factory],
|
|
92
100
|
summary=summary,
|
|
93
101
|
dependencies=self.delete_tree_route,
|
|
94
102
|
)
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
import time
|
|
2
3
|
from typing import Optional, Type, Any, Union
|
|
3
4
|
|
|
@@ -20,9 +21,11 @@ class DeleteView(BaseView):
|
|
|
20
21
|
|
|
21
22
|
delete_route: Union[bool, DEPENDENCIES] = True
|
|
22
23
|
delete_schema: Optional[Type[BaseModel]] = IdList
|
|
24
|
+
delete_response_schema: Optional[Type[BaseModel]] = IdList
|
|
23
25
|
"""
|
|
24
26
|
delete_route: 删除路由开关,可以放依赖函数列表
|
|
25
27
|
delete_schema: 删除请求模型
|
|
28
|
+
delete_response_schema: 删除返回模型
|
|
26
29
|
"""
|
|
27
30
|
|
|
28
31
|
@atomic()
|
|
@@ -67,10 +70,15 @@ class DeleteView(BaseView):
|
|
|
67
70
|
def _handler_delete_settings(self):
|
|
68
71
|
if not self.delete_route:
|
|
69
72
|
return
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
if not
|
|
73
|
-
self.
|
|
73
|
+
|
|
74
|
+
func_type = inspect.signature(self.destroy).return_annotation
|
|
75
|
+
if func_type != inspect._empty and func_type is not None:
|
|
76
|
+
self.delete_response_schema = func_type
|
|
77
|
+
if self.delete_response_schema:
|
|
78
|
+
self.delete_response_schema_factory = response_factory(self.delete_response_schema, name="Delete")
|
|
79
|
+
else:
|
|
80
|
+
self.delete_response_schema_factory = self.gen_get_one_response_schema_factory()
|
|
81
|
+
|
|
74
82
|
doc = self.destroy.__doc__
|
|
75
83
|
summary = doc.strip().split("\n")[0] if doc else "Delete All"
|
|
76
84
|
path = f"/{settings.app_settings.ROUTER_DELETE_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -78,7 +86,7 @@ class DeleteView(BaseView):
|
|
|
78
86
|
path=path,
|
|
79
87
|
endpoint=self._delete_decorator(),
|
|
80
88
|
methods=["DELETE"],
|
|
81
|
-
response_model=Optional[self.
|
|
89
|
+
response_model=Optional[self.delete_response_schema_factory],
|
|
82
90
|
summary=summary,
|
|
83
91
|
dependencies=self.delete_route,
|
|
84
92
|
)
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Union, Optional, Type, cast, List, Any, Callable, Coroutine
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends, Query
|
|
@@ -22,7 +23,7 @@ from fastgenerateapi.deps import paginator_deps, filter_params_deps
|
|
|
22
23
|
from fastgenerateapi.deps.filter_params_deps import search_params_deps
|
|
23
24
|
from fastgenerateapi.schemas_factory import get_all_schema_factory, get_page_schema_factory, get_one_schema_factory, \
|
|
24
25
|
response_factory
|
|
25
|
-
from fastgenerateapi.schemas_factory.get_all_schema_factory import get_list_schema_factory
|
|
26
|
+
from fastgenerateapi.schemas_factory.get_all_schema_factory import get_list_schema_factory, hasattr_get_all_schema
|
|
26
27
|
from fastgenerateapi.settings.all_settings import settings
|
|
27
28
|
|
|
28
29
|
|
|
@@ -49,7 +50,7 @@ class GetAllView(BaseView, GetMixin):
|
|
|
49
50
|
auto_add_id_order: 是否自动在 order_by_fields 后面追加id排序
|
|
50
51
|
"""
|
|
51
52
|
|
|
52
|
-
async def get_all(self, search: Optional[str], filters: dict, *args, **kwargs)
|
|
53
|
+
async def get_all(self, search: Optional[str], filters: dict, *args, **kwargs):
|
|
53
54
|
queryset = await self.get_queryset(search=search, filters=filters, *args, **kwargs)
|
|
54
55
|
|
|
55
56
|
return await self.pagination_data(queryset=queryset, *args, **kwargs)
|
|
@@ -169,21 +170,25 @@ class GetAllView(BaseView, GetMixin):
|
|
|
169
170
|
return
|
|
170
171
|
self.search_controller = SearchController(self.get_base_filter(self.search_fields))
|
|
171
172
|
self.filter_controller = FilterController(self.get_base_filter(self.filter_fields, self.filter_schema))
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
173
|
+
|
|
174
|
+
func_type = inspect.signature(self.get_all).return_annotation
|
|
175
|
+
if func_type != inspect._empty and func_type is not None:
|
|
176
|
+
self.get_all_schema = func_type
|
|
177
|
+
if not self.get_all_schema:
|
|
178
|
+
get_all_schema_include = []
|
|
179
|
+
if self.prefetch_related_fields:
|
|
180
|
+
for key, value in self.prefetch_related_fields.items():
|
|
181
|
+
if value and type(value) in [list, tuple, set]:
|
|
182
|
+
for val in value:
|
|
183
|
+
val_str = val
|
|
184
|
+
if type(val) in [list, tuple, set]:
|
|
185
|
+
val_str = val[0]
|
|
186
|
+
get_all_schema_include.append(key + "__" + val_str)
|
|
187
|
+
self.get_all_schema = get_all_schema_factory(self.model_class, include=get_all_schema_include) \
|
|
188
|
+
if (get_all_schema_include or hasattr_get_all_schema(self.model_class)) else self.gen_get_one_response_schema()
|
|
184
189
|
self.get_page_schema = get_page_schema_factory(self.get_all_schema)
|
|
185
190
|
self.get_list_schema = get_list_schema_factory(self.get_all_schema)
|
|
186
|
-
self.
|
|
191
|
+
self.get_all_response_schema_factory = response_factory(self.get_page_schema, name="GetPage")
|
|
187
192
|
doc = self.get_all.__doc__
|
|
188
193
|
summary = doc.strip().split("\n")[0] if doc else "Get All"
|
|
189
194
|
path = f"/{settings.app_settings.ROUTER_GET_ALL_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -191,7 +196,7 @@ class GetAllView(BaseView, GetMixin):
|
|
|
191
196
|
path=path,
|
|
192
197
|
endpoint=self._get_all_decorator(),
|
|
193
198
|
methods=["GET"],
|
|
194
|
-
response_model=self.
|
|
199
|
+
response_model=self.get_all_response_schema_factory,
|
|
195
200
|
summary=summary,
|
|
196
201
|
dependencies=self.get_all_route,
|
|
197
202
|
)
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Any, Union, Optional, Type
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends
|
|
@@ -66,20 +67,13 @@ class GetOneView(BaseView, GetMixin):
|
|
|
66
67
|
def _handler_get_one_settings(self):
|
|
67
68
|
if not self.get_one_route:
|
|
68
69
|
return
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
val_str = val[0]
|
|
77
|
-
get_one_schema_include.append(key + "__" + val_str)
|
|
78
|
-
self.get_one_schema = self.schema or self.get_one_schema or get_one_schema_factory(
|
|
79
|
-
model_class=self.model_class,
|
|
80
|
-
include=get_one_schema_include,
|
|
81
|
-
)
|
|
82
|
-
self.get_one_response_schema = response_factory(self.get_one_schema, name="GetOne")
|
|
70
|
+
|
|
71
|
+
func_type = inspect.signature(self.get_one).return_annotation
|
|
72
|
+
if func_type != inspect._empty and func_type is not None:
|
|
73
|
+
self.get_one_schema = func_type
|
|
74
|
+
if not self.get_one_schema:
|
|
75
|
+
self.get_one_schema = self.gen_get_one_response_schema()
|
|
76
|
+
self.get_one_response_schema_factory = response_factory(self.get_one_schema, name="GetOne")
|
|
83
77
|
doc = self.get_one.__doc__
|
|
84
78
|
summary = doc.strip().split("\n")[0] if self.get_one.__doc__ else "Get One"
|
|
85
79
|
path = f"/{settings.app_settings.ROUTER_GET_ONE_SUFFIX_FIELD}/{'{pk}'}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else "/{pk}"
|
|
@@ -87,7 +81,7 @@ class GetOneView(BaseView, GetMixin):
|
|
|
87
81
|
path=path,
|
|
88
82
|
endpoint=self._get_one_decorator(),
|
|
89
83
|
methods=["GET"],
|
|
90
|
-
response_model=self.
|
|
84
|
+
response_model=self.get_one_response_schema_factory,
|
|
91
85
|
summary=summary,
|
|
92
86
|
dependencies=self.get_one_route,
|
|
93
87
|
error_responses=[NOT_FOUND],
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/get_relation_view.py
RENAMED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Union, Optional, Type, cast, List, Any
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends, Query
|
|
@@ -53,7 +54,7 @@ class GetRelationView(BaseView):
|
|
|
53
54
|
relation_order_by_fields: 多对多关联表排序对应字段
|
|
54
55
|
"""
|
|
55
56
|
|
|
56
|
-
async def get_relation(self, pk: str, search: str, filters: dict, relation_filters: dict, *args, **kwargs)
|
|
57
|
+
async def get_relation(self, pk: str, search: str, filters: dict, relation_filters: dict, *args, **kwargs):
|
|
57
58
|
relation_queryset = await self.get_relation_queryset(filters=relation_filters, *args, **kwargs)
|
|
58
59
|
id_list = relation_queryset.filter(eval(f"Q({self.path_id_name}='{pk}')")).values_list(self.relation_id_name, flat=True)
|
|
59
60
|
|
|
@@ -183,10 +184,14 @@ class GetRelationView(BaseView):
|
|
|
183
184
|
self.search_controller = SearchController(self.get_base_filter(self.search_fields))
|
|
184
185
|
self.filter_controller = FilterController(self.get_base_filter(self.filter_fields))
|
|
185
186
|
self.filter_relation_controller = FilterController(self.get_base_filter(self.relation_filter_fields))
|
|
187
|
+
|
|
188
|
+
func_type = inspect.signature(self.get_relation).return_annotation
|
|
189
|
+
if func_type != inspect._empty and func_type is not None:
|
|
190
|
+
self.get_relation_schema = func_type
|
|
186
191
|
self.get_relation_schema = self.get_relation_schema or get_relation_schema_factory(self.model_class)
|
|
187
192
|
self.get_relation_page_schema = get_page_schema_factory(self.get_relation_schema)
|
|
188
193
|
self.get_relation_list_schema = get_list_schema_factory(self.get_relation_schema)
|
|
189
|
-
self.
|
|
194
|
+
self.get_relation_response_schema_factory = response_factory(self.get_relation_page_schema, name="GetPage")
|
|
190
195
|
doc = self.get_relation.__doc__
|
|
191
196
|
summary = doc.strip().split("\n")[0] if doc else f"Get {self.model_class.__name__.title()}"
|
|
192
197
|
path = f"/get-{self.relation_id_name.removesuffix('_id')}-by-{self.path_id_name.removesuffix('_id')}/{'{pk}'}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -194,7 +199,7 @@ class GetRelationView(BaseView):
|
|
|
194
199
|
path=path,
|
|
195
200
|
endpoint=self._get_relation_decorator(),
|
|
196
201
|
methods=["GET"],
|
|
197
|
-
response_model=self.
|
|
202
|
+
response_model=self.get_relation_response_schema_factory,
|
|
198
203
|
summary=summary,
|
|
199
204
|
dependencies=self.get_relation_route,
|
|
200
205
|
)
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Union, Optional, Type, cast, List, Any, Callable, Coroutine
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends, Query
|
|
@@ -56,7 +57,7 @@ class GetTreeView(BaseView):
|
|
|
56
57
|
search: str,
|
|
57
58
|
filters: dict,
|
|
58
59
|
request, *args, **kwargs
|
|
59
|
-
)
|
|
60
|
+
):
|
|
60
61
|
if settings.app_settings.METHOD_TREE_CHOICE.upper() == "MAP":
|
|
61
62
|
data_list = await self.map_method(
|
|
62
63
|
node_id=node_id, search=search, filters=filters, request=request, *args, **kwargs)
|
|
@@ -177,9 +178,13 @@ class GetTreeView(BaseView):
|
|
|
177
178
|
return
|
|
178
179
|
self.search_controller = SearchController(self.get_base_filter(self.search_fields))
|
|
179
180
|
self.filter_controller = FilterController(self.get_base_filter(self.filter_fields))
|
|
181
|
+
|
|
182
|
+
func_type = inspect.signature(self.get_tree).return_annotation
|
|
183
|
+
if func_type != inspect._empty and func_type is not None:
|
|
184
|
+
self.get_tree_schema = func_type
|
|
180
185
|
self.get_tree_schema = self.get_tree_schema or get_tree_schema_factory(self.model_class)
|
|
181
186
|
self.get_tree_data_schema = get_list_schema_factory(self.get_tree_schema)
|
|
182
|
-
self.
|
|
187
|
+
self.get_tree_response_schema_factory = response_factory(self.get_tree_data_schema, name="GetTree")
|
|
183
188
|
doc = self.get_tree.__doc__
|
|
184
189
|
summary = doc.strip().split("\n")[0] if self.get_tree.__doc__ else "Get Tree"
|
|
185
190
|
path = f"/{settings.app_settings.ROUTER_GET_TREE_SUFFIX_FIELD}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else ""
|
|
@@ -187,7 +192,7 @@ class GetTreeView(BaseView):
|
|
|
187
192
|
path=path,
|
|
188
193
|
endpoint=self._get_tree_decorator(),
|
|
189
194
|
methods=["GET"],
|
|
190
|
-
response_model=self.
|
|
195
|
+
response_model=self.get_tree_response_schema_factory,
|
|
191
196
|
summary=summary,
|
|
192
197
|
dependencies=self.get_tree_route,
|
|
193
198
|
)
|
|
@@ -59,10 +59,7 @@ class SwitchView(BaseView):
|
|
|
59
59
|
def _handler_switch_route_settings(self):
|
|
60
60
|
if not self.switch_route_fields:
|
|
61
61
|
return
|
|
62
|
-
|
|
63
|
-
self.get_one_schema = get_one_schema_factory(model_class=self.model_class)
|
|
64
|
-
if not hasattr(self, "get_one_response_schema"):
|
|
65
|
-
self.get_one_response_schema = response_factory(self.get_one_schema, name="GetOne")
|
|
62
|
+
|
|
66
63
|
for switch_route_field in self.switch_route_fields:
|
|
67
64
|
if self.model_class._meta.fields_map.get(switch_route_field).field_type not in [bool, int]:
|
|
68
65
|
self.error(msg=f"{switch_route_field} is not bool or int")
|
|
@@ -72,7 +69,7 @@ class SwitchView(BaseView):
|
|
|
72
69
|
path="/%s/{pk}" % ("switch_"+switch_route_field),
|
|
73
70
|
endpoint=self._switch_decorator(switch_route_field),
|
|
74
71
|
methods=["PUT"],
|
|
75
|
-
response_model=self.
|
|
72
|
+
response_model=self.gen_get_one_response_schema_factory(),
|
|
76
73
|
summary=summary,
|
|
77
74
|
dependencies=True,
|
|
78
75
|
error_responses=[NOT_FOUND],
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/update_relation_view.py
RENAMED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Optional, Type, Union, Any
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends
|
|
@@ -23,6 +24,7 @@ class UpdateRelationView(BaseView, SaveMixin):
|
|
|
23
24
|
path_id_name: str
|
|
24
25
|
relation_id_name: str
|
|
25
26
|
update_relation_schema: Optional[Type[BaseModel]] = IdList
|
|
27
|
+
update_relation_response_schema: Optional[Type[BaseModel]] = None
|
|
26
28
|
update_relation_route: Union[bool, DEPENDENCIES] = True
|
|
27
29
|
"""
|
|
28
30
|
path_id_name: 路径id在模型中对应的字段名
|
|
@@ -72,7 +74,12 @@ class UpdateRelationView(BaseView, SaveMixin):
|
|
|
72
74
|
def _handler_update_relation_settings(self):
|
|
73
75
|
if not self.update_relation_route:
|
|
74
76
|
return
|
|
75
|
-
|
|
77
|
+
|
|
78
|
+
func_type = inspect.signature(self.create).return_annotation
|
|
79
|
+
if func_type != inspect._empty and func_type is not None:
|
|
80
|
+
self.update_relation_response_schema = func_type
|
|
81
|
+
self.update_relation_response_schema_factory = response_factory(self.update_relation_response_schema, name="UpdateRelation")
|
|
82
|
+
|
|
76
83
|
doc = self.update_relation.__doc__
|
|
77
84
|
summary = doc.strip().split("\n")[0] if doc else f"Update {self.model_class.__name__.title()}"
|
|
78
85
|
path = f"/update-{self.relation_id_name.removesuffix('_id')}-by-{self.path_id_name.removesuffix('_id')}/{'{pk}'}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else "/{pk}"
|
|
@@ -80,7 +87,7 @@ class UpdateRelationView(BaseView, SaveMixin):
|
|
|
80
87
|
path=path,
|
|
81
88
|
endpoint=self._update_relation_decorator(),
|
|
82
89
|
methods=["PUT"],
|
|
83
|
-
response_model=self.
|
|
90
|
+
response_model=self.update_relation_response_schema_factory,
|
|
84
91
|
summary=summary,
|
|
85
92
|
dependencies=self.update_relation_route,
|
|
86
93
|
error_responses=[NOT_FOUND],
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import inspect
|
|
1
2
|
from typing import Optional, Type, Union, Any
|
|
2
3
|
|
|
3
4
|
from fastapi import Depends
|
|
@@ -21,6 +22,7 @@ from fastgenerateapi.utils.exception import NOT_FOUND
|
|
|
21
22
|
class UpdateView(BaseView, SaveMixin):
|
|
22
23
|
|
|
23
24
|
update_schema: Optional[Type[BaseModel]] = None
|
|
25
|
+
update_response_schema: Optional[Type[BaseModel]] = None
|
|
24
26
|
update_route: Union[bool, DEPENDENCIES] = True
|
|
25
27
|
"""
|
|
26
28
|
update_schema: 修改请求模型
|
|
@@ -81,10 +83,15 @@ class UpdateView(BaseView, SaveMixin):
|
|
|
81
83
|
if not self.update_route:
|
|
82
84
|
return
|
|
83
85
|
self.update_schema = self.update_schema or update_schema_factory(self.model_class)
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
if not
|
|
87
|
-
self.
|
|
86
|
+
|
|
87
|
+
func_type = inspect.signature(self.update).return_annotation
|
|
88
|
+
if func_type != inspect._empty and func_type is not None:
|
|
89
|
+
self.update_response_schema = func_type
|
|
90
|
+
if self.update_response_schema:
|
|
91
|
+
self.update_response_schema_factory = response_factory(self.update_response_schema, name="Update")
|
|
92
|
+
else:
|
|
93
|
+
self.update_response_schema_factory = self.gen_get_one_response_schema_factory()
|
|
94
|
+
|
|
88
95
|
doc = self.update.__doc__
|
|
89
96
|
summary = doc.strip().split("\n")[0] if doc else f"Update"
|
|
90
97
|
path = f"/{settings.app_settings.ROUTER_UPDATE_SUFFIX_FIELD}/{'{pk}'}" if settings.app_settings.ROUTER_WHETHER_ADD_SUFFIX else "/{pk}"
|
|
@@ -92,7 +99,7 @@ class UpdateView(BaseView, SaveMixin):
|
|
|
92
99
|
path=path,
|
|
93
100
|
endpoint=self._update_decorator(),
|
|
94
101
|
methods=["PUT"],
|
|
95
|
-
response_model=self.
|
|
102
|
+
response_model=self.update_response_schema_factory,
|
|
96
103
|
summary=summary,
|
|
97
104
|
dependencies=self.update_route,
|
|
98
105
|
error_responses=[NOT_FOUND],
|
|
@@ -11,6 +11,13 @@ from fastgenerateapi.schemas_factory.common_function import get_dict_from_model_
|
|
|
11
11
|
from fastgenerateapi.settings.all_settings import settings
|
|
12
12
|
|
|
13
13
|
|
|
14
|
+
def hasattr_get_all_schema(model_class: Type[Model],):
|
|
15
|
+
if not hasattr(model_class, "PydanticMeta"):
|
|
16
|
+
return False
|
|
17
|
+
if hasattr(model_class.PydanticMeta, "get_all_include") or hasattr(model_class.PydanticMeta, "get_all_exclude"):
|
|
18
|
+
return True
|
|
19
|
+
return False
|
|
20
|
+
|
|
14
21
|
def get_all_schema_factory(
|
|
15
22
|
model_class: Type[Model],
|
|
16
23
|
include: Union[list, tuple, set] = None,
|
|
@@ -21,40 +28,37 @@ def get_all_schema_factory(
|
|
|
21
28
|
"""
|
|
22
29
|
Is used to create a GetAllSchema
|
|
23
30
|
"""
|
|
24
|
-
if not hasattr(model_class, "PydanticMeta"):
|
|
25
|
-
return None
|
|
26
|
-
if not include and not extra_include and not exclude and not hasattr(model_class.PydanticMeta, "get_all_include") and not hasattr(model_class.PydanticMeta, "get_all_exclude"):
|
|
27
|
-
return None
|
|
28
|
-
|
|
29
31
|
all_fields_info = get_dict_from_model_fields(model_class)
|
|
30
32
|
|
|
31
33
|
include_fields = set()
|
|
32
34
|
exclude_fields = set()
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
35
|
+
if hasattr(model_class, "PydanticMeta"):
|
|
36
|
+
if hasattr(model_class.PydanticMeta, "include"):
|
|
37
|
+
include_fields_dict = get_dict_from_pydanticmeta(model_class, model_class.PydanticMeta.include)
|
|
38
|
+
all_fields_info.update(include_fields_dict)
|
|
39
|
+
include_fields.update(include_fields_dict.keys())
|
|
40
|
+
else:
|
|
41
|
+
include_fields.update(all_fields_info.keys())
|
|
42
|
+
if hasattr(model_class.PydanticMeta, "exclude"):
|
|
43
|
+
exclude_fields.update(model_class.PydanticMeta.exclude)
|
|
44
|
+
|
|
45
|
+
if hasattr(model_class.PydanticMeta, "get_include"):
|
|
46
|
+
get_include_fields_dict = get_dict_from_pydanticmeta(model_class, model_class.PydanticMeta.get_include)
|
|
47
|
+
all_fields_info.update(get_include_fields_dict)
|
|
48
|
+
include_fields.update(get_include_fields_dict.keys())
|
|
49
|
+
if hasattr(model_class.PydanticMeta, "get_exclude"):
|
|
50
|
+
exclude_fields.update(model_class.PydanticMeta.get_exclude)
|
|
51
|
+
|
|
52
|
+
# get_all_include
|
|
53
|
+
if hasattr(model_class.PydanticMeta, "get_all_include"):
|
|
54
|
+
get_all_include_fields_dict = get_dict_from_pydanticmeta(model_class, model_class.PydanticMeta.get_all_include)
|
|
55
|
+
all_fields_info.update(get_all_include_fields_dict)
|
|
56
|
+
include_fields.update(get_all_include_fields_dict.keys())
|
|
57
|
+
# get_all_exclude
|
|
58
|
+
if hasattr(model_class.PydanticMeta, "get_all_exclude"):
|
|
59
|
+
exclude_fields.update(model_class.PydanticMeta.get_all_exclude)
|
|
38
60
|
else:
|
|
39
61
|
include_fields.update(all_fields_info.keys())
|
|
40
|
-
if hasattr(model_class.PydanticMeta, "exclude"):
|
|
41
|
-
exclude_fields.update(model_class.PydanticMeta.exclude)
|
|
42
|
-
|
|
43
|
-
if hasattr(model_class.PydanticMeta, "get_include"):
|
|
44
|
-
get_include_fields_dict = get_dict_from_pydanticmeta(model_class, model_class.PydanticMeta.get_include)
|
|
45
|
-
all_fields_info.update(get_include_fields_dict)
|
|
46
|
-
include_fields.update(get_include_fields_dict.keys())
|
|
47
|
-
if hasattr(model_class.PydanticMeta, "get_exclude"):
|
|
48
|
-
exclude_fields.update(model_class.PydanticMeta.get_exclude)
|
|
49
|
-
|
|
50
|
-
# get_all_include
|
|
51
|
-
if hasattr(model_class.PydanticMeta, "get_all_include"):
|
|
52
|
-
get_all_include_fields_dict = get_dict_from_pydanticmeta(model_class, model_class.PydanticMeta.get_all_include)
|
|
53
|
-
all_fields_info.update(get_all_include_fields_dict)
|
|
54
|
-
include_fields.update(get_all_include_fields_dict.keys())
|
|
55
|
-
# get_all_exclude
|
|
56
|
-
if hasattr(model_class.PydanticMeta, "get_all_exclude"):
|
|
57
|
-
exclude_fields.update(model_class.PydanticMeta.get_all_exclude)
|
|
58
62
|
|
|
59
63
|
# 参数处理
|
|
60
64
|
if include:
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import os
|
|
2
2
|
from functools import lru_cache
|
|
3
3
|
from pathlib import Path
|
|
4
|
-
from typing import Union, Optional
|
|
4
|
+
from typing import Union, Optional
|
|
5
5
|
|
|
6
6
|
import yaml
|
|
7
7
|
from fastapi.exceptions import ValidationException
|
|
@@ -66,10 +66,7 @@ class SettingsModel(BaseModel):
|
|
|
66
66
|
content += f" # {v.description}\n"
|
|
67
67
|
content += "\n"
|
|
68
68
|
if etcd_settings and etcd_settings.ETCD_SETTING_KEY:
|
|
69
|
-
|
|
70
|
-
etcd_dict = etcd_settings.model_dump(exclude_unset=True, by_alias=True, exclude={"ETCD_SETTING_KEY", })
|
|
71
|
-
etcd = etcd3.client(**{key.removeprefix("ETCD_").lower(): value for key, value in etcd_dict.items()})
|
|
72
|
-
etcd.put(etcd_settings.ETCD_SETTING_KEY, content)
|
|
69
|
+
etcd_settings.client.put(etcd_settings.ETCD_SETTING_KEY, content)
|
|
73
70
|
else:
|
|
74
71
|
with open(file=path, mode='w', encoding='utf-8') as f:
|
|
75
72
|
f.writelines(content)
|
|
@@ -78,42 +75,47 @@ class SettingsModel(BaseModel):
|
|
|
78
75
|
@lru_cache
|
|
79
76
|
def get_global_settings(
|
|
80
77
|
cls,
|
|
81
|
-
path: Union[Path, str, None] =
|
|
82
|
-
etcd_settings: Optional[EtcdSettings] = None,
|
|
78
|
+
path: Union[Path, str, None] = None,
|
|
83
79
|
):
|
|
84
80
|
"""
|
|
85
81
|
get global settings and set into cache
|
|
86
|
-
:param path:
|
|
87
|
-
|
|
82
|
+
:param path:
|
|
83
|
+
None时,自动检测本地文件,优先级 application.yaml,.env
|
|
84
|
+
推荐参数 .env / application.yaml / etcd.yaml
|
|
88
85
|
:return:
|
|
89
86
|
"""
|
|
90
|
-
|
|
87
|
+
is_yaml = False
|
|
88
|
+
if path and str(path).__contains__('.yaml'):
|
|
89
|
+
is_yaml = True
|
|
90
|
+
elif os.path.isfile("application.yaml"):
|
|
91
|
+
is_yaml = True
|
|
91
92
|
|
|
93
|
+
setting_models = cls.model_fields.copy()
|
|
92
94
|
setting_dict = {}
|
|
93
|
-
if
|
|
95
|
+
if not is_yaml:
|
|
94
96
|
for k, v in setting_models.items():
|
|
95
97
|
if isinstance(v, FieldInfo):
|
|
96
98
|
setting_dict[k] = v.annotation(_env_file=str(path))
|
|
97
|
-
|
|
98
|
-
data_dict =
|
|
99
|
+
else:
|
|
100
|
+
data_dict = {}
|
|
99
101
|
if os.path.isfile(path):
|
|
100
102
|
with open(path, 'r', encoding='utf-8') as file:
|
|
101
|
-
data_dict = yaml.safe_load(file)
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
import etcd3
|
|
107
|
-
etcd_dict = etcd_settings.model_dump(exclude_unset=True, by_alias=True, exclude={"ETCD_SETTING_KEY",})
|
|
108
|
-
etcd = etcd3.client(**{key.removeprefix("ETCD_").lower(): value for key, value in etcd_dict.items()})
|
|
109
|
-
res, metadata = etcd.get(etcd_settings.ETCD_SETTING_KEY)
|
|
110
|
-
data_dict = yaml.safe_load(res)
|
|
103
|
+
data_dict = yaml.safe_load(file) or {}
|
|
104
|
+
etcd_settings = EtcdSettings(**data_dict.get("EtcdSettings", {}))
|
|
105
|
+
if etcd_settings.ETCD_SETTING_KEY:
|
|
106
|
+
res, metadata = etcd_settings.client.get(etcd_settings.ETCD_SETTING_KEY)
|
|
107
|
+
data_dict.update(yaml.safe_load(res))
|
|
111
108
|
if not data_dict:
|
|
112
109
|
raise ValidationException(errors="配置错误")
|
|
113
110
|
for k, v in setting_models.items():
|
|
114
111
|
if isinstance(v, FieldInfo):
|
|
112
|
+
env_prefix = None
|
|
115
113
|
if hasattr(v.annotation, "Config") and v.annotation.Config.env_prefix:
|
|
116
|
-
|
|
114
|
+
env_prefix = v.annotation.Config.env_prefix
|
|
115
|
+
if not env_prefix and hasattr(v.annotation, "model_config"):
|
|
116
|
+
env_prefix = v.annotation.model_config.get("env_prefix")
|
|
117
|
+
if env_prefix:
|
|
118
|
+
annotation_dict = {k_i.removeprefix(env_prefix): v_i for k_i, v_i in data_dict.get(v.annotation.__name__, {}).items()}
|
|
117
119
|
else:
|
|
118
120
|
annotation_dict = data_dict.get(v.annotation.__name__, {})
|
|
119
121
|
setting_dict[k] = v.annotation(**annotation_dict)
|
|
@@ -125,6 +127,14 @@ class SettingsModel(BaseModel):
|
|
|
125
127
|
settings.redis_settings = setting_data.redis_settings
|
|
126
128
|
return setting_data
|
|
127
129
|
|
|
130
|
+
def watch(self):
|
|
131
|
+
"""
|
|
132
|
+
监听文件或这etcd变化,待完善
|
|
133
|
+
借用 etcd.watch(target)
|
|
134
|
+
:return:
|
|
135
|
+
"""
|
|
136
|
+
...
|
|
137
|
+
|
|
128
138
|
|
|
129
139
|
settings = SettingsModel()
|
|
130
140
|
|
|
@@ -11,7 +11,7 @@ class DBSettings(BaseSettings):
|
|
|
11
11
|
|
|
12
12
|
DB_TYPE: Optional[str] = Field(default='mysql', description="数据库类型")
|
|
13
13
|
DB_HOST: Optional[str] = Field(default='127.0.0.1', description="数据库域名")
|
|
14
|
-
DB_PORT: Optional[
|
|
14
|
+
DB_PORT: Optional[int] = Field(default='3306', description="数据库端口")
|
|
15
15
|
DB_DATABASE: Optional[str] = Field(default='admin', description="数据库名")
|
|
16
16
|
DB_USERNAME: Optional[str] = Field(default='root', description="数据库用户名")
|
|
17
17
|
DB_PASSWORD: Optional[str] = Field(default='', description="数据库密码")
|
|
@@ -27,6 +27,13 @@ class EtcdSettings(BaseSettings):
|
|
|
27
27
|
frozen=True,
|
|
28
28
|
)
|
|
29
29
|
|
|
30
|
+
@property
|
|
31
|
+
def client(self):
|
|
32
|
+
import etcd3
|
|
33
|
+
etcd_dict = self.model_dump(exclude_unset=True, by_alias=True, exclude={"ETCD_SETTING_KEY", })
|
|
34
|
+
etcd = etcd3.client(**{key.removeprefix("ETCD_").lower(): value for key, value in etcd_dict.items()})
|
|
35
|
+
|
|
36
|
+
return etcd
|
|
30
37
|
|
|
31
38
|
|
|
32
39
|
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/__init__.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/base_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/dbmodel_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/get_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/response_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/save_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/tool_mixin.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/__init__.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/docx_util.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/file_util.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/pdf_util.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/xlsx_util.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/api_view/mixin/utils/zip_util.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/channel/connection_manager.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/filter_controller.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/router_controller.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/rpc_controller.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/search_controller.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/controller/ws_controller.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/data_type/mysql_data_type.py
RENAMED
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/deps/filter_params_deps.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/param_utils.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/fastapi_utils/response_utils.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/my_fields/soft_delete_field.py
RENAMED
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/__init__.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/base_model.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/base_settings.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/pydantic_utils/json_encoders.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/__init__.py
RENAMED
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/schemas_factory/common_function.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/redis_settings.py
RENAMED
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi/settings/system_settings.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastgenerateapi-1.1.20 → fastgenerateapi-1.1.24}/fastgenerateapi.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|