virtualenv: ambientes virtuais para desenvolvimento

O post de hoje não será tão estreitamente relacionado à dicas sobre código Python como foram os anteriores. Ele irá tratar sobre o ambiente usado para o desenvolvimento em sua máquina.

Para quem está envolvido no desenvolvimento de vários projetos em paralelo, é bastante comum que um projeto tenha dependências de bibliotecas diferentes das usadas pelos outros projetos.
Em um ambiente Ubuntu Linux, por exemplo, os módulos Python instalados no sistema são armazenados em /usr/lib/python2.7/dist-packages/ (para Python 2.7). Dessa forma, se tivermos desenvolvendo dois projetos diferentes, eles estarão compartilhando algumas bibliotecas. E se for necessário que o projeto A utilize a versão x de determinado módulo, enquanto que o projeto B deve utilizar a versão y do mesmo módulo? Como os dois projetos, A e B, utilizam os módulos instalados no mesmo local do disco, fica difícil satisfazer esse requisito.

Outra situação muito comum de acontecer é estarmos desenvolvendo ou testando uma aplicação em um ambiente sobre o qual não temos permissões para a instalação de pacotes no sistema. Sabendo que muita gente passa por situações parecidas, foi criado o virtualenv. Se tivermos o virtualenv à disposição, podemos criar um ambiente virtual em nossa pasta pessoal e instalar os pacotes necessários dentro desse ambiente, sem a necessidade de ter privilégios de super-usuário. Quando for necessário lidar com vários projetos ao mesmo tempo, podemos criar um ambiente virtual para cada projeto, ambos na mesma máquina.

Assim, o virtualenv é uma ferramenta que permite que criemos, com o perdão da redundância, ambientes virtuais isolados para projetos Python. Por exemplo, se tivermos dois projetos, A e B, podemos criar dois ambientes virtuais, um para cada um dos projetos. Poderíamos chamá-los de venvA e venvB, por exemplo. Quando criamos esses dois ambientes, é criado um diretório com o nome de cada ambiente, com o seguinte conteúdo cada um:

bin  include  lib  local

Dentro do diretório bin, são criados arquivos binários (executáveis) necessários em um ambiente de desenvolvimento Python:

$ ls bin/
activate          activate.fish     easy_install    get_env_details
pip-2.7           postdeactivate    predeactivate   activate.csh
activate_this.py  easy_install-2.7  pip             postactivate
preactivate       python

Perceba que temos, dentre os arquivos listados, o interpretador Python (python), além de outras ferramentas importantes como o pip, que pode ser usadoo como instalador de pacotes do virtualenv. Existem também arquivos que são relacionados ao próprio ambiente virtual. Assim, cada ambiente virtual terá seus próprios executáveis para interpretar seus programas e gerenciar seus pacotes. Além disso, é criado também um diretório lib/python2.7/site-packages/, onde serão armazenados os pacotes que você instalar para aquele ambiente. Ou seja, ambos os ambientes venvA e venvB possuirão seu próprio interpretador Python, bem como suas próprias bibliotecas de código. Assim, cada projeto poderá ter versões específicas de determinados pacotes, sem a ocorrência de conflitos entre versões.

Como usar o virtualenv?

O virtualenv pode ser instalado de várias formas. A forma mais comum é através do gerenciador de pacotes pip. Tendo o pip instalado, você pode instalar o virtualenv com o seguinte comando:

user@host:~/$ sudo pip install virtualenv

Tendo feito isso, agora podemos começar a criar os ambientes virtuais para projetos Python. Primeiramente, vamos criar um ambiente:

user@host:~/$ virtualenv NomeDoAmbiente

Após executado o comando acima, será criado, no diretório atual, um subdiretório chamado NomeDoAmbiente, contendo aquela mesma estrutura já comentada anteriormente. Após o ambiente ter sido criado, precisamos ativá-lo:

user@host:~/$ source ./NomeDoAmbiente/bin/activate
(NomeDoAmbiente)user@host:~/$

Você irá perceber que o prompt do seu shell é alterado após a execução do comando acima, sendo a partir daí, precedido pelo nome do ambiente virtual ativo entre parênteses (veja acima). Isso faz também com que sua variável de ambiente $PATH passe a apontar, em primeiro lugar, para a pasta bin de dentro do ambiente virtual, de forma que quando você chamar o interpretador Python pela linha de comando, o executável que será aberto será o interpretador que está instalado dentro do ambiente virtual atual, pois será o primeiro encontrado no $PATH.

Instalando pacotes dentro do ambiente virtual

Uma vez que ativamos o ambiente virtual que desejamos usar, podemos então instalar os pacotes que forem necessários para nosso projeto. Por exemplo, considere que estamos trabalhando em nosso ambiente (ativado anteriormente), chamado de NomeDoAmbiente, e desejamos instalar o pacote Django. Podemos utilizar o gerenciador de pacotes pip que está instalado dentro de nosso ambiente virtual NomeDoAmbiente:

(NomeDoAmbiente)user@host:~/$ pip install Django
Downloading/unpacking Django
    Downloading Django-1.4.1.tar.gz (7.7Mb): 7.7Mb downloaded
    Running setup.py egg_info for package Django
Installing collected packages: Django
    Running setup.py install for Django
Successfully installed Django
Cleaning up...

Agora, podemos abrir um shell Python dentro do ambiente NomeDoAmbiente recém criado, e testar se o Django está mesmo instalado:

(NomeDoAmbiente)user@host:~/$ python
Python 2.7.2+ (default, Jul 20 2012, 22:15:08) 
[GCC 4.6.1] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import django
>>> django.__file__
'/home/user/NomeDoAmbiente/local/lib/python2.7/site-packages/django/__init__.pyc'

Tudo certo, o Django está instalado corretamente dentro do ambiente NomeDoAmbiente.

Para sair do ambiente virtual ativo, utilize o comando deactivate.

Gerando lista de dependências do projeto

Lembra quando você envia um projeto pronto para o chefe e ele manda um email dizendo que o projeto não funciona? Muitas vezes, o problema é que o computador do chefe não possui instaladas as bibliotecas que o projeto necessita. Nessa situação, a dupla virtualenv + pip nos ajuda novamente.

Uma vez que estejamos utilizando ambientes virtuais para nossos projetos, e que estejamos instalando todos os pacotes necessários via pip, temos facilmente em mãos a lista de pacotes dos quais nosso projeto depende. Para obter essa lista, basta utilizar o comando freeze do pip:

(NomeDoAmbiente)user@host:~/$ pip freeze
Django==1.4.1
Werkzeug==0.8.3
argparse==1.2.1
distribute==0.6.24
django-bootstrap-toolkit==2.5.8
django-extensions==0.9
django-registration==0.8
wsgiref==0.1.2

Tal comando escreve na saída-padrão a lista de pacotes (bem como suas versões), de cada uma das dependências instaladas via pip no projeto ativo. De posse dessa lista, podemos agora facilmente enviar a lista de dependências para o nosso chefe, utilizando as informações fornecidas pelo pip freeze para garantir que a máquina do chefe irá satisfazer todas as dependências do nosso projeto. Primeiro, devemos armazenar em um arquivo as informações geradas pelo pip freeze:

(NomeDoAmbiente)user@host:~/$ pip freeze > requirements.txt

Após isso, podemos enviar o arquivo requirements.txt para o chefão e, usando o pip, ele poderá executar:

(NomeDoAmbiente)anotheruser@anotherhost:~/$ pip install -r requirements.txt

O comando acima irá instalar as versões especificadas dos pacotes listados no arquivo fornecido como entrada. Tendo instalado corretamente os pacotes listados, nosso projeto estará com todas as dependências satisfeitas no computador do chefe, e poderá ser executado sem problemas.

virtualenvwrapper

Existe outro projeto, chamado virtualenvwrapper, que é um wrapper sobre o virtualenv, e que provê uma série de facilidades para a manipulação de ambientes virtuais. Vale muito a pena dar uma conferida nele!

Utilizando o virtualenvwrapper, a ativação de um ambiente fica muito mais simples:

user@host:~/$ workon NomeDoAmbiente
(NomeDoAmbiente)user@host:~/$

Além disso, ele provê vários atalhos para facilitar a nossa vida, como o cdvirtualenv, que troca o diretório atual para o diretório do virtualenv ativo. Alguns outros aliases úteis:

  • cdsitepackages: troca o diretório atual para o diretório onde os pacotes Python do ambiente virtual ativo estão instalados.
  • lssitepackages: comando muito útil para listarmos os arquivos/diretórios presentes no diretório de instalação dos módulos do ambiente virtual ativo.
  • mkvirtualenv NOME: cria um ambiente virtual chamado NOME.
  • dentre outros 😉

virtualenv embutido no Python 3.3

A versão 3.3 do Python traz consigo a possibilidade de criarmos ambientes virtuais sem a necessidade de instalação do pacote virtualenv separadamente, ou seja, o virtualenv fará parte da distribuição oficial do Python. Mais informações podem ser encontradas na documentação oficial: http://docs.python.org/dev/library/venv.html.

Enfim…

O virtualenv é extremamente útil quando você está trabalhando com vários projetos ao mesmo tempo, ou em um ambiente sobre o qual você não tenha permissões de super-usuário. Mas fique atento, pois o virtualenv irá instalar uma versão de cada biblioteca e dos executáveis para cada um dos seus ambientes virtuais, o que irá consumir mais espaço em disco.

Anúncios

26 comentários sobre “virtualenv: ambientes virtuais para desenvolvimento

  1. Pingback: Acessando recursos na web com Python | Python Help
  2. Pingback: Criando um site com Django | Rafaela S. Sacconi
  3. Li diversos artigos a respeito do virtualenv e este, de fato, foi um dos mais diretos, completos e de fácil entendimento que encontrei. Parabéns!

  4. Pingback: Eclipse, PyDev, Virtualenv | Fernando Jr's Blog
  5. Muito bom!

    No teu texto, o “Enfim” conflita com esse trecho deste [0] artigo:

    “Packages installed here will not affect the global Python installation.
    Virtualenv does not create every file needed to get a whole new python environment
    It uses links to global environment files instead in order to save disk space end
    speed up your virtualenv.
    Therefore, there must already have an active python environment installed on your
    system.”

    [0] http://www.pythonforbeginners.com/basics/how-to-use-python-virtualenv/

    • Opa, ainda a tempo, consegui a informacao que eu precisava.
      Em todo o caso, compartilho com vcs caso alguém venha a ter a mesma dúvida que tive:

      ~blablabla/meuprojeto$ echo -e “\nsource activate.sh” >> ~/.bashrc
      ~blablabla/meuprojeto$ echo “workon meuprojeto” > .env

      Com isso, mesmo que vc feche o terminal e o reabra novamente o virtualenv sempre estará habilitado a partir desse projeto. Ex:

      host@name:~$ cd blablabla
      host@name:~/blablabla$ cd meuprojeto
      (meuprojeto)host@name:~/blablabla/meuprojeto$ cd xpto
      (meuprojeto)host@name:~/blablabla/meuprojeto/xpto$

      Agradeco a minha colega Tatiane pela ajuda! 🙂

  6. Pingback: Como usar o virtualenv para gerenciar as dependências duma aplicação Python? | CL-UAT
  7. Pingback: 2 – Instalação de Bottle | Meu blog pessoal
  8. Pingback: Como instalar pip no Ubuntu |
  9. Pingback: LEDS/MapaSocial | GITROOM
  10. Pingback: Configurando Virtualenvwrapper no Pyenv | Paulo Romano
  11. Bom dia!
    Primeiramente parabéns pela postagem, muito bem explicado.
    Me restou uma dúvida, eu estou em um ambiente Windows onde não tenho permissões de instalar nada, nem mesmo o python está instalado, eu consigo criar um ambiente virtual em outra maquina e utilizar nesse ambiente sem acessos?

    • Herbert, se há alguma de forma de fazer o que você precisa, eu a desconheço. Um workaround seria se logar remotamente em uma máquina que tem python instalado usando algum cliente ssh.

      À propósito, você não consegue instalar Python em sua pasta de usuário no Windows?

      Valdir.

  12. Pingback: Python: Ambientes Virtuais | Frederico Vieira
  13. Oi, Valdir, desde já, desejo-te um ótimo final de semana, seguinte estou apanhando muito na utilização do python e django, pois não estou conseguindo trabalhar com o virtualenv no windows, pois os curso que comprei é da treinaWeb e eles não explicação como se faz essa instalação, pois quando vou criar os templates o django não encontra a pasta, mesmo ela estando lá, estou utilizando o sublime text, fico agradecido se me retornar com uma solução, abraço!

Deixe um comentário

Preencha os seus dados abaixo ou clique em um ícone para log in:

Logotipo do WordPress.com

Você está comentando utilizando sua conta WordPress.com. Sair / Alterar )

Imagem do Twitter

Você está comentando utilizando sua conta Twitter. Sair / Alterar )

Foto do Facebook

Você está comentando utilizando sua conta Facebook. Sair / Alterar )

Foto do Google+

Você está comentando utilizando sua conta Google+. Sair / Alterar )

Conectando a %s