amsdal 0.4.12__cp312-cp312-macosx_10_13_universal2.whl → 0.5.0__cp312-cp312-macosx_10_13_universal2.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.
- amsdal/__about__.py +1 -1
- amsdal/__migrations__/0000_initial.py +24 -205
- amsdal/__migrations__/0001_create_class_file.py +160 -0
- amsdal/cloud/__init__.cpython-312-darwin.so +0 -0
- amsdal/cloud/client.cpython-312-darwin.so +0 -0
- amsdal/cloud/constants.cpython-312-darwin.so +0 -0
- amsdal/cloud/enums.cpython-312-darwin.so +0 -0
- amsdal/cloud/models/__init__.cpython-312-darwin.so +0 -0
- amsdal/cloud/models/base.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/__init__.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/__init__.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/add_allowlist_ip.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/add_basic_auth.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/add_dependency.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/add_secret.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/base.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/create_deploy.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/create_env.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/create_session.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/delete_allowlist_ip.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/delete_basic_auth.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/delete_dependency.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/delete_env.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/delete_secret.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/destroy_deploy.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/expose_db.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/get_basic_auth_credentials.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/get_monitoring_info.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/list_dependencies.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/list_deploys.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/list_envs.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/list_secrets.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/manager.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/signup_action.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/actions/update_deploy.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/__init__.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/base.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/credentials.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/manager.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/signup_service.cpython-312-darwin.so +0 -0
- amsdal/cloud/services/auth/token.cpython-312-darwin.so +0 -0
- amsdal/contrib/__init__.cpython-312-darwin.so +0 -0
- amsdal/contrib/auth/migrations/0000_initial.py +55 -52
- amsdal/contrib/frontend_configs/migrations/0000_initial.py +154 -183
- amsdal/fixtures/__init__.cpython-312-darwin.so +0 -0
- amsdal/fixtures/manager.cpython-312-darwin.so +0 -0
- amsdal/fixtures/utils.cpython-312-darwin.so +0 -0
- amsdal/manager.cpython-312-darwin.so +0 -0
- amsdal/mixins/__init__.cpython-312-darwin.so +0 -0
- amsdal/mixins/class_versions_mixin.cpython-312-darwin.so +0 -0
- amsdal/models/core/class_object.py +7 -6
- amsdal/models/core/class_object.pyi +6 -5
- amsdal/models/core/class_property.py +6 -1
- amsdal/models/core/class_property.pyi +5 -1
- amsdal/models/core/storage_metadata.py +15 -0
- amsdal/models/core/storage_metadata.pyi +11 -0
- amsdal/models/types/object.py +3 -3
- amsdal/models/types/object.pyi +3 -3
- amsdal/schemas/core/class_object/model.json +20 -0
- amsdal/schemas/core/class_property/model.json +19 -0
- amsdal/schemas/core/storage_metadata/model.json +52 -0
- amsdal/schemas/manager.cpython-312-darwin.so +0 -0
- amsdal/services/__init__.cpython-312-darwin.so +0 -0
- amsdal/services/transaction_execution.cpython-312-darwin.so +0 -0
- amsdal/utils/tests/helpers.py +8 -8
- {amsdal-0.4.12.dist-info → amsdal-0.5.0.dist-info}/METADATA +4 -4
- {amsdal-0.4.12.dist-info → amsdal-0.5.0.dist-info}/RECORD +70 -75
- {amsdal-0.4.12.dist-info → amsdal-0.5.0.dist-info}/WHEEL +1 -1
- amsdal/__migrations__/0001_datetime_type.py +0 -18
- amsdal/__migrations__/0002_fixture_order.py +0 -44
- amsdal/__migrations__/0003_schema_type_in_class_meta.py +0 -44
- amsdal/models/core/class_object_meta.py +0 -26
- amsdal/models/core/class_object_meta.pyi +0 -15
- amsdal/models/core/class_property_meta.py +0 -15
- amsdal/models/core/class_property_meta.pyi +0 -10
- amsdal/schemas/core/class_object_meta/model.json +0 -59
- amsdal/schemas/core/class_property_meta/model.json +0 -23
- {amsdal-0.4.12.dist-info → amsdal-0.5.0.dist-info}/licenses/LICENSE.txt +0 -0
- {amsdal-0.4.12.dist-info → amsdal-0.5.0.dist-info}/top_level.txt +0 -0
@@ -6,79 +6,82 @@ class Migration(migrations.Migration):
|
|
6
6
|
operations: list[migrations.Operation] = [
|
7
7
|
migrations.CreateClass(
|
8
8
|
module_type=ModuleType.CONTRIB,
|
9
|
-
class_name=
|
9
|
+
class_name="LoginSession",
|
10
10
|
new_schema={
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
11
|
+
"title": "LoginSession",
|
12
|
+
"required": ["email", "password"],
|
13
|
+
"properties": {
|
14
|
+
"email": {"type": "string", "title": "Email"},
|
15
|
+
"password": {"type": "string", "title": "Password (hash)"},
|
16
|
+
"token": {"type": "string", "title": "Token"},
|
17
|
+
},
|
18
|
+
"custom_code": "from datetime import UTC\nfrom datetime import datetime\nfrom datetime import timedelta\nfrom typing import Any\n\nimport jwt\n\n\n@property\ndef display_name(self) -> str:\n \"\"\"\n Returns the display name of the user.\n\n This method returns the email of the user as their display name.\n\n Returns:\n str: The email of the user.\n \"\"\"\n return self.email\n\nasync def apre_create(self) -> None:\n import bcrypt\n\n from amsdal.contrib.auth.errors import AuthenticationError\n from amsdal.contrib.auth.models.user import User\n user = await User.objects.filter(email=self.email).latest().first().aexecute()\n if not user:\n msg = 'User not found'\n raise AuthenticationError(msg)\n if not bcrypt.checkpw(self.password.encode(), user.password):\n msg = 'Invalid password'\n raise AuthenticationError(msg)\n self.password = 'validated'\n\nasync def apre_update(self) -> None:\n from amsdal.contrib.auth.errors import AuthenticationError\n msg = 'Update not allowed'\n raise AuthenticationError(msg)\n\ndef pre_create(self) -> None:\n import bcrypt\n\n from amsdal.contrib.auth.errors import AuthenticationError\n from amsdal.contrib.auth.models.user import User\n user = User.objects.filter(email=self.email).latest().first().execute()\n if not user:\n msg = 'User not found'\n raise AuthenticationError(msg)\n if not bcrypt.checkpw(self.password.encode(), user.password):\n msg = 'Invalid password'\n raise AuthenticationError(msg)\n self.password = 'validated'\n\ndef pre_init(self, *, is_new_object: bool, kwargs: dict[str, Any]) -> None:\n \"\"\"\n Pre-initializes a user object by validating email and password, and generating a JWT token.\n\n This method checks if the object is new and validates the provided email and password.\n If the email and password are valid, it generates a JWT token and adds it to the kwargs.\n\n Args:\n is_new_object (bool): Indicates if the object is new.\n kwargs (dict[str, Any]): The keyword arguments containing user details.\n\n Raises:\n AuthenticationError: If the email or password is invalid.\n \"\"\"\n if not is_new_object or '_metadata' in kwargs:\n return\n from amsdal.contrib.auth.errors import AuthenticationError\n from amsdal.contrib.auth.settings import auth_settings\n email = kwargs.get('email', None)\n password = kwargs.get('password', None)\n if not email:\n msg = \"Email can't be empty\"\n raise AuthenticationError(msg)\n if not password:\n msg = \"Password can't be empty\"\n raise AuthenticationError(msg)\n lowercased_email = email.lower()\n if not auth_settings.AUTH_JWT_KEY:\n msg = 'JWT key is not set'\n raise AuthenticationError(msg)\n expiration_time = datetime.now(tz=UTC) + timedelta(seconds=auth_settings.AUTH_TOKEN_EXPIRATION)\n token = jwt.encode({'email': lowercased_email, 'exp': expiration_time}, key=auth_settings.AUTH_JWT_KEY, algorithm='HS256')\n kwargs['token'] = token\n\ndef pre_update(self) -> None:\n from amsdal.contrib.auth.errors import AuthenticationError\n msg = 'Update not allowed'\n raise AuthenticationError(msg)",
|
19
|
+
"storage_metadata": {
|
20
|
+
"table_name": "LoginSession",
|
21
|
+
"db_fields": {},
|
22
|
+
"primary_key": ["partition_key"],
|
23
|
+
"foreign_keys": {},
|
16
24
|
},
|
17
|
-
"primary_key": ["partition_key"],
|
18
|
-
"table_name": "Permission",
|
19
|
-
'custom_code': "@property # type: ignore[misc]\ndef display_name(self) -> str: # type: ignore[no-untyped-def]\n return f'{self.model}:{self.action}'",
|
20
25
|
},
|
21
26
|
),
|
22
27
|
migrations.CreateClass(
|
23
28
|
module_type=ModuleType.CONTRIB,
|
24
|
-
class_name=
|
29
|
+
class_name="Permission",
|
25
30
|
new_schema={
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
31
|
+
"title": "Permission",
|
32
|
+
"required": ["model", "action"],
|
33
|
+
"properties": {
|
34
|
+
"model": {"type": "string", "title": "Model"},
|
35
|
+
"action": {"type": "string", "title": "Action"},
|
36
|
+
},
|
37
|
+
"custom_code": '@property\ndef display_name(self) -> str:\n """\n Returns the display name of the user.\n\n This method returns a formatted string combining the model and action of the user.\n\n Returns:\n str: The formatted display name in the format \'model:action\'.\n """\n return f\'{self.model}:{self.action}\'',
|
38
|
+
"storage_metadata": {
|
39
|
+
"table_name": "Permission",
|
40
|
+
"db_fields": {},
|
41
|
+
"primary_key": ["partition_key"],
|
42
|
+
"foreign_keys": {},
|
32
43
|
},
|
33
|
-
"primary_key": ["partition_key"],
|
34
|
-
"table_name": "User",
|
35
|
-
'custom_code': "from typing import Any\n\n\ndef pre_init(self, *, is_new_object: bool, kwargs: dict[str, Any]) -> None: # type: ignore[no-untyped-def] # noqa: ARG001\n import bcrypt\n\n from amsdal.contrib.auth.errors import UserCreationError\n\n email = kwargs.get('email', None)\n password = kwargs.get('password', None)\n\n if email is None or email == '':\n msg = \"Email can't be empty\"\n raise UserCreationError(msg)\n\n if password is None or password == '':\n msg = \"Password can't be empty\"\n raise UserCreationError(msg)\n\n kwargs['email'] = email.lower()\n\n if is_new_object and '_metadata' not in kwargs:\n hashed_password = bcrypt.hashpw(password.encode('utf-8'), bcrypt.gensalt())\n kwargs['password'] = hashed_password\n kwargs['_object_id'] = email.lower()\n\ndef pre_create(self) -> None: # type: ignore[no-untyped-def] # noqa: ARG001\n pass\n\n@property # type: ignore[misc]\ndef display_name(self) -> str: # type: ignore[no-untyped-def]\n return self.email",
|
36
44
|
},
|
37
45
|
),
|
38
46
|
migrations.CreateClass(
|
39
47
|
module_type=ModuleType.CONTRIB,
|
40
|
-
class_name=
|
48
|
+
class_name="User",
|
41
49
|
new_schema={
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
'title': 'Permission',
|
49
|
-
'db_field': ['permission_partition_key'],
|
50
|
-
},
|
50
|
+
"title": "User",
|
51
|
+
"required": ["email", "password"],
|
52
|
+
"properties": {
|
53
|
+
"email": {"type": "string", "title": "Email"},
|
54
|
+
"password": {"type": "binary", "title": "Password (hash)"},
|
55
|
+
"permissions": {"type": "array", "items": {"type": "Permission"}, "title": "Permissions"},
|
51
56
|
},
|
52
|
-
"
|
53
|
-
"
|
54
|
-
"
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
],
|
59
|
-
"permission": [
|
60
|
-
{"permission_partition_key": "string"},
|
61
|
-
"Permission",
|
62
|
-
["partition_key"],
|
63
|
-
],
|
57
|
+
"custom_code": "from typing import Any\n\nfrom amsdal.contrib.auth.models.permission import *\n\n\n@property\ndef display_name(self) -> str:\n \"\"\"\n Returns the display name of the user.\n\n This method returns the email of the user as their display name.\n\n Returns:\n str: The email of the user.\n \"\"\"\n return self.email\n\nasync def apre_update(self) -> None:\n import bcrypt\n original_object = await self.arefetch_from_db()\n password = self.password\n if original_object.password and password is not None:\n if isinstance(password, str):\n password = password.encode('utf-8')\n try:\n if not bcrypt.checkpw(password, original_object.password):\n self.password = password\n except ValueError:\n hashed_password = bcrypt.hashpw(password, bcrypt.gensalt())\n self.password = hashed_password\n\ndef __repr__(self) -> str:\n return str(self)\n\ndef __str__(self) -> str:\n return f'User(email={self.email})'\n\ndef post_init(self, *, is_new_object: bool, kwargs: dict[str, Any]) -> None:\n \"\"\"\n Post-initializes a user object by validating email and password, and hashing the password.\n\n This method checks if the email and password are provided and valid. If the object is new,\n it hashes the password and sets the object ID to the lowercased email.\n\n Args:\n is_new_object (bool): Indicates if the object is new.\n kwargs (dict[str, Any]): The keyword arguments containing user details.\n\n Raises:\n UserCreationError: If the email or password is invalid.\n \"\"\"\n import bcrypt\n\n from amsdal.contrib.auth.errors import UserCreationError\n email = kwargs.get('email', None)\n password = kwargs.get('password', None)\n if email is None or email == '':\n msg = \"Email can't be empty\"\n raise UserCreationError(msg)\n if password is None or password == '':\n msg = \"Password can't be empty\"\n raise UserCreationError(msg)\n kwargs['email'] = email.lower()\n if is_new_object and '_metadata' not in kwargs:\n if isinstance(password, str):\n password = password.encode('utf-8')\n hashed_password = bcrypt.hashpw(password, bcrypt.gensalt())\n self.password = hashed_password\n self._object_id = email.lower()\n\ndef pre_create(self) -> None:\n \"\"\"\n Pre-creates a user object.\n\n This method is a placeholder for any pre-creation logic that needs to be executed\n before a user object is created.\n \"\"\"\n pass\n\ndef pre_update(self) -> None:\n import bcrypt\n original_object = self.refetch_from_db()\n password = self.password\n if original_object.password and password is not None:\n if isinstance(password, str):\n password = password.encode('utf-8')\n try:\n if not bcrypt.checkpw(password, original_object.password):\n self.password = password\n except ValueError:\n hashed_password = bcrypt.hashpw(password, bcrypt.gensalt())\n self.password = hashed_password",
|
58
|
+
"storage_metadata": {
|
59
|
+
"table_name": "User",
|
60
|
+
"db_fields": {},
|
61
|
+
"primary_key": ["partition_key"],
|
62
|
+
"foreign_keys": {},
|
64
63
|
},
|
65
|
-
"table_name": "UserPermission",
|
66
64
|
},
|
67
65
|
),
|
68
66
|
migrations.CreateClass(
|
69
67
|
module_type=ModuleType.CONTRIB,
|
70
|
-
class_name=
|
68
|
+
class_name="UserPermission",
|
71
69
|
new_schema={
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
70
|
+
"title": "UserPermission",
|
71
|
+
"required": ["user", "permission"],
|
72
|
+
"properties": {
|
73
|
+
"user": {"type": "User", "title": "User"},
|
74
|
+
"permission": {"type": "Permission", "title": "Permission"},
|
75
|
+
},
|
76
|
+
"storage_metadata": {
|
77
|
+
"table_name": "UserPermission",
|
78
|
+
"db_fields": {"user": ["user_partition_key"], "permission": ["permission_partition_key"]},
|
79
|
+
"primary_key": ["user", "permission"],
|
80
|
+
"foreign_keys": {
|
81
|
+
"user": [{"user_partition_key": "string"}, "User", ["partition_key"]],
|
82
|
+
"permission": [{"permission_partition_key": "string"}, "Permission", ["partition_key"]],
|
83
|
+
},
|
78
84
|
},
|
79
|
-
"primary_key": ["partition_key"],
|
80
|
-
"table_name": "LoginSession",
|
81
|
-
'custom_code': "from datetime import datetime\nfrom datetime import timedelta\nfrom datetime import timezone\nfrom typing import Any\n\nimport bcrypt\nimport jwt\nfrom amsdal_utils.models.enums import Versions\n\n\ndef pre_init(self, *, is_new_object: bool, kwargs: dict[str, Any]) -> None: # type: ignore[no-untyped-def] # noqa: ARG001\n if not is_new_object or '_metadata' in kwargs:\n return\n\n from amsdal.contrib.auth.errors import AuthenticationError\n from amsdal.contrib.auth.settings import auth_settings\n\n email = kwargs.get('email', None)\n password = kwargs.get('password', None)\n\n if not email:\n msg = \"Email can't be empty\"\n raise AuthenticationError(msg)\n\n if not password:\n msg = \"Password can't be empty\"\n raise AuthenticationError(msg)\n\n lowercased_email = email.lower()\n\n from amsdal.contrib.auth.models.user import User # type: ignore[import-not-found]\n\n user = User.objects.filter(email=lowercased_email, _address__object_version=Versions.LATEST).get_or_none().execute()\n\n if not user:\n msg = 'Invalid email / password'\n raise AuthenticationError(msg)\n\n if not bcrypt.checkpw(password.encode('utf-8') if isinstance(password, str) else password, user.password):\n msg = 'Invalid email / password'\n raise AuthenticationError(msg)\n\n kwargs['password'] = 'validated'\n expiration_time = datetime.now(tz=timezone.utc) + timedelta(seconds=1200)\n token = jwt.encode(\n {'email': lowercased_email, 'exp': expiration_time},\n key=auth_settings.AUTH_JWT_KEY, # type: ignore[arg-type]\n algorithm='HS256',\n )\n\n kwargs['token'] = token\n\n@property # type: ignore[misc]\ndef display_name(self) -> str: # type: ignore[no-untyped-def]\n return self.email",
|
82
85
|
},
|
83
86
|
),
|
84
87
|
]
|
@@ -6,251 +6,222 @@ class Migration(migrations.Migration):
|
|
6
6
|
operations: list[migrations.Operation] = [
|
7
7
|
migrations.CreateClass(
|
8
8
|
module_type=ModuleType.CONTRIB,
|
9
|
-
class_name=
|
9
|
+
class_name="FrontendConfigSkipNoneBase",
|
10
10
|
new_schema={
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
11
|
+
"title": "FrontendConfigSkipNoneBase",
|
12
|
+
"properties": {},
|
13
|
+
"meta_class": "TypeMeta",
|
14
|
+
"custom_code": "from typing import Any\n\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
15
|
+
"storage_metadata": {"table_name": "FrontendConfigSkipNoneBase", "db_fields": {}, "foreign_keys": {}},
|
15
16
|
},
|
16
17
|
),
|
17
18
|
migrations.CreateClass(
|
18
19
|
module_type=ModuleType.CONTRIB,
|
19
|
-
class_name=
|
20
|
+
class_name="FrontendConfigAsyncValidator",
|
20
21
|
new_schema={
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
'type': 'string',
|
28
|
-
'title': 'Condition',
|
29
|
-
'options': [
|
30
|
-
{'key': 'Less Than', 'value': 'lt'},
|
31
|
-
{'key': 'Less Than or Equal', 'value': 'lte'},
|
32
|
-
{'key': 'Greater Than', 'value': 'gt'},
|
33
|
-
{'key': 'Greater Than or Equal', 'value': 'gte'},
|
34
|
-
{'key': 'Equal', 'value': 'eq'},
|
35
|
-
{'key': 'Not Equal', 'value': 'neq'},
|
36
|
-
{'key': 'Exist', 'value': 'exist'},
|
37
|
-
],
|
38
|
-
},
|
39
|
-
},
|
40
|
-
'meta_class': 'TypeMeta',
|
22
|
+
"title": "FrontendConfigAsyncValidator",
|
23
|
+
"type": "FrontendConfigSkipNoneBase",
|
24
|
+
"properties": {"endpoint": {"type": "string", "title": "Endpoint"}},
|
25
|
+
"meta_class": "TypeMeta",
|
26
|
+
"custom_code": "from typing import Any\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
27
|
+
"storage_metadata": {"table_name": "FrontendConfigAsyncValidator", "db_fields": {}, "foreign_keys": {}},
|
41
28
|
},
|
42
29
|
),
|
43
30
|
migrations.CreateClass(
|
44
31
|
module_type=ModuleType.CONTRIB,
|
45
|
-
class_name=
|
32
|
+
class_name="FrontendConfigControlAction",
|
46
33
|
new_schema={
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
34
|
+
"title": "FrontendConfigControlAction",
|
35
|
+
"type": "FrontendConfigSkipNoneBase",
|
36
|
+
"required": ["action", "text", "type"],
|
37
|
+
"properties": {
|
38
|
+
"action": {"type": "string", "title": "Action"},
|
39
|
+
"text": {"type": "string", "title": "Text"},
|
40
|
+
"type": {"type": "string", "title": "Type"},
|
41
|
+
"dataLayerEvent": {"type": "string", "title": "Data Layer Event"},
|
42
|
+
"activator": {"type": "string", "title": "Activator"},
|
43
|
+
"icon": {"type": "string", "title": "Icon"},
|
44
|
+
},
|
45
|
+
"meta_class": "TypeMeta",
|
46
|
+
"custom_code": "from typing import Any\n\nfrom amsdal_models.builder.validators.options_validators import validate_options\nfrom pydantic import field_validator\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\n@field_validator('action', mode='after')\n@classmethod\ndef validate_action(cls, v: str) -> str:\n \"\"\"\n Validates the action string to ensure it is one of the allowed values.\n\n This method checks if the action string starts with 'navigate::' or is one of the predefined\n actions. If the action string is invalid, it raises a ValueError.\n\n Args:\n cls: The class this method is attached to.\n v (str): The action string to validate.\n\n Returns:\n str: The validated action string.\n\n Raises:\n ValueError: If the action string is not valid.\n \"\"\"\n if not v.startswith('navigate::') and v not in ['goPrev', 'goNext', 'goNextWithSubmit', 'submit', 'submitWithDataLayer']:\n msg = 'Action must be one of: goPrev, goNext, goNextWithSubmit, submit, submitWithDataLayer, navigate::{string}'\n raise ValueError(msg)\n return v\n\n@field_validator('type')\n@classmethod\ndef validate_value_in_options_type(cls: type, value: Any) -> Any:\n return validate_options(value, options=['action-button', 'arrow-next', 'arrow-prev', 'text-next', 'text-prev'])\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
47
|
+
"storage_metadata": {"table_name": "FrontendConfigControlAction", "db_fields": {}, "foreign_keys": {}},
|
51
48
|
},
|
52
49
|
),
|
53
50
|
migrations.CreateClass(
|
54
51
|
module_type=ModuleType.CONTRIB,
|
55
|
-
class_name=
|
52
|
+
class_name="FrontendConfigGroupValidator",
|
56
53
|
new_schema={
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
'suffix': {'type': 'string', 'title': 'Suffix'},
|
64
|
-
'thousands_separator': {'type': 'string', 'title': 'Thousands Separator'},
|
54
|
+
"title": "FrontendConfigGroupValidator",
|
55
|
+
"type": "FrontendConfigSkipNoneBase",
|
56
|
+
"properties": {
|
57
|
+
"mainControl": {"type": "string", "title": "Main Control"},
|
58
|
+
"dependentControls": {"type": "array", "items": {"type": "string"}, "title": "Dependent Controls"},
|
59
|
+
"condition": {"type": "string", "title": "Condition"},
|
65
60
|
},
|
66
|
-
|
61
|
+
"meta_class": "TypeMeta",
|
62
|
+
"custom_code": "from typing import Any\n\nfrom amsdal_models.builder.validators.options_validators import validate_options\nfrom pydantic.functional_validators import field_validator\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\n@field_validator('condition')\n@classmethod\ndef validate_value_in_options_condition(cls: type, value: Any) -> Any:\n return validate_options(value, options=['eq', 'exist', 'gt', 'gte', 'lt', 'lte', 'neq'])\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
63
|
+
"storage_metadata": {"table_name": "FrontendConfigGroupValidator", "db_fields": {}, "foreign_keys": {}},
|
67
64
|
},
|
68
65
|
),
|
69
66
|
migrations.CreateClass(
|
70
67
|
module_type=ModuleType.CONTRIB,
|
71
|
-
class_name=
|
68
|
+
class_name="FrontendConfigOption",
|
72
69
|
new_schema={
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
'range': {'type': 'boolean', 'title': 'Range'},
|
70
|
+
"title": "FrontendConfigOption",
|
71
|
+
"type": "FrontendConfigSkipNoneBase",
|
72
|
+
"properties": {
|
73
|
+
"label": {"type": "string", "title": "Label"},
|
74
|
+
"value": {"type": "string", "title": "Value"},
|
79
75
|
},
|
80
|
-
|
76
|
+
"meta_class": "TypeMeta",
|
77
|
+
"custom_code": "from typing import Any\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
78
|
+
"storage_metadata": {"table_name": "FrontendConfigOption", "db_fields": {}, "foreign_keys": {}},
|
81
79
|
},
|
82
80
|
),
|
83
81
|
migrations.CreateClass(
|
84
82
|
module_type=ModuleType.CONTRIB,
|
85
|
-
class_name=
|
83
|
+
class_name="FrontendConfigSliderOption",
|
86
84
|
new_schema={
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
'options': [
|
94
|
-
{'key': 'Minimum', 'value': 'min'},
|
95
|
-
{'key': 'Maximum', 'value': 'max'},
|
96
|
-
{'key': 'Minimum Length', 'value': 'minLength'},
|
97
|
-
{'key': 'Maximum Length', 'value': 'maxLength'},
|
98
|
-
{'key': 'Required', 'value': 'required'},
|
99
|
-
{'key': 'Pattern', 'value': 'pattern'},
|
100
|
-
],
|
101
|
-
},
|
102
|
-
'value': {'type': 'string', 'title': 'Value'},
|
85
|
+
"title": "FrontendConfigSliderOption",
|
86
|
+
"type": "FrontendConfigSkipNoneBase",
|
87
|
+
"properties": {
|
88
|
+
"min": {"type": "number", "title": "Minimum"},
|
89
|
+
"max": {"type": "number", "title": "Maximum"},
|
90
|
+
"range": {"type": "boolean", "title": "Range"},
|
103
91
|
},
|
104
|
-
|
92
|
+
"meta_class": "TypeMeta",
|
93
|
+
"custom_code": "from typing import Any\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
94
|
+
"storage_metadata": {"table_name": "FrontendConfigSliderOption", "db_fields": {}, "foreign_keys": {}},
|
105
95
|
},
|
106
96
|
),
|
107
97
|
migrations.CreateClass(
|
108
98
|
module_type=ModuleType.CONTRIB,
|
109
|
-
class_name=
|
99
|
+
class_name="FrontendConfigTextMask",
|
110
100
|
new_schema={
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
101
|
+
"title": "FrontendConfigTextMask",
|
102
|
+
"type": "FrontendConfigSkipNoneBase",
|
103
|
+
"required": ["mask_string"],
|
104
|
+
"properties": {
|
105
|
+
"mask_string": {"type": "string", "title": "Mask String"},
|
106
|
+
"prefix": {"type": "string", "title": "Prefix"},
|
107
|
+
"suffix": {"type": "string", "title": "Suffix"},
|
108
|
+
"thousands_separator": {"type": "string", "title": "Thousands Separator"},
|
109
|
+
},
|
110
|
+
"meta_class": "TypeMeta",
|
111
|
+
"custom_code": "from typing import Any\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
112
|
+
"storage_metadata": {"table_name": "FrontendConfigTextMask", "db_fields": {}, "foreign_keys": {}},
|
115
113
|
},
|
116
114
|
),
|
117
115
|
migrations.CreateClass(
|
118
116
|
module_type=ModuleType.CONTRIB,
|
119
|
-
class_name=
|
117
|
+
class_name="FrontendActivatorConfig",
|
120
118
|
new_schema={
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
'type': 'string',
|
129
|
-
'title': 'Type',
|
130
|
-
'options': [
|
131
|
-
{'key': 'Arrow Next', 'value': 'arrow-next'},
|
132
|
-
{'key': 'Arrow Prev', 'value': 'arrow-prev'},
|
133
|
-
{'key': 'Action Button', 'value': 'action-button'},
|
134
|
-
{'key': 'Text Next', 'value': 'text-next'},
|
135
|
-
{'key': 'Text Prev', 'value': 'text-prev'},
|
136
|
-
],
|
137
|
-
},
|
138
|
-
'dataLayerEvent': {'type': 'string', 'title': 'Data Layer Event'},
|
139
|
-
'activator': {'type': 'string', 'title': 'Activator'},
|
140
|
-
'icon': {'type': 'string', 'title': 'Icon'},
|
119
|
+
"title": "FrontendActivatorConfig",
|
120
|
+
"type": "FrontendConfigGroupValidator",
|
121
|
+
"properties": {
|
122
|
+
"mainControl": {"type": "string", "title": "Main Control"},
|
123
|
+
"dependentControls": {"type": "array", "items": {"type": "string"}, "title": "Dependent Controls"},
|
124
|
+
"condition": {"type": "string", "title": "Condition"},
|
125
|
+
"value": {"type": "anything", "title": "Value"},
|
141
126
|
},
|
142
|
-
|
143
|
-
|
127
|
+
"meta_class": "TypeMeta",
|
128
|
+
"custom_code": "from typing import Any\n\nfrom amsdal_models.builder.validators.options_validators import validate_options\nfrom pydantic.functional_validators import field_validator\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_group_validator import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\n@field_validator('condition')\n@classmethod\ndef validate_value_in_options_condition(cls: type, value: Any) -> Any:\n return validate_options(value, options=['eq', 'exist', 'gt', 'gte', 'lt', 'lte', 'neq'])\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
129
|
+
"storage_metadata": {"table_name": "FrontendActivatorConfig", "db_fields": {}, "foreign_keys": {}},
|
144
130
|
},
|
145
131
|
),
|
146
132
|
migrations.CreateClass(
|
147
133
|
module_type=ModuleType.CONTRIB,
|
148
|
-
class_name=
|
134
|
+
class_name="FrontendConfigValidator",
|
149
135
|
new_schema={
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
136
|
+
"title": "FrontendConfigValidator",
|
137
|
+
"type": "FrontendConfigGroupValidator",
|
138
|
+
"properties": {
|
139
|
+
"mainControl": {"type": "string", "title": "Main Control"},
|
140
|
+
"dependentControls": {"type": "array", "items": {"type": "string"}, "title": "Dependent Controls"},
|
141
|
+
"condition": {"type": "string", "title": "Condition"},
|
142
|
+
"function": {"type": "string", "title": "Function"},
|
143
|
+
"value": {"type": "string", "title": "Value"},
|
155
144
|
},
|
156
|
-
|
145
|
+
"meta_class": "TypeMeta",
|
146
|
+
"custom_code": "from typing import Any\n\nfrom amsdal_models.builder.validators.options_validators import validate_options\nfrom pydantic.functional_validators import field_validator\n\nfrom amsdal.contrib.frontend_configs.models.frontend_config_group_validator import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\n\n\n@field_validator('condition')\n@classmethod\ndef validate_value_in_options_condition(cls: type, value: Any) -> Any:\n return validate_options(value, options=['eq', 'exist', 'gt', 'gte', 'lt', 'lte', 'neq'])\n\n@field_validator('function')\n@classmethod\ndef validate_value_in_options_function(cls: type, value: Any) -> Any:\n return validate_options(value, options=['max', 'maxLength', 'min', 'minLength', 'pattern', 'required'])\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
147
|
+
"storage_metadata": {"table_name": "FrontendConfigValidator", "db_fields": {}, "foreign_keys": {}},
|
157
148
|
},
|
158
149
|
),
|
159
150
|
migrations.CreateClass(
|
160
151
|
module_type=ModuleType.CONTRIB,
|
161
|
-
class_name=
|
152
|
+
class_name="FrontendControlConfig",
|
162
153
|
new_schema={
|
163
|
-
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
{'key': 'Email', 'value': 'email'},
|
182
|
-
{'key': 'Phone', 'value': 'phone'},
|
183
|
-
{'key': 'textarea', 'value': 'textarea'},
|
184
|
-
{'key': 'Multiselect', 'value': 'multiselect'},
|
185
|
-
{'key': 'number_initial', 'value': 'number_initial'},
|
186
|
-
{'key': 'number_plus', 'value': 'number_plus'},
|
187
|
-
{'key': 'number_minus', 'value': 'number_minus'},
|
188
|
-
{'key': 'number_equals', 'value': 'number_equals'},
|
189
|
-
{'key': 'toggle', 'value': 'toggle'},
|
190
|
-
{'key': 'radio', 'value': 'radio'},
|
191
|
-
{'key': 'checkbox', 'value': 'checkbox'},
|
192
|
-
{'key': 'number-slider', 'value': 'number-slider'},
|
193
|
-
{'key': 'number-operations', 'value': 'number-operations'},
|
194
|
-
{'key': 'date', 'value': 'date'},
|
195
|
-
{'key': 'dateTriplet', 'value': 'dateTriplet'},
|
196
|
-
{'key': 'array', 'value': 'array'},
|
197
|
-
{'key': 'object', 'value': 'object'},
|
198
|
-
{'key': 'file', 'value': 'file'},
|
199
|
-
{'key': 'dropzone', 'value': 'dropzone'},
|
200
|
-
{'key': 'object_latest', 'value': 'object_latest'},
|
201
|
-
{'key': 'Dictionary', 'value': 'dict'},
|
202
|
-
{'key': 'Time', 'value': 'time'},
|
203
|
-
{'key': 'Datetime', 'value': 'datetime'},
|
204
|
-
{'key': 'Bytes', 'value': 'Bytes'},
|
205
|
-
],
|
154
|
+
"title": "FrontendControlConfig",
|
155
|
+
"type": "FrontendConfigSkipNoneBase",
|
156
|
+
"required": ["type", "name"],
|
157
|
+
"properties": {
|
158
|
+
"type": {"type": "string", "title": "Type"},
|
159
|
+
"name": {"type": "string", "title": "Name"},
|
160
|
+
"label": {"type": "string", "title": "Label"},
|
161
|
+
"required": {"type": "boolean", "title": "Required"},
|
162
|
+
"hideLabel": {"type": "boolean", "title": "Hide Label"},
|
163
|
+
"actions": {
|
164
|
+
"type": "array",
|
165
|
+
"items": {"type": "FrontendConfigControlAction", "title": "FrontendConfigControlAction"},
|
166
|
+
"title": "Actions",
|
167
|
+
},
|
168
|
+
"validators": {
|
169
|
+
"type": "array",
|
170
|
+
"items": {"type": "FrontendConfigValidator", "title": "FrontendConfigValidator"},
|
171
|
+
"title": "Validators",
|
206
172
|
},
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
211
|
-
'actions': {'type': 'array', 'items': {'type': 'FrontendConfigControlAction'}, 'title': 'Actions'},
|
212
|
-
'validators': {
|
213
|
-
'type': 'array',
|
214
|
-
'items': {'type': 'FrontendConfigValidator'},
|
215
|
-
'title': 'Validators',
|
173
|
+
"asyncValidators": {
|
174
|
+
"type": "array",
|
175
|
+
"items": {"type": "FrontendConfigAsyncValidator", "title": "FrontendConfigAsyncValidator"},
|
176
|
+
"title": "Async Validators",
|
216
177
|
},
|
217
|
-
|
218
|
-
|
219
|
-
|
220
|
-
|
178
|
+
"activators": {
|
179
|
+
"type": "array",
|
180
|
+
"items": {"type": "FrontendActivatorConfig", "title": "FrontendActivatorConfig"},
|
181
|
+
"title": "Activators",
|
221
182
|
},
|
222
|
-
|
223
|
-
|
224
|
-
|
225
|
-
|
183
|
+
"additionalText": {"type": "string", "title": "Additional Text"},
|
184
|
+
"value": {"type": "anything", "title": "Value"},
|
185
|
+
"placeholder": {"type": "string", "title": "Placeholder"},
|
186
|
+
"options": {
|
187
|
+
"type": "array",
|
188
|
+
"items": {"type": "FrontendConfigOption", "title": "FrontendConfigOption"},
|
189
|
+
"title": "Options",
|
226
190
|
},
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
231
|
-
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
191
|
+
"mask": {"type": "FrontendConfigTextMask", "title": "Mask"},
|
192
|
+
"controls": {
|
193
|
+
"type": "array",
|
194
|
+
"items": {"type": "FrontendControlConfig", "title": "FrontendControlConfig"},
|
195
|
+
"title": "Controls",
|
196
|
+
},
|
197
|
+
"showSearch": {"type": "boolean", "title": "Show Search"},
|
198
|
+
"sliderOptions": {"type": "FrontendConfigSliderOption", "title": "Slider Option"},
|
199
|
+
"customLabel": {"type": "array", "items": {"type": "string"}, "title": "Custom Label"},
|
200
|
+
"control": {"type": "FrontendControlConfig", "title": "Control"},
|
201
|
+
"entityType": {"type": "string", "title": "Entity Type"},
|
238
202
|
},
|
239
|
-
|
203
|
+
"meta_class": "TypeMeta",
|
204
|
+
"custom_code": "from typing import Any\n\nfrom amsdal_models.builder.validators.options_validators import validate_options\nfrom pydantic.functional_validators import field_validator\n\nfrom amsdal.contrib.frontend_configs.models.frontend_activator_config import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_async_validator import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_control_action import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_option import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_skip_none_base import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_slider_option import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_text_mask import *\nfrom amsdal.contrib.frontend_configs.models.frontend_config_validator import *\n\n\n@field_validator('type')\n@classmethod\ndef validate_value_in_options_type(cls: type, value: Any) -> Any:\n return validate_options(value, options=['Bytes', 'array', 'checkbox', 'date', 'dateTriplet', 'datetime', 'dict', 'dropzone', 'email', 'file', 'group', 'group_switch', 'group_toggle', 'info-group', 'infoscreen', 'multiselect', 'number', 'number-operations', 'number-slider', 'number_equals', 'number_initial', 'number_minus', 'number_plus', 'object', 'object_group', 'object_latest', 'password', 'phone', 'radio', 'select', 'text', 'textarea', 'time', 'toggle'])\n\ndef model_dump(self, **kwargs: Any) -> dict[str, Any]:\n kwargs['exclude_none'] = True\n return super().model_dump(**kwargs)\n\ndef model_dump_json(self, **kwargs: Any) -> str:\n kwargs['exclude_none'] = True\n return super().model_dump_json(**kwargs)",
|
205
|
+
"storage_metadata": {"table_name": "FrontendControlConfig", "db_fields": {}, "foreign_keys": {}},
|
240
206
|
},
|
241
207
|
),
|
242
208
|
migrations.CreateClass(
|
243
209
|
module_type=ModuleType.CONTRIB,
|
244
|
-
class_name=
|
210
|
+
class_name="FrontendModelConfig",
|
245
211
|
new_schema={
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
|
212
|
+
"title": "FrontendModelConfig",
|
213
|
+
"required": ["class_name"],
|
214
|
+
"properties": {
|
215
|
+
"class_name": {"type": "string", "title": "Class Name"},
|
216
|
+
"control": {"type": "FrontendControlConfig", "title": "Control"},
|
217
|
+
},
|
218
|
+
"custom_code": "from amsdal.contrib.frontend_configs.models.frontend_control_config import *",
|
219
|
+
"storage_metadata": {
|
220
|
+
"table_name": "FrontendModelConfig",
|
221
|
+
"db_fields": {},
|
222
|
+
"primary_key": ["partition_key"],
|
223
|
+
"foreign_keys": {},
|
251
224
|
},
|
252
|
-
"primary_key": ["partition_key"],
|
253
|
-
"table_name": "FrontendModelConfig",
|
254
225
|
},
|
255
226
|
),
|
256
227
|
]
|
Binary file
|