gflow-cli 0.21.0__tar.gz → 0.23.0__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.
- gflow_cli-0.23.0/.claude/commands/gflow/issue-assessment.md +28 -0
- gflow_cli-0.23.0/.claude/commands/gflow/issue-resolve.md +18 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/pr-council-review.md +6 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/release.md +4 -2
- gflow_cli-0.23.0/.claude/commands/gflow/sonar.md +82 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/workflows/ci.yml +5 -2
- gflow_cli-0.23.0/.github/workflows/main-base-guard.yml +50 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.gitignore +12 -6
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/AGENTS.md +10 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/CHANGELOG.md +103 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/CONFIGURATION.md +2 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/CONTRIBUTING.md +17 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/GEMINI.md +1 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/KNOWN_ISSUES.md +22 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/PKG-INFO +3 -2
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/PLAN.md +8 -2
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/README.md +1 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/CONFIGURATION.md +25 -2
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/INDEX.md +6 -2
- gflow_cli-0.23.0/docs/LIVE_VERIFICATION_v0.22.0.md +120 -0
- gflow_cli-0.23.0/docs/LIVE_VERIFICATION_v0.23.0.md +76 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/MCP.md +4 -4
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/PROJECT_STATUS.md +25 -2
- gflow_cli-0.23.0/docs/PROMPT_EXPANSION.md +247 -0
- gflow_cli-0.23.0/docs/TOOLS.md +301 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/USAGE.md +65 -1
- gflow_cli-0.23.0/docs/superpowers/research/2026-06-27-tool-abstraction-evaluation.md +141 -0
- gflow_cli-0.23.0/docs/superpowers/specs/2026-06-29-issue-assessment-workflow-design.md +143 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/pyproject.toml +3 -3
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_patchright.py +9 -2
- gflow_cli-0.23.0/skills/issue-assessment/SKILL.md +142 -0
- gflow_cli-0.23.0/skills/issue-resolve/SKILL.md +123 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/__init__.py +1 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/_cli_helpers.py +104 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/client.py +224 -4
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/image.py +8 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/ui_automation.py +10 -9
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/video.py +7 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/cookies.py +36 -3
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/browser_manager.py +112 -12
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/chain.py +7 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli.py +23 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_image.py +64 -3
- gflow_cli-0.23.0/src/gflow_cli/cli_tools.py +88 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_video.py +88 -6
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/config.py +13 -1
- gflow_cli-0.23.0/src/gflow_cli/data/migrations/0008_add_operation_expanded_prompt.sql +6 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/models.py +3 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/recorder.py +79 -4
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/repository.py +5 -3
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/image_batch.py +13 -1
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/mcp/prompts.py +12 -1
- gflow_cli-0.23.0/src/gflow_cli/mcp/tools.py +781 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/paths.py +5 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/banned.py +81 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/builtin/creative-director.toml +229 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/expander.py +303 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/invocation.py +87 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/loader.py +64 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/registry.py +52 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/runtime.py +63 -0
- gflow_cli-0.23.0/src/gflow_cli/tools/spec.py +78 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/worker/daemon.py +132 -34
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_image.py +47 -0
- gflow_cli-0.23.0/tests/api/test_client_launch_kwargs.py +310 -0
- gflow_cli-0.23.0/tests/auth/test_cookies.py +51 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_image.py +51 -0
- gflow_cli-0.23.0/tests/cli/test_cli_tools.py +46 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_video.py +114 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_helpers.py +147 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_t2i_multi_prompt.py +47 -0
- gflow_cli-0.23.0/tests/data/test_recorder.py +488 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_store_migrations.py +1 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/dev/test_recording_client.py +1 -0
- gflow_cli-0.23.0/tests/e2e/test_tools_e2e.py +201 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/mcp/test_server.py +171 -10
- gflow_cli-0.23.0/tests/mcp/test_tools_wired.py +440 -0
- gflow_cli-0.23.0/tests/services/__init__.py +0 -0
- gflow_cli-0.23.0/tests/smoke/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_browser_manager.py +89 -0
- gflow_cli-0.23.0/tests/tools/__init__.py +0 -0
- gflow_cli-0.23.0/tests/tools/test_banned.py +58 -0
- gflow_cli-0.23.0/tests/tools/test_expander.py +295 -0
- gflow_cli-0.23.0/tests/tools/test_invocation.py +88 -0
- gflow_cli-0.23.0/tests/tools/test_loader.py +52 -0
- gflow_cli-0.23.0/tests/tools/test_registry.py +77 -0
- gflow_cli-0.23.0/tests/tools/test_runtime.py +64 -0
- gflow_cli-0.23.0/tests/tools/test_spec.py +97 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/worker/test_daemon.py +108 -19
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/uv.lock +25 -25
- gflow_cli-0.21.0/docs/superpowers/plans/2026-06-23-mcp-ui-worker-integration/DESIGN.md +0 -117
- gflow_cli-0.21.0/docs/superpowers/plans/2026-06-23-mcp-ui-worker-integration/PLAN.md +0 -110
- gflow_cli-0.21.0/docs/superpowers/plans/2026-06-23-mcp-ui-worker-integration/SCENARIO.md +0 -66
- gflow_cli-0.21.0/docs/superpowers/plans/2026-06-23-mcp-ui-worker-integration/STUDIO_DESIGN.md +0 -233
- gflow_cli-0.21.0/src/gflow_cli/mcp/tools.py +0 -263
- gflow_cli-0.21.0/tests/api/test_client_launch_kwargs.py +0 -77
- gflow_cli-0.21.0/tests/data/test_recorder.py +0 -214
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/active.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/branch-review.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/changelog.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/check.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/doc-review.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/known-issues.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/next.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/plan.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/predict.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/scenario.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.claude/commands/gflow/status.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.env.template +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.gitattributes +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/CODEOWNERS +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/PULL_REQUEST_TEMPLATE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/copilot-instructions.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/dependabot.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/workflows/external-pr-triage.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/workflows/governance-advisory.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/workflows/governance-benchmark.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.github/workflows/release.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.gitleaks.toml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.pre-commit-config.yaml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/.secrets.baseline +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/CLAUDE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/DISCLAIMER.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/LICENSE +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/RELEASE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/ROADMAP.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/conftest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docker-compose.yml +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/AGENT_GUIDE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/AGENT_UI_E2E.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/AGENT_UI_RECON.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/ARCHITECTURE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/AUTHENTICATION.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/CHARACTER.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/CHARACTER_RECON.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/DATA_LAYER.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/DEBUGGING.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/DEMOS.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/DEVELOPMENT.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/E2E_TESTING.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/EXTERNAL_STORAGE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/GITHUB.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/GOVERNANCE_BENCHMARK.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/IMAGE_UPSCALE_RECON.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_data_layer.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_image_batch.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.10.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.11.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.12.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.13.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.16.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.17.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.18.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.19.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.20.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.20.1.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.21.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.7.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.8.1.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.9.0.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_v0.9.1.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/LIVE_VERIFICATION_video_download.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/MOVIE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/SECURITY.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/USER_GUIDE.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/assets/demo-split-pf.gif +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/assets/example-run.gif +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/assets/examples.webp +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/medium_tutorial.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/schemas/movie-handoff.schema.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/sonar-cleanup-tracker.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-12-issue-174-library-ui-attach/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-mcp-server/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-mcp-server/PREDICT.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-mcp-server/SCENARIO.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-prompt-expansion/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-prompt-expansion/PREDICT.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-22-prompt-expansion/SCENARIO.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-24-gflow-studio-scaffold/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-24-rest-api-layer/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/docs/superpowers/plans/2026-06-26-mcp-e2e-test/PLAN.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/batch_from_config.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/multi_prompt_t2i.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/sample_config.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/sample_prompts.txt +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/single_image_t2i.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/examples/workflow_chain.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/llms.txt +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/01_upload_image.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/02_batchAsyncGenerateVideoText.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/03_batchCheckAsyncVideoGenerationStatus.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/04_archive_workflow.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/05_createProject.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/06_batchGenerateImages.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/07_batchGenerateImages_seeded.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/08_batchAsyncGenerateVideoStartAndEndImage.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/09_batchAsyncGenerateVideoReferenceImages.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/10_batchCheckAsyncVideoGenerationStatus_successful.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/11_batchCheckAsyncVideoGenerationStatus_failed.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/12_create_scene.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/13_sceneWorkflows_update.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/14_get_scene_workflows.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/samples/captured/15_commit_flowWorkflow.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/ci/check_doc_links.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/ci/check_materiality.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/ci/check_repo_hygiene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/debug_editor.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/debug_gen_settings.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/debug_settings.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/_recording_client.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/_spike_common.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/active_plan.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/analyze_agent_ui_capture.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_i2v_frame_slots_dom.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_i2v_intercept_submit.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_i2v_model_select_repro.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_i2v_post_bind_state.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_image_add_media_dom.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/capture_locale_invariants.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/cdp_drive_and_probe.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/character_create_spike.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/character_create_spike_v2.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/dump_character_selectors.js +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/make_project.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/materiality_backtest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/monitor_pr_38.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/patch_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/skillopt/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/skillopt/harness.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/skillopt/tasks.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_char_editor_dom.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_char_gen_capture.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_image_upscale_capture.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_image_upscale_drive.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_image_upscale_recaptcha_action.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_image_upscale_rest_probe.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_issue170_picker_locale_recon.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_issue174_library_ui_recon.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_movie_attach_payload.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_movie_entity_recon.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_movie_gen_capture.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_movie_picker_select.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_movie_voice_list.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/dev/spike_patch_entity.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/diag/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/diag/capture_flow_traffic.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/diag/memory_profile.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/diag/recaptcha_mint.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/e2e/agentic_image_e2e.ps1 +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/e2e/capture_agent_toggle.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/record_demo.ps1 +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/smoke_image.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/smoke_real_chrome_image.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/smoke_video_editor.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/smoke_worker_style.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/scripts/verify_chrome_auth_viability.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/README.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/gflow-cli/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/plan/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/pr-council-review/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/predict/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/scenario/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/skills/status/SKILL.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/sonar-project.properties +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/__main__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/_engine.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/_retry.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/_sapisidhash.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/dto.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/image_upscale.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/recaptcha.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/routes.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/scene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/_common.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/_fingerprint.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/base.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/drivers/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/drivers/agentic.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/drivers/base.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/drivers/classic.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/drivers/factory.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/experimental/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/experimental/bearer.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/experimental/evaluate_fetch.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/experimental/sapisidhash.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/api/transports/ui_automation_video.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/base.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/factory.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/internal_chromium.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/real_chrome.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/strategies.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/auth/verification.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/chain_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_data.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_models.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_movie.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_run.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/cli_scene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/composition.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/chain_repo.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0001_initial.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0002_add_cloud_storage.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0003_add_scene_tables.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0004_add_scene_output_path.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0005_add_chain_links.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0006_add_operations_metadata.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/0007_queue.sql +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/migrations/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/queries.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/redaction.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/data/store.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/errors.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/exceptions.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/json_output.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/mcp/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/mcp/resources.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/mcp/server.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/media.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/movie_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/observability.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/profile_store.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/services/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/services/character_create.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/storage.py +0 -0
- {gflow_cli-0.21.0/tests → gflow_cli-0.23.0/src/gflow_cli/tools}/__init__.py +0 -0
- {gflow_cli-0.21.0/tests/api → gflow_cli-0.23.0/src/gflow_cli/tools/builtin}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/ui/app.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/ui/server.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/src/gflow_cli/worker/queue.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tasks/lessons.md +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/test_assets/sample_batch.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/test_assets/sample_batch.tsv +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/test_assets/sample_batch_invalid.tsv +0 -0
- {gflow_cli-0.21.0/tests/api/transports → gflow_cli-0.23.0/tests}/__init__.py +0 -0
- {gflow_cli-0.21.0/tests/api/transports/drivers → gflow_cli-0.23.0/tests/api}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/fixtures/character_gen_response.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/fixtures/patch_entity_response.json +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_aisandbox_auth_error.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_aisandbox_auth_headers.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_bearer_redaction.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_delete_characters.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_generate_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_patch_entity.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_scene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_client_upscale.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_concurrency.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_dto.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_engine.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_image.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_image_dto.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_image_upscale.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_post_json_aisandbox_auth.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_recaptcha.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_retry.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_routes.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_routes_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_routes_scene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_sapisidhash_helper.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_scene_models.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_video.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/test_video_request.py +0 -0
- {gflow_cli-0.21.0/tests/cli → gflow_cli-0.23.0/tests/api/transports}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/conftest.py +0 -0
- {gflow_cli-0.21.0/tests/data → gflow_cli-0.23.0/tests/api/transports/drivers}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/drivers/test_agentic.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/drivers/test_factory.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_base.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_bearer.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_common.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_evaluate_fetch.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_factory.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_fingerprint.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_sapisidhash.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_transport_timeout.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_ui_automation.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_ui_automation_batch.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_ui_automation_image_mode.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_ui_automation_video.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/api/transports/test_ui_character_editor.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/auth/strategies/test_factory.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/auth/strategies/test_strategies.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/auth/test_verification.py +0 -0
- {gflow_cli-0.21.0/tests/e2e → gflow_cli-0.23.0/tests/cli}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_auth_list.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_character_create.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_data.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_image_seed_removed.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_image_selector_drift.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_image_upscale.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_models.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_movie.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_run.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_scene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_cli_video_chain.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_error_handling.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_movie_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/cli/test_settings_validation.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/composition/test_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/composition/test_compose_prompt.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/composition/test_handoff.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/conftest.py +0 -0
- {gflow_cli-0.21.0/tests/features → gflow_cli-0.23.0/tests/data}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_chain_repo.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_find_incomplete_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_models.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_packaging.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_recorder_character.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_redaction.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_repository.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_scene_persistence.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/data/test_settings_and_errors.py +0 -0
- {gflow_cli-0.21.0/tests/fixtures → gflow_cli-0.23.0/tests/e2e}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/conftest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_aisandbox_auth_live.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_auth_verification_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_chain_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_character_create_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_daemon_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_data_layer_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_i2v_flags_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_image_batch_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_image_i2i_ref_cap_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_json_output_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_locale_selectors_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_scene_compose_live.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_transports_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_video_r2v_ref_cap_e2e.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/e2e/test_video_t2v_e2e.py +0 -0
- {gflow_cli-0.21.0/tests/image_batch → gflow_cli-0.23.0/tests/features}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/auth.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/auth_login.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/character_create.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/character_read.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/conftest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/image.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/image_upscale.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/locale_picker_include.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_auth_login_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_auth_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_character_create_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_character_read_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_image_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_image_upscale_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_locale_picker_include_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_step_collision_guard.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_video_agent_ui_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/test_video_chain_steps.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/video_agent_ui.feature +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/features/video_chain.feature +0 -0
- {gflow_cli-0.21.0/tests/integration → gflow_cli-0.23.0/tests/fixtures}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/fixtures/seeded_catalog.py +0 -0
- {gflow_cli-0.21.0/tests/services → gflow_cli-0.23.0/tests/image_batch}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/image_batch/test_image_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/image_batch/test_observability_events.py +0 -0
- {gflow_cli-0.21.0/tests/smoke → gflow_cli-0.23.0/tests/integration}/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/integration/conftest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/integration/constants.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/integration/test_storage_gcs.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/integration/test_storage_s3.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/mcp/__init__.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/mcp/conftest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/mcp/test_stdio_transport.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/scripts/test_analyze_agent_ui_capture.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/scripts/test_capture_locale_invariants.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/scripts/test_check_materiality.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/scripts/test_check_repo_hygiene.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/scripts/test_materiality_backtest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/services/test_character_create_redaction.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/services/test_character_create_saga.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/services/test_character_gen_no_direct_post.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/smoke/test_profile_account_smoke.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/smoke/test_real_flow.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_auth.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_chain.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_chain_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_cli_data.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_config.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_conftest_isolation.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_data_queries.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_documentation_gate.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_errors.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_errors_403.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_json_output.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_manifest.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_marker_registry.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_media.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_observability.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_paths.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_profile_store.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/test_smoke.py +0 -0
- {gflow_cli-0.21.0 → gflow_cli-0.23.0}/tests/ui/test_app.py +0 -0
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: >
|
|
3
|
+
Triage a gflow-cli GitHub issue: verify the reporter's claim against code,
|
|
4
|
+
tests, docs, KNOWN_ISSUES, and memory; classify it (CONFIRMED / NEEDS-E2E /
|
|
5
|
+
NEEDS-INFO / DUPLICATE / INVALID / WONTFIX); judge whether it is verifiable
|
|
6
|
+
end-to-end in the current environment; and draft a reporter-facing reply.
|
|
7
|
+
Read-only — changes nothing and posts nothing on its own.
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# `/gflow:issue-assessment [issue number or URL]`
|
|
11
|
+
|
|
12
|
+
**Read `skills/issue-assessment/SKILL.md` and follow its protocol now**, passing `$ARGUMENTS` as the issue to assess.
|
|
13
|
+
|
|
14
|
+
> Do **not** call `Skill(skill="issue-assessment")` — the repo's `skills/*/SKILL.md` files are plain Markdown, not Skill-tool-invocable (only `.claude/commands/gflow/*` are). Read the file directly instead.
|
|
15
|
+
|
|
16
|
+
The skill at `skills/issue-assessment/SKILL.md` ingests the issue, verifies the
|
|
17
|
+
claim (dispatching a search agent to keep context clean), assigns one verdict,
|
|
18
|
+
applies the **e2e-gate** (never claim a fix is verified on an unverifiable
|
|
19
|
+
surface), and emits a standard report artifact. On a `CONFIRMED` / `LIKELY-BUG`
|
|
20
|
+
verdict with localized, verifiable scope it hands off to `issue-resolve`;
|
|
21
|
+
otherwise it replies only.
|
|
22
|
+
|
|
23
|
+
**Typical chain:**
|
|
24
|
+
```
|
|
25
|
+
/gflow:issue-assessment <N> → verdict + e2e-gate + reply artifact
|
|
26
|
+
↓ (if scope clear & verifiable)
|
|
27
|
+
issue-resolve <N> → worktree + TDD + draft PR for human review
|
|
28
|
+
```
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: >
|
|
3
|
+
Drive an assessed gflow-cli issue (verdict CONFIRMED-BUG or LIKELY-BUG, with
|
|
4
|
+
localized verifiable scope) to a fix: isolated worktree off develop, test-first
|
|
5
|
+
fix, /gflow:check, then a DRAFT PR for human review. Mutating and gated — runs
|
|
6
|
+
inside a strict action envelope (never merges, never spends credits, never
|
|
7
|
+
marks a PR ready, never claims an unverified fix verified).
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
# `/gflow:issue-resolve [issue number]`
|
|
11
|
+
|
|
12
|
+
**Read `skills/issue-resolve/SKILL.md` and follow its protocol now**, passing `$ARGUMENTS` as the issue to resolve.
|
|
13
|
+
|
|
14
|
+
> Do **not** call `Skill(skill="issue-resolve")` — the repo's `skills/*/SKILL.md` files are plain Markdown, not Skill-tool-invocable (only `.claude/commands/gflow/*` are). Read the file directly instead.
|
|
15
|
+
|
|
16
|
+
Preconditions (from `/gflow:issue-assessment`): verdict ∈ {`CONFIRMED-BUG`, `LIKELY-BUG`}, scope single-surface, and the fix is verifiable in this environment (or the gap is carried into the PR as "needs human e2e"). The skill isolates a `bugfix/` worktree off `develop`, gates high-stakes changes through `/gflow:predict` + `/gflow:scenario`, fixes test-first (Opus plans → Sonnet codes → Opus reviews for non-trivial work), runs `/gflow:check`, opens a **draft** PR with a Verification-status section, runs `/gflow:pr-council-review`, and **stops** for a human to promote and merge.
|
|
17
|
+
|
|
18
|
+
**Chain:** `/gflow:issue-assessment <N>` → (if scope clear) `/gflow:issue-resolve <N>` → human promotes draft → human runs any headed/e2e check → merge.
|
|
@@ -8,4 +8,10 @@ description: Multi-dimensional LLM council review of an open PR. Five baseline d
|
|
|
8
8
|
|
|
9
9
|
> Do **not** call `Skill(skill="pr-council-review")` — the repo's `skills/*/SKILL.md` files are plain Markdown, not registered as Skill-tool-invocable (only `.claude/commands/gflow/*` are). Invoking it errors with `Unknown skill: pr-council-review`. Read the file directly instead.
|
|
10
10
|
|
|
11
|
+
**Required gate — SonarCloud must be green.** The council reviews the *diff*; it does
|
|
12
|
+
not see SonarCloud's verdict. Before declaring the final verdict, run **`/gflow:sonar`**
|
|
13
|
+
for this PR — the `SonarCloud analysis` gate must be green (zero new issues). A red gate
|
|
14
|
+
is a blocking finding regardless of the council's own conclusions; report it with the
|
|
15
|
+
exact failing conditions and do not call the PR merge-ready until it is green.
|
|
16
|
+
|
|
11
17
|
Sibling: `/review` is the single-agent Claude-Code built-in (fast, one-pass). Use it for spot-checks; use this command for pre-merge multi-dim audits.
|
|
@@ -198,8 +198,10 @@ gh pr create --base main --head chore/release-v<NEW_VERSION> \
|
|
|
198
198
|
--title "chore(release): v<NEW_VERSION>"
|
|
199
199
|
```
|
|
200
200
|
|
|
201
|
-
Wait for PR CI to go green (`gh pr checks <N> --watch`)
|
|
202
|
-
|
|
201
|
+
Wait for PR CI to go green (`gh pr checks <N> --watch`). **The `SonarCloud analysis`
|
|
202
|
+
check must be green (gate passed) — not just the test matrix.** If it is red or you
|
|
203
|
+
want the verdict, run `/gflow:sonar <N>` and drive it to zero before merging. Then
|
|
204
|
+
merge with a **merge commit** — never squash:
|
|
203
205
|
|
|
204
206
|
```bash
|
|
205
207
|
gh pr merge <N> --merge --delete-branch
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Check the SonarCloud quality gate for a PR (or the current branch) and drive it to zero. Reports GREEN, or the exact PR-scoped new issues/hotspots/coverage gaps to fix.
|
|
3
|
+
---
|
|
4
|
+
|
|
5
|
+
# `/gflow:sonar [PR#]` — SonarCloud quality gate
|
|
6
|
+
|
|
7
|
+
The reusable Sonar primitive. `/gflow:check` is **local** and cannot see Sonar (it
|
|
8
|
+
is server-side, post-push); `/gflow:pr-council-review` is an LLM diff review, not the
|
|
9
|
+
gate verdict. This command answers one question: **is the SonarCloud gate green
|
|
10
|
+
(zero new issues) for this PR, and if not, exactly what must be fixed?**
|
|
11
|
+
|
|
12
|
+
`$ARGUMENTS` is the PR number. If empty, resolve it from the current branch
|
|
13
|
+
(`gh pr view --json number -q .number`).
|
|
14
|
+
|
|
15
|
+
Project: key `ffroliva_gflow-cli`, org `ffroliva-github` (see `sonar-project.properties`).
|
|
16
|
+
The CI scan sets `sonar.qualitygate.wait=true`, so a **green `SonarCloud analysis`
|
|
17
|
+
check means the gate genuinely passed** — but the gate **API is stale until that
|
|
18
|
+
check finishes**, so always check the GitHub check FIRST.
|
|
19
|
+
|
|
20
|
+
## Steps
|
|
21
|
+
|
|
22
|
+
**1. Check the GitHub check first (never trust the gate API while it's pending).**
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
gh pr checks <N> --json name,state,bucket | \
|
|
26
|
+
jq -r '.[] | select(.name=="SonarCloud analysis") | "\(.bucket) \(.state)"'
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
- `pass` → **gate is GREEN / zero new issues. Done.** Report GREEN and stop.
|
|
30
|
+
- `pending` → the SonarCloud job (~50s) runs *after* the ~3.5min test matrix; wait
|
|
31
|
+
(`gh pr checks <N> --watch`) before reading the API, or the API returns the
|
|
32
|
+
previous commit's verdict.
|
|
33
|
+
- `fail` → continue to step 2 to enumerate the exact failing conditions.
|
|
34
|
+
|
|
35
|
+
**2. Enumerate the failing conditions (PR-scoped — this is the #1 gotcha).**
|
|
36
|
+
|
|
37
|
+
New-code issues live on the PR branch, NOT `main`. **Scope every call with
|
|
38
|
+
`&pullRequest=<N>`** or the API reports 0 and you chase phantoms. Token is in
|
|
39
|
+
`.env.local` as `SONAR_TOKEN` — read it inside a sandbox so it never lands in chat.
|
|
40
|
+
`curl` may be blocked by the context-mode hook → use `ctx_execute` (javascript
|
|
41
|
+
`fetch` with `Authorization: Basic base64(token+":")`).
|
|
42
|
+
|
|
43
|
+
```bash
|
|
44
|
+
# Which gate conditions are ERROR:
|
|
45
|
+
GET /api/qualitygates/project_status?projectKey=ffroliva_gflow-cli&pullRequest=<N>
|
|
46
|
+
# New issues (bugs/smells) with file:line + rule + creationDate:
|
|
47
|
+
GET /api/issues/search?componentKeys=ffroliva_gflow-cli&pullRequest=<N>&resolved=false
|
|
48
|
+
# Unreviewed security hotspots:
|
|
49
|
+
GET /api/hotspots/search?projectKey=ffroliva_gflow-cli&pullRequest=<N>&status=TO_REVIEW
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
**3. Fix by condition — no gaming.**
|
|
53
|
+
|
|
54
|
+
- **`new_coverage < 80%`** → add **real** unit tests for the uncovered new lines
|
|
55
|
+
(usually a new orchestration/`_run_*`/helper). There is NO mark-safe shortcut and
|
|
56
|
+
NEVER widen `sonar.coverage.exclusions` to dodge it.
|
|
57
|
+
- **`new_code_smells` / `new_maintainability_rating` (e.g. S1192 duplicated literal,
|
|
58
|
+
S3776 cognitive complexity)** → fix at source. For a duplicated literal your diff
|
|
59
|
+
merely *touched*, collapse it to one module-scope alias so it falls under the
|
|
60
|
+
threshold (pyright/tests prove it's safe). For S7497, re-raise swallowed
|
|
61
|
+
`asyncio.CancelledError`.
|
|
62
|
+
- **`new_security_hotspots_reviewed < 100%`** → only for a **genuine** false positive:
|
|
63
|
+
`POST /api/hotspots/change_status` form body
|
|
64
|
+
`hotspot=<key>&status=REVIEWED&resolution=SAFE&comment=<justification>` (204 = ok),
|
|
65
|
+
then **re-run the SonarCloud job** so it reposts the GitHub status
|
|
66
|
+
(`gh run rerun <run-id> --job <sonar-job-id>` — the coverage artifact is reused).
|
|
67
|
+
Never mark a real hotspot SAFE.
|
|
68
|
+
|
|
69
|
+
**4. Push fixes, then re-verify from step 1** (the check must read `pass`).
|
|
70
|
+
|
|
71
|
+
## Output
|
|
72
|
+
|
|
73
|
+
- Verdict: **GREEN** (gate passed, zero new issues) or **RED** with the exact failing
|
|
74
|
+
conditions and a fix list (`file:line · rule · what to do`).
|
|
75
|
+
- After any fix: re-confirm via step 1 — green check = gate passed.
|
|
76
|
+
|
|
77
|
+
## See also
|
|
78
|
+
|
|
79
|
+
- `docs/GITHUB.md` § SonarCloud Quality Gate — full policy + coverage-exclusion rationale.
|
|
80
|
+
- `/gflow:check` — the local pre-commit gates (coverage floor pre-empts `new_coverage`).
|
|
81
|
+
- Memory: [[sonarcloud-pr-issues-scope-s7497]], [[sonarcloud-new-code-gotchas]],
|
|
82
|
+
[[sonarcloud-hotspot-review-workflow]], [[sonarcloud-setup]].
|
|
@@ -93,10 +93,13 @@ jobs:
|
|
|
93
93
|
runs-on: ubuntu-latest
|
|
94
94
|
needs: test # wait for tests + coverage report
|
|
95
95
|
# Forked pull_request runs do not receive repository secrets, so SONAR_TOKEN
|
|
96
|
-
# is empty there and the scanner fails before analysis.
|
|
97
|
-
#
|
|
96
|
+
# is empty there and the scanner fails before analysis. Dependabot-triggered
|
|
97
|
+
# runs are the same case: GitHub serves them the separate Dependabot secrets
|
|
98
|
+
# namespace, so SONAR_TOKEN is also empty even though the branch is in-repo.
|
|
99
|
+
# Keep SonarCloud on trusted pushes/internal PRs where the token is available.
|
|
98
100
|
if: >
|
|
99
101
|
always() &&
|
|
102
|
+
github.actor != 'dependabot[bot]' &&
|
|
100
103
|
(
|
|
101
104
|
github.event_name != 'pull_request' ||
|
|
102
105
|
github.event.pull_request.head.repo.full_name == github.repository
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
name: Guard main base
|
|
2
|
+
|
|
3
|
+
# Blocks the divergence class that bit v0.21.0: a non-release branch merged
|
|
4
|
+
# straight into `main` (PR #203 — base mistakenly set to `main`, then squashed),
|
|
5
|
+
# which bypassed `develop` and skipped the `main -> develop` back-merge, leaving
|
|
6
|
+
# `main` ahead of `develop` by an orphaned squash commit.
|
|
7
|
+
#
|
|
8
|
+
# Policy: only `chore/release-*` (cut by /gflow:release) or `hotfix/*` branches
|
|
9
|
+
# may target `main`. Everything else must go through `develop` (the default /
|
|
10
|
+
# integration branch). Dependabot and normal PRs already default to `develop`,
|
|
11
|
+
# so this only catches a deliberate, mistaken `--base main`.
|
|
12
|
+
#
|
|
13
|
+
# The job runs on EVERY PR and passes trivially when the base is not `main`, so
|
|
14
|
+
# it is safe to mark as a *required* status check on `main` without blocking
|
|
15
|
+
# `develop` PRs (which would otherwise hang as "expected — waiting").
|
|
16
|
+
|
|
17
|
+
on:
|
|
18
|
+
pull_request:
|
|
19
|
+
types: [opened, reopened, edited, synchronize]
|
|
20
|
+
|
|
21
|
+
permissions:
|
|
22
|
+
contents: read
|
|
23
|
+
|
|
24
|
+
jobs:
|
|
25
|
+
guard:
|
|
26
|
+
name: Only release/hotfix branches may target main
|
|
27
|
+
runs-on: ubuntu-latest
|
|
28
|
+
steps:
|
|
29
|
+
- name: Verify base/head pairing
|
|
30
|
+
env:
|
|
31
|
+
BASE_REF: ${{ github.base_ref }}
|
|
32
|
+
HEAD_REF: ${{ github.head_ref }}
|
|
33
|
+
run: |
|
|
34
|
+
echo "PR head '$HEAD_REF' -> base '$BASE_REF'"
|
|
35
|
+
if [ "$BASE_REF" != "main" ]; then
|
|
36
|
+
echo "Base is '$BASE_REF' (not main) — nothing to enforce."
|
|
37
|
+
exit 0
|
|
38
|
+
fi
|
|
39
|
+
case "$HEAD_REF" in
|
|
40
|
+
chore/release-*|hotfix/*)
|
|
41
|
+
echo "OK: '$HEAD_REF' is allowed to target 'main'."
|
|
42
|
+
;;
|
|
43
|
+
*)
|
|
44
|
+
echo "::error title=Wrong base branch::PR head '$HEAD_REF' must not target 'main'."
|
|
45
|
+
echo "Only 'chore/release-*' (via /gflow:release) or 'hotfix/*' branches may merge into 'main'."
|
|
46
|
+
echo "Feature, CI, fix, docs, and dependency work must target 'develop' (the integration branch)."
|
|
47
|
+
echo "Fix: re-target this PR to 'develop', or — if this really is a release — rename the branch to 'chore/release-vX.Y.Z'."
|
|
48
|
+
exit 1
|
|
49
|
+
;;
|
|
50
|
+
esac
|
|
@@ -32,12 +32,15 @@ htmlcov/
|
|
|
32
32
|
.DS_Store
|
|
33
33
|
|
|
34
34
|
# Project-specific — secrets / session storage (NEVER commit)
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
.
|
|
35
|
+
# NOTE: git does NOT support trailing inline comments in .gitignore — a `#` only
|
|
36
|
+
# starts a comment at the START of a line. Keep each pattern on its own line so
|
|
37
|
+
# the comment text isn't folded into the pattern (which silently un-ignores it).
|
|
38
|
+
/auth/
|
|
39
|
+
profile_*/
|
|
40
|
+
*.cookies.json
|
|
41
|
+
storage_state.json
|
|
42
|
+
secrets.json
|
|
43
|
+
.env
|
|
41
44
|
.env.local
|
|
42
45
|
.env.*.local
|
|
43
46
|
|
|
@@ -93,3 +96,6 @@ worktrees/
|
|
|
93
96
|
# Understand Anything (local knowledge graph)
|
|
94
97
|
.understand-anything/
|
|
95
98
|
.worktrees
|
|
99
|
+
|
|
100
|
+
# Subagent-driven-development scratch (ledger + task reports)
|
|
101
|
+
.superpowers/
|
|
@@ -50,6 +50,7 @@ Or invoke the wrapper: `/gflow:check`.
|
|
|
50
50
|
- Use `pytest -m "not live and not e2e and not smoke"` locally; full suite OOMs on small dev machines. Scope to changed dirs; trust CI for the full sweep.
|
|
51
51
|
- TDD is non-negotiable. Coverage floor: 80% overall.
|
|
52
52
|
- Documentation is a first-class deliverable. Every behavior, workflow, config, or operator-facing change must update the relevant docs or state why no docs changed in the PR/checklist. `scripts/ci/check_doc_links.py` is a merge gate.
|
|
53
|
+
- **A PR is not done until its SonarCloud gate is green (zero new issues).** The six gates above are local/pre-commit; SonarCloud is server-side and runs in CI (`sonar.qualitygate.wait=true` → a red gate turns the `SonarCloud analysis` check red). Before calling a PR merge-ready, verify it with `/gflow:sonar <N>` (it is skipped on fork PRs — maintainer-checked there).
|
|
53
54
|
- Live tests (`@pytest.mark.live`) opt in via `GFLOW_LIVE=1`. E2E tests require `GFLOW_CLI_E2E_PROFILE`.
|
|
54
55
|
|
|
55
56
|
## Code style
|
|
@@ -68,6 +69,15 @@ Or invoke the wrapper: `/gflow:check`.
|
|
|
68
69
|
- Run `/gflow:check` (or the Impeccable Routine) before every commit.
|
|
69
70
|
- All releases require a signed annotated tag (`git tag -s vX.Y.Z`); CI rejects unsigned tags.
|
|
70
71
|
|
|
72
|
+
## Working discipline — verify before you act
|
|
73
|
+
|
|
74
|
+
These rules exist because docs alone don't bind under momentum: a "check open PRs first" rule was already written and still got skipped, and a PR was merged without seeing an entangled open one. Follow them on every task.
|
|
75
|
+
|
|
76
|
+
- **Check what's already in flight before coding a fix, opening a PR, or merging.** Run `gh pr list` and `git ls-remote` first — another open PR may already touch the same issue or files. Reconcile against it; don't re-derive "the only thing left" from a stale handoff. (A `PreToolUse` hook also surfaces same-issue open PRs at `gh pr create`/`merge` time, but treat that as a backstop, not a substitute for looking.)
|
|
77
|
+
- **Truth is the CLI and running the code — not IDE/LSP "reminder" diagnostics.** Editor / `pyright`-in-worktree warnings go stale for an entire session and throw false positives (especially across multiple worktrees). Confirm with `ruff` / `pyright` / `pytest` from the terminal — or trust the worktree's own venv — never an IDE squiggle.
|
|
78
|
+
- **Verify third-party runtime behavior empirically before wiring it in.** Don't assume how an external library, API, or browser actually behaves — exercise it once and observe, then build on the observed contract.
|
|
79
|
+
- **If a claim can't be verified in the current environment, it's LIKELY — not CONFIRMED.** Keep the issue open, reference it with `Refs #N` (not `Closes #N`), and ship diagnostics rather than a blind fix. When you can't reproduce it, hand the fix to whoever can.
|
|
80
|
+
|
|
71
81
|
## Skills reference (cross-tool)
|
|
72
82
|
|
|
73
83
|
The `skills/` directory ships installable agent skill docs in plain Markdown with YAML frontmatter. Any agent can consume them directly:
|
|
@@ -7,6 +7,106 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.23.0] — 2026-07-01
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
|
|
14
|
+
- **MCP generation is now functional (#228)**: the `gflow_generate_image` and
|
|
15
|
+
`gflow_generate_video` MCP tools — previously non-functional stubs — now enqueue onto
|
|
16
|
+
the FlowWorker queue and run end-to-end, with the background worker owning download and
|
|
17
|
+
history recording. The `tools` parameter (e.g. `creative-director`) is now applied to
|
|
18
|
+
expand the prompt before generation (it was previously accepted but never applied), and
|
|
19
|
+
reference images are supported across the image (`i2i`) and video (`i2v` / `r2v`) tools.
|
|
20
|
+
|
|
21
|
+
### Fixed
|
|
22
|
+
|
|
23
|
+
- **macOS generation 401 — resolved (#222, #230)**: Flow cookies are now read from the
|
|
24
|
+
full cookie jar filtered by domain instead of a path-`/` URL filter that silently
|
|
25
|
+
dropped the `/fx`-scoped `__Secure-next-auth.session-token`; and on macOS — where the
|
|
26
|
+
headed generation context can intermittently fail to decrypt the on-disk cookie store —
|
|
27
|
+
the session is seeded into the context from a snapshot captured pre-launch via the
|
|
28
|
+
working `--password-store=basic` reader. Verified end-to-end on macOS (Apple Silicon) by
|
|
29
|
+
the reporter. Thanks @gunalak.
|
|
30
|
+
- **MCP video task safety (#228)**: `i2v` now requires `initial_frame` and `r2v` requires
|
|
31
|
+
`reference_images`, validated at the tool boundary with a clear error; a post-success
|
|
32
|
+
recording failure no longer flips a credit-spent video to `failed`; and any
|
|
33
|
+
non-`completed` task status is reported as a failure rather than a false success.
|
|
34
|
+
- **Chrome channel on Chromium-only hosts**: `channel_for_profile()` now gates
|
|
35
|
+
Playwright's `channel="chrome"` on a new `_is_playwright_chrome_channel_available()`
|
|
36
|
+
check that probes only the exact Google-Chrome paths Playwright hardcodes, instead
|
|
37
|
+
of `is_chrome_available()` (which also accepts Chromium). On a host with only
|
|
38
|
+
Chromium installed, the CLI no longer requests `channel="chrome"` and fails with
|
|
39
|
+
`Chromium distribution 'chrome' is not found at /opt/google/chrome/chrome`; it falls
|
|
40
|
+
back to bundled Chromium and logs an actionable warning (#219).
|
|
41
|
+
- **Text-to-image extra-image billing**: the generation-settings trigger selector now
|
|
42
|
+
requires `button[aria-haspopup='menu']` (aliased to `MODE_SWITCH_TRIGGER_SELECTORS`),
|
|
43
|
+
preventing a mis-click on an icon-only aspect thumbnail that skipped the count panel
|
|
44
|
+
and left Flow's own default count (typically 2) in effect — billing extra generations
|
|
45
|
+
while the CLI saved only one (#219).
|
|
46
|
+
- **Extra-image observability**: `generate_image()` now logs a
|
|
47
|
+
`client.generate_image_extra_returned` warning when the transport returns more images
|
|
48
|
+
than the requested `count=1`, so silent over-generation is surfaced to the user (#219).
|
|
49
|
+
- **macOS generation 401 — fail loud (#222)**: a `chrome`-strategy profile that is
|
|
50
|
+
silently downgraded to bundled Chromium at generation launch now raises instead of
|
|
51
|
+
running logged-out, so the macOS auth failure surfaces at its cause rather than as an
|
|
52
|
+
opaque later `401`.
|
|
53
|
+
|
|
54
|
+
### Diagnostics
|
|
55
|
+
|
|
56
|
+
- **Persistent-context cookie state (#222)**: generation launch now logs the resolved
|
|
57
|
+
`cookies_db_path` (`client.persistent_context_launch`) and the launched context's own
|
|
58
|
+
cookie state (`client.context_cookie_state`: `flow_session_cookie_present` / count /
|
|
59
|
+
expiry — **never values**, safe to paste publicly). This splits a cookie-**load**
|
|
60
|
+
failure (the macOS persistent context cannot decrypt the profile's cookies) from a
|
|
61
|
+
server-side rejection — the observability that localized the macOS `401` root cause,
|
|
62
|
+
now resolved (see the #222/#230 entry above).
|
|
63
|
+
|
|
64
|
+
## [0.22.0] — 2026-06-28
|
|
65
|
+
|
|
66
|
+
### Added
|
|
67
|
+
|
|
68
|
+
- **Tools framework ("Creative Director")**: a TOML-defined prompt-tool system with
|
|
69
|
+
`creative-director` as the first built-in tool, exposed via two surfaces:
|
|
70
|
+
- **`gflow tools list/show/run`** — discover tools, inspect their styles, and run them
|
|
71
|
+
standalone (e.g. `gflow tools run creative-director "a cat" --style cinema --json`).
|
|
72
|
+
- **`-t` / `--tool` option** on every generation command — `image t2i` / `i2i` / `batch`,
|
|
73
|
+
`video t2v` / `i2v` / `r2v` / `chain` — apply one or more tools before generating
|
|
74
|
+
(e.g. `--tool creative-director:style=cinema`). Repeatable. On multi-prompt batches and
|
|
75
|
+
chains the tool is applied per prompt/link. Replaces the never-released `-e/--expand` flag.
|
|
76
|
+
- The `creative-director` tool rewrites a terse prompt into a vivid one using Google's
|
|
77
|
+
five-component formula (Subject + Action + Context/Location + Composition/Camera + Style)
|
|
78
|
+
via the public Gemini API. Requires `GFLOW_CLI_GEMINI_API_KEY`
|
|
79
|
+
([get one](https://aistudio.google.com/apikey)); optional `GFLOW_CLI_GEMINI_MODEL`
|
|
80
|
+
(default `gemini-2.5-flash`). Domain-vocabulary modes (`--style cinema`, `portrait`,
|
|
81
|
+
`product`, etc.) inject specialized lens/lighting/colour vocabulary; styles are
|
|
82
|
+
**category-gated**, so image styles apply to image commands and video styles to video.
|
|
83
|
+
- Tool application is **never fatal** — missing key, rate limit, or any API/network fault
|
|
84
|
+
degrades gracefully to the original prompt.
|
|
85
|
+
- **History**: a generation rewritten by a tool records the user's original prompt in the
|
|
86
|
+
`prompt` column, the submitted expansion in `expanded_prompt`, and the applied tool
|
|
87
|
+
(`{name, version, model, params, config_hash}`) in `operations.metadata_json.tool` — all
|
|
88
|
+
honoring `GFLOW_CLI_HISTORY_PROMPTS=redacted` (the redacted form stores only
|
|
89
|
+
`{name, version, params_hash, config_hash}`).
|
|
90
|
+
- MCP parity: `gflow_list_tools` tool and a `tools` array parameter (`[{name, options}]`) on
|
|
91
|
+
`gflow_generate_image` / `gflow_generate_video`, validated and adapted to the CLI
|
|
92
|
+
`--tool` form.
|
|
93
|
+
- **"My Tools"**: drop your own tool TOMLs into `<GFLOW_CLI_HOME>/tools/*.toml` and they are
|
|
94
|
+
registered automatically — listed by `gflow tools list`, usable via `--tool`, and exposed over
|
|
95
|
+
MCP, just like built-ins. A user tool may override a built-in of the same name (logged via
|
|
96
|
+
`tool_user_override`); a malformed user TOML fails loud. See [docs/TOOLS.md](docs/TOOLS.md).
|
|
97
|
+
- The Gemini prompt expander gained an overall **wall-clock budget** (default ~60s per call)
|
|
98
|
+
on top of the lowered 20s per-attempt timeout, so sustained rate limiting can no longer
|
|
99
|
+
block a generation for the full retry schedule before falling back to the original prompt.
|
|
100
|
+
|
|
101
|
+
### Deprecated
|
|
102
|
+
|
|
103
|
+
- **`expand_prompt` MCP prompt**: superseded by the `creative-director` tool, which performs the
|
|
104
|
+
rewrite server-side (calls Gemini, strips banned keywords, supports domain styles, records
|
|
105
|
+
provenance). The prompt still works and now carries a `[DEPRECATED]` marker in its
|
|
106
|
+
client-visible description; it is slated for removal in a future major release. Use
|
|
107
|
+
`gflow tools run creative-director` / `--tool` (CLI) or `gflow_list_tools` + the `tools` array
|
|
108
|
+
param (MCP) instead.
|
|
109
|
+
|
|
10
110
|
## [0.21.0] — 2026-06-26
|
|
11
111
|
|
|
12
112
|
### Added
|
|
@@ -1582,7 +1682,9 @@ shell-script template that branches on these codes.
|
|
|
1582
1682
|
|
|
1583
1683
|
First skeleton. Not functional end-to-end yet.
|
|
1584
1684
|
|
|
1585
|
-
[Unreleased]: https://github.com/ffroliva/gflow-cli/compare/v0.
|
|
1685
|
+
[Unreleased]: https://github.com/ffroliva/gflow-cli/compare/v0.23.0...HEAD
|
|
1686
|
+
[0.23.0]: https://github.com/ffroliva/gflow-cli/compare/v0.22.0...v0.23.0
|
|
1687
|
+
[0.22.0]: https://github.com/ffroliva/gflow-cli/compare/v0.21.0...v0.22.0
|
|
1586
1688
|
[0.21.0]: https://github.com/ffroliva/gflow-cli/compare/v0.20.1...v0.21.0
|
|
1587
1689
|
[0.20.1]: https://github.com/ffroliva/gflow-cli/compare/v0.20.0...v0.20.1
|
|
1588
1690
|
[0.20.0]: https://github.com/ffroliva/gflow-cli/compare/v0.19.0...v0.20.0
|
|
@@ -9,6 +9,8 @@
|
|
|
9
9
|
| `GFLOW_CLI_BROWSER` | `auto` | Browser mode. See **Browser mode** section below. |
|
|
10
10
|
| `CHROME_BINARY` | (autodetect) | Override Chrome binary path. Falls back to platform-standard locations. |
|
|
11
11
|
| `GFLOW_CLI_CONCURRENCY` | `4` | Maximum parallel API requests per batch. |
|
|
12
|
+
| `GFLOW_CLI_GEMINI_API_KEY` | _(unset)_ | Public Gemini key enabling prompt expansion (`-e`/`--expand`). Unset = expansion is a graceful no-op. [Get one](https://aistudio.google.com/apikey). |
|
|
13
|
+
| `GFLOW_CLI_GEMINI_MODEL` | `gemini-2.5-flash` | Gemini model used for prompt expansion. |
|
|
12
14
|
| `GFLOW_LIVE` | _(unset)_ | Set to `1` to enable live-API test markers (`@pytest.mark.live`). |
|
|
13
15
|
|
|
14
16
|
---
|
|
@@ -102,6 +102,23 @@ pip install pre-commit && pre-commit install
|
|
|
102
102
|
|
|
103
103
|
The `.pre-commit-config.yaml` already ships ruff and the hygiene gate.
|
|
104
104
|
|
|
105
|
+
### SonarCloud quality gate
|
|
106
|
+
|
|
107
|
+
On top of the six gates, CI runs a **SonarCloud** analysis whose quality gate must be
|
|
108
|
+
**green** before a PR is merge-ready — the target is **zero new issues** on changed code
|
|
109
|
+
(new bugs, vulnerabilities, and code smells = 0; coverage of new lines ≥ 80%; security
|
|
110
|
+
hotspots reviewed = 100%). The local `--cov-fail-under=80` gate already pre-empts the
|
|
111
|
+
coverage condition, so if your tests are green locally you have usually cleared the part
|
|
112
|
+
of the gate you can run yourself.
|
|
113
|
+
|
|
114
|
+
SonarCloud is **server-side and maintainer-run**: it needs a repo secret (`SONAR_TOKEN`)
|
|
115
|
+
that, for security, GitHub does **not** share with pull requests from forks. So **on a
|
|
116
|
+
fork PR the SonarCloud check is skipped** — you cannot run it, and that is expected. A
|
|
117
|
+
maintainer checks the gate before merging (and, for fork PRs, may re-run the branch
|
|
118
|
+
internally to produce an analysis). Don't worry if you see the SonarCloud check absent or
|
|
119
|
+
skipped on your PR; focus on keeping the six local gates green and your diff free of new
|
|
120
|
+
smells. Full policy: [`docs/GITHUB.md`](docs/GITHUB.md) § SonarCloud Quality Gate.
|
|
121
|
+
|
|
105
122
|
### Script output convention
|
|
106
123
|
|
|
107
124
|
All runtime output — smoke runs, debug dumps, generated images — **must** go
|
|
@@ -25,7 +25,7 @@
|
|
|
25
25
|
|
|
26
26
|
## Active phase
|
|
27
27
|
|
|
28
|
-
- **Decoupled Daemon/Worker Plan:** The
|
|
28
|
+
- **Decoupled Daemon/Worker Plan:** The MCP→FlowWorker wiring shipped in v0.23.0 (PR #228). The remaining headless SSE Daemon + Tauri/React editor blueprint is scheduled in [gflow-studio-scaffold/PLAN.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-24-gflow-studio-scaffold/PLAN.md) and [rest-api-layer/PLAN.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-24-rest-api-layer/PLAN.md).
|
|
29
29
|
- **Core Lesson (Retrospective):** Kept `gflow-cli` strictly headless (running Uvicorn and FastMCP over localhost HTTP/SSE). Bypassed browser context locks by serializing task writes in SQLite queue, allowing parallel client database reads via WAL mode.
|
|
30
30
|
|
|
31
31
|
See [PLAN.md](PLAN.md) or type `gflow:status` for the current task. Type `gflow:plan <feature>` to create a new feature plan.
|
|
@@ -14,6 +14,28 @@ Living list of behaviour that's broken, surprising, or limited by design — alo
|
|
|
14
14
|
|
|
15
15
|
## Open
|
|
16
16
|
|
|
17
|
+
### macOS: generation runs logged-out → HTTP 401, even with `--browser chrome`
|
|
18
|
+
|
|
19
|
+
- **Status:** **RESOLVED in v0.23.0** ([#222](https://github.com/ffroliva/gflow-cli/issues/222),
|
|
20
|
+
fixed by [#230](https://github.com/ffroliva/gflow-cli/pull/230), @gunalak)
|
|
21
|
+
- **Severity:** High · **Affected:** all `gflow` generation on **macOS** with a
|
|
22
|
+
`chrome`-strategy profile; Windows was unaffected
|
|
23
|
+
|
|
24
|
+
On macOS, generation calls failed with **HTTP 401** (`AuthExpiredError` at
|
|
25
|
+
`project.createProject`) on a profile that `gflow auth login` and verification
|
|
26
|
+
accepted. Two corrections fixed it (verified end-to-end on macOS Apple Silicon):
|
|
27
|
+
|
|
28
|
+
1. **Cookie-read bug (unconditional).** The Flow cookie snapshot read the jar via
|
|
29
|
+
`ctx.cookies(["https://labs.google"])`, whose path-`/` filter silently dropped
|
|
30
|
+
the `/fx`-scoped `__Secure-next-auth.session-token`. Now the full jar is read
|
|
31
|
+
and filtered by domain, so the session token is captured.
|
|
32
|
+
2. **macOS headed-context decrypt (intermittent).** When the headed generation
|
|
33
|
+
context can't decrypt the on-disk store, the session is seeded from a snapshot
|
|
34
|
+
captured **pre-launch** via the working `--password-store=basic` reader. No-op on
|
|
35
|
+
Windows and on runs where the context decrypts natively.
|
|
36
|
+
|
|
37
|
+
Evidence: [LIVE_VERIFICATION_v0.23.0](docs/LIVE_VERIFICATION_v0.23.0.md).
|
|
38
|
+
|
|
17
39
|
### Flow's new full-page media-library UI breaks entity attach (A/B rollout)
|
|
18
40
|
|
|
19
41
|
- **Status:** **Open** — Flow-side staged rollout; tracked in
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: gflow-cli
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.23.0
|
|
4
4
|
Summary: Unofficial CLI for Google Flow — drive Veo image-to-video generations from the terminal.
|
|
5
5
|
Project-URL: Homepage, https://github.com/ffroliva/gflow-cli
|
|
6
6
|
Project-URL: Issues, https://github.com/ffroliva/gflow-cli/issues
|
|
@@ -58,7 +58,7 @@ Requires-Dist: numpy>=1.24; extra == 'dev'
|
|
|
58
58
|
Requires-Dist: pyright>=1.1.0; extra == 'dev'
|
|
59
59
|
Requires-Dist: pytest-asyncio>=0.23.0; extra == 'dev'
|
|
60
60
|
Requires-Dist: pytest>=8.0.0; extra == 'dev'
|
|
61
|
-
Requires-Dist: ruff==0.15.
|
|
61
|
+
Requires-Dist: ruff==0.15.20; extra == 'dev'
|
|
62
62
|
Provides-Extra: gcs
|
|
63
63
|
Requires-Dist: gcsfs>=2024.2.0; extra == 'gcs'
|
|
64
64
|
Requires-Dist: universal-pathlib>=0.2.5; extra == 'gcs'
|
|
@@ -94,6 +94,7 @@ You pay for Google AI Ultra or Pro, you have Veo credits, and you run real batch
|
|
|
94
94
|
|
|
95
95
|
- **Batch generation.** Loop prompts straight from the shell: `for p in $(cat prompts.txt); do gflow image t2i "$p"; done`. Image batching plus `gflow video t2v` / `i2v` / `r2v` all ship today.
|
|
96
96
|
- **Consistent subjects.** `gflow character create` mints a Flow Character (face and body reference) so the same person appears from one generation to the next.
|
|
97
|
+
- **Prompt tools.** `--tool creative-director` rewrites a terse prompt into a vivid one (Google's 5-component formula) before generating — on any command. Bring your own with [My Tools](docs/TOOLS.md).
|
|
97
98
|
- **Pipelines.** Wire Veo into your content automation, AI-video stack, or batch experiments.
|
|
98
99
|
- **Terminal-native.** After one `gflow auth login`, you stay in the shell. No clicking through dialogs.
|
|
99
100
|
|
|
@@ -359,8 +359,14 @@ The video-generation feature has its own sub-phase plan (spike → Phase A → P
|
|
|
359
359
|
- **Phase 4 (Task #6, 2026-05-26, branch `claude/next-quick-win-gBPqS`, PR #93):** `NEW_PROJECT_SELECTORS` expanded to all 14 locales (icon-first tier + 14-locale text tier); English-only ARIA fallbacks (`[aria-label*='New project']`, `[aria-label*='Project']`) removed. `SUBMIT_BUTTON_SELECTORS` drops its English-only `button[aria-label*="Create"]` entry — `arrow_forward` icon selectors cover it in all locales. Both tuples are now fully locale-invariant. Note: issue #24 was closed 2026-05-24 after Phases 1–3; Phase 4 is cosmetic tail work. `--lang=en-US` retained only to stabilise `IMAGE_MODEL_OPTION_SELECTORS` (product names like "Nano Banana 2" may be localised). Removing it requires converting the image model picker to a structural anchor — tracked as issue #94 (Phase 5 below). **R2V live e2e on non-EN not yet exercised** — still open.
|
|
360
360
|
- **Phase 5 (2026-05-30, branch `claude/issue-94-staleness-check-MnsEY`, PR #127):** `IMAGE_MODEL_OPTION_SELECTORS` and `VIDEO_MODEL_OPTION_SELECTORS` converted from `dict[Model, str]` to `dict[Model, tuple[str, ...]]` (cascade discipline; Tier 1 structural slots reserved for future DOM-probe-confirmed anchors). `--lang=en-US` removed from Chromium launch args — locale controlled by `locale=locale_env` Playwright kwarg (persists across all navigations including `/project/<uuid>` deep-links) + `FLOW_URL`'s `?hl=en` on initial load. Branded model names confirmed locale-stable. Four new `TestSelectorLocaleInvariance` tests + four `TestSelectImageModel` runtime tests. **R2V live e2e on non-EN still pending (owner gate — requires authenticated non-EN Chrome profile).**
|
|
361
361
|
- [ ] **Model Context Protocol (MCP) Server.** (Backlog) Expose core gflow-cli tools via MCP for language-agnostic agentic access. Planned in [PREDICT.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-22-mcp-server/PREDICT.md) / [SCENARIO.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-22-mcp-server/SCENARIO.md) / [PLAN.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-22-mcp-server/PLAN.md).
|
|
362
|
-
- [
|
|
363
|
-
-
|
|
362
|
+
- [x] **Tools framework + Prompt Expansion ("Creative Director") — shipped → develop (PRs #210 + #211, 2026-06-28).** Prompt expansion evolved from the never-released `-e`/`--expand` flag into a TOML-defined **Tools framework**: `creative-director` is the first built-in tool, invoked uniformly via `--tool/-t <name>[:k=v]` on every generation command (`image t2i`/`i2i`/`batch`, `video t2v`/`i2v`/`r2v`/`chain`) or standalone via `gflow tools list/show/run`. The tool rewrites a terse prompt via Gemini's 5-component formula (`src/gflow_cli/tools/`, stdlib-urllib expander, never-fatal: missing key / 429-backoff / network / empty-clean all fall back to the original), with 15 domain styles and deterministic banned-keyword stripping. `operations.expanded_prompt` records original + submitted expansion (withheld under `history_prompts=redacted`); `metadata_json.tool` records `{name, version, model, params, config_hash}` provenance (minimized in redacted mode). Reuses `GFLOW_CLI_GEMINI_API_KEY`; `GFLOW_CLI_GEMINI_MODEL` overrides. MCP parity: `gflow_list_tools` + a `tools` array param per AGENTS.md §61. Docs: [TOOLS.md](file:///C:/development/github/gflow-cli/docs/TOOLS.md) + [PROMPT_EXPANSION.md](file:///C:/development/github/gflow-cli/docs/PROMPT_EXPANSION.md). Memory `[[prompt-expansion-feature]]`.
|
|
363
|
+
- **PR #210 (framework):** `tools/` package (spec/loader/registry/runtime/expander/banned/invocation), `creative-director.toml`, `gflow tools list/show/run`, `--tool` on t2i/t2v (single-prompt guard kept), MCP `gflow_list_tools` + `tools` param.
|
|
364
|
+
- **PR #211 (broaden surface):** `original_prompt`/`tool` carried on the request DTOs (`GenerateImageRequest`/`GenerateVideoRequest`/`BatchPromptItem`/`ChainLinkSpec`); recorder reads `request.original_prompt` (kwarg retired); `metadata_json.tool` recording; `--tool` wired into i2i/batch/i2v/r2v/chain; single-prompt guard removed. Silent-misrecord hazard resolved by carrying `original_prompt` on the DTO rather than re-threading a kwarg through each recorder method.
|
|
365
|
+
- **Expander robustness — DONE 2026-06-28 (PR #214).** Per-attempt timeout lowered 30s→20s and an overall `max_total_seconds` wall-clock budget (default 60s) added to `tools/expander.py` — retries stop once the budget is spent and each attempt's timeout is clamped to the remaining budget, so sustained 429s can no longer block ~120s before fallback. `tenacity` (a dep) was evaluated and **rejected**: it is built around re-raising after retries whereas the expander must never raise (fall back to the original), and the per-attempt structlog + total-budget logic is clearer as a hand-rolled loop with injectable `transport`/`sleep`/`clock` seams.
|
|
366
|
+
- **`expand_prompt` reconcile — DONE 2026-06-28 (PR #215).** The legacy `mcp/prompts.py` `expand_prompt` MCP prompt is **deprecated** in favor of the `creative-director` tool (client-visible `[DEPRECATED]` marker; kept functional; removal slated for a future major). See [PROMPT_EXPANSION § Relationship to expand_prompt](file:///C:/development/github/gflow-cli/docs/PROMPT_EXPANSION.md).
|
|
367
|
+
- **My Tools — DONE 2026-06-28 (PR #216).** User-authored TOMLs in `<GFLOW_CLI_HOME>/tools/*.toml` are loaded into the registry (override-a-builtin-with-warning; malformed fails loud).
|
|
368
|
+
- **Backlog — deferred by design:** the S3 `Tool.apply(ctx)→outcome` dispatch framework. The research doc gates it on a *second, non-prompt* tool (e.g. Mockup) — building it now with a single prompt-only implementer is the documented "premature uniformity (guessed contract)" anti-pattern.
|
|
369
|
+
- [ ] **Integrated Filmmaking Studio, Flow Worker & MCP SSE Service.** (Backlog) The MCP→FlowWorker wiring shipped in v0.23.0 (PR #228). Remaining: a local FastAPI/React filmmaking studio dashboard + HTTP/SSE MCP. Planned in [gflow-studio-scaffold/PLAN.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-24-gflow-studio-scaffold/PLAN.md) and [rest-api-layer/PLAN.md](file:///C:/development/github/gflow-cli/docs/superpowers/plans/2026-06-24-rest-api-layer/PLAN.md).
|
|
364
370
|
- [x] **Issue #92: Google account identity persistence shipped 2026-05-28 (PR #110).** After every `gflow auth login`, both auth strategies write the verified email to `$GFLOW_CLI_HOME/profile_<name>/.gflow_account`. `ProfileMeta.google_account` surfaces it; `gflow auth list` and `gflow auth list --json` display it. First-login auto-rename: when no `--profile` flag was given and the only profile is named `default`, it is renamed to the email local-part. `profile_store.rename_profile()` primitive added. Zero-credit smoke test (`tests/smoke/test_profile_account_smoke.py`) ships with backfill path for pre-existing profiles. LLM council (9-dim) run; all must-fix items applied before merge. See `KNOWN_ISSUES.md` § Resolved for full detail.
|
|
365
371
|
- [x] **`/gflow:pr-council-review` slash command shipped 2026-05-26 (PR #97).** Multi-dimensional LLM council for open PRs (4 baseline + 8 adaptive dimensions, mandatory memory-slug binding, draft-PR guard, YELLOW escape valve, live-verify gate). Validated on PR #93; self-audited by 3-agent meta-council surfacing 13 must-fix items applied before merge. See memory `[[llm-council-code-review-pr93]]`.
|
|
366
372
|
- **Phase A (Backlog — Portability):** extract command body into `skills/pr-council-review/SKILL.md` so Gemini CLI / Codex / Cursor / Aider can consume it. Keep `.claude/commands/gflow/pr-council-review.md` as a thin wrapper. Memory: `[[pr-council-review-portability-backlog]]`.
|
|
@@ -23,6 +23,7 @@ You pay for Google AI Ultra or Pro, you have Veo credits, and you run real batch
|
|
|
23
23
|
|
|
24
24
|
- **Batch generation.** Loop prompts straight from the shell: `for p in $(cat prompts.txt); do gflow image t2i "$p"; done`. Image batching plus `gflow video t2v` / `i2v` / `r2v` all ship today.
|
|
25
25
|
- **Consistent subjects.** `gflow character create` mints a Flow Character (face and body reference) so the same person appears from one generation to the next.
|
|
26
|
+
- **Prompt tools.** `--tool creative-director` rewrites a terse prompt into a vivid one (Google's 5-component formula) before generating — on any command. Bring your own with [My Tools](docs/TOOLS.md).
|
|
26
27
|
- **Pipelines.** Wire Veo into your content automation, AI-video stack, or batch experiments.
|
|
27
28
|
- **Terminal-native.** After one `gflow auth login`, you stay in the shell. No clicking through dialogs.
|
|
28
29
|
|
|
@@ -27,6 +27,9 @@ $env:GFLOW_CLI_HOME = "D:\gflow-cli" # PowerShell
|
|
|
27
27
|
```
|
|
28
28
|
|
|
29
29
|
See [AUTHENTICATION § Session storage](AUTHENTICATION.md#session-storage) for the full layout.
|
|
30
|
+
`$GFLOW_CLI_HOME` also holds `config.toml`, the SQLite catalog (`gflow.db`), and — if you
|
|
31
|
+
create it — a `tools/` directory of user-authored "My Tools" TOMLs
|
|
32
|
+
(`<GFLOW_CLI_HOME>/tools/*.toml`, auto-loaded; see [TOOLS.md § My Tools](TOOLS.md)).
|
|
30
33
|
|
|
31
34
|
### `GFLOW_CLI_PROFILE`
|
|
32
35
|
|
|
@@ -112,11 +115,26 @@ Deep setup, verification, and security notes live in
|
|
|
112
115
|
|
|
113
116
|
### `GFLOW_CLI_GEMINI_API_KEY`
|
|
114
117
|
|
|
115
|
-
**What:** API key
|
|
116
|
-
|
|
118
|
+
**What:** Public Gemini API key. Used by the **`creative-director`** prompt tool
|
|
119
|
+
(`--tool creative-director` / `gflow tools run creative-director`, see
|
|
120
|
+
[TOOLS.md](TOOLS.md) and [PROMPT_EXPANSION.md](PROMPT_EXPANSION.md)) and, in future, by the
|
|
121
|
+
official Veo 3.1 SDK.
|
|
122
|
+
**Required when:** you apply the `creative-director` tool (via `--tool` on any generation
|
|
123
|
+
command, or `gflow tools run`), or `GFLOW_CLI_PROVIDER=official`.
|
|
117
124
|
**Default:** unset
|
|
125
|
+
**Behavior when unset:** the tool is a no-op — gflow logs an `INFO` notice and generates
|
|
126
|
+
from your original prompt (it never fails the run). API errors (rate limit, network) fall
|
|
127
|
+
back the same way after a short exponential-backoff retry, bounded by an overall ~60s
|
|
128
|
+
wall-clock budget per call.
|
|
118
129
|
**Get one:** <https://aistudio.google.com/apikey>
|
|
119
130
|
|
|
131
|
+
### `GFLOW_CLI_GEMINI_MODEL`
|
|
132
|
+
|
|
133
|
+
**What:** Gemini model used by the `creative-director` prompt tool.
|
|
134
|
+
**Default:** `gemini-2.5-flash`
|
|
135
|
+
**Note:** Override to select a newer Flash revision without upgrading gflow-cli, e.g.
|
|
136
|
+
`GFLOW_CLI_GEMINI_MODEL=gemini-2.5-flash-lite`.
|
|
137
|
+
|
|
120
138
|
### `GFLOW_CLI_AUTH_LOGIN_TIMEOUT`
|
|
121
139
|
|
|
122
140
|
**What:** Maximum time (seconds) that `gflow auth login` waits for the user to complete the Google sign-in flow in the browser.
|
|
@@ -179,6 +197,11 @@ Use this when you want the DB on a different volume, outside `GFLOW_CLI_HOME`, o
|
|
|
179
197
|
|
|
180
198
|
**Default:** `store`
|
|
181
199
|
|
|
200
|
+
**Tool provenance:** when a prompt tool (e.g. `creative-director`) rewrites a prompt, `store`
|
|
201
|
+
mode also records the submitted `expanded_prompt` and a full `metadata_json.tool` descriptor;
|
|
202
|
+
`redacted` withholds the expanded prompt and reduces the descriptor to
|
|
203
|
+
`{name, version, params_hash, config_hash}`. See [PROMPT_EXPANSION.md](PROMPT_EXPANSION.md).
|
|
204
|
+
|
|
182
205
|
```bash
|
|
183
206
|
GFLOW_CLI_HISTORY_PROMPTS=redacted gflow image t2i "confidential brief"
|
|
184
207
|
```
|