Integração contínua sincrona com Rails/Rake

English version here

Bom, integração contínua acho que todos concordam que é uma necessidade em qualquer projeto de software, mas a integração contínua assíncrona utilizada normalmente tem alguns problemas, como por exemplo:

  • O código mesmo não passando nos testes é comitado
  • Os testes só serão executados algum tempo depois pelo servidor de integração, e só no final disto é que o desenvolvedor ficara sabendo se ocorreu algum problema de integração com o código que ele ja não esta mais trabalhando
  • O desenvolvedor provavelmente ja esta no meio de outra tarefa quando receber o e-mail dizendo que ocorreu algum problema com a tarefa anterior

Eu não estou dizendo que não é interessante existir um servidor de integração, é interessante para que todos os envolvidos no projeto tenham sempre acesso aos relatórios e a última versão do sistema compilado, mas não acho que deva ser dele a tarefa de integrar o sistema.

Ou seja, o que antigamente era o servidor de integração, agora passa a ser apenas um servidor de builds, e gerador de relatórios sobre o código fonte e progresso do projeto.

O ideal é que o desenvolvedor, durante o processo de commit, seja obrigado a executar todos os testes, e este commit só ser realmente executado se todos os testes passarem.

Claro que isto pode ser melhorado, adicionando ainda algumas restrições, por exemplo, exigir uma cobertura de testes mínima, mas no meu caso, eu desenvolvi esta task do Rake para um projeto em que estou trabalhando sozinho, e estou utilizando o GIT para controle de versões (escreverei um post sobre o GIT ainda esta semana se der tempo), e estou utilizando integração sincrona também em alguns projetos com Java, em outra oportunidade escrevo sobre o processo com Java.

Estou adotando esta prática de integração sincrona para todos os novos projetos da minha empresa e dos clientes que aceitam a idéia.

Mas voltando ao assunto, é bastante fácil implementar isto em um projeto Rails, basta seguir estes passos:

1 - criar um arquivo de nome ‘git.rake’ dentro do diretório lib/tasks com o seguinte conteúdo:

namespace :git do
  desc "Update every thing before the tests"
  task :update do
    puts "Lets update it all, but we are using GIT so we already have the latest source for this repo"
  end
  desc "Run all tests, if all are OK, then commit every thing to the git local repository"
  task :commit => [:update, :test] do
    puts "No test failures, now we can commit it all"
    exec 'git commit -a'
  end
end

Como podem ver esta task do Rake é bem simples, e com certeza isto vai aumentar muito a qualidade do projeto!

2 - sempre ao final de uma tarefa, em vez de executar o comando “git commit -a”, executar o comando: “rake git:update”

Só isto, a partir de agora você esta utilizando integração continua sincrona :D

Claro que esta task do Rake pode ser melhorada ainda, pode ser configurado por exemplo um pull de um repositório central, ou um update de um subversion ou qualquer coisa do gênero, mas acho que ja serve como exemplo para quem quiser começar a utilizar integração sincrona.

Se todos os testes passarem, o GIT vai abrir o VIM para que o desenvolvedor edite a mensagem de commit, depois da mensagem editada o código alterado é comitado sem problemas e sem medo de quebrar o próximo build com tudo integrado.

E vocês, o qu acham deste processo de integração continua? preferem sincrona ou assincrona? por que?

Só para lembrar: Estão abertas as incrições para o curso de Java Server Faces da Tech Office

Se você gostou deste post, lembre-se de assinar o RSS feed do blog, para ser notificado de novos posts!

