Ruby, Capistrano e administração remota

Por Lucas Cavalcanti em 06/08/07

Algumas vezes nos deparamos com a seguinte situação:

Temos uns 15 computadores em rede e precisamos executar um mesmo comando em cada um deles, como por exemplo instalar a JavaVM…

Uma primeira solução seria logar como root máquina por máquina, e executar o comando em todas… Muito ruim…

Agora, se você souber um pouquinho de bash script, em cinco minutos conseguirá fazer um script que loga via ssh em todas as máquinas e executa o comando nelas. Mas ainda tem o problema de você ter que digitar o password para cada máquina, e de ter que assistir a execução do comando, caso ele precise de alguma confirmação, ou algo do tipo…

Felizmente existe uma ferramenta muito útil que pode nos ajudar nessa tarefa entediante. E ela se chama Capistrano (www.capify.org). Com os mesmos 5 min você consegue escrever um script que execute o comando que você quer, digite as confirmações pra você nos lugares necessários, e você só precisará digitar a senha uma única vez!

O Capistrano requer que você o use em sistemas compatíveis com bash, e que exista um mesmo usuário em todas as máquinas que tenha uma única senha.

Para o script funcionar você precisa, com o capistrano instalado corretamente:

  • Definir o usuário a que você vai se conectar nos micros:

    set :user = "root" #pode ser qualquer usuário

  • Definir os ips dos micros aos quais você irá se conectar:

    role :micros = "192.168.0.10", "192.168.0.11"

  • Ou se for uma faixa de IPs:

    role :micros = *("192.168.0.10" .. "192.168.0.25").to_a

  • E, finalmente, definir a tarefa que você quer executar, ou seja, o(s) comando(s). Para isso temos que passar os roles a que queremos nos conectar (os micros)
    task :instalaJava, :roles => :micros do
      run "apt-get install java-virtual-machine"
    end
  • Pronto! O comando será executado em todas as máquinas!
    Ou melhor, quase pronto…
    Você sabe que o apt-get pode pedir confirmação para continuar instalando o programa pedido…
    Você pode automatizar isso usando um recurso muito útil do capistrano:

    run "apt-get install java-virtual-machine" do |channel, stream, data|
      #channel é um objeto que nos permite enviar dados para o comando
      #stream identifica se a saída do comando foi a padrão (:out) ou a de erros(:err)
      #data é uma string com a saída do comando
      if data =~ /Do you want to proceed/ #se na saída do comando tiver essa frase
        channel.send_data "y\\n" #manda pro comando um y e um enter
      end
      puts data #pra saída do comando aparecer na tela
    end

    Agora sim, o script vai fazer o que a gente queria: executar o comando e confirmar!
    O comando run vai ser executado em todos os micros paralelamente, e o bloco de código entre do e end do run vai ser executado toda vez que o comando “apt-get” jogar algum texto na tela ou na saída de erros.

    Pra executar o script basta salvar o código que escrevemos como “capfile” e chamar pela linha de comando cap + o nome da nossa task:

    $ cap instalaJava

    O comando irá mostrar qual task está sendo executado e pedirá uma vez a senha. E é só ficar assistindo, ou ir fazer algo mais produtivo.

    Nesse arquivo capfile você pode usar toda a sintaxe e as funcionalidades de um rakefile e, consequentemente, código em ruby. Então dá pra fazer coisas bem legais, como chamar tasks dentro de tasks, popular um role dinamicamente, executar uma tarefa antes e/ou depois da task chamada, enfim, muitas coisas…

    Você só terá que se preocupar com uma coisa: se um dos micros que estiver no role da task não estiver acessível pela rede, ou se acontecer um erro fatal qualquer, o capistrano não irá executar a task em nenhum dos micros.

    É isso. Divirta-se!

5 Comments »

  1. Eu nunca usei, mas já ouvi falar bastante do Smartfrog. Eu tenho a impressão que é 100% Java (não interage direto com o shell) então não daria para instalar o JRE usando ele, mas parece útil para deploy e teste de apps. Vocês já deram uma olhada?

    Comment by Rafael de F. Ferreira — August 6, 2007 @ 5:46 pm

  2. Valeu a dica Rafael. Pior que procuramos pra caramba algo em java. Vamos ver se ele é comparavel ao capistrano, e se nao é muito burocratico.

    Comment by Paulo Silveira — August 7, 2007 @ 12:21 pm

  3. Ótima dica, quem nunca passou por essa situação? Agora com essa ferramenta tudo fica mais fácil.

    Comment by Tiago Albineli Motta — August 7, 2007 @ 2:22 pm

  4. [...] Ainda com o Ruby, uma ótima dica de ferramenta escrita em Ruby, com a intenção de ser uma ferramenta de deploy para aplicações em Ruby, mas que no final se tornou um automatizador de tarefas é o Capistrano, mais detalhes e exemplos neste post do blog da Caelum. [...]

    Pingback by Random Tips 2 - Java, Ruby, Propaganda, Dicas, Yoga e tudo o que você precisava como desculpa para parar uns minutos de trabalhar :D — August 13, 2007 @ 3:17 pm

  5. Gostei bastante desse post, só que tenho uma dúvida.
    Eu vi que quando o run é executado ele utiliza o sh -c, existe a possibilidade dele não utilizar o sh -c e utilizar apenas o que eu coloquei no run??

    Obrigado.

    Comment by Marcio — September 3, 2008 @ 6:17 am

RSS feed for comments on this post. TrackBack URL

Leave a comment