まず、フォームのフォーム
ユーザーの選択の投票を受信するために、我々は、フロントページにポーリングインタフェースを表示する必要があります
世論調査/ detail.html
<H1> {{question.question_text}} </ H1> {%なら ERROR_MESSAGE%} <P>の<strong> {{ERROR_MESSAGE}} </ strong>の</ P> {%のENDIFの%} <フォームアクション= " { %URL '投票:投票' question.id%} "メソッド= " ポスト" > {%csrf_token%} {%のための選択肢で question.choice_set.allの%} の<input type = " ラジオ"名前= " 選択" ID = " 選択{{forloop.counter}} "値= " {{}} choice.id" > <ラベルのため = " 選択{{forloop.counter}} " > {{choice.choice_text}} </ label>は<BR> {%ENDFOR%} の<input type = " 提出"値= " 投票" > < /フォーム>
- forloop.counterが特別にあなたの現在のサイクルの数を示すために設けられた可変Djangoのテンプレートシステムで、サイクルは一般的に対数スケールを発注した項目を追加するために使用されます。
- 我々はPOSTリクエストを送信するので、我々は、クロスサイトリクエストフォージェリの安全性を考慮しなければならない、CSRF(特定の意味下さい百度)と呼ばれます。Djangoはこのトラブルを回避するための簡単な方法を提供し、それは形で添加される{%csrf_token%}タグ、ラベル名を形成する限り、フォームが形であるように、任意の位置に、固定フォーマット、変更することができません。この方法では、道の形に便利なHaoshi提出フォームであるが、それはAJAXの方法を使用してデータを提出した場合、このメソッドは持って使用していません。
投票ビュー機能(ポーリング/ views.py)プロセス
デフ投票(リクエスト、question_id): 質問 = get_object_or_404(質問、PK = question_id) してみてください: selected_choice = question.choice_set.get(PK = request.POST [ ' 選択' ]) を除く(KeyError例外、Choice.DoesNotExist): リターンレンダリング(リクエスト、' 世論調査/ detail.html ' 、{ ' 質問' :質問、 ' ERROR_MESSAGE ':" あなたは選択肢を選択しなかった。" 、 }) 他: selected_choice.votes + = 1 selected_choice.save() の戻り HttpResponseRedirect((リバース' 世論調査:結果'、引数の=(question.idを、)))
request.POSTを使用すると、キー名によってデータ・アクセスを提出することができ、辞書のようなオブジェクトです。この例では、request.POST[’choice’]
それはデジタルのように見える場合でも、それは選択されたオプションのIDを返し、文字列の型の値は常に文字列です!
request.POST[’choice’]
あなたの選択は、POSTデータのキーで提供されていない場合はKeyError例外例外を引き起こす可能性があり、この場合には、上記のコードは、フォームページを返すと、エラーメッセージが表示されますされます。PSは:通常、我々は、例えば、例外を防ぐために、デフォルト値を与えrequest.POST[’choice’,None]
、
カウンタープラス1を選択した後、リターンであるHttpResponseRedirect
代わりに、我々が以前に使用HttpResponse
。リダイレクトURL:HttpResponseRedirect、1つのパラメータを取ります。ここでは、成功したPOSTデータを扱う提案、常にHttpResponseRedirectを返し、良い習慣を維持しなければならないのです。これは、WEBを開発するための良い習慣だ、ただDjangoのためではありません。
私たちは、HttpResponseRedirect上記1つのコンストラクタを使用するreverse()
機能を。これは、ビュー機能にハードコードされたURLを避けるために私たちを助けることができます。それはまず、我々は名前で指定のURLconf、およびデータ転送を必要とします。例えば'/polls/3/results/'
、ここで図3は、あるquestion.id
値。リダイレクト入力した後polls:results
、対応するビューを、そしてquestion.id
それに渡されます。
誰かが問題に投票すると、投票()ビューには、アンケート結果の表示ページにリダイレクトします。のは、このビューの処理結果ページ(ポーリング/ views.py)を書いてみましょう:
django.shortcuts インポートget_object_or_404を、レンダリング DEF 結果を(リクエスト、question_id): 質問 = get_object_or_404(質問、PK = question_id)を 返すレンダリング(リクエスト、' ポーリング/ results.htmlを' { ' 質問':質問})
テンプレートpolls/templates/polls/results.html
<H1> {{question.question_text}} </ H1> <UL> {%ための選択で question.choice_set.all%} <LI> {{choice.choice_text}} - {{choice.votes}}投票{ {choice.votes |複数形}} </ LI> {%ENDFOR%} </ UL> <a href= "{% URL'polls:detail' question.id %}"> 再び投票する</a>?
第二に、汎用ビューの使用:コードの重複を減らします
改善されたのURLconf
開きpolls/urls.py
、ファイルを次のようにそれを編集します。
ロムdjango.urlsは、インポートパスを から。インポートビュー APP_NAME = ' 世論調査' urlpatternsを = [ パス(''、views.IndexView.as_view()、名前= ' インデックス' )、 パス(' <整数:PK> / '、views.DetailView.as_view()、名= ' 詳細' )、 パス(' <INT:PK> /結果/ '、views.ResultsView.as_view()、名前= ' 結果' )、 パス('<整数:question_id> /投票/ 'views.vote、名前= ' 投票" )、 ]
ビューを変更します。
次に、開いてpolls/views.py
、ファイルを結果のインデックス、詳細ビューを削除して、ジャンゴの一般的な見解を交換します
クラスIndexView(generic.ListView): テンプレート名 = ' 世論調査/ index.htmlを' context_object_name = ' latest_question_list ' DEF get_queryset(自己): "" " 最後の5つの公表の質問を返す""" を返す(Question.objects.order_byを" - PUB_DATE ')[:5 ] クラスDetailView(generic.DetailView): モデル = 質問 テンプレート名 = ' 世論調査/ detail.html " クラス ResultsView(総称。DetailView): モデル =質問 テンプレート名 = ' 世論調査/ results.html ' DEF 投票(リクエスト、question_id): 質問 = get_object_or_404(質問、PK = question_id) してみてください: selected_choice = question.choice_set.get(PK = request.POST.get(' 選択' ) ) を除く(KeyError例外、Choice.DoesNotExist): リターン(要求、レンダリング' ポーリング/ detail.htmlを' 、{ ' 質問' :質問、 ' ERROR_MESSAGE ': " あなたは選択肢を選択しなかった。" 、 }) 他: selected_choice.votes + = 1 selected_choice.save()を 返す(HttpResponseRedirectを逆(' 世論調査:結果'、引数の=(question.id、)))
我々は2つの共通のビューを使用ListView
し、DetailView
(彼らは親として継承されています)。両方は、「オブジェクトのリストを表示し、」抽象「オブジェクトの特定のタイプの表示詳細ページ」を表します。
-
各汎用ビューは、このモデルは、プロパティにより提供される、それがモデルに基づいて行動することが何であるかを知る必要があります。
-
DetailView
「PK」と呼ばれる主キーにURLをキャプチャする必要があるので、私たちのurlファイル内の2と3のエントリ<question_id>
に変更<pk>
。
デフォルトでは、DetailView
一般的なビューを使用して呼ばれている<app name>/<model name>_detail.html
テンプレートを。本例では、実際に使用されますpolls/detail.html
。template_name
この属性は、デフォルト名の代わりに使用するテンプレートが自動的に生成され、テンプレートの名前を指定するために使用されます。指定された、resutlsリストビューで、同様に(細部へのこだわり、非難、慎重に上記のコードを必ず守ってください)template_name
として'polls/results.html'
、resulstビューと詳細ビューでも同じモデル使用して、DetailViewクラスを継承したが、これを保証する:Qeustionを彼らはまだ別のページが表示されます。(異なるまあ用テンプレート!とても簡単!)
同様に、リストビュー一般的なビューがデフォルトと呼ばれるテンプレートを使用しています<app name>/<model name>_list.html
。また、使用しtemplate_name
、当社の既存の使用するリストビューを伝えるために、この変数を "polls/index.html"
、むしろ独自のデフォルトの1を使用するよりも、テンプレートを。
チュートリアルの前の部分では、我々は、格納するためのテンプレートを提供question
し、latest_question_list
コンテキスト変数を。DetailViewのために、自動的に提供されquestion'll私たちはDjangoのモデル(質問)を使用しているため、Djangoはインテリジェントに適切なコンテキスト変数を選択します。ただし、リストビューのために、コンテキスト変数の自動生成question_list
。それをカバーするために、我々は提供しcontext_object_name
、我々が使用することを指定するプロパティlatest_question_list
の代わりにquestion_list
。
第三に、静的ファイル
サーバによって生成されたHTMLファイルに加えて、WEBアプリケーションは通常、このような画像ファイル、JavaScriptのスクリプトやCSSスタイルシートなど、いくつかの他の必要な書類を、提供する必要があるなど、ユーザーがページ全体に提示されます。ジャンゴでは、我々は、これらの文書の内容は基本的に固定されているので、あなたが動的に生成する必要はありません、総称して「静的ファイル」と呼ばれるこれらの文書を参照してください。
小規模なプロジェクトでは、これらは大きな問題ではありません、あなたはまだあなたのWebサーバーを見つけることができるの任意の場所にファイルをすることができます。しかし、大規模なプロジェクトのために、特にアプリからの静的ファイルとは異なるセットの治療を含む複数のアプリのプロジェクトを含むものは、生きて面倒をもたらします。
しかし、これはあるdjango.contrib.staticfiles
目的:これは、各アプリケーション(および指定した任意の場所)を収集静的ファイルの統一、およびアクセスに簡単に指定された場所へ。
世論調査の中でディレクトリを作成しstatic
たディレクトリ。Djangoはテンプレートファイルを対応するジャンゴの方法を模索していた、そこに静的ファイルを探すことはポーリング/テンプレート/中で同じです。
DjangoのSTATICFILES_FINDERS
検索リストに含まれる設定項目は、彼らはさまざまなソースからの静的なファイルを検索する方法を知っています。デフォルトのFinder市の一つAppDirectoriesFinder
、
それぞれがことがありINSTALLED_APPS
、次見つけるためにstatic
、このような私たちが作成したものとして、サブディレクトリ、static
ディレクトリを。管理者の管理サイトでは、その静的ファイルの同じディレクトリ構造を使用しています。
static
新しいディレクトリを作成しpolls
、サブディレクトリ、およびその後にサブディレクトリを作成しstyle.css
、ファイル
グッドディレクトリ構造は、各アプリケーションは、独自のURL、フォーム、ビュー、モデル、テンプレートと静的を作成する必要があり、各テンプレートは、アプリケーションと同じ名前のサブディレクトリが含まれ、それぞれの静的なアプリケーションにも同じ名前のサブディレクトリが含まれていることです。
polls/static/polls/style.css
:
李{
色:緑。
}
テンプレートファイルでpolls/templates/polls/index.html
頭を参照
{%負荷静的%} <リンクREL = " スタイルシート"タイプ= " テキスト/ CSS " HREF = " {%静的'ポーリング/ style.cssに' %} " >
{% static %}
テンプレートタグは、絶対URLパス静的ファイルを生成します。
サーバーを再起動し、ブラウザにアクセスするhttp://localhost:8000/polls/
には、緑色の質問へのハイパーリンクが表示されます
背景画像を追加
でpolls/static/polls/
写真を保存するディレクトリの作成images
、サブディレクトリを、サブディレクトリに`background.gifファイルを置きます
CSSスタイルファイルpolls/static/polls/style.css
を追加
本体{ 背景:白URL(" 画像/ background.gif ")NO- リピート; }
リロードhttp://localhost:8000/polls/
(CTRL + F5または直接F5)は、画面の左上隅にロードされた背景画像が表示されます
ヒント:
{% static %}
彼らはジャンゴによって生成されていないので、テンプレートタグは、スタイルシートなどの静的ファイルで使用することはできません。あなたはお互い静的ファイルへのリンクを相対パスを使用する必要があります
静的ファイルへの直接アクセス