loom-kernel 0.9.0__tar.gz → 0.9.2__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 (802) hide show
  1. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.github/workflows/docs.yml +4 -3
  2. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/CHANGELOG.md +48 -77
  3. loom_kernel-0.9.2/CHANGELOG_RELEASE.md +15 -0
  4. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/PKG-INFO +6 -1
  5. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/pyproject.toml +14 -2
  6. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/__init__.py +4 -0
  7. loom_kernel-0.9.2/src/loom/core/config/_resolver_utils.py +116 -0
  8. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/keys.py +1 -0
  9. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/loader.py +1 -1
  10. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/resolver.py +22 -15
  11. loom_kernel-0.9.2/src/loom/core/config/secrets.py +144 -0
  12. loom_kernel-0.9.2/src/loom/core/config/ssm.py +141 -0
  13. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/__init__.py +5 -0
  14. loom_kernel-0.9.2/src/loom/streaming/bytewax/_sink_registry.py +137 -0
  15. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/runner.py +88 -14
  16. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/core/_exceptions.py +5 -0
  17. loom_kernel-0.9.2/tests/unit/core/config/test_resolver_utils.py +130 -0
  18. loom_kernel-0.9.2/tests/unit/core/config/test_secrets.py +229 -0
  19. loom_kernel-0.9.2/tests/unit/core/config/test_ssm.py +215 -0
  20. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_runner.py +185 -0
  21. loom_kernel-0.9.2/tests/unit/streaming/bytewax/test_sink_registry.py +198 -0
  22. loom_kernel-0.9.2/tests/unit/testing/__init__.py +0 -0
  23. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/uv.lock +61 -2
  24. loom_kernel-0.9.0/CHANGELOG_RELEASE.md +0 -98
  25. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.github/workflows/ci-main.yml +0 -0
  26. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.github/workflows/ci-pr.yml +0 -0
  27. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.github/workflows/release.yml +0 -0
  28. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.gitignore +0 -0
  29. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.pre-commit-config.yaml +0 -0
  30. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/.readthedocs.yaml +0 -0
  31. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/LICENSE +0 -0
  32. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/Makefile +0 -0
  33. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/README.md +0 -0
  34. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/codecov.yml +0 -0
  35. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/_static/.gitkeep +0 -0
  36. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/_static/custom.css +0 -0
  37. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/_static/logo-transparent.png +0 -0
  38. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/_static/logo.svg +0 -0
  39. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/architecture/adr/README.md +0 -0
  40. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/architecture/clean-architecture.md +0 -0
  41. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/architecture/overview.md +0 -0
  42. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/conf.py +0 -0
  43. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/etl/examples.md +0 -0
  44. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/etl/pipelines.md +0 -0
  45. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/etl/testing.md +0 -0
  46. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/examples-repo/index.md +0 -0
  47. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/getting-started/etl.md +0 -0
  48. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/getting-started/rest.md +0 -0
  49. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/getting-started/streaming.md +0 -0
  50. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/autocrud.md +0 -0
  51. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/celery.md +0 -0
  52. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/etl.md +0 -0
  53. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/fake-repo-examples.md +0 -0
  54. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/quickstart.md +0 -0
  55. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/guides/use-case-dsl.md +0 -0
  56. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/index.rst +0 -0
  57. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/overview.md +0 -0
  58. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/core.rst +0 -0
  59. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/etl.rst +0 -0
  60. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/repository.rst +0 -0
  61. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/rest.rst +0 -0
  62. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/streaming.rst +0 -0
  63. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/api/testing.rst +0 -0
  64. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/reference/index.rst +0 -0
  65. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/requirements.txt +0 -0
  66. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/rest/autocrud.md +0 -0
  67. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/rest/celery.md +0 -0
  68. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/rest/examples.md +0 -0
  69. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/rest/testing.md +0 -0
  70. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/rest/use-case-dsl.md +0 -0
  71. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/docs/streaming/bytewax.md +0 -0
  72. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/sonar-project.properties +0 -0
  73. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/__init__.py +0 -0
  74. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/__init__.py +0 -0
  75. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/auto.py +0 -0
  76. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/bootstrap.py +0 -0
  77. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/config.py +0 -0
  78. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/constants.py +0 -0
  79. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/runner.py +0 -0
  80. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/celery/service.py +0 -0
  81. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/async_bridge.py +0 -0
  82. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/backend/__init__.py +0 -0
  83. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/backend/core_model.py +0 -0
  84. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/backend/protocol.py +0 -0
  85. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/backend/sqlalchemy.py +0 -0
  86. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/bootstrap/__init__.py +0 -0
  87. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/bootstrap/bootstrap.py +0 -0
  88. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/bootstrap/kernel.py +0 -0
  89. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/__init__.py +0 -0
  90. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/abc/__init__.py +0 -0
  91. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/abc/backend.py +0 -0
  92. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/abc/config.py +0 -0
  93. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/abc/dependency.py +0 -0
  94. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/codec.py +0 -0
  95. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/decorators.py +0 -0
  96. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/dependency.py +0 -0
  97. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/gateway.py +0 -0
  98. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/keys.py +0 -0
  99. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/repository.py +0 -0
  100. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/cache/serializer.py +0 -0
  101. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/command/__init__.py +0 -0
  102. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/command/adapter.py +0 -0
  103. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/command/base.py +0 -0
  104. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/command/field.py +0 -0
  105. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/command/introspection.py +0 -0
  106. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/compiler.py +0 -0
  107. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/binder.py +0 -0
  108. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/configurable.py +0 -0
  109. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/context.py +0 -0
  110. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/errors.py +0 -0
  111. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/model.py +0 -0
  112. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/config/observability.py +0 -0
  113. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/contracts/__init__.py +0 -0
  114. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/contracts/manifest.py +0 -0
  115. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/di/__init__.py +0 -0
  116. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/di/container.py +0 -0
  117. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/di/scope.py +0 -0
  118. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/__init__.py +0 -0
  119. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/_utils.py +0 -0
  120. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/base.py +0 -0
  121. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/interfaces.py +0 -0
  122. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/manifest.py +0 -0
  123. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/discovery/modules.py +0 -0
  124. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/__init__.py +0 -0
  125. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/compilable.py +0 -0
  126. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/compiler.py +0 -0
  127. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/events.py +0 -0
  128. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/executor.py +0 -0
  129. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/metrics.py +0 -0
  130. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/engine/plan.py +0 -0
  131. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/errors/__init__.py +0 -0
  132. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/errors/codes.py +0 -0
  133. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/errors/errors.py +0 -0
  134. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/expr/__init__.py +0 -0
  135. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/expr/eval.py +0 -0
  136. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/expr/nodes.py +0 -0
  137. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/expr/refs.py +0 -0
  138. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/__init__.py +0 -0
  139. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/callback.py +0 -0
  140. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/context.py +0 -0
  141. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/handle.py +0 -0
  142. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/job.py +0 -0
  143. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/job/service.py +0 -0
  144. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/logger/__init__.py +0 -0
  145. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/logger/abc.py +0 -0
  146. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/logger/config.py +0 -0
  147. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/logger/registry.py +0 -0
  148. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/logger/structlogger.py +0 -0
  149. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/__init__.py +0 -0
  150. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/base.py +0 -0
  151. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/enums.py +0 -0
  152. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/field.py +0 -0
  153. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/introspection.py +0 -0
  154. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/projection.py +0 -0
  155. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/relation.py +0 -0
  156. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/struct.py +0 -0
  157. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/timestamped.py +0 -0
  158. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/types.py +0 -0
  159. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/model/types_postgres.py +0 -0
  160. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/__init__.py +0 -0
  161. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/config.py +0 -0
  162. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/event.py +0 -0
  163. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/observer/__init__.py +0 -0
  164. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/observer/noop.py +0 -0
  165. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/observer/otel.py +0 -0
  166. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/observer/structlog.py +0 -0
  167. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/protocol.py +0 -0
  168. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/runtime.py +0 -0
  169. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/observability/topology.py +0 -0
  170. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/projection/__init__.py +0 -0
  171. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/projection/loaders.py +0 -0
  172. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/projection/runtime.py +0 -0
  173. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/__init__.py +0 -0
  174. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/abc/__init__.py +0 -0
  175. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/abc/query.py +0 -0
  176. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/abc/repo_for.py +0 -0
  177. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/abc/repository.py +0 -0
  178. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/mutation.py +0 -0
  179. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/registration.py +0 -0
  180. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/registry.py +0 -0
  181. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/__init__.py +0 -0
  182. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/integrity.py +0 -0
  183. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/loaders.py +0 -0
  184. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/mixins.py +0 -0
  185. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/model.py +0 -0
  186. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/profile_loader.py +0 -0
  187. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/projection.py +0 -0
  188. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/__init__.py +0 -0
  189. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/compiler.py +0 -0
  190. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/cursor.py +0 -0
  191. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/errors.py +0 -0
  192. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/filters.py +0 -0
  193. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/ordering.py +0 -0
  194. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/paths.py +0 -0
  195. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/query_compiler/subquery.py +0 -0
  196. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/registry.py +0 -0
  197. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/repository.py +0 -0
  198. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/session_manager.py +0 -0
  199. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/transactional.py +0 -0
  200. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/repository/sqlalchemy/uow.py +0 -0
  201. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/response/__init__.py +0 -0
  202. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/response/base.py +0 -0
  203. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/routing/__init__.py +0 -0
  204. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/routing/ref.py +0 -0
  205. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/routing/resolver.py +0 -0
  206. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/runner.py +0 -0
  207. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/schema/__init__.py +0 -0
  208. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/schema/schema_mode.py +0 -0
  209. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/tracing/__init__.py +0 -0
  210. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/tracing/context.py +0 -0
  211. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/transport/__init__.py +0 -0
  212. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/transport/adapter.py +0 -0
  213. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/uow/__init__.py +0 -0
  214. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/uow/abc.py +0 -0
  215. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/uow/context.py +0 -0
  216. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/__init__.py +0 -0
  217. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/_predicates.py +0 -0
  218. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/compute.py +0 -0
  219. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/constants.py +0 -0
  220. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/factory.py +0 -0
  221. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/field_ref.py +0 -0
  222. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/invoker.py +0 -0
  223. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/keys.py +0 -0
  224. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/markers.py +0 -0
  225. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/registry.py +0 -0
  226. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/rule.py +0 -0
  227. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/core/use_case/use_case.py +0 -0
  228. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/__init__.py +0 -0
  229. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/__init__.py +0 -0
  230. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_format_registry.py +0 -0
  231. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/__init__.py +0 -0
  232. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/_common.py +0 -0
  233. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/_log.py +0 -0
  234. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/_ops.py +0 -0
  235. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/_snapshot.py +0 -0
  236. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_historify/_transform.py +0 -0
  237. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_merge.py +0 -0
  238. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_predicate.py +0 -0
  239. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_schema_aligner/__init__.py +0 -0
  240. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_schema_aligner/_aligner.py +0 -0
  241. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_schema_aligner/_policy.py +0 -0
  242. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/_write_policy.py +0 -0
  243. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/__init__.py +0 -0
  244. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_dtype.py +0 -0
  245. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_file_writer.py +0 -0
  246. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_historify.py +0 -0
  247. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_predicate.py +0 -0
  248. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_reader.py +0 -0
  249. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_schema.py +0 -0
  250. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_schema_aligner.py +0 -0
  251. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/_writer.py +0 -0
  252. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/polars/provider.py +0 -0
  253. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/__init__.py +0 -0
  254. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_dtype.py +0 -0
  255. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_historify.py +0 -0
  256. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_reader.py +0 -0
  257. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_schema.py +0 -0
  258. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_schema_aligner.py +0 -0
  259. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/_writer.py +0 -0
  260. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/backends/spark/provider.py +0 -0
  261. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/__init__.py +0 -0
  262. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_backends/_polars.py +0 -0
  263. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_backends/_spark.py +0 -0
  264. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_cleaners.py +0 -0
  265. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_paths.py +0 -0
  266. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_scope.py +0 -0
  267. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/checkpoint/_store.py +0 -0
  268. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/__init__.py +0 -0
  269. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_binding.py +0 -0
  270. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_compiler.py +0 -0
  271. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_errors.py +0 -0
  272. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_plan.py +0 -0
  273. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_validators.py +0 -0
  274. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_validators_plan.py +0 -0
  275. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/compiler/_validators_step.py +0 -0
  276. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/__init__.py +0 -0
  277. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/_format.py +0 -0
  278. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/_read_options.py +0 -0
  279. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/_utils.py +0 -0
  280. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/_write_options.py +0 -0
  281. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/expr/__init__.py +0 -0
  282. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/expr/_params.py +0 -0
  283. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/expr/_predicate.py +0 -0
  284. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/expr/_predicate_dialect.py +0 -0
  285. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/expr/_refs.py +0 -0
  286. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/source/__init__.py +0 -0
  287. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/source/_from.py +0 -0
  288. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/source/_from_clickhouse.py +0 -0
  289. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/source/_from_mongo.py +0 -0
  290. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/source/_specs.py +0 -0
  291. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/__init__.py +0 -0
  292. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_file.py +0 -0
  293. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/__init__.py +0 -0
  294. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/_builder.py +0 -0
  295. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/_enums.py +0 -0
  296. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/_errors.py +0 -0
  297. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/_report.py +0 -0
  298. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_history/_spec.py +0 -0
  299. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_into.py +0 -0
  300. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_schema_mode.py +0 -0
  301. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_table.py +0 -0
  302. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/declarative/target/_temp.py +0 -0
  303. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/executor/__init__.py +0 -0
  304. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/executor/_dispatcher.py +0 -0
  305. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/executor/_executor.py +0 -0
  306. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/__init__.py +0 -0
  307. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/_registry.py +0 -0
  308. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/__init__.py +0 -0
  309. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/_clickhouse.py +0 -0
  310. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/_mongo.py +0 -0
  311. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/_mongo_batch.py +0 -0
  312. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/_mongo_bson.py +0 -0
  313. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/sources/_mongo_predicate.py +0 -0
  314. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/targets/__init__.py +0 -0
  315. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/io/targets/_clickhouse.py +0 -0
  316. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/__init__.py +0 -0
  317. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/_config.py +0 -0
  318. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/_observer.py +0 -0
  319. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/_records.py +0 -0
  320. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/sinks/__init__.py +0 -0
  321. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/sinks/_protocol.py +0 -0
  322. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/sinks/_table.py +0 -0
  323. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/lineage/sinks/_writer.py +0 -0
  324. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/__init__.py +0 -0
  325. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_generics.py +0 -0
  326. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_params.py +0 -0
  327. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_pipeline.py +0 -0
  328. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_process.py +0 -0
  329. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_sql.py +0 -0
  330. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_step.py +0 -0
  331. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/pipeline/_step_sql.py +0 -0
  332. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/__init__.py +0 -0
  333. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/_providers.py +0 -0
  334. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/_wiring.py +0 -0
  335. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/config_loader.py +0 -0
  336. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/core.py +0 -0
  337. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/errors.py +0 -0
  338. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runner/filtering.py +0 -0
  339. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runtime/__init__.py +0 -0
  340. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/runtime/contracts.py +0 -0
  341. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/schema/__init__.py +0 -0
  342. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/schema/_contract.py +0 -0
  343. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/schema/_schema.py +0 -0
  344. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/storage/__init__.py +0 -0
  345. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/storage/_config.py +0 -0
  346. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/storage/_file_locator.py +0 -0
  347. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/storage/_locator.py +0 -0
  348. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/storage/routing.py +0 -0
  349. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/__init__.py +0 -0
  350. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/_result.py +0 -0
  351. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/_runners.py +0 -0
  352. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/_scenario.py +0 -0
  353. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/_stubs.py +0 -0
  354. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/etl/testing/spark.py +0 -0
  355. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/prometheus/__init__.py +0 -0
  356. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/prometheus/adapter.py +0 -0
  357. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/prometheus/kafka.py +0 -0
  358. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/prometheus/lifecycle.py +0 -0
  359. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/prometheus/middleware.py +0 -0
  360. /loom_kernel-0.9.0/tests/__init__.py → /loom_kernel-0.9.2/src/loom/py.typed +0 -0
  361. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/__init__.py +0 -0
  362. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/adapter.py +0 -0
  363. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/autocrud.py +0 -0
  364. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/compiler.py +0 -0
  365. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/constants.py +0 -0
  366. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/errors.py +0 -0
  367. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/__init__.py +0 -0
  368. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/app.py +0 -0
  369. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/auto.py +0 -0
  370. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/openapi.py +0 -0
  371. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/response.py +0 -0
  372. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/fastapi/router_runtime.py +0 -0
  373. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/middleware.py +0 -0
  374. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/model.py +0 -0
  375. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/rest/rest_adapter.py +0 -0
  376. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/__init__.py +0 -0
  377. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_adapter.py +0 -0
  378. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_commit_tracker.py +0 -0
  379. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_dlq.py +0 -0
  380. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_error_boundary.py +0 -0
  381. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_operators.py +0 -0
  382. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_resource_manager.py +0 -0
  383. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/_runtime_io.py +0 -0
  384. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/__init__.py +0 -0
  385. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/_shared.py +0 -0
  386. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/boundary.py +0 -0
  387. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/dispatcher.py +0 -0
  388. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/routing.py +0 -0
  389. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/scopes.py +0 -0
  390. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/shapes.py +0 -0
  391. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/steps.py +0 -0
  392. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/bytewax/handlers/storage.py +0 -0
  393. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/__init__.py +0 -0
  394. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/_bindings.py +0 -0
  395. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/_compiler.py +0 -0
  396. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/_plan.py +0 -0
  397. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/phases/build_plan.py +0 -0
  398. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/compiler/phases/validate.py +0 -0
  399. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/core/__init__.py +0 -0
  400. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/core/_errors.py +0 -0
  401. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/core/_message.py +0 -0
  402. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/core/_typing.py +0 -0
  403. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/graph/__init__.py +0 -0
  404. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/graph/_flow.py +0 -0
  405. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/__init__.py +0 -0
  406. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_codec.py +0 -0
  407. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_config.py +0 -0
  408. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_errors.py +0 -0
  409. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_key_resolver.py +0 -0
  410. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_message.py +0 -0
  411. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_record.py +0 -0
  412. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/_wire.py +0 -0
  413. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/client/__init__.py +0 -0
  414. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/client/_consumer.py +0 -0
  415. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/client/_producer.py +0 -0
  416. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/client/_protocol.py +0 -0
  417. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/message/__init__.py +0 -0
  418. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/message/_consumer.py +0 -0
  419. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/message/_producer.py +0 -0
  420. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/kafka/message/_protocol.py +0 -0
  421. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/mongo/__init__.py +0 -0
  422. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/mongo/_bytewax_source.py +0 -0
  423. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/mongo/_config.py +0 -0
  424. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/mongo/_event.py +0 -0
  425. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/mongo/_normalize.py +0 -0
  426. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/__init__.py +0 -0
  427. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_boundary.py +0 -0
  428. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_broadcast.py +0 -0
  429. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_capabilities.py +0 -0
  430. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_decompose.py +0 -0
  431. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_expand_routes.py +0 -0
  432. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_expr_eval.py +0 -0
  433. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_fork.py +0 -0
  434. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_helpers.py +0 -0
  435. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_mongo.py +0 -0
  436. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_protocols.py +0 -0
  437. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_router.py +0 -0
  438. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_shape.py +0 -0
  439. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_sink.py +0 -0
  440. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_step.py +0 -0
  441. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_table/__init__.py +0 -0
  442. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_table/common.py +0 -0
  443. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_table/config.py +0 -0
  444. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/_with.py +0 -0
  445. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/nodes/refs.py +0 -0
  446. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/streaming/testing.py +0 -0
  447. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/__init__.py +0 -0
  448. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/golden.py +0 -0
  449. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/http_harness.py +0 -0
  450. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/in_memory.py +0 -0
  451. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/repository_harness.py +0 -0
  452. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/src/loom/testing/runner.py +0 -0
  453. {loom_kernel-0.9.0/tests/golden → loom_kernel-0.9.2/tests}/__init__.py +0 -0
  454. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/conftest.py +0 -0
  455. {loom_kernel-0.9.0/tests/integration → loom_kernel-0.9.2/tests/golden}/__init__.py +0 -0
  456. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/golden/baselines/.gitkeep +0 -0
  457. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/golden/outputs/.gitkeep +0 -0
  458. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/golden/plans/.gitkeep +0 -0
  459. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/helpers/__init__.py +0 -0
  460. {loom_kernel-0.9.0/tests/integration/celery_bootstrap → loom_kernel-0.9.2/tests/integration}/__init__.py +0 -0
  461. {loom_kernel-0.9.0/tests/integration/core → loom_kernel-0.9.2/tests/integration/celery_bootstrap}/__init__.py +0 -0
  462. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/celery_bootstrap/config/conf.celery.integration.yaml +0 -0
  463. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/celery_bootstrap/test_auto_create_app_integration.py +0 -0
  464. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/celery_bootstrap/test_bootstrap_worker.py +0 -0
  465. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/conftest.py +0 -0
  466. {loom_kernel-0.9.0/tests/integration/core/bootstrap → loom_kernel-0.9.2/tests/integration/core}/__init__.py +0 -0
  467. {loom_kernel-0.9.0/tests/integration/core/repository → loom_kernel-0.9.2/tests/integration/core/bootstrap}/__init__.py +0 -0
  468. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/bootstrap/test_bootstrap_integration.py +0 -0
  469. {loom_kernel-0.9.0/tests/integration/core/repository/sqlalchemy → loom_kernel-0.9.2/tests/integration/core/repository}/__init__.py +0 -0
  470. {loom_kernel-0.9.0/tests/integration/core/rest → loom_kernel-0.9.2/tests/integration/core/repository/sqlalchemy}/__init__.py +0 -0
  471. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/repository/sqlalchemy/conftest.py +0 -0
  472. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/repository/sqlalchemy/test_cache_integration.py +0 -0
  473. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/repository/sqlalchemy/test_repository_integration.py +0 -0
  474. {loom_kernel-0.9.0/tests/integration/core/use_case → loom_kernel-0.9.2/tests/integration/core/rest}/__init__.py +0 -0
  475. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/rest/test_auto_interface_integration.py +0 -0
  476. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/rest/test_fastapi_app_integration.py +0 -0
  477. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/rest/test_rest_error_mapping.py +0 -0
  478. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/rest/test_rest_observability.py +0 -0
  479. {loom_kernel-0.9.0/tests/integration/fake_repo → loom_kernel-0.9.2/tests/integration/core/use_case}/__init__.py +0 -0
  480. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/use_case/test_custom_repository_integration.py +0 -0
  481. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/core/use_case/test_use_case_crud_integration.py +0 -0
  482. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/etl/__init__.py +0 -0
  483. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/etl/test_runner_integration.py +0 -0
  484. {loom_kernel-0.9.0/tests/integration/fake_repo/product/category → loom_kernel-0.9.2/tests/integration/fake_repo}/__init__.py +0 -0
  485. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/config/__init__.py +0 -0
  486. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/config/conf.interfaces.yaml +0 -0
  487. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/config/conf.manifest.yaml +0 -0
  488. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/config/conf.modules.yaml +0 -0
  489. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/config/conf.yaml +0 -0
  490. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/main.py +0 -0
  491. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/manifest.py +0 -0
  492. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/__init__.py +0 -0
  493. {loom_kernel-0.9.0/tests/integration/fake_repo/product/review → loom_kernel-0.9.2/tests/integration/fake_repo/product/category}/__init__.py +0 -0
  494. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/category/model.py +0 -0
  495. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/category/schemas.py +0 -0
  496. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/interface.py +0 -0
  497. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/jobs.py +0 -0
  498. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/model.py +0 -0
  499. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/relations.py +0 -0
  500. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/repository.py +0 -0
  501. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/repository_contract.py +0 -0
  502. {loom_kernel-0.9.0/tests/integration/streaming → loom_kernel-0.9.2/tests/integration/fake_repo/product/review}/__init__.py +0 -0
  503. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/review/model.py +0 -0
  504. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/review/schemas.py +0 -0
  505. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/schemas.py +0 -0
  506. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/fake_repo/product/use_cases.py +0 -0
  507. {loom_kernel-0.9.0/tests/unit → loom_kernel-0.9.2/tests/integration/streaming}/__init__.py +0 -0
  508. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/streaming/test_into_table_integration.py +0 -0
  509. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/support/__init__.py +0 -0
  510. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/integration/support/logical_repo_fixtures.py +0 -0
  511. {loom_kernel-0.9.0/tests/unit/celery_bootstrap → loom_kernel-0.9.2/tests/unit}/__init__.py +0 -0
  512. {loom_kernel-0.9.0/tests/unit/celery_jobs → loom_kernel-0.9.2/tests/unit/celery_bootstrap}/__init__.py +0 -0
  513. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_bootstrap/test_async_runtime.py +0 -0
  514. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_bootstrap/test_bootstrap.py +0 -0
  515. {loom_kernel-0.9.0/tests/unit/core → loom_kernel-0.9.2/tests/unit/celery_jobs}/__init__.py +0 -0
  516. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_jobs/test_auto.py +0 -0
  517. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_jobs/test_celery_service.py +0 -0
  518. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_jobs/test_config.py +0 -0
  519. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/celery_jobs/test_runner.py +0 -0
  520. {loom_kernel-0.9.0/tests/unit/core/backend → loom_kernel-0.9.2/tests/unit/core}/__init__.py +0 -0
  521. {loom_kernel-0.9.0/tests/unit/core/bootstrap → loom_kernel-0.9.2/tests/unit/core/backend}/__init__.py +0 -0
  522. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/backend/test_backend_compiler.py +0 -0
  523. {loom_kernel-0.9.0/tests/unit/core/cache → loom_kernel-0.9.2/tests/unit/core/bootstrap}/__init__.py +0 -0
  524. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/bootstrap/test_bootstrap.py +0 -0
  525. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/bootstrap/test_bootstrap_metrics.py +0 -0
  526. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/bootstrap/test_kernel.py +0 -0
  527. {loom_kernel-0.9.0/tests/unit/core/command → loom_kernel-0.9.2/tests/unit/core/cache}/__init__.py +0 -0
  528. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/cache/test_cached_repository.py +0 -0
  529. {loom_kernel-0.9.0/tests/unit/core/config → loom_kernel-0.9.2/tests/unit/core/command}/__init__.py +0 -0
  530. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/command/test_command_base.py +0 -0
  531. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/command/test_command_field.py +0 -0
  532. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/command/test_command_patch.py +0 -0
  533. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/command/test_introspection.py +0 -0
  534. {loom_kernel-0.9.0/tests/unit/core/di → loom_kernel-0.9.2/tests/unit/core/config}/__init__.py +0 -0
  535. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/config/test_binder.py +0 -0
  536. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/config/test_config.py +0 -0
  537. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/config/test_configurable.py +0 -0
  538. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/config/test_context.py +0 -0
  539. {loom_kernel-0.9.0/tests/unit/core/discovery → loom_kernel-0.9.2/tests/unit/core/di}/__init__.py +0 -0
  540. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/di/test_container.py +0 -0
  541. {loom_kernel-0.9.0/tests/unit/core/engine → loom_kernel-0.9.2/tests/unit/core/discovery}/__init__.py +0 -0
  542. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/discovery/test_manifest.py +0 -0
  543. {loom_kernel-0.9.0/tests/unit/core/errors → loom_kernel-0.9.2/tests/unit/core/engine}/__init__.py +0 -0
  544. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_compiler.py +0 -0
  545. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_executor.py +0 -0
  546. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_executor_trace.py +0 -0
  547. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_executor_uow.py +0 -0
  548. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_metrics.py +0 -0
  549. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/engine/test_plan.py +0 -0
  550. {loom_kernel-0.9.0/tests/unit/core/expr → loom_kernel-0.9.2/tests/unit/core/errors}/__init__.py +0 -0
  551. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/errors/test_errors.py +0 -0
  552. {loom_kernel-0.9.0/tests/unit/core/job → loom_kernel-0.9.2/tests/unit/core/expr}/__init__.py +0 -0
  553. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/expr/test_expr.py +0 -0
  554. {loom_kernel-0.9.0/tests/unit/core/logger → loom_kernel-0.9.2/tests/unit/core/job}/__init__.py +0 -0
  555. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/conftest.py +0 -0
  556. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/test_callback.py +0 -0
  557. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/test_context.py +0 -0
  558. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/test_handle.py +0 -0
  559. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/test_inline_service.py +0 -0
  560. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/job/test_job.py +0 -0
  561. {loom_kernel-0.9.0/tests/unit/core/model → loom_kernel-0.9.2/tests/unit/core/logger}/__init__.py +0 -0
  562. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/logger/test_config.py +0 -0
  563. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/logger/test_registry.py +0 -0
  564. {loom_kernel-0.9.0/tests/unit/core/observability → loom_kernel-0.9.2/tests/unit/core/model}/__init__.py +0 -0
  565. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/model/test_model.py +0 -0
  566. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/model/test_struct.py +0 -0
  567. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/model/test_timestamped.py +0 -0
  568. {loom_kernel-0.9.0/tests/unit/core/projection → loom_kernel-0.9.2/tests/unit/core/observability}/__init__.py +0 -0
  569. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/observability/test_observers.py +0 -0
  570. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/observability/test_runtime.py +0 -0
  571. {loom_kernel-0.9.0/tests/unit/core/repository → loom_kernel-0.9.2/tests/unit/core/projection}/__init__.py +0 -0
  572. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/projection/test_runtime.py +0 -0
  573. {loom_kernel-0.9.0/tests/unit/core/repository/abc → loom_kernel-0.9.2/tests/unit/core/repository}/__init__.py +0 -0
  574. {loom_kernel-0.9.0/tests/unit/core/repository/sqlalchemy → loom_kernel-0.9.2/tests/unit/core/repository/abc}/__init__.py +0 -0
  575. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/abc/conftest.py +0 -0
  576. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/abc/test_query.py +0 -0
  577. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/abc/test_repository_contract.py +0 -0
  578. {loom_kernel-0.9.0/tests/unit/core/routing → loom_kernel-0.9.2/tests/unit/core/repository/sqlalchemy}/__init__.py +0 -0
  579. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/sqlalchemy/conftest.py +0 -0
  580. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/sqlalchemy/test_loaders.py +0 -0
  581. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/sqlalchemy/test_repository.py +0 -0
  582. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/repository/sqlalchemy/test_transactional.py +0 -0
  583. {loom_kernel-0.9.0/tests/unit/core/tracing → loom_kernel-0.9.2/tests/unit/core/routing}/__init__.py +0 -0
  584. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/routing/test_routing.py +0 -0
  585. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/test_async_bridge.py +0 -0
  586. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/test_compiler_contracts.py +0 -0
  587. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/test_runner_contracts.py +0 -0
  588. {loom_kernel-0.9.0/tests/unit/core/uow → loom_kernel-0.9.2/tests/unit/core/tracing}/__init__.py +0 -0
  589. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/tracing/test_context.py +0 -0
  590. {loom_kernel-0.9.0/tests/unit/core/use_case → loom_kernel-0.9.2/tests/unit/core/uow}/__init__.py +0 -0
  591. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/uow/test_executor_uow.py +0 -0
  592. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/uow/test_sqlalchemy_uow.py +0 -0
  593. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/uow/test_uow_protocols.py +0 -0
  594. {loom_kernel-0.9.0/tests/unit/etl → loom_kernel-0.9.2/tests/unit/core/use_case}/__init__.py +0 -0
  595. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_compute.py +0 -0
  596. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_factory.py +0 -0
  597. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_field_ref.py +0 -0
  598. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_invoker.py +0 -0
  599. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_markers.py +0 -0
  600. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_rule.py +0 -0
  601. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/core/use_case/test_use_case.py +0 -0
  602. {loom_kernel-0.9.0/tests/unit/etl/backends → loom_kernel-0.9.2/tests/unit/etl}/__init__.py +0 -0
  603. {loom_kernel-0.9.0/tests/unit/etl/backends/test_polars → loom_kernel-0.9.2/tests/unit/etl/backends}/__init__.py +0 -0
  604. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/_historify_contract.py +0 -0
  605. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_historify_common.py +0 -0
  606. {loom_kernel-0.9.0/tests/unit/etl/backends/test_spark → loom_kernel-0.9.2/tests/unit/etl/backends/test_polars}/__init__.py +0 -0
  607. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/conftest.py +0 -0
  608. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_apply_schema.py +0 -0
  609. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_backend.py +0 -0
  610. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_dtype.py +0 -0
  611. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_file_writer.py +0 -0
  612. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_historify_polars.py +0 -0
  613. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_predicate_pushdown.py +0 -0
  614. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_reader_columns.py +0 -0
  615. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_reader_json_columns.py +0 -0
  616. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_step_execution.py +0 -0
  617. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_upsert_writer.py +0 -0
  618. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_writer_null_schema.py +0 -0
  619. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_polars/test_writer_to_frame.py +0 -0
  620. {loom_kernel-0.9.0/tests/unit/etl/checkpoint → loom_kernel-0.9.2/tests/unit/etl/backends/test_spark}/__init__.py +0 -0
  621. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/conftest.py +0 -0
  622. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/test_dtype.py +0 -0
  623. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/test_historify_spark.py +0 -0
  624. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/test_spark_apply_schema.py +0 -0
  625. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/test_step_execution.py +0 -0
  626. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_spark/test_writer_to_frame.py +0 -0
  627. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/backends/test_write_policy_historify.py +0 -0
  628. {loom_kernel-0.9.0/tests/unit/etl/checkpoint/backends → loom_kernel-0.9.2/tests/unit/etl/checkpoint}/__init__.py +0 -0
  629. {loom_kernel-0.9.0/tests/unit/etl/compiler → loom_kernel-0.9.2/tests/unit/etl/checkpoint/backends}/__init__.py +0 -0
  630. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/checkpoint/backends/test_checkpoint_polars.py +0 -0
  631. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/checkpoint/test_checkpoint_paths.py +0 -0
  632. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/checkpoint/test_cleaners.py +0 -0
  633. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/checkpoint/test_store.py +0 -0
  634. {loom_kernel-0.9.0/tests/unit/etl/io → loom_kernel-0.9.2/tests/unit/etl/compiler}/__init__.py +0 -0
  635. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_catalog_validator.py +0 -0
  636. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_compiler.py +0 -0
  637. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_compiler_catalog.py +0 -0
  638. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_compiler_upsert.py +0 -0
  639. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_errors.py +0 -0
  640. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_errors_additional_factories.py +0 -0
  641. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_errors_runtime_factories.py +0 -0
  642. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_historify_validator.py +0 -0
  643. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_param_exprs_validator.py +0 -0
  644. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_plan_traversal.py +0 -0
  645. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_step_validator.py +0 -0
  646. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_structural.py +0 -0
  647. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_temp_validator.py +0 -0
  648. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/compiler/test_upsert_validator.py +0 -0
  649. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/conftest.py +0 -0
  650. {loom_kernel-0.9.0/tests/unit/etl/io/sources → loom_kernel-0.9.2/tests/unit/etl/io}/__init__.py +0 -0
  651. {loom_kernel-0.9.0/tests/unit/etl/io/targets → loom_kernel-0.9.2/tests/unit/etl/io/sources}/__init__.py +0 -0
  652. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/sources/test_clickhouse_reader.py +0 -0
  653. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/sources/test_from_clickhouse.py +0 -0
  654. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/sources/test_from_mongo.py +0 -0
  655. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/sources/test_mongo_predicate.py +0 -0
  656. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/sources/test_mongo_reader.py +0 -0
  657. {loom_kernel-0.9.0/tests/unit/etl/schema → loom_kernel-0.9.2/tests/unit/etl/io/targets}/__init__.py +0 -0
  658. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/targets/test_clickhouse_writer.py +0 -0
  659. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/targets/test_into_clickhouse.py +0 -0
  660. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_history_target.py +0 -0
  661. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_registry.py +0 -0
  662. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_source.py +0 -0
  663. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_source_json.py +0 -0
  664. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_source_options.py +0 -0
  665. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_target.py +0 -0
  666. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_utils.py +0 -0
  667. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/io/test_variants.py +0 -0
  668. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/lineage/test_observer.py +0 -0
  669. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/lineage/test_records.py +0 -0
  670. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/lineage/test_store.py +0 -0
  671. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/pipeline/__init__.py +0 -0
  672. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/pipeline/test_pipeline_process.py +0 -0
  673. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/pipeline/test_proxy.py +0 -0
  674. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/pipeline/test_step.py +0 -0
  675. {loom_kernel-0.9.0/tests/unit/etl/sql → loom_kernel-0.9.2/tests/unit/etl/schema}/__init__.py +0 -0
  676. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/schema/test_contract.py +0 -0
  677. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/schema/test_schema.py +0 -0
  678. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/schema/test_table.py +0 -0
  679. {loom_kernel-0.9.0/tests/unit/etl/storage → loom_kernel-0.9.2/tests/unit/etl/sql}/__init__.py +0 -0
  680. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/sql/test_merge.py +0 -0
  681. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/sql/test_predicate.py +0 -0
  682. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/sql/test_predicate_dialect.py +0 -0
  683. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/sql/test_sql_runtime.py +0 -0
  684. {loom_kernel-0.9.0/tests/unit/etl/testing → loom_kernel-0.9.2/tests/unit/etl/storage}/__init__.py +0 -0
  685. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_backend_factory.py +0 -0
  686. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_io_protocols.py +0 -0
  687. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_locator.py +0 -0
  688. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_observability_and_protocols.py +0 -0
  689. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_route_build.py +0 -0
  690. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_schema_readers.py +0 -0
  691. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/storage/test_storage_config.py +0 -0
  692. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_config_loader.py +0 -0
  693. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_executor.py +0 -0
  694. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_format_registry.py +0 -0
  695. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_module_contracts.py +0 -0
  696. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_public_api_discovery.py +0 -0
  697. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_record_schema_coverage.py +0 -0
  698. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_runner.py +0 -0
  699. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_runner_errors.py +0 -0
  700. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/test_spark_testing.py +0 -0
  701. {loom_kernel-0.9.0/tests/unit/prometheus → loom_kernel-0.9.2/tests/unit/etl/testing}/__init__.py +0 -0
  702. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/testing/test_runners.py +0 -0
  703. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/testing/test_scenario_and_stubs.py +0 -0
  704. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/etl/testing/test_spark_helpers.py +0 -0
  705. {loom_kernel-0.9.0/tests/unit/rest → loom_kernel-0.9.2/tests/unit/prometheus}/__init__.py +0 -0
  706. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/prometheus/test_adapter.py +0 -0
  707. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/prometheus/test_middleware.py +0 -0
  708. {loom_kernel-0.9.0/tests/unit/streaming/bytewax → loom_kernel-0.9.2/tests/unit/rest}/__init__.py +0 -0
  709. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_autocrud.py +0 -0
  710. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_fastapi_auto_logger.py +0 -0
  711. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_middleware.py +0 -0
  712. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_pydantic_adapter.py +0 -0
  713. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_response.py +0 -0
  714. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_rest_adapter.py +0 -0
  715. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_rest_compiler.py +0 -0
  716. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_rest_model.py +0 -0
  717. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/rest/test_router_runtime.py +0 -0
  718. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/__init__.py +0 -0
  719. {loom_kernel-0.9.0/tests/unit/streaming/compiler → loom_kernel-0.9.2/tests/unit/streaming/bytewax}/__init__.py +0 -0
  720. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/cases.py +0 -0
  721. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/conftest.py +0 -0
  722. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_adapter.py +0 -0
  723. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_batch_key.py +0 -0
  724. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_bytewax_dispatcher.py +0 -0
  725. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_collect_batch.py +0 -0
  726. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_dlq.py +0 -0
  727. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_error_boundary.py +0 -0
  728. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_operators.py +0 -0
  729. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_resource_manager.py +0 -0
  730. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_runtime_io.py +0 -0
  731. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_runtime_sink.py +0 -0
  732. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_runtime_source.py +0 -0
  733. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_steps.py +0 -0
  734. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/bytewax/test_storage.py +0 -0
  735. {loom_kernel-0.9.0/tests/unit/streaming/contracts → loom_kernel-0.9.2/tests/unit/streaming/compiler}/__init__.py +0 -0
  736. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/cases.py +0 -0
  737. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_async_walk.py +0 -0
  738. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_basics.py +0 -0
  739. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_config_bindings.py +0 -0
  740. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_mongo_source.py +0 -0
  741. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_multi_source.py +0 -0
  742. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_router.py +0 -0
  743. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_window.py +0 -0
  744. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/compiler/test_with.py +0 -0
  745. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/conftest.py +0 -0
  746. {loom_kernel-0.9.0/tests/unit/streaming/nodes → loom_kernel-0.9.2/tests/unit/streaming/contracts}/__init__.py +0 -0
  747. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/cases.py +0 -0
  748. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/test_boundary.py +0 -0
  749. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/test_message.py +0 -0
  750. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/test_mongo_contracts.py +0 -0
  751. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/test_multi_boundary.py +0 -0
  752. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/contracts/test_steps.py +0 -0
  753. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/__init__.py +0 -0
  754. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/__init__.py +0 -0
  755. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/batch.py +0 -0
  756. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/explode.py +0 -0
  757. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/fork.py +0 -0
  758. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/router.py +0 -0
  759. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/shared.py +0 -0
  760. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/cases/simple.py +0 -0
  761. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/conftest.py +0 -0
  762. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/test_compiler_examples.py +0 -0
  763. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/flows/test_flow_examples.py +0 -0
  764. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/__init__.py +0 -0
  765. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/cases.py +0 -0
  766. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/conftest.py +0 -0
  767. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/fakes.py +0 -0
  768. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_client.py +0 -0
  769. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_config.py +0 -0
  770. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_key_resolver.py +0 -0
  771. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_message.py +0 -0
  772. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_message_client.py +0 -0
  773. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_multi_wire.py +0 -0
  774. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_observability.py +0 -0
  775. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_settings.py +0 -0
  776. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/kafka/test_wire.py +0 -0
  777. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/mongo/test_bytewax_source.py +0 -0
  778. {loom_kernel-0.9.0/tests/unit/streaming/observability → loom_kernel-0.9.2/tests/unit/streaming/nodes}/__init__.py +0 -0
  779. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/nodes/conftest.py +0 -0
  780. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/nodes/test_broadcast.py +0 -0
  781. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/nodes/test_delta_config.py +0 -0
  782. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/nodes/test_logging.py +0 -0
  783. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/nodes/test_table_package.py +0 -0
  784. {loom_kernel-0.9.0/tests/unit/streaming/support → loom_kernel-0.9.2/tests/unit/streaming/observability}/__init__.py +0 -0
  785. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/cases.py +0 -0
  786. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/conftest.py +0 -0
  787. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/test_observability_runner.py +0 -0
  788. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/test_protocols.py +0 -0
  789. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/test_registry.py +0 -0
  790. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/observability/test_structlog.py +0 -0
  791. {loom_kernel-0.9.0/tests/unit/testing → loom_kernel-0.9.2/tests/unit/streaming/support}/__init__.py +0 -0
  792. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/support/flow_cases.py +0 -0
  793. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_expand_routes.py +0 -0
  794. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_fork.py +0 -0
  795. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_otel_observability.py +0 -0
  796. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_routing.py +0 -0
  797. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_testing_mongo.py +0 -0
  798. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/streaming/test_with.py +0 -0
  799. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/testing/test_golden.py +0 -0
  800. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/testing/test_http_harness.py +0 -0
  801. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/testing/test_in_memory.py +0 -0
  802. {loom_kernel-0.9.0 → loom_kernel-0.9.2}/tests/unit/testing/test_runner.py +0 -0