9 comments so far

  1. […] Versão em portugues aqui I think that everyone agrees that continuous integrationis a need for any and every software project, but the asynchronous integration largely used has some problems, like: […]

  2. Wilerson October 17, 2007 9:27 am

    Achei a idéia bem legal, mas que tal combinar as duas coisas? Por exemplo, a integração feita na máquina do desenvolvedor poderia ter uma cobertura de testes menor que a do servidor de integração (afinal, às vezes rodar todos os testes pode ser demorado).

    Além disso, dessa forma tem-se uma maior segurança de que o desenvolvedor commitou tudo que é necessário para os testes passarem, pois se ele não o fizer, os testes passarão na máquina do desenvolvedor, mas não no servidor de integração.

  3. AkitaOnRails October 17, 2007 12:15 pm

    O Vinicius da ImproveIT acha a mesma coisa. Eu particularmente me sinto dividido. Por mais que a suite de testes do Rails rode rápido, eu faço micro-commits o tempo todo, para mim esse é todo o sentido de se ter um repositório: poder fazer commits o tempo todo.

    Se toda vez que eu precisar fazer um commit de uma linha, a suite inteira rodar, o que vai acontecer é o esperado: vou parar de fazer commits mais do que uma vez ao dia. Mas aí vem o problema: uma das vantagens de se ter um repositório é pode voltar atrás se mudar de idéia. E no começo do desenvolvimento isso acontece com frequencia.

    Preciso um jeito um pouco mais hibrido: usar um sistema distribuido como GIT ajudaria exatamente nisso: commits locais deveriam ser baratos e rapidos. Dentro do proprio ambiente de desenvolvedor tudo funciona. Portanto se eu quiser fazer 20 commits em 1 hora, posso fazer.

    Mas quando for integrar com o repositório global, ai sim poderia rodar os testes, no merge ao servidor. Nunca testei dessa maneira. Em equipes muito pequenas (como a que estou agora), eu preciso deixar Autotest rodando, fazer um update primeiro - daí o Autotest só vai rodar o que mudou - e depois fazer o commit. Isso só funciona em equipes pequenas porque todos tem que fazer o mesmo ritual todas as vezes em vez disso estar de maneira obrigada num trigger de commit por exemplo.

  4. Urubatan October 17, 2007 10:58 pm

    Akita, uma solução seria integrar mais com o git e usar o “git status” para saber quais arquivos foram alterados antes de executar os testes …
    Outra que eu estava pensando seria executar apenas os testes unitários …
    mas ambas tem um problema grave, que é, tu não detectar se aquela alteração quebrou alguma outra coisa …

    Utilizando o GIT ainda teria uma terceira opção, que acho mais indicada, que seria comitar sem executar os testes no repositório local, mas obrigar a execução de todos os testes antes de integrar com um repositório remoto (repositorio central ou de qualquer outro colaborador)

    O que você acha destas abordagens?

  5. Felipe Giotto October 22, 2007 4:58 pm

    Olá, Urubatan!

    Li o seu post e achei interessante a idéia de integração síncrona com Rails + GIT e decidi portar a sua rake task para quem utiliza repositórios Subversion!

    A task pode ser acessada neste endereço:
    http://www.inovare.net/noticias/3

    Todos que tiverem interesse podem utilizar, modificar ou sugerir melhorias!!

    Um abraço!

    Felipe Giotto
    Inovare Tecnologia

  6. AC de Souza October 24, 2007 3:28 pm

    Urubatan,

    Você ficou de: “(escreverei um post sobre o GIT ainda esta semana se der tempo)”.
    Não encare como uma cobrança :)
    É que você usa Linux, e o Git tem suas implicâncias com este SO. Por isso, imaginei que este projeto do Google Code, Git on MSys, te adiantaria.

    [],
    AC

    P.S.: Atualmente estou testando o Bazaar, que é suportado pelo pessoal da Canonical. Além disso ele tem um “bom relacionamento” com o Subversion, que uso no trabalho.
    Se tiver alguma coisa que o desmereça, vai me poupar um bom trabalho… :)

  7. Urubatan October 24, 2007 3:39 pm

    O git atualmente acho que só funciona em linux/*nix, esta implementação com o MSys é um port dele pra windows que funciona legal, mas roda dentro de um sandbox, não curti muito :D
    o git também se entende muito bem com o SVN :D
    ja comecei a escrever o post sobre o GIT mas não me animei a terminar ele ainda :D
    Quero ver se tenho tempo em algum momento para testar o Bazaar :D

  8. […] Recentemente foram escritos dois posts muito bons sobre o assunto. Você pode conferí-los no blog da ImproveIT e do Urubatan. […]

  9. AC de Souza October 25, 2007 10:43 am

    “[…]Quero ver se tenho tempo em algum momento para testar o Bazaar […]”

    Escrevi dois textos sobre o Bazaar, se te interessar.
    Um guia de consulta rápida: http://beyondclick.wordpress.com/2007/10/24/tutorial-do-bazaar/
    Uma breve apresentação sobre a ferramenta: http://beyondclick.wordpress.com/2007/10/24/sistema-de-controle-de-versao-distribuido-bazaar/

    [],
    AC

    P.S.: Eu compreendo que estou sendo muito OFF-TOPIC, mas achei menos inconveniente do que te mandar um email.
    Sinta-se à vontade para apagar este comentário, é como se o blog fosse seu… ;-)

Leave a comment

Please be polite and on topic. Your e-mail will never be published.