ara-cli 0.1.9.51__tar.gz → 0.1.9.52__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 (164) hide show
  1. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/PKG-INFO +1 -1
  2. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/ara_command_action.py +28 -34
  3. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_creator.py +3 -4
  4. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_lister.py +11 -13
  5. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/artefact_model.py +20 -8
  6. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_reader.py +10 -16
  7. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_renamer.py +8 -8
  8. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/file_classifier.py +3 -33
  9. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_ara_command_action.py +6 -6
  10. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_artefact_lister.py +149 -91
  11. ara_cli-0.1.9.52/ara_cli/tests/test_artefact_reader.py +16 -0
  12. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_file_classifier.py +2 -2
  13. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/version.py +1 -1
  14. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/PKG-INFO +1 -1
  15. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/SOURCES.txt +0 -2
  16. ara_cli-0.1.9.51/ara_cli/artefact.py +0 -172
  17. ara_cli-0.1.9.51/ara_cli/tests/test_artefact.py +0 -304
  18. ara_cli-0.1.9.51/ara_cli/tests/test_artefact_reader.py +0 -57
  19. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/MANIFEST.in +0 -0
  20. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/README.md +0 -0
  21. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/__init__.py +0 -0
  22. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/__main__.py +0 -0
  23. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/analyse_artefacts.py +0 -0
  24. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/ara_command_parser.py +0 -0
  25. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/ara_config.py +0 -0
  26. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_deleter.py +0 -0
  27. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_fuzzy_search.py +0 -0
  28. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_link_updater.py +0 -0
  29. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/artefact_load.py +0 -0
  30. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/artefact_mapping.py +0 -0
  31. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/artefact_templates.py +0 -0
  32. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/businessgoal_artefact_model.py +0 -0
  33. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/capability_artefact_model.py +0 -0
  34. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/epic_artefact_model.py +0 -0
  35. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/example_artefact_model.py +0 -0
  36. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/feature_artefact_model.py +0 -0
  37. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/issue_artefact_model.py +0 -0
  38. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/keyfeature_artefact_model.py +0 -0
  39. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/task_artefact_model.py +0 -0
  40. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/userstory_artefact_model.py +0 -0
  41. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_models/vision_artefact_model.py +0 -0
  42. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/artefact_scan.py +0 -0
  43. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/chat.py +0 -0
  44. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/classifier.py +0 -0
  45. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/codefusionretriever.py +0 -0
  46. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/codehierachieretriever.py +0 -0
  47. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/commandline_completer.py +0 -0
  48. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/directory_navigator.py +0 -0
  49. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/file_lister.py +0 -0
  50. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/filename_validator.py +0 -0
  51. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/list_filter.py +0 -0
  52. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/output_suppressor.py +0 -0
  53. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/prompt_chat.py +0 -0
  54. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/prompt_extractor.py +0 -0
  55. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/prompt_handler.py +0 -0
  56. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/prompt_rag.py +0 -0
  57. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/run_file_lister.py +0 -0
  58. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tag_extractor.py +0 -0
  59. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/template_manager.py +0 -0
  60. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/agile.artefacts +0 -0
  61. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/blueprints/complete_pytest_unittest.blueprint.md +0 -0
  62. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/blueprints/empty.blueprint.md +0 -0
  63. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/blueprints/task_todo_list_C4_architecture_analysis.blueprint.md +0 -0
  64. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/blueprints/task_todo_list_implement_feature_BDD_way.blueprint.md +0 -0
  65. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/architecture_C4_analysis.commands.md +0 -0
  66. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/architecture_radon_cc_score.commands.md +0 -0
  67. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/architecture_radon_halstead_v.commands.md +0 -0
  68. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/architecture_radon_maintainability_score.commands.md +0 -0
  69. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/artefact_classification.commands.md +0 -0
  70. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/artefact_extension.commands.md +0 -0
  71. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/artefact_formulation.commands.md +0 -0
  72. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/behave_step_generation.commands.md +0 -0
  73. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/code_generation_complex.commands.md +0 -0
  74. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/code_generation_simple.commands.md +0 -0
  75. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/empty.commands.md +0 -0
  76. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/error_fixing.commands.md +0 -0
  77. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/feature_file_update.commands.md +0 -0
  78. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/feature_formulation.commands.md +0 -0
  79. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/js_code_generation_simple.commands.md +0 -0
  80. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/refactoring.commands.md +0 -0
  81. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/refactoring_analysis.commands.md +0 -0
  82. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/reverse_engineer_feature_file.commands.md +0 -0
  83. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/commands/reverse_engineer_program_flow.commands.md +0 -0
  84. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/classify_task.intention.md +0 -0
  85. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/empty.intention.md +0 -0
  86. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/error_fixing.intention.md +0 -0
  87. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_fix_steps_for_scenario.intention.md +0 -0
  88. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_formulation.intention.md +0 -0
  89. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_reverse_formulation_from_code.intention.md +0 -0
  90. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_scenario_implementation.intention.md +0 -0
  91. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_scenario_implementation_update.intention.md +0 -0
  92. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_scenario_outline_extension.intention.md +0 -0
  93. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/feature_update_formulation.intention.md +0 -0
  94. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/fibonacci_example_implementation.intention.md +0 -0
  95. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/js_implementation_from_task_description.intention.md +0 -0
  96. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/js_steps_implementation.intention.md +0 -0
  97. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/python_cli_implementation_with_test.intention.md +0 -0
  98. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/python_code_understanding.intention.md +0 -0
  99. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/task_implementation.intention.md +0 -0
  100. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/task_prompt_control_by_status.intention.md +0 -0
  101. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/task_stepwise_implementation_by_number.intention.md +0 -0
  102. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/intentions/task_stepwise_implementation_by_status.intention.md +0 -0
  103. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/architecture_analyst.rules.md +0 -0
  104. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/code_analyst.rules.md +0 -0
  105. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/empty.rules.md +0 -0
  106. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/error_analyst.rules.md +0 -0
  107. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/gherkin_expert.rules.md +0 -0
  108. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/js_expert_developer.rules.md +0 -0
  109. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/product_owner.rules.md +0 -0
  110. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/python_behave.rules.md +0 -0
  111. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/prompt-modules/rules/python_developer.rules.md +0 -0
  112. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.concept.exploration.md +0 -0
  113. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.concept.md +0 -0
  114. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.customer.exploration.md +0 -0
  115. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.customer.md +0 -0
  116. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.persona.exploration.md +0 -0
  117. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.persona.md +0 -0
  118. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.step.exploration.md +0 -0
  119. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.step.md +0 -0
  120. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.technology.exploration.md +0 -0
  121. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/specification_breakdown_files/template.technology.md +0 -0
  122. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.businessgoal +0 -0
  123. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.businessgoal.prompt_log.md +0 -0
  124. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.capability +0 -0
  125. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.capability.prompt_log.md +0 -0
  126. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.epic +0 -0
  127. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.epic.prompt_log.md +0 -0
  128. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.example +0 -0
  129. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.example.prompt_log.md +0 -0
  130. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.feature +0 -0
  131. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.feature.prompt_log.md +0 -0
  132. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.issue +0 -0
  133. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.issue.prompt_log.md +0 -0
  134. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.keyfeature +0 -0
  135. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.keyfeature.prompt_log.md +0 -0
  136. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.steps.prompt_log.md +0 -0
  137. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.task +0 -0
  138. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.task.prompt_log.md +0 -0
  139. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.userstory +0 -0
  140. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.userstory.prompt_log.md +0 -0
  141. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.vision +0 -0
  142. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/templates/template.vision.prompt_log.md +0 -0
  143. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/__init__.py +0 -0
  144. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_ara_config.py +0 -0
  145. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_artefact_fuzzy_search.py +0 -0
  146. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_artefact_link_updater.py +0 -0
  147. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_artefact_renamer.py +0 -0
  148. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_artefact_scan.py +0 -0
  149. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_chat.py +0 -0
  150. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_classifier.py +0 -0
  151. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_directory_navigator.py +0 -0
  152. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_file_creator.py +0 -0
  153. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_file_lister.py +0 -0
  154. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_list_filter.py +0 -0
  155. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_tag_extractor.py +0 -0
  156. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_template_manager.py +0 -0
  157. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/tests/test_update_config_prompt.py +0 -0
  158. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli/update_config_prompt.py +0 -0
  159. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/dependency_links.txt +0 -0
  160. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/entry_points.txt +0 -0
  161. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/requires.txt +0 -0
  162. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/ara_cli.egg-info/top_level.txt +0 -0
  163. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/setup.cfg +0 -0
  164. {ara_cli-0.1.9.51 → ara_cli-0.1.9.52}/setup.py +0 -0
