alpha-python 0.3.4__tar.gz → 0.5.0__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.
Files changed (141) hide show
  1. {alpha_python-0.3.4 → alpha_python-0.5.0}/LICENSE +1 -1
  2. {alpha_python-0.3.4/src/alpha_python.egg-info → alpha_python-0.5.0}/PKG-INFO +58 -2
  3. alpha_python-0.5.0/README.md +58 -0
  4. {alpha_python-0.3.4 → alpha_python-0.5.0}/pyproject.toml +10 -2
  5. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/__init__.py +22 -8
  6. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/adapters/__init__.py +2 -0
  7. alpha_python-0.5.0/src/alpha/adapters/rest_api_unit_of_work.py +105 -0
  8. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/adapters/sqla_unit_of_work.py +9 -9
  9. alpha_python-0.5.0/src/alpha/domain/models/group.py +35 -0
  10. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/exceptions.py +12 -0
  11. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/jwt_factory.py +18 -0
  12. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/controller.mustache +1 -0
  13. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/__init__.py +5 -1
  14. alpha_python-0.5.0/src/alpha/interfaces/api_repository.py +610 -0
  15. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/providers.py +1 -1
  16. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/sql_repository.py +0 -11
  17. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/mixins/jwt_provider.py +7 -7
  18. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/database_provider.py +2 -2
  19. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/ldap_provider.py +9 -9
  20. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/models/identity.py +55 -21
  21. alpha_python-0.5.0/src/alpha/providers/models/token.py +55 -0
  22. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/oidc_provider.py +7 -5
  23. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/repositories/__init__.py +2 -0
  24. alpha_python-0.5.0/src/alpha/repositories/models/repository_model.py +34 -0
  25. alpha_python-0.5.0/src/alpha/repositories/rest_api_repository.py +1199 -0
  26. alpha_python-0.5.0/src/alpha/services/authentication_service.py +824 -0
  27. alpha_python-0.5.0/src/alpha/services/models/cookie.py +51 -0
  28. alpha_python-0.5.0/src/alpha/utils/response_object.py +166 -0
  29. alpha_python-0.5.0/src/alpha/utils/secret_generator.py +19 -0
  30. {alpha_python-0.3.4 → alpha_python-0.5.0/src/alpha_python.egg-info}/PKG-INFO +58 -2
  31. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha_python.egg-info/SOURCES.txt +7 -1
  32. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha_python.egg-info/requires.txt +1 -0
  33. alpha_python-0.3.4/README.md +0 -3
  34. alpha_python-0.3.4/src/alpha/providers/models/token.py +0 -7
  35. alpha_python-0.3.4/src/alpha/repositories/models/repository_model.py +0 -16
  36. alpha_python-0.3.4/src/alpha/services/authentication_service.py +0 -200
  37. alpha_python-0.3.4/src/alpha/utils/response_object.py +0 -26
  38. {alpha_python-0.3.4 → alpha_python-0.5.0}/setup.cfg +0 -0
  39. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/cli.py +0 -0
  40. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/containers/__init__.py +0 -0
  41. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/containers/container.py +0 -0
  42. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/domain/__init__.py +0 -0
  43. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/domain/models/__init__.py +0 -0
  44. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/domain/models/base_model.py +0 -0
  45. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/domain/models/life_cycle_base.py +0 -0
  46. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/domain/models/user.py +0 -0
  47. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/encoder.py +0 -0
  48. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/__init__.py +0 -0
  49. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/_type_conversion_matrix.py +0 -0
  50. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/_type_mapping.py +0 -0
  51. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/class_factories.py +0 -0
  52. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/default_field_factory.py +0 -0
  53. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/field_iterator.py +0 -0
  54. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/logging_handler_factory.py +0 -0
  55. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/model_class_factory.py +0 -0
  56. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/models/__init__.py +0 -0
  57. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/models/factory_classes.py +0 -0
  58. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/password_factory.py +0 -0
  59. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/request_factory.py +0 -0
  60. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/response_factory.py +0 -0
  61. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/factories/type_factories.py +0 -0
  62. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/__init__.py +0 -0
  63. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/api_generate_handler.py +0 -0
  64. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/api_run_handler.py +0 -0
  65. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/base_handler.py +0 -0
  66. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/gen-code.sh +0 -0
  67. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/models/__init__.py +0 -0
  68. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/models/argument.py +0 -0
  69. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/models/command.py +0 -0
  70. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/models/section.py +0 -0
  71. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/models/subparser.py +0 -0
  72. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/run-api.sh +0 -0
  73. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/__init__.py +0 -0
  74. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/Dockerfile.mustache +0 -0
  75. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/README.mustache +0 -0
  76. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/__init__model.mustache +0 -0
  77. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/__init__test.mustache +0 -0
  78. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/__main__.mustache +0 -0
  79. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/base_model.mustache +0 -0
  80. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/controller_test.mustache +0 -0
  81. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/dockerignore.mustache +0 -0
  82. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/encoder.mustache +0 -0
  83. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/git_push.sh.mustache +0 -0
  84. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/gitignore.mustache +0 -0
  85. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/model.mustache +0 -0
  86. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/openapi.mustache +0 -0
  87. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/param_type.mustache +0 -0
  88. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/requirements.mustache +0 -0
  89. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/security_controller_.mustache +0 -0
  90. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/setup.mustache +0 -0
  91. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/test-requirements.mustache +0 -0
  92. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/tox.mustache +0 -0
  93. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/travis.mustache +0 -0
  94. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/typing_utils.mustache +0 -0
  95. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/handlers/templates/python-flask/util.mustache +0 -0
  96. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/__init__.py +0 -0
  97. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/connectors/__init__.py +0 -0
  98. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/connectors/ldap_connector.py +0 -0
  99. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/connectors/oidc_connector.py +0 -0
  100. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/databases/__init__.py +0 -0
  101. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/databases/sql_alchemy.py +0 -0
  102. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/__init__.py +0 -0
  103. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/filter_operators.py +0 -0
  104. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/json_patch.py +0 -0
  105. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/order_by.py +0 -0
  106. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/query_clause.py +0 -0
  107. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/infra/models/search_filter.py +0 -0
  108. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/attrs_instance.py +0 -0
  109. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/dataclass_instance.py +0 -0
  110. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/factories.py +0 -0
  111. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/handler.py +0 -0
  112. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/openapi_model.py +0 -0
  113. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/patchable.py +0 -0
  114. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/pydantic_instance.py +0 -0
  115. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/sql_database.py +0 -0
  116. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/sql_mapper.py +0 -0
  117. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/token_factory.py +0 -0
  118. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/unit_of_work.py +0 -0
  119. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/interfaces/updateable.py +0 -0
  120. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/mixins/__init__.py +0 -0
  121. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/__init__.py +0 -0
  122. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/api_key_provider.py +0 -0
  123. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/models/__init__.py +0 -0
  124. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/providers/models/credentials.py +0 -0
  125. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/py.typed +0 -0
  126. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/repositories/models/__init__.py +0 -0
  127. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/repositories/sql_alchemy_repository.py +0 -0
  128. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/services/__init__.py +0 -0
  129. /alpha_python-0.3.4/src/alpha/providers/local_provider.py → /alpha_python-0.5.0/src/alpha/services/models/__init__.py +0 -0
  130. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/__init__.py +0 -0
  131. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/_http_codes.py +0 -0
  132. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/is_attrs.py +0 -0
  133. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/is_pydantic.py +0 -0
  134. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/logging_configurator.py +0 -0
  135. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/logging_level_checker.py +0 -0
  136. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/verify_identity.py +0 -0
  137. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha/utils/version_checker.py +0 -0
  138. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha_python.egg-info/dependency_links.txt +0 -0
  139. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha_python.egg-info/entry_points.txt +0 -0
  140. {alpha_python-0.3.4 → alpha_python-0.5.0}/src/alpha_python.egg-info/top_level.txt +0 -0
  141. {alpha_python-0.3.4 → alpha_python-0.5.0}/tests/test_encoder.py +0 -0
@@ -1,6 +1,6 @@
1
1
  MIT License
2
2
 
3
- Copyright (c) 2025 breijling
3
+ Copyright (c) 2026 Bart Reijling
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: alpha-python
3
- Version: 0.3.4
3
+ Version: 0.5.0
4
4
  Summary: Alpha is intended to be the first dependency you need to add to your Python application. It is a Python library which contains standard building blocks that can be used in applications that are used as APIs and/or make use of database interaction.
5
5
  Author-email: Bart Reijling <bart@reijling.eu>
6
6
  Requires-Python: >=3.11
@@ -29,6 +29,7 @@ Requires-Dist: itsdangerous==1.1.0; extra == "flask"
29
29
  Requires-Dist: MarkupSafe<2.0.2; extra == "flask"
30
30
  Requires-Dist: Jinja2==2.11.2; extra == "flask"
31
31
  Requires-Dist: Flask<2,>=1.1.2; extra == "flask"
32
+ Requires-Dist: Werkzeug<2.1.0,>=1.0.1; extra == "flask"
32
33
  Requires-Dist: flask-cors>=3.0.10; extra == "flask"
33
34
  Requires-Dist: Flask-Compress>=1.13; extra == "flask"
34
35
  Provides-Extra: mysql
@@ -41,4 +42,59 @@ Dynamic: license-file
41
42
 
