devflow-engine 1.0.0__py3-none-any.whl
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.
- devflow_engine/__init__.py +3 -0
- devflow_engine/agentic_prompts.py +100 -0
- devflow_engine/agentic_runtime.py +398 -0
- devflow_engine/api_key_flow_harness.py +539 -0
- devflow_engine/api_keys.py +357 -0
- devflow_engine/bootstrap/__init__.py +2 -0
- devflow_engine/bootstrap/provision_from_template.py +84 -0
- devflow_engine/cli/__init__.py +0 -0
- devflow_engine/cli/app.py +7270 -0
- devflow_engine/core/__init__.py +0 -0
- devflow_engine/core/config.py +86 -0
- devflow_engine/core/logging.py +29 -0
- devflow_engine/core/paths.py +45 -0
- devflow_engine/core/toml_kv.py +33 -0
- devflow_engine/devflow_event_worker.py +1292 -0
- devflow_engine/devflow_state.py +201 -0
- devflow_engine/devin2/__init__.py +9 -0
- devflow_engine/devin2/agent_definition.py +120 -0
- devflow_engine/devin2/pi_runner.py +204 -0
- devflow_engine/devin_orchestration.py +69 -0
- devflow_engine/docs/prompts/anti-patterns.md +42 -0
- devflow_engine/docs/prompts/devin-agent-prompt.md +55 -0
- devflow_engine/docs/prompts/devin2-agent-prompt.md +81 -0
- devflow_engine/docs/prompts/examples/devin-vapi-clone-reference-exchange.json +85 -0
- devflow_engine/doctor/__init__.py +2 -0
- devflow_engine/doctor/triage.py +140 -0
- devflow_engine/error/__init__.py +0 -0
- devflow_engine/error/remediation.py +21 -0
- devflow_engine/errors/error_solver_dag.py +522 -0
- devflow_engine/errors/runtime_observability.py +67 -0
- devflow_engine/idea/__init__.py +4 -0
- devflow_engine/idea/actors.py +481 -0
- devflow_engine/idea/agentic.py +465 -0
- devflow_engine/idea/analyze.py +93 -0
- devflow_engine/idea/devin_chat_dag.py +1 -0
- devflow_engine/idea/diff.py +99 -0
- devflow_engine/idea/drafts.py +446 -0
- devflow_engine/idea/idea_creation_dag.py +643 -0
- devflow_engine/idea/ideation_enrichment.py +355 -0
- devflow_engine/idea/ideation_enrichment_worker.py +19 -0
- devflow_engine/idea/paths.py +28 -0
- devflow_engine/idea/promote.py +53 -0
- devflow_engine/idea/redaction.py +27 -0
- devflow_engine/idea/repo_tools.py +1277 -0
- devflow_engine/idea/response_mode.py +30 -0
- devflow_engine/idea/story_pipeline.py +1585 -0
- devflow_engine/idea/sufficiency.py +376 -0
- devflow_engine/idea/traditional_stories.py +1257 -0
- devflow_engine/implementation/__init__.py +0 -0
- devflow_engine/implementation/alembic_preflight.py +700 -0
- devflow_engine/implementation/dag.py +8450 -0
- devflow_engine/implementation/green_gate.py +93 -0
- devflow_engine/implementation/prompts.py +108 -0
- devflow_engine/implementation/test_runtime.py +623 -0
- devflow_engine/integration/__init__.py +19 -0
- devflow_engine/integration/agentic.py +66 -0
- devflow_engine/integration/dag.py +3539 -0
- devflow_engine/integration/prompts.py +114 -0
- devflow_engine/integration/supabase_schema.sql +31 -0
- devflow_engine/integration/supabase_sync.py +177 -0
- devflow_engine/llm/__init__.py +1 -0
- devflow_engine/llm/cli_one_shot.py +84 -0
- devflow_engine/llm/cli_stream.py +371 -0
- devflow_engine/llm/execution_context.py +26 -0
- devflow_engine/llm/invoke.py +1322 -0
- devflow_engine/llm/provider_api.py +304 -0
- devflow_engine/llm/repo_knowledge.py +588 -0
- devflow_engine/llm_primitives.py +315 -0
- devflow_engine/orchestration.py +62 -0
- devflow_engine/planning/__init__.py +0 -0
- devflow_engine/planning/analyze_repo.py +92 -0
- devflow_engine/planning/render_drafts.py +133 -0
- devflow_engine/playground/__init__.py +0 -0
- devflow_engine/playground/hooks.py +26 -0
- devflow_engine/playwright_workflow/__init__.py +5 -0
- devflow_engine/playwright_workflow/dag.py +1317 -0
- devflow_engine/process/__init__.py +5 -0
- devflow_engine/process/dag.py +59 -0
- devflow_engine/project_registration/__init__.py +3 -0
- devflow_engine/project_registration/dag.py +1581 -0
- devflow_engine/project_registry.py +109 -0
- devflow_engine/prompts/devin/generic/prompt.md +6 -0
- devflow_engine/prompts/devin/ideation/prompt.md +263 -0
- devflow_engine/prompts/devin/ideation/scenarios.md +5 -0
- devflow_engine/prompts/devin/ideation_loop/prompt.md +6 -0
- devflow_engine/prompts/devin/insight/prompt.md +11 -0
- devflow_engine/prompts/devin/insight/scenarios.md +5 -0
- devflow_engine/prompts/devin/intake/prompt.md +15 -0
- devflow_engine/prompts/devin/iterate/prompt.md +12 -0
- devflow_engine/prompts/devin/shared/eval_doctrine.md +9 -0
- devflow_engine/prompts/devin/shared/principles.md +246 -0
- devflow_engine/prompts/devin_eval/assessment/prompt.md +18 -0
- devflow_engine/prompts/idea/api_ideation_agent/prompt.md +8 -0
- devflow_engine/prompts/idea/api_insight_agent/prompt.md +8 -0
- devflow_engine/prompts/idea/response_doctrine/prompt.md +18 -0
- devflow_engine/prompts/implementation/dependency_assessment/prompt.md +12 -0
- devflow_engine/prompts/implementation/green/green/prompt.md +11 -0
- devflow_engine/prompts/implementation/green/node_config/prompt.md +3 -0
- devflow_engine/prompts/implementation/green_review/outcome_review/prompt.md +5 -0
- devflow_engine/prompts/implementation/green_review/prior_run_review/prompt.md +5 -0
- devflow_engine/prompts/implementation/red/prompt.md +27 -0
- devflow_engine/prompts/implementation/redreview/prompt.md +23 -0
- devflow_engine/prompts/implementation/redreview_repair/prompt.md +16 -0
- devflow_engine/prompts/implementation/setupdoc/prompt.md +10 -0
- devflow_engine/prompts/implementation/story_planning/prompt.md +13 -0
- devflow_engine/prompts/implementation/test_design/prompt.md +27 -0
- devflow_engine/prompts/integration/README.md +185 -0
- devflow_engine/prompts/integration/green/example.md +67 -0
- devflow_engine/prompts/integration/green/green/prompt.md +10 -0
- devflow_engine/prompts/integration/green/node_config/prompt.md +42 -0
- devflow_engine/prompts/integration/green/past_prompts/20260417T212300/green/prompt.md +15 -0
- devflow_engine/prompts/integration/green/past_prompts/20260417T212300/node_config/prompt.md +42 -0
- devflow_engine/prompts/integration/green_enrich/example.md +79 -0
- devflow_engine/prompts/integration/green_enrich/green_enrich/prompt.md +9 -0
- devflow_engine/prompts/integration/green_enrich/node_config/prompt.md +41 -0
- devflow_engine/prompts/integration/green_enrich/past_prompts/20260417T212300/green_enrich/prompt.md +14 -0
- devflow_engine/prompts/integration/green_enrich/past_prompts/20260417T212300/node_config/prompt.md +41 -0
- devflow_engine/prompts/integration/red/code_repair/prompt.md +12 -0
- devflow_engine/prompts/integration/red/example.md +152 -0
- devflow_engine/prompts/integration/red/node_config/prompt.md +86 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T212300/code_repair/prompt.md +19 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T212300/node_config/prompt.md +84 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T212300/red/prompt.md +16 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T212300/red_repair/prompt.md +15 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T215032/code_repair/prompt.md +10 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T215032/node_config/prompt.md +84 -0
- devflow_engine/prompts/integration/red/past_prompts/20260417T215032/red_repair/prompt.md +11 -0
- devflow_engine/prompts/integration/red/red/prompt.md +11 -0
- devflow_engine/prompts/integration/red/red_repair/prompt.md +12 -0
- devflow_engine/prompts/integration/red_review/example.md +71 -0
- devflow_engine/prompts/integration/red_review/node_config/prompt.md +41 -0
- devflow_engine/prompts/integration/red_review/past_prompts/20260417T212300/node_config/prompt.md +41 -0
- devflow_engine/prompts/integration/red_review/past_prompts/20260417T212300/red_review/prompt.md +15 -0
- devflow_engine/prompts/integration/red_review/red_review/prompt.md +9 -0
- devflow_engine/prompts/integration/resolve/example.md +111 -0
- devflow_engine/prompts/integration/resolve/node_config/prompt.md +64 -0
- devflow_engine/prompts/integration/resolve/past_prompts/20260417T212300/node_config/prompt.md +64 -0
- devflow_engine/prompts/integration/resolve/past_prompts/20260417T212300/resolve_implicated_users/prompt.md +15 -0
- devflow_engine/prompts/integration/resolve/past_prompts/20260417T212300/resolve_side_effects/prompt.md +15 -0
- devflow_engine/prompts/integration/resolve/resolve_implicated_users/prompt.md +10 -0
- devflow_engine/prompts/integration/resolve/resolve_side_effects/prompt.md +10 -0
- devflow_engine/prompts/integration/validate/build_idea_acceptance_coverage/prompt.md +12 -0
- devflow_engine/prompts/integration/validate/code_repair/prompt.md +13 -0
- devflow_engine/prompts/integration/validate/example.md +143 -0
- devflow_engine/prompts/integration/validate/node_config/prompt.md +87 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T212300/code_repair/prompt.md +19 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T212300/node_config/prompt.md +67 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T212300/validate_enrich_gate/prompt.md +17 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T212300/validate_repair/prompt.md +16 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T215032/code_repair/prompt.md +10 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T215032/node_config/prompt.md +67 -0
- devflow_engine/prompts/integration/validate/past_prompts/20260417T215032/validate_repair/prompt.md +9 -0
- devflow_engine/prompts/integration/validate/validate_enrich_gate/prompt.md +10 -0
- devflow_engine/prompts/integration/validate/validate_repair/prompt.md +20 -0
- devflow_engine/prompts/integration/write_workflows/example.md +100 -0
- devflow_engine/prompts/integration/write_workflows/node_config/prompt.md +44 -0
- devflow_engine/prompts/integration/write_workflows/past_prompts/20260417T212300/node_config/prompt.md +44 -0
- devflow_engine/prompts/integration/write_workflows/past_prompts/20260417T212300/write_workflows/prompt.md +17 -0
- devflow_engine/prompts/integration/write_workflows/write_workflows/prompt.md +11 -0
- devflow_engine/prompts/iterate/README.md +7 -0
- devflow_engine/prompts/iterate/coder/prompt.md +11 -0
- devflow_engine/prompts/iterate/framer/prompt.md +11 -0
- devflow_engine/prompts/iterate/iterator/prompt.md +13 -0
- devflow_engine/prompts/iterate/observer/prompt.md +11 -0
- devflow_engine/prompts/recovery/diagnosis/prompt.md +7 -0
- devflow_engine/prompts/recovery/execution/prompt.md +8 -0
- devflow_engine/prompts/recovery/execution_verification/prompt.md +7 -0
- devflow_engine/prompts/recovery/failure_investigation/prompt.md +10 -0
- devflow_engine/prompts/recovery/preflight_health_repo_repair/prompt.md +8 -0
- devflow_engine/prompts/recovery/remediation_execution/prompt.md +11 -0
- devflow_engine/prompts/recovery/root_cause_investigation/prompt.md +12 -0
- devflow_engine/prompts/scope_idea/doctrine/prompt.md +7 -0
- devflow_engine/prompts/source_doc_eval/document/prompt.md +6 -0
- devflow_engine/prompts/source_doc_eval/targeted_mutation/prompt.md +9 -0
- devflow_engine/prompts/source_doc_mutation/domain_entities/prompt.md +6 -0
- devflow_engine/prompts/source_doc_mutation/product_brief/prompt.md +6 -0
- devflow_engine/prompts/source_doc_mutation/project_doc_coherence/prompt.md +7 -0
- devflow_engine/prompts/source_doc_mutation/project_doc_render/prompt.md +9 -0
- devflow_engine/prompts/source_doc_mutation/source_doc_coherence/prompt.md +5 -0
- devflow_engine/prompts/source_doc_mutation/source_doc_enrichment_coherence/prompt.md +6 -0
- devflow_engine/prompts/source_doc_mutation/user_workflows/prompt.md +6 -0
- devflow_engine/prompts/source_scope/doctrine/prompt.md +10 -0
- devflow_engine/prompts/ui_grounding/doctrine/prompt.md +7 -0
- devflow_engine/recovery/__init__.py +3 -0
- devflow_engine/recovery/dag.py +2609 -0
- devflow_engine/recovery/models.py +220 -0
- devflow_engine/refactor.py +93 -0
- devflow_engine/registry/__init__.py +1 -0
- devflow_engine/registry/cards.py +238 -0
- devflow_engine/registry/domain_normalize.py +60 -0
- devflow_engine/registry/effects.py +65 -0
- devflow_engine/registry/enforce_report.py +150 -0
- devflow_engine/registry/module_cards_classify.py +164 -0
- devflow_engine/registry/module_cards_draft.py +184 -0
- devflow_engine/registry/module_cards_gate.py +59 -0
- devflow_engine/registry/packages.py +347 -0
- devflow_engine/registry/pathways.py +323 -0
- devflow_engine/review/__init__.py +11 -0
- devflow_engine/review/dag.py +588 -0
- devflow_engine/review/review_story.py +67 -0
- devflow_engine/scope_idea/__init__.py +3 -0
- devflow_engine/scope_idea/agentic.py +39 -0
- devflow_engine/scope_idea/dag.py +1069 -0
- devflow_engine/scope_idea/models.py +175 -0
- devflow_engine/skills/builtins/devflow/queue_failure_investigation/SKILL.md +112 -0
- devflow_engine/skills/builtins/devflow/queue_idea_to_story/SKILL.md +120 -0
- devflow_engine/skills/builtins/devflow/queue_integration/SKILL.md +105 -0
- devflow_engine/skills/builtins/devflow/queue_recovery/SKILL.md +108 -0
- devflow_engine/skills/builtins/devflow/queue_runtime_core/SKILL.md +155 -0
- devflow_engine/skills/builtins/devflow/queue_story_implementation/SKILL.md +122 -0
- devflow_engine/skills/builtins/devin/idea_to_story_handoff/SKILL.md +120 -0
- devflow_engine/skills/builtins/devin/ideation/SKILL.md +168 -0
- devflow_engine/skills/builtins/devin/ideation/state-and-phrasing-reference.md +18 -0
- devflow_engine/skills/builtins/devin/insight/SKILL.md +22 -0
- devflow_engine/skills/registry.example.yaml +42 -0
- devflow_engine/source_doc_assumptions.py +291 -0
- devflow_engine/source_doc_mutation_dag.py +1606 -0
- devflow_engine/source_doc_mutation_eval.py +417 -0
- devflow_engine/source_doc_mutation_worker.py +25 -0
- devflow_engine/source_docs_schema.py +207 -0
- devflow_engine/source_docs_updater.py +309 -0
- devflow_engine/source_scope/__init__.py +15 -0
- devflow_engine/source_scope/agentic.py +45 -0
- devflow_engine/source_scope/dag.py +1626 -0
- devflow_engine/source_scope/models.py +177 -0
- devflow_engine/stores/__init__.py +0 -0
- devflow_engine/stores/execution_store.py +3534 -0
- devflow_engine/story/__init__.py +0 -0
- devflow_engine/story/contracts.py +160 -0
- devflow_engine/story/discovery.py +47 -0
- devflow_engine/story/evidence.py +118 -0
- devflow_engine/story/hashing.py +27 -0
- devflow_engine/story/implemented_queue_purge.py +148 -0
- devflow_engine/story/indexer.py +105 -0
- devflow_engine/story/io.py +20 -0
- devflow_engine/story/markdown_contracts.py +298 -0
- devflow_engine/story/reconciliation.py +408 -0
- devflow_engine/story/validate_stories.py +149 -0
- devflow_engine/story/validate_tests_story.py +512 -0
- devflow_engine/story/validation.py +133 -0
- devflow_engine/ui_grounding/__init__.py +11 -0
- devflow_engine/ui_grounding/agentic.py +31 -0
- devflow_engine/ui_grounding/dag.py +874 -0
- devflow_engine/ui_grounding/models.py +224 -0
- devflow_engine/ui_grounding/pencil_bridge.py +247 -0
- devflow_engine/vendor/__init__.py +0 -0
- devflow_engine/vendor/datalumina_genai/__init__.py +11 -0
- devflow_engine/vendor/datalumina_genai/core/__init__.py +0 -0
- devflow_engine/vendor/datalumina_genai/core/exceptions.py +9 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/__init__.py +0 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/agent.py +48 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/agent_streaming_node.py +26 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/base.py +89 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/concurrent.py +30 -0
- devflow_engine/vendor/datalumina_genai/core/nodes/router.py +69 -0
- devflow_engine/vendor/datalumina_genai/core/schema.py +72 -0
- devflow_engine/vendor/datalumina_genai/core/task.py +52 -0
- devflow_engine/vendor/datalumina_genai/core/validate.py +139 -0
- devflow_engine/vendor/datalumina_genai/core/workflow.py +200 -0
- devflow_engine/worker.py +1086 -0
- devflow_engine/worker_guard.py +233 -0
- devflow_engine-1.0.0.dist-info/METADATA +235 -0
- devflow_engine-1.0.0.dist-info/RECORD +393 -0
- devflow_engine-1.0.0.dist-info/WHEEL +4 -0
- devflow_engine-1.0.0.dist-info/entry_points.txt +3 -0
- devin/__init__.py +6 -0
- devin/dag.py +58 -0
- devin/dag_two_arm.py +138 -0
- devin/devin_chat_scenario_catalog.json +588 -0
- devin/devin_eval.py +677 -0
- devin/nodes/__init__.py +0 -0
- devin/nodes/ideation/__init__.py +0 -0
- devin/nodes/ideation/node.py +195 -0
- devin/nodes/ideation/playground.py +267 -0
- devin/nodes/ideation/prompt.md +65 -0
- devin/nodes/ideation/scenarios/continue_refinement.py +13 -0
- devin/nodes/ideation/scenarios/continue_refinement_evals.py +18 -0
- devin/nodes/ideation/scenarios/idea_fits_existing_patterns.py +17 -0
- devin/nodes/ideation/scenarios/idea_fits_existing_patterns_evals.py +16 -0
- devin/nodes/ideation/scenarios/large_idea_split.py +4 -0
- devin/nodes/ideation/scenarios/large_idea_split_evals.py +17 -0
- devin/nodes/ideation/scenarios/source_documentation_added.py +4 -0
- devin/nodes/ideation/scenarios/source_documentation_added_evals.py +16 -0
- devin/nodes/ideation/scenarios/user_says_create_it.py +30 -0
- devin/nodes/ideation/scenarios/user_says_create_it_evals.py +23 -0
- devin/nodes/ideation/scenarios/vague_idea.py +16 -0
- devin/nodes/ideation/scenarios/vague_idea_evals.py +47 -0
- devin/nodes/ideation/tools.json +312 -0
- devin/nodes/insight/__init__.py +0 -0
- devin/nodes/insight/node.py +49 -0
- devin/nodes/insight/playground.py +154 -0
- devin/nodes/insight/prompt.md +61 -0
- devin/nodes/insight/scenarios/architecture_pattern_query.py +15 -0
- devin/nodes/insight/scenarios/architecture_pattern_query_evals.py +25 -0
- devin/nodes/insight/scenarios/codebase_exploration.py +15 -0
- devin/nodes/insight/scenarios/codebase_exploration_evals.py +23 -0
- devin/nodes/insight/scenarios/devin_ideation_routing.py +19 -0
- devin/nodes/insight/scenarios/devin_ideation_routing_evals.py +39 -0
- devin/nodes/insight/scenarios/devin_insight_routing.py +20 -0
- devin/nodes/insight/scenarios/devin_insight_routing_evals.py +40 -0
- devin/nodes/insight/scenarios/operational_debugging.py +15 -0
- devin/nodes/insight/scenarios/operational_debugging_evals.py +23 -0
- devin/nodes/insight/scenarios/operational_question.py +9 -0
- devin/nodes/insight/scenarios/operational_question_evals.py +8 -0
- devin/nodes/insight/scenarios/queue_status.py +15 -0
- devin/nodes/insight/scenarios/queue_status_evals.py +23 -0
- devin/nodes/insight/scenarios/source_doc_explanation.py +14 -0
- devin/nodes/insight/scenarios/source_doc_explanation_evals.py +21 -0
- devin/nodes/insight/scenarios/worker_state_check.py +15 -0
- devin/nodes/insight/scenarios/worker_state_check_evals.py +22 -0
- devin/nodes/insight/tools.json +126 -0
- devin/nodes/intake/__init__.py +0 -0
- devin/nodes/intake/node.py +27 -0
- devin/nodes/intake/playground.py +47 -0
- devin/nodes/intake/prompt.md +12 -0
- devin/nodes/intake/scenarios/ideation_routing.py +4 -0
- devin/nodes/intake/scenarios/ideation_routing_evals.py +5 -0
- devin/nodes/intake/scenarios/insight_routing.py +4 -0
- devin/nodes/intake/scenarios/insight_routing_evals.py +5 -0
- devin/nodes/iterate/README.md +44 -0
- devin/nodes/iterate/__init__.py +1 -0
- devin/nodes/iterate/_archived_design_stages/01-objectives-requirements.md +112 -0
- devin/nodes/iterate/_archived_design_stages/02-evals.md +131 -0
- devin/nodes/iterate/_archived_design_stages/03-tools-and-boundaries.md +110 -0
- devin/nodes/iterate/_archived_design_stages/04-harness-and-playground.md +32 -0
- devin/nodes/iterate/_archived_design_stages/05-prompt-deferred.md +11 -0
- devin/nodes/iterate/_archived_design_stages/coder_agent_design/01-objectives-requirements.md +20 -0
- devin/nodes/iterate/_archived_design_stages/coder_agent_design/02-evals.md +8 -0
- devin/nodes/iterate/_archived_design_stages/coder_agent_design/03-tools-and-boundaries.md +14 -0
- devin/nodes/iterate/_archived_design_stages/coder_agent_design/04-harness-and-playground.md +12 -0
- devin/nodes/iterate/_archived_design_stages/framer_agent_design/01-objectives-requirements.md +20 -0
- devin/nodes/iterate/_archived_design_stages/framer_agent_design/02-evals.md +8 -0
- devin/nodes/iterate/_archived_design_stages/framer_agent_design/03-tools-and-boundaries.md +13 -0
- devin/nodes/iterate/_archived_design_stages/framer_agent_design/04-harness-and-playground.md +12 -0
- devin/nodes/iterate/_archived_design_stages/iterator_agent_design/01-objectives-requirements.md +25 -0
- devin/nodes/iterate/_archived_design_stages/iterator_agent_design/02-evals.md +9 -0
- devin/nodes/iterate/_archived_design_stages/iterator_agent_design/03-tools-and-boundaries.md +14 -0
- devin/nodes/iterate/_archived_design_stages/iterator_agent_design/04-harness-and-playground.md +12 -0
- devin/nodes/iterate/_archived_design_stages/observer_agent_design/01-objectives-requirements.md +20 -0
- devin/nodes/iterate/_archived_design_stages/observer_agent_design/02-evals.md +8 -0
- devin/nodes/iterate/_archived_design_stages/observer_agent_design/03-tools-and-boundaries.md +14 -0
- devin/nodes/iterate/_archived_design_stages/observer_agent_design/04-harness-and-playground.md +13 -0
- devin/nodes/iterate/agent-roles.md +89 -0
- devin/nodes/iterate/agents/README.md +10 -0
- devin/nodes/iterate/artifacts.md +504 -0
- devin/nodes/iterate/contract.md +100 -0
- devin/nodes/iterate/eval-plan.md +74 -0
- devin/nodes/iterate/node.py +100 -0
- devin/nodes/iterate/pipeline/README.md +13 -0
- devin/nodes/iterate/playground-contract.md +76 -0
- devin/nodes/iterate/prompt.md +11 -0
- devin/nodes/iterate/scenarios/README.md +38 -0
- devin/nodes/iterate/scenarios/artifact-and-loop-scenarios.md +101 -0
- devin/nodes/iterate/scenarios/coder_artifact_alignment.py +32 -0
- devin/nodes/iterate/scenarios/coder_artifact_alignment_evals.py +45 -0
- devin/nodes/iterate/scenarios/coder_bounded_fix.py +27 -0
- devin/nodes/iterate/scenarios/coder_bounded_fix_evals.py +45 -0
- devin/nodes/iterate/scenarios/devin_iterate_routing.py +21 -0
- devin/nodes/iterate/scenarios/devin_iterate_routing_evals.py +36 -0
- devin/nodes/iterate/scenarios/framer_scope_boundary.py +25 -0
- devin/nodes/iterate/scenarios/framer_scope_boundary_evals.py +57 -0
- devin/nodes/iterate/scenarios/framer_task_framing.py +25 -0
- devin/nodes/iterate/scenarios/framer_task_framing_evals.py +58 -0
- devin/nodes/iterate/scenarios/iterate_error_fix.py +21 -0
- devin/nodes/iterate/scenarios/iterate_error_fix_evals.py +39 -0
- devin/nodes/iterate/scenarios/iterate_quick_change.py +21 -0
- devin/nodes/iterate/scenarios/iterate_quick_change_evals.py +35 -0
- devin/nodes/iterate/scenarios/iterate_to_idea_promotion.py +23 -0
- devin/nodes/iterate/scenarios/iterate_to_idea_promotion_evals.py +53 -0
- devin/nodes/iterate/scenarios/iterate_to_insight_reroute.py +23 -0
- devin/nodes/iterate/scenarios/iterate_to_insight_reroute_evals.py +53 -0
- devin/nodes/iterate/scenarios/observer_evidence_seam.py +28 -0
- devin/nodes/iterate/scenarios/observer_evidence_seam_evals.py +55 -0
- devin/nodes/iterate/scenarios/observer_repro_creation.py +28 -0
- devin/nodes/iterate/scenarios/observer_repro_creation_evals.py +45 -0
- devin/nodes/iterate/scenarios/routing-matrix.md +45 -0
- devin/nodes/shared/__init__.py +0 -0
- devin/nodes/shared/filemaker_expert.md +80 -0
- devin/nodes/shared/filemaker_expert.py +354 -0
- devin/nodes/shared/filemaker_expert_eval/runner.py +176 -0
- devin/nodes/shared/filemaker_expert_eval/scenarios.json +65 -0
- devin/nodes/shared/goldilocks_advisor_eval/runner.py +214 -0
- devin/nodes/shared/goldilocks_advisor_eval/scenarios.json +58 -0
- devin/nodes/shared/helpers.py +156 -0
- devin/nodes/shared/idea_compliance_advisor_eval/runner.py +252 -0
- devin/nodes/shared/idea_compliance_advisor_eval/scenarios.json +75 -0
- devin/nodes/shared/models.py +44 -0
- devin/nodes/shared/post.py +40 -0
- devin/nodes/shared/router.py +107 -0
- devin/nodes/shared/tools.py +191 -0
- devin/shared/devin-chat-rubric.md +237 -0
- devin/shared/devin-chat-scenario-suite.md +90 -0
- devin/shared/eval_doctrine.md +9 -0
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import os
|
|
4
|
+
import signal
|
|
5
|
+
from dataclasses import dataclass
|
|
6
|
+
from pathlib import Path
|
|
7
|
+
from typing import Any
|
|
8
|
+
|
|
9
|
+
try: # pragma: no cover - python 3.11+
|
|
10
|
+
import tomllib
|
|
11
|
+
except Exception: # pragma: no cover
|
|
12
|
+
tomllib = None # type: ignore
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
_TRUE_VALUES = {"1", "true", "yes", "on"}
|
|
16
|
+
_FALSE_VALUES = {"0", "false", "no", "off"}
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
@dataclass(frozen=True)
|
|
20
|
+
class WorkerGuardBlock:
|
|
21
|
+
reason: str
|
|
22
|
+
source: str
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
class WorkerGuardEnabledError(RuntimeError):
|
|
26
|
+
def __init__(self, block: WorkerGuardBlock):
|
|
27
|
+
self.block = block
|
|
28
|
+
super().__init__(block.reason)
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
def _global_devflow_dir() -> Path:
|
|
32
|
+
home = os.environ.get("DEVFLOW_HOME")
|
|
33
|
+
if home:
|
|
34
|
+
return Path(home).expanduser() / ".devflow"
|
|
35
|
+
return Path.home() / ".devflow"
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
def _read_toml(path: Path) -> dict[str, object]:
|
|
39
|
+
if tomllib is None or not path.exists():
|
|
40
|
+
return {}
|
|
41
|
+
try:
|
|
42
|
+
with path.open("rb") as fh:
|
|
43
|
+
data = tomllib.load(fh)
|
|
44
|
+
except Exception:
|
|
45
|
+
return {}
|
|
46
|
+
return data if isinstance(data, dict) else {}
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def _nested_get(data: dict[str, object], *keys: str) -> object | None:
|
|
50
|
+
cur: object = data
|
|
51
|
+
for key in keys:
|
|
52
|
+
if not isinstance(cur, dict):
|
|
53
|
+
return None
|
|
54
|
+
cur = cur.get(key)
|
|
55
|
+
return cur
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
def _parse_bool(value: object) -> bool | None:
|
|
59
|
+
if isinstance(value, bool):
|
|
60
|
+
return value
|
|
61
|
+
if value is None:
|
|
62
|
+
return None
|
|
63
|
+
text = str(value).strip().lower()
|
|
64
|
+
if not text:
|
|
65
|
+
return True
|
|
66
|
+
if text in _TRUE_VALUES:
|
|
67
|
+
return True
|
|
68
|
+
if text in _FALSE_VALUES:
|
|
69
|
+
return False
|
|
70
|
+
return None
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
def _flag_file_enabled(path: Path) -> bool:
|
|
74
|
+
if not path.exists():
|
|
75
|
+
return False
|
|
76
|
+
try:
|
|
77
|
+
raw = path.read_text(encoding="utf-8").strip()
|
|
78
|
+
except Exception:
|
|
79
|
+
return True
|
|
80
|
+
parsed = _parse_bool(raw)
|
|
81
|
+
return True if parsed is None else parsed
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
def get_worker_guard_block(*, repo_root: Path | None) -> WorkerGuardBlock | None:
|
|
85
|
+
env_value = _parse_bool(os.environ.get("DEVFLOW_DO_NOT_RUN_WORKER"))
|
|
86
|
+
if env_value is True:
|
|
87
|
+
return WorkerGuardBlock(
|
|
88
|
+
reason="Worker start is disabled by DEVFLOW_DO_NOT_RUN_WORKER.",
|
|
89
|
+
source="env:DEVFLOW_DO_NOT_RUN_WORKER",
|
|
90
|
+
)
|
|
91
|
+
|
|
92
|
+
global_devflow_dir = _global_devflow_dir()
|
|
93
|
+
global_flag_path = global_devflow_dir / "do-not-run-worker"
|
|
94
|
+
if _flag_file_enabled(global_flag_path):
|
|
95
|
+
return WorkerGuardBlock(
|
|
96
|
+
reason="Worker start is disabled by global flag file ~/.devflow/do-not-run-worker.",
|
|
97
|
+
source=str(global_flag_path),
|
|
98
|
+
)
|
|
99
|
+
|
|
100
|
+
global_cfg = _read_toml(global_devflow_dir / "config.toml")
|
|
101
|
+
global_cfg_value = _parse_bool(_nested_get(global_cfg, "worker", "do_not_run"))
|
|
102
|
+
if global_cfg_value is True:
|
|
103
|
+
return WorkerGuardBlock(
|
|
104
|
+
reason="Worker start is disabled by global config worker.do_not_run=true.",
|
|
105
|
+
source=str(global_devflow_dir / "config.toml"),
|
|
106
|
+
)
|
|
107
|
+
|
|
108
|
+
if repo_root is None:
|
|
109
|
+
return None
|
|
110
|
+
|
|
111
|
+
repo_root = repo_root.expanduser().resolve()
|
|
112
|
+
project_flag_path = repo_root / ".devflow" / "do-not-run-worker"
|
|
113
|
+
if _flag_file_enabled(project_flag_path):
|
|
114
|
+
return WorkerGuardBlock(
|
|
115
|
+
reason=f"Worker start is disabled by project flag file {project_flag_path}.",
|
|
116
|
+
source=str(project_flag_path),
|
|
117
|
+
)
|
|
118
|
+
|
|
119
|
+
project_cfg_path = repo_root / ".devflow" / "config.toml"
|
|
120
|
+
project_cfg = _read_toml(project_cfg_path)
|
|
121
|
+
project_cfg_value = _parse_bool(_nested_get(project_cfg, "worker", "do_not_run"))
|
|
122
|
+
if project_cfg_value is True:
|
|
123
|
+
return WorkerGuardBlock(
|
|
124
|
+
reason=f"Worker start is disabled by project config worker.do_not_run=true in {project_cfg_path}.",
|
|
125
|
+
source=str(project_cfg_path),
|
|
126
|
+
)
|
|
127
|
+
|
|
128
|
+
return None
|
|
129
|
+
|
|
130
|
+
|
|
131
|
+
def ensure_worker_start_allowed(*, repo_root: Path | None) -> None:
|
|
132
|
+
block = get_worker_guard_block(repo_root=repo_root)
|
|
133
|
+
if block is not None:
|
|
134
|
+
raise WorkerGuardEnabledError(block)
|
|
135
|
+
|
|
136
|
+
|
|
137
|
+
def _check_no_running_worker_process(
|
|
138
|
+
*, repo_root: Path, project_id: str
|
|
139
|
+
) -> WorkerGuardBlock | None:
|
|
140
|
+
"""Check if a live worker process is already running for this project.
|
|
141
|
+
|
|
142
|
+
Returns a WorkerGuardBlock if a running worker is found and confirmed alive.
|
|
143
|
+
If a stale running row exists (dead process), marks it stopped and returns None.
|
|
144
|
+
"""
|
|
145
|
+
import re
|
|
146
|
+
import sqlite3
|
|
147
|
+
import subprocess
|
|
148
|
+
import time
|
|
149
|
+
|
|
150
|
+
repo_root = repo_root.expanduser().resolve()
|
|
151
|
+
db_path = repo_root / ".devflow" / "execution.sqlite"
|
|
152
|
+
if not db_path.exists():
|
|
153
|
+
return None
|
|
154
|
+
|
|
155
|
+
try:
|
|
156
|
+
conn = sqlite3.connect(db_path)
|
|
157
|
+
conn.row_factory = sqlite3.Row
|
|
158
|
+
except Exception:
|
|
159
|
+
return None
|
|
160
|
+
|
|
161
|
+
try:
|
|
162
|
+
now = int(time.time())
|
|
163
|
+
rows = conn.execute(
|
|
164
|
+
(
|
|
165
|
+
"SELECT worker_id, status, active_queue_type, active_item_id, updated_at "
|
|
166
|
+
"FROM project_workers "
|
|
167
|
+
"WHERE project_id=? AND status='running'"
|
|
168
|
+
),
|
|
169
|
+
(project_id,),
|
|
170
|
+
).fetchall()
|
|
171
|
+
|
|
172
|
+
if not rows:
|
|
173
|
+
return None
|
|
174
|
+
|
|
175
|
+
# Resolve project path to check against running process cmdlines
|
|
176
|
+
resolved_repo = str(repo_root.resolve())
|
|
177
|
+
|
|
178
|
+
# ps aux output to find running devflow worker processes
|
|
179
|
+
try:
|
|
180
|
+
ps_output = subprocess.check_output(
|
|
181
|
+
["ps", "aux"], text=True, stderr=subprocess.DEVNULL
|
|
182
|
+
)
|
|
183
|
+
except Exception:
|
|
184
|
+
ps_output = ""
|
|
185
|
+
|
|
186
|
+
for line in ps_output.splitlines():
|
|
187
|
+
if "devflow worker start" not in line:
|
|
188
|
+
continue
|
|
189
|
+
# Extract PID (field 1 in ps aux)
|
|
190
|
+
parts = line.split()
|
|
191
|
+
if len(parts) < 2:
|
|
192
|
+
continue
|
|
193
|
+
try:
|
|
194
|
+
pid = int(parts[1])
|
|
195
|
+
except ValueError:
|
|
196
|
+
continue
|
|
197
|
+
# Check if this process is still alive (signal 0)
|
|
198
|
+
try:
|
|
199
|
+
os.kill(pid, 0)
|
|
200
|
+
except (OSError, ValueError):
|
|
201
|
+
# Process is dead — clean up stale DB row
|
|
202
|
+
stale_ids = [r["worker_id"] for r in rows if r["worker_id"] == str(pid)]
|
|
203
|
+
for wid in stale_ids:
|
|
204
|
+
conn.execute(
|
|
205
|
+
"UPDATE project_workers SET status='stopped', stopped_at=?, updated_at=? "
|
|
206
|
+
"WHERE worker_id=?",
|
|
207
|
+
(now, now, wid),
|
|
208
|
+
)
|
|
209
|
+
conn.commit()
|
|
210
|
+
continue
|
|
211
|
+
# Check if it matches our project path
|
|
212
|
+
if resolved_repo in line:
|
|
213
|
+
row = rows[0]
|
|
214
|
+
return WorkerGuardBlock(
|
|
215
|
+
reason=(
|
|
216
|
+
f"A worker process (PID {pid}) is already running for this project "
|
|
217
|
+
f"and is currently handling queue_type={row['active_queue_type']!r}, "
|
|
218
|
+
f"item_id={row['active_item_id']!r}."
|
|
219
|
+
),
|
|
220
|
+
source=f"process:PID={pid}",
|
|
221
|
+
)
|
|
222
|
+
|
|
223
|
+
# No alive process found matching this project — clean up all stale rows
|
|
224
|
+
for row in rows:
|
|
225
|
+
conn.execute(
|
|
226
|
+
"UPDATE project_workers SET status='stopped', stopped_at=?, updated_at=? "
|
|
227
|
+
"WHERE worker_id=?",
|
|
228
|
+
(now, now, row["worker_id"]),
|
|
229
|
+
)
|
|
230
|
+
conn.commit()
|
|
231
|
+
return None
|
|
232
|
+
finally:
|
|
233
|
+
conn.close()
|
|
@@ -0,0 +1,235 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: devflow-engine
|
|
3
|
+
Version: 1.0.0
|
|
4
|
+
Summary: DevFlow v2 CLI-first engine (projects, stories, execution store, review packets)
|
|
5
|
+
Project-URL: Homepage, https://github.com/Nuosis/devflow_engine
|
|
6
|
+
Project-URL: Repository, https://github.com/Nuosis/devflow_engine
|
|
7
|
+
Project-URL: Issues, https://github.com/Nuosis/devflow_engine/issues
|
|
8
|
+
Author: DevFlow
|
|
9
|
+
License: Proprietary
|
|
10
|
+
Keywords: agentic,automation,cli,devflow,testing,workflow
|
|
11
|
+
Classifier: Development Status :: 5 - Production/Stable
|
|
12
|
+
Classifier: Environment :: Console
|
|
13
|
+
Classifier: Intended Audience :: Developers
|
|
14
|
+
Classifier: License :: Other/Proprietary License
|
|
15
|
+
Classifier: Operating System :: OS Independent
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
19
|
+
Classifier: Topic :: Software Development
|
|
20
|
+
Classifier: Topic :: Software Development :: Build Tools
|
|
21
|
+
Requires-Python: >=3.11
|
|
22
|
+
Requires-Dist: cryptography>=45.0
|
|
23
|
+
Requires-Dist: pydantic>=2.6
|
|
24
|
+
Requires-Dist: pyyaml>=6.0
|
|
25
|
+
Requires-Dist: rich>=13.7
|
|
26
|
+
Requires-Dist: typer>=0.12
|
|
27
|
+
Description-Content-Type: text/markdown
|
|
28
|
+
|
|
29
|
+
# DevFlow Engine
|
|
30
|
+
|
|
31
|
+
CLI-first Python engine for DevFlow. The PyPI distribution is
|
|
32
|
+
`devflow-engine`; it installs the `devflow` command.
|
|
33
|
+
|
|
34
|
+
## Goals
|
|
35
|
+
- Project lifecycle: draft shell -> bind workspace/repo -> init/register/list/remove
|
|
36
|
+
- Story lifecycle: index/validate/register/execute
|
|
37
|
+
- Planning support: repo analysis -> source docs -> scopes -> approved scope -> idea(s) -> DevFlow stories
|
|
38
|
+
- Implementation workflow: "green" gate = tests + typecheck + lint
|
|
39
|
+
- Review workflow: story-driven compliance/soundness/security review packets persisted in SQLite
|
|
40
|
+
- Error workflow: error queue + remediation runs
|
|
41
|
+
- Execution store: `.devflow/execution.sqlite`
|
|
42
|
+
|
|
43
|
+
## Documentation
|
|
44
|
+
- `docs/story-implementation-planning-node.md` — per-story planning/gating node before TestDesign/Red, with dependency findings, queue decisions, and registry expectations consumed by downstream implementation nodes.
|
|
45
|
+
- `docs/llm-input-primitives-v0.02.md` — v0.02 LLM-facing input primitive contract for `idea` and `story`.
|
|
46
|
+
|
|
47
|
+
## Install
|
|
48
|
+
|
|
49
|
+
Install the CLI from PyPI:
|
|
50
|
+
|
|
51
|
+
```bash
|
|
52
|
+
pipx install devflow-engine
|
|
53
|
+
# or
|
|
54
|
+
python -m pip install devflow-engine
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
Run the CLI:
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
devflow --help
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
## Development
|
|
64
|
+
|
|
65
|
+
This repo is intended to be developed with **uv**.
|
|
66
|
+
|
|
67
|
+
```bash
|
|
68
|
+
cd devflow_engine
|
|
69
|
+
uv venv
|
|
70
|
+
uv pip install -e '.[dev]'
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
Print the v0.02 LLM input guidance:
|
|
74
|
+
```bash
|
|
75
|
+
devflow llm guide
|
|
76
|
+
devflow llm guide --primitive idea --json
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
## Happy path
|
|
80
|
+
1. project shell created in control plane
|
|
81
|
+
2. workspace/repo bound to project
|
|
82
|
+
3. registration DAG runs via `devflow project add`
|
|
83
|
+
4. project reaches `ready_for_source_scope`
|
|
84
|
+
5. source docs -> scopes
|
|
85
|
+
6. approved scope -> idea(s)
|
|
86
|
+
7. idea -> DevFlow stories
|
|
87
|
+
8. story -> implementation
|
|
88
|
+
9. implementation -> review
|
|
89
|
+
|
|
90
|
+
## Quickstart
|
|
91
|
+
Register an existing repo with DevFlow:
|
|
92
|
+
```bash
|
|
93
|
+
devflow project add --path /absolute/path/to/repo --name my-repo --json
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
Submit an idea or a ready story:
|
|
97
|
+
```bash
|
|
98
|
+
devflow idea submit --project /absolute/path/to/repo --from idea.json --json
|
|
99
|
+
# or
|
|
100
|
+
devflow story submit --project /absolute/path/to/repo --from story.json --json
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
Run delivery and inspect health:
|
|
104
|
+
```bash
|
|
105
|
+
devflow run start --project /absolute/path/to/repo --json
|
|
106
|
+
devflow run health --project /absolute/path/to/repo --json
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
Triage and repair failures:
|
|
110
|
+
```bash
|
|
111
|
+
devflow doctor --project /absolute/path/to/repo --json
|
|
112
|
+
devflow recovery run --project /absolute/path/to/repo --json
|
|
113
|
+
devflow error solve --project /absolute/path/to/repo --json
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
When you have a deterministic project-code repro, pass it to error solving:
|
|
117
|
+
```bash
|
|
118
|
+
devflow error solve \
|
|
119
|
+
--project /absolute/path/to/repo \
|
|
120
|
+
--repro-command 'uv run pytest' \
|
|
121
|
+
--json
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
Inspect per-node outputs from a stored run:
|
|
125
|
+
```bash
|
|
126
|
+
# dump a specific run by run_id
|
|
127
|
+
python scripts/dump_run_node_outputs.py \
|
|
128
|
+
--run-id <run_uuid>
|
|
129
|
+
|
|
130
|
+
# or dump the latest run for any DAG by dag_id
|
|
131
|
+
python scripts/dump_run_node_outputs.py \
|
|
132
|
+
--dag-id implementation_dag
|
|
133
|
+
|
|
134
|
+
# second-most-recent run for that DAG
|
|
135
|
+
python scripts/dump_run_node_outputs.py \
|
|
136
|
+
--dag-id implementation_dag \
|
|
137
|
+
--latest-index 2
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
Dumps are written under `.devflow/node_output_dumps/<dag>/<label>/<timestamp>/` by default.
|
|
141
|
+
The navigation path intentionally stays human-readable and omits run IDs / object IDs where possible:
|
|
142
|
+
- `<dag>` comes from `runs.dag_id` unless it looks like an ID, in which case the folder falls back to `dag`
|
|
143
|
+
- `<label>` is derived from readable config fields such as `label`, `name`, `title`, `idea_title`, `scope_title`, or `story_title`
|
|
144
|
+
- the exact `run_id` still lands in `manifest.json` inside the dump directory
|
|
145
|
+
|
|
146
|
+
Use `--output-root /tmp/devflow-dumps` to write somewhere else.
|
|
147
|
+
|
|
148
|
+
Run the source -> scope scaffold end-to-end:
|
|
149
|
+
```bash
|
|
150
|
+
devflow source-scope run \
|
|
151
|
+
--project-id proj_demo \
|
|
152
|
+
--intake-id source_demo \
|
|
153
|
+
--text "Customers approve quotes online. Approved quotes create jobs. Completed jobs create invoices and customers can pay online."
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
Gate a pre-shaped normalized packet + scope outline deterministically:
|
|
157
|
+
```bash
|
|
158
|
+
devflow source-scope gate \
|
|
159
|
+
--project-id proj_demo \
|
|
160
|
+
--source-packet .devflow/path/to/normalized_source_packet.json \
|
|
161
|
+
--scope-outline .devflow/path/to/scope_outline.json
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
## Story contracts
|
|
165
|
+
Story contracts are YAML documents containing:
|
|
166
|
+
- `id`, `title`
|
|
167
|
+
- `planes`: required plane write-ups (`product`, `ux`, `technical`, `security`, `compliance`, `operations`)
|
|
168
|
+
- `plane_oracles`: list of `{plane, anchor}` entries used as verification anchors
|
|
169
|
+
|
|
170
|
+
The contract validator enforces presence of required planes + non-empty plane_oracles.
|
|
171
|
+
|
|
172
|
+
## Execution store
|
|
173
|
+
All runs/events/errors/review packets are stored in:
|
|
174
|
+
- `.devflow/execution.sqlite`
|
|
175
|
+
|
|
176
|
+
This database is created automatically on first CLI usage.
|
|
177
|
+
|
|
178
|
+
## Workers / Background services
|
|
179
|
+
|
|
180
|
+
### Supabase execution-event listener (`devflow worker supabase-events`)
|
|
181
|
+
|
|
182
|
+
This is the DFE-side listener/dispatcher for the `devflow_execution_events` Supabase table.
|
|
183
|
+
It is the single long-running process that bridges the control-plane (Supabase) to the local
|
|
184
|
+
DevFlow engine — picking up queued events and dispatching the appropriate DFE workflow for each.
|
|
185
|
+
|
|
186
|
+
**Normal operation (continuous loop with Realtime):**
|
|
187
|
+
```bash
|
|
188
|
+
devflow worker supabase-events
|
|
189
|
+
```
|
|
190
|
+
|
|
191
|
+
Starts an indefinite polling loop. While running it also opens a Supabase Realtime WebSocket
|
|
192
|
+
subscription on `devflow_execution_events`. New `INSERT` events on that table wake the dispatch
|
|
193
|
+
loop immediately rather than waiting for the next poll interval (default: 3 s). If the WebSocket
|
|
194
|
+
connection drops it reconnects automatically in the background; polling continues as the fallback
|
|
195
|
+
during any gap.
|
|
196
|
+
|
|
197
|
+
**Process a single queued event and exit:**
|
|
198
|
+
```bash
|
|
199
|
+
devflow worker supabase-events --once
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
Useful for manual trigger / smoke testing.
|
|
203
|
+
|
|
204
|
+
**Disable Realtime (polling only):**
|
|
205
|
+
```bash
|
|
206
|
+
devflow worker supabase-events --no-realtime
|
|
207
|
+
```
|
|
208
|
+
|
|
209
|
+
Runs the same polling loop but skips the WebSocket listener entirely. Use this when the
|
|
210
|
+
`websockets` Python package is unavailable, or when you need to debug without a live connection.
|
|
211
|
+
|
|
212
|
+
**Additional options:**
|
|
213
|
+
| Flag | Default | Description |
|
|
214
|
+
|---|---|---|
|
|
215
|
+
| `--sleep-seconds N` | `3.0` | Idle sleep between polls (also caps realtime wake latency) |
|
|
216
|
+
| `--max-iterations N` | unlimited | Stop after N loop iterations |
|
|
217
|
+
| `--json` | off | Emit JSON summary on exit |
|
|
218
|
+
|
|
219
|
+
**When queued events are not being picked up — checklist:**
|
|
220
|
+
1. Verify the worker is running: there should be a live `devflow worker supabase-events` process.
|
|
221
|
+
2. Check Supabase credentials: `SUPABASE_URL` and `SUPABASE_SERVICE_KEY` (or equivalent config)
|
|
222
|
+
must be set and valid.
|
|
223
|
+
3. Confirm the event row in `devflow_execution_events` has `status = queued` and `run_id IS NULL`
|
|
224
|
+
— events with any other status are skipped.
|
|
225
|
+
4. Check that the event's `event_type` is in the supported set (see
|
|
226
|
+
`docs/queue-worker-infra.md` → *Supported event types*).
|
|
227
|
+
5. Run with `--once` to get an immediate result and check stderr/stdout for errors.
|
|
228
|
+
6. If Realtime is misbehaving (false wake-ups or missed wakes), try `--no-realtime` to isolate
|
|
229
|
+
the issue to the polling path.
|
|
230
|
+
|
|
231
|
+
See `docs/queue-worker-infra.md` for full architecture details.
|
|
232
|
+
|
|
233
|
+
## Design notes
|
|
234
|
+
- `docs/scope-idea-agentification.md` — current scope->idea agentic runtime notes
|
|
235
|
+
- `docs/ui-grounding-curtis-medium-tier-doctrine.md` — follow-on UI grounding / wireframe planning doctrine from the Curtis pass, including the proposed `ui_screen_inventory.json` contract and the default medium-tier minimum for customer-facing wireframes
|