[[Open棟梁Project>http://opentouryo.osscons.jp/]] - [[マイクロソフト系技術情報 Wiki>http://techinfoofmicrosofttech.osscons.jp/]]

-[[戻る>ASP.NET MVC]]

* 目次 [#n8bb5f94]
#contents

*概要 [#qe050a8a]

*モジュール化の考え方 [#qfa205f4]

**ModelとViewの関係 [#u005fdca]
Model (0..1) <---> (1) View

**ControllerとViewの関係 [#xc23cbb6]
View (1..*) <---> (1) Controller

***View (1) <---> (1) Controller [#va1ffd01]
ASP.NETのWebFormに近い

***View (1..*) <---> (1) Controller [#n9abe57a]
[[スキャフォールディング(scaffolding)>ASP.NET MVCの用語#e701b267]]では、この考え方を採用している。

-スキャフォールディングの時のMとCの関係はCRUDと割り切っているから、~
Model (0..1) <---> (1) View (1..*) <---> (1) Controller となる。

-しかし、1画面に、全てのCRUD機能が詰まっていたら、~
Model (0..1) <---> (1) View (1) <---> (1) Controller と[[WebForm>#va1ffd01]]的になる。

***上記に中立 [#p6842b7c]
1業務、1Controllerなどの考え方でもイイ。

**モジュール化の要約 [#j2c8410a]
以下の2つの方式から選択する。

業務画面は、Modelに対応するCRUD画面を生成するスキャフォールディングと異なり~
Controllerが厳密に1つのModelに紐付かないため、画面単位のモジュール化のほうが適合するかもしれない。

***スキャフォールディング方式 [#td62a820]
Model (0..1) <---> (1) View (1..*) <---> (1) Controller

***ASPXライクな1画面1モジュール方式 [#se3008cd]
Model (0..1) <---> View (1) <---> (1) Controller

*Controllerの作成 [#ra660e99]

**Actionの作成 [#m1334cd3]

***URLルーティング [#zed8012c]
ユーザーがブラウザーに URL を入力すると、MVC アプリケーションでは、~
RouteConfig.cs / .vb ファイルに定義されているルーティング規則~
を使用してURL が解析され、コントローラーのパスが特定される。

-コントローラーは、要求を処理する適切なアクション メソッドを決定する。
-既定では、要求の URL は、コントローラー名とアクション名を含むサブパスとして扱われる。

***HTTP method [#qa67aa3b]

-Get :

--メソッド定義 : [HttpGet]メソッド属性を付与
---Get メソッドのみ受け入れる。
---それ以外の HTTP メソッドは受け入れない(404 が返る)。

--ユースケース:
---Getで別画面に画面遷移する場合
---入力項目が無い状態で、同一画面内で状態遷移する場合

-Post :~

--メソッド定義 : [HttpPost]メソッド属性を付与
---Post メソッドのみ受け入れる。
---それ以外の HTTP メソッドは受け入れない(404 が返る)。

--ユースケース :
---入力項目がある状態でのPostBackする場合。
---Postで別画面に画面遷移する場合。

-,etc. : ,etc.

-メソッド属性を指定しない場合の動作~
全ての HTTP method を受け入れる。

***引数 [#i5d9821b]
-マップの方法

--POSTやGETのパラメタの名前と一致した引数を定義しておけば、自動的にマップされる。
---Get ならクエリ文字列のキー名
---Post ならフォームデータのキー名

--FormCollection を使う (Post の場合のみ)~
&lt;form&gt; の中身がコレクション型として保持されたもの。

--モデルクラスを使う (Post の場合のみ)~
コントローラーとビューで、モデルクラスのデータを双方向バインディングしている場合に使用される。

-HtmlHelperの生成するパラメタ~
HtmlHelperの生成するパラメタのうち、HtmlHelperが使用するものは~
メソッド引数にマップしない(そのパラメタを自分で使いたければ、マップしても構わない)。

***戻り値 [#v19d2983]
[[アクションメソッドの結果として、クライアントに返す適切なビューを選択する。>#q7da2efc]]

*Modelの作成 [#r127e540]

*Viewの作成 [#m019c385]
**Razer、ASPX の使い分け[#m195fa6e]
Razer、ASPX構文でModelを使ってHTMLを生成。

ASPX と Razor の記述方法の比較

||ASPX|Razor|h
|インライン式 (プロパティの値を表示する場合など)|<%: Model.Property1 %>|@Model.Property1|
|インライン式 (エスケープ処理をスキップし、プロパティの値をそのまま表示する場合)|<%= Model.Property1 %>|@Html.Raw(Model.Property1)|
|コードブロック (ロジックを直接 View に記述する場合) (C#)|<% string str = "あいうえお"; %>|@{ string str = "あいうえお"; }|
|コードブロック (ロジックを直接 View に記述する場合) (VB)|<% Dim str As String = "あいうえお" %>|@Code&br;&nbsp;&nbsp;&nbsp;&nbsp;Dim str As String = "あいうえお"&br;End Code|

**BeginForm の使い分け [#sf5c2980]
-HTML(Ajax).BeginFormを記述(そもそもこれはFormタグを生成するヘルパ)
--ここで指定した名前のaction属性を持つFormが生成される。
--これがPOSTされると、その名称のコントローラーのActionに入る。

-MicrosoftのASP.NET MVCのAjax.BeginFormは、~
クライアント・サイドのJavaScriptフレームワークとシームレスに連動しているので~
JavaのOSSフレームワークと比べて、かなり実装し易くトラブルも起き難くなっている。

***HTML.BeginForm [#y7008c56]
部分Viewの作成は共通化のため。

-全体更新が多数を占める場合(画面設計による)。

-レガシー技術で構築したい場合
--クライアント・サイドのJavaScriptフレームワークにより~
ブラックボックス化されておりトラブルシュートに心配がある場合がある。
--ただし、JavaのOSSフレームワークと比べてシームレスに連動しているので~
マイクロソフトのサポートを活用して解決できる可能性が高い。

-画面リフレッシュにより、リクエスト・レスポンスのステータスを明確にしたい場合。

***Ajax.BeginForm [#b0eaca55]
部分Viewの作成は更新範囲の定義のため。

-部分更新が多数を占める場合(画面設計による)。

-サーバー側処理が非常に重い業務の場合(Ajax は非同期処理のため)。

-画面入力状態を保持したまま POST 送信したい場合
--ViewstateがサポートされないMVCで情報復元処理を割愛したい場合。

-リクエスト・レスポンスのサイズを削減して、性能向上を図りたい場合。

-画面リフレッシュによる、画面のちらつき等をなくしたい場合。

***参考 [#q5e2db0d]
-ajaxの使いどころ~
http://okwave.jp/qa/q8112782.html

-Html.BeginForm() vs Ajax.BeginForm() in MVC3 - CodeProject~
http://www.codeproject.com/Articles/429164/Html-BeginForm-vs-Ajax-BeginForm-in-MVC3

**Fromタグの切り方 [#j1aac0c9]
-1画面、1Form?
-1画面、複数Form?

複数Formの場合はFormをネストさせないこと。~
#HTMLの仕様でFormのネストは禁止されている。

**HTML ヘルパーの使い分け [#c3297525]
Html.xxxx と Html.xxxxFor の2種類のHTML ヘルパーがある。

***Html.xxxx [#o7472bbe]
Html.TextBox("Category") のように、プロパティを文字列でマップ指定する場合は、"For" がつかない HTML ヘルパーを使用する。

***Html.xxxxFor [#b6d55f13]
Html.TextBoxFor(model => model.Category) のように、プロパティをラムダ式でマップ指定する場合は、"For" で終わる HTML ヘルパーを使用する。

-...Forを使用してマップ指定すると、ViewとModel間で双方向バインディングされる。

-とは言え、HTTPを経由しての双方向バインディングになるので、~
処理方式的には、以下の様な処理シーケンスになる。
--POST時に、Formsの情報を自動的にModelに復元する。
--Viewでは復元されたModelから情報を取得して画面を生成する。

***使い分け [#uc043058]
以下のケースで使い分ける。

-ASPXライクな1画面1モジュール方式か?
-スキャフォールディング方式か?
-BeginFormの種類
--[[HTML.BeginForm>#y7008c56]]」か?
--[[Ajax.BeginForm>#b0eaca55]]」か?

個人的には、
-ASPXライクな1画面1モジュール方式
-[[HTML.BeginForm>#y7008c56]]

の場合に最も適合すると考える。

***グリッドの生成 [#j629d667]
WebGridのHTML ヘルパーを使用すると、MVCなのにHTML感を味わえないので、Loopで実装することもある。

**View [#j11c45d9]
***全体View [#od7cef82]
-Controller上のActionメソッド(のリージョン)を右クリック、
-Viewを選択するとウィザードが起動する。

-Viewテンプレート(スキャフォールディング)を選択

--Modelへの対応付け~
テンプレートを使用した場合、対応した自動生成がされる。

--オプション
---部分View
---スクリプト・ライブラリ参照
---レイアウト・ページ(個別設定可能)

***部分View [#j4280e7b]
-Viewのフォルダ(Controller名)を右クリック、
-Viewを選択するとウィザードが起動する。

-ウィザードの入力
--_XXXViewと名称を付与する。
--部分Viewにチェック入れる。

-親画面から部分Viewを呼び出す。
--親Viewからは、HTMLヘルパのHtml.Partialを使用する。
--PartialViewNameとModelを引数に取る~
親と同じModelを渡すか?Model.Modelを渡すか?どちらでもOK。

-Ajax.BeginFormの場合、親画面から部分ViewをDIVで囲っておく。

*画面遷移の考え方 [#q3d2aae4]
「[[ルーティング>ASP.NET MVCの用語#abe121d3]]」で説明したとおり、~
URLでController+Actionを指定すると指定のControllerのActionが実行される。~
#ただし、Actionを省略した時は、Index(既定のAction)が呼ばれる。

**画面遷移のメソッド [#q7da2efc]
***Viewの選択 [#vfdf6f42]
下記ヘルパ・メソッドを使用する。

-Return View("Result")
--基本的には「[[HTML.BeginForm>#y7008c56]]」の場合に使用する。
--ControllerからViewResultを選択して返す(通常は自画面を選択)。
--Ajax.BeginFormの場合は、画面の初期表示などにも用いられる

-Return PartialView("Result")
--基本的には「[[Ajax.BeginForm>#b0eaca55]]」の場合に使用する。
--ControllerからPartialViewResultを選択して返す。

***画面遷移 [#b9d4724d]
-Redirect遷移方式~
--画面に対応するコントローラーを選択する。
--下記のRedirect系ヘルパ・メソッドを使用する。

-Redirect系ヘルパ・メソッド
--Return Redirect
---指定されたURLにリダイレクト。
---Return Redirect("http://www.wings.msn.to/");

--Return RedirectToAction
---アクション名、コントローラー名、ルート値を使用して、指定されたアクションにリダイレクト。
---Return RedirectToAction("Index")

--Return RedirectToRoute
---ルート名とパラメータ値を引数とし、適切なルーティングフレンドリなURLへリダイレクト
---RedirectToRoute("View Product", new { ProductName = <商品名> }); 

**画面遷移の方法 [#ycae9af6]
以下の方式が考えられる。

***POSTでView選択 or 画面遷移 [#tc702cd7]
-BeginFormに任意のController&Actionを指定する。
-POST遷移後、Actionの中でReturn View("Result") ヘルパ・メソッドを使用して画面遷移する。

***自ControllerにPOST後にView選択 or 画面遷移 [#qba5f1f4]
-BeginFormに自Controller&任意のActionを指定する。

-自ControllerにPOST後、任意のActionの中で
--View選択(Transfer的な)~
Return View("Result") ヘルパ・メソッドを使用して画面遷移する。
--画面遷移(Redirect)~
Return RedirectToAction ヘルパ・メソッドを使用して画面遷移する。

***例外的な遷移 [#nda50fd0]
-例外的にクライアントからGETで遷移するケースもある。
-Link, IFRAME, window.open, etc.

**URLと画面 [#p47f7c6e]
***View (1..*) <---> (1) Controller(スキャフォールディング)+ POST遷移 [#f5f1cb0f]
URLは
-Controllerにだけ対応する。
-Viewにまでは対応しない。

***View (1) <---> (1) Controller(ASPXライク)+ 自ControllerにPOST後に遷移 [#uaea1303]
URLは
-Controllerに対応する。
-Viewにまで対応する。

*フォルダ構成 [#c0d7785c]
**フォルダ分けの意味 [#f6c4f503]
-グルーピングのため。
-名前空間が分かれる。

**各フォルダについて [#k32c9ab6]
***App_Start [#s308455d]
-初期設定(起動時)を行うモジュールが配置される。
-例えば、RouteConfigはURLの設定を行う。

***Contents [#x1809e9f]
-CSSはココに置く。
-フォルダ構成は自由
-規定のものは変更しない(BundleConfigで使用しているため)。

***Scripts [#d30cbb78]
-Javascriptはココに置く。
-フォルダ構成は自由
-規定のものは変更しない(BundleConfigで使用しているため)。

***Models [#j9f85022]
-Modelはココに置く。
-フォルダ構成は自由

***Controllers [#i31b0bdb]
-Controllerはココに置く。
-フォルダ構成は自由(ただし、フォルダはURLに反映されない)

-種類
--EntityFramework~
EntityFrameworkを使用する場合に選択する。

--空~
Action→Index(既定のAction)が生成される。

--スキャフォールディング~
スキャフォールディングに対応したActionが生成される。

-Controllers.Action~
HTTPのGETもPOSTも処理できる(メソッド属性で制限できる)。

***Views [#w1a844a4]
-Viewはココに置く。

-Viewsの下位フォルダは作成できない。
--Controller名に対応するフォルダが自動的に生成される。
--補足:XXXXControllerXXXXという所がController名

-規定のページ
--_ViewStart.cshtml
---規定の設定をする、個別に上書き(変更)可能。
---規定では、Layoutに_Layout.cshtmlを設定している。

--_Layout.cshtml
---規定のマスター・ページ(レイアウト・ページ)
---Sharedの_Layout.cshtml(規定のレイアウト)

***Area [#re760150]
なお、Areaを作るとViewsも含めたサブシステム単位のフォルダ分割ができる。~
以下、App_Startのマップルートが追加されるような感じ。

*情報の持ち回り・状態管理方式 [#i6db0cb0]
**Viewstate [#s3a7d336]
利用不可能(必要であれば、自前で実装する必要がある)

**Hidden [#o0afdc6f]
Formの定義・分割が可能なため、持ち回りも共通化困難。

*チェック処理方式 [#hc015ceb]
**クライアント [#i39f251f]
JavaScriptでのチェック

**サーバ [#k1290bb8]
Action内でのチェック

**モデルにチェックコードを実装 [#k61bb861]
色々あってよく解らない。

-お楽しみはこれからだ!
--ASP.NET MVC RCの入力検証~
http://takepara.blogspot.jp/2009/02/aspnet-mvc-rc.html
--強力になったDefaultModelBinder~
http://takepara.blogspot.jp/2009/02/defaultmodelbinder.html
--DataAnnotationsだけでの入力検証の盲点~
http://takepara.blogspot.jp/2009/02/dataannotations.html

-こんなこともできるもよう(Entity Frameworkが必要)。
--ASP.NET MVC 3における検証まわりの改善点 (3-4):CodeZine~
http://codezine.jp/article/detail/6176?p=3
--ASP.NET MVC 4 ことはじめ(5)モデルと足場 - アーキテクチャをスマートに。~
http://d.hatena.ne.jp/architect-wat/20130512/1368360044

*脆弱性 [#jd31de6d]
**サニタイジング [#m59baf7f]
-HTMLヘルパーを使用すれば自動。
-Response.Writeの場合は自前。

**リクエスト検証 [#ra245005]
-requestValidationModeをMVCでも利用可能。~
http://stackoverflow.com/questions/6206540/what-does-requestvalidationmode-2-0-actually-do


トップ   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS