静的ファイル

Pylons では、アプリケーションの “public” ディレクトリは “/” の上の 静的なオーバーレイとして設定されます。その結果、 URL “/images/logo.png” は “pylonsapp/public/images/logo.png” に行き着きます。これはミドルウェア を使って行われます。 Pyramid にはこれの厳密な等価物はありませんが、静的 ファイルを返す方法はあります。また、アドオンパッケージが別の方法を提供 しています。

静的ビュー

これは Pyramid で静的ファイルを返すデフォルトの方法です。 前の方の章にあった main 関数を思い出してください:

config.add_static_view('static', 'static', cache_max_age=3600)

これは、ディレクトリ “pyramidapp/static” を URL “/static” の下で公開する ように Pyramid に伝えます。その結果、 URL “/static/images/logo.png” は “pyramidapp/static/images/logo.png” に行き着きます。

それは トラバーサル を使用して実装されます。トラバーサルに関しては、 このガイドの中ではあまり話していません。トラバーサルベースのビューは ビュー名 を持っていて、URL プレフィックスまたはコンポーネントとして 使えます。最初の引数はビュー名 (“static”) です。それはこのビューが URL “/static” とマッチすることを意味しています。第 2 の引数は、 (アプリ ケーションの Python パッケージからの相対) ディレクトリに対する asset スペックです。キーワード引数は HTTP expire ヘッダーを 3600 秒 (1時間) 後に設定するオプションです。これ以外にもパーミッションその他のための キーワード引数があります。

Pyramid の静的ビューは、 Pylons に対して次のような利点があります:

  • すべての静的ファイルが単一の URL プレフィックスの下に置かれるように 強制します。したがって、静的ファイルが URL 空間に散在しません。
  • URL を生成するメソッドが提供されます: request.static_url()request.static_path()
  • 別の静的メディアサーバからファイルを返すために、デプロイ設定 (INI ファイル) でベース URL (“/static”) を上書きすることができます。
  • デプロイ設定では、さらに静的ディレクトリの中のアイテムを、他のサブ ディレクトリあるいはファイルを代わりに指すことによって上書きすることが できます。これは Pyramid マニュアルの中で「asset の上書き」と呼ばれます。

一方 Pyramid と比較して次のような欠点があります:

  • 静的 URLにプレフィックス “/static” が付きます。
  • トップレベルのファイル URL を返すことができません。

静的ビューで任意の URL ディレクトリを返すことが可能です。したがって、以下の ように各 URL ディレクトリに対する個別のビューを持つことができるでしょう:

config.add_images_view('images', 'static/images')
config.add_stylesheets_view('stylesheets', 'static/stylesheets')
config.add_javascript_view('javascript', 'static/javascript')

これは、例えば URL “/images” をディレクトリ “pyramidapp/static/images” を 指すように設定します。

Pyramid の認証システムを使用していれば、特定のパーミッションを要求する ファイルに対する別のビューを作ることもできます:

config.add_static_view("private", "private", permission="admin")

静的 URL の生成

静的ファイルへの URL をこのように生成することができます:

href="${request.static_url('static/images/logo.png')}

トップレベルのファイル URL

それで、どのようにしてトップレベルのファイル URL の問題を避ければ良いの でしょうか? 後述するように、それらに対する通常のビューを登録することが できます。 “/favicon.ico” については、サイトテンプレート中でそれを HTTP ヘッダに置き換えることができます:

<link rel="shortcut icon" href="${request.static_url('pyramidapp:static/favicon.ico')}" />

標準の Pyramid scaffold は実際にこれを行います。 “/robots.txt” について は、実際にはこれがアプリケーションではなくウェブサーバに所属すると決めて、 したがってこのように Apache にそのファイルを直接返させることができます。

Alias   /robots.txt   /var/www/static/norobots.txt

もちろん、 Apache に静的ディレクトリも返させることができます:

Alias   /static   /PATH-TO/PyramidApp/pyramidapp/static

しかし、 mod_proxy を使用していれば、 virtualhost 設定の中の 前の方 でそのディレクトリのプロキシを無効にしなければならないでしょう:

Alias ProxyPass   /static   !

Alias のような他のパスディレクティブと RewriteRule を組み合わせて使用 している場合、 RewriteRule フラグドキュメンテーション (特に “PT” および “F”) を読んで、ディレクティブが期待通りに連携するようにしてください。

外部の静的メディアサーバ

静的メディアサーバに対して設定を柔軟にするために:

# In INI file
static_assets = "static"
# -OR-
static_assets = "http://staticserver.com/"

main 関数:

config.add_static_view(settings["static_assets"], "zzz:static")

すると、それは設定に依存して “http://mysite.com/static/foo.jpg” または “http://staticserver.com/foo.jpg” を生成するでしょう。

静的 route

この戦略は Akhet で利用可能です。それは Pylons が行うように “/” の上に 静的なディレクトリを覆います。したがって、 URL を変更したり、トップレベル のファイル URL について心配したりする必要はありません。

1
2
3
4
5
config.include('akhet')
# Put your regular routes here.
config.add_static_route('zzz', 'static', cache_max_age=3600)
# Arg 1 is the Python package containing the static files.
# Arg 2 is the subdirectory in the package containing the files.

これは、すべての URL とマッチする静的 route とその URL を返すビューを 登録します。実際には、 route はファイルが存在するかどうかチェックする 述語を持ち、ファイルが存在しなければ route は URL とマッチしません。 とはいえ、他の route より後に静的 route を登録するのはよいことです。

それより前にいくつかの静的 URL とマッチする別の包括的な route があれば、 この例のように route からそれらの URL を除外しなければならないでしょう。

config.add_route("main", "/{action}",
    path_info=r"/(?!favicon\.ico|robots\.txt|w3c)")
config.add_static_route('zzz', 'static', cache_max_age=3600)

静的 route 実装は、静的ファイルに対する URL を生成 しません 。 したがって、それを自分自身でしなければならないでしょう。Pylons も あまり効果的にそれをしませんでした。

トップレベルのファイル URL を返す別の方法

静的ビューを使用していて、あくまでトップレベルのファイル URL を返す必要 があれば、それをするための方法はいくつかあります。

手作業によるファイルビュー

これは Pyramid マニュアルの静的 asset の章でドキュメント化されています。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
# Main function.
config.add_route("favicon", "/favicon.ico")

# Views module.
import os
from pyramid.response import FileResponse

@view_config(route_name="favicon")
def favicon_view(request):
    here = os.path.dirname(__file__)
    icon = os.path.join(here, "static", "favicon.ico")
    return FileResponse(icon, request=request

または、 route のないトラバースに対してビューを設定する方法がとても気に なる場合:

@view_config(name="favicon.ico")

pyramid_assetviews

“pyramid_assetviews” はトップレベルのファイル URL のためのサードパーティ のパッケージです。

1
2
3
4
5
6
7
# In main function.
config.include("pyramid_assetviews")
config.add_asset_views("static", "robots.txt")  # Defines /robots.txt .

# Or to register multiple files at once.
filenames = ["robots.txt", "humans.txt", "favicon.ico"]
config.add_asset_views("static", filenames=filenames, http_cache=3600)

もちろん、ファイルが static ディレクトリの中にあれば、それらは “/robots.txt” だけでなく “/static/robots.txt” としても見えるでしょう。 これが問題となる場合、 static ディレクトリの外にこれらのファイルのための 別のディレクトリを作成してください。