Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 9 additions & 4 deletions .github/workflows/add-community-bundle.md
Original file line number Diff line number Diff line change
Expand Up @@ -118,11 +118,16 @@ Run every check and collect all failures before deciding the outcome.

### 2c. Release artifact

- The download URL must be an HTTPS GitHub release asset URL under the submitted
repository:
- The download URL MUST follow the accepted tag-pinned pattern under the
submitted repository:
`https://github.com/<owner>/<repo>/releases/download/<tag>/<asset>.zip`.
- Confirm the release exists, its tag corresponds to the submitted version
(`vX.Y.Z` or `X.Y.Z`), and the exact ZIP asset is attached to that release.
- If the download URL path contains `releases/latest/`, reject with an
explanation — this URL is floating and not acceptable. Fail immediately,
before any HTTP check.
- The version segment embedded in the URL (`/download/<tag>/`) MUST match the
submitted version (`vX.Y.Z` or `X.Y.Z`).
- Only after the pinning checks pass: confirm the release exists, the exact ZIP
asset is attached to that release, and the download URL returns HTTP 200.
- Confirm the asset name is versioned and consistent with the submitted bundle
ID and version.

Expand Down
10 changes: 8 additions & 2 deletions .github/workflows/add-community-extension.md
Original file line number Diff line number Diff line change
Expand Up @@ -110,11 +110,17 @@ deciding pass/fail:
- Confirm the repository contains a `LICENSE` file

### 2d. Release and download URL validation
- The download URL should follow the pattern
- The download URL MUST follow one of the accepted tag-pinned patterns:
`https://github.com/<owner>/<repo>/archive/refs/tags/v<version>.zip`
or
`https://github.com/<owner>/<repo>/releases/download/<tag>/<asset>.zip`
- Verify a GitHub release exists matching the submitted version
- If the download URL path contains `releases/latest/`, reject with an
explanation — this URL is floating and not acceptable. Fail immediately,
before any HTTP check.
- The version segment embedded in the URL (`/tags/v<version>.zip` or
`/download/<tag>/`) MUST match the submitted version (`vX.Y.Z` or `X.Y.Z`).
- Only after the pinning checks pass: verify a GitHub release exists matching
the submitted version, and that the download URL returns HTTP 200.

### 2e. Submission checklists
- Confirm that all required checkboxes in the Testing Checklist and Submission
Expand Down
10 changes: 8 additions & 2 deletions .github/workflows/add-community-preset.md
Original file line number Diff line number Diff line change
Expand Up @@ -161,11 +161,17 @@ preset** — not just any file named `README.md`, and not a product/framework pi
`specify preset add ...` command for this preset; otherwise it fails check 2d above.

### 2e. Release and download URL validation
- The download URL should follow the pattern
- The download URL MUST follow one of the accepted tag-pinned patterns:
`https://github.com/<owner>/<repo>/archive/refs/tags/v<version>.zip`
or
`https://github.com/<owner>/<repo>/releases/download/<tag>/<asset>.zip`
- Verify a GitHub release exists matching the submitted version
- If the download URL path contains `releases/latest/`, reject with an
explanation — this URL is floating and not acceptable. Fail immediately,
before any HTTP check.
- The version segment embedded in the URL (`/tags/v<version>.zip` or
`/download/<tag>/`) MUST match the submitted version (`vX.Y.Z` or `X.Y.Z`).
- Only after the pinning checks pass: verify a GitHub release exists matching
the submitted version, and that the download URL returns HTTP 200.

### 2f. Submission checklists
- Confirm that all required checkboxes in the Testing Checklist and Submission
Expand Down
15 changes: 15 additions & 0 deletions tests/test_github_workflows.py
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,21 @@ def test_community_submission_automation_is_wired_to_allowed_files():
assert label in assignment_text


def test_community_submission_workflows_require_tag_pinned_download_urls():
"""Catalog agents must reject floating releases/latest URLs (issue #4185)."""
for workflow, *_ in COMMUNITY_SUBMISSION_WORKFLOWS:
source_text = (WORKFLOWS_DIR / f"add-community-{workflow}.md").read_text(
encoding="utf-8"
)
lowered = source_text.lower()

assert "should follow the pattern" not in lowered
assert "releases/latest/" in source_text
assert "reject" in lowered
assert "`vX.Y.Z` or `X.Y.Z`" in source_text
assert "MUST" in source_text or "must" in lowered


def test_community_submission_allowed_files_do_not_include_other_catalogs_or_docs():
allowed_by_workflow = {
workflow: set(
Expand Down