quarta-feira, 25 de novembro de 2009

remove-temps - Refactoring script para apagar arquivos temporários

Adicionei no projeto Refactoring-scripts um novo script: o remove-temps. Ele apenas busca recursivamente em um diretório por arquivos temporários e os elimina. Como é útil rodar antes de comitar, adicionei a opção -g, ou --git, que executa o comando "git rm" para todos os arquivos temporários, sendo que para utilizar esta opção, deve-se estar na diretório root do projeto e os arquivos ainda devem existir.

[ ]'s

segunda-feira, 23 de novembro de 2009

afterFormat - script pós formatação para Ubuntu Karmic Koala

Para melhorar nossas vidas nas aulas, alguns amigos e eu tivemos que formatar os PC's das bancadas de aula. Como em nossas bancadas utilizamos Linux, mais precisamente o Ubuntu, fiz um script em shell para automatizar o processo de configuração das máquinas e instalação dos softwares necessários.

Como também tenho que formatar minha máquina e alguns amigos disseram que também irão formatar as suas, e todos iremos instalar o Ubuntu Karmic Koala, fiz uma adaptação do script das bancadas para uma versão que baixe tudo da Internet, instalando automaticamente diversos softwares básicos que sempre são necessários após uma formatação.

Criei um projeto no github para o script afterFormat.sh. Na imagem abaixo está a interface dos script na qual você pode escolher o que quer instalar ou não.

screenshot do afterFormat

Dê uma olhada no README para mais informações sobre os softwares que afterFormat instala, como executá-lo e como fazer a configuração básica do StarDict.

[ ]'s

domingo, 15 de novembro de 2009

Refactoring scripts em shell

Mês passado estava trabalhando em um sistema que estou desenvolvendo em Rails com amigos da faculdade quando um deles viu que tinha feito uma merda. Ele tinha criado um modelo "viagem" com o scaffolding mas esqueceu de colocar o plural correto no inflections. Assim o scaffolding criou vários arquivos que continham no nome as palavras "viagems" ou "Viagems" e vários arquivos que tinham em seu conteúdo essas mesmas palavras. Contudo ele já havia programado bastante coisa depois disso e ficaria ruim retornar ao commit anterior no git.

Ele já ia alterar tudo manualmente quando falei: Calma aí! Vou criar um script para isso!

Era uma boa oportunidade, já que estou aprendendo a programar em shell. Em pouco tempo criei dois scripts básicos: um para modificar os nomes dos arquivos e outro para modificar o conteúdo. Logo pensei em montar um conjunto de scripts para refactoring já que uso o combo Gedit + Terminal para programar. Daí essa semana comecei a ler o livro Shell Script Professional do Aurélio Marinho, que é muito bom livro por sinal, e dei uma profissionalizada nos scripts para colocar em prática meus aprendizados.

O resultado está no projeto Refactoring-scripts github. Por enquanto são dois:
  • find-replace.sh - Busca em um arquivo, ou recursivamente em todos os arquivos de um diretório, por uma palavra e a substitui por outra.
  • change-file-name.sh - Busca recursivamente em um diretório por arquivos que contenham uma palavra em seu nome e a substitui por outra.
A pretensão é, além criar outros scripts, cirar um fork para um plugin de refactoring em python para o gedit. Mas isso é coisa para as férias de fim de ano. =)

sábado, 12 de setembro de 2009

Erro ao rodar rake db:migrate

Se ao rodar o comando rake db:migrate você está tendo o seguinte erro:

rake aborted!
undefined method 'reenable' for [environment]>:Rake::Task

Pode estar tendo o mesmo problema que eu tive.

Quando estava montando um ambiente de desenvolvimento para Ruby on Rails em minha máquina, provavelmente dei uma noobada e instalei o rake com o apt-get ou ele entrou como dependência de alguma coisa e eu não parcebi.

Enfim, estava instalado no sistema como pacote Debian a versão 0.8.1 do rake e também como gem a versão 0.8.7

Para resolver isso, bastou desinstalar o rake do sistema com o comando:

sudo apt-get remove rake
Após ter feito isso, o rake rodou normalmente. Para testar rode:

rake --version
Se após isso ele indicar que o pacote não está instalado ou algo do tipo, dê uma olhada nesse post: Chamando aplicativos instalados com o ruby gem com um comando no terminal

[ ]'s

sexta-feira, 11 de setembro de 2009

Chamando aplicativos instalados com o ruby gem com um comando no terminal

Primeiramente um conselho: Tudo que puder instalar para desenvolvimento Ruby via ruby gem instale (melhor ainda se usar o rvm). Evite instalar qualquer coisa no sistema via apt-get. Isso pode gerar uma série de conflitos e, além disso, geralmente o repositório do synaptic demora um tempo para ser atualizado. Assim, instalando as gems você terá um sistema mais limpo e os frameworks/aplicativos mais atualizados, além da facilidade de manutenção.

Para que você possa chamar os aplicativos instalados via ruby gem (gem install "aplicativo"), você pode adicionar o path dos binários destes aplicativos rodando os seguinte comandos no terminal (neste caso utiliznado o ruby 1.8):

sudo su
echo "export PATH=\"\$PATH:/var/lib/gems/1.8/bin\"" >> /etc/bash.bashrc
exit

Isso fará com a linha export PATH="$PATH:/var/lib/gems/1.8/bin" seja adicionada ao aquivo /etc/bash.bashrc. Assim, toda vez que for iniciado o bash, sua variável ambiente $PATH receberá também o caminho dos binários instalados via ruby gem que ficam contidos na pasta /var/lib/gems/1.8/bin.

Contudo, na versão 9.10 do Ubuntu (se você utiliza outra versão, procure saber), o comando sudo foi compilado com a opção --with-secure-path. Assim, mudanças realizadas na variável não surtem efeito quando utilizado o comando sudo. Para contornar isso faça:

echo "alias sudo='sudo env PATH=\$PATH'" >> ~/.bashrc
Desta forma a variável $PATH será a mesma usando o comando sudo ou não.

Com isso, se eu instalar o rails assim:

sudo gem install rails
e poderei chamar o rails no terminal simplesmente rodando:

rails
As mudanças apenas surtirão efeito ao reiniciar seu terminal ou fazendo:

source /etc/bash.bashrc
source ~/.bashrc

[ ]'s

sábado, 11 de abril de 2009

Faça download de pacotes .deb e de todas suas dependências diretas e indiretas

Algumas vezes podemos ter a necessidades de instalar um pacote sem termos acesso a internet para baixar suas dependências (sei que é praticamente impossível, mas pode acontecer). Também podemos querer congelar uma versão de algum projeto que estamos desenvolvendo, sem que mudanças em pacotes de terceiros dos quais dependemos nos criem problemas. Podemos ainda querer criar um CD completo de instalação de nossas solução, para que a instalação execute tudo localmente, sem baixar pacotes da internet. Em fim, este script (projeto no github) serve para qualquer situação que se deseja fazer o download de um pacote .deb e todas suas dependências diretas e indiretas.

Pesquisando, achei a função apt-cache depends. Porém ela lista apenas as dependências diretas do pacote. Mas precisava de uma função que listasse todas as dependências, inclusive as dependências das dependências. Foi quando encontrei o blog do Thiago Ribeiro. Lá encontrei a dica do apt-rdepends, que lista recursivamente todas as dependências de um dado pacote, e a ideia geral que usei para construir o meu script.

Como o apt-rdepends não vem instalado no Ubuntu, instale-o rodando no terminal:

sudo apt-get install apt-rdepends
Em seguida, rode o apt-rdepends para ver como é a sua saída. Assim, terá uma noção melhor de como funciona o script. Rode por exemplo:

apt-rdepends python
Serão listadas todas as dependências e as dependências das dependências, necessárias para a instalação do pacote python.deb, recursivamente.

O script na verdade é composto por dois scripts - um em shell script e o outro em python - e sua ideia básica de funcionamento é a seguinte:
  • O script downloadDependencies.sh baixa o pacote informado e salva um arquivo depends.txt contendo a saída do atp-rdepends para este pacote. Em seguida é invocado o script downloadDependencies.py que, através de expressões regulares, trata o arquivo depends.txt gerando um shell script depends.sh que irá fazer o download de todas as dependências do pacote. Por existirem pacotes que são dependência de mais de um pacote, provavelmente este arquivo conterá entradas repetidas para baixar um mesmo pacote mais de uma vez. Porém esse não eh um problema, já que o apititude download não baixa pacotes já existentes na pasta.
  • O script salva o pacote e suas dependências em uma pasta com o seu nome e apaga todos os arquivos gerados para o seu uso. O único arquivo que não é apagado é o depends.txt que contém a arvore de dependências e vai servir para saber qual a ordem dos pacotes a serem instalados.
Como documentei bem (em inglês) o script, acredito que não há necessidade de mais detalhes sobre a implementação. Os códigos estão comentados e criei um readme também.

Uma segunda etapa seria criar um script para instalar ordenadamente os pacotes. Mas isso fica para um outro post, quando tiver um outro feriado para ter um tempo livre para me divertir. =P