@@ -1,3 +1,3 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: ara_cli
3
- Version: 0.1.9.51
3
+ Version: 0.1.9.52
@@ -318,55 +318,49 @@ def read_action(args):
318
318
 
319
319
 
320
320
  def reconnect_action(args):
321
- from ara_cli.artefact import Artefact
321
+ from ara_cli.artefact_models.artefact_load import artefact_from_content
322
+ from ara_cli.artefact_models.artefact_model import Contribution
322
323
  from ara_cli.artefact_reader import ArtefactReader
323
- from ara_cli.file_classifier import FileClassifier
324
- from ara_cli.directory_navigator import DirectoryNavigator
325
324
 
326
325
  classifier = args.classifier
327
326
  artefact_name = args.parameter
328
327
  parent_classifier = args.parent_classifier
329
328
  parent_name = args.parent_name
330
329
 
331
- file_classifier = FileClassifier(os)
332
- classified_artefacts_info = file_classifier.classify_files_new()
333
-
334
- all_artefact_names = [info["title"] for info in classified_artefacts_info.get(classifier, [])]
335
- if artefact_name not in all_artefact_names:
336
- suggest_close_name_matches(artefact_name, all_artefact_names)
337
- return
330
+ read_error_message = f"Could not connect {classifier} '{artefact_name}' to {parent_classifier} '{parent_name}'"
338
331
 
339
- all_artefact_names = [info["title"] for info in classified_artefacts_info.get(parent_classifier, [])]
340
- if parent_name not in all_artefact_names:
341
- suggest_close_name_matches(parent_name, all_artefact_names)
342
- return
343
-
344
- directory_navigator = DirectoryNavigator()
345
- original_directory = directory_navigator.navigate_to_target()
346
-
347
- content, file_path = ArtefactReader.read_artefact(
332
+ content, artefact_info = ArtefactReader.read_artefact(
348
333
  artefact_name=artefact_name,
349
334
  classifier=classifier
350
335
  )
336
+ if not content:
337
+ print(read_error_message)
338
+ return
351
339
 
352
- parent_content, parent_path = ArtefactReader.read_artefact(
340
+ parent_content, parent_info = ArtefactReader.read_artefact(
353
341
  artefact_name=parent_name,
354
342
  classifier=parent_classifier
355
343
  )
344
+ if not parent_content:
345
+ print(read_error_message)
346
+ return
356
347
 
357
- artefact = Artefact.from_content(
348
+ artefact = artefact_from_content(
358
349
  content=content,
359
- file_path=file_path
360
- )
361
- parent = Artefact.from_content(
362
- content=parent_content,
363
- file_path=parent_path
364
350
  )
351
+ artefact._file_path = artefact_info["file_path"]
365
352
 
366
- artefact._parent = parent
367
- artefact.write_to_file()
353
+ parent = artefact_from_content(
354
+ content=parent_content
355
+ )
368
356
 
369
- os.chdir(original_directory)
357
+ artefact.contribution = Contribution(
358
+ artefact_name=parent.title,
359
+ classifier=parent.artefact_type
360
+ )
361
+ with open(artefact.file_path, 'w') as file:
362
+ artefact_content = artefact.serialize()
363
+ file.write(artefact_content)
370
364
 
371
365
 
372
366
  def read_status_action(args):
@@ -377,7 +371,7 @@ def read_status_action(args):
377
371
  artefact_name = args.parameter
378
372
 
379
373
  file_classifier = FileClassifier(os)
380
- artefact_info = file_classifier.classify_files_new()
374
+ artefact_info = file_classifier.classify_files()
381
375
  artefact_info_dicts = artefact_info.get(classifier, [])
382
376
 
383
377
  all_artefact_names = [artefact_info["title"] for artefact_info in artefact_info_dicts]
@@ -409,7 +403,7 @@ def read_user_action(args):
409
403
  artefact_name = args.parameter
410
404
 
411
405
  file_classifier = FileClassifier(os)
412
- artefact_info = file_classifier.classify_files_new()
406
+ artefact_info = file_classifier.classify_files()
413
407
  artefact_info_dicts = artefact_info.get(classifier, [])
414
408
 
415
409
  all_artefact_names = [artefact_info["title"] for artefact_info in artefact_info_dicts]
@@ -451,7 +445,7 @@ def set_status_action(args):
451
445
  check_validity(new_status in status_tags, "Invalid status provided. Please provide a valid status.")
452
446
 
453
447
  file_classifier = FileClassifier(os)
454
- classified_artefacts_info = file_classifier.classify_files_new()
448
+ classified_artefacts_info = file_classifier.classify_files()
455
449
  classified_artefact_dict = classified_artefacts_info.get(classifier, [])
456
450
  all_artefact_names = [artefact_info["title"] for artefact_info in classified_artefact_dict]
457
451
 
@@ -488,7 +482,7 @@ def set_user_action(args):
488
482
  new_user = new_user.lstrip('@')
489
483
 
490
484
  file_classifier = FileClassifier(os)
491
- classified_artefacts_info = file_classifier.classify_files_new()
485
+ classified_artefacts_info = file_classifier.classify_files()
492
486
  classified_artefact_dict = classified_artefacts_info.get(classifier, [])
493
487
  all_artefact_names = [artefact_info["title"] for artefact_info in classified_artefact_dict]
494
488
 
@@ -527,7 +521,7 @@ def scan_action(args):
527
521
  from ara_cli.artefact_scan import find_invalid_files, show_results
528
522
  import os
529
523
 
530
- classified_artefact_info = FileClassifier(os).classify_files_new()
524
+ classified_artefact_info = FileClassifier(os).classify_files()
531
525
  invalid_artefacts = {}
532
526
  for classifier in classified_artefact_info:
533
527
  invalid = find_invalid_files(classified_artefact_info, classifier)
@@ -2,9 +2,9 @@ import os
2
2
  from functools import lru_cache
3
3
  from ara_cli.classifier import Classifier
4
4
  from ara_cli.template_manager import DirectoryNavigator
5
- from ara_cli.artefact import Artefact
5
+ from ara_cli.artefact_reader import ArtefactReader
6
+ from ara_cli.artefact_models.artefact_model import Artefact
6
7
  from ara_cli.artefact_models.artefact_templates import template_artefact_of_type
7
- from ara_cli.file_classifier import FileClassifier
8
8
  from ara_cli.artefact_fuzzy_search import suggest_close_name_matches
9
9
  from pathlib import Path
10
10
  from shutil import copyfile
@@ -75,8 +75,7 @@ class ArtefactCreator:
75
75
  return True
76
76
 
77
77
  def set_artefact_parent(self, artefact, parent_classifier, parent_file_name) -> Artefact:
78
- file_classifier = FileClassifier(os)
79
- classified_artefacts = file_classifier.classify_files()
78
+ classified_artefacts = ArtefactReader.read_artefacts()
80
79
  if parent_classifier not in classified_artefacts:
81
80
  return artefact
82
81
  artefact_list = classified_artefacts[parent_classifier]
@@ -66,7 +66,7 @@ class ArtefactLister:
66
66
  list_filter: ListFilter | None = None
67
67
  ):
68
68
  file_classifier = FileClassifier(os)
69
- classified_artefacts = file_classifier.classify_files_new()
69
+ classified_artefacts = file_classifier.classify_files()
70
70
  artefact_info = classified_artefacts.get(classifier, [])
71
71
  matching_artefact_info = [p for p in artefact_info if p["title"] == artefact_name]
72
72
 
@@ -92,7 +92,7 @@ class ArtefactLister:
92
92
  list_filter: ListFilter | None = None
93
93
  ):
94
94
  file_classifier = FileClassifier(os)
95
- classified_artefacts = file_classifier.classify_files_new()
95
+ classified_artefacts = file_classifier.classify_files()
96
96
  artefact_info = classified_artefacts.get(classifier, [])
97
97
  matching_artefact_info = [p for p in artefact_info if p["title"] == artefact_name]
98
98
 
@@ -118,21 +118,19 @@ class ArtefactLister:
118
118
  list_filter: ListFilter | None = None
119
119
  ):
