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
23 changes: 23 additions & 0 deletions .github/actions/setup-docker/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
name: "Set up Docker"
description: >-
Set up QEMU + Docker Buildx and authenticate to Docker Hub for multi-arch
image builds. Centralizes the QEMU/Buildx/login trio used by release,
preview, and stable workflows.

inputs:
dockerhub-username:
description: "Docker Hub username (pass from secrets)"
required: true
dockerhub-token:
description: "Docker Hub token/password (pass from secrets)"
required: true

runs:
using: "composite"
steps:
- uses: docker/setup-qemu-action@06116385d9baf250c9f4dcb4858b16962ea869c3 # v4.1.0
- uses: docker/setup-buildx-action@d7f5e7f509e45cec5c76c4d5afdd7de93d0b3df5 # v4.1.0
- uses: docker/login-action@650006c6eb7dba73a995cc03b0b2d7f5ca915bee # v4.2.0
with:
username: ${{ inputs.dockerhub-username }}
password: ${{ inputs.dockerhub-token }}
13 changes: 13 additions & 0 deletions .github/actions/setup-hatch/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
name: "Set up Hatch build tooling"
description: >-
Install the pinned hatch / hatchling / virtualenv toolchain used to build
and publish the package. Assumes Python is already set up by the caller.

runs:
using: "composite"
steps:
- shell: bash
run: |
python -m pip install --upgrade pip
pip install "virtualenv<20.36"
pip install hatchling==1.27.0 hatch==1.14.0
39 changes: 39 additions & 0 deletions .github/actions/setup-sfw/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
name: "Set up Socket Firewall (free)"
description: >-
Set up the requested language toolchain and install Socket Firewall (free
edition) so subsequent steps can run package-manager commands wrapped with
`sfw`. Free/anonymous mode -- no API token, safe on untrusted/Dependabot PRs.

inputs:
python:
description: "Set up Python 3.12"
default: "false"
node:
description: "Set up Node 20 (needed for npm-wrapped checks)"
default: "false"
uv:
description: "Install uv (implies Python)"
default: "false"

runs:
using: "composite"
steps:
- if: ${{ inputs.python == 'true' || inputs.uv == 'true' }}
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: "3.12"

- if: ${{ inputs.node == 'true' }}
uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0
with:
node-version: "20"

# Official Socket setup action. Wires up sfw routing correctly.
- uses: socketdev/action@ba6de6cc0565af1f42295590380973573297e31f # v1.3.2
with:
mode: firewall-free

- if: ${{ inputs.uv == 'true' }}
name: Install uv
shell: bash
run: python -m pip install --upgrade pip uv
6 changes: 4 additions & 2 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
Expand Up @@ -36,9 +36,11 @@ updates:
cooldown:
default-days: 7

# GitHub Actions used in workflows
# GitHub Actions used in workflows and local composite actions.
- package-ecosystem: "github-actions"
directory: "/"
directories:
- "/"
- "/.github/actions/*"
schedule:
interval: "weekly"
open-pull-requests-limit: 2
Expand Down
52 changes: 19 additions & 33 deletions .github/workflows/dependabot-review.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ jobs:
dockerfile_changed: ${{ steps.diff.outputs.dockerfile_changed }}
workflow_or_action_changed: ${{ steps.diff.outputs.workflow_or_action_changed }}
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 0
persist-credentials: false
Expand Down Expand Up @@ -68,7 +68,7 @@ jobs:
echo "fixture_npm_changed=$(has_file '^tests/e2e/fixtures/simple-npm/')"
echo "fixture_pypi_changed=$(has_file '^tests/e2e/fixtures/simple-pypi/')"
echo "dockerfile_changed=$(has_file '^Dockerfile$')"
echo "workflow_or_action_changed=$(has_file '^\.github/workflows/|^\.github/dependabot\.yml$')"
echo "workflow_or_action_changed=$(has_file '^\.github/workflows/|^\.github/actions/|^\.github/dependabot\.yml$')"
} >> "$GITHUB_OUTPUT"

- name: Summarize review expectations
Expand All @@ -89,27 +89,23 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 15
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false

- uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
- uses: ./.github/actions/setup-sfw
with:
python-version: "3.12"

- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af
with:
node-version: "20"

- name: Install Socket Firewall
run: npm install -g sfw

- name: Install uv
run: python -m pip install --upgrade pip uv
uv: "true"

- name: Sync project through Socket Firewall
run: sfw uv sync --extra test --extra dev
# `sfw uv sync` is the intended way to route uv through Socket Firewall
# (per Socket's own uv wrapper guidance). --locked verifies the exact
# uv.lock set and fails on lockfile drift rather than silently
# re-resolving, so the firewall inspects precisely what would install.
# Note: uv's sfw integration is quieter than npm/pip -- it does not
# print the "N packages fetched" footer, but interception is active.
run: sfw uv sync --locked --extra test --extra dev

- name: Import smoke test
run: |
Expand All @@ -130,17 +126,14 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 15
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false

- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af
- uses: ./.github/actions/setup-sfw
with:
node-version: "20"

- name: Install Socket Firewall
run: npm install -g sfw
node: "true"

- name: Install fixture through Socket Firewall
working-directory: tests/e2e/fixtures/simple-npm
Expand All @@ -152,21 +145,14 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 15
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false

- uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
with:
python-version: "3.12"

- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af
- uses: ./.github/actions/setup-sfw
with:
node-version: "20"

- name: Install Socket Firewall
run: npm install -g sfw
python: "true"

- name: Install fixture through Socket Firewall
working-directory: tests/e2e/fixtures/simple-pypi
Expand All @@ -182,7 +168,7 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false
Expand Down
20 changes: 8 additions & 12 deletions .github/workflows/docker-stable.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ jobs:
stable:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
persist-credentials: false