@@ -19,10 +19,11 @@ on:
19
19
  - ".github/workflows/docs.yml"
20
20
  workflow_dispatch:
21
21
 
22
- # Prevent concurrent deploys; let an in-progress run finish.
22
+ # PRs use a per-PR group so they never block or wait on the Pages deploy lock.
23
+ # Push/dispatch use the shared 'pages' group to serialise concurrent deploys.
23
24
  concurrency:
24
- group: pages
25
- cancel-in-progress: false
25
+ group: ${{ github.event_name == 'pull_request' && format('docs-pr-{0}', github.event.pull_request.number) || 'pages' }}
26
+ cancel-in-progress: ${{ github.event_name == 'pull_request' }}
26
27
 
27
28
  jobs:
28
29
  build:
@@ -1,98 +1,69 @@
1
- # 🚀 Release 0.9.0 ([#32](https://github.com/the-reacher-data/loom-py/pull/32)) ([`14072d1`](https://github.com/the-reacher-data/loom-py/commit/14072d1be9212116235f26d7a2590a4f0e622451))
1
+ # 🚀 Release 0.9.2 ([#39](https://github.com/the-reacher-data/loom-py/pull/39)) ([`f1a482d`](https://github.com/the-reacher-data/loom-py/commit/f1a482d03f8b83f8e0c7725e7af6160466ac6126))
2
2
 
3
3
 
4
4
  ## ✨ Features
5
- ### streaming
6
- - **streaming:** add Mongo CDC source
7
- - **streaming:** add MongoObjectId and MongoDBRef domain types<br>
8
- > Replace opaque str/dict BSON normalization with structured domain types:
9
- > MongoObjectId(id, created_at_ms) preserves ObjectId hex and creation
10
- > timestamp extracted from the embedded 4-byte BSON timestamp field
11
- > MongoDBRef(id, collection, database) models cross-collection references
12
- > with explicit collection and optional database fields
13
- > MongoCDCEvent.document_id widened to MongoObjectId | str | None to
14
- > expose rich type when _id is an ObjectId
15
- > _normalize_objectid and _normalize_dbref updated to produce the new types
16
- > Guard clause added to _normalize_dbref for None identifier
17
- > _message_key helper centralizes MongoObjectId → str key extraction
18
- > MongoObjectId and MongoDBRef exported from loom.streaming public API
19
- > Contract tests cover DBRef without database, integer id, None id error,
20
- > and ObjectId without generation_time (created_at_ms=None)
21
-
22
- - **streaming:** add Backend.CLICKHOUSE with native clickhouse-connect sink<br>
23
- > Add _ClickHouseTablePartition as a standalone SinkPartition backed by
24
- > clickhouse-connect (HTTP/2, no SQLAlchemy). Uses a column-oriented buffer
25
- > layout matching clickhouse-connect's column_oriented=True path, avoiding
26
- > the internal pivot() transposition for maximum insert throughput.
27
- > Resolves the _json_serializer crash that occurred when inserting list[str]
28
- > fields via the SQLAlchemy backend against ClickHouseDialect_asynch. With the
29
- > native client, Array(String) and all CH-native types work without workarounds.
30
-
31
- - **streaming:** add ExpandRoutes fan-out node and JsonStr semantic type<br>
32
- > ExpandRoutes: expands one event once via PayloadExpander and routes each
33
- > typed output list to its own independent Process (dict-based API, optional
34
- > default route); wired in Bytewax via flat_map per route branch
35
- > JsonStr: Annotated[str, _JsonMarker()] sentinel type for raw JSON fields;
36
- > mapped to Text() in SQLAlchemy; passes through as str in ClickHouse/Delta
37
- > ProcessNode union extended to include ExpandRoutes[Any]
5
+ ### config
6
+ - **config:** add SecretsManagerResolver + shared resolver utilities
38
7
 
39
8
 
40
9
 
41
- ## 🐛 Fixes
42
- ### streaming
43
- - **streaming:** replace assert with explicit TypeError in _adapter.py<br>
44
- > Bandit B101: assert statements are stripped when running with -O.
45
- > Replaced both isinstance asserts with explicit TypeError raises to
46
- > preserve the runtime invariant checks under all execution modes.
47
10
 
48
- - **streaming:** age-based buffer flush never fired in IntoTable sink partitions<br>
49
- > Two bugs prevented buffer_max_age_s from triggering a flush:
50
- > 1. write_batch([]) returned immediately on empty epochs, so quiet periods
51
- > never checked the age threshold.
52
- > 2. _last_append_at was updated right before _should_flush(), making the
53
- > elapsed-time expression always ≈0ms.
54
- > Replace _last_append_at with _buffer_started_at (set when the buffer
55
- > transitions from empty, reset after each flush) in both
56
- > _SQLAlchemyTablePartition and _DeltaTablePartition. Empty epoch calls
57
- > now check for an age-based flush before returning.
58
11
 
59
- - **streaming:** wire ExpandRoutes runtime and ClickHouse HTTP URL resolution
60
12
 
61
- ### compiler
62
- - **compiler:** add Backend.CLICKHOUSE dispatch in build_plan storage sink resolver
63
- - **compiler:** validate ExpandRoutes branches for terminal output detection
64
13
 
65
14
 
66
15
 
67
16
 
68
- ## ♻️ Refactor
17
+
18
+ # 🚀 Release 0.9.1 ([#36](https://github.com/the-reacher-data/loom-py/pull/36)) ([`5c420c9`](https://github.com/the-reacher-data/loom-py/commit/5c420c9dd4efe0f697affb8a921054bc6504358f))
19
+
20
+
21
+ ## ✨ Features
69
22
  ### streaming
70
- - **streaming:** improve Mongo CDC architecture compliance<br>
71
- > Replace bare except Exception with specific OperationFailure catch
72
- > Replace type(x).__name__ string dispatch with isinstance and lazy import
73
- > Type watch_options as Mapping[str, object] to eliminate implicit Any
74
- > Introduce _BSON_NORMALIZERS dispatch map in normalize_bson_value
75
- > Define _ChangeStream and _DatabaseLike Protocols for PyMongo types
76
- > Make FromMongoCDC generic with covariant MongoCDCPayloadT (PEP 696)
77
- > Add needs_decode: ClassVar[bool] to compiled source types
78
- > Replace isinstance type-switches with dispatch maps (_SOURCE_BUILDERS,
79
- > _RUNTIME_SOURCE_BUILDERS) across compiler and bytewax runtime layers
80
- > Declare typing_extensions>=4.12 as direct dependency
81
- > Add contract tests for FromMongoCDC generic parametrization
82
-
83
- - **streaming:** simplify source dispatch and pymongo error handling<br>
84
- > Replace _RUNTIME_SOURCE_BUILDERS dispatch map with direct isinstance check in build_runtime_source
85
- > Replace lazy _operation_failure_type() with module-level try/except import for OperationFailure
86
- > Use explicit isinstance in _source_topic_or_none instead of getattr duck-typing
87
- > Remove redundant empty-collections branch in _open_change_stream
88
- > Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
23
+ - **streaming:** add register_sink to StreamingRunner<br>
24
+ > Allows applications to declare sinks once via register_sink(cls) and
25
+ > let the runner resolve them from YAML config at startup, eliminating
26
+ > manual sink wiring in entrypoints.
27
+ > New public API:
28
+ > runner = StreamingRunner()
29
+ > runner.register_sink(ClickHouseErrorTableSink)
30
+ > runner.run(flow=build_flow(), config_path=streaming_config_path())
31
+ > Sink classes satisfy the RegisteredSink protocol (sink_type, config_type,
32
+ > build_binding). The runner matches YAML entries by type field, deserializes
33
+ > each section with config_type, and calls build_binding(cfg, ctx).
34
+ > Adds DuplicateErrorSinkError for conflicting ErrorKind assignments.
35
+ > Adds STREAMING_SINKS to ConfigKey.
36
+ > StreamingRunner.__init__ is now no-arg; factory methods unchanged.
37
+ > prepare_run(error_sinks=...) remains supported for tests and overrides.
89
38
 
90
39
 
40
+ ### config
41
+ - **config:** add SSM dot-notation key navigation and resolve logging<br>
42
+ > _split_ssm_key splits /path/param.key into SSM path + JSON key list
43
+ > _navigate_json parses SSM value as JSON and traverses key path
44
+ > resolve() emits INFO log with expanded SSM path (never the value)
45
+ > ConfigResolver.resolve() widened to -> object (str <= object, LSP-safe)
46
+ > Guard against empty key with explicit ConfigError
91
47
 
92
48
 
93
- ## ✅ Tests
94
- ### streaming
95
- - **streaming:** add unit tests for ExpandRoutes fan-out node
49
+
50
+ ## 🐛 Fixes
51
+ ### tests
52
+ - **tests:** guard received[0] index access in test_sink_registry
53
+
54
+
55
+
56
+
57
+
58
+
59
+
60
+ ## 🛠 Chores
61
+ ### release
62
+ - **release:** sync pyproject.toml version to 0.9.0<br>
63
+ > The v0.9.0 tag was created by a hotfix but the version bump PR did not
64
+ > merge cleanly, leaving pyproject.toml stuck at 0.8.0 on master. This
65
+ > aligns the declared version with the existing tag so the next release
66
+ > computes 0.10.0 instead of colliding with v0.9.0.
96
67
 
97
68
 
98
69
 
@@ -0,0 +1,15 @@
1
+ # 🚀 Release 0.9.2 ([#39](https://github.com/the-reacher-data/loom-py/pull/39)) ([`f1a482d`](https://github.com/the-reacher-data/loom-py/commit/f1a482d03f8b83f8e0c7725e7af6160466ac6126))
2
+
3
+
4
+ ## ✨ Features
5
+ ### config
6
+ - **config:** add SecretsManagerResolver + shared resolver utilities
7
+
8
+
9
+
10
+
11
+
12
+
13
+
14
+
15
+
@@ -1,8 +1,9 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: loom-kernel
3
- Version: 0.9.0
3
+ Version: 0.9.2
4
4
  Summary: Loom Python project
5
5
  License-File: LICENSE
6
+ Classifier: Typing :: Typed
6
7
  Requires-Python: >=3.11
7
8
  Requires-Dist: aiocache<1.0,>=0.12
8
9
  Requires-Dist: msgspec<1.0,>=0.18
@@ -22,6 +23,10 @@ Requires-Dist: clickhouse-connect<1.0,>=0.7; extra == 'clickhouse'
22
23
  Provides-Extra: config
23
24
  Requires-Dist: fsspec>=2024.2.0; extra == 'config'
24
25
  Requires-Dist: omegaconf<3.0,>=2.3; extra == 'config'
26
+ Provides-Extra: config-ssm
27
+ Requires-Dist: boto3>=1.35; extra == 'config-ssm'
28
+ Requires-Dist: fsspec>=2024.2.0; extra == 'config-ssm'
29
+ Requires-Dist: omegaconf<3.0,>=2.3; extra == 'config-ssm'
25
30
  Provides-Extra: etl-otel
26
31
  Requires-Dist: opentelemetry-api<2.0,>=1.20; extra == 'etl-otel'
27
32
  Requires-Dist: opentelemetry-exporter-otlp-proto-grpc<2.0,>=1.20; extra == 'etl-otel'
@@ -1,9 +1,12 @@
1
1
  [project]
2
2
  name = "loom-kernel"
3
- version = "0.9.0"
3
+ version = "0.9.2"
4
4
  description = "Loom Python project"
5
5
  readme = "README.md"
6
6
  requires-python = ">=3.11"
7
+ classifiers = [
8
+ "Typing :: Typed",
9
+ ]
7
10
  dependencies = [
8
11
  "msgspec>=0.18,<1.0",
9
12
  "structlog>=24.4,<26.0",
@@ -32,6 +35,11 @@ config = [
32
35
  "omegaconf>=2.3,<3.0",
33
36
  "fsspec>=2024.2.0",
34
37
  ]
38
+ config-ssm = [
39
+ "omegaconf>=2.3,<3.0",
40
+ "fsspec>=2024.2.0",
41
+ "boto3>=1.35",
42
+ ]
35
43
  cache = [
36
44
  "aiocache>=0.12,<1.0",
37
45
  "omegaconf>=2.3,<3.0",
@@ -129,6 +137,7 @@ dev = [
129
137
  "findspark>=2.0.1",
130
138
  "confluent-kafka>=2.6,<3.0",
131
139
  "bytewax>=0.21",
140
+ "boto3>=1.35",
132
141
  "pymongo>=4.6,<5.0",
133
142
  "opentelemetry-api>=1.20,<2.0",
134
143
  "opentelemetry-sdk>=1.20,<2.0",
@@ -140,6 +149,9 @@ dev = [
140
149
  packages = [
141
150
  "src/loom",
142
151
  ]
152
+ include = [
153
+ "src/loom/py.typed",
154
+ ]
143
155
 
144
156
  [tool.ruff]
145
157
  line-length = 100
@@ -235,7 +247,7 @@ markers = [
235
247
 
236
248
  [tool.commitizen]
237
249
  name = "cz_conventional_commits"
238
- version = "0.9.0"
250
+ version = "0.9.2"
239
251
  tag_format = "v$version"
240
252
  version_files = [
241
253
  "pyproject.toml:project.version",
@@ -20,6 +20,8 @@ from loom.core.config.keys import ConfigKey
20
20
  from loom.core.config.loader import load_config, section
21
21
  from loom.core.config.observability import OtelConfig
22
22
  from loom.core.config.resolver import ConfigResolver
23
+ from loom.core.config.secrets import SecretsManagerResolver
24
+ from loom.core.config.ssm import SsmResolver
23
25
 
24
26
  __all__ = [
25
27
  "ConfigBinding",
@@ -29,6 +31,8 @@ __all__ = [
29
31
  "ConfigResolver",
30
32
  "Configurable",
31
33
  "OtelConfig",
34
+ "SecretsManagerResolver",
35
+ "SsmResolver",
32
36
  "StructBinder",
33
37
  "load_config",
34
38
  "section",
@@ -0,0 +1,116 @@
1
+ """Shared utilities for config resolvers (SSM, Secrets Manager, etc.)."""
2
+
3
+ from __future__ import annotations
4
+
5
+ import json
6
+ import os
7
+ import re
8
+
9
+ from loom.core.config.errors import ConfigError
10
+
11
+ _ENV_VAR_PATTERN = re.compile(r"%([A-Z][A-Z0-9_]*)%")
12
+
13
+
14
+ def _expand_env_vars(key: str) -> str:
15
+ """Expand ``%VAR_NAME%`` placeholders in *key* using environment variables.
16
+
17
+ Only uppercase identifiers matching ``[A-Z][A-Z0-9_]*`` are expanded.
18
+ The ``%VAR%`` syntax avoids conflicts with OmegaConf's ANTLR grammar,
19
+ which rejects bare ``{`` inside ``${resolver:...}`` interpolations.
20
+
21
+ Args:
22
+ key: Resolver path, possibly containing ``%VAR_NAME%`` tokens.
23
+
24
+ Returns:
25
+ Path with all tokens replaced by their environment variable values.
26
+
27
+ Raises:
28
+ ConfigError: When a referenced variable is absent from the environment.
29
+ """
30
+ if not _ENV_VAR_PATTERN.search(key):
31
+ return key
32
+
33
+ def _replace(match: re.Match[str]) -> str:
34
+ var_name = match.group(1)
35
+ value = os.environ.get(var_name)
36
+ if value is None:
37
+ raise ConfigError(
38
+ f"Env var {var_name!r} not found in environment "
39
+ f"(referenced in resolver path {key!r})"
40
+ )
41
+ return value
42
+
43
+ return _ENV_VAR_PATTERN.sub(_replace, key)
44
+
45
+
46
+ def _split_resolver_key(key: str) -> tuple[str, list[str]]:
47
+ """Split a resolver key into the base path and JSON navigation keys.
48
+
49
+ The first dot after the last '/' separator marks the start of a JSON key
50
+ path. Both SSM and Secrets Manager use '/' as path separator, so a dot
51
+ is unambiguously a JSON navigation token.
52
+
53
+ Note: ARN-style SecretIds (``arn:aws:secretsmanager:...``) are not
54
+ supported for dot-notation — use short names instead.
55
+
56
+ **Limitation — env-var values with dots in the final path segment:**
57
+ If a ``%VAR%`` token expands to a value that contains a dot *and* that
58
+ token appears in the last path segment (after the final ``/``), the dot
59
+ will be interpreted as a JSON navigation separator, producing a confusing
60
+ ``ConfigError``. Example: ``/app/svc/%ENV%`` where ``ENV=db.prod`` becomes
61
+ ``/app/svc/db`` with JSON key ``["prod"]``. Use env-var tokens only in
62
+ path segments that are guaranteed to be dot-free (environment names,
63
+ region codes, etc.).
64
+
65
+ Args:
66
+ key: Expanded resolver key, e.g. ``"/app/prod/db_config.host"``.
67
+
68
+ Returns:
69
+ A 2-tuple ``(base_path, json_keys)`` where *base_path* is the path
70
+ to fetch and *json_keys* is a list of dict keys to navigate
71
+ (empty list when no dot-notation is present).
72
+ """
73
+ if not key:
74
+ return key, []
75
+ last_slash = key.rfind("/")
76
+ after_last_slash = key[last_slash + 1 :] if last_slash != -1 else key
77
+ dot_pos = after_last_slash.find(".")
78
+ if dot_pos == -1:
79
+ return key, []
80
+ base_end = (last_slash + 1 + dot_pos) if last_slash != -1 else dot_pos
81
+ json_tail = key[base_end + 1 :]
82
+ return key[:base_end], [k for k in json_tail.split(".") if k]
83
+
84
+
85
+ def _navigate_json(raw: str, keys: list[str], path: str) -> object:
86
+ """Parse *raw* as JSON and navigate to the value at *keys*.
87
+
88
+ Args:
89
+ raw: Raw string value from the resolver backend.
90
+ keys: Ordered list of dict keys to traverse.
91
+ path: Original path, used only in error messages.
92
+
93
+ Returns:
94
+ The value at the navigated position. May be any JSON-compatible type.
95
+
96
+ Raises:
97
+ ConfigError: When *raw* is not valid JSON, or a key is absent.
98
+ """
99
+ try:
100
+ data: object = json.loads(raw)
101
+ except json.JSONDecodeError as exc:
102
+ # Suppress chain (from None) — JSONDecodeError.doc holds the raw secret
103
+ # and would be exposed via __cause__ in tracebacks / APM serialisation.
104
+ raise ConfigError(
105
+ f"Resolver path {path!r} value is not valid JSON "
106
+ f"(required for key navigation): {exc.msg} at position {exc.pos}"
107
+ ) from None
108
+ current: object = data
109
+ for k in keys:
110
+ if not isinstance(current, dict) or k not in current:
111
+ raise ConfigError(f"Key {k!r} not found at resolver path {path!r}")
112
+ current = current[k]
113
+ return current
114
+
115
+
116
+ __all__ = ["_expand_env_vars", "_split_resolver_key", "_navigate_json"]
@@ -24,6 +24,7 @@ class ConfigKey(StrEnum):
24
24
  STORAGE = "storage"
25
25
  STREAMING = "streaming"
26
26
  STREAMING_RUNTIME = "streaming.runtime"
27
+ STREAMING_SINKS = "streaming.sinks"
27
28
  OBSERVABILITY = "observability"
28
29
  LOGGER = "logger"
29
30
  METRICS = "metrics"
@@ -212,7 +212,7 @@ def _register_resolvers(resolvers: Sequence[Any], omega_conf: Any) -> None:
212
212
  """
213
213
  for resolver in resolvers:
214
214
  with contextlib.suppress(Exception):
215
- omega_conf.register_new_resolver(resolver.name, resolver.resolve)
215
+ omega_conf.register_new_resolver(resolver.name, resolver.resolve, use_cache=True)
216
216
 
217
217
 
218
218
  def load_config(
@@ -18,6 +18,15 @@ YAML placeholders::
18
18
  The resolver name becomes the placeholder prefix. Values are resolved
19
19
  when OmegaConf materialises the config — i.e. at job startup, so secret
20
20
  rotation takes effect on the next run without redeployment.
21
+
22
+ Built-in resolvers
23
+ ------------------
24
+ :class:`~loom.core.config.ssm.SsmResolver` is the bundled implementation
25
+ for AWS SSM Parameter Store. Install ``loom[config-ssm]`` to use it::
26
+
27
+ from loom.core.config import load_config, SsmResolver
28
+
29
+ cfg = load_config("config/prod.yaml", resolvers=[SsmResolver()])
21
30
  """
22
31
 
23
32
  from __future__ import annotations
@@ -32,22 +41,19 @@ class ConfigResolver(Protocol):
32
41
  Implementors provide a *name* (used as the OmegaConf placeholder prefix)
33
42
  and a *resolve* callable that fetches the actual value at parse time.
34
43
 
35
- Example::
36
-
37
- class SsmResolver:
38
- name = "ssm"
44
+ See :class:`~loom.core.config.ssm.SsmResolver` for the bundled AWS SSM
45
+ implementation. Custom resolvers only need to satisfy this two-member
46
+ protocol::
39
47
 
40
- def __init__(self, region: str) -> None:
41
- self._region = region
48
+ class VaultResolver:
49
+ @property
50
+ def name(self) -> str:
51
+ return "vault"
42
52
 
43
- def resolve(self, key: str) -> str:
44
- import boto3
45
- client = boto3.client("ssm", region_name=self._region)
46
- return client.get_parameter(Name=key, WithDecryption=True)[
47
- "Parameter"
48
- ]["Value"]
53
+ def resolve(self, key: str) -> object:
54
+ return vault_client.read_secret(key)
49
55
 
50
- cfg = load_config("s3://bucket/prod.yaml", resolvers=[SsmResolver("eu-west-1")])
56
+ cfg = load_config("config/prod.yaml", resolvers=[VaultResolver()])
51
57
  """
52
58
 
53
59
  @property
@@ -62,7 +68,7 @@ class ConfigResolver(Protocol):
62
68
  """
63
69
  ...
64
70
 
65
- def resolve(self, key: str) -> str:
71
+ def resolve(self, key: str) -> object:
66
72
  """Resolve *key* to its string value.
67
73
 
68
74
  Called by OmegaConf when materialising ``${<name>:key}``
@@ -74,7 +80,8 @@ class ConfigResolver(Protocol):
74
80
  (e.g. ``"/prod/token"`` for ``${ssm:/prod/token}``).
75
81
 
76
82
  Returns:
77
- Resolved string value.
83
+ Resolved value. Typically a string, but may be a structured type
84
+ when the resolver supports JSON navigation.
78
85
  """
79
86
  ...
80
87
 
@@ -0,0 +1,144 @@
1
+ """AWS Secrets Manager resolver for loom configuration.
2
+
3
+ Resolves ``${secrets:/path/to/secret}`` placeholders in OmegaConf configs
4
+ by fetching values from AWS Secrets Manager at parse time.
5
+
6
+ Example::
7
+
8
+ from loom.core.config import load_config
9
+ from loom.core.config.secrets import SecretsManagerResolver
10
+
11
+ cfg = load_config("config/prod.yaml", resolvers=[SecretsManagerResolver("eu-west-1")])
12
+ """
13
+
14
+ from __future__ import annotations
15
+
16
+ import logging
17
+ from typing import Any
18
+
19
+ try:
20
+ import boto3 as _boto3_module # type: ignore[import-untyped]
21
+ except ImportError:
22
+ _boto3_module = None
23
+
24
+ from loom.core.config._resolver_utils import (
25
+ _expand_env_vars,
26
+ _navigate_json,
27
+ _split_resolver_key,
28
+ )
29
+ from loom.core.config.errors import ConfigError
30
+
31
+ logger = logging.getLogger(__name__)
32
+
33
+
34
+ def _fetch_secret(client: Any, name: str) -> str:
35
+ """Fetch a string secret value from AWS Secrets Manager.
36
+
37
+ Args:
38
+ client: Boto3 secretsmanager client.
39
+ name: Secret name or short ARN. ARN-style names are supported for
40
+ plain fetches but not for dot-notation JSON navigation.
41
+
42
+ Returns:
43
+ The secret value as a string.
44
+
45
+ Raises:
46
+ ConfigError: When the secret is binary, or on any API error.
47
+ """
48
+ try:
49
+ result = client.get_secret_value(SecretId=name)
50
+ except Exception as exc:
51
+ raise ConfigError(f"Failed to fetch Secrets Manager secret {name!r}: {exc}") from exc
52
+ if "SecretString" not in result:
53
+ raise ConfigError(
54
+ f"Secrets Manager secret {name!r} is binary — only string secrets are supported"
55
+ )
56
+ return str(result["SecretString"])
57
+
58
+
59
+ class SecretsManagerResolver:
60
+ """Resolves AWS Secrets Manager paths for use with :func:`~loom.core.config.load_config`.
61
+
62
+ Fetches secret values from AWS Secrets Manager. The boto3 client is
63
+ created lazily on first use and reused across calls.
64
+
65
+ Env-var tokens in the form ``%VAR_NAME%`` (uppercase letters, digits,
66
+ and underscores only) are expanded from ``os.environ`` before the
67
+ request is made.
68
+
69
+ Args:
70
+ region: AWS region name. Passed directly to ``boto3.client``.
71
+ Defaults to ``None``, which lets boto3 use its own resolution
72
+ chain (env vars, instance metadata, etc.).
73
+
74
+ Example::
75
+
76
+ resolver = SecretsManagerResolver("eu-west-1")
77
+ value = resolver.resolve("/myapp/%ENV%/db_password")
78
+ """
79
+
80
+ def __init__(self, region: str | None = None) -> None:
81
+ self._region = region
82
+ self._client: Any = None
83
+
84
+ @property
85
+ def name(self) -> str:
86
+ """OmegaConf resolver prefix.
87
+
88
+ Returns:
89
+ The string ``"secrets"``.
90
+ """
91
+ return "secrets"
92
+
93
+ def _get_client(self) -> Any:
94
+ """Return the boto3 secretsmanager client, creating it on first call.
95
+
96
+ Returns:
97
+ A boto3 secretsmanager client instance.
98
+
99
+ Raises:
100
+ ConfigError: When boto3 is not installed.
101
+ """
102
+ if self._client is None:
103
+ if _boto3_module is None:
104
+ raise ConfigError(
105
+ "boto3 is required for SecretsManagerResolver. "
106
+ "Install it with: pip install loom[config-ssm]"
107
+ )
108
+ self._client = _boto3_module.client("secretsmanager", region_name=self._region)
109
+ return self._client
110
+
111
+ def resolve(self, key: str) -> object:
112
+ """Resolve an AWS Secrets Manager path to its stored value.
113
+
114
+ Expands ``%VAR_NAME%`` tokens in *key* from the environment, then
115
+ fetches the secret from AWS Secrets Manager.
116
+
117
+ Args:
118
+ key: Secret path, optionally containing ``%VAR_NAME%``
119
+ placeholders that are replaced with environment variable values.
120
+ Supports dot-notation for JSON key navigation: ``/path/secret.key``
121
+ fetches ``/path/secret`` and returns ``secret["key"]``.
122
+
123
+ Returns:
124
+ Resolved value. A plain string for secrets without dot-notation;
125
+ a structured value (string, int, dict, etc.) when dot-notation
126
+ navigates into a JSON secret.
127
+
128
+ Raises:
129
+ ConfigError: When *key* is empty, an env-var placeholder is
130
+ missing, boto3 is not installed, the secret is binary,
131
+ or the API call fails.
132
+ """
133
+ if not key:
134
+ raise ConfigError("Secrets Manager key must not be empty")
135
+ expanded = _expand_env_vars(key)
136
+ path, json_keys = _split_resolver_key(expanded)
137
+ logger.info("secrets_resolver: fetching %s", path)
138
+ raw = _fetch_secret(self._get_client(), path)
139
+ if not json_keys:
140
+ return raw
141
+ return _navigate_json(raw, json_keys, path)
142
+
143
+
144
+ __all__ = ["SecretsManagerResolver"]