120
120
  file_classifier = FileClassifier(os)
121
- classified_artefacts = file_classifier.classify_files()
122
- artefact_paths = classified_artefacts.get(classifier, [])
123
- matching_paths = [p for p in artefact_paths if os.path.basename(p).startswith(artefact_name + '.')]
121
+ classified_artefact_info = file_classifier.classify_files()
122
+ artefact_info_dict = classified_artefact_info.get(classifier, [])
124
123
 
125
- if not matching_paths:
124
+ matching_info = [info for info in artefact_info_dict if info["title"] == artefact_name]
125
+
126
+ if not matching_info:
126
127
  suggest_close_name_matches(
127
128
  artefact_name,
128
- [os.path.basename(f).split('.')[0] for f in artefact_paths]
129
+ [info["title"] for info in artefact_info_dict]
129
130
  )
130
- artefact_paths = classified_artefacts.get(classifier, [])
131
- matching_paths = [p for p in artefact_paths if os.path.basename(p).startswith(artefact_name + '.')]
132
-
133
- if len(matching_paths) == 0:
134
131
  return
135
- artefact_path = matching_paths[0]
136
- data_dir = os.path.splitext(artefact_path)[0] + '.data'
132
+
133
+ artefact_info = matching_info[0]
134
+ data_dir = os.path.splitext(artefact_info["file_path"])[0] + '.data'
137
135
  if os.path.exists(data_dir):
138
136
  list_files_in_directory(data_dir, list_filter)
@@ -11,6 +11,14 @@ import string
11
11
  ALLOWED_STATUS_VALUES = ("to-do", "in-progress", "review", "done", "closed")
12
12
 
13
13
 
14
+ def replace_space_with_underscore(input: string):
15
+ return input.replace(' ', '_')
16
+
17
+
18
+ def replace_underscore_with_space(input: string):
19
+ return input.replace('_', ' ')
20
+
21
+
14
22
  class ArtefactType(str, Enum):
15
23
  vision = "vision"
16
24
  businessgoal = "businessgoal"
@@ -44,6 +52,12 @@ class Contribution(BaseModel):
44
52
  classifier = self.classifier
45
53
  rule = self.rule
46
54
 
55
+ if artefact_name:
56
+ artefact_name = replace_space_with_underscore(artefact_name)
57
+ if artefact_name and classifier:
58
+ artefact_name = artefact_name.removesuffix(f"_{classifier}")
59
+ artefact_name = artefact_name.removesuffix(f"_{classifier.capitalize()}")
60
+ self.artefact_name = artefact_name
47
61
  if not artefact_name or not classifier:
48
62
  self.artefact_name = None
49
63
  self.classifier = None
@@ -60,7 +74,7 @@ class Contribution(BaseModel):
60
74
  return value
61
75
  if ' ' in value:
62
76
  warnings.warn(message="artefact_name can not contain spaces. Replacing spaces with '_'")
63
- value = value.replace(' ', '_')
77
+ value = replace_space_with_underscore(value)
64
78
  return value
65
79
 
66
80
  @field_validator('classifier', mode='after')
@@ -102,7 +116,7 @@ class Contribution(BaseModel):
102
116
  if not self.classifier or not self.artefact_name:
103
117
  return ""
104
118
  artefact_type = Classifier.get_artefact_title(self.classifier)
105
- artefact_name = self.artefact_name.replace("_", " ")
119
+ artefact_name = replace_underscore_with_space(self.artefact_name)
106
120
  contribution = f"{artefact_name} {artefact_type}"
107
121
  if self.rule:
108
122
  contribution = f"{contribution} using rule {self.rule}"
@@ -136,6 +150,7 @@ class Artefact(BaseModel, ABC):
136
150
  "validate_assignment": True
137
151
  }
138
152
 
153
+ _file_path: Optional[str] = None
139
154
  artefact_type: ArtefactType = Field(
140
155
  ...,
141
156
  description=f"Artefact classifier (mandatory). Allowed classifiers are {', '.join(ArtefactType)}"
@@ -165,7 +180,6 @@ class Artefact(BaseModel, ABC):
165
180
  default=None,
166
181
  description="Optional further description to understand the artefact. It is strongly recommended to add a description to every artefact."
167
182
  )
168
- _file_path: Optional[str] = None
169
183
 
170
184
  @property
171
185
  def file_path(self) -> str:
@@ -207,9 +221,7 @@ class Artefact(BaseModel, ABC):
207
221
  def validate_title(cls, v):
208
222
  if not v.strip():
209
223
  raise ValueError("artefact_title must not be empty")
210
- if ' ' in v:
211
- warnings.warn(message="artefact_name can not contain spaces. Replacing spaces with '_'")
212
- v = v.replace(' ', '_')
224
+ v = replace_space_with_underscore(v)
213
225
 
214
226
  letters = list(string.ascii_letters)
215
227
  digits = list(string.digits)
@@ -281,7 +293,7 @@ class Artefact(BaseModel, ABC):
281
293
  raise ValueError(
282
294
  f"No title found in {cls._artefact_type()}. Expected '{title_prefix}' as start of the title in line '{title_line}'")
283
295
  title = title_line[len(title_prefix):].strip()
284
- title = title.replace(' ', '_')
296
+ title = replace_space_with_underscore(title)
285
297
  return title, lines
286
298
 
287
299
  @classmethod
@@ -351,7 +363,7 @@ class Artefact(BaseModel, ABC):
351
363
  pass
352
364
 
353
365
  def _serialize_title(self) -> str:
354
- title = self.title.replace('_', ' ')
366
+ title = replace_underscore_with_space(self.title)
355
367
  return f"{self._title_prefix()} {title}"
356
368
 
357
369
  def _serialize_tags(self) -> (Optional[str]):
@@ -1,4 +1,3 @@
1
- from ara_cli.directory_navigator import DirectoryNavigator
2
1
  from ara_cli.classifier import Classifier
3
2
  from ara_cli.file_classifier import FileClassifier
4
3
  from ara_cli.artefact_models.artefact_model import Artefact
@@ -11,33 +10,28 @@ import re
11
10
  class ArtefactReader:
12
11
  @staticmethod
13
12
  def read_artefact(artefact_name, classifier):
14
- original_directory = os.getcwd()
15
- navigator = DirectoryNavigator()
16
- navigator.navigate_to_target()
17
-
18
13
  if not Classifier.is_valid_classifier(classifier):
19
14
  print("Invalid classifier provided. Please provide a valid classifier.")
20
- os.chdir(original_directory)
21
15
  return None, None
22
16
 
23
17
  file_classifier = FileClassifier(os)
24
- classified_files = file_classifier.classify_files()
25
- artefact_paths = classified_files.get(classifier, [])
18
+ classified_file_info = file_classifier.classify_files()
19
+ artefact_info_of_classifier = classified_file_info.get(classifier, [])
26
20
 
27
- for file_path in artefact_paths:
28
- if os.path.basename(file_path).startswith(artefact_name + '.'):
21
+ for artefact_info in artefact_info_of_classifier:
22
+ file_path = artefact_info["file_path"]
23
+ artefact_title = artefact_info["title"]
24
+ if artefact_title == artefact_name:
29
25
  with open(file_path, 'r') as file:
30
26
  content = file.read()
31
- os.chdir(original_directory)
32
- return content, file_path
27
+ return content, artefact_info
33
28
 
34
- print(f"No match found for artefact with name '{artefact_name}'")
29
+ all_artefact_names = [info["title"] for info in artefact_info_of_classifier]
35
30
  suggest_close_name_matches(
36
31
  artefact_name,
37
- [os.path.basename(f).split('.')[0] for f in artefact_paths]
32
+ all_artefact_names
38
33
  )
