web-dev-qa-db-fra.com

Qu'est-ce qu'un "point final" dans Flask?

Le documentation de la fiole montre :

add_url_rule(*args, **kwargs)
      Connects a URL rule. Works exactly like the route() decorator.
      If a view_func is provided it will be registered with the endpoint.

     endpoint – the endpoint for the registered URL rule. Flask itself assumes the name of the view function as endpoint

Qu'entend-on exactement par "point final"?

106
Fuziang

Comment Flask Le routage fonctionne

L’idée même de Flask (et de la bibliothèque Werkzeug sous-jacente) est de mapper les chemins d’URL à une logique que vous exécuterez (généralement la "fonction de vue"). Votre vue de base est définie ainsi: :

@app.route('/greeting/<name>')
def give_greeting(name):
    return 'Hello, {0}!'.format(name)

Notez que la fonction à laquelle vous avez fait référence (add_url_rule) atteint le même objectif, sans utiliser la notation décorative. Par conséquent, ce qui suit est le même:

# No "route" decorator here. We will add routing using a different method below.
def give_greeting(name):
    return 'Hello, {0}!'.format(name)

app.add_url_rule('/greeting/<name>', 'give_greeting', give_greeting)

Supposons que votre site Web se trouve à l'adresse www.exemple.org et utilise la vue ci-dessus. L'utilisateur entre l'URL suivante dans son navigateur:

http://www.example.org/greeting/Mark

Le travail de Flask consiste à prendre cette URL, à comprendre ce que l'utilisateur veut faire, et à le transmettre à l'une de vos nombreuses python fonctions de traitement Il prend le chemin :

/greeting/Mark

... et correspond à la liste des itinéraires. Dans notre cas, nous avons défini ce chemin pour aller à la fonction give_greeting.

Toutefois, bien qu’il s’agisse de la manière habituelle de créer une vue, elle vous permet de soustraire des informations supplémentaires. En coulisse, Flask n'a pas fait le saut directement de l'URL à la fonction de vue qui devrait gérer cette demande. Il ne dit pas simplement ...

URL (http://www.example.org/greeting/Mark) should be handled by View Function (the function "my_greeting")

En fait, il y a une autre étape, où il mappe l'URL vers un noeud final:

URL (http://www.example.org/greeting/Mark) should be handled by Endpoint "my_greeting".
Requests to Endpoint "my_greeting" should be handled by View Function "my_greeting"

Fondamentalement, le "noeud final" est un identificateur utilisé pour déterminer quelle unité logique de votre code doit gérer la demande . Normalement, un noeud final est simplement le nom d'une fonction de vue. Cependant, vous pouvez réellement changer le noeud final, comme dans l'exemple suivant.

@app.route('/greeting/<name>', endpoint='say_hello')
def give_greeting(name):
    return 'Hello, {0}!'.format(name)

Maintenant, lorsque Flask achemine la demande, la logique ressemble à ceci:

URL (http://www.example.org/greeting/Mark) should be handled by Endpoint "say_hello".
Endpoint "say_hello" should be handled by View Function "my_greeting"

Comment vous utilisez le point final

Le point final est couramment utilisé pour la "recherche inversée". Par exemple, dans une vue de votre Flask, vous souhaitez référencer une autre vue (peut-être lorsque vous créez un lien d'une zone du site à une autre)). Plutôt que de coder en dur l'URL, vous pouvez utiliser url_for() . Supposons ce qui suit

@app.route('/')
def index():
    print url_for('give_greeting', name='Mark') # This will print '/greeting/Mark'

@app.route('/greeting/<name>')
def give_greeting(name):
    return 'Hello, {0}!'.format(name)

Ceci est avantageux, car nous pouvons maintenant changer les URL de notre application sans avoir besoin de changer la ligne où nous référençons cette ressource.

Pourquoi ne pas simplement utiliser le nom de la fonction de vue?

Une question qui pourrait se poser est la suivante: "Pourquoi avons-nous besoin de cette couche supplémentaire?" Pourquoi mapper un chemin vers un noeud final, puis un noeud final vers une fonction de vue? Pourquoi ne pas sauter cette étape intermédiaire?

La raison est parce que c'est plus puissant de cette façon. Par exemple, Flask Blueprints vous permet de diviser votre application en différentes parties. Il se peut que toutes mes ressources côté administrateur se trouvent dans un plan directeur appelé "admin", et que toutes mes ressources de niveau utilisateur se trouvent sur un noeud final appelé "utilisateur".

Les plans vous permettent de les séparer en espaces de noms. Par exemple...

main.py:

from flask import Flask, Blueprint
from admin import admin
from user import user

app = Flask(__name__)
app.register_blueprint(admin, url_prefix='admin')
app.register_blueprint(user, url_prefix='user')

admin.py:

admin = Blueprint('admin', __name__)

@admin.route('/greeting')
def greeting():
    return 'Hello, administrative user!'

user.py:

user = Blueprint('user', __name__)
@user.route('/greeting')
def greeting():
    return 'Hello, lowly normal user!'

Notez que dans les deux plans, la route "/ greeting" est une fonction appelée "greeting". Si je voulais faire référence à la fonction "salutation" de l'administrateur, je ne pouvais pas simplement dire "salutation" car il existe également une fonction "salutation" de l'utilisateur. Les points finaux autorisent une sorte d'espacement de noms en vous demandant de spécifier le nom du plan directeur dans le cadre du point final. Donc, je pourrais faire ce qui suit ...

print url_for('admin.greeting') # Prints '/admin/greeting'
print url_for('user.greeting') # Prints '/user/greeting'
231
Mark Hildreth

Endpoint est le nom utilisé pour inverser la recherche des règles d'URL avec url_for et le nom par défaut de la fonction de vue apparaît.

Petit exemple:

from flask import Flask, url_for

app = Flask(__name__)

# We can use url_for('foo_view') for reverse-lookups in templates or view functions
@app.route('/foo')
def foo_view():
    pass

# We now specify the custom endpoint named 'bufar'. url_for('bar_view') will fail!
@app.route('/bar', endpoint='bufar')
def bar_view():
    pass

with app.test_request_context('/'):
    print url_for('foo_view')
    print url_for('bufar')
    # url_for('bar_view') will raise werkzeug.routing.BuildError
    print url_for('bar_view')
21
plaes