このチュートリアル シリーズでは、ASP.NET Web フォーム プロジェクトでモデル バインドを使用する基本的な側面について説明します。 モデル バインドを使用すると、データ ソース オブジェクト (ObjectDataSource や SqlDataSource など) を扱うよりも、データの対話が簡単になります。 このシリーズは入門資料から始まり、後のチュートリアルでより高度な概念に移行します。
モデル バインド パターンは、任意のデータ アクセス テクノロジで動作します。 このチュートリアルでは Entity Framework を使用しますが、最も身近なデータ アクセス テクノロジを使用できます。 GridView、ListView、DetailsView、FormView コントロールなどのデータ バインド サーバー コントロールから、データの選択、更新、削除、および作成に使用するメソッドの名前を指定します。 このチュートリアルでは、SelectMethod の値を指定します。
そのメソッド内で、データを取得するためのロジックを指定します。 次のチュートリアルでは、UpdateMethod、DeleteMethod、InsertMethod の値を設定します。
完全なプロジェクトは、C# または Visual Basic で ダウンロード できます。 ダウンロード可能なコードは、Visual Studio 2012 以降で動作します。 このチュートリアルで示す Visual Studio 2017 テンプレートとは若干異なる Visual Studio 2012 テンプレートを使用します。
このチュートリアルでは、Visual Studio でアプリケーションを実行します。 また、ホスティング プロバイダーにアプリケーションをデプロイし、インターネット経由で利用できるようにすることもできます。 Microsoft は、最大 10 個の Web サイトに対して無料の Web ホスティングを提供しています。
無料の Azure 試用版アカウント。 Azure App Service Web Apps に Visual Studio Web プロジェクトをデプロイする方法については、Visual Studio シリーズを 使用した ASP.NET Web デプロイ に関するページを参照してください。 このチュートリアルでは、Entity Framework Code First Migrations を使用して SQL Server データベースを Azure SQL Database にデプロイする方法についても説明します。チュートリアルで使用するソフトウェアのバージョン
- Microsoft Visual Studio 2017 または Microsoft Visual Studio Community 2017
このチュートリアルは Visual Studio 2012 と Visual Studio 2013 でも動作しますが、ユーザー インターフェイスとプロジェクト テンプレートにはいくつかの違いがあります。
作成するもの
このチュートリアルでは、次のことについて説明します。
- コースに登録されている学生を含む大学を反映するデータ オブジェクトを作成する
- オブジェクトからデータベース テーブルをビルドする
- データベースにテスト データを設定する
- Web フォームでデータを表示する
プロジェクトを作成する
Visual Studio 2017 で、ContosoUniversityModelBinding という ASP.NET Web アプリケーション (.NET Framework) プロジェクトを作成します。
[OK] を選択. テンプレートを選択するダイアログ ボックスが表示されます。
Web フォーム テンプレートを選択します。
必要に応じて、認証を [個々のユーザー アカウント] に変更します。
[ OK] を 選択してプロジェクトを作成します。
サイトの外観を変更する
サイトの外観をカスタマイズするには、いくつかの変更を加えます。
Site.Master ファイルを開きます。
タイトルを変更して、マイ ASP.NET アプリケーションではなく Contoso University を表示します。
<title><%: Page.Title %> - Contoso University</title>ヘッダー テキストを アプリケーション名 から Contoso University に変更します。
<div class="navbar-header"> <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse"> <span class="icon-bar"></span> <span class="icon-bar"></span> <span class="icon-bar"></span> </button> <a class="navbar-brand" runat="server" href="~/">Contoso University</a> </div>ナビゲーション ヘッダー リンクをサイトの適切なリンクに変更します。
[バージョン情報] と [連絡先] のリンクを削除し、代わりに学生ページへのリンクを作成します。
<ul class="nav navbar-nav"> <li><a runat="server" href="~/">Home</a></li> <li><a runat="server" href="~/Students">Students</a></li> </ul>Site.Master を保存します。
学生データを表示する Web フォームを追加する
ソリューション エクスプローラーでプロジェクトを右クリックし、[追加] を選択し、[新しい項目] を選択します。
[ 新しい項目の追加 ] ダイアログ ボックス で、マスター ページ テンプレートを含む Web フォーム を選択し、 Students.aspx名前を付けます。
[] を選択し、[] を追加します。
Web フォームのマスター ページで、 Site.Master を選択します。
[OK] を選択.
データ モデルを追加する
Models フォルダーに 、UniversityModels.csという名前のクラス を追加します。
[ モデル] を右クリックし、[ 追加]、[ 新しい項目] の順に選択します。 [新しい項目の追加] ダイアログ ボックスが表示されます。
左側のナビゲーション メニューから[ コード]、[ クラス]の順に選択します。
クラスに UniversityModels.cs 名前を付け、[ 追加] を選択します。
このファイルでは、次のように、
SchoolContext、Student、Enrollment、およびCourseクラスを定義します。using System; using System.Collections.Generic; using System.Data.Entity; using System.ComponentModel.DataAnnotations; namespace ContosoUniversityModelBinding.Models { public class SchoolContext : DbContext { public DbSet<Student> Students { get; set; } public DbSet<Enrollment> Enrollments { get; set; } public DbSet<Course> Courses { get; set; } } public class Student { [Key, Display(Name = "ID")] [ScaffoldColumn(false)] public int StudentID { get; set; } [Required, StringLength(40), Display(Name="Last Name")] public string LastName { get; set; } [Required, StringLength(20), Display(Name = "First Name")] public string FirstName { get; set; } [EnumDataType(typeof(AcademicYear)), Display(Name = "Academic Year")] public AcademicYear Year { get; set; } public virtual ICollection<Enrollment> Enrollments { get; set; } } public class Enrollment { [Key] public int EnrollmentID { get; set; } public int CourseID { get; set; } public int StudentID { get; set; } public decimal? Grade { get; set; } public virtual Course Course { get; set; } public virtual Student Student { get; set; } } public class Course { [Key] public int CourseID { get; set; } public string Title { get; set; } public int Credits { get; set; } public virtual ICollection<Enrollment> Enrollments { get; set; } } public enum AcademicYear { Freshman, Sophomore, Junior, Senior } }SchoolContextクラスは、データベース接続とデータの変更を管理するDbContextから派生します。Studentクラスで、FirstName、LastName、およびYearプロパティに適用される属性に注目してください。 このチュートリアルでは、これらの属性をデータ検証に使用します。 コードを簡略化するために、これらのプロパティのみがデータ検証属性でマークされます。 実際のプロジェクトでは、検証を必要とするすべてのプロパティに検証属性を適用します。UniversityModels.cs保存します。
クラスに基づいてデータベースを設定する
このチュートリアルでは 、Code First Migrations を使用してオブジェクトとデータベース テーブルを作成します。 これらのテーブルには、学生とそのコースに関する情報が格納されます。
[ ツール>NuGet パッケージ マネージャー>Package Manager コンソール] を選択します。
パッケージ マネージャー コンソールで、次のコマンドを実行します。
enable-migrations -ContextTypeName ContosoUniversityModelBinding.Models.SchoolContextコマンドが正常に完了すると、移行が有効になっていることを示すメッセージが表示されます。
Configuration.csという名前 の ファイルが作成されていることに注意してください。
ConfigurationクラスにはSeedメソッドがあり、データベース テーブルにテスト データを事前に設定できます。
データベースを事前にデータ入力する
Configuration.csを開きます。
Seedメソッドに次のコードを追加します。 また、using名前空間のContosoUniversityModelBinding. Modelsステートメントを追加します。namespace ContosoUniversityModelBinding.Migrations { using System; using System.Data.Entity; using System.Data.Entity.Migrations; using System.Linq; using ContosoUniversityModelBinding.Models; internal sealed class Configuration : DbMigrationsConfiguration<SchoolContext> { public Configuration() { AutomaticMigrationsEnabled = false; } protected override void Seed(SchoolContext context) { context.Students.AddOrUpdate( new Student { FirstName = "Carson", LastName = "Alexander", Year = AcademicYear.Freshman }, new Student { FirstName = "Meredith", LastName = "Alonso", Year = AcademicYear.Freshman }, new Student { FirstName = "Arturo", LastName = "Anand", Year = AcademicYear.Sophomore }, new Student { FirstName = "Gytis", LastName = "Barzdukas", Year = AcademicYear.Sophomore }, new Student { FirstName = "Yan", LastName = "Li", Year = AcademicYear.Junior }, new Student { FirstName = "Peggy", LastName = "Justice", Year = AcademicYear.Junior }, new Student { FirstName = "Laura", LastName = "Norman", Year = AcademicYear.Senior }, new Student { FirstName = "Nino", LastName = "Olivetto", Year = AcademicYear.Senior } ); context.SaveChanges(); context.Courses.AddOrUpdate( new Course { Title = "Chemistry", Credits = 3 }, new Course { Title = "Microeconomics", Credits = 3 }, new Course { Title = "Macroeconomics", Credits = 3 }, new Course { Title = "Calculus", Credits = 4 }, new Course { Title = "Trigonometry", Credits = 4 }, new Course { Title = "Composition", Credits = 3 }, new Course { Title = "Literature", Credits = 4 } ); context.SaveChanges(); context.Enrollments.AddOrUpdate( new Enrollment { StudentID = 1, CourseID = 1, Grade = 1 }, new Enrollment { StudentID = 1, CourseID = 2, Grade = 3 }, new Enrollment { StudentID = 1, CourseID = 3, Grade = 1 }, new Enrollment { StudentID = 2, CourseID = 4, Grade = 2 }, new Enrollment { StudentID = 2, CourseID = 5, Grade = 4 }, new Enrollment { StudentID = 2, CourseID = 6, Grade = 4 }, new Enrollment { StudentID = 3, CourseID = 1 }, new Enrollment { StudentID = 4, CourseID = 1 }, new Enrollment { StudentID = 4, CourseID = 2, Grade = 4 }, new Enrollment { StudentID = 5, CourseID = 3, Grade = 3 }, new Enrollment { StudentID = 6, CourseID = 4 }, new Enrollment { StudentID = 7, CourseID = 5, Grade = 2 } ); context.SaveChanges(); } } }Configuration.cs保存します。
パッケージ マネージャー コンソールで、 コマンド add-migration initial を実行します。
コマンド update-database を実行します。
このコマンドの実行時に例外が発生した場合、
StudentID値とCourseID値がSeedメソッドの値と異なる場合があります。 これらのデータベース テーブルを開き、StudentIDとCourseIDの既存の値を見つけます。 これらの値をコードに追加して、Enrollmentsテーブルをシード処理します。
GridView コントロールを追加する
入力されたデータベースのデータを使用して、そのデータを取得し表示する準備が整いました。
Students.aspxを開きます。
MainContentプレースホルダーを見つけます。 そのプレースホルダー内に、このコードを含む GridView コントロールを追加します。<asp:Content ID="Content1" ContentPlaceHolderID="MainContent" runat="server"> <asp:GridView runat="server" ID="studentsGrid" ItemType="ContosoUniversityModelBinding.Models.Student" DataKeyNames="StudentID" SelectMethod="studentsGrid_GetData" AutoGenerateColumns="false"> <Columns> <asp:DynamicField DataField="StudentID" /> <asp:DynamicField DataField="LastName" /> <asp:DynamicField DataField="FirstName" /> <asp:DynamicField DataField="Year" /> <asp:TemplateField HeaderText="Total Credits"> <ItemTemplate> <asp:Label Text="<%# Item.Enrollments.Sum(en => en.Course.Credits) %>" runat="server" /> </ItemTemplate> </asp:TemplateField> </Columns> </asp:GridView> </asp:Content>考慮事項:
GridView 要素の
SelectMethodプロパティに設定されている値に注目してください。 この値は、次の手順で作成する GridView データの取得に使用するメソッドを指定します。ItemTypeプロパティは、先ほど作成したStudentクラスに設定されます。 この設定を使用すると、マークアップのクラス プロパティを参照できます。 たとえば、StudentクラスにはEnrollmentsという名前のコレクションがあります。Item.Enrollmentsを使用してコレクションを取得し、LINQ 構文を使用して各学生の登録済みクレジットの合計を取得できます。
Students.aspx保存します。
データを取得するコードを追加する
Students.aspxのコードビハインド ファイルで、指定されたSelectMethodの値用のメソッドを追加します。
Students.aspx.csを開きます。
usingおよびContosoUniversityModelBinding. Models名前空間のSystem.Data.Entityステートメントを追加します。using ContosoUniversityModelBinding.Models; using System.Data.Entity;SelectMethodに指定したメソッドを追加します。public IQueryable<Student> studentsGrid_GetData() { SchoolContext db = new SchoolContext(); var query = db.Students.Include(s => s.Enrollments.Select(e => e.Course)); return query; }Include句を使用すると、クエリのパフォーマンスが向上しますが、必須ではありません。Include句がないと、遅延読み込みを使用してデータが取得されます。これには、関連するデータが取得されるたびにデータベースに個別のクエリを送信する必要があります。Include句では、イーガーロードを使用してデータが取得されます。つまり、1回のデータベースクエリですべての関連データが取得されます。 関連するデータを使用しない場合、より多くのデータが取得されるため、一括読み込みの効率は低下します。 ただし、この場合、一括読み込みでは、関連するデータがレコードごとに表示されるため、最適なパフォーマンスが得られます。関連データを読み込む場合のパフォーマンスに関する考慮事項の詳細については、「関連 データの遅延読み込み、一括読み込み、明示的読み込み 」セクションの「 ASP.NET MVC アプリケーションの Entity Framework を使用した関連データの読み取 り」を参照してください。
既定では、データはキーとしてマークされたプロパティの値で並べ替えられます。
OrderBy句を追加して、別の並べ替え値を指定できます。 この例では、既定のStudentIDプロパティを使用して並べ替えを行います。 データの 並べ替え、ページング、およびフィルター処理 に関する記事では、ユーザーは並べ替えの列を選択できます。Students.aspx.cs保存します。
アプリケーションを実行する
Web アプリケーション (F5) を実行し、[ 学生 ] ページに移動します。次の内容が表示されます。
モデル バインド メソッドの自動生成
このチュートリアル シリーズを使用する場合は、チュートリアルからプロジェクトにコードをコピーするだけです。 ただし、この方法の欠点の 1 つは、モデル バインド メソッドのコードを自動的に生成するために Visual Studio によって提供される機能に気付かない可能性があることです。 独自のプロジェクトで作業する場合、コードの自動生成によって時間を節約し、操作を実装する方法を理解するのに役立ちます。 このセクションでは、コード生成の自動機能について説明します。 このセクションは情報提供のみを行うものであり、プロジェクトに実装する必要があるコードは含まれていません。
マークアップ コードで SelectMethod、 UpdateMethod、 InsertMethod、または DeleteMethod プロパティの値を設定する場合は、[ 新しいメソッドの作成 ] オプションを選択できます。
Visual Studio は、適切なシグネチャを使用して分離コード内にメソッドを作成するだけでなく、操作を実行する実装コードも生成します。 自動コード生成機能を使用する前に最初に ItemType プロパティを設定した場合、生成されたコードはその型を操作に使用します。 たとえば、 UpdateMethod プロパティを設定すると、次のコードが自動的に生成されます。
// The id parameter name should match the DataKeyNames value set on the control
public void studentsGrid_UpdateItem(int id)
{
ContosoUniversityModelBinding.Models.Student item = null;
// Load the item here, e.g. item = MyDataLayer.Find(id);
if (item == null)
{
// The item wasn't found
ModelState.AddModelError("", String.Format("Item with id {0} was not found", id));
return;
}
TryUpdateModel(item);
if (ModelState.IsValid)
{
// Save changes here, e.g. MyDataLayer.SaveChanges();
}
}
ここでも、このコードをプロジェクトに追加する必要はありません。 次のチュートリアルでは、新しいデータを更新、削除、追加するためのメソッドを実装します。
概要
このチュートリアルでは、データ モデル クラスを作成し、それらのクラスからデータベースを生成しました。 データベース テーブルにテスト データを入力しました。 モデル バインドを使用してデータベースからデータを取得し、GridView にデータを表示しました。
このシリーズの次の チュートリアル では、データの更新、削除、作成を有効にします。