42
43
  # alpha
43
44
 
44
- Alpha is intended to be the first dependency you need to add to your Python application. It is a Python library which contains standard building blocks that can be used in applications that are used as APIs and/or make use of database interaction.
45
+ Alpha is intended to be the first dependency you need to add to your Python application. It is a Python library which contains standard building blocks that can be used in applications that are used as APIs and/or make use of database interaction.
46
+
47
+ ## Badges
48
+
49
+ [![PyPI version](https://badge.fury.io/py/alpha-python.svg)](https://badge.fury.io/py/alpha-python)
50
+ [![Build Status](https://travis-ci.com/breijling/alpha.svg?branch=main)](https://travis-ci.com/breijling/alpha)
51
+ [![Coverage Status](https://coveralls.io/repos/github/breijling/alpha/badge.svg?branch=main)](https://coveralls.io/github/breijling/alpha?branch=main)
52
+ [![MIT License](https://img.shields.io/badge/License-MIT-green.svg)](https://choosealicense.com/licenses/mit/)
53
+
54
+ ## Documentation
55
+
56
+ TODO: Add documentation link when available.
57
+
58
+ ## Installation
59
+
60
+ The library is still in development, but you can already install it using pip:
61
+
62
+ ```shell
63
+ pip install alpha-python
64
+ ```
65
+
66
+ If you want to use the alpha cli for generating API code, you can install it using pip as well:
67
+
68
+ ```shell
69
+ pip install alpha-python[api-generator]
70
+ ```
71
+
72
+ If you want to add the library to your API project, you can add it to your pyproject.toml file:
73
+
74
+ ```shell
75
+ # Poetry example
76
+ poetry add alpha-python --extras "flask, postgresql"
77
+ poetry add --dev alpha-python --extras "api-generator"
78
+
79
+ # UV example
80
+ uv add alpha-python --extra flask --extra postgresql
81
+ uv add --dev alpha-python --extra api-generator
82
+ ```
83
+
84
+ ## Usage
85
+
86
+ The library contains a lot of different components, but the most important ones are:
87
+
88
+ - `alpha.encoder.JSONEncoder`: A JSON encoder that can be used to serialize complex objects to JSON.
89
+
90
+ ## Features
91
+
92
+
93
+
94
+ ## Contributing
95
+
96
+ If you want to contribute to the development of this library, you can fork the repository and create a pull request with your changes.
97
+
98
+ ## License
99
+
100
+ This library is licensed under the MIT License. See the LICENSE file for more information.
@@ -0,0 +1,58 @@
1
+ # alpha
2
+
3
+ Alpha is intended to be the first dependency you need to add to your Python application. It is a Python library which contains standard building blocks that can be used in applications that are used as APIs and/or make use of database interaction.
4
+
5
+ ## Badges
6
+
7
+ [![PyPI version](https://badge.fury.io/py/alpha-python.svg)](https://badge.fury.io/py/alpha-python)
8
+ [![Build Status](https://travis-ci.com/breijling/alpha.svg?branch=main)](https://travis-ci.com/breijling/alpha)
9
+ [![Coverage Status](https://coveralls.io/repos/github/breijling/alpha/badge.svg?branch=main)](https://coveralls.io/github/breijling/alpha?branch=main)
10
+ [![MIT License](https://img.shields.io/badge/License-MIT-green.svg)](https://choosealicense.com/licenses/mit/)
11
+
12
+ ## Documentation
13
+
14
+ TODO: Add documentation link when available.
15
+
16
+ ## Installation
17
+
18
+ The library is still in development, but you can already install it using pip:
19
+
20
+ ```shell
21
+ pip install alpha-python
22
+ ```
23
+
24
+ If you want to use the alpha cli for generating API code, you can install it using pip as well:
25
+
26
+ ```shell
27
+ pip install alpha-python[api-generator]
28
+ ```
29
+
30
+ If you want to add the library to your API project, you can add it to your pyproject.toml file:
31
+
32
+ ```shell
33
+ # Poetry example
34
+ poetry add alpha-python --extras "flask, postgresql"
35
+ poetry add --dev alpha-python --extras "api-generator"
36
+
37
+ # UV example
38
+ uv add alpha-python --extra flask --extra postgresql
39
+ uv add --dev alpha-python --extra api-generator
40
+ ```
41
+
42
+ ## Usage
43
+
44
+ The library contains a lot of different components, but the most important ones are:
45
+
46
+ - `alpha.encoder.JSONEncoder`: A JSON encoder that can be used to serialize complex objects to JSON.
47
+
48
+ ## Features
49
+
50
+
51
+
52
+ ## Contributing
53
+
54
+ If you want to contribute to the development of this library, you can fork the repository and create a pull request with your changes.
55
+
56
+ ## License
57
+
58
+ This library is licensed under the MIT License. See the LICENSE file for more information.
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "alpha-python"
3
- version = "0.3.4"
3
+ version = "0.5.0"
4
4
  description = "Alpha is intended to be the first dependency you need to add to your Python application. It is a Python library which contains standard building blocks that can be used in applications that are used as APIs and/or make use of database interaction."
5
5
  readme = "README.md"
6
6
  authors = [
@@ -56,7 +56,10 @@ dev = [
56
56
  "psycopg2-binary>=2.9.11",
57
57
  "pymysql>=1.1.2",
58
58
  "ldap3>=2.9.1",
59
- "cryptography>=46.0.3"
59
+ "cryptography>=46.0.3",
60
+ "ipykernel>=7.2.0",
61
+ "flask<2",
62
+ "httpx>=0.28.1",
60
63
  ]
61
64
 
62
65
  [project.optional-dependencies]
@@ -72,6 +75,7 @@ flask = [
72
75
  "MarkupSafe<2.0.2",
73
76
  "Jinja2==2.11.2",
74
77
  "Flask>=1.1.2,<2",
78
+ "Werkzeug>=1.0.1,<2.1.0",
75
79
  "flask-cors>=3.0.10",
76
80
  "Flask-Compress>=1.13",
77
81
  ]
@@ -116,5 +120,9 @@ force_grid_wrap = 0
116
120
  python_version = "3.11"
117
121
  exclude = ['^tests/']
118
122
 
123
+ [[tool.mypy.overrides]]
124
+ module = ["flask", "flask.*"]
125
+ ignore_missing_imports = true
126
+
119
127
  [tool.ruff]
120
128
  line-length = 79
@@ -1,3 +1,4 @@
1
+ from alpha.adapters.rest_api_unit_of_work import RestApiUnitOfWork
1
2
  from alpha.adapters.sqla_unit_of_work import SqlAlchemyUnitOfWork
2
3
  from alpha.factories.jwt_factory import JWTFactory
3
4
  from alpha.factories.logging_handler_factory import LoggingHandlerFactory
@@ -20,6 +21,7 @@ from alpha.interfaces.pydantic_instance import PydanticInstance
20
21
  from alpha.interfaces.openapi_model import OpenAPIModel
21
22
  from alpha.interfaces.updateable import Updateable
22
23
  from alpha.interfaces.patchable import Patchable
24
+ from alpha.interfaces.api_repository import ApiRepository
23
25
  from alpha.interfaces.sql_repository import SqlRepository
24
26
  from alpha.interfaces.sql_mapper import SqlMapper
25
27
  from alpha.interfaces.sql_database import SqlDatabase
@@ -44,6 +46,7 @@ from alpha.providers.models.credentials import PasswordCredentials
44
46
  from alpha.providers.models.token import Token
45
47
  from alpha.providers.oidc_provider import OIDCProvider, KeyCloakProvider
46
48
  from alpha.repositories.models.repository_model import RepositoryModel
49
+ from alpha.repositories.rest_api_repository import RestApiRepository
47
50
  from alpha.repositories.sql_alchemy_repository import SqlAlchemyRepository
48
51
  from alpha.services.authentication_service import AuthenticationService
49
52
  from alpha.utils.is_attrs import is_attrs
@@ -60,13 +63,20 @@ from alpha.encoder import JSONEncoder
60
63
 
61
64
  # Optional LDAP support - only import if ldap3 is available
62
65
  try:
63
- from alpha.infra.connectors.ldap_connector import LDAPConnector # noqa: F401
64
- from alpha.providers.ldap_provider import LDAPProvider, ADProvider # noqa: F401
66
+ from alpha.infra.connectors.ldap_connector import (
67
+ LDAPConnector, # noqa: F401
68
+ )
69
+ from alpha.providers.ldap_provider import (
70
+ LDAPProvider, # noqa: F401
71
+ ADProvider, # noqa: F401
72
+ )
73
+
65
74
  _LDAP_AVAILABLE = True
66
75
  except ImportError:
67
- _LDAP_AVAILABLE = False # type: ignore
76
+ _LDAP_AVAILABLE = False # type: ignore
68
77
 
69
78
  __all__ = [
79
+ "RestApiUnitOfWork",
70
80
  "SqlAlchemyUnitOfWork",
71
81
  "JWTFactory",
72
82
  "LoggingHandlerFactory",
@@ -91,6 +101,7 @@ __all__ = [
91
101
  "OpenAPIModel",
92
102
  "Updateable",
93
103
  "Patchable",
104
+ "ApiRepository",
94
105
  "SqlRepository",
95
106
  "SqlMapper",
96
107
  "SqlDatabase",
@@ -112,6 +123,7 @@ __all__ = [
112
123
  "OIDCProvider",
113
124
  "KeyCloakProvider",
114
125
  "RepositoryModel",
126
+ "RestApiRepository",
115
127
  "SqlAlchemyRepository",
116
128
  "AuthenticationService",
117
129
  "is_attrs",
@@ -128,8 +140,10 @@ __all__ = [
128
140
 
129
141
  # Conditionally add LDAP-related exports if available
130
142
  if _LDAP_AVAILABLE:
131
- __all__.extend([
132
- "LDAPConnector",
133
- "LDAPProvider",
134
- "ADProvider",
135
- ])
143
+ __all__.extend(
144
+ [
145
+ "LDAPConnector",
146
+ "LDAPProvider",
147
+ "ADProvider",
148
+ ]
149
+ )
@@ -1,5 +1,7 @@
1
+ from alpha.adapters.rest_api_unit_of_work import RestApiUnitOfWork
1
2
  from alpha.adapters.sqla_unit_of_work import SqlAlchemyUnitOfWork
2
3
 
3
4
  __all__ = [
5
+ "RestApiUnitOfWork",
4
6
  "SqlAlchemyUnitOfWork",
5
7
  ]
@@ -0,0 +1,105 @@
1
+ """Contains the REST API Unit of Work implementation."""
2
+
3
+ from typing import Any, TypeVar
4
+
5
+ import requests
6
+
7
+ from alpha.repositories.models.repository_model import RepositoryModel
8
+
9
+
10
+ UOW = TypeVar("UOW", bound="RestApiUnitOfWork")
11
+
12
+
13
+ class RestApiUnitOfWork:
14
+ """Unit of Work implementation for REST API interactions."""
15
+
16
+ def __init__(
17
+ self,
18
+ repos: list[RepositoryModel[Any]],
19
+ session: requests.sessions.Session | None = None,
20
+ ) -> None:
21
+ """Initialize the Unit of Work with repositories.
22
+
23
+ Parameters
24
+ ----------
25
+ repos : list[RepositoryModel]
26
+ The list of repository models to use.
27
+ session : requests.sessions.Session | None
28
+ The requests session (or compatible HTTP client, e.g., httpx) to
29
+ use for context management, by default None
30
+
31
+ Raises
32
+ ------
33
+ TypeError
34
+ If any repository does not implement its specified interface.
35
+ """
36
+ self._repositories = repos
37
+ self._session = session
38
+
39
+ def __enter__(self: UOW) -> UOW:
40
+ """Enter the REST API Unit of Work context.
41
+ Initializes a :class:`requests.sessions.Session` if one was not
42
+ provided and attaches the configured repositories as attributes on the
43
+ unit of work instance. Each repository is constructed using the shared
44
+ session and its associated configuration, and optionally validated
45
+ against a declared interface.
46
+
47
+ Returns
48
+ -------
49
+ UOW
50
+ The configured :class:`RestApiUnitOfWork` instance to be used
51
+ within the context manager.
52
+ """
53
+ self._session = self._session or requests.sessions.Session()
54
+
55
+ for repo in self._repositories:
56
+ name: str = repo.name
57
+ interface: Any = repo.interface
58
+ additional_config: dict[str, Any] = dict(
59
+ repo.additional_config or {}
60
+ )
61
+
62
+ self.__setattr__(
63
+ name,
64
+ repo.repository(
65
+ session=self._session,
66
+ default_model=repo.default_model,
67
+ **additional_config,
68
+ ),
69
+ )
70
+
71
+ if interface:
72
+ if not isinstance(getattr(self, name), interface):
73
+ raise TypeError(f"Repository for {name} has no interface")
74
+
75
+ return self
76
+
77
+ def __exit__(self, *args: Any) -> None:
78
+ """Finalize the Unit of Work context."""
79
+ if self._session:
80
+ self._session.close()
81
+
82
+ def commit(self) -> None:
83
+ raise NotImplementedError("RestApiUnitOfWork does not support commit")
84
+
85
+ def flush(self) -> None:
86
+ raise NotImplementedError("RestApiUnitOfWork does not support flush")
87
+
88
+ def rollback(self) -> None:
89
+ raise NotImplementedError(
90
+ "RestApiUnitOfWork does not support rollback"
91
+ )
92
+
93
+ def refresh(self, obj: object) -> None:
94
+ raise NotImplementedError("RestApiUnitOfWork does not support refresh")
95
+
96
+ @property
97
+ def session(self) -> requests.sessions.Session | None:
98
+ """Get the current session.
99
+
100
+ Returns
101
+ -------
102
+ requests.sessions.Session | None
103
+ The current session used for API interactions.
104
+ """
105
+ return self._session
@@ -14,7 +14,11 @@ UOW = TypeVar("UOW", bound="SqlAlchemyUnitOfWork")
14
14
  class SqlAlchemyUnitOfWork:
15
15
  """Unit of Work implementation for SQLAlchemy databases."""
16
16
 
17
- def __init__(self, db: SqlDatabase, repos: list[RepositoryModel]) -> None:
17
+ def __init__(
18
+ self,
19
+ db: SqlDatabase,
20
+ repos: list[RepositoryModel[Any]],
21
+ ) -> None:
18
22
  """Initialize the Unit of Work with a database and repositories.
19
23
 
20
24
  Parameters
@@ -28,9 +32,6 @@ class SqlAlchemyUnitOfWork:
28
32
  ------
29
33
  TypeError
30
34
  If the provided database is not a valid SqlDatabase instance.
31
- TypeError
32
- If the provided repositories list is empty or contains invalid
33
- models.
34
35
  """
35
36
  if not isinstance(db, SqlDatabase): # type: ignore
36
37
  raise TypeError("No valid database provided")
@@ -55,17 +56,16 @@ class SqlAlchemyUnitOfWork:
55
56
  self._session = self._db.get_session()
56
57
 
57
58
  for repo in self._repositories:
58
- session = self._session
59
- model = repo.default_model
60
-
61
59
  name: str = repo.name
62
- repository = repo.repository
63
60
  interface: Any = repo.interface
64
61
 
65
62
  self.__setattr__(
66
63
  name,
67
- repository(session=session, default_model=model), # type: ignore
64
+ repo.repository(
65
+ session=self._session, default_model=repo.default_model
66
+ ),
68
67
  )
68
+
69
69
  if interface:
70
70
  if not isinstance(getattr(self, name), interface):
71
71
  raise TypeError(f"Repository for {name} has no interface")
@@ -0,0 +1,35 @@
1
+ from dataclasses import dataclass
2
+ from datetime import datetime, timezone
3
+ from typing import Sequence, cast
4
+ from uuid import UUID
5
+
6
+ from alpha.domain.models.base_model import BaseDomainModel, DomainModel
7
+ from alpha.domain.models.life_cycle_base import LifeCycleBase
8
+
9
+
10
+ @dataclass(kw_only=True)
11
+ class Group(LifeCycleBase, BaseDomainModel):
12
+ id: UUID | int | str | None = None
13
+ name: str | None = None
14
+ description: str | None = None
15
+ permissions: Sequence[str] | None = None
16
+ is_active: bool = True
17
+
18
+ def update(self, obj: DomainModel) -> DomainModel:
19
+ """Update the Group instance with data from another Group instance.
20
+
21
+ Parameters
22
+ ----------
23
+ obj
24
+ Group object to update from.
25
+ """
26
+ if not isinstance(obj, Group):
27
+ raise TypeError("Group.update expects a Group instance.")
28
+
29
+ self.name = obj.name
30
+ self.description = obj.description
31
+ self.permissions = obj.permissions
32
+ self.modified_at = datetime.now(tz=timezone.utc)
33
+ self.is_active = obj.is_active
34
+
35
+ return cast(DomainModel, self)
@@ -19,6 +19,10 @@ class NotFoundException(ClientErrorException):
19
19
  """Equivalent to HTTP code 404"""
20
20
 
21
21
 
22
+ class MethodNotAllowedException(ClientErrorException):
23
+ """Equivalent to HTTP code 405"""
24
+
25
+
22
26
  class NotAcceptableException(ClientErrorException):
23
27
  """Equivalent to HTTP code 406"""
24
28
 
@@ -55,11 +59,19 @@ class ServiceUnavailableException(ServerErrorException):
55
59
  """Equivalent to HTTP code 503"""
56
60
 
57
61
 
62
+ class GatewayTimeoutException(ServerErrorException):
63
+ """Equivalent to HTTP code 504"""
64
+
65
+
58
66
  # General Exceptions
59
67
  class MissingConfigurationException(Exception):
60
68
  """Raised when a required configuration is missing."""
61
69
 
62
70
 
71
+ class InvalidAttributeError(Exception):
72
+ """Raised when a required attribute is invalid."""
73
+
74
+
63
75
  class MissingDependencyException(Exception):
64
76
  """Raised when a required dependency is missing."""
65
77
 
@@ -19,6 +19,24 @@ class JWTFactory:
19
19
  issuer: str = "http://localhost",
20
20
  jwt_algorithm: str = "HS256",
21
21
  ) -> None:
22
+ """Initialize the JWTFactory.
23
+
24
+ Parameters
25
+ ----------
26
+ secret
27
+ The secret key used to sign the JWT.
28
+ lifetime_hours, optional
29
+ The lifetime of the JWT in hours, by default "12"
30
+ issuer, optional
31
+ The issuer of the JWT, by default "http://localhost"
32
+ jwt_algorithm, optional
33
+ The algorithm used to sign the JWT, by default "HS256"
34
+
35
+ Raises
36
+ ------
37
+ ValueError
38
+ If the secret value is empty.
39
+ """
22
40
  if not secret:
23
41
  raise ValueError("Secret value cannot be empty")
24
42
  if lifetime_hours is None:
@@ -231,6 +231,7 @@ def {{operationId}}(
231
231
  status_message='{{message}}',
232
232
  data=result,
233
233
  {{#vendorExtensions.x-content-type}}data_type='{{vendorExtensions.x-content-type}}'{{/vendorExtensions.x-content-type}}
234
+ {{#vendorExtensions.x-alpha-cookie-support}}response_type='flask'{{/vendorExtensions.x-alpha-cookie-support}}
234
235
  )
235
236
  return response_object, status_code
236
237
  {{/returnType}}
@@ -6,8 +6,11 @@ from alpha.interfaces.openapi_model import OpenAPIModel
6
6
  from alpha.interfaces.updateable import Updateable
7
7
  from alpha.interfaces.patchable import Patchable
8
8
 
9
- # import all database related interfaces
9
+ # import all repository related interfaces
10
+ from alpha.interfaces.api_repository import ApiRepository
10
11
  from alpha.interfaces.sql_repository import SqlRepository
12
+
13
+ # import all database related interfaces
11
14
  from alpha.interfaces.sql_mapper import SqlMapper
12
15
  from alpha.interfaces.sql_database import SqlDatabase
13
16
  from alpha.interfaces.unit_of_work import UnitOfWork
@@ -30,6 +33,7 @@ __all__ = [
30
33
  "OpenAPIModel",
31
34
  "Updateable",
32
35
  "Patchable",
36
+ "ApiRepository",
33
37
  "SqlRepository",
34
38
  "SqlMapper",
35
39
  "SqlDatabase",