Como dividir o aplicativo balão em vários arquivos py?

146

Atualmente, meu aplicativo de balão consiste em um único test.pyarquivo com várias rotas e a main()rota definida. Existe alguma maneira de criar um test2.pyarquivo que contenha rotas que não foram tratadas test.py?

@app.route('/somepath')
def somehandler():
    # Handler code here

Estou preocupado com a existência de muitas rotas test.pye gostaria de fazê-las para que eu possa executar python test.py, o que também selecionará as rotas test.pycomo se fizessem parte do mesmo arquivo. Que mudanças eu tenho que fazer test.pye / ou incluir test2.pypara que isso funcione?

Rolando
fonte

Respostas:

152

Você pode usar a estrutura de pacotes Python usual para dividir seu aplicativo em vários módulos, consulte os documentos do Flask.

Contudo,

O Flask usa um conceito de blueprints para criar componentes de aplicativos e suportar padrões comuns dentro de um aplicativo ou entre aplicativos.

Você pode criar um subcomponente do seu aplicativo como um Blueprint em um arquivo separado:

simple_page = Blueprint('simple_page', __name__, template_folder='templates')
@simple_page.route('/<page>')
def show(page):
    # stuff

E então use-o na parte principal:

from yourapplication.simple_page import simple_page

app = Flask(__name__)
app.register_blueprint(simple_page)

Os projetos também podem agrupar recursos específicos: modelos ou arquivos estáticos. Consulte os documentos do Flask para obter todos os detalhes.

pixelistik
fonte
1
como podemos ter as rotas do blueprint em arquivo que não sejam o init desse blueprint?
divyenduz
se eu quiser fazer um seguro pontos finais usando JWT, então, como vai fazer isso em todos os arquivos route.py
Ashok Sri
18

Você pode usar um truque simples, que é a variável de aplicativo de frasco de importação do principal dentro de outro arquivo, como:

test-routes.py

from __main__ import app

@app.route('/test', methods=['GET'])
def test():
    return 'it works!'

e em seus arquivos principais, onde você declarou o aplicativo de balão, importe rotas de teste, como:

app.py

from flask import Flask, request, abort

app = Flask(__name__)

# import declared routes
import test-routes

Funciona do meu lado.

nimeresam
fonte
2
É apenas um exemplo, __main__refere-se ao seu arquivo de entrada, é isso!
nimeresam 26/01
3
Brilhante, muito obrigado. O modelo ou a abordagem de pacote acima são um exagero para aplicativos pequenos.
VH-NZZ 28/01
Aqui está um link para os documentos em que esse método é explicado: https://flask.palletsprojects.com/en/1.1.x/patterns/packages/
Christopher
1
@nimeresam Funcionou para mim, mas tive que aprender que import test-routeso app.pyarquivo não pode estar no topo do arquivo. Ele travou o gunicorn, mas, depois de mover a importação para a parte inferior do arquivo, funcionou. "apenas garantindo que o módulo seja importado e estamos fazendo isso na parte inferior do arquivo"
Niklas R.
5

Dividir o aplicativo em plantas é uma ótima idéia. No entanto, se isso não for suficiente, e se você quiser dividir o próprio Blueprint em vários arquivos py, isso também é possível usando o sistema regular de importação de módulos Python e, em seguida, percorrendo todas as rotas importadas dos outros arquivos .

Eu criei um Gist com o código para fazer isso:

https://gist.github.com/Jaza/61f879f577bc9d06029e

Tanto quanto sei, esta é a única maneira viável de dividir um Blueprint no momento. Não é possível criar "sub-projetos" no Flask, embora haja um problema em aberto com muita discussão sobre isso:

https://github.com/mitsuhiko/flask/issues/593

Além disso, mesmo que fosse possível (e provavelmente seja possível usar alguns dos trechos desse segmento de problema), os sub-projetos podem ser muito restritivos para o seu caso de uso - por exemplo, se você não quiser todas as rotas em um submódulo para ter o mesmo sub-prefixo de URL.

Jaza
fonte
4

Esta tarefa pode ser realizada sem blueprints e importações complicadas usando o Mapa de URL Centralizado

app.py

import views
from flask import Flask

app = Flask(__name__)

app.add_url_rule('/', view_func=views.index)
app.add_url_rule('/other', view_func=views.other)

if __name__ == '__main__':
    app.run(debug=True, use_reloader=True)

views.py

from flask import render_template

def index():
    return render_template('index.html')

def other():
    return render_template('other.html')
Bleiz
fonte