generated from john/python-template
Phase 6: enforce the quality gate in CI and export the V4.7 review log
Quality Gate / gate (push) Successful in 33s
Quality Gate / gate (push) Successful in 33s
Adds .github/workflows/quality-gate.yml, running the gate on push and pull request. CI invokes `pre-commit run --all-files` rather than restating the `ruff check` and `ty check` commands, so the checks keep a single definition in .pre-commit-config.yaml and local and CI cannot drift (plan task 2). The workflow writes a .env file rather than exporting an environment variable. The two are not equivalent here: Settings reads the .env file, while the external-test skip guard reads os.getenv, so an exported variable un-skips the external tests and sends them to the network. Measured in CI: no .env gave 115 failures and 18 errors, an exported dummy key gave 3 failures, and a written .env file reproduced the local baseline exactly. Negative-tested on a scratch branch: a deliberate lint error failed the run at `ruff check` with exactly the planted errors, confirming the gate blocks rather than merely reporting (plan task 4). The subsequent clean run passed ruff and ty and reported 295 passed, 4 skipped, matching local and confirming the four credential-gated tests skip cleanly (plan task 3). That first green run caught a real platform-dependent defect. PromptStore rejected non-direct-child names via `Path(name).name != name`, which is platform-dependent: on POSIX a backslash is an ordinary filename character, so "nested\prompt.md" passed the guard and failed later as NOT_FOUND rather than VALIDATION. Windows cannot reproduce it. No traversal was possible, since the path.parent != root check still held, so the impact was a wrong error category and a red gate. Both separators are now rejected explicitly, matching the ^[^/\\]+$ pattern config.PromptFilename already used. Also exports docs/ver4.7/review_log_v4_7.md, the working record kept across all six phases: 50 entries, 1 still open. The open entry is a pre-existing /ui redirect defect found during the Phase 3 UI walk and deliberately left unfixed as outside the V4.7 scope boundary. Co-authored-by: Copilot App <[email protected]>
This commit is contained in:
@@ -104,8 +104,11 @@ class PromptStore:
|
||||
|
||||
def _resolve_existing_prompt(self, name: str) -> Path:
|
||||
normalized_name = name.strip()
|
||||
# Path().name is platform-dependent: POSIX treats "\" as an ordinary filename
|
||||
# character, so reject both separators explicitly to match config.PromptFilename.
|
||||
if (
|
||||
not normalized_name
|
||||
or any(separator in normalized_name for separator in ("/", "\\"))
|
||||
or Path(normalized_name).name != normalized_name
|
||||
or Path(normalized_name).suffix.lower() != PROMPT_EXTENSION
|
||||
):
|
||||
|
||||
Reference in New Issue
Block a user