1 起個頭
html
不少95後的程序員沒有搞明白MVC,須要多練習才行。程序員
MVC實際上不是設計模式,而是架構模式/體系結構模式,體系結構是老稱呼了,如今基本上都叫架構了。正則表達式
模型-視圖-控制器 (MVC) 體系結構模式將應用分紅 3 個主要組件:模型 (M)、視圖 (V) 和控制器 (C)。 MVC 模式有助於建立比傳統單片應用更易於測試和更新的應用。 數據庫
模型 (M):表示應用數據的類。 模型類使用驗證邏輯來對該數據強制實施業務規則。 一般,模型對象檢索模型狀態並將其存儲在數據庫中。json
視圖 (V):視圖是顯示應用用戶界面 (UI) 的組件。 此 UI 一般會顯示模型數據。設計模式
控制器 (C):處理瀏覽器請求的類。 它們檢索模型數據並調用返回響應的視圖模板。 在 MVC 應用中,視圖僅顯示信息;控制器處理並響應用戶輸入和交互。 例如,控制器處理路由數據和查詢字符串值,並將這些值傳遞給模型。 該模型可以使用這些值查詢數據庫。瀏覽器
1.1 MVC優勢服務器
l MVC 模式可幫助建立分隔不一樣應用特性(輸入邏輯、業務邏輯和 UI 邏輯)的應用,同時讓這些元素之間實現鬆散耦合。 網絡
l 該模式可指定應用中每種邏輯的位置。 UI 邏輯位於視圖中。 輸入邏輯位於控制器中。 業務邏輯位於模型中。架構
l 這種隔離有助於控制構建應用時的複雜程度,由於它可用於一次處理一個實現特性,而不影響其餘特性的代碼。 例如,處理視圖代碼時沒必要依賴業務邏輯代碼
1.2 建立一個MVC項目
1.3 新增一個控制器
1.4 新增HTTP終結點調用
控制器中的每一個 public 方法都可做爲 HTTP 終結點調用。
HTTP 終結點是 Web 應用程序中可定向的 URL(例如 https://localhost:44399/EdisonTest ),其中結合了所用的協議HTTPS 、TCP 端口等 Web 服務器的網絡位置 localhost:44399 ,以及目標 URI EdisonTest。
2 進一步
2.1 路由
MVC 根據入站 URL 調用控制器類(及其中的操做方法)。 MVC 所用的默認 URL 路由邏輯使用以下格式來肯定調用的代碼:
/[Controller]/[ActionName]/[Parameters]
在 Startup.cs 文件的 Configure 方法中設置路由格式。
若是瀏覽到應用且不提供任何 URL 段,它將默認爲左邊紅線行中指定的「Home」控制器和「Index」方法。
第一個 URL 段決定要運行的控制器類。 localhost: 44399映射到 EdisonTestController 類。
第二個 URL段決定類上的操做方法。 localhost:44399/EdisonTest/GetOwnerName 將觸發 EdisonTestController 類的GetOwnerName 運行。 請注意,只需瀏覽到 localhost:xxxx/EdisonTest ,而GetOwnerName 方法默認調用。 緣由是 GetOwnerName 是默認方法,若是未顯式指定方法名稱,則將在控制器上調用它。
第三個URL 段 ( id ) 針對的是路由數據。
測試:
2.2 增長參數
修改代碼,將一些參數信息從 URL 傳遞到控制器。
l 使用 C# 可選參數功能指示,未爲 numTimes 參數傳遞值時該參數默認爲 1。
l 使用 HtmlEncoder.Default.Encode 防止惡意輸入(即 JavaScript)損害應用。
l 在 $"I am Edison.Feng, you are {name}. Number of Times:{numTimes}"中使用內插字符串。
測試:
2.3 參數路由
參數也能夠做爲路由:
測試:
問題1:路由的第三部分怎麼解析的?
問題2:路由的第三部分的問號表示什麼?
2.4 增長一個View視圖
目的:消除前面的硬編碼,不直接返回HTML文件內容,而是返回視圖對象:
l 使用 Razor 視圖文件來順利封裝爲客戶端生成 HTML 響應。
l 使用 Razor 建立視圖模板文件。 基於 Razor 的模板具備「.cshtml」文件擴展名。 它們提供了一種巧妙的方法來使用 C# 建立 HTML 輸出。
l 右鍵單擊「Views」文件夾,而後單擊「添加」>「新文件夾」,並將文件夾命名爲「EdisonTest」。
l 右鍵單擊「Views/EdisonTest」文件夾,而後單擊「添加」>「新項」。
l 在「添加新項 - MvcMovie」對話框中
l 在右上角的搜索框中,輸入「視圖」
l 選擇「Razor 視圖」
l 保持「名稱」框的值:getownername.cshtml。
l 選擇「添加」
修改視圖文件getownername.cshtml:
修改默認路由,Startup.cs:
修改控制器,增長一個get方法:
測試:
2.5 給視圖傳點數據
使用ViewData在視圖和控制器之間傳遞數據:
(1)修改控制器
(2)修改視圖
(3)測試
3 數據庫操做
3.1 將真實的數據存在數據庫中,並取出來
l 結合 Entity Framework Core (EF Core) 使用這些類來處理數據庫。 EF Core 是對象關係映射 (ORM) 框架,能夠簡化須要編寫的數據訪問代碼。
l 要建立的模型類稱爲 POCO 類(源自「簡單傳統 CLR 對象」),由於它們與 EF Core 沒有任何依賴關係。 它們只定義將存儲在數據庫中的數據的屬性。
3.2 新增一個模型Model
選中Models文件夾,右鍵菜單......
3.3 增長屬性
數據庫須要 Id 字段以獲取主鍵。
[DataType(DataType.Date)] :DataType 屬性指定數據的類型 ( Date )。
經過此特性:
用戶無需在數據字段中輸入時間信息。
僅顯示日期,而非時間信息。
DataAnnotations
3.4 「腳手架」工具
l 腳手架:Scaffold,或者翻譯爲基架
l .net core經過腳手架工具(Scaffolded Item)生成頁面,用於對模型Model執行建立、讀取、更新和刪除 (CRUD) 操做
3.5 使用EF Core的視圖
l 模型類:選擇剛剛建好的模型類Movie
l 數據Context類:新建,默認命名爲MvcMovie1Context
l 視圖:默認
l 控制器名稱:默認
3.6 「搭建基架」過程自動建立哪些文件?
l EF Core數據庫Context類
l 控制器
l Razor視圖文件(CRUD)
l Create
l Index
l Details
l Edit
l Delete
3.7 EF Core遷移功能
不使用EFCore遷移功能,只「搭建基架」則程序運行提示SqlException:不能打開數據庫
l 初始遷移
l 進入PMC(即程序包管理控制檯)
l 輸入Add-Migration Initial並回車,生成用於建立初始數據庫架構的代碼,數據庫架構基於在 MvcMovieContext 類中指定的模型。Initial 參數是遷移名稱
l 輸入Update-Database並回車,在 Migrations/{time-stamp}_InitialCreate.cs 文件中運行 Up 方法。Migrations/{time-stamp}_InitialCreate.cs用於建立數據庫
l 依賴注入
l 腳手架工具已經把數據上下文類MvcMovie1Context注入到容器services中
l AddDbContext 指定數據庫和鏈接字符串
l =>是Lambda運算符
l 數據上下文類爲 Movie 模型協調 EF Core 功能
l (建立、讀取、更新、刪除等)
l 實體集DbSet對應數據庫的數據表
l 經過調用 DbContextOptions 對象中的一個方法將鏈接字符串名稱傳遞到上下文。
l 進行本地開發時, ASP.NET Core 配置系統 在 appsettings.json 文件中讀取數據庫鏈接字符串。
3.8 CRUD: Details
l Details方法
l 將強類型模型對象傳遞給視圖:憑藉此強類型方法可更好地對代碼進行編譯時檢查
l FirstOrDefaultAsync返回知足條件的第一個元素,或者在不知足條件下的默認元素
l m => m.Id == id 元素的ID等於給定的ID
l Details.cshtml
l @model MvcMovie1.Models.Movie
l 經過將 @model 語句包括在視圖文件的頂端,
l 能夠指定視圖指望的對象類型
3.9 CRUD: Index
l Index方法
l ToListAsync異步建立一個List
l Index.cshtml
3.10 CRUD: Edit
3.11 CRUD: Create
3.12 CRUD: Delete
4 擴展更多的
4.1 數據庫鏈接字符串
l DbContextOptionsBuilder.UseSqlServer
l IConfiguration.GetConnectionString
l AppSettings.json
3.2 SQL Server Express LocalDB
l SQL Server對象資源管理器
l 視圖設計器
l 查看數據
4.3 數據庫種子
l 數據庫種子:沒有任何數據時初始化數據
l 修改Main方法
l 增長SeedData類
測試:
l 刪除數據庫的數據以後測試,如圖。
l 刷新數據庫後查看數據
4.4 修改顯示列表
l 修改列Title。
l 修改列數據顯示格式
4.5 按標題搜索
l 給Index操做增長一個參數。
l s => s.Title.Contains() 代碼是 Lambda 表達式
l Lambda 表達式在基於方法的 LINQ 查詢中用做標準查詢運算符方法的參數,如 Where 方法或 Contains,在對 LINQ 查詢進行定義或經過調用方法(如 Where、Contains 或 OrderBy)進行修改前不會被執行。這意味着表達式的計算會延遲,直到真正循環訪問其實現的值或者調用 ToListAsync 方法爲止。
l Contains 方法在數據庫上運行,而不是在 C# 代碼中運行
l 在cshtml中綁定兩個input標籤。
l <form> 標記使用表單標記幫助器,提交表單時篩選器字符串會發布到電影控制器的 Index 操做。
l 增長一個POST Index操做
l 測試
l 再也不出現過濾頁面
l 修改index.cshtml
l 測試:可以轉到過濾頁面
4.6 按流派搜索
l 修改index操做方法
l System.linq命名空間,有兩個靜態類:Queryable和Enumerable
l IQueryable:where條件接收表達式,延遲執行
l IEnumerable:where條件接收一個謂詞表達式(委託),當即執行
l SelectList是SelectListItem的集合,和<select>標籤聯合使用
l 修改index.cshtml
l 最上面一句改成:@model MvcMovie1.Models.GenreViewModel
l 在Title: <input......上面增長:
l <select asp-for="MovieGenre" asp-items="Model.Genres">
l <option value="">all</option>
l </select>
l 修改Title: <input......爲Title: <input type="text" asp-for="searchString">
l 把model.Title改成model.Movies[0].Title
l 把model.ReleaseDate改成model.Movies[0].ReleaseDate
l 把model.Genre改成model.Movies[0].Genre
l 把model.Price改成model.Movies[0].Price
l 把@foreach (var item in Model) {改成@foreach (var item in Model.Movies) {
4.7 增長新屬性
l 修改Models/Movie.cs
l 修改控制器
l 更新Create方法的[Bind]屬性
l 更新Edit方法的[Bind]屬性
l 修改Views/Movies/Index.cshtml
l 更新 /Views/Movies/Create.cshtml
l 更新 /Views/Movies/Edit.cshtml
l 更新 SeedData 類
l 更新數據庫
l 讓EF Core重建數據庫
l 對數據庫直接修改表結構
l 使用Code First遷移(將新字段添加到模型,將新字段遷移到數據庫)
l 進入PMC
l 執行Add-Migration Rating
l Add-Migration 命令會通知遷移框架使用當前 Movie DB 架構檢查當前 Movie 模型,並建立必要的代碼,將 DB 遷移到新模型。
l 名稱「Rating」是任意的,用於對遷移文件進行命名。 爲遷移文件使用有意義的名稱是有幫助的。
l 執行Update-Database
l 若是刪除 DB 中的全部記錄,初始化方法會設定 DB 種子,並將包括 Rating 字段。
4.8 預校驗
以下圖,有以下幾種標註:
l Required
l 必需,缺乏則返回400錯誤
l MinimumLength
l 最小長度
l RegularExpression
l 正則表達式
l Range
l 範圍
l StringLength
l 字串長度
l DataType
l 數據類型
l 須要禁用 jQuery 日期驗證才能使用具備 DateTime 的 Range 特性
DRY原則是很是有用的: