De acordo com Martin Fowler, entrega contínua é uma prática de desenvolvimento na qual o software é construído de um certo modo em que pode ser colocado em produção a qualquer momento.
Basicamente, você deve ser capaz de colocar uma versão em produção somente com um clique; a versão desejada vai passar por várias etapas de testes em um pipeline de implantação, colocando a mesma em produção caso passe com sucesso em todas as etapas.
O deploy contínuo é um passo à frente. Cada integração de alterações no repositório de código fonte dispara um novo processo de deploy automaticamente, resultando em frequentes entregas de código em produção.
Para exemplificar, vamos criar um pipeline de implantação que é disparado a cada push na branch master de nossa aplicação Laravel Somador hospedada no GitHub. Para executar os passos do deploy, e por fim publicar na Umbler, vamos utlizar o Snap CI , uma ferramenta de integração contínua SaaS criada pela Thoughtworks que se integra naturalmente com o GitHub.
Nosso pipeline de implantação vai consistir em quatro etapas:
- 1. Testes de unidade
- 2. Deploy em ambiente de homologação
- 3. Testes de integração
- 4. Deploy em produção
Para poder implementar estas etapas, nós criamos dois sites compartilhados PHP na Umbler, cada um com seu respectivo banco de dados: rc.phpnaumbler.com.br, que servirá como ambiente de homologação, e o phpnaumbler.com.br, que será nosso ambiente de produção. Como não temos domínios registrados, os sites serão acessados através dos endereços temporários que a própria Umbler fornece (meusite-com-br.umbler.net).
O Laravel utiliza o arquivo .env para guardar as configurações de ambiente. Como você pode notar no nosso exemplo, as configurações de banco de dados e o nome do ambiente no arquivo versionado estão com variáveis. Estas serão substituidas por valores configurados no próprio Snap CI para cada etapa através do script alterar_variaveis.sh.
Nossa aplicação foi criada utlizando o laragon.
Testes Unitários
A nossa primeira etapa é a de testes unitários, porque esse processo é o mais rápido para se executar e de se conseguir um feedback. Testaremos a classe Somador, que contém a regra de negócio de nossa aplicação e utilizaremos a classe BancoFake porque não queremos que nossos testes acessem o banco da dados (a integração com o banco de dados será testada mais à frente). Note que a classe recebe uma interface no construtor (Injeção de dependência), possibilitando assim a utilização de um dublê de teste. Para rodar os testes do PHP, o Snap CI nos disponibiliza o PHPUnit, bastando invocá-lo na linha de comando apontando para phpunit.xml que já vem configurado no laravel:
$ phpunit --configuration phpunit.xml
Deploy em Homologação
Se os nossos testes unitários passarem, nosso pipeline prossegue para a próxima etapa. Nesta etapa precisamos configurar as variáveis de ambiente no Snap CI para que o nosso script, antes de publicar, altere o .env para os valores desejados. Para configurar o Git na Umbler é só seguir estes passos e adicionar a chave privada do SSH gerada no Snap. Com tudo configurado, podemos publicar na Umbler nossa versão de homologação, e, após publicar, rodamos outro script para arrumar a estrutura, pois a estrutura do laravel mantém a maioria dos arquivos fora da pasta public.
$ ../alterar_variaveis.sh
$ git remote add rcumbler ssh://rc.phpnaumbler.com.br@rc-phpnaumbler-com-br.umbler.net:9922/~/git/rc-phpnaumbler-com-br.git
$ git add .
$ git commit -m "deploy homologacao"
$ git push rcumbler master --force
$ ssh rc.phpnaumbler.com.br@rc.phpnaumbler-com-br.umbler.net -p 9922 'bash -s' < corrigir_caminho_laravel.sh
Testes de Integração
Com o nosso site publicado no ambiente de homologação, podemos aplicar os nossos testes de integração, que vão testar nosso sistema de ponta a ponta. Para realizar estes testes vamos utilizar o PhantomJS, que está disponível na linha de comando, assim como PHPUnit, bastando executá-lo com o nosso arquivo javascript que contém os testes. O PhantomJS é um automatizador de browser que fornece uma API javascript para realizar os passos. O nosso teste consistirá em digitar valores na inferface, clicar no botão do formulário e verificar o resultado na próxima página:
$ phantomjs tests/teste_integracao.js
Deploy em Produção
Por fim, podemos publicar em ambiente de produção, com uma garantia de riscos reduzidos. O processo é igual ao da segunda etapa, somente alterando as variáveis de ambiente configuradas no Snap e os nossos endereços de SSH para os dados de produção:
$ ../alterar_variaveis.sh
$ git remote add rcumbler ssh://phpnaumbler.com.br@rc-phpnaumbler-com-br.umbler.net:9922/~/git/rc-phpnaumbler-com-br.git
$ git add .
$ git commit -m "deploy produção"
$ git push rcumbler master --force
$ ssh phpnaumbler.com.br@phpnaumbler-com-br.umbler.net -p 9922 'bash -s' < corrigir_caminho_laravel.sh
E depois?
Outras práticas e ferramentas podem ser adotadas, variando muito da necessidade e gosto dos times:
Notificações: O próprio Snap se integra com algumas ferramentas, como por exemplo o Slack. Você poderia disparar notificações quando certos eventos, como por exemplo falhas no processo, ocorrerem.
Testes de integração: é interessante limpar o banco de dados, ou mesmo garantir um certo conjunto de dados, antes de rodar testes que causam alterações, garantindo assim uma maior integridade na execução.
Testes manuais: obviamente, testes manuais não são possíveis. Para isso a Entrega Contínua é mais adequada. Na prática, você poderia utilizar somente os três primeiros passos, deixando o deploy em produção para outro momento.