Skip to content
Latchkey

Publish to PyPI workflow (sunscrapers/djoser)

The Publish to PyPI workflow from sunscrapers/djoser, explained and optimized by Latchkey.

C

CI health: C - fair

Point runs-on at Latchkey and get caching, job timeouts, SHA-pinned actions, self-healing for flaky steps, and up to 58% lower cost, applied automatically.

Grade your own workflow free or run it on Latchkey →
Source: sunscrapers/djoser.github/workflows/publish_pypi.ymlLicense MITView source

What it does

This is the Publish to PyPI workflow from the sunscrapers/djoser repository, a real project running GitHub Actions. It is shown here with attribution under its MIT license.

Below, Latchkey shows a faster, safer version produced by its optimization engine.

The workflow

workflow (.yml)
name: Publish to PyPI

on:
  release:
    types:
      - released

jobs:
  publish:
    runs-on: ubuntu-latest
    environment:
      name: pypi
      url: https://pypi.org/p/djoser/

    steps:
      - name: Checkout code
        uses: actions/checkout@v4
        with:
          fetch-depth: 0
          fetch-tags: true

      - name: Set up Python
        uses: actions/setup-python@v5
        with:
          python-version: "3.9"

      - name: Install Poetry
        uses: abatilo/actions-poetry@v4
        with:
          poetry-version: "1.8.4"

      - name: Get release tag
        id: get_tag
        run: |
          TAG=$(git describe --tags)
          echo "TAG=$TAG" >> $GITHUB_ENV
          VERSION=${TAG#v}  # Remove "v" prefix if present
          echo "VERSION=$VERSION" >> $GITHUB_ENV

      - name: Verify package version matches tag
        run: |
          PACKAGE_VERSION=$(poetry version -s)
          if [ "$PACKAGE_VERSION" != "${{ env.VERSION }}" ]; then
            echo "Package version ($PACKAGE_VERSION) does not match tag version (${{ env.VERSION }})"
            exit 1
          fi

      - name: Update package version from tag
        run: |
          echo "Updating version to ${{ env.VERSION }}"
          poetry version ${{ env.VERSION }}

      - name: Compile translations
        run: |
          echo "Compiling translation files..."
          poetry run pybabel compile --domain django --directory djoser/locale -f

      - name: Build package
        run: |
          echo "Building package..."
          poetry build
          echo "Package contents:"
          ls -l dist/

      # Test PyPI deployment for pre-releases
      - name: Configure Test PyPI
        if: github.event.release.prerelease
        run: |
          echo "Configuring Test PyPI..."
          poetry config repositories.testpypi https://test.pypi.org/legacy/
          poetry config pypi-token.testpypi ${{ secrets.TEST_PYPI_TOKEN }}

      - name: Publish to Test PyPI
        if: github.event.release.prerelease
        run: |
          echo "Publishing to Test PyPI..."
          poetry publish --no-interaction -r testpypi
          echo "Package published to Test PyPI successfully"

      # Production PyPI deployment
      - name: Configure PyPI
        if: "!github.event.release.prerelease"
        run: |
          echo "Configuring PyPI..."
          poetry config pypi-token.pypi ${{ secrets.PYPI_TOKEN }}

      - name: Publish to PyPI
        if: "!github.event.release.prerelease"
        run: |
          echo "Publishing to PyPI..."
          poetry publish --no-interaction
          echo "Package published to PyPI successfully"

      - name: Verify publish
        run: |
          echo "Published version ${{ env.VERSION }} successfully"
          echo "Package is available at https://pypi.org/p/djoser/${{ env.VERSION }}/"

The same workflow, on Latchkey

Estimated ~20% faster on cache hits, plus fewer wasted runs and a safer supply chain. Added and changed lines are highlighted.

name: Publish to PyPI
 
on:
  release:
    types:
      - released
 
jobs:
  publish:
    timeout-minutes: 30
    runs-on: latchkey-small
    environment:
      name: pypi
      url: https://pypi.org/p/djoser/
 
    steps:
      - name: Checkout code
        uses: actions/checkout@v4
        with:
          fetch-depth: 0
          fetch-tags: true
 
      - name: Set up Python
        uses: actions/setup-python@v5
        with:
          cache: 'pip'
          python-version: "3.9"
 
      - name: Install Poetry
        uses: abatilo/actions-poetry@v4
        with:
          poetry-version: "1.8.4"
 
      - name: Get release tag
        id: get_tag
        run: |
          TAG=$(git describe --tags)
          echo "TAG=$TAG" >> $GITHUB_ENV
          VERSION=${TAG#v}  # Remove "v" prefix if present
          echo "VERSION=$VERSION" >> $GITHUB_ENV
 
      - name: Verify package version matches tag
        run: |
          PACKAGE_VERSION=$(poetry version -s)
          if [ "$PACKAGE_VERSION" != "${{ env.VERSION }}" ]; then
            echo "Package version ($PACKAGE_VERSION) does not match tag version (${{ env.VERSION }})"
            exit 1
          fi
 
      - name: Update package version from tag
        run: |
          echo "Updating version to ${{ env.VERSION }}"
          poetry version ${{ env.VERSION }}
 
      - name: Compile translations
        run: |
          echo "Compiling translation files..."
          poetry run pybabel compile --domain django --directory djoser/locale -f
 
      - name: Build package
        run: |
          echo "Building package..."
          poetry build
          echo "Package contents:"
          ls -l dist/
 
      # Test PyPI deployment for pre-releases
      - name: Configure Test PyPI
        if: github.event.release.prerelease
        run: |
          echo "Configuring Test PyPI..."
          poetry config repositories.testpypi https://test.pypi.org/legacy/
          poetry config pypi-token.testpypi ${{ secrets.TEST_PYPI_TOKEN }}
 
      - name: Publish to Test PyPI
        if: github.event.release.prerelease
        run: |
          echo "Publishing to Test PyPI..."
          poetry publish --no-interaction -r testpypi
          echo "Package published to Test PyPI successfully"
 
      # Production PyPI deployment
      - name: Configure PyPI
        if: "!github.event.release.prerelease"
        run: |
          echo "Configuring PyPI..."
          poetry config pypi-token.pypi ${{ secrets.PYPI_TOKEN }}
 
      - name: Publish to PyPI
        if: "!github.event.release.prerelease"
        run: |
          echo "Publishing to PyPI..."
          poetry publish --no-interaction
          echo "Package published to PyPI successfully"
 
      - name: Verify publish
        run: |
          echo "Published version ${{ env.VERSION }} successfully"
          echo "Package is available at https://pypi.org/p/djoser/${{ env.VERSION }}/"
 

What changed

1 third-party action is referenced by a movable tag. Pin it to the commit SHA (Latchkey resolves and applies this automatically) so a repointed tag cannot change what runs.

This workflow runs 1 job per trigger. On Latchkey the same minutes cost up to 58% less than GitHub-hosted, with zero queue time.

Actions used in this workflow