Skip to content

fix(extensions): harden URL download cache - #3869

Open
mnriem wants to merge 1 commit into
github:mainfrom
mnriem:fix/extension-add-cache-symlink-hardening
Open

fix(extensions): harden URL download cache#3869
mnriem wants to merge 1 commit into
github:mainfrom
mnriem:fix/extension-add-cache-symlink-hardening

Conversation

@mnriem

@mnriem mnriem commented Jul 29, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • validate each extension download-cache component and reject symlinks, non-directories, and resolved escapes
  • create URL download ZIPs through dir_fd + O_NOFOLLOW with exclusive mode 0600, failing closed when atomic primitives are unavailable
  • clean up downloads through a descriptor-relative no-follow walk and cover symlink, alias, collision, unsupported-platform, and happy paths

Testing

  • .venv/bin/python -m pytest tests/test_extension_add_path_traversal.py tests/test_extensions.py::TestExtensionAddCLI -q (40 passed)
  • broader extension suite: 854 passed, 1 skipped, 1 unrelated existing assertion mismatch in test_empty_provides_and_no_hooks_keeps_its_own_message

Authored autonomously on behalf of @mnriem by GitHub Copilot (model: GPT-5.6 Sol).

Assisted-by: GitHub Copilot (model: GPT-5.6 Sol, autonomous)

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

Copilot-Session: 8f71e02a-bc64-4593-b305-2554debe96f6
Copilot AI review requested due to automatic review settings July 29, 2026 21:25

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Not ready to approve

Installation still has a pathname-reopen race, and existing Windows URL-install tests will fail.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

This review doesn't count toward merge requirements. Sign up for the private preview to control whether Copilot approvals count.

Pull request overview

Hardens custom-URL extension downloads against cache path and symlink attacks.

Changes:

  • Adds descriptor-relative, no-follow ZIP creation and cleanup.
  • Enforces private file permissions and fails closed on unsupported platforms.
  • Adds security and successful-install coverage.
File summaries
File Description
src/specify_cli/extensions/_commands.py Implements secure cache handling.
tests/test_extension_add_path_traversal.py Tests cache traversal and platform behavior.
Review details
  • Files reviewed: 2/2 changed files
  • Comments generated: 3
  • Review effort level: Medium

We're testing this review assessment. Please use 👍 or 👎 to tell us if it's correct.

pass

# Install from downloaded ZIP
manifest = manager.install_from_zip(zip_path, speckit_version, priority=priority, force=force)
Comment on lines +500 to +502
"URL-based extension installs require POSIX-style dir_fd and "
"O_NOFOLLOW support, which is unavailable on this platform. "
"Use --dev with a local directory or install from a catalog instead."
def test_url_install_writes_and_cleans_up_secure_download(
project_dir: Path, monkeypatch: pytest.MonkeyPatch
) -> None:
_require_secure_dir_fd()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants