414 lines
13 KiB
YAML
414 lines
13 KiB
YAML
name: CI
|
|
|
|
on:
|
|
push:
|
|
branches:
|
|
- '**'
|
|
- '!dependabot/**'
|
|
- '!*-patch-*'
|
|
pull_request:
|
|
merge_group:
|
|
workflow_dispatch:
|
|
|
|
permissions:
|
|
contents: read
|
|
|
|
concurrency:
|
|
group: ${{ github.workflow }}-${{ github.ref }}
|
|
cancel-in-progress: true
|
|
|
|
jobs:
|
|
lint:
|
|
uses: mhils/workflows/.github/workflows/python-tox.yml@v12
|
|
with:
|
|
cmd: tox -e lint
|
|
|
|
filename-matching:
|
|
uses: mhils/workflows/.github/workflows/python-tox.yml@v12
|
|
with:
|
|
cmd: tox -e filename_matching
|
|
|
|
mypy:
|
|
uses: mhils/workflows/.github/workflows/python-tox.yml@v12
|
|
with:
|
|
cmd: tox -e mypy
|
|
|
|
individual-coverage:
|
|
uses: mhils/workflows/.github/workflows/python-tox.yml@v12
|
|
with:
|
|
cmd: tox -e individual_coverage
|
|
|
|
test:
|
|
strategy:
|
|
fail-fast: false
|
|
matrix:
|
|
include:
|
|
- os: ubuntu-latest
|
|
py: "3.13"
|
|
- os: windows-latest
|
|
py: "3.13"
|
|
- os: macos-latest
|
|
py: "3.13"
|
|
- os: ubuntu-latest
|
|
py: "3.12"
|
|
- os: ubuntu-latest
|
|
py: "3.11"
|
|
- os: ubuntu-latest
|
|
py: "3.10"
|
|
runs-on: ${{ matrix.os }}
|
|
steps:
|
|
- run: printenv
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
fetch-depth: 0
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version: ${{ matrix.py }}
|
|
- run: pip install tox
|
|
- run: tox -e py
|
|
if: matrix.os != 'ubuntu-latest'
|
|
- name: Run tox -e py (without internet)
|
|
run: |
|
|
# install dependencies (requires internet connectivity)
|
|
tox -e py --notest
|
|
# run tests with loopback only. We need to sudo for unshare, which means we need an absolute path for tox.
|
|
sudo unshare --net -- sh -c "ip link set lo up; $(which tox) -e py"
|
|
if: matrix.os == 'ubuntu-latest'
|
|
- uses: codecov/codecov-action@v5
|
|
with:
|
|
token: ${{ secrets.CODECOV_TOKEN }}
|
|
files: ./coverage.xml
|
|
|
|
test-old-dependencies:
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
fetch-depth: 0
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
- run: pip install tox-uv
|
|
- run: tox -e old-dependencies
|
|
|
|
build:
|
|
strategy:
|
|
fail-fast: false
|
|
matrix:
|
|
include:
|
|
- image: macos-14
|
|
platform: macos-arm64
|
|
- image: macos-13
|
|
platform: macos-x86_64
|
|
- image: windows-2019
|
|
platform: windows
|
|
- image: ubuntu-20.04 # Oldest available version so we get oldest glibc possible.
|
|
platform: linux
|
|
runs-on: ${{ matrix.image }}
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
fetch-depth: 0
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
- run: pip install .[dev] # pyinstaller 5.9 does not like pyproject.toml + editable installs.
|
|
|
|
- if: startsWith(matrix.platform, 'macos') && github.repository == 'mitmproxy/mitmproxy'
|
|
&& (startsWith(github.ref, 'refs/heads/') || startsWith(github.ref, 'refs/tags/'))
|
|
id: keychain
|
|
uses: apple-actions/import-codesign-certs@63fff01cd422d4b7b855d40ca1e9d34d2de9427d
|
|
with:
|
|
keychain: ${{ runner.temp }}/temp
|
|
p12-file-base64: ${{ secrets.APPLE_CERTIFICATE }}
|
|
p12-password: ${{ secrets.APPLE_CERTIFICATE_PASSWORD }}
|
|
- if: startsWith(matrix.platform, 'macos') && github.repository == 'mitmproxy/mitmproxy'
|
|
&& (startsWith(github.ref, 'refs/heads/') || startsWith(github.ref, 'refs/tags/'))
|
|
run: |
|
|
python -u release/build.py macos-app \
|
|
--keychain "${{ runner.temp }}/temp.keychain" \
|
|
--team-id "S8XHQB96PW" \
|
|
--apple-id "${{ secrets.APPLE_ID }}" \
|
|
--password "${{ secrets.APPLE_APP_PASSWORD }}"
|
|
|
|
# Linux
|
|
- if: matrix.platform == 'linux'
|
|
run: python -u release/build.py standalone-binaries wheel
|
|
|
|
# Windows
|
|
- if: matrix.platform == 'windows'
|
|
run: python -u release/build.py standalone-binaries
|
|
|
|
- uses: actions/upload-artifact@v4
|
|
with:
|
|
name: binaries.${{ matrix.platform }}
|
|
path: release/dist
|
|
|
|
build-wheel:
|
|
uses: mhils/workflows/.github/workflows/python-build.yml@v12
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
artifact: binaries.wheel
|
|
|
|
build-windows-installer:
|
|
runs-on: windows-latest
|
|
if: github.repository == 'mitmproxy/mitmproxy' && (
|
|
github.ref == 'refs/heads/main' ||
|
|
github.ref == 'refs/heads/citest' ||
|
|
startsWith(github.ref, 'refs/tags/')
|
|
)
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
fetch-depth: 0
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
|
|
- run: pip install .[dev] # pyinstaller 5.9 does not like pyproject.toml + editable installs.
|
|
- run: python -u release/build.py installbuilder-installer msix-installer
|
|
env:
|
|
CI_BUILD_KEY: ${{ secrets.CI_BUILD_KEY }}
|
|
|
|
- uses: actions/upload-artifact@v4
|
|
with:
|
|
name: binaries.windows-installer
|
|
path: release/dist
|
|
|
|
test-web-ui:
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
- uses: actions/setup-node@v4
|
|
with:
|
|
node-version-file: .github/node-version.txt
|
|
- name: Cache Node.js modules
|
|
uses: actions/cache@v4
|
|
with:
|
|
# npm cache files are stored in `~/.npm` on Linux/macOS
|
|
path: ~/.npm
|
|
key: ${{ runner.OS }}-node-${{ hashFiles('**/package-lock.json') }}
|
|
restore-keys: |
|
|
${{ runner.OS }}-node-
|
|
${{ runner.OS }}-
|
|
- working-directory: ./web
|
|
run: npm ci
|
|
- working-directory: ./web
|
|
run: npm test
|
|
- uses: codecov/codecov-action@v5
|
|
with:
|
|
token: ${{ secrets.CODECOV_TOKEN }}
|
|
files: ./web/coverage/coverage-final.json
|
|
|
|
test-docker:
|
|
runs-on: ubuntu-latest
|
|
needs: build-wheel
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
- uses: actions/download-artifact@v4
|
|
with:
|
|
name: binaries.wheel
|
|
path: release/docker
|
|
- name: Build container
|
|
run: docker build --tag localtesting release/docker
|
|
- name: Test container
|
|
run: docker run --rm -v $PWD/release:/release localtesting mitmdump -s /release/selftest.py
|
|
|
|
docs:
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
- run: |
|
|
wget -q https://github.com/gohugoio/hugo/releases/download/v0.139.3/hugo_extended_0.139.3_linux-amd64.deb
|
|
echo "3e58800d1fee57269208d07d104ae1a6ab886615344099f2dca0c6ad5279bc11 hugo_extended_0.139.3_linux-amd64.deb" | sha256sum -c
|
|
sudo dpkg -i hugo*.deb
|
|
- run: pip install -e .[dev]
|
|
- run: ./docs/build.py
|
|
- uses: actions/upload-artifact@v4
|
|
with:
|
|
name: docs
|
|
path: docs/public
|
|
# For releases, also build the archive version of the docs.
|
|
- run: ./docs/build.py
|
|
env:
|
|
DOCS_ARCHIVE: true
|
|
- if: startsWith(github.ref, 'refs/tags/')
|
|
uses: actions/upload-artifact@v4
|
|
with:
|
|
name: docs-archive
|
|
path: docs/public
|
|
|
|
check:
|
|
if: always()
|
|
needs:
|
|
- lint
|
|
- filename-matching
|
|
- mypy
|
|
- individual-coverage
|
|
- test
|
|
- test-docker
|
|
- test-old-dependencies
|
|
- test-web-ui
|
|
- build
|
|
- build-wheel
|
|
- build-windows-installer
|
|
- docs
|
|
uses: mhils/workflows/.github/workflows/alls-green.yml@v12
|
|
with:
|
|
jobs: ${{ toJSON(needs) }}
|
|
allowed-skips: build-windows-installer
|
|
|
|
# Separate from everything else because slow.
|
|
deploy-docker:
|
|
if: github.repository == 'mitmproxy/mitmproxy' && (
|
|
github.ref == 'refs/heads/main' ||
|
|
github.ref == 'refs/heads/citest' ||
|
|
startsWith(github.ref, 'refs/tags/')
|
|
)
|
|
permissions:
|
|
id-token: write
|
|
attestations: write
|
|
packages: write
|
|
environment: deploy-docker
|
|
needs: check
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
- uses: actions/download-artifact@v4
|
|
with:
|
|
name: binaries.wheel
|
|
path: release/docker
|
|
- uses: docker/setup-qemu-action@49b3bc8e6bdd4a60e6116a5414239cba5943d3cf # v3.2.0
|
|
- uses: docker/setup-buildx-action@c47758b77c9736f4b2ef4073d4d51994fabfe349 # v1.6.0
|
|
|
|
- name: Login to Docker Hub
|
|
uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567 # v3.3.0
|
|
with:
|
|
username: mitmbot
|
|
password: ${{ secrets.DOCKER_PASSWORD }}
|
|
- name: Login to GitHub Container Registry
|
|
uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567 # v3.3.0
|
|
with:
|
|
registry: ghcr.io
|
|
username: ${{ github.repository_owner }}
|
|
password: ${{ secrets.GITHUB_TOKEN }}
|
|
|
|
- name: Docker meta
|
|
id: meta
|
|
uses: docker/metadata-action@369eb591f429131d6889c46b94e711f089e6ca96
|
|
env:
|
|
DOCKER_METADATA_ANNOTATIONS_LEVELS: index
|
|
with:
|
|
images: |
|
|
mitmproxy/mitmproxy
|
|
ghcr.io/mitmproxy/mitmproxy
|
|
tags: |
|
|
type=semver,pattern={{version}}
|
|
type=semver,pattern={{major}}.{{minor}}
|
|
type=semver,pattern={{major}}
|
|
type=raw,value=dev,enable=${{ github.ref == 'refs/heads/main' }}
|
|
type=raw,value=citest,enable=${{ github.ref == 'refs/heads/citest' }}
|
|
|
|
- name: Build and push
|
|
id: push
|
|
uses: docker/build-push-action@48aba3b46d1b1fec4febb7c5d0c644b249a11355 # v6.10.0
|
|
with:
|
|
context: release/docker
|
|
platforms: linux/amd64,linux/arm64
|
|
push: true
|
|
provenance: false
|
|
tags: ${{ steps.meta.outputs.tags }}
|
|
labels: ${{ steps.meta.outputs.labels }}
|
|
annotations: ${{ steps.meta.outputs.annotations }}
|
|
- uses: actions/attest-build-provenance@v1
|
|
with:
|
|
subject-name: ghcr.io/${{ github.repository }}
|
|
subject-digest: ${{ steps.push.outputs.digest }}
|
|
|
|
deploy:
|
|
# This action has access to our AWS keys, so we are extra careful here.
|
|
# In particular, we don't blindly `pip install` anything to minimize the risk of supply chain attacks.
|
|
if: github.repository == 'mitmproxy/mitmproxy' && (startsWith(github.ref, 'refs/heads/') || startsWith(github.ref, 'refs/tags/'))
|
|
environment: ${{ (github.ref == 'refs/heads/citest' || startsWith(github.ref, 'refs/tags/')) && 'deploy-release' || 'deploy-snapshot' }}
|
|
needs: check
|
|
runs-on: ubuntu-latest
|
|
permissions:
|
|
id-token: write
|
|
attestations: write
|
|
env:
|
|
# PyPI and MSFT keys are only available for the deploy-release environment
|
|
# The AWS access key for snapshots is scoped to branches/* as well.
|
|
TWINE_USERNAME: __token__
|
|
TWINE_PASSWORD: ${{ secrets.TWINE_PASSWORD }}
|
|
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
|
|
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
|
|
AWS_DEFAULT_REGION: us-west-2
|
|
MSFT_APP_ID: 9NWNDLQMNZD7
|
|
MSFT_TENANT_ID: ${{ secrets.MSFT_TENANT_ID }}
|
|
MSFT_CLIENT_ID: ${{ secrets.MSFT_CLIENT_ID }}
|
|
MSFT_CLIENT_SECRET: ${{ secrets.MSFT_CLIENT_SECRET }}
|
|
R2_ACCOUNT_ID: ${{ secrets.R2_ACCOUNT_ID }}
|
|
R2_ACCESS_KEY_ID: ${{ secrets.R2_ACCESS_KEY_ID }}
|
|
R2_SECRET_ACCESS_KEY: ${{ secrets.R2_SECRET_ACCESS_KEY }}
|
|
steps:
|
|
- uses: actions/checkout@v4
|
|
with:
|
|
persist-credentials: false
|
|
- uses: actions/setup-python@v5
|
|
with:
|
|
python-version-file: .github/python-version.txt
|
|
- run: sudo apt-get update
|
|
- run: sudo apt-get install -y awscli
|
|
- if: startsWith(github.ref, 'refs/tags/')
|
|
run: sudo apt-get install -y twine
|
|
|
|
- uses: actions/download-artifact@v4
|
|
with:
|
|
name: docs
|
|
path: docs/public
|
|
- if: startsWith(github.ref, 'refs/tags/')
|
|
uses: actions/download-artifact@v4
|
|
with:
|
|
name: docs-archive
|
|
path: docs/archive
|
|
- uses: actions/download-artifact@v4
|
|
with:
|
|
pattern: binaries.*
|
|
merge-multiple: true
|
|
path: release/dist
|
|
- id: provenance
|
|
uses: actions/attest-build-provenance@v1
|
|
with:
|
|
subject-path: 'release/dist/*'
|
|
- run: |
|
|
REF=${{ github.ref_name }}
|
|
mv ${{ steps.provenance.outputs.bundle-path }} release/dist/mitmproxy-${REF#v}.sigstore
|
|
- run: ls docs/public
|
|
- run: ls release/dist
|
|
|
|
- run: ./release/deploy.py
|
|
|
|
- name: Deploy to Microsoft Store (test flight)
|
|
if: github.ref == 'refs/heads/citest'
|
|
run: ./release/deploy-microsoft-store.py release/dist/*.msix
|
|
env:
|
|
MSFT_APP_FLIGHT: 174ca570-8cae-4444-9858-c07293f1f13a
|
|
- name: Deploy to Microsoft Store
|
|
if: startsWith(github.ref, 'refs/tags/')
|
|
run: ./release/deploy-microsoft-store.py release/dist/*.msix
|