Expand All @@ -28,23 +28,19 @@ jobs:
fi
echo "Version ${INPUT_VERSION} found on PyPI - proceeding with release"

- name: Set up QEMU
uses: docker/setup-qemu-action@c7c53464625b32c7a7e944ae62b3e17d2b600130 # v3

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3

- name: Login to Docker Hub with Organization Token
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3
- name: Set up Docker publishing
uses: ./.github/actions/setup-docker
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
dockerhub-username: ${{ secrets.DOCKERHUB_USERNAME }}
dockerhub-token: ${{ secrets.DOCKERHUB_TOKEN }}

- name: Build & Push Stable Docker
uses: docker/build-push-action@ca052bb54ab0790a636c9b5f226502c73d547a25 # v5
uses: docker/build-push-action@f9f3042f7e2789586610d6e8b85c8f03e5195baf # v7.2.0
with:
push: true
platforms: linux/amd64,linux/arm64
cache-from: type=gha
cache-to: type=gha,mode=max
tags: socketdev/cli:stable
build-args: |
CLI_VERSION=${{ inputs.version }}
Expand Down
6 changes: 3 additions & 3 deletions .github/workflows/e2e-test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -70,16 +70,16 @@ jobs:

name: e2e-${{ matrix.name }}
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 0
persist-credentials: false

- uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: '3.12'

- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af
- uses: actions/setup-node@48b55a011bda9f5d6aeb4c2d9c7362e8dae4041e # v6.4.0
if: matrix.setup-node == 'true'
with:
node-version: '20'
Expand Down
53 changes: 30 additions & 23 deletions .github/workflows/pr-preview.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,29 +3,37 @@ on:
pull_request:
types: [opened, synchronize, ready_for_review]

# Cancel an in-flight preview when the PR is pushed again -- previews are slow
# (publish + multi-step Docker build), so superseded runs shouldn't keep going.
concurrency:
group: pr-preview-${{ github.event.pull_request.number }}
cancel-in-progress: true

jobs:
preview:
if: github.event.pull_request.head.repo.full_name == github.repository
# Skip on:
# - PRs from forks (no access to publish secrets)
# - Dependabot PRs: preview-publishing a dependency bump to Test PyPI /
# Docker Hub is pointless and fails (no version bump, secret access).
if: >-
github.event.pull_request.head.repo.full_name == github.repository &&
github.event.pull_request.user.login != 'dependabot[bot]'
runs-on: ubuntu-latest
permissions:
id-token: write
contents: read
pull-requests: write
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 0
persist-credentials: false
- uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: '3.13'

# Install all dependencies from pyproject.toml
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install "virtualenv<20.36"
pip install hatchling==1.27.0 hatch==1.14.0
- name: Install build tooling
uses: ./.github/actions/setup-hatch

- name: Inject full dynamic version
run: python .hooks/sync_version.py --dev
Expand Down Expand Up @@ -57,14 +65,14 @@ jobs:

- name: Publish to Test PyPI
if: steps.version_check.outputs.exists != 'true'
uses: pypa/gh-action-pypi-publish@ab69e431e9c9f48a3310be0a56527c679f56e04d
uses: pypa/gh-action-pypi-publish@cef221092ed1bacb1cc03d23a2d87d1d172e277b # v1.14.0
with:
repository-url: https://test.pypi.org/legacy/
verbose: true

- name: Comment on PR
if: steps.version_check.outputs.exists != 'true'
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea
uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
env:
VERSION: ${{ env.VERSION }}
with:
Expand Down Expand Up @@ -133,27 +141,26 @@ jobs:
echo "success=false" >> $GITHUB_OUTPUT
exit 1

- name: Set up QEMU
uses: docker/setup-qemu-action@49b3bc8e6bdd4a60e6116a5414239cba5943d3cf

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@c47758b77c9736f4b2ef4073d4d51994fabfe349

- name: Login to Docker Hub with Organization Token
- name: Set up Docker publishing
if: steps.verify_package.outputs.success == 'true'
uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567
uses: ./.github/actions/setup-docker
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
dockerhub-username: ${{ secrets.DOCKERHUB_USERNAME }}
dockerhub-token: ${{ secrets.DOCKERHUB_TOKEN }}

- name: Build & Push Docker Preview
if: steps.verify_package.outputs.success == 'true'
uses: docker/build-push-action@4f58ea79222b3b9dc2c8bbdd6debcef730109a75
uses: docker/build-push-action@f9f3042f7e2789586610d6e8b85c8f03e5195baf # v7.2.0
env:
VERSION: ${{ env.VERSION }}
with:
push: true
platforms: linux/amd64,linux/arm64
# Preview images are for quick testing -- build amd64 only. arm64 via
# QEMU emulation is the slowest part of the job; release builds keep
# multi-arch. GHA layer cache speeds up repeated preview builds.
platforms: linux/amd64
cache-from: type=gha
cache-to: type=gha,mode=max
tags: |
socketdev/cli:pr-${{ github.event.pull_request.number }}
build-args: |
Expand Down
8 changes: 4 additions & 4 deletions .github/workflows/python-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false
- name: 🐍 setup python
uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: ${{ env.PYTHON_VERSION }}
- name: 🛠️ install deps
Expand Down Expand Up @@ -71,12 +71,12 @@ jobs:
runs-on: ubuntu-latest
timeout-minutes: 10
steps:
- uses: actions/checkout@eef61447b9ff4aafe5dcd4e0bbf5d482be7e7871
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
with:
fetch-depth: 1
persist-credentials: false
- name: 🐍 setup python
uses: actions/setup-python@f677139bbe7f9c59b41e40162b753c062f5d49a3
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: "3.10"
- name: 🚫 verify install is rejected on unsupported python
Expand Down
Loading