8부. ASP.NET Core MVC 앱에 새 필드 추가
참고 항목
이 문서의 최신 버전은 아닙니다. 현재 릴리스는 이 문서의 .NET 9 버전을 참조 하세요.
Important
이 정보는 상업적으로 출시되기 전에 실질적으로 수정될 수 있는 시험판 제품과 관련이 있습니다. Microsoft는 여기에 제공된 정보에 대해 어떠한 명시적, 또는 묵시적인 보증을 하지 않습니다.
현재 릴리스는 이 문서의 .NET 9 버전을 참조 하세요.
작성자: Rick Anderson
이 섹션에서 는 Entity Framework 마이그레이션을 사용하여 다음을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF(Entity Framework)를 사용하여 모델 클래스에서 데이터베이스를 자동으로 만드는 경우:
- 데이터베이스의 스키마를 추적하기 위해 테이블이 데이터베이스에 추가됩니다.
- 데이터베이스가 생성된 모델 클래스와 동기화된 것으로 확인됩니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string? Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string? Rating { get; set; }
}
앱 빌드
Ctrl Shift B를+누릅니다.+
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<table class="table">
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies!)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
<a asp-action="Edit" asp-route-id="@item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="@item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="@item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
Rating
나머지 Create.cshtml
, 및 Delete.cshtml
Details.cshtml
Edit.cshtml
보기 템플릿에 속성을 추가합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Entity Framework 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Entity Framework 마이그레이션이 사용됩니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
패키지 관리자 콘솔에서 다음 명령을 입력합니다.
Add-Migration Rating
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
패키지 관리자 콘솔에서 다음 명령을 입력합니다.
Update-Database
Update-Database 명령은 적용되지 않은 마이그레이션에서 Up 메서드를 실행합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
이 섹션에서는 Entity Framework Code First 마이그레이션으로 다음 작업을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF Code First를 사용하여 자동으로 데이터베이스를 만들 경우 Code First는 다음 작업을 수행합니다.
- 데이터베이스 스키마를 추적하기 위해 데이터베이스에 테이블을 추가합니다.
- 데이터베이스가 생성된 모델 클래스와 동기화되어 있는지 확인합니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string? Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string? Rating { get; set; }
}
앱 빌드
Ctrl Shift B를+누릅니다.+
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<table class="table">
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies!)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
<a asp-action="Edit" asp-route-id="@item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="@item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="@item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
나머지 템플릿을 수정합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Code First 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Code First 마이그레이션을 사용합니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
PMC에서 다음 명령을 입력합니다.
Add-Migration Rating
Update-Database
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
이 섹션에서는 Entity Framework Code First 마이그레이션으로 다음 작업을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF Code First를 사용하여 자동으로 데이터베이스를 만들 경우 Code First는 다음 작업을 수행합니다.
- 데이터베이스 스키마를 추적하기 위해 데이터베이스에 테이블을 추가합니다.
- 데이터베이스가 생성된 모델 클래스와 동기화되어 있는지 확인합니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string? Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string? Rating { get; set; }
}
앱 빌드
Ctrl Shift B를+누릅니다.+
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<table class="table">
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies![0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies!)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
<a asp-action="Edit" asp-route-id="@item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="@item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="@item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
나머지 템플릿을 수정합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Code First 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Code First 마이그레이션을 사용합니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
PMC에서 다음 명령을 입력합니다.
Add-Migration Rating
Update-Database
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
이 섹션에서는 Entity Framework Code First 마이그레이션으로 다음 작업을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF Code First를 사용하여 자동으로 데이터베이스를 만들 경우 Code First는 다음 작업을 수행합니다.
- 데이터베이스 스키마를 추적하기 위해 데이터베이스에 테이블을 추가합니다.
- 데이터베이스가 생성된 모델 클래스와 동기화되어 있는지 확인합니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models
{
public class Movie
{
public int Id { get; set; }
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string? Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string? Rating { get; set; }
}
}
앱 빌드
Ctrl+Shift+B
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<table class="table">
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
<a asp-action="Edit" asp-route-id="@item.Id">Edit</a> |
<a asp-action="Details" asp-route-id="@item.Id">Details</a> |
<a asp-action="Delete" asp-route-id="@item.Id">Delete</a>
</td>
</tr>
}
</tbody>
</table>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
나머지 템플릿을 수정합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Code First 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Code First 마이그레이션을 사용합니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
PMC에서 다음 명령을 입력합니다.
Add-Migration Rating
Update-Database
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
이 섹션에서는 Entity Framework Code First 마이그레이션으로 다음 작업을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF Code First를 사용하여 자동으로 데이터베이스를 만들 경우 Code First는 다음 작업을 수행합니다.
- 데이터베이스 스키마를 추적하기 위해 데이터베이스에 테이블을 추가합니다.
- 데이터베이스가 생성된 모델 클래스와 동기화되어 있는지 확인합니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models
{
public class Movie
{
public int Id { get; set; }
public string Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string Rating { get; set; }
}
}
앱 빌드
Ctrl+Shift+B
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
나머지 템플릿을 수정합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Code First 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Code First 마이그레이션을 사용합니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
PMC에서 다음 명령을 입력합니다.
Add-Migration Rating
Update-Database
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
이 섹션에서는 Entity Framework Code First 마이그레이션으로 다음 작업을 수행합니다.
- 모델에 새 필드를 추가합니다.
- 새 필드를 데이터베이스로 마이그레이션합니다.
EF Code First를 사용하여 자동으로 데이터베이스를 만들 경우 Code First는 다음 작업을 수행합니다.
- 데이터베이스 스키마를 추적하기 위해 데이터베이스에 테이블을 추가합니다.
- 데이터베이스가 생성된 모델 클래스와 동기화되어 있는지 확인합니다. 동기화되어 있지 않은 경우 EF에서 예외를 throw합니다. 이렇게 하면 더 쉽게 일관성이 없는 데이터베이스/코드 문제를 찾을 수 있습니다.
영화 모델에 Rating 속성 추가
Models/Movie.cs
에 Rating
속성을 추가합니다.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models
{
public class Movie
{
public int Id { get; set; }
public string Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
public string Genre { get; set; }
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
public string Rating { get; set; }
}
}
앱 빌드
Ctrl+Shift+B
Movie
클래스에 새 필드를 추가했으므로 이 새 속성이 포함되도록 속성 바인딩 목록을 업데이트해야 합니다. MoviesController.cs
에서 Rating
속성을 포함하도록 Create
및 Edit
작업 메서드에 대한 [Bind]
특성을 업데이트합니다.
[Bind("Id,Title,ReleaseDate,Genre,Price,Rating")]
브라우저 보기에서 새 Rating
속성을 표시, 작성 및 편집하기 위해 보기 템플릿을 수정합니다.
/Views/Movies/Index.cshtml
파일을 편집하고 Rating
필드를 추가합니다.
<thead>
<tr>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Title)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].ReleaseDate)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Genre)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Price)
</th>
<th>
@Html.DisplayNameFor(model => model.Movies[0].Rating)
</th>
<th></th>
</tr>
</thead>
<tbody>
@foreach (var item in Model.Movies)
{
<tr>
<td>
@Html.DisplayFor(modelItem => item.Title)
</td>
<td>
@Html.DisplayFor(modelItem => item.ReleaseDate)
</td>
<td>
@Html.DisplayFor(modelItem => item.Genre)
</td>
<td>
@Html.DisplayFor(modelItem => item.Price)
</td>
<td>
@Html.DisplayFor(modelItem => item.Rating)
</td>
<td>
Rating
필드를 사용하여 /Views/Movies/Create.cshtml
을 업데이트합니다.
이전 "양식 그룹"을 복사/붙여넣기하고 intelliSense에서 필드를 업데이트하도록 할 수 있습니다. IntelliSense는 태그 도우미와 함께 작동합니다.
나머지 템플릿을 수정합니다.
새 열에 대한 값을 제공하도록 SeedData
클래스를 수정합니다. 아래에서 변경 예제를 볼 수 있지만 각 new Movie
마다 이 변경을 수행해야 합니다.
new Movie
{
Title = "When Harry Met Sally",
ReleaseDate = DateTime.Parse("1989-1-11"),
Genre = "Romantic Comedy",
Rating = "R",
Price = 7.99M
},
새 필드를 포함하도록 DB가 수정될 때까지 앱은 작동하지 않습니다. 지금 앱을 실행하면 SqlException
이 던져집니다.
SqlException: Invalid column name 'Rating'.
이 오류는 수정된 Movie 모델 클래스가 기존 데이터베이스의 Movie 테이블 스키마와 다르기 때문에 발생합니다. (데이터베이스 테이블에 Rating
열이 없습니다.)
이 오류를 해결할 수 있는 몇 가지 방법이 있습니다.
Entity Framework에서 새 모델 클래스 스키마에 따라 데이터베이스를 자동으로 삭제하고 다시 만들도록 합니다. 이 방법은 테스트 데이터베이스에서 활발한 개발을 수행할 때 개발 주기의 초기 단계에서 매우 편리하며 신속하게 모델 및 데이터베이스 스키마를 함께 개발할 수 있습니다. 그러나 단점은 데이터베이스에서 기존 데이터를 손실한다는 것입니다. 따라서 프로덕션 데이터베이스에서 이 방법을 사용하지 않으려 합니다. 테스트 데이터로 데이터베이스를 자동으로 시드하는 데 이니셜라이저를 사용하는 것은 종종 애플리케이션을 개발하는 효율적인 방법입니다. 이는 초기 개발과 SQLite를 사용할 때 좋은 방법입니다.
모델 클래스와 일치하도록 기존 데이터베이스의 스키마를 명시적으로 수정합니다. 이 방법의 장점은 데이터가 유지된다는 점입니다. 이러한 변경을 수동으로 수행하거나 데이터베이스 변경 스크립트를 만들어 수행할 수 있습니다.
Code First 마이그레이션을 사용하여 데이터베이스 스키마를 업데이트합니다.
이 자습서에서는 Code First 마이그레이션을 사용합니다.
도구 메뉴에서 NuGet 패키지 관리자 > 패키지 관리자 콘솔을 선택합니다.
PMC에서 다음 명령을 입력합니다.
Add-Migration Rating
Update-Database
Add-Migration
명령은 마이그레이션 프레임워크에서 현재 Movie
DB 스키마로 현재 Movie
모델을 검사하고 DB를 새 모델로 마이그레이션하는 데 필요한 코드를 만들도록 합니다.
"Rating" 이름은 임의로 지정되며 마이그레이션 파일의 이름을 지정하는 데 사용됩니다. 마이그레이션 파일에 의미 있는 이름을 사용하는 것이 좋습니다.
DB의 모든 레코드가 삭제되면 initialize 메서드가 DB를 시드하고 Rating
필드를 포함합니다.
앱을 실행하고 Rating
필드를 사용하여 영화를 생성, 편집, 표시할 수 있는지 확인합니다.
ASP.NET Core