modwire 9.2.1__tar.gz → 9.2.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 (365) hide show
  1. {modwire-9.2.1 → modwire-9.2.2}/.dev/modwire.egg-info/SOURCES.txt +3 -2
  2. {modwire-9.2.1 → modwire-9.2.2}/PKG-INFO +1 -1
  3. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/application.py +2 -1
  4. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/application.py +17 -23
  5. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/cache_outcome.py +1 -10
  6. modwire-9.2.2/src/modwire/cli/cache/models/cache_stage.py +9 -0
  7. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/cached_result.py +2 -1
  8. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/services/cache_identity.py +1 -1
  9. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/domain.py +1 -1
  10. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/batch_source_reader.py +2 -2
  11. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/base_test.py +1 -1
  12. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/insights/base_test.py +2 -2
  13. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/insights/test_02_invariants.py +19 -10
  14. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/shape/base_test.py +3 -1
  15. modwire-9.2.2/tests/architecture/shape/test_01_limits.py +178 -0
  16. {modwire-9.2.1 → modwire-9.2.2}/tests/shared/code/test_02_invariants.py +12 -9
  17. {modwire-9.2.1 → modwire-9.2.2}/tests/support/code_map.py +17 -24
  18. modwire-9.2.1/tests/architecture/shape/test_01_limits.py +0 -126
  19. {modwire-9.2.1 → modwire-9.2.2}/.github/workflows/ci.yml +0 -0
  20. {modwire-9.2.1 → modwire-9.2.2}/.github/workflows/release.yml +0 -0
  21. {modwire-9.2.1 → modwire-9.2.2}/.gitignore +0 -0
  22. {modwire-9.2.1 → modwire-9.2.2}/AGENTS.md +0 -0
  23. {modwire-9.2.1 → modwire-9.2.2}/LICENSE +0 -0
  24. {modwire-9.2.1 → modwire-9.2.2}/MANIFEST.in +0 -0
  25. {modwire-9.2.1 → modwire-9.2.2}/Makefile +0 -0
  26. {modwire-9.2.1 → modwire-9.2.2}/README.md +0 -0
  27. {modwire-9.2.1 → modwire-9.2.2}/docs/target-language-ownership.md +0 -0
  28. {modwire-9.2.1 → modwire-9.2.2}/pyproject.toml +0 -0
  29. {modwire-9.2.1 → modwire-9.2.2}/scripts/check_extractors.py +0 -0
  30. {modwire-9.2.1 → modwire-9.2.2}/scripts/generate_docs.py +0 -0
  31. {modwire-9.2.1 → modwire-9.2.2}/scripts/verify_consumer.py +0 -0
  32. {modwire-9.2.1 → modwire-9.2.2}/setup.cfg +0 -0
  33. {modwire-9.2.1 → modwire-9.2.2}/setup.py +0 -0
  34. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/__init__.py +0 -0
  35. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/__main__.py +0 -0
  36. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/__init__.py +0 -0
  37. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/__init__.py +0 -0
  38. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/application.py +0 -0
  39. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/domain.py +0 -0
  40. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/models/__init__.py +0 -0
  41. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/models/edge_rule_violation.py +0 -0
  42. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/models/flow_report.py +0 -0
  43. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/models/flow_violation.py +0 -0
  44. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/models/types.py +0 -0
  45. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/__init__.py +0 -0
  46. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/backward_flow_analyzer.py +0 -0
  47. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/boundaries_flow_analyzer.py +0 -0
  48. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/module_boundary_analyzer.py +0 -0
  49. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/no_cycles_flow_analyzer.py +0 -0
  50. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/boundaries/services/no_reentry_flow_analyzer.py +0 -0
  51. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/__init__.py +0 -0
  52. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/application.py +0 -0
  53. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/__init__.py +0 -0
  54. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/architecture_config.py +0 -0
  55. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/boundaries_config.py +0 -0
  56. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/boundary_rule.py +0 -0
  57. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/configuration_value.py +0 -0
  58. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/flow_realm.py +0 -0
  59. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/flow_rules.py +0 -0
  60. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/shape_config.py +0 -0
  61. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/shape_realm.py +0 -0
  62. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/shape_rules.py +0 -0
  63. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/config/models/tag_rule.py +0 -0
  64. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/facade.py +0 -0
  65. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/__init__.py +0 -0
  66. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/application.py +0 -0
  67. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/domain.py +0 -0
  68. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/__init__.py +0 -0
  69. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/callable_report_entry.py +0 -0
  70. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/callables_report.py +0 -0
  71. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/clusters_report.py +0 -0
  72. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/clusters_report_item.py +0 -0
  73. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/coherence_report.py +0 -0
  74. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/exports_report.py +0 -0
  75. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/exports_report_item.py +0 -0
  76. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/hotspots_report.py +0 -0
  77. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/hotspots_report_item.py +0 -0
  78. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/models/insight_report.py +0 -0
  79. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/__init__.py +0 -0
  80. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/callables_reporter.py +0 -0
  81. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/clusters_reporter.py +0 -0
  82. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/coherence_reporter.py +0 -0
  83. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/exports_reporter.py +0 -0
  84. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/hotspots_reporter.py +0 -0
  85. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/insights/services/insight_report_field_map.py +0 -0
  86. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/__init__.py +0 -0
  87. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/application.py +0 -0
  88. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/domain.py +0 -0
  89. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/models/__init__.py +0 -0
  90. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/models/architecture_map.py +0 -0
  91. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/models/architecture_realm.py +0 -0
  92. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/models/tag_map.py +0 -0
  93. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/models/tag_match.py +0 -0
  94. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/services/__init__.py +0 -0
  95. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/services/architecture_map_loader.py +0 -0
  96. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/map/services/tag_matcher.py +0 -0
  97. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/__init__.py +0 -0
  98. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/application.py +0 -0
  99. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/domain.py +0 -0
  100. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/__init__.py +0 -0
  101. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/architecture_group.py +0 -0
  102. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/map_report.py +0 -0
  103. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_catalog.py +0 -0
  104. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_descriptor.py +0 -0
  105. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_item.py +0 -0
  106. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_metadata.py +0 -0
  107. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_node.py +0 -0
  108. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/models/report_section.py +0 -0
  109. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/services/__init__.py +0 -0
  110. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/report/services/map_report_collector.py +0 -0
  111. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/__init__.py +0 -0
  112. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/application.py +0 -0
  113. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/domain.py +0 -0
  114. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/models/__init__.py +0 -0
  115. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/models/shape_realm_architecture_map.py +0 -0
  116. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/models/shape_report.py +0 -0
  117. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/models/shape_violation.py +0 -0
  118. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/__init__.py +0 -0
  119. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/abstract_class_resolver.py +0 -0
  120. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/callable_resolver.py +0 -0
  121. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/class_resolver.py +0 -0
  122. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/file_resolver.py +0 -0
  123. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/import_resolver.py +0 -0
  124. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/property_resolver.py +0 -0
  125. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/signature_resolver.py +0 -0
  126. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/architecture/shape/services/symbol_resolver.py +0 -0
  127. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/autowiring.py +0 -0
  128. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/__init__.py +0 -0
  129. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/__init__.py +0 -0
  130. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/domain.py +0 -0
  131. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/__init__.py +0 -0
  132. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/cache_entry.py +0 -0
  133. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/cache_key.py +0 -0
  134. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/cache_options.py +0 -0
  135. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/models/extraction_snapshot.py +0 -0
  136. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/services/__init__.py +0 -0
  137. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/services/cache_codec.py +0 -0
  138. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/cache/services/filesystem_cache_storage.py +0 -0
  139. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/documentation/__init__.py +0 -0
  140. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/documentation/application.py +0 -0
  141. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/documentation/services/__init__.py +0 -0
  142. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/documentation/services/documentation_generator.py +0 -0
  143. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/facade.py +0 -0
  144. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/__init__.py +0 -0
  145. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/application.py +0 -0
  146. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/models/__init__.py +0 -0
  147. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/models/initialization_result.py +0 -0
  148. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/services/__init__.py +0 -0
  149. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/initialization/services/initialization_service.py +0 -0
  150. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/__init__.py +0 -0
  151. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/application.py +0 -0
  152. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/__init__.py +0 -0
  153. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/command_request.py +0 -0
  154. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/extractor_batch_input.py +0 -0
  155. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/extractor_command_input.py +0 -0
  156. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/extractor_source_input.py +0 -0
  157. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/report_pipeline_context.py +0 -0
  158. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/models/scan_policy.py +0 -0
  159. {modwire-9.2.1/src/modwire/cli/cache → modwire-9.2.2/src/modwire/cli/pipeline}/models/source_entry.py +0 -0
  160. {modwire-9.2.1/src/modwire/cli/cache → modwire-9.2.2/src/modwire/cli/pipeline}/models/source_inventory.py +0 -0
  161. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/__init__.py +0 -0
  162. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/callables_insight.py +0 -0
  163. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/clusters_insight.py +0 -0
  164. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/coherence_insight.py +0 -0
  165. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/command_line.py +0 -0
  166. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/configuration_loader.py +0 -0
  167. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/extractor_command.py +0 -0
  168. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/flow_violations.py +0 -0
  169. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/hotspots_insight.py +0 -0
  170. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/map_tree.py +0 -0
  171. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/output_console.py +0 -0
  172. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/shape_violations.py +0 -0
  173. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/success.py +0 -0
  174. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/unknown_files_warning.py +0 -0
  175. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/pipeline/services/unused_exports_insight.py +0 -0
  176. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/__init__.py +0 -0
  177. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/application.py +0 -0
  178. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/models/__init__.py +0 -0
  179. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/models/defaults.py +0 -0
  180. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/models/init_asset.py +0 -0
  181. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/AGENTS.md +0 -0
  182. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/ARCHITECTURE.md +0 -0
  183. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/INDEX.md +0 -0
  184. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/MODWIRE.md +0 -0
  185. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/RULES.md +0 -0
  186. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/TESTING.md +0 -0
  187. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/WORKFLOW.md +0 -0
  188. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/cli/resources/templates/architecture.yaml +0 -0
  189. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/__init__.py +0 -0
  190. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/__init__.py +0 -0
  191. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/application.py +0 -0
  192. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/domain.py +0 -0
  193. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/services/__init__.py +0 -0
  194. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/services/graph_builder.py +0 -0
  195. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/services/import_resolver.py +0 -0
  196. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/dependency/services/suffix_index.py +0 -0
  197. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/__init__.py +0 -0
  198. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/application.py +0 -0
  199. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/domain.py +0 -0
  200. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/__init__.py +0 -0
  201. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/batch_config.py +0 -0
  202. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/extraction_request.py +0 -0
  203. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/extractor_resource.py +0 -0
  204. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/extractor_runtime.py +0 -0
  205. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/models/python_call_context.py +0 -0
  206. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/__init__.py +0 -0
  207. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/build.php +0 -0
  208. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/build.py +0 -0
  209. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/composer.json +0 -0
  210. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/composer.lock +0 -0
  211. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/script.php +0 -0
  212. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/php/script.src.php +0 -0
  213. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/python/__init__.py +0 -0
  214. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/python/script.py +0 -0
  215. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/build.mjs +0 -0
  216. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/build.py +0 -0
  217. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/package-lock.json +0 -0
  218. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/package.json +0 -0
  219. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/script.js +0 -0
  220. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/script.ts +0 -0
  221. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/resources/typescript/tsconfig.json +0 -0
  222. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/__init__.py +0 -0
  223. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/php_extractor.py +0 -0
  224. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/python_call_reader.py +0 -0
  225. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/python_extractor.py +0 -0
  226. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/python_syntax_parser.py +0 -0
  227. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/extractors/services/type_script_extractor.py +0 -0
  228. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/extraction/facade.py +0 -0
  229. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/py.typed +0 -0
  230. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/__init__.py +0 -0
  231. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/__init__.py +0 -0
  232. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/application.py +0 -0
  233. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/domain.py +0 -0
  234. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/__init__.py +0 -0
  235. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/code_map.py +0 -0
  236. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/code_package.py +0 -0
  237. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/dependency_edge_result.py +0 -0
  238. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/dependency_graph.py +0 -0
  239. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/dependency_node_result.py +0 -0
  240. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/duplicate_identity_error.py +0 -0
  241. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/edge.py +0 -0
  242. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/edge_resolution.py +0 -0
  243. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/identity.py +0 -0
  244. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/node.py +0 -0
  245. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/query_builder.py +0 -0
  246. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/query_types.py +0 -0
  247. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/queryable_code_map.py +0 -0
  248. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_abstract_class.py +0 -0
  249. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_call.py +0 -0
  250. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_callable.py +0 -0
  251. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_callable_symbol.py +0 -0
  252. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_class.py +0 -0
  253. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_class_method.py +0 -0
  254. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_class_property.py +0 -0
  255. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_export.py +0 -0
  256. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_extraction.py +0 -0
  257. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_file.py +0 -0
  258. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_file_result.py +0 -0
  259. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_function.py +0 -0
  260. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_import.py +0 -0
  261. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_imported_symbol.py +0 -0
  262. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_interface.py +0 -0
  263. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_item_result.py +0 -0
  264. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_parameter.py +0 -0
  265. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_signature.py +0 -0
  266. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_symbol.py +0 -0
  267. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_type.py +0 -0
  268. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/source_value.py +0 -0
  269. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/models/types.py +0 -0
  270. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/services/__init__.py +0 -0
  271. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/services/glob_path_matcher.py +0 -0
  272. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/code/services/identity_resolver.py +0 -0
  273. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/values/__init__.py +0 -0
  274. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/values/models/__init__.py +0 -0
  275. {modwire-9.2.1 → modwire-9.2.2}/src/modwire/shared/values/models/value_model.py +0 -0
  276. {modwire-9.2.1 → modwire-9.2.2}/tests/__init__.py +0 -0
  277. {modwire-9.2.1 → modwire-9.2.2}/tests/application/__init__.py +0 -0
  278. {modwire-9.2.1 → modwire-9.2.2}/tests/application/base_test.py +0 -0
  279. {modwire-9.2.1 → modwire-9.2.2}/tests/application/test_01_attacks.py +0 -0
  280. {modwire-9.2.1 → modwire-9.2.2}/tests/application/test_06_happy_path.py +0 -0
  281. {modwire-9.2.1 → modwire-9.2.2}/tests/application/test_07_cache.py +0 -0
  282. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/__init__.py +0 -0
  283. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/__init__.py +0 -0
  284. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/base_test.py +0 -0
  285. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/test_01_attacks.py +0 -0
  286. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/test_02_invariants.py +0 -0
  287. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/test_03_public_api.py +0 -0
  288. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/boundaries/test_04_paths.py +0 -0
  289. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/config/__init__.py +0 -0
  290. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/config/test_01_attacks.py +0 -0
  291. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/config/test_02_invariants.py +0 -0
  292. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/insights/__init__.py +0 -0
  293. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/map/__init__.py +0 -0
  294. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/map/test_02_patterns.py +0 -0
  295. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/report/__init__.py +0 -0
  296. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/report/test_02_invariants.py +0 -0
  297. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/shape/__init__.py +0 -0
  298. {modwire-9.2.1 → modwire-9.2.2}/tests/architecture/shape/test_02_invariants.py +0 -0
  299. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/__init__.py +0 -0
  300. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/base_test.py +0 -0
  301. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/documentation/__init__.py +0 -0
  302. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/documentation/test_02_invariants.py +0 -0
  303. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/__init__.py +0 -0
  304. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/test_01_attacks.py +0 -0
  305. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/test_02_invariants.py +0 -0
  306. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/test_03_interruption.py +0 -0
  307. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/test_04_cleanup.py +0 -0
  308. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/initialization/test_05_recovery.py +0 -0
  309. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/__init__.py +0 -0
  310. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/base_test.py +0 -0
  311. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_01_attacks.py +0 -0
  312. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_02_invariants.py +0 -0
  313. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_03_interruption.py +0 -0
  314. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_04_command_transport.py +0 -0
  315. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_05_recovery.py +0 -0
  316. {modwire-9.2.1 → modwire-9.2.2}/tests/cli/pipeline/test_06_happy_path.py +0 -0
  317. {modwire-9.2.1 → modwire-9.2.2}/tests/conftest.py +0 -0
  318. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/__init__.py +0 -0
  319. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/base_test.py +0 -0
  320. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/__init__.py +0 -0
  321. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/project.py +0 -0
  322. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/projects.json +0 -0
  323. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/resolution_results.json +0 -0
  324. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/results.json +0 -0
  325. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/big_projects/run.py +0 -0
  326. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/cache_benchmark/__init__.py +0 -0
  327. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/cache_benchmark/run.py +0 -0
  328. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/dependency/__init__.py +0 -0
  329. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/dependency/test_02_invariants.py +0 -0
  330. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/extractors/__init__.py +0 -0
  331. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/extractors/test_01_attacks.py +0 -0
  332. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/extractors/test_02_invariants.py +0 -0
  333. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/extractors/test_03_native_symbols.py +0 -0
  334. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/scan_benchmark/__init__.py +0 -0
  335. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/scan_benchmark/prepare.py +0 -0
  336. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/scan_benchmark/results.json +0 -0
  337. {modwire-9.2.1 → modwire-9.2.2}/tests/extraction/scan_benchmark/run.py +0 -0
  338. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/php/ignored/example_generated.php +0 -0
  339. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/php/src/example_application/example_actions/example_action.php +0 -0
  340. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/php/src/example_domain/example_model/example_record.php +0 -0
  341. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/php/src/example_domain/example_services/example_policy.php +0 -0
  342. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/php/src/example_interfaces/example_http/example_controller.php +0 -0
  343. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/python/ignored/example_generated.py +0 -0
  344. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/python/src/example_application/example_actions/example_action.py +0 -0
  345. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/python/src/example_domain/example_model/example_record.py +0 -0
  346. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/python/src/example_domain/example_services/example_policy.py +0 -0
  347. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/python/src/example_interfaces/example_http/example_controller.py +0 -0
  348. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/ignored/example_generated.ts +0 -0
  349. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_application/example_actions/example_action.ts +0 -0
  350. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_domain/example_model/example_record.ts +0 -0
  351. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_domain/example_model/example_view.tsx +0 -0
  352. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_domain/example_services/example_audit.js +0 -0
  353. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_domain/example_services/example_callables.ts +0 -0
  354. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_domain/example_services/example_policy.ts +0 -0
  355. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_interfaces/example_http/example_controller.ts +0 -0
  356. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/languages/typescript/src/example_interfaces/example_http/example_view.jsx +0 -0
  357. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/syntax/php/example_shapes.php +0 -0
  358. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/syntax/python/example_shapes.py +0 -0
  359. {modwire-9.2.1 → modwire-9.2.2}/tests/fixtures/syntax/typescript/example_shapes.ts +0 -0
  360. {modwire-9.2.1 → modwire-9.2.2}/tests/shared/__init__.py +0 -0
  361. {modwire-9.2.1 → modwire-9.2.2}/tests/shared/code/__init__.py +0 -0
  362. {modwire-9.2.1 → modwire-9.2.2}/tests/support/__init__.py +0 -0
  363. {modwire-9.2.1 → modwire-9.2.2}/tests/support/base_test.py +0 -0
  364. {modwire-9.2.1 → modwire-9.2.2}/tests/support/service_test.py +0 -0
  365. {modwire-9.2.1 → modwire-9.2.2}/uv.lock +0 -0
@@ -120,10 +120,9 @@ src/modwire/cli/cache/models/cache_entry.py
120
120
  src/modwire/cli/cache/models/cache_key.py
121
121
  src/modwire/cli/cache/models/cache_options.py
122
122
  src/modwire/cli/cache/models/cache_outcome.py
123
+ src/modwire/cli/cache/models/cache_stage.py
123
124
  src/modwire/cli/cache/models/cached_result.py
124
125
  src/modwire/cli/cache/models/extraction_snapshot.py
125
- src/modwire/cli/cache/models/source_entry.py
126
- src/modwire/cli/cache/models/source_inventory.py
127
126
  src/modwire/cli/cache/services/__init__.py
128
127
  src/modwire/cli/cache/services/cache_codec.py
129
128
  src/modwire/cli/cache/services/cache_identity.py
@@ -148,6 +147,8 @@ src/modwire/cli/pipeline/models/extractor_command_input.py
148
147
  src/modwire/cli/pipeline/models/extractor_source_input.py
149
148
  src/modwire/cli/pipeline/models/report_pipeline_context.py
150
149
  src/modwire/cli/pipeline/models/scan_policy.py
150
+ src/modwire/cli/pipeline/models/source_entry.py
151
+ src/modwire/cli/pipeline/models/source_inventory.py
151
152
  src/modwire/cli/pipeline/services/__init__.py
152
153
  src/modwire/cli/pipeline/services/batch_source_reader.py
153
154
  src/modwire/cli/pipeline/services/callables_insight.py
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: modwire
3
- Version: 9.2.1
3
+ Version: 9.2.2
4
4
  Summary: Code extraction, architecture analysis and the Modwire CLI.
5
5
  Author: Tomasz Szpak
6
6
  License-Expression: MIT
@@ -11,7 +11,8 @@ from .architecture.facade import ArchitectureFacade
11
11
  from .architecture.report.models.report_catalog import ReportCatalog
12
12
  from .architecture.report.models.report_node import ReportNode
13
13
  from .cli.cache.models.cache_options import CacheOptions
14
- from .cli.cache.models.cache_outcome import CacheOutcome, CacheStage
14
+ from .cli.cache.models.cache_outcome import CacheOutcome
15
+ from .cli.cache.models.cache_stage import CacheStage
15
16
  from .cli.cache.models.cached_result import CachedResult
16
17
  from .cli.facade import CliFacade
17
18
  from .cli.pipeline.models.scan_policy import ScanPolicy
@@ -18,19 +18,14 @@ from ..pipeline.models.scan_policy import ScanPolicy
18
18
  from .domain import CacheStorage
19
19
  from .models.cache_key import CacheKey
20
20
  from .models.cache_options import CacheOptions
21
- from .models.cache_outcome import CacheOutcome, CacheStage
21
+ from .models.cache_outcome import CacheOutcome
22
+ from .models.cache_stage import CacheStage
22
23
  from .models.cached_result import CachedResult
23
24
  from .models.extraction_snapshot import ExtractionSnapshot
24
25
  from .services.cache_codec import CacheCodec
25
26
  from .services.cache_identity import CacheIdentity
26
27
 
27
28
 
28
- @dataclass(frozen=True)
29
- class _CacheRead:
30
- value: object | None
31
- invalidated: bool
32
-
33
-
34
29
  @injectable
35
30
  @dataclass(frozen=True)
36
31
  class CacheApplication:
@@ -57,17 +52,17 @@ class CacheApplication:
57
52
  invalidated = 0
58
53
  for entry in inventory.entries:
59
54
  key = keys[entry.source_id]
60
- cached = self._read(options, key)
55
+ cached_value, cached_invalidated = self._read(options, key)
61
56
  try:
62
- source_file = SourceFile.model_validate(cached.value)
57
+ source_file = SourceFile.model_validate(cached_value)
63
58
  if source_file.file_id != entry.source_id:
64
59
  raise ValueError("Cached source identity does not match its key.")
65
60
  files[entry.source_id] = source_file
66
61
  hits += 1
67
62
  except (TypeError, ValueError, ValidationError):
68
- if cached.value is not None and not cached.invalidated:
63
+ if cached_value is not None and not cached_invalidated:
69
64
  self.storage.delete(options, key)
70
- invalidated += int(cached.invalidated or cached.value is not None)
65
+ invalidated += int(cached_invalidated or cached_value is not None)
71
66
  misses.append(entry.source_id)
72
67
 
73
68
  if misses or not inventory.entries:
@@ -128,19 +123,19 @@ class CacheApplication:
128
123
 
129
124
  def code_map(self, snapshot: ExtractionSnapshot, options: CacheOptions) -> CachedResult[CodeMap | None]:
130
125
  key = self.identity.code_map("", snapshot.manifest)
131
- cached = self._read(options, key)
126
+ cached_value, cached_invalidated = self._read(options, key)
132
127
  try:
133
- value = CodeMap.model_validate(cached.value)
128
+ value = CodeMap.model_validate(cached_value)
134
129
  outcome = CacheOutcome(stage=CacheStage.CODE_MAP, namespace=options.namespace, hits=1)
135
130
  except (TypeError, ValueError, ValidationError):
136
- if cached.value is not None and not cached.invalidated:
131
+ if cached_value is not None and not cached_invalidated:
137
132
  self.storage.delete(options, key)
138
133
  value = None
139
134
  outcome = CacheOutcome(
140
135
  stage=CacheStage.CODE_MAP,
141
136
  namespace=options.namespace,
142
137
  misses=1,
143
- invalidated=int(cached.invalidated or cached.value is not None),
138
+ invalidated=int(cached_invalidated or cached_value is not None),
144
139
  )
145
140
  return CachedResult[CodeMap | None](value=value, outcomes=(outcome,))
146
141
 
@@ -152,9 +147,8 @@ class CacheApplication:
152
147
  self, code_map: CodeMap, config: ArchitectureConfig, options: CacheOptions
153
148
  ) -> CachedResult[tuple[ReportNode, ...] | None]:
154
149
  key = self.identity.reports(code_map, config)
155
- cached = self._read(options, key)
156
- cached_value: object | None = cached.value
157
- invalidated = cached.invalidated or cached_value is not None
150
+ cached_value, cached_invalidated = self._read(options, key)
151
+ invalidated = cached_invalidated or cached_value is not None
158
152
  try:
159
153
  if not isinstance(cached_value, list):
160
154
  raise ValueError("Cached reports must be a list.")
@@ -162,7 +156,7 @@ class CacheApplication:
162
156
  value = tuple(sorted(reports, key=lambda item: (item.metadata.order, item.metadata.id)))
163
157
  outcome = CacheOutcome(stage=CacheStage.REPORTS, namespace=options.namespace, hits=1)
164
158
  except (AttributeError, ImportError, KeyError, TypeError, ValueError, ValidationError):
165
- if cached_value is not None and not cached.invalidated:
159
+ if cached_value is not None and not cached_invalidated:
166
160
  self.storage.delete(options, key)
167
161
  value = None
168
162
  outcome = CacheOutcome(
@@ -202,15 +196,15 @@ class CacheApplication:
202
196
  self.storage.delete(options, entry.key)
203
197
  total -= entry.size
204
198
 
205
- def _read(self, options: CacheOptions, key: CacheKey) -> _CacheRead:
199
+ def _read(self, options: CacheOptions, key: CacheKey) -> tuple[object | None, bool]:
206
200
  payload = self.storage.read(options, key)
207
201
  if payload is None:
208
- return _CacheRead(value=None, invalidated=False)
202
+ return None, False
209
203
  value = self.codec.decode(key, payload)
210
204
  if value is None:
211
205
  self.storage.delete(options, key)
212
- return _CacheRead(value=None, invalidated=True)
213
- return _CacheRead(value=value, invalidated=False)
206
+ return None, True
207
+ return value, False
214
208
 
215
209
  def _write(self, options: CacheOptions, key: CacheKey, value: object) -> None:
216
210
  self.storage.write(options, key, self.codec.encode(key, value))
@@ -1,16 +1,7 @@
1
- from enum import StrEnum
2
-
3
1
  from pydantic import field_validator
4
2
 
5
3
  from ....shared.values.models.value_model import ValueModel
6
-
7
-
8
- class CacheStage(StrEnum):
9
- """Public stages reported by cached Modwire operations."""
10
-
11
- EXTRACTION = "extraction"
12
- CODE_MAP = "code-map"
13
- REPORTS = "reports"
4
+ from .cache_stage import CacheStage
14
5
 
15
6
 
16
7
  class CacheOutcome(ValueModel):
@@ -0,0 +1,9 @@
1
+ from enum import StrEnum
2
+
3
+
4
+ class CacheStage(StrEnum):
5
+ """Public stages reported by cached Modwire operations."""
6
+
7
+ EXTRACTION = "extraction"
8
+ CODE_MAP = "code-map"
9
+ REPORTS = "reports"
@@ -1,7 +1,8 @@
1
1
  from pydantic import field_validator
2
2
 
3
3
  from ....shared.values.models.value_model import ValueModel
4
- from .cache_outcome import CacheOutcome, CacheStage
4
+ from .cache_outcome import CacheOutcome
5
+ from .cache_stage import CacheStage
5
6
 
6
7
 
7
8
  class CachedResult[Result](ValueModel):
@@ -11,8 +11,8 @@ from ....architecture.config.models.architecture_config import ArchitectureConfi
11
11
  from ....extraction.extractors.models.extraction_request import ExtractionRequest
12
12
  from ....shared.code.models.code_map import CodeMap
13
13
  from ...cache.models.cache_key import CacheKey, CacheKind
14
- from ...cache.models.source_entry import SourceEntry
15
14
  from ...pipeline.models.scan_policy import ScanPolicy
15
+ from ...pipeline.models.source_entry import SourceEntry
16
16
 
17
17
 
18
18
  @injectable
@@ -5,9 +5,9 @@ from ...extraction.extractors.models.extractor_runtime import ExtractorRuntime
5
5
  from ...shared.code.models.identity import FileId
6
6
  from ...shared.code.models.source_extraction import SourceExtraction
7
7
  from ...shared.code.models.source_file import SourceFile
8
- from ..cache.models.source_inventory import SourceInventory
9
8
  from .models.report_pipeline_context import ReportPipelineContext
10
9
  from .models.scan_policy import ScanPolicy
10
+ from .models.source_inventory import SourceInventory
11
11
 
12
12
 
13
13
  class ReportPipelineStep(ABC):
@@ -20,10 +20,10 @@ from ....shared.code.models.duplicate_identity_error import DuplicateIdentityErr
20
20
  from ....shared.code.models.identity import FileId, ModuleId
21
21
  from ....shared.code.models.source_extraction import SourceExtraction
22
22
  from ....shared.code.models.source_file import SourceFile
23
- from ...cache.models.source_entry import SourceEntry
24
- from ...cache.models.source_inventory import SourceInventory
25
23
  from ..domain import SourceReader
26
24
  from ..models.scan_policy import ScanPolicy
25
+ from ..models.source_entry import SourceEntry
26
+ from ..models.source_inventory import SourceInventory
27
27
 
28
28
 
29
29
  @injectable(as_type=SourceReader)
@@ -10,4 +10,4 @@ class ArchitectureTestCase(ServiceTestCase):
10
10
  return {}
11
11
 
12
12
  def queryable_map(self, paths: tuple[str, ...], edges: tuple[tuple[str, str | None, str, str], ...]):
13
- return CodeMapFactory.queryable({path: self.source_file(path) for path in paths}, edges)
13
+ return CodeMapFactory().queryable({path: self.source_file(path) for path in paths}, edges)
@@ -6,7 +6,7 @@ class InsightTestCase(ArchitectureTestCase):
6
6
  def insight(
7
7
  self,
8
8
  files: dict[str, dict[str, object]],
9
- edges: tuple[tuple[str, str | None, str, str], ...] = (),
9
+ edges: tuple[tuple[str, str | None, str, str], ...],
10
10
  ):
11
- code_map = CodeMapFactory.queryable(files, edges)
11
+ code_map = CodeMapFactory().queryable(files, edges)
12
12
  return self.report("architecture.insights", self.example_configuration(), code_map)
@@ -34,14 +34,22 @@ class TestInsightInvariants(InsightTestCase):
34
34
  {
35
35
  "example_values.source": {
36
36
  "exports": [
37
- CodeMapFactory.source_export("ExampleUsed"),
38
- CodeMapFactory.source_export("ExampleUnused"),
37
+ CodeMapFactory().source_export("ExampleUsed"),
38
+ CodeMapFactory().source_export("ExampleUnused"),
39
39
  ]
40
40
  },
41
41
  "example_consumer.source": {
42
- "imports": [CodeMapFactory.source_import("example_values", imported_name="ExampleUsed")]
42
+ "imports": [
43
+ CodeMapFactory().source_import(
44
+ "example_values",
45
+ imported_name="ExampleUsed",
46
+ is_aliased=False,
47
+ imported_symbols=(),
48
+ )
49
+ ]
43
50
  },
44
- }
51
+ },
52
+ (),
45
53
  ).exports
46
54
  assert tuple((item.source_id, item.name) for item in result.unused_exports) == (
47
55
  ("example_values.source", "ExampleUnused"),
@@ -53,15 +61,16 @@ class TestInsightInvariants(InsightTestCase):
53
61
  {
54
62
  source_id: {
55
63
  "callables": [
56
- CodeMapFactory.source_callable(source_id, "example_target"),
57
- CodeMapFactory.source_callable(source_id, "example_caller"),
64
+ CodeMapFactory().source_callable(source_id, "example_target"),
65
+ CodeMapFactory().source_callable(source_id, "example_caller"),
58
66
  ],
59
67
  "calls": [
60
- CodeMapFactory.source_call(source_id, "example_caller", "example_target"),
61
- CodeMapFactory.source_call(source_id, "example_caller", "example_target"),
68
+ CodeMapFactory().source_call(source_id, "example_caller", "example_target"),
69
+ CodeMapFactory().source_call(source_id, "example_caller", "example_target"),
62
70
  ],
63
71
  }
64
- }
72
+ },
73
+ (),
65
74
  ).callables
66
75
  entries = {item.source_callable: item for item in result.entries}
67
76
  caller = next(item for key, item in entries.items() if key.endswith("example_caller"))
@@ -71,7 +80,7 @@ class TestInsightInvariants(InsightTestCase):
71
80
  assert target.calls == ()
72
81
 
73
82
  def test_empty_project_has_empty_insights(self) -> None:
74
- result = self.insight({})
83
+ result = self.insight({}, ())
75
84
  assert result.clusters.clusters == ()
76
85
  assert result.hotspots.hotspots == ()
77
86
  assert result.callables.entries == ()
@@ -4,4 +4,6 @@ from ..base_test import ArchitectureTestCase
4
4
 
5
5
  class ShapeTestCase(ArchitectureTestCase):
6
6
  def source_file(self, file_id: str) -> dict[str, object]:
7
- return {"functions": [CodeMapFactory.symbol("example_function")]}
7
+ return {
8
+ "functions": [CodeMapFactory().symbol("example_function", line_count=1, declared_args=0, optional_args=0)]
9
+ }
@@ -0,0 +1,178 @@
1
+ import pytest
2
+
3
+ from ...support.code_map import CodeMapFactory
4
+ from .base_test import ShapeTestCase
5
+
6
+
7
+ class TestShapeLimits(ShapeTestCase):
8
+ @pytest.mark.parametrize(
9
+ ("rule", "source_file", "actual"),
10
+ (
11
+ (
12
+ "max_classes_per_file",
13
+ {
14
+ "classes": [
15
+ CodeMapFactory().source_class("ExampleFirst", line_count=1, methods=(), properties=()),
16
+ CodeMapFactory().source_class("ExampleSecond", line_count=1, methods=(), properties=()),
17
+ ]
18
+ },
19
+ 2,
20
+ ),
21
+ (
22
+ "max_functions_per_file",
23
+ {
24
+ "functions": [
25
+ CodeMapFactory().symbol("example_first", line_count=1, declared_args=0, optional_args=0),
26
+ CodeMapFactory().symbol("example_second", line_count=1, declared_args=0, optional_args=0),
27
+ ]
28
+ },
29
+ 2,
30
+ ),
31
+ (
32
+ "max_methods_per_class",
33
+ {
34
+ "classes": [
35
+ CodeMapFactory().source_class(
36
+ "ExampleValue",
37
+ line_count=1,
38
+ methods=(
39
+ CodeMapFactory().symbol(
40
+ "example_first", line_count=1, declared_args=0, optional_args=0
41
+ ),
42
+ CodeMapFactory().symbol(
43
+ "example_second", line_count=1, declared_args=0, optional_args=0
44
+ ),
45
+ ),
46
+ properties=(),
47
+ )
48
+ ]
49
+ },
50
+ 2,
51
+ ),
52
+ (
53
+ "max_declared_args",
54
+ {
55
+ "functions": [
56
+ CodeMapFactory().symbol("example_function", line_count=1, declared_args=2, optional_args=0)
57
+ ]
58
+ },
59
+ 2,
60
+ ),
61
+ (
62
+ "max_function_lines",
63
+ {
64
+ "functions": [
65
+ CodeMapFactory().symbol("example_function", line_count=3, declared_args=0, optional_args=0)
66
+ ]
67
+ },
68
+ 3,
69
+ ),
70
+ (
71
+ "max_method_lines",
72
+ {
73
+ "classes": [
74
+ CodeMapFactory().source_class(
75
+ "ExampleValue",
76
+ line_count=1,
77
+ methods=(
78
+ CodeMapFactory().symbol(
79
+ "example_method", line_count=3, declared_args=0, optional_args=0
80
+ ),
81
+ ),
82
+ properties=(),
83
+ )
84
+ ]
85
+ },
86
+ 3,
87
+ ),
88
+ (
89
+ "max_class_lines",
90
+ {"classes": [CodeMapFactory().source_class("ExampleValue", line_count=3, methods=(), properties=())]},
91
+ 3,
92
+ ),
93
+ ),
94
+ )
95
+ @pytest.mark.parametrize("offset", (-1, 0, 1))
96
+ def test_limits_report_only_values_above_the_threshold(
97
+ self, rule: str, source_file: dict[str, object], actual: int, offset: int
98
+ ) -> None:
99
+ code_map = CodeMapFactory().queryable({"example.source": source_file}, ())
100
+ config = self.application.configure(
101
+ {"shape": {"realms": [{"name": "example-source", "match": "*", "shape": {rule: actual + offset}}]}}
102
+ )
103
+ violations = tuple(
104
+ item
105
+ for item in self.report("architecture.violations.shape", config, code_map).violations
106
+ if item.rule_name == rule
107
+ )
108
+ if offset < 0:
109
+ assert len(violations) == 1
110
+ assert violations[0].actual == actual
111
+ assert violations[0].limit == actual + offset
112
+ assert violations[0].source_id == "example.source"
113
+ else:
114
+ assert violations == ()
115
+
116
+ @pytest.mark.parametrize(
117
+ ("rule", "source_file"),
118
+ (
119
+ (
120
+ "allow_optional_function_args",
121
+ {
122
+ "functions": [
123
+ CodeMapFactory().symbol("example_function", line_count=1, declared_args=1, optional_args=1)
124
+ ]
125
+ },
126
+ ),
127
+ (
128
+ "allow_optional_method_args",
129
+ {
130
+ "classes": [
131
+ CodeMapFactory().source_class(
132
+ "ExampleValue",
133
+ line_count=1,
134
+ methods=(
135
+ CodeMapFactory().symbol(
136
+ "example_method", line_count=1, declared_args=1, optional_args=1
137
+ ),
138
+ ),
139
+ properties=(),
140
+ )
141
+ ]
142
+ },
143
+ ),
144
+ (
145
+ "allow_optional_class_properties",
146
+ {
147
+ "classes": [
148
+ CodeMapFactory().source_class(
149
+ "ExampleValue",
150
+ line_count=1,
151
+ methods=(),
152
+ properties=({"name": "example_value", "is_optional": True},),
153
+ )
154
+ ]
155
+ },
156
+ ),
157
+ (
158
+ "allow_import_aliases",
159
+ {
160
+ "imports": [
161
+ CodeMapFactory().source_import(
162
+ "example_external", imported_name="", is_aliased=True, imported_symbols=()
163
+ )
164
+ ]
165
+ },
166
+ ),
167
+ ),
168
+ )
169
+ @pytest.mark.parametrize("allowed", (False, True))
170
+ def test_boolean_permissions_apply_to_the_public_report(
171
+ self, rule: str, source_file: dict[str, object], allowed: bool
172
+ ) -> None:
173
+ code_map = CodeMapFactory().queryable({"example.source": source_file}, ())
174
+ config = self.application.configure(
175
+ {"shape": {"realms": [{"name": "example-source", "match": "*", "shape": {rule: allowed}}]}}
176
+ )
177
+ violations = self.report("architecture.violations.shape", config, code_map).violations
178
+ assert any(item.rule_name == rule for item in violations) is not allowed
@@ -6,16 +6,17 @@ from ...support.service_test import ServiceTestCase
6
6
 
7
7
  class TestPublicCodeValues(ServiceTestCase):
8
8
  def test_query_filters_are_composable_without_changing_the_original_query(self) -> None:
9
- result = CodeMapFactory.queryable(
9
+ result = CodeMapFactory().queryable(
10
10
  {
11
11
  "example.source": {
12
12
  "classes": [
13
- CodeMapFactory.source_class("ExampleFirst"),
14
- CodeMapFactory.source_class("ExampleSecond"),
15
- CodeMapFactory.source_class("ExampleThird"),
13
+ CodeMapFactory().source_class("ExampleFirst", line_count=1, methods=(), properties=()),
14
+ CodeMapFactory().source_class("ExampleSecond", line_count=1, methods=(), properties=()),
15
+ CodeMapFactory().source_class("ExampleThird", line_count=1, methods=(), properties=()),
16
16
  ]
17
17
  }
18
- }
18
+ },
19
+ (),
19
20
  )
20
21
  original = result.classes()
21
22
  selected = original.where_contains(lambda item: item.item.name, "example", case_sensitive=False)
@@ -28,7 +29,7 @@ class TestPublicCodeValues(ServiceTestCase):
28
29
 
29
30
  def test_incoming_and_outgoing_queries_preserve_edge_direction(self) -> None:
30
31
  paths = ("example_first.source", "example_second.source", "example_third.source")
31
- result = CodeMapFactory.queryable(
32
+ result = CodeMapFactory().queryable(
32
33
  dict.fromkeys(paths, {}),
33
34
  (
34
35
  (paths[0], paths[1], "resolved", "example_second"),
@@ -42,16 +43,18 @@ class TestPublicCodeValues(ServiceTestCase):
42
43
  assert result.dependencies_between(paths[2], paths[1]).all() == ()
43
44
 
44
45
  def test_code_map_round_trips_json(self) -> None:
45
- original = CodeMapFactory.queryable({"src/example.source": {}}).code_map
46
+ original = CodeMapFactory().queryable({"src/example.source": {}}, ()).code_map
46
47
  restored = type(original).model_validate_json(original.to_json())
47
48
  assert restored.to_dict() == original.to_dict()
48
49
  assert original.schema_version == 2
49
50
  assert set(json.loads(original.to_json())) == {"language", "extraction", "dependency_graph"}
50
51
 
51
52
  def test_query_surfaces_keep_external_and_tracked_edges_distinct(self) -> None:
52
- result = CodeMapFactory.queryable(
53
+ result = CodeMapFactory().queryable(
53
54
  {
54
- "example_values.source": {"classes": [CodeMapFactory.source_class("ExampleValue")]},
55
+ "example_values.source": {
56
+ "classes": [CodeMapFactory().source_class("ExampleValue", line_count=1, methods=(), properties=())]
57
+ },
55
58
  "example_consumer.source": {},
56
59
  },
57
60
  (
@@ -6,13 +6,12 @@ from modwire.application import CodeMap, QueryableCodeMap
6
6
 
7
7
 
8
8
  class CodeMapFactory:
9
- @classmethod
10
9
  def queryable(
11
- cls,
10
+ self,
12
11
  files: Mapping[str, Mapping[str, object]],
13
- edges: tuple[tuple[str, str | None, str, str], ...] = (),
12
+ edges: tuple[tuple[str, str | None, str, str], ...],
14
13
  ) -> QueryableCodeMap:
15
- source_files = {source_id: cls.source_file(source_id, values) for source_id, values in files.items()}
14
+ source_files = {source_id: self.source_file(source_id, values) for source_id, values in files.items()}
16
15
  modules = {str(source_file["module_id"]): source_id for source_id, source_file in source_files.items()}
17
16
  nodes = {source_id: {"id": source_id, "kind": "file"} for source_id in source_files}
18
17
  dependency_edges = []
@@ -43,8 +42,7 @@ class CodeMapFactory:
43
42
  )
44
43
  return QueryableCodeMap(code_map=code_map)
45
44
 
46
- @staticmethod
47
- def source_file(source_id: str, values: Mapping[str, object]) -> dict[str, object]:
45
+ def source_file(self, source_id: str, values: Mapping[str, object]) -> dict[str, object]:
48
46
  defaults: dict[str, object] = {
49
47
  "file_id": source_id,
50
48
  "module_id": str(PurePosixPath(source_id).with_suffix("")).replace("/", "."),
@@ -64,8 +62,7 @@ class CodeMapFactory:
64
62
  }
65
63
  return {**defaults, **values}
66
64
 
67
- @staticmethod
68
- def symbol(name: str, *, line_count: int = 1, declared_args: int = 0, optional_args: int = 0) -> dict[str, Any]:
65
+ def symbol(self, name: str, *, line_count: int, declared_args: int, optional_args: int) -> dict[str, Any]:
69
66
  return {
70
67
  "name": name,
71
68
  "visibility": "public",
@@ -75,14 +72,13 @@ class CodeMapFactory:
75
72
  "optional_args": optional_args,
76
73
  }
77
74
 
78
- @classmethod
79
75
  def source_class(
80
- cls,
76
+ self,
81
77
  name: str,
82
78
  *,
83
- line_count: int = 1,
84
- methods: tuple[Mapping[str, object], ...] = (),
85
- properties: tuple[Mapping[str, object], ...] = (),
79
+ line_count: int,
80
+ methods: tuple[Mapping[str, object], ...],
81
+ properties: tuple[Mapping[str, object], ...],
86
82
  ) -> dict[str, object]:
87
83
  return {
88
84
  "name": name,
@@ -93,13 +89,13 @@ class CodeMapFactory:
93
89
  "properties": list(properties),
94
90
  }
95
91
 
96
- @staticmethod
97
92
  def source_import(
93
+ self,
98
94
  specifier: str,
99
95
  *,
100
- imported_name: str = "",
101
- is_aliased: bool = False,
102
- imported_symbols: tuple[Mapping[str, object], ...] = (),
96
+ imported_name: str,
97
+ is_aliased: bool,
98
+ imported_symbols: tuple[Mapping[str, object], ...],
103
99
  ) -> dict[str, object]:
104
100
  return {
105
101
  "path": specifier,
@@ -117,8 +113,7 @@ class CodeMapFactory:
117
113
  "imported_symbols": list(imported_symbols),
118
114
  }
119
115
 
120
- @staticmethod
121
- def source_export(name: str) -> dict[str, object]:
116
+ def source_export(self, name: str) -> dict[str, object]:
122
117
  return {
123
118
  "name": name,
124
119
  "local_name": name,
@@ -133,10 +128,9 @@ class CodeMapFactory:
133
128
  "statement_id": 0,
134
129
  }
135
130
 
136
- @classmethod
137
- def source_callable(cls, source_id: str, name: str) -> dict[str, object]:
131
+ def source_callable(self, source_id: str, name: str) -> dict[str, object]:
138
132
  return {
139
- **cls.symbol(name),
133
+ **self.symbol(name, line_count=1, declared_args=0, optional_args=0),
140
134
  "id": f"{source_id}::{name}",
141
135
  "source_id": source_id,
142
136
  "qualified_name": name,
@@ -150,8 +144,7 @@ class CodeMapFactory:
150
144
  "docstring": "",
151
145
  }
152
146
 
153
- @staticmethod
154
- def source_call(source_id: str, source_name: str, target_name: str) -> dict[str, object]:
147
+ def source_call(self, source_id: str, source_name: str, target_name: str) -> dict[str, object]:
155
148
  return {
156
149
  "source_callable_id": f"{source_id}::{source_name}",
157
150
  "target_callable_id": f"{source_id}::{target_name}",