1. ホーム
  2. python

[解決済み] Flaskの「エンドポイント」とは何ですか?

2022-05-15 06:10:29

質問

その Flaskのドキュメントでは :

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

エンドポイントとは具体的に何を意味するのでしょうか?

どのように解決するのですか?

Flaskのルーティングの仕組み

Flask (およびその基盤である Werkzeug ライブラリ) の全体のアイデアは、URL パスを実行するロジック (典型的には "view function") にマップすることです。基本的なビューはこのように定義されます。

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

参照した関数(add_url_rule)は、デコレータ表記を使わないだけで同じ目的を達成することに注意してください。したがって、以下は同じです。

# 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)

あなたのウェブサイトが'www.example.org'にあり、上記のビューを使用しているとします。ユーザーはブラウザに次のURLを入力します。

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

Flaskの仕事は、このURLを受け取り、ユーザーが何をしたいのかを把握し、それを処理するためにあなたの多くのPython関数の1つに渡すことです。これは パス :

/greeting/Mark

...そして、それを経路のリストにマッチさせます。この例では、このパスの行き先を give_greeting 関数に行くように定義しています。

しかし、これはビューを作成するための典型的な方法ですが、実際にはいくつかの余分な情報を抽象化しています。舞台裏では、FlaskはURLからこのリクエストを処理するビュー関数に直接ジャンプすることはありませんでした。それは単に...と言うわけではありません。

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

実はもう一つステップがあり、そこではURLをエンドポイントにマッピングしています。

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

基本的には エンドポイントは、コードのどの論理ユニットがリクエストを処理すべきかを決定するために使用される識別子です。 . 通常、エンドポイントは単にビュー関数の名前です。しかし、次の例で行われているように、実際にエンドポイントを変更することができます。

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

さて、Flaskがリクエストをルーティングすると、ロジックは次のようになります。

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

エンドポイントの使用方法

エンドポイントは一般的に "逆引き" のために使われます。例えば、Flask アプリケーションのあるビューで、別のビューを参照したいとします(おそらくサイトのある領域から別の領域にリンクしているとき)。URLをハードコードするよりも、むしろ url_for() . 次のように仮定します。

@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)

これは、リソースを参照する行を変更しなくても、アプリケーションの URL を変更できるようになったという点で有利です。

なぜ常にビュー関数の名前を使用しないのですか?

なぜこのような余分なレイヤーが必要なのでしょうか?なぜパスをエンドポイントにマップし、次にエンドポイントをビュー関数にマップするのでしょうか? なぜ、その中間ステップをスキップしないのでしょうか?

その理由は、この方法がより強力だからです。たとえば Flask ブループリント を使うと、アプリケーションを様々な部分に分割することができます。管理者側のリソースをすべて "admin" というブループリントに、ユーザーレベルのリソースをすべて "user" というエンドポイントに置くことができるかもしれません。

ブループリントを使用すると、これらをネームスペースに分離することができます。たとえば...

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!'

どちらのブループリントでも、'/greeting' ルートは "greeting" と呼ばれる関数であることに注意してください。管理者の "greeting" 関数を参照したい場合、ユーザーの "greeting" 関数も存在するため、単に "greeting" と言うわけには行きません。エンドポイントでは、エンドポイントの一部としてブループリントの名前を指定することで、一種のネームスペーシングを行うことができます。つまり、次のようなことができます...

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