Série API em Flask - Parte 2 - Organizando as dependências e requerimentos
Hoje, vamos organizar e estruturar toda a aplicação assim como instalar os pacotes de desenvolvimento para a nossa API.
Para entendimento, segue os capítulos que serão abordados.
Capítulo 1: Introdução, configuração e Hello World
Capítulo 2: Organizando as dependências e requerimentos Estamos aqui
Capítulo 3: Configurando o pytest e nosso primeiro teste
Capítulo 4: Configurando o Makefile
Capítulo 5: Adicionando o MongoDB
Capítulo 6: Criando e testando o modelo de usuários
Capítulo 7: Criando usuários
Capítulo 8: Listando usuários
Capítulo 9: Buscando usuários
Capítulo 10: Editando um usuário
Capítulo 11: Deletando um usuário
Capítulo 12: Autênticação por JWT
Capítulo 13: Criando um container Docker
Capítulo 14: Arquivos de configuração para Deploy na Digital Ocean
Capítulo 15: Automatizando o processo de deploy com Fabric
Capítulo 16: CI e CD com Jenkins, Python, Flask e Fabric
Capítulo 17: Utilizando o RabbitMQ com Flask e Sendgrid para enviar e-mails de boas vindas e ativar a conta do usuário
O repositório com todo o código fonte esta aqui. Os capítulos estão em branches
.
Pacotes
Nos tempos atuais existe um gerenciador de pacotes como parte da configuração da aplicação. No capítulo 1 - Introdução, configuração e Hello World vimos o comando pip
responsável por instalar estes pacotes como o flask, flask-restful, python-dotenv
com suas respectivas versões.
Para termos uma visão geral do que está instalado em nosso ambiente executamos o comando pip freeze
.
Nota: Lembrando que o virtualenv deve estar ativo. O virtualenvwrapper deve estar instalado e configurado. Logo execute o comando workon flask-api-users
.
Voltando, ao executar o pip freeze
, temos uma listagem do que foi instalado.
$ pip freeze
aniso8601==3.0.0
click==6.7
Flask==1.0.2
Flask-RESTful==0.3.6
itsdangerous==0.24
Jinja2==2.10
MarkupSafe==1.0
python-dotenv==0.8.2
pytz==2018.4
six==1.11.0
Werkzeug==0.14.1
wheel==0.24.0
Algumas informações importantes devem ser feitas para entendimento dos requerimentos da aplicação:
Flask==1.0.2: Ao temos um
==
interpretamos que a dependência do Flask esta fixada a versão1.0.2
. Desta maneira nosso projeto sempre que for instalado utilizará essa versão do pacote, já que, o pacote pode sofrer atualizações e mudanças.Flask>=1.0.2: Da mesma forma que o sinal de
==
definimos uma versão minima a ser instalada. O sinal de>=
é interpretado como qualquer versão do Flask superior ou igual a versão1.0.2
. Logo se existir uma versão1.1.10
ela será a versão instalada. Também podemos definir um intervalo de versões, por exemplo, Flask>=0.12,<=1.0.2.Flask: Sempre irá instalar a última versão disponível deste pacote.
git+https://github.com/lucassimon/django-sendgrid.git@master#egg=django-sendgrid
: Através deste caminho podemos instalar os pacotes disponíveis no Github do branch master -@master
- com o nome django-sendgrid -#egg=django-sendgrid
-. É uma dica útil pois podemos instalar os forks dos projetos oficiais doPyPi
como foi neste caso.
Organização
O intuito de organizar é separar os pacotes de desenvolvimento, testes, produção e os comuns entre eles.
Vamos primeiro criar um diretório $ mkdir requirements
na raiz da pasta flask-api-users
. Depois executar o comando pip freeze > requirements/base.txt
. Observe que ele irá gerar um arquivo txt no diretório criado com o conteúdo do comando pip freeze
.
Dependências de teste
Crie um arquivo chamado tests.txt
dentro deste diretório requirements/
.
Seu conteúdo deve ser conforme esse:
-r base.txt
flake8==3.5.0
pytest==3.6.1
pytest-cov==2.5.1
pytest-flask==0.10.0
pytest-runner==4.2
Faker==0.8.15
A opção -r base.txt
significa que estamos importando todas as configurações de pacotes listadas no arquivo base.txt
O flake8 é um styleguide e também uma ferramenta de lint para melhorar a codificação.
O pytest é um framework de testes simples.
pytest-cov, pytest-flask, pytest-runner
são extensões dopytest
O Faker é um utilitário para gerar dados fakes e randômicos, por exemplo nomes de países, cidades, pessoas, data de nascimento, cores, datas e etc..
Dependências de desenvolvimento
Agora criamos nossos pacotes de desenvolvimento, útil para padronizar os pacotes comuns dos desenvolvedores envolvidos na aplicação.
-r base.txt
-r test.txt
ipdb==0.11
ipython==6.4.0
flask-shell-ipython==0.3.0
isort==4.3.4
O Ipython melhora a experiência em utilizar o
REPL
do python adicionando cores, auto complete e demais outras facilidades.O ipdb é um utilitário para melhorar a experiência e uso da depuração de erros do python
pdb
. Por utilizar oIpython
deu-se o nome deipdb
.O flask-shell-ipython substituí o
flask shell
instalado por padrão peloflask
utilizando oipython
.O isort nos ajuda a padronizar os
imports
de pacotes em ordem alfabética e por seções. É útil pois cada desenvolvedor tem manias e pode fazer de um jeito. Com esse utilitário definimos um padrão e a ferramenta fica responsável por automatizar esse processo nos arquivos da aplicação.
Dependências de produção
Por fim temos as dependências de produção.
-r base.txt
gunicorn==19.7.1
- O gunicorn é responsável por servir um servidor http utilizando o wsgi.
Agora por quê separamos? Primeiro é pela organização. Segundo é separar os pacotes de desenvolvimento de produção de forma simples, ou seja, não precisamos do ipython
ou pytest
exclusivos dos ambientes de desenvolvimento e teste em nosso servidor de produção.
Feito todo esse processo podemos instalar os pacotes através dos arquivos que criamos. Para isso execute
pip install -r requirements.dev.txt
Esse comando irá instalar todas as dependências dos arquivos base.txt
e test.txt
incluindo os de dev.txt
. Vale lembrar que, somente o comando pip install [nome do pacote]
não adicionará automaticamente esse comando nos requerimentos da aplicação. Logo é necessário escreve-los cada pacote em seu respectivo arquivo.
Concluindo, comitamos essas alterações em nossa ferramenta de versionamento e agora todos os envolvidos e participantes saberão o que este aplicativo web utiliza e quais pacotes compõem o aplicativo.
Espero ter colaborado com o entendimento e a importância em utilizar o gerenciador de pacotes e versões. Ele é extensível a todos os outros pacotes, bibliotecas e aplicações utilizando python como base.
Abraços a todos.
Próximo artigo: Configurando o pytest e nosso primeiro teste