hexcore 9.7.2__tar.gz → 9.7.4__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 (351) hide show
  1. {hexcore-9.7.2/hexcore.egg-info → hexcore-9.7.4}/PKG-INFO +11 -1
  2. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/sqlalchemy/repositories.py +6 -4
  3. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/sqlalchemy/repository.py +3 -1
  4. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/sqlalchemy/utils.py +20 -0
  5. {hexcore-9.7.2 → hexcore-9.7.4/hexcore.egg-info}/PKG-INFO +11 -1
  6. {hexcore-9.7.2 → hexcore-9.7.4}/pyproject.toml +26 -1
  7. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_documentation_examples.py +60 -6
  8. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_repositories_utils.py +11 -2
  9. {hexcore-9.7.2 → hexcore-9.7.4}/LICENSE +0 -0
  10. {hexcore-9.7.2 → hexcore-9.7.4}/MANIFEST.in +0 -0
  11. {hexcore-9.7.2 → hexcore-9.7.4}/README.md +0 -0
  12. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/__init__.py +0 -0
  13. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/__main__.py +0 -0
  14. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/_deprecation.py +0 -0
  15. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/__init__.py +0 -0
  16. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/__init__.py +0 -0
  17. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/adapters.py +0 -0
  18. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/config.py +0 -0
  19. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/factory.py +0 -0
  20. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/in_memory_buses.py +0 -0
  21. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/pipeline.py +0 -0
  22. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/registry.py +0 -0
  23. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/cqrs/scheduler.py +0 -0
  24. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/dtos/__init__.py +0 -0
  25. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/dtos/base.py +0 -0
  26. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/dtos/cursor.py +0 -0
  27. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/dtos/errors.py +0 -0
  28. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/dtos/query.py +0 -0
  29. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/__init__.py +0 -0
  30. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/config.py +0 -0
  31. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/factory.py +0 -0
  32. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/projector.py +0 -0
  33. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/relay.py +0 -0
  34. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/eventsourcing/repository.py +0 -0
  35. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/use_cases/__init__.py +0 -0
  36. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/use_cases/base.py +0 -0
  37. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/application/use_cases/query.py +0 -0
  38. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/capabilities.py +0 -0
  39. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/config.py +0 -0
  40. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/cqrs.py +0 -0
  41. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/cqrs.pyi +0 -0
  42. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/__init__.py +0 -0
  43. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/__init__.pyi +0 -0
  44. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/__init__.py +0 -0
  45. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/commands.py +0 -0
  46. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/config.py +0 -0
  47. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/container.py +0 -0
  48. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/hooks.py +0 -0
  49. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/plugins.py +0 -0
  50. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/application/services.py +0 -0
  51. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/__init__.py +0 -0
  52. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/context.py +0 -0
  53. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/entities.py +0 -0
  54. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/events.py +0 -0
  55. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/exceptions.py +0 -0
  56. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/permissions.py +0 -0
  57. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/plugins.py +0 -0
  58. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/ports.py +0 -0
  59. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/domain/value_objects.py +0 -0
  60. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/__init__.py +0 -0
  61. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/api/__init__.py +0 -0
  62. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/api/dependencies.py +0 -0
  63. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/api/middlewares.py +0 -0
  64. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/api/routers.py +0 -0
  65. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/cli.py +0 -0
  66. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/clock.py +0 -0
  67. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/envelope.py +0 -0
  68. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/hashing.py +0 -0
  69. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/keys.py +0 -0
  70. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/lifespan.py +0 -0
  71. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/__init__.py +0 -0
  72. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/beanie/__init__.py +0 -0
  73. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/beanie/documents.py +0 -0
  74. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/beanie/repositories.py +0 -0
  75. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/beanie/schema.py +0 -0
  76. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/selection.py +0 -0
  77. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/sqlalchemy/__init__.py +0 -0
  78. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/sqlalchemy/models.py +0 -0
  79. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/sqlalchemy/models_mixins.py +0 -0
  80. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/orms/sqlalchemy/schema.py +0 -0
  81. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/revocation.py +0 -0
  82. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/secretbox.py +0 -0
  83. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/tokens.py +0 -0
  84. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/infrastructure/transports.py +0 -0
  85. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/__init__.py +0 -0
  86. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/impersonate/__init__.py +0 -0
  87. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/impersonate/commands.py +0 -0
  88. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/impersonate/domain.py +0 -0
  89. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/impersonate/router.py +0 -0
  90. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/impersonate/service.py +0 -0
  91. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/magic_link/__init__.py +0 -0
  92. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/magic_link/commands.py +0 -0
  93. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/magic_link/router.py +0 -0
  94. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/__init__.py +0 -0
  95. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/domain.py +0 -0
  96. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/http.py +0 -0
  97. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/__init__.py +0 -0
  98. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/beanie/__init__.py +0 -0
  99. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/beanie/repository.py +0 -0
  100. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/sqlalchemy/__init__.py +0 -0
  101. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/sqlalchemy/models.py +0 -0
  102. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/orms/sqlalchemy/models_mixins.py +0 -0
  103. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/providers.py +0 -0
  104. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/router.py +0 -0
  105. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/oauth/service.py +0 -0
  106. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/__init__.py +0 -0
  107. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/domain.py +0 -0
  108. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/__init__.py +0 -0
  109. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/beanie/__init__.py +0 -0
  110. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/beanie/repository.py +0 -0
  111. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/sqlalchemy/__init__.py +0 -0
  112. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/sqlalchemy/models.py +0 -0
  113. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/sqlalchemy/models_mixins.py +0 -0
  114. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/orms/sqlalchemy/repository.py +0 -0
  115. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/router.py +0 -0
  116. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/organization/service.py +0 -0
  117. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/__init__.py +0 -0
  118. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/domain.py +0 -0
  119. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/__init__.py +0 -0
  120. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/beanie/__init__.py +0 -0
  121. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/beanie/repository.py +0 -0
  122. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/sqlalchemy/__init__.py +0 -0
  123. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/sqlalchemy/models.py +0 -0
  124. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/sqlalchemy/models_mixins.py +0 -0
  125. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/orms/sqlalchemy/repository.py +0 -0
  126. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/router.py +0 -0
  127. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/service.py +0 -0
  128. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/passkey/webauthn_adapter.py +0 -0
  129. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/storage.py +0 -0
  130. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/__init__.py +0 -0
  131. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/commands.py +0 -0
  132. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/crypto.py +0 -0
  133. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/domain.py +0 -0
  134. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/__init__.py +0 -0
  135. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/beanie/__init__.py +0 -0
  136. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/beanie/repository.py +0 -0
  137. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/sqlalchemy/__init__.py +0 -0
  138. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/sqlalchemy/models.py +0 -0
  139. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/sqlalchemy/models_mixins.py +0 -0
  140. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/orms/sqlalchemy/repository.py +0 -0
  141. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/router.py +0 -0
  142. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/service.py +0 -0
  143. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/plugins/two_factor/totp.py +0 -0
  144. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/testing/__init__.py +0 -0
  145. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/testing/fakes.py +0 -0
  146. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/testing/fixtures.py +0 -0
  147. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/darwin/testing/helpers.py +0 -0
  148. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/__init__.py +0 -0
  149. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/auth/__init__.py +0 -0
  150. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/auth/permissions.py +0 -0
  151. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/auth/value_objects.py +0 -0
  152. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/base.py +0 -0
  153. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/__init__.py +0 -0
  154. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/buses.py +0 -0
  155. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/commands.py +0 -0
  156. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/context.py +0 -0
  157. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/cron.py +0 -0
  158. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/decorators.py +0 -0
  159. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/dispatch.py +0 -0
  160. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/envelope.py +0 -0
  161. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/exceptions.py +0 -0
  162. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/handlers.py +0 -0
  163. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/middleware.py +0 -0
  164. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/queries.py +0 -0
  165. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/resolution.py +0 -0
  166. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/serializer.py +0 -0
  167. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/cqrs/task_queues.py +0 -0
  168. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/events.py +0 -0
  169. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/__init__.py +0 -0
  170. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/aggregate.py +0 -0
  171. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/exceptions.py +0 -0
  172. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/projections.py +0 -0
  173. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/snapshots.py +0 -0
  174. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/store.py +0 -0
  175. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/eventsourcing/stored.py +0 -0
  176. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/exceptions.py +0 -0
  177. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/repositories.py +0 -0
  178. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/services.py +0 -0
  179. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/domain/uow.py +0 -0
  180. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/eventsourcing.py +0 -0
  181. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/eventsourcing.pyi +0 -0
  182. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/fastapi.py +0 -0
  183. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/fastapi.pyi +0 -0
  184. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/__init__.py +0 -0
  185. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/__init__.py +0 -0
  186. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/app.py +0 -0
  187. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/cqrs.py +0 -0
  188. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/eventsourcing.py +0 -0
  189. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/exception_handlers.py +0 -0
  190. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/health.py +0 -0
  191. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/lifespan.py +0 -0
  192. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/middlewares.py +0 -0
  193. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/rate_limit.py +0 -0
  194. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/routing.py +0 -0
  195. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/streaming.py +0 -0
  196. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/api/utils.py +0 -0
  197. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cache/__init__.py +0 -0
  198. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cache/cache_backends/__init__.py +0 -0
  199. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cache/cache_backends/memory.py +0 -0
  200. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cache/cache_backends/redis.py +0 -0
  201. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cli.py +0 -0
  202. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/__init__.py +0 -0
  203. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/cron_sql.py +0 -0
  204. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/middlewares.py +0 -0
  205. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/postgres_bus.py +0 -0
  206. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/postgres_lock.py +0 -0
  207. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/procrastinate.py +0 -0
  208. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/pydantic_serializer.py +0 -0
  209. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/rabbitmq.py +0 -0
  210. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/redis_bus.py +0 -0
  211. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/cqrs/redis_lock.py +0 -0
  212. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/events/__init__.py +0 -0
  213. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/events/events_backends/__init__.py +0 -0
  214. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/events/events_backends/memory.py +0 -0
  215. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/__init__.py +0 -0
  216. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/beanie_documents.py +0 -0
  217. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/beanie_store.py +0 -0
  218. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/memory.py +0 -0
  219. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/redis_store.py +0 -0
  220. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/sqlalchemy_models.py +0 -0
  221. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/sqlalchemy_models_mixins.py +0 -0
  222. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/eventsourcing/sqlalchemy_store.py +0 -0
  223. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/__init__.py +0 -0
  224. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/_beanie_impl.py +0 -0
  225. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/_sqlalchemy_impl.py +0 -0
  226. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/base.py +0 -0
  227. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/decorators.py +0 -0
  228. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/implementations.py +0 -0
  229. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/__init__.py +0 -0
  230. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/beanie/__init__.py +0 -0
  231. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/beanie/utils.py +0 -0
  232. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/sqlalchemy/__init__.py +0 -0
  233. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/orms/sqlalchemy/session.py +0 -0
  234. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/repositories/utils.py +0 -0
  235. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/task_queues/__init__.py +0 -0
  236. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/task_queues/celery_adapter.py +0 -0
  237. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/task_queues/procrastinate_adapter.py +0 -0
  238. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/uow/__init__.py +0 -0
  239. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/uow/decorators.py +0 -0
  240. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/uow/helpers.py +0 -0
  241. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/uow/scopes.py +0 -0
  242. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/workers/__init__.py +0 -0
  243. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/workers/consumer.py +0 -0
  244. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/workers/rabbitmq_worker.py +0 -0
  245. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/infrastructure/workers/runner.py +0 -0
  246. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/py.typed +0 -0
  247. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/sql.py +0 -0
  248. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/sql.pyi +0 -0
  249. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/testing/__init__.py +0 -0
  250. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/testing/fakes.py +0 -0
  251. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/testing/fixtures.py +0 -0
  252. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/testing/helpers.py +0 -0
  253. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/testing/repositories.py +0 -0
  254. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore/types.py +0 -0
  255. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore.egg-info/SOURCES.txt +0 -0
  256. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore.egg-info/dependency_links.txt +0 -0
  257. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore.egg-info/entry_points.txt +0 -0
  258. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore.egg-info/requires.txt +0 -0
  259. {hexcore-9.7.2 → hexcore-9.7.4}/hexcore.egg-info/top_level.txt +0 -0
  260. {hexcore-9.7.2 → hexcore-9.7.4}/setup.cfg +0 -0
  261. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_alembic_metadata_completeness.py +0 -0
  262. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_anclas_del_repo.py +0 -0
  263. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_app_and_lifespan.py +0 -0
  264. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_cqrs_providers.py +0 -0
  265. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_exception_handlers.py +0 -0
  266. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_health.py +0 -0
  267. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_middlewares_and_routing.py +0 -0
  268. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_rate_limit.py +0 -0
  269. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_api_streaming.py +0 -0
  270. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_basic.py +0 -0
  271. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_beanie_query_utils.py +0 -0
  272. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_celery_event_loop.py +0 -0
  273. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_config_cors_security.py +0 -0
  274. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_config_loading.py +0 -0
  275. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_consumer_optional_event_bus.py +0 -0
  276. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_cqrs.py +0 -0
  277. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_cqrs_envelope.py +0 -0
  278. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_cqrs_factory.py +0 -0
  279. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_cqrs_middlewares.py +0 -0
  280. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_cron_sql.py +0 -0
  281. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_backend_neutrality.py +0 -0
  282. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_beanie.py +0 -0
  283. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_cli.py +0 -0
  284. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_container.py +0 -0
  285. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_context.py +0 -0
  286. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_custom_plugin.py +0 -0
  287. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_envelope.py +0 -0
  288. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_facade_and_events.py +0 -0
  289. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_flows.py +0 -0
  290. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_hashing.py +0 -0
  291. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_http.py +0 -0
  292. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_impersonate.py +0 -0
  293. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_magic_link.py +0 -0
  294. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_models.py +0 -0
  295. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_oauth.py +0 -0
  296. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_openapi.py +0 -0
  297. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_organization.py +0 -0
  298. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_passkey.py +0 -0
  299. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_permissions.py +0 -0
  300. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_plugin_decoupling.py +0 -0
  301. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_plugins.py +0 -0
  302. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_repositories.py +0 -0
  303. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_revocation.py +0 -0
  304. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_schema_registration.py +0 -0
  305. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_storage_selection.py +0 -0
  306. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_tokens.py +0 -0
  307. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_two_factor.py +0 -0
  308. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_darwin_value_objects.py +0 -0
  309. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_deprecations.py +0 -0
  310. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_domain_base_contract.py +0 -0
  311. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_domain_service_query.py +0 -0
  312. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_dotted_resolution.py +0 -0
  313. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_event_dispatch_mro.py +0 -0
  314. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_aggregate.py +0 -0
  315. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_beanie.py +0 -0
  316. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_config.py +0 -0
  317. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_ports.py +0 -0
  318. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_projections.py +0 -0
  319. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_redis.py +0 -0
  320. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_relay.py +0 -0
  321. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_repository.py +0 -0
  322. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_snapshot_checkpoint.py +0 -0
  323. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_sql_schema.py +0 -0
  324. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_store_contract.py +0 -0
  325. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_eventsourcing_uow_integration.py +0 -0
  326. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_facades.py +0 -0
  327. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_handler_registry.py +0 -0
  328. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_infrastructure_query_path.py +0 -0
  329. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_lock_error_policy.py +0 -0
  330. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_optional_dependencies.py +0 -0
  331. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_packaging.py +0 -0
  332. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_postgres_bus.py +0 -0
  333. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_postgres_lock.py +0 -0
  334. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_query_cursor_and_endpoint.py +0 -0
  335. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_query_field_validation.py +0 -0
  336. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_rabbitmq_bus.py +0 -0
  337. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_redis_bus.py +0 -0
  338. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_redis_lock.py +0 -0
  339. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_scheduler.py +0 -0
  340. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_scheduler_catchup.py +0 -0
  341. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_smart_routing.py +0 -0
  342. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_sql_naming_convention.py +0 -0
  343. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_sql_session_layer.py +0 -0
  344. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_task_queues_adapters.py +0 -0
  345. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_testing_kit.py +0 -0
  346. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_testing_utilities.py +0 -0
  347. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_typing_gate.py +0 -0
  348. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_uow_session_regression.py +0 -0
  349. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_use_cases_query.py +0 -0
  350. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_worker_bus_integration.py +0 -0
  351. {hexcore-9.7.2 → hexcore-9.7.4}/tests/test_worker_runner.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: hexcore
