Como Configurar Zig no GitHub Actions (CI/CD)

Como Configurar Zig no GitHub Actions (CI/CD)

Automatizar a compilação, os testes e o deploy do seu projeto Zig com GitHub Actions é uma prática essencial para manter a qualidade do código. Este guia mostra como configurar pipelines de integração contínua (CI) e entrega contínua (CD) para projetos Zig, desde configurações simples até workflows avançados com matrix de versões, cache e cross-compilation.

Se você ainda está montando seu projeto, consulte o guia Criar seu Primeiro Projeto Zig. Para outras formas de automação com containers, veja o guia de Zig com Docker.


Workflow Básico: Build e Testes

Comece com um workflow simples que compila e testa seu projeto a cada push ou pull request. Crie o arquivo .github/workflows/ci.yml na raiz do seu repositório:

name: CI

on:
  push:
    branches: [main, master]
  pull_request:
    branches: [main, master]

jobs:
  build-and-test:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig
        uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"

      - name: Verificar versão do Zig
        run: zig version

      - name: Compilar o projeto
        run: zig build

      - name: Executar testes
        run: zig build test

      - name: Compilar em modo Release
        run: zig build -Doptimize=ReleaseSafe

Entendendo o Workflow

  • on — Define os gatilhos. O workflow roda em pushes e pull requests para as branches main ou master.
  • actions/checkout@v4 — Clona o repositório no runner do GitHub Actions.
  • mlugg/setup-zig@v1 — Action da comunidade que instala o Zig automaticamente no runner. Suporta versões específicas e a versão master.
  • zig build — Compila o projeto usando o sistema de build do Zig.
  • zig build test — Executa todos os testes definidos no build.zig.

Matrix de Versões e Plataformas

Para projetos que precisam suportar múltiplas versões do Zig ou rodar em diferentes sistemas operacionais, use uma matrix strategy:

name: CI Matrix

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

jobs:
  test:
    strategy:
      fail-fast: false
      matrix:
        os: [ubuntu-latest, macos-latest, windows-latest]
        zig-version: ["0.13.0", "0.14.0", "master"]

    runs-on: ${{ matrix.os }}

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig ${{ matrix.zig-version }}
        uses: mlugg/setup-zig@v1
        with:
          version: ${{ matrix.zig-version }}

      - name: Exibir informações do ambiente
        run: |
          zig version
          zig env

      - name: Compilar
        run: zig build

      - name: Executar testes
        run: zig build test

      - name: Build Release
        run: zig build -Doptimize=ReleaseSafe

Detalhes da Matrix

  • fail-fast: false — Se uma combinação falhar, as outras continuam executando. Isso é útil para identificar exatamente quais versões ou plataformas têm problemas.
  • matrix.os — Testa em Linux, macOS e Windows simultaneamente.
  • matrix.zig-version — Testa contra múltiplas versões do Zig, incluindo a nightly (master).

A matrix gera 9 jobs (3 sistemas x 3 versões), todos executados em paralelo. Para mais informações sobre como gerenciar múltiplas versões localmente, consulte o guia Gerenciar Versões do Zig.


Cache para Builds Mais Rápidos

O Zig mantém um cache de compilação que pode ser persistido entre execuções do workflow para acelerar builds subsequentes:

name: CI com Cache

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig
        uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"

      - name: Cache do Zig
        uses: actions/cache@v4
        with:
          path: |
            ~/.cache/zig
            zig-cache
            .zig-cache
          key: zig-cache-${{ runner.os }}-${{ hashFiles('build.zig', 'build.zig.zon') }}
          restore-keys: |
            zig-cache-${{ runner.os }}-

      - name: Compilar e testar
        run: |
          zig build
          zig build test

O cache reduz o tempo de compilação significativamente em projetos com muitas dependências ou código extenso.


Cross-Compilation no CI

Uma das maiores forças do Zig é a cross-compilation integrada. Configure o CI para gerar binários para múltiplas plataformas a partir de um único runner:

name: Cross Build

on:
  push:
    tags:
      - "v*"

jobs:
  cross-compile:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        target:
          - x86_64-linux-gnu
          - aarch64-linux-gnu
          - x86_64-linux-musl
          - aarch64-linux-musl
          - x86_64-macos-none
          - aarch64-macos-none
          - x86_64-windows-gnu

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig
        uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"

      - name: Compilar para ${{ matrix.target }}
        run: zig build -Doptimize=ReleaseSafe -Dtarget=${{ matrix.target }}

      - name: Upload do artefato
        uses: actions/upload-artifact@v4
        with:
          name: build-${{ matrix.target }}
          path: zig-out/bin/

Este workflow gera binários para Linux (x86_64 e ARM64, com glibc e musl), macOS (Intel e Apple Silicon) e Windows, tudo a partir de um runner Ubuntu.


Release Automatizado

Combine cross-compilation com criação automática de releases no GitHub:

name: Release

on:
  push:
    tags:
      - "v*"

permissions:
  contents: write

jobs:
  build:
    runs-on: ubuntu-latest

    strategy:
      matrix:
        include:
          - target: x86_64-linux-musl
            artifact: meu-app-linux-x86_64
          - target: aarch64-linux-musl
            artifact: meu-app-linux-aarch64
          - target: x86_64-macos-none
            artifact: meu-app-macos-x86_64
          - target: aarch64-macos-none
            artifact: meu-app-macos-aarch64
          - target: x86_64-windows-gnu
            artifact: meu-app-windows-x86_64.exe

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig
        uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"

      - name: Compilar para ${{ matrix.target }}
        run: zig build -Doptimize=ReleaseSafe -Dtarget=${{ matrix.target }}

      - name: Renomear artefato
        run: |
          cp zig-out/bin/meu-app* ${{ matrix.artifact }} || true

      - name: Upload do artefato
        uses: actions/upload-artifact@v4
        with:
          name: ${{ matrix.artifact }}
          path: ${{ matrix.artifact }}

  release:
    needs: build
    runs-on: ubuntu-latest

    steps:
      - name: Download de todos os artefatos
        uses: actions/download-artifact@v4
        with:
          path: artefatos
          merge-multiple: true

      - name: Criar Release no GitHub
        uses: softprops/action-gh-release@v2
        with:
          files: artefatos/*
          generate_release_notes: true

Para criar uma release, basta criar uma tag versionada:

git tag v1.0.0
git push origin v1.0.0

O workflow compilará o projeto para todas as plataformas e publicará os binários automaticamente na página de Releases do GitHub.


Verificação de Formatação e Linting

O Zig possui um formatador integrado (zig fmt). Adicione uma verificação de formatação ao CI para manter a consistência do código:

name: Lint

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

jobs:
  format-check:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout do código
        uses: actions/checkout@v4

      - name: Instalar Zig
        uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"

      - name: Verificar formatação
        run: |
          zig fmt --check src/
          zig fmt --check build.zig

O comando zig fmt --check retorna um código de erro se algum arquivo não estiver formatado corretamente, fazendo o job falhar. Isso incentiva a equipe a rodar zig fmt localmente antes de enviar código.


Workflow Completo de Produção

Aqui está um workflow abrangente que combina todas as boas práticas para um projeto Zig profissional:

name: Pipeline Completo

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

concurrency:
  group: ${{ github.workflow }}-${{ github.ref }}
  cancel-in-progress: true

jobs:
  # Job 1: Verificação de formatação
  formato:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"
      - name: Verificar formatação
        run: zig fmt --check src/ build.zig

  # Job 2: Testes em múltiplas plataformas
  testes:
    needs: formato
    strategy:
      fail-fast: false
      matrix:
        os: [ubuntu-latest, macos-latest, windows-latest]
    runs-on: ${{ matrix.os }}
    steps:
      - uses: actions/checkout@v4
      - uses: mlugg/setup-zig@v1
        with:
          version: "0.14.0"
      - name: Cache do Zig
        uses: actions/cache@v4
        with:
          path: |
            ~/.cache/zig
            .zig-cache
          key: zig-${{ runner.os }}-${{ hashFiles('build.zig', 'build.zig.zon') }}
      - name: Executar testes
        run: zig build test
      - name: Build Debug
        run: zig build
      - name: Build Release
        run: zig build -Doptimize=ReleaseSafe

  # Job 3: Compatibilidade com versão nightly
  nightly:
    needs: formato
    runs-on: ubuntu-latest
    continue-on-error: true
    steps:
      - uses: actions/checkout@v4
      - uses: mlugg/setup-zig@v1
        with:
          version: "master"
      - name: Build e testes (nightly)
        run: |
          zig build || echo "Build falhou na nightly"
          zig build test || echo "Testes falharam na nightly"

Pontos Importantes

  • concurrency — Cancela execuções anteriores do mesmo workflow se um novo push for feito, economizando minutos de CI.
  • needs: formato — Os testes só executam se a verificação de formatação passar.
  • continue-on-error: true — O job nightly pode falhar sem bloquear o pipeline, servindo como alerta antecipado de incompatibilidades futuras.

Usando Zig com Docker no CI

Se seu projeto usa Docker, combine o Zig com a action de Docker para builds em containers:

jobs:
  docker-build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Build da imagem Docker
        run: docker build -t meu-app:${{ github.sha }} .

      - name: Executar testes no container
        run: docker run --rm meu-app:${{ github.sha }} zig build test

Para configurações mais completas com Docker, consulte o guia Usar Zig com Docker.


Problemas Comuns

Workflow falha com “zig: command not found”

Verifique se a action mlugg/setup-zig está configurada antes dos passos que usam o Zig. O step de instalação deve vir antes de qualquer comando zig.

Testes passam localmente mas falham no CI

Diferenças comuns entre o ambiente local e o CI:

  • Sistema operacional diferente — Use a matrix para testar em múltiplas plataformas.
  • Versão do Zig diferente — Fixe a versão na action para garantir consistência. Verifique sua versão local com zig version.
  • Dependências do sistema ausentes — Se seu projeto usa FFI ou liga com bibliotecas C, instale-as no runner com apt-get install.

Build lento no CI

  • Use o cache do Zig conforme descrito na seção de cache.
  • Considere runners maiores (GitHub oferece runners com mais CPU e RAM para planos pagos).
  • Evite compilar em modo Debug no CI se apenas o Release for necessário.

Timeout no GitHub Actions

O limite padrão é 360 minutos, mas builds Zig grandes podem ser lentos. Ajuste o timeout por job:

jobs:
  build:
    runs-on: ubuntu-latest
    timeout-minutes: 30
    steps:
      # ...

Para mais soluções, visite nossa página de erros comuns.


Próximos Passos

Com o CI/CD configurado para seu projeto Zig:

  1. Domine o build systemGuia completo do Zig Build System para configurar builds avançados, dependências e steps customizados
  2. Crie ou aprimore seu projetoPrimeiro projeto Zig
  3. Use Docker para builds reprodutíveisZig com Docker
  4. Gerencie versões localmenteGerenciar versões do Zig
  5. Configure seu editorVS Code ou Neovim
  6. Aprenda a linguagemIntrodução ao Zig
  7. Veja exemplos práticosReceitas

Continue aprendendo Zig

Explore mais tutoriais e artigos em português para dominar a linguagem Zig.