ASP.NET Core MVC处理数据
在这个系列的前一部分中,我们使用一些模拟数据构建了一个ASP.NET Core MVC应用程序。在这一部分中,我们将探讨如何将应用程序连接到数据库并处理数据。
我们将使用EF Core Code-First方法,这是在开始新项目时处理数据的首选方式。
我们强烈建议访问本系列的完整导航:ASP.NET Core MVC系列。
要下载本文的源代码,请访问:在ASP.NET Core MVC中处理数据的源代码。
首先,我们需要创建一个模型。然后,我们将对模型进行脚手架,以生成与模型的创建、读取、更新和删除(CRUD)操作相对应的控制器操作方法和视图。在此之后,我们将使用EF Core迁移来创建数据库。最后,我们将用一些初始数据填充数据库。
一旦完成这些步骤,我们就会有一个能够连接到数据库的工作中的ASP.NET Core MVC应用程序。
在ASP.NET MVC中创建Model
让我们创建Book模型,这是一个与我们在本系列前一部分中创建的对象类似的对象,只是没有Authors属性:
public class Book
{
public int Id { get; set; }
[Display(Name = "Book Title")]
[Required]
public string Title { get; set; }
public string Genre { get; set; }
[DataType(DataType.Currency)]
[Range(1, 100)]
public decimal Price { get; set; }
[Display(Name = "Publish Date")]
[DataType(DataType.Date)]
public DateTime PublishDate { get; set; }
}
这个模型将作为构建项目的基础。
脚手架Model
下一步是对模型进行脚手架操作,以生成控制器操作方法和视图。脚手架将创建一个新的、功能完备的控制器。
右击 Controllers
文件夹 > 添加
> 新的脚手架项
:
在添加脚手架
对话框中,我们将选择使用Entity Framework的MVC控制器与视图
> 添加
:
让我们完成添加控制器对话框:
- Model类: Book (BookStoreWithData.Models)
- 数据上下文类: 请悬着 + 图标.
- 保留模型名称 (BookStoreWithData.Models.BookStoreWithDataContext)
- 点击添加
添加数据上下文:
- Views: 保持每个选项的勾选状态
- Controller Name: 保持默认的 BooksController
- 点击Add
Visual Studio创建了:
一个Entity Framework Core
数据库上下文类(Data/BookStoreWithDataContext.cs
)
一个控制器(Controllers/BooksController.cs
)
用于创建、删除、详情、编辑和索引页面的Razor视图文件(Views/Books/*.cshtml
)
这个自动创建数据库上下文、CRUD(创建、读取、更新和删除)操作方法和视图的过程被称为脚手架。
脚手架是可选的,您也可以手动完成整个过程。在不需要或不适用脚手架的情况下,我们可以控制整个创建过程。
数据迁移
迁移自动基于我们的模型创建数据库。
首先,让我们在包管理器控制台中运行以下命令:
Add-Migration BookStoreWithData.Data.BookStoreWithDataContext
这将创建支持迁移的类。
现在,我们需要将这些更改应用到数据库。在此之前,请确保在appsettings.json
文件中指定的连接字符串指向我们想要连接的数据库服务器。默认情况下,脚手架过程会使它指向SQL Server Express本地数据库。
为了将更改应用到数据库,让我们运行以下命令:
PM> update-database
这将根据我们的模型更新数据库。
我们在《ASP.NET Core Web API与EF Core Code-First方法》一文中详细介绍了这种方法。
一旦我们完成所有步骤,就会根据模型定义创建数据库和列。我们的数据库表和列将如下所示:
我们已经成功地使用EF Core Code-First迁移从我们的代码创建了数据库。
数据填充
下一步是进行数据填充。数据填充允许我们在创建数据库时提供初始数据。
正如上面链接的文章中提到的,让我们在BookContext
中重写OnModelCreating
方法:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Book>().HasData(new Book
{
Id = 1,
Title = "Book1",
Genre = "Genre1",
Price = 20,
PublishDate = new DateTime(2012, 4, 23)
}, new Book
{
Id = 2,
Title = "Book2",
Genre = "Genre2",
Price = 30,
PublishDate = new DateTime(2008, 6, 13)
});
}
一旦我们应用迁移并更新数据库,我们可以看到数据库表已经用我们提供的种子数据进行了更新:
ASP.NET Core MVC
现在,让我们运行这个应用。
列表页面
让我们导航到/Books
;
这将调用控制器中的Index()
方法:
我们可以看到,索引页面显示了数据库中所有书籍的列表。在网格上还有编辑、查看详情和删除书籍的链接。在顶部,还有一个创建新书的链接。
Create 页面
让我们点击Create new
链接
点击链接将带我们进入 /Books/Create
。这将通过GET请求调用控制器中的Create()
方法:
这个页面可以用来创建新书。在输入书籍详细信息并点击创建按钮后,将调用带有[HttpPost]
属性的Create()
方法。这将是一个POST
请求,表单数据将被提交。
底部有一个链接,可以返回到列表页面。
Detials页面
在列表页面上,如果我们点击任何一本书的详情链接,我们将被带到 /Books/Details/{id}
这将调用控制器中的Details()
方法:
这个页面展示了一本书的详细信息。在详情页面上,我们可以看到用于编辑和返回列表的按钮。
Edit页面
如果我们从这里或列表页面点击编辑链接,它将带我们到 /Book/Edit/{id}
这将调用控制器中第一个仅支持GET
请求的Edit()
方法:
点击保存按钮将调用带有[HttpPost]
属性的Edit()
方法。这将使用我们在页面上提供的值更新记录。根据请求类型,MVC
决定调用哪个Edit
方法。
对于编辑记录,PUT
请求是更合适的方法。但在这里,自动生成的代码使用了POST
方法,这也可以使用。然而,当我们自己创建控制器方法时,推荐的做法是使用PUT
方法来更新记录。
Delete页面
最后,如果我们在列表页面点击删除链接,我们将被导航到 /Book/Delete/{id}
这将调用控制器中第一个仅支持GET
请求的Delete()
方法。
这是删除确认页面:
一旦我们通过点击删除按钮确认删除,带有 [HttpPost] 属性的 DeleteConfirmed() 方法将被调用。这将从数据库中删除记录。
代码解释
通过遵循上述步骤,我们已经成功创建了一个具有数据库集成的完全功能的应用程序。现在,让我们来看看自动生成的代码,并尝试理解应用程序是如何运作的。
Visual Studio作为脚手架的一部分生成了以下文件:
DB Context
数据库上下文(DB Context)文件负责促进与数据库的所有通信。要了解更多关于DBContext的详细信息,请查看我们的文章:Context Class and the Database Connection。
本应用的上下文文件在脚手架的一部分中自动生成,位于Data/BookStoreWithDataContext
。
Controller
在Controllers/BooksController.cs
生成了一个控制器文件,其中包含与CRUD
操作相对应的操作方法。如果我们查看BooksController
文件,我们可以看到以下操作方法:
GET api/books
- 列出所有书籍。
GET api/books/details/{id}
- 获取一本书的详细信息。
GET api/books/create
- 显示初始创建书籍页面。
POST api/books/create
- 创建一本新书。
GET api/books/edit/{id}
- 显示初始编辑页面。
POST api/books/edit/{id}
- 更新一本书的详细信息。
GET api/books/delete/{id}
- 显示删除确认页面。
POST api/books/delete/{id} - 删除一本书。
控制器中的操作方法访问上下文以执行数据操作。
例如,在Details()
方法中,我们可以看到通过访问上下文获取书籍记录:
var book = await _context.Book
.FirstOrDefaultAsync(m => m.Id == id);
同样,在带有[HttpPost]
属性的Create()
方法中,我们访问上下文以添加新记录:
_context.Add(book);
理想情况下,控制器不应直接访问上下文文件。相反,我们应该在中间引入一个仓储层。我们在其他文章的一个部分中详细解释了仓库模式:实现仓库模式。
Razor view文件
在Views/Books
文件夹内,我们可以看到为Create
、Delete
、Details
、Edit
和Index
方法创建了视图页面。这些视图页面基于razor
语法。我们将在后续的文章中详细讨论使用razor
语法创建视图页面。
总结
在这篇文章中,我们研究了以下内容:
创建模型。
对模型进行脚手架操作以生成上下文、控制器和视图文件。
使用迁移创建数据库。
数据填充。
脚手架自动生成的代码。
在本系列的下一部分中,我们将探讨使用razor语法创建视图页面。
发表回复