Introdução

O Jenkins é uma das ferramentas de automação mais populares e poderosas, amplamente utilizada para integrar e implantar projetos de software de forma contínua. Embora seja possível iniciar rapidamente o Jenkins usando um simples comando Docker, essa configuração básica é semelhante a um “Hello World” em programação: útil para começar, mas insuficiente para ambientes de produção.
Neste post, vamos além do básico. O objetivo aqui é guiá-lo com algumas técnicas para uma arquitetura robusta e escalável para o Jenkins, utilizando Docker e Docker Compose. Vamos explorar conceitos fundamentais, como o isolamento de máquinas, e configurar um ambiente mais próximo da realidade. Ao final, você terá uma estrutura sólida, pronta para ser adaptada e expandida conforme suas próprias necessidades.
Se você está pronto para sair do básico e construir um ambiente de CI/CD profissional, siga adiante!
Pré-Requisitos
Antes de mergulharmos nos detalhes técnicos, é essencial garantir que alguns pré-requisitos estejam atendidos:
- Linux (No meu caso, uso Windows como SO principal, entáo utilizo um virtualizador como WSL, Virtualbox, VmWare, etc…)
- Docker
Conceitos principais
Com os pré-requisitos definidos, podemos agora explorar os conceitos principais que orientarão a configuração do Jenkins.
Isolamento
A primeira boa prática de utilização do Jenkins é não realizar tudo em uma mesma máquina. Tanto por uma questão de segurança quanto de escalabilidade, é recomendado o uso de, no mínimo, duas máquinas.
A primeira máquina é a que chamamos normalmente de controller. Ela é a máquina principal, sendo responsável principalmente pela interface, configurações e controle de execução de jobs.
As demais máquinas são chamadas de nodes. Estas máquinas são responsáveis pela execução de todos os jobs.
Configuração das máquinas
Tanto o controller quanto os nodes precisam ser configurados dentro de um sistema operacional.
Instalar os pré-requisitos, criar pastas, e definir permissões de usuário são alguns exemplos. Além disso, vamos aproveitar para realizar, neste momento, algumas configurações do Jenkins que só surtirão efeito na inicialização ou reinicialização.
Usaremos as imagens do Jenkins e o Docker Compose para esta fase.
Configurações do Jenkins
Com o Jenkins em execução, precisamos realizar as configurações para o ambiente funcionar:
- Credenciais de acesso
- Configuração da comunicação entre o controller e o node
Estas configurações não serão feitas manualmente. Utilizaremos o plugin Configuration as Code para automatizar este processo.
Estrutura básica
Entendidos os conceitos que serão aplicados, é hora de começar a definir a estrutura básica do projeto.
Esta é a estrutura básica. Este modelo será utilizado em posts futuros.
.
└── demo/
├── casc/ #Configuração do Jenkins as code
│ └── *.yaml
├── plugins/
│ └── plugins.txt #Lista de plugins
├── scripts/
│ └── *.groovy #Scripts de inicialização do jenkins
├── ssh #Chave pública e privada
├── docker-compose.yaml
├── Dockerfile
├── start.sh
└── stop.shDockerfile
Dentro dessa estrutura, o Dockerfile desempenha um papel central. Vamos examiná-lo em detalhes:
|
|
Um resumo do conteúdo do Dockerfile:
- linhas 3 a 8: Criação do diretório
.sshe a cópia da chave privada armazenada na pastasshdo projeto. - linha 10: Cópia dos scripts
Groovyarmazenada na pastascriptsdo projeto. - linhas 12 e 13: Cópia da lista de plugins e a instalação dos plugins na imagem.
- linhas 15 a 17: Criação da pasta do plugin
JCasCe cópia dos arquivos de configuração da pastacasc(Configuration as Code) do projeto. - linha 20: Define a variável de ambiente
CASC_JENKINS_CONFIGpara configurar a pasta padrão onde o Jenkins irá recuperar estes arquivos. - linha 21: Configuração da variável de ambiente
JAVA_OPTSinformando que não é necessária a execução do Wizard de instalação.
docker-compose.yaml
Depois de configurar o Dockerfile, precisamos orquestrar os serviços com o docker-compose.yaml:
|
|
Não há muito segredo no docker-compose. O serviço jenkins executa a imagem oficial do Jenkins, com as principais portas mapeadas, e o serviço ssh-agent que será o node de execução dos pipelines.
Na linha 19 configuramos a variável de ambiente JENKINS_AGENT_SSH_PUBKEY para informar a chave pública gerada.
plugins.txt
Agora que os serviços estão configurados, vamos definir os plugins essenciais no arquivo plugins.txt:
|
|
executors.groovy
Seguindo as recomendações no início do artigo, é necessário ajustar os executores do Jenkins, o que faremos no script executors.groovy:
|
|
ssh-agent.yaml
Por fim, precisamos configurar a comunicação segura entre o controller e os nodes, usando o ssh-agent.yaml:
|
|
Aqui, configuramos o jenkins pelo plugin configuration as code:
- Linhas 1 a 12: Criação de uma credencial do jenkins do tipo
SSH Username with private keycom a chave privada. - Linhas 13 a 25: Criamos a configuração do node
Start up
Com todas as configurações em ordem, é hora de colocar tudo em prática e iniciar o ambiente. Vamos utilizar o script start.sh para automatizar a execução do docker-compose (especialmente útil para execuções repetidas):
|
|
Em resumo, o script start.sh:
- Executa o script
stop.shpara garantir a limpeza de arquivos criados em execuções anteriores. - Gera as chaves públicas e privadas
- Cria a variável de ambiente
JENKINS_AGENT_SSH_PUButilizada nodocker-compose.yaml - Executa o
docker-compose
E o script stop.sh:
- Deleta as chaves da pasta
ssh - Para o serviço
- Remove os containers
- Remove os volumes criados
Execução
|
|

Concluões
O exemplo deste artigo está disponível aqui. Está muito longe de um ambiente produtivo de execução, mas para serve como uma base para meus testes quando preciso de um ambiente local de execução.
Até a próxima!
Referências
https://github.com/jenkinsci/docker/blob/master/README.md#install-plugins https://github.com/jenkinsci/docker-ssh-agent?tab=readme-ov-file#running-with-the-ssh-build-agents-plugin https://www.jenkins.io/doc/book/security/controller-isolation/ https://plugins.jenkins.io/configuration-as-code/
Foto de Chilli Charlie na Unsplash