アプリケーションの作成
actix-web
は、Rustで Webサーバやアプリケーションを構築するための様々な機能構造を提供します。ルーティング、ミドルウェア、リクエストの前処理、レスポンスの後処理などを提供します。
すべての actix-web サーバは、App
インスタンスを中心に構築されています。リソースやミドルウェアのルーティングを登録するために利用されます。また、同じスコープ内のすべてのハンドラで共有されるアプリケーションのステート(状態)も保存されます。
アプリケーションの scope
は、すべてのルートの名前空間として機能します。つまり、特定のアプリケーションスコープのすべてのルートは、同じURLパスのプレフィックスを持っています。アプリケーションのプレフィックスは、常に先頭の「/」スラッシュを含んでいます。提供されたプレフィックスが先頭のスラッシュを含んでいない場合は、自動的に挿入されます。プレフィックスは、値のパスセグメントで構成されている必要があります。
scope("/app")
を持つアプリケーションでは、パス/app
、/app/
、または/app/test
を持つすべてのリクエストにマッチするが、パス/application
はマッチしません。
この例では、/app
という接頭辞を持つアプリケーションとindex.html
というリソースを作成します。このリソースは、/app/index.html
という url で利用できます。
詳細はURLディスパッチャでご確認下さい。
ステート(State)
アプリケーションのステートは、同じスコープ内のすべてのルートとリソースで共有されます。ステートはweb::Data<T>
デストラクタ(T
はステートの型)を使ってアクセスできます。ステートは、ミドルウェアからもアクセス可能です。
簡単なアプリケーションを書いて、アプリケーション名をステートに保存してみましょう。
次に、Appの初期化時のステートを渡し、アプリケーションを起動します。
アプリケーション内には、何種類ものステートを登録することができる。
Sharedな可変ステート
HttpServer
は、アプリケーションインスタンスではなく、アプリケーションファクトリ(application factory)を受け付けます。HttpServer
は、各スレッドに対してアプリケーションのインスタンスを構築します。そのため、アプリケーションのデータを複数回構築する必要があります。異なるスレッド間でデータを共有したい場合は、Send
+ Sync
のような共有可能なオブジェクトを使用する必要があります。
内部的には、web::Data
はArc
を使用します。そのため、2つのArc
を作成しないように、App::app_data()
を使って登録する前に、Data
を作成する必要があります。
次の例では、変更可能で共有されたステートを持つアプリケーションを書きます。まず、ステートを定義し、ハンドラを作成します。
そしてそのデータをApp
に登録します。
重要ポイント:
HttpServer::new
に渡されたクロージャ内で初期化されたステートは、ワーカスレッドに対してローカルであり、変更されると同期が解除される可能性があります。グローバルに共有されているステートを実現するためには、①
HttpServer::new
に渡されるクロージャの外部
で事前にステートを作成し、②クロージャー内部へ所有権の移動そしてクローンする必要があります。 (原文:To achieve globally shared state, it must be created outside of the closure passed toHttpServer::new
and moved/cloned in.)
アプリケーションスコープを使用したアプリケーションの構成
web::scope()
メソッドでは、リソースグループのプレフィックスを設定することができます。このスコープは、リソース設定によって追加されるすべてのリソースパターンの前に付加されるリソースプレフィックスを表します。これを使うと、同じリソース名を維持したまま、元の作者が意図したのとは異なる場所に一連のルートをマウントするのに役立ちます。
サンプルコード:
上記の例では、show_users
ルートは/show
ではなく/users/show
という有効なルートパターンを持ちます。これは、アプリケーションのスコープ引数がパターンの前に追加されるからです。そして、ルートはURLパスが/users/show
の場合にのみマッチし、ルート名show_users
でHttpRequest.url_for()
関数が呼ばれると、同じパスのURLが生成されます。
アプリケーションガードと仮想ホスト
.guard()
メソッドは、requestオブジェクトの参照を受け取り、true または false を返す単純な関数と考えることができます。形式的には、guard はGuard
トレイトを実装した任意のオブジェクトです。Actix Web はいくつかの guard を提供します。API ドキュメントのfunctions sectionを参照してください。
提供されているガードのひとつにHeader
があります。これは、リクエストヘッダ情報に基づくフィルタとして使用することができます。
設定
シンプルさと再利用性のために、App
と web::Scope
の両方がconfigure()
メソッドを提供しています。この関数は、設定の一部を別のモジュール、あるいはライブラリに移動するのに便利です。例えば、リソースの設定の一部を別のモジュールに移動させることができます。
上記サンプルの実行結果は、次のようになります。
/ -> "/"
/app -> "app"
/api/test -> "test"
各ServiceConfig
は、独自のdata
,routes
,そしてservices
を持つことができます。