3
- Version: 9.7.2
3
+ Version: 9.7.4
4
4
  Summary: Reusable core for Python projects with hexagonal architecture, DDD, CQRS and background tasks. Ships the abstractions and the infrastructure: SQL session layer, FastAPI factories, worker runner, dynamic cron and identity.
5
5
  Author-email: "David Latosefki (Indroic)" <indroic@outlook.com>
6
6
  License-Expression: MIT
@@ -10,6 +10,16 @@ Project-URL: Repository, https://github.com/Indroic/HexCore
10
10
  Project-URL: Changelog, https://github.com/Indroic/HexCore/blob/master/CHANGELOG.md
11
11
  Project-URL: Issues, https://github.com/Indroic/HexCore/issues
12
12
  Keywords: hexagonal-architecture,ddd,cqrs,event-sourcing,fastapi,sqlalchemy,background-tasks,cron,authentication,identity
13
+ Classifier: Development Status :: 5 - Production/Stable
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: Programming Language :: Python :: 3
16
+ Classifier: Programming Language :: Python :: 3.12
17
+ Classifier: Programming Language :: Python :: 3.13
18
+ Classifier: Programming Language :: Python :: 3.14
19
+ Classifier: Programming Language :: Python :: 3 :: Only
20
+ Classifier: Framework :: FastAPI
21
+ Classifier: Topic :: Software Development :: Libraries :: Application Frameworks
22
+ Classifier: Typing :: Typed
13
23
  Requires-Python: >=3.12
14
24
  Description-Content-Type: text/markdown
15
25
  License-File: LICENSE
@@ -28,6 +28,8 @@ from uuid import UUID
28
28
 
29
29
  from sqlalchemy import delete, select, update
30
30
 
31
+ from hexcore.infrastructure.repositories.orms.sqlalchemy.utils import filas_afectadas
32
+
31
33
  from hexcore.darwin.domain.entities import (
32
34
  CREDENTIAL_PROVIDER,
33
35
  Account,
@@ -228,7 +230,7 @@ class SqlAlchemySessionRepository(_BaseIdentityRepository, AbstractSessionReposi
228
230
  .values(revoked_at=at)
229
231
  )
230
232
  await session.commit()
231
- return int(resultado.rowcount or 0)
233
+ return filas_afectadas(resultado)
232
234
 
233
235
  async def consume_for_rotation(
234
236
  self, session_id: UUID, *, at: datetime
@@ -272,7 +274,7 @@ class SqlAlchemySessionRepository(_BaseIdentityRepository, AbstractSessionReposi
272
274
  delete(self._model).where(self._model.expires_at < before)
273
275
  )
274
276
  await session.commit()
275
- return int(resultado.rowcount or 0)
277
+ return filas_afectadas(resultado)
276
278
 
277
279
 
278
280
  class SqlAlchemyAccountRepository(_BaseIdentityRepository, AbstractAccountRepository):
@@ -427,7 +429,7 @@ class SqlAlchemyVerificationRepository(
427
429
  .values(consumed_at=at)
428
430
  )
429
431
  await session.commit()
430
- return int(resultado.rowcount or 0)
432
+ return filas_afectadas(resultado)
431
433
 
432
434
  async def delete_expired(self, *, before: datetime) -> int:
433
435
  async with self._session_scope() as session:
@@ -435,7 +437,7 @@ class SqlAlchemyVerificationRepository(
435
437
  delete(self._model).where(self._model.expires_at < before)
436
438
  )
437
439
  await session.commit()
438
- return int(resultado.rowcount or 0)
440
+ return filas_afectadas(resultado)
439
441
 
440
442
 
441
443
  class SqlAlchemyAuditSink(AbstractAuditSink):
@@ -17,6 +17,8 @@ from datetime import UTC, datetime
17
17
 
18
18
  from sqlalchemy import delete, update
19
19
 
20
+ from hexcore.infrastructure.repositories.orms.sqlalchemy.utils import filas_afectadas
21
+
20
22
  from hexcore.darwin.plugins.oauth.domain import (
21
23
  AbstractOAuthStateRepository,
22
24
  OAuthState,
@@ -111,7 +113,7 @@ class SqlAlchemyOAuthStateRepository(AbstractOAuthStateRepository):
111
113
  delete(self._model).where(self._model.expires_at < before)
112
114
  )
113
115
  await session.commit()
114
- return int(resultado.rowcount or 0)
116
+ return filas_afectadas(resultado)
115
117
 
116
118
 
117
119
  def _a_entidad(fila: t.Any) -> OAuthState:
@@ -6,6 +6,7 @@ from datetime import datetime
6
6
  from uuid import UUID
7
7
 
8
8
  from sqlalchemy import and_, cast, func, or_, select, String
9
+ from sqlalchemy import Result
9
10
  from sqlalchemy.ext.asyncio import AsyncSession
10
11
  from sqlalchemy.orm import selectinload, RelationshipProperty
11
12
 
@@ -523,3 +524,22 @@ def ensure_framework_models_loaded() -> list[str]:
523
524
  continue
524
525
  importados.append(module_name)
525
526
  return importados
527
+
528
+
529
+ def filas_afectadas(resultado: "Result[t.Any]") -> int:
530
+ """
531
+ Cuántas filas tocó un `DELETE` o un `UPDATE`, leído de forma que tipe.
532
+
533
+ `session.execute()` está tipado como que devuelve `Result[Any]`, pero con una sentencia DML
534
+ lo que devuelve en runtime es un `CursorResult`, que es la única de las dos clases que tiene
535
+ `rowcount`. Hasta SQLAlchemy 2.0.43 los stubs dejaban pasar `resultado.rowcount` igual;
536
+ 2.0.54 afinó la jerarquía y pyright empezó a marcarlo — doce errores, todos este mismo
537
+ acceso repetido en cinco lugares.
538
+
539
+ El cast va acá y una sola vez, con el motivo escrito, en vez de cinco `# pyright: ignore`
540
+ sueltos que el próximo lector tendría que reconstruir de memoria. `rowcount` es `-1` cuando
541
+ el driver no lo sabe, y `or 0` lo aplana — que es lo que los repositorios ya hacían.
542
+ """
543
+ from sqlalchemy import CursorResult
544
+
545
+ return int(t.cast("CursorResult[t.Any]", resultado).rowcount or 0)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: hexcore
3
- Version: 9.7.2
3
+ Version: 9.7.4
4
4
  Summary: Reusable core for Python projects with hexagonal architecture, DDD, CQRS and background tasks. Ships the abstractions and the infrastructure: SQL session layer, FastAPI factories, worker runner, dynamic cron and identity.
5
5
  Author-email: "David Latosefki (Indroic)" <indroic@outlook.com>
6
6
  License-Expression: MIT
@@ -10,6 +10,16 @@ Project-URL: Repository, https://github.com/Indroic/HexCore
10
10
  Project-URL: Changelog, https://github.com/Indroic/HexCore/blob/master/CHANGELOG.md
11
11
  Project-URL: Issues, https://github.com/Indroic/HexCore/issues
12
12
  Keywords: hexagonal-architecture,ddd,cqrs,event-sourcing,fastapi,sqlalchemy,background-tasks,cron,authentication,identity
13
+ Classifier: Development Status :: 5 - Production/Stable
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: Programming Language :: Python :: 3
16
+ Classifier: Programming Language :: Python :: 3.12
17
+ Classifier: Programming Language :: Python :: 3.13
18
+ Classifier: Programming Language :: Python :: 3.14
19
+ Classifier: Programming Language :: Python :: 3 :: Only
20
+ Classifier: Framework :: FastAPI
21
+ Classifier: Topic :: Software Development :: Libraries :: Application Frameworks
22
+ Classifier: Typing :: Typed
13
23
  Requires-Python: >=3.12
14
24
  Description-Content-Type: text/markdown
15
25
  License-File: LICENSE
@@ -10,7 +10,7 @@ build-backend = "setuptools.build_meta"
10
10
 
11
11
  [project]
12
12
  name = "hexcore"
13
- version = "9.7.2"
13
+ version = "9.7.4"
14
14
  authors = [
15
15
  { name="David Latosefki (Indroic)", email="indroic@outlook.com" },
16
16
  ]
@@ -31,6 +31,31 @@ keywords = [
31
31
  "sqlalchemy", "background-tasks", "cron", "authentication", "identity",
32
32
  ]
33
33
 
34
+ # El badge de "Python" del README sale de acá y **no** de `requires-python`: shields.io lee los
35
+ # trove classifiers `Programming Language :: Python :: X.Y` de la metadata de PyPI. Sin esta
36
+ # tabla el badge renderizaba literalmente "missing", que es peor que no tenerlo — parecía que
37
+ # el paquete no declaraba ninguna versión soportada.
38
+ #
39
+ # Cada versión declarada acá tiene su pata en la matriz de `pytest.yml`. Es la mitad que
40
+ # importa: un classifier es una afirmación sobre en qué corre el paquete, y una afirmación que
41
+ # nadie verifica es exactamente lo que este repo evita en todos lados. Si se agrega una versión
42
+ # acá, va también a la matriz — y al revés.
43
+ #
44
+ # No va `License :: OSI Approved :: MIT License`: la licencia ya se declara arriba como
45
+ # expresión SPDX (PEP 639), y setuptools >=77 rechaza tener las dos formas a la vez.
46
+ classifiers = [
47
+ "Development Status :: 5 - Production/Stable",
48
+ "Intended Audience :: Developers",
49
+ "Programming Language :: Python :: 3",
50
+ "Programming Language :: Python :: 3.12",
51
+ "Programming Language :: Python :: 3.13",
52
+ "Programming Language :: Python :: 3.14",
53
+ "Programming Language :: Python :: 3 :: Only",
54
+ "Framework :: FastAPI",
55
+ "Topic :: Software Development :: Libraries :: Application Frameworks",
56
+ "Typing :: Typed",
57
+ ]
58
+
34
59
  # La documentación **no** se empaqueta en la wheel (`MANIFEST.in` sólo incluye `*.pyi` y
35
60
  # `py.typed`), así que estas URLs son la única forma de llegar a ella desde PyPI. Apuntan a
36
61
  # `docs/` de la raíz del monorepo, que es donde vive desde la consolidación — un enlace
@@ -477,6 +477,43 @@ def test_docs_facade_attributes_exist():
477
477
  )
478
478
 
479
479
 
480
+ # ── Los classifiers de Python dicen la verdad ──────────────────────────────
481
+
482
+
483
+ def test_cada_version_de_python_declarada_tiene_su_pata_en_la_matriz():
484
+ """
485
+ Los `Programming Language :: Python :: X.Y` de `pyproject.toml` y la matriz de
486
+ `pytest.yml` tienen que coincidir exactamente.
487
+
488
+ Un classifier no es decoración: es la respuesta a "¿corre en mi Python?", y es de donde
489
+ shields.io saca el badge del README. Prometer una versión que la CI no ejecuta es un verde
490
+ falso con la peor latencia posible — se descubre cuando alguien la instala.
491
+
492
+ Al revés también falla: una pata en la matriz que no esté declarada significa que se está
493
+ pagando el runner por una versión que el paquete no dice soportar.
494
+ """
495
+ tomllib = pytest.importorskip("tomllib")
496
+ yaml = pytest.importorskip("yaml")
497
+
498
+ with (REPO / "packages" / "hexcore" / "pyproject.toml").open("rb") as archivo:
499
+ classifiers = tomllib.load(archivo)["project"]["classifiers"]
500
+
501
+ prefijo = "Programming Language :: Python :: "
502
+ declaradas = {
503
+ c[len(prefijo) :]
504
+ for c in classifiers
505
+ if c.startswith(prefijo) and c[len(prefijo) :][:1].isdigit() and "." in c
506
+ }
507
+
508
+ flujo = yaml.safe_load((REPO / ".github" / "workflows" / "pytest.yml").read_text(encoding="utf-8"))
509
+ en_matriz = {str(v) for v in flujo["jobs"]["test"]["strategy"]["matrix"]["python"]}
510
+
511
+ assert declaradas == en_matriz, (
512
+ f"pyproject declara {sorted(declaradas)} y pytest.yml corre {sorted(en_matriz)}. "
513
+ "Agreg\u00e1 la versi\u00f3n que falta al otro lado, o sac\u00e1 la que sobra."
514
+ )
515
+
516
+
480
517
  # ── La skill de agente ─────────────────────────────────────────────────────────
481
518
  #
482
519
  # `skills/hexcore/` ya entra en los guardas de arriba por `ALL_DOC_FILES`: sus `from hexcore…
@@ -515,20 +552,37 @@ def _surface():
515
552
 
516
553
  def test_la_skill_tiene_frontmatter_utilizable():
517
554
  """
518
- Sin `name` y `description` en el frontmatter, Claude Code no carga la skill y nadie se
519
- entera: no hay error, simplemente el agente no la usa nunca. Un typo en el YAML la apaga
520
- en silencio, que es el mismo modo de falla que la skill entera existe para documentar.
555
+ El frontmatter de `SKILL.md` tiene que **parsear como YAML**, no sólo contener las claves.
556
+
557
+ Chequear que el texto `description:` esté presente no alcanza, y no es una hipótesis: la
558
+ primera versión de este test hacía exactamente eso y dejó pasar una `description` con un
559
+ `: ` en el medio (`"...del monorepo: el framework Python..."`), que YAML lee como un mapping
560
+ anidado dentro de un mapping compacto. El parser de Claude Code es lo bastante tolerante
561
+ como para cargarla igual, así que acá todo se veía bien; el de `npx skills` no lo es y
562
+ rechazó la skill entera con "No valid skills found".
563
+
564
+ Ese es justo el modo de falla que esta skill documenta en otros lados: no levanta una
565
+ excepción donde está el error, simplemente el agente no la usa nunca.
521
566
  """
567
+ yaml = pytest.importorskip("yaml")
568
+
522
569
  contenido = (SKILL_DIR / "SKILL.md").read_text(encoding="utf-8")
523
570
 
524
571
  assert contenido.startswith("---\n"), "SKILL.md tiene que abrir con el frontmatter YAML"
525
572
  cierre = contenido.index("\n---\n", 3)
526
573
  frontmatter = contenido[4:cierre]
527
574
 
528
- for clave in ("name:", "description:"):
529
- assert clave in frontmatter, f"al frontmatter de SKILL.md le falta `{clave}`"
575
+ try:
576
+ metadatos = yaml.safe_load(frontmatter)
577
+ except yaml.YAMLError as error: # pragma: no cover - el mensaje es el valor del test
578
+ pytest.fail(f"el frontmatter de SKILL.md no parsea como YAML: {error}")
579
+
580
+ assert isinstance(metadatos, dict), "el frontmatter tiene que ser un mapping YAML"
581
+
582
+ for clave in ("name", "description"):
583
+ assert metadatos.get(clave), f"al frontmatter de SKILL.md le falta `{clave}`"
530
584
 
531
- assert "darwin-client" in frontmatter, (
585
+ assert "darwin-client" in metadatos["description"], (
532
586
  "la `description` es lo único que el modelo lee para decidir si activa la skill: si no "
533
587
  "nombra el cliente TypeScript, un prompt de frontend no la dispara"
534
588
  )
@@ -248,8 +248,17 @@ def test_discover_sql_repositories_warns_for_abstract_repositories() -> None:
248
248
  assert "concretewarning" in discovered
249
249
  assert discovered["concretewarning"] is _ConcreteWarningRepo
250
250
  assert caught
251
- warning_message = str(caught[0].message)
252
- assert "_AbstractWarningRepo" in warning_message
251
+ # El warning se busca, no se asume que sea `caught[0]`. `catch_warnings(record=True)`
252
+ # captura **todos** los del bloque, incluidos los que no son de este código: en Python 3.14
253
+ # el recolector cierra las conexiones sqlite pendientes dentro de la ventana y mete un
254
+ # `ResourceWarning: unclosed database` que llega primero. El test fallaba comparando contra
255
+ # ese, con un mensaje que no nombraba la causa real.
256
+ mensajes = [str(w.message) for w in caught]
257
+ coincidencias = [m for m in mensajes if "_AbstractWarningRepo" in m]
258
+ assert coincidencias, (
259
+ "ning\u00fan warning menciona _AbstractWarningRepo; se capturaron: " + repr(mensajes)
260
+ )
261
+ warning_message = coincidencias[0]
253
262
  assert "custom_required" in warning_message
254
263
 
255
264
 
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