Introdução

Neste post explico como configurei o fluxo de deploy do site Hugo usando o Cloudflare Pages, com ambientes separados para staging e production.

O projeto usa:

  • Hugo com o tema PaperMod
  • config/_default/ para base comum
  • config/staging/ para staging
  • config/production/ para produção
  • Branches do Git para escolher o ambiente automaticamente

Por que usar staging no Cloudflare Pages

Staging é útil para:

  • validar conteúdo antes de publicar
  • testar layout e integrações em um domínio seguro
  • evitar deploys acidentais no site principal

No meu caso, o staging roda em https://staging.bortoloso.me/ e a produção em https://bortoloso.me/.

Até o momento da escrita deste post, ambos os ambientes ficam abertos, talvez eu bloqueie o staging no futuro, mas de momento ambos são visíveis.


Configuração do Hugo

O repositório separa as configurações por ambiente:

  • config/_default/hugo.toml: configuração comum
  • config/production/hugo.toml: produção
  • config/staging/hugo.toml: homologação

No arquivo config/production/hugo.toml está definido:

  • baseURL = "https://bortoloso.me/"
  • params.env = "production"
  • Google Analytics ativo

No arquivo config/staging/hugo.toml está definido:

  • baseURL = "https://staging.bortoloso.me/"
  • params.env = "staging"

O params.env é usado pelo tema para ativar metadados, Open Graph e analytics conforme o ambiente.


Build no Cloudflare Pages

O projeto usa um comando de build que verifica CF_PAGES_BRANCH e escolhe o ambiente Hugo correto.

git submodule update --init --recursive && echo "Branch=$CF_PAGES_BRANCH"; if [ "$CF_PAGES_BRANCH" = "main" ]; then echo "ENV=production"; hugo --environment production --gc --minify; elif [ "$CF_PAGES_BRANCH" = "staging" ]; then echo "ENV=staging"; hugo --environment staging --gc --minify; else echo "ERROR: unsupported branch '$CF_PAGES_BRANCH'"; exit 1; fi

Isso garante:

  • main > build de produção
  • staging > build de staging
  • outras branches > falha explícita

O git submodule update --init --recursive garante que o tema PaperMod seja carregado na versão travada pelo repositório, evitando mudanças inesperadas em builds automatizados.


Configuração de DNS e domínios customizados

O projeto usa domínios customizados em Cloudflare Pages para manter os dois ambientes separados.

No Pages:

  • main branch > domínio de produção bortoloso.me
  • staging branch > domínio de homologação staging.bortoloso.me

No DNS, os registros configurados são:

  • CNAME bortoloso.me > bortolog.pages.dev
  • CNAME www > bortolog.pages.dev
  • CNAME staging > staging.bortolog.pages.dev

Todos os registros podem ficar com proxy ativado.

É importante registrar explicitamente staging.bortoloso.me no projeto Cloudflare Pages. Caso contrário, o Pages pode aplicar o domínio principal ao ambiente de staging ou redirecionar para bortoloso.me.


Por que o domínio de staging precisa estar registrado

O Cloudflare Pages usa o domínio principal do projeto para o deploy quando um custom domain não está configurado corretamente.

Sem o domínio staging.bortoloso.me no Pages, o staging pode acabar:

  • redirecionando para bortoloso.me
  • aplicando um canonical host incorreto
  • quebrando a separação entre produção e homologação

A correção aplicada foi:

  1. adicionar staging.bortoloso.me no projeto Pages
  2. configurar CNAME staging > staging.bortolog.pages.dev
  3. manter main e staging como domínios distintos

Controle de indexação e SEO

O projeto já tem um partial que adiciona meta tags extras no <head>:

  • layouts/partials/extend_head.html

Esse partial contém uma condição baseada em ambiente:

{{ if eq hugo.Environment "staging" }}
<meta name="robots" content="noindex, nofollow, noarchive, nosnippet">
{{ end }}

Assim, apenas o site de staging ganha noindex, sem alterar o template principal.


Fluxo prático

  1. main é o branch de produção

    • build com hugo --environment production
    • usa config/production/hugo.toml
    • deploy em https://bortoloso.me/
  2. staging é o branch de homologação

    • build com hugo --environment staging
    • usa config/staging/hugo.toml
    • deploy em https://staging.bortoloso.me/
  3. branches de feature não são deployadas automaticamente

    • evita previews acidentais fora do fluxo esperado

Boas práticas aplicadas

  • separar claramente produção e staging
  • usar domínios customizados distintos no Cloudflare Pages
  • controlar indexação de staging via partial do Hugo
  • manter o tema PaperMod fixo com submodule sync, sem buscar mudanças automáticas no build
  • rejeitar builds de branches não suportadas

Conclusão

Com esse setup, o blog tem:

  • um ambiente de staging real e isolado em staging.bortoloso.me
  • um deploy de produção controlado em bortoloso.me
  • configuração de DNS e domínios customizados alinhados ao Pages
  • menor risco de indexação do staging ou de deploys acidentais

Esse fluxo mantém a operação previsível e facilita a validação antes de publicar qualquer alteração no site principal.

Existe uma grande chance de muito em breve eu não utilizar mais o staging, montei mais pela experiência de ver como ficaria o fluxo do que por necessidade real. Após o blog estar bem alinhado, creio que serão poucas as mudanças e necessidades de validação, posts irão direto para produção(se algum build quebrar, ele não sobe e a versão anterior se mantém ativa).