39
34
 
40
- os.chdir(original_directory)
41
35
  return None, None
42
36
 
43
37
  @staticmethod
@@ -72,7 +66,7 @@ class ArtefactReader:
72
66
 
73
67
  if classified_artefacts is None:
74
68
  file_classifier = FileClassifier(file_system)
75
- classified_artefacts = file_classifier.classify_files_new()
69
+ classified_artefacts = file_classifier.classify_files()
76
70
 
77
71
  artefacts = {artefact_type: []
78
72
  for artefact_type in classified_artefacts.keys()}
@@ -12,16 +12,17 @@ class ArtefactRenamer:
12
12
  self.link_updater = ArtefactLinkUpdater()
13
13
 
14
14
  @lru_cache(maxsize=None)
15
- def navigate_to_target(self):
15
+ def navigate_to_target(self) -> str:
16
16
  navigator = DirectoryNavigator()
17
- navigator.navigate_to_target()
17
+ original_directory = navigator.navigate_to_target()
18
+ return original_directory
18
19
 
19
20
  @lru_cache(maxsize=None)
20
21
  def compile_pattern(self, pattern):
21
22
  return re.compile(pattern)
22
23
 
23
24
  def rename(self, old_name, new_name, classifier):
24
- self.navigate_to_target()
25
+ original_directory = self.navigate_to_target()
25
26
 
26
27
  if not new_name:
27
28
  raise ValueError("New name must be provided for renaming.")
@@ -50,13 +51,10 @@ class ArtefactRenamer:
50
51
 
51
52
  # Perform the renaming of the file and directory
52
53
  self.file_system.rename(old_file_path, new_file_path)
54
+ print(f"Renamed file: {old_file_path} to {new_file_path}")
53
55
  if old_dir_exists:
54
56
  self.file_system.rename(old_dir_path, new_dir_path)
55
- # TODO: we should be able to remove this next line once ara delete ignores non-existent data folders
56
- os.makedirs(new_dir_path, exist_ok=True)
57
-
58
- print(f"Renamed file: {old_file_path} to {new_file_path}")
59
- print(f"Renamed directory: {old_dir_path} to {new_dir_path}")
57
+ print(f"Renamed directory: {old_dir_path} to {new_dir_path}")
60
58
 
61
59
  # Update the title within the artefact file
62
60
  self._update_title_in_artefact(new_file_path, new_name, classifier)
@@ -64,6 +62,8 @@ class ArtefactRenamer:
64
62
  # Update links in related artefact files
65
63
  self.link_updater.update_links_in_related_artefacts(old_name, new_name)
66
64
 
65
+ os.chdir(original_directory)
66
+
67
67
  def _update_title_in_artefact(self, artefact_path, new_title, classifier):
68
68
  # Format the new title: replace underscores with spaces
69
69
  formatted_new_title = new_title.replace('_', ' ')
@@ -1,5 +1,5 @@
1
1
  from ara_cli.classifier import Classifier
2
- from ara_cli.artefact import Artefact
2
+ from ara_cli.artefact_models.artefact_model import Artefact
3
3
  from ara_cli.artefact_fuzzy_search import find_closest_name_match
4
4
  from functools import lru_cache
5
5
  from typing import Optional
@@ -14,7 +14,7 @@ class FileClassifier:
14
14
  def find_closest_artefact_name_match(self, name, classifier) -> Optional[str]:
15
15
  classified_artefacts = self.classify_files()
16
16
  all_artefact_names = [
17
- artefact_name for artefact_name in classified_artefacts.get(classifier, [])]
17
+ info["title"] for info in classified_artefacts.get(classifier, [])]
18
18
  if name in all_artefact_names:
19
19
  return name
20
20
  return find_closest_name_match(name, all_artefact_names)
@@ -64,37 +64,7 @@ class FileClassifier:
64
64
  return classifier
65
65
  return None
66
66
 
67
- def classify_files(self, tags=None, read_content=False) -> dict[str, list]:
68
- from ara_cli.artefact_models.artefact_load import artefact_from_content
69
-
70
- files_by_classifier = {classifier: []
71
- for classifier in Classifier.ordered_classifiers()}
72
-
73
- # TODO: file location information inside the artefact.
74
- for root, _, files in self.file_system.walk("."):
75
- for file in files:
76
- file_path = self.file_system.path.join(root, file)
77
- classifier = self.classify_file(file_path, tags)
78
- if not classifier:
79
- continue
80
-
81
- if not read_content:
82
- files_by_classifier[classifier].append(file_path)
83
- continue
84
-
85
- with open(file_path, 'r') as f:
86
- content = f.read()
87
- try:
88
- artefact = artefact_from_content(content)
89
- if artefact:
90
- artefact._file_path = file_path
91
- files_by_classifier[classifier].append(artefact)
92
- except ValueError:
93
- continue
94
-
95
- return files_by_classifier
96
-
97
- def classify_files_new(self, tags=None) -> dict[str, list[dict]]:
67
+ def classify_files(self, tags=None) -> dict[str, list[dict]]:
98
68
  files_by_classifier = {classifier: [] for classifier in Classifier.ordered_classifiers()}
99
69
 
100
70
  for root, _, files in self.file_system.walk("."):
@@ -385,7 +385,7 @@ def test_read_status_action(classifier, artefact_name, artefact_exists, status,
385
385
 
386
386
  # Configure file classifier mock
387
387
  mock_classifier_instance = MockFileClassifier.return_value
388
- mock_classifier_instance.classify_files_new.return_value = {classifier: artefact_info_dicts}
388
+ mock_classifier_instance.classify_files.return_value = {classifier: artefact_info_dicts}
389
389
 
390
390
  # Configure file open mock
391
391
  mock_file_handle = MagicMock()
@@ -422,7 +422,7 @@ def read_user_action(args):
422
422
  artefact_name = args.parameter
423
423
 
424
424
  file_classifier = FileClassifier(os)
425
- artefact_info = file_classifier.classify_files_new()
425
+ artefact_info = file_classifier.classify_files()
426
426
  artefact_info_dicts = artefact_info.get(classifier, [])
427
427
 
428
428
  all_artefact_names = [artefact_info["title"] for artefact_info in artefact_info_dicts]
@@ -489,7 +489,7 @@ def test_set_status_action(classifier, artefact_name, artefact_names, new_status
489
489
 
490
490
  # Configure mock file classifier
491
491
  mock_classifier_instance = MockFileClassifier.return_value
492
- mock_classifier_instance.classify_files_new.return_value = {classifier: artefact_info_dicts}
492
+ mock_classifier_instance.classify_files.return_value = {classifier: artefact_info_dicts}
493
493
 
494
494
  # Configure mock file handling
495
495
  mock_file_handle = MagicMock()
@@ -569,7 +569,7 @@ def test_set_user_action(
569
569
 
570
570
  # Configure mocks
571
571
  mock_file_classifier_instance = MockFileClassifier.return_value
572
- mock_file_classifier_instance.classify_files_new.return_value = {classifier: artefact_info_dicts}
572
+ mock_file_classifier_instance.classify_files.return_value = {classifier: artefact_info_dicts}
573
573
 
574
574
  mock_file_handle = MagicMock()
575
575
  mock_file_handle.__enter__.return_value.read.return_value = mock_file_content
@@ -628,7 +628,7 @@ def test_scan_action_with_issues(capsys):
628
628
  patch("builtins.open", mock_open()) as m:
629
629
 
630
630
  mock_classifier = MockFileClassifier.return_value
631
- mock_classifier.classify_files_new.return_value = {
631
+ mock_classifier.classify_files.return_value = {
632
632
  "classifier1": ["file1.txt"],
633
633
  "classifier2": ["file2.txt"]
634
634
  }
@@ -667,7 +667,7 @@ def test_scan_action_all_good(capsys):
667
667
  patch("builtins.open", mock_open()) as m:
668
668
 
669
669
  mock_classifier = MockFileClassifier.return_value
670
- mock_classifier.classify_files_new.return_value = {
670
+ mock_classifier.classify_files.return_value = {
671
671
  "classifier1": ["file1.txt"],
672
672
  "classifier2": ["file2.txt"]
673
673
  }