索引:html
目錄索引git
Create a web API with ASP.NET Core MVC and Visual Studio for Windowsgithub
在windows上用vs與asp.net core mvc 建立一個 web api 程序web
2017-5-24 8 分鐘閱讀時長 數據庫
本文內容json
1.Overview小程序
綜述windows
2.Create the projectapi
建立一個項目瀏覽器
3.Register the database context
註冊db上下文
添加一個控制器
開始要作的事兒
6.Implement the other CRUD operations
實現 CRUD 操做
By Rick Anderson and Mike Wasson
In this tutorial, you’ll build a web API for managing a list of "to-do" items. You won’t build a UI.
在本篇教程中,咱們將建立一個用於管理「to-do」列表web api 小程序,他不須要界面。
There are 3 versions of this tutorial:
Windows+vs 建立
Apple+vs 建立
vs code 跨平臺建立
Overview
概覽
Here is the API that you’ll create:
下面是將要建立的api 列表
API |
Description |
Request body |
Response body |
GET /api/todo |
Get all to-do items 獲取全部 to-do 數據 |
None |
Array of to-do items |
GET /api/todo/{id} |
Get an item by ID 獲取一條 to-do 數據 |
None |
To-do item |
POST /api/todo |
Add a new item 新增一條 to-do 數據 |
To-do item |
To-do item |
PUT /api/todo/{id} |
Update an existing item 修改一條 to-do 數據 |
To-do item |
None |
DELETE /api/todo/{id} |
Delete an item 刪除一條 to-do 數據 |
None |
None |
The following diagram shows the basic design of the app.
下圖展現了這個程序的基本設計
不管 api 的調用方是 手機app仍是桌面瀏覽器,咱們不用寫一個客戶端。
use Postman or curl to test the app.
咱們能夠用 postman 或者 curl 進行接口調用測試
在你的應用中用model來表明一個數據對象。在本例中,只有一個 to-do 數據model,
represented as C# classes, also know as Plain Old C# Object (POCOs).
Models 表明了 項目中的數據類。
Controller 是一個用來處理 HTTP 請求與相應的對象類。這個app中只有一個 controller。
爲保持教程的簡單性,app 中不使用持久化的db,而是將 to-do 數據存在內存數據庫中。
database.
Create the project
建立項目
From Visual Studio, select File menu, > New > Project.
在 vs 中選擇 新建項目菜單
Select the ASP.NET Core Web Application (.NET Core) project template. Name the project TodoApi and select OK.
選擇以下圖中的項目模板,並確認。
In the New ASP.NET Core Web Application (.NET Core) - TodoApi dialog, select the Web API template. Select OK.
在模板類型彈框中選擇 Web API 模板,並確認。
Do not select Enable Docker Support.
不要選擇 Docker 支持
Launch the app
運行 app
In Visual Studio, press CTRL+F5 to launch the app. Visual Studio launches a browser and navigates
在 vs 中,按下 CTRL+F5 快捷鍵,啓動app。VS 將啓動一個瀏覽器,並
to http://localhost:port/api/values, where port is a randomly chosen port number. If you're using Chrome, Edge or Firefox,
導航到 http://localhost:port/api/values 這個地址,端口是隨機選擇的。若是你用的是 Chrome、Edge、Firefox 瀏覽器,
the ValuesController data will be displayed:
ValuesController 控制器中的數據將會以下顯示:
1 ["value1","value2"]
If you're using IE, you are prompted to open or save the values.json file.
若果你用的是 IE 瀏覽器,會提示你打開或保存 values.json 文件。
Add support for Entity Framework Core
添加 Entity Framework Core 的支持
Install the Entity Framework Core InMemory database provider. This database provider allows Entity Framework Core to be used
安裝 Entity Framework Core InMemory 數據提供程序。這個數據庫提供程序容許 EF 使用
with an in-memory database.
內存中的數據庫。
Edit the TodoApi.csproj file. In Solution Explorer, right-click the project. Select Edit TodoApi.csproj. In the ItemGroup element,
編輯 TodoApi.csproj 文件。在解決方案資源管理器中,郵件點擊項目,選擇 Edit TodoApi.csproj ,在 ItemGroup 節點中
add "Microsoft.EntityFrameworkCore.InMemory":
添加 Microsoft.EntityFrameworkCore.InMemory 。
1 <Project Sdk="Microsoft.NET.Sdk.Web"> 2 3 <PropertyGroup> 4 <TargetFramework>netcoreapp1.1</TargetFramework> 5 </PropertyGroup> 6 7 <ItemGroup> 8 <Folder Include="wwwroot\" /> 9 </ItemGroup> 10 <ItemGroup> 11 <PackageReference Include="Microsoft.ApplicationInsights.AspNetCore" Version="2.0.0" /> 12 <PackageReference Include="Microsoft.AspNetCore" Version="1.1.1" /> 13 <PackageReference Include="Microsoft.AspNetCore.Mvc" Version="1.1.2" /> 14 <PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="1.1.1" /> 15 <PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="1.1.1" /> 16 </ItemGroup> 17 <ItemGroup> 18 <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="1.0.0" /> 19 </ItemGroup> 20 21 </Project>
Add a model class
添加一個 model 數據類
A model is an object that represents the data in your application. In this case, the only model is a to-do item.
model 是一個用來描述並表現app中數據的類對象。在本例中,只有一個 to-do model.
Add a folder named "Models". In Solution Explorer, right-click the project. Select Add > New Folder. Name the folder Models.
添加一個 Models 文件夾。 在解決方案資源管理器中,右擊項目,選擇 Add > New Folder 。將文件夾命名爲 Models 。
Note: You can put model classes anywhere in your project, but the Models folder is used by convention.
注意:你能夠在項目中的任何位置建立 model 類,可是習慣上一般使用 Models 文件夾。
Add a TodoItem class. Right-click the Models folder and select Add > Class. Name the class TodoItemand select Add.
添加 TodoItem 類。在 Models 文件夾下,添加類。
Replace the generated code with:
使用下面的代碼替換 vs 自動生成的代碼:
1 namespace TodoApi.Models 2 3 { 4 5 public class TodoItem 6 7 { 8 9 public long Id { get; set; } 10 11 public string Name { get; set; } 12 13 public bool IsComplete { get; set; } 14 15 } 16 17 }
Create the database context
建立 db 上下文
The database context is the main class that coordinates Entity Framework functionality for a given data model. You create this class
database context 是EF 未提供數據model 功能的主類,有建立的這個上下文類
by deriving from the Microsoft.EntityFrameworkCore.DbContext class.
繼承自 Microsoft.EntityFrameworkCore.DbContext 類。
Add a TodoContext class. Right-click the Models folder and select Add > Class. Name the class TodoContext and select Add.
添加一個 TodoContext 類。添加以下代碼中的類:
1 using Microsoft.EntityFrameworkCore; 2 3 4 5 namespace TodoApi.Models 6 7 { 8 9 public class TodoContext : DbContext 10 11 { 12 13 public TodoContext(DbContextOptions<TodoContext> options) 14 15 : base(options) 16 17 { 18 19 } 20 21 22 23 public DbSet<TodoItem> TodoItems { get; set; } 24 25 26 27 } 28 29 }
Register the database context
註冊 db 上下文
In order to inject the database context into the controller, we need to register it with the dependency injection container. Register
爲了在控制器中注入 db context ,咱們須要在依賴注入容器中註冊一下。
the database context with the service container using the built-in support for dependency injection. Replace the contents of
註冊 db context 使用內建的依賴注入服務容器。將下面的代碼copy 到
the Startup.cs file with the following:
Startup.cs 文件中:
1 using Microsoft.AspNetCore.Builder; 2 3 using Microsoft.EntityFrameworkCore; 4 5 using Microsoft.Extensions.DependencyInjection; 6 7 using TodoApi.Models; 8 9 10 11 namespace TodoApi 12 13 { 14 15 public class Startup 16 17 { 18 19 public void ConfigureServices(IServiceCollection services) 20 21 { 22 23 services.AddDbContext<TodoContext>(opt => opt.UseInMemoryDatabase()); 24 25 services.AddMvc(); 26 27 } 28 29 30 31 public void Configure(IApplicationBuilder app) 32 33 { 34 35 app.UseMvc(); 36 37 } 38 39 } 40 41 }
The preceding code:
前述代碼:
移除咱們不須要的代碼
指定一個注入到服務容器中的 內存 db
Add a controller
添加一個控制器
In Solution Explorer, right-click the Controllers folder. Select Add > New Item. In the Add New Itemdialog, select the Web API
在解決方案資源管理器中,右擊 Controllers 文件夾,以下圖選擇 web api 模板
Controller Class template. Name the class TodoController.
添加 TodoController 類。
Replace the generated code with the following:
在類中添加下面的代碼:
1 using System.Collections.Generic; 2 3 using Microsoft.AspNetCore.Mvc; 4 5 using TodoApi.Models; 6 7 using System.Linq; 8 9 10 11 namespace TodoApi.Controllers 12 13 { 14 15 [Route("api/[controller]")] 16 17 public class TodoController : Controller 18 19 { 20 21 private readonly TodoContext _context; 22 23 24 25 public TodoController(TodoContext context) 26 27 { 28 29 _context = context; 30 31 32 33 if (_context.TodoItems.Count() == 0) 34 35 { 36 37 _context.TodoItems.Add(new TodoItem { Name = "Item1" }); 38 39 _context.SaveChanges(); 40 41 } 42 43 } 44 45 } 46 47 }
The preceding code:
前述代碼:
定義一個空的控制器。在下面的部分中,咱們將添加方法來實現 api 。
構造函數經過依賴注入將 db context 注入到 控制器中。
context is used in each of the CRUD methods in the controller.
數據上下文將在控制器中的每一個crud方法中被使用。
在構造函數中將會向 內存db增長一條數據,當這條數據不存在時。
Getting to-do items
獲取 to-do 數據
To get to-do items, add the following methods to the TodoController class.
在 TodoController 中添加方法,以用於獲取 to-do 數據
1 [HttpGet] 2 3 public IEnumerable<TodoItem> GetAll() 4 5 { 6 7 return _context.TodoItems.ToList(); 8 9 } 10 11 12 13 [HttpGet("{id}", Name = "GetTodo")] 14 15 public IActionResult GetById(long id) 16 17 { 18 19 var item = _context.TodoItems.FirstOrDefault(t => t.Id == id); 20 21 if (item == null) 22 23 { 24 25 return NotFound(); 26 27 } 28 29 return new ObjectResult(item); 30 31 }
These methods implement the two GET methods:
下面的方法是獲取數據的方法:
Here is an example HTTP response for the GetAll method:
下面是 GetAll 方法的 HTTP 響應數據:
1 HTTP/1.1 200 OK 2 3 Content-Type: application/json; charset=utf-8 4 5 Server: Microsoft-IIS/10.0 6 7 Date: Thu, 18 Jun 2015 20:51:10 GMT 8 9 Content-Length: 82 10 11 12 13 [{"Key":"1", "Name":"Item1","IsComplete":false}]
Later in the tutorial I'll show how you can view the HTTP response using Postman or curl.
在本文的後面,我將展現使用 postman 與 curl 的 HTTP 響應報文。
Routing and URL paths
路由與URL路徑
The [HttpGet] attribute specifies an HTTP GET method. The URL path for each method is constructed as follows:
[HttpGet] 特性標記,指定了 HTTP GET 類型的請求動詞。每個方法的 URL 路徑的定義路徑結構以下:
在控制器的路由標記採起以下的字符串模板:
1 namespace TodoApi.Controllers 2 3 { 4 5 [Route("api/[controller]")] 6 7 public class TodoController : Controller 8 9 { 10 11 private readonly TodoContext _context;
用控制器的名字替換 [Controller] ,控制器的名字就是去除 "Controller" 結尾的字符串。例如,
sample, the controller class name is TodoController and the root name is "todo". ASP.NET Core routing is not case sensitive.
TodoController 的名字就是 todo 。asp.net core 的路由不區分大小寫。
若是 [HttpGet] 特性標記有一個路由模板,附加到路徑上。這個例子不使用模板。
doesn't use a template. See Attribute routing with Http[Verb] attributes for more information.
能夠查看 Attribute routing with Http[Verb] attributes已得到更多信息。
In the GetById method:
在 GetById 方法中
1 [HttpGet("{id}", Name = "GetTodo")] 2 3 public IActionResult GetById(long id)
"{id}" is a placeholder variable for the ID of the todo item. When GetById is invoked, it assigns the value of "{id}" in the URL to
"{id}" 是一個變量佔位符,這個變量就是 todo 的ID。當 GetById 方法被調用時,他將 URL 中的id的值分派給了方法的id
the method's id parameter.
參數上。
Name = "GetTodo" creates a named route and allows you to link to this route in an HTTP Response. I'll explain it with an example
Name = "GetTodo" 建立了一個命名路由並容許你連接到這個路由在HTTP 響應中。稍後,我會在一個示例中進行說明。
later. See Routing to Controller Actions for detailed information.
在 Routing to Controller Actions 中能夠查看更詳細的信息。
Return values
返回值
The GetAll method returns an IEnumerable. MVC automatically serializes the object to JSON and writes the JSON into the body
GetAll 方法返回一個 IEnumerable 類型。MVC 自動將其序列化爲json 並寫入響應體中。
of the response message. The response code for this method is 200, assuming there are no unhandled exceptions. (Unhandled
這個方法的http 響應碼是200 ,假設這裏沒有作異常處理,
exceptions are translated into 5xx errors.)
(未處理異常將被轉化爲 5xx 這類的錯誤碼)。
In contrast, the GetById method returns the more general IActionResult type, which represents a wide range of return
相比之下 GetById 返回普通的 IActionResult 類型,一種能夠描述更普遍的返回類型的類型。
types. GetById has two different return types:
GetById 方法有兩種不一樣的返回類型:
若是沒有找到id匹配的項,將由 NotFound 結束方法,此時返回 404 。
不然,將由 ObjectResult 結束方法,方法返回一個json值,而且狀態碼200.
Launch the app
運行app
In Visual Studio, press CTRL+F5 to launch the app. Visual Studio launches a browser and navigates
在vs中,按下CTRL+F5 啓動app。VS將啓動一個瀏覽器並導航到
to http://localhost:port/api/values, where port is a randomly chosen port number. If you're using Chrome, Edge or Firefox,
http://localhost:port/api/values 這個地址,端口被隨機選擇。若是你使用的是 Chrome, Edge or Firefox,
the data will be displayed. If you're using IE, IE will prompt to you open or save the values.json file. Navigate to the Todo controller
數據將直接展現出來,若是你用的是IE,將會提示打開或保存 values.json 文件。導航至 Todo 控制器
we just created http://localhost:port/api/todo.
咱們建立 http://localhost:port/api/todo 。
Implement the other CRUD operations
實現其它的CRUD操做
We'll add Create, Update, and Delete methods to the controller. These are variations on a theme, so I'll just show the code and
咱們將在控制器中添加 Create、Update、Delete 三個方法。這些都是同一種主題的不一樣類型表現而已,所以我只展現代碼而且
highlight the main differences. Build the project after adding or changing code.
高亮出主要的不一樣地方。
Create
1 [HttpPost] 2 3 public IActionResult Create([FromBody] TodoItem item) 4 5 { 6 7 if (item == null) 8 9 { 10 11 return BadRequest(); 12 13 } 14 15 16 17 _context.TodoItems.Add(item); 18 19 _context.SaveChanges(); 20 21 22 23 return CreatedAtRoute("GetTodo", new { id = item.Id }, item); 24 25 }
This is an HTTP POST method, indicated by the [HttpPost] attribute. The [FromBody] attribute tells MVC to get the value of the
這個方法指明瞭 [HttpPost] 標記是一個 HTTP POST 方法。[FromBody] 標記告訴MVC
to-do item from the body of the HTTP request.
從http 請求體中獲取item數據
The CreatedAtRoute method returns a 201 response, which is the standard response for an HTTP POST method that creates a
CreatedAtRoute 方法返回一個201響應碼,是對http post產生的一個標準的響應,表示
new resource on the server. CreatedAtRoute also adds a Location header to the response. The Location header specifies the URI
在服務器上建立了一條新數據。同時,也添加了一個重定向頭,這個重定向指向了
of the newly created to-do item. See 10.2.2 201 Created.
新建的這條 to-do 數據。
Use Postman to send a Create request
使用 postman 發送一個建立請求
選擇 post 爲要使用的HTTP方法
點擊 body 按鈕
選擇原始數據 按鈕
選擇 json 數據類型
在編輯框中,輸入下面的數據:
1 { 2 3 "name":"walk dog", 4 5 "isComplete":true 6 7 }
點擊 send 按鈕
You can use the Location header URI to access the resource you just created. Recall the GetById method created the "GetTodo" named route:
1 [HttpGet("{id}", Name = "GetTodo")] 2 3 public IActionResult GetById(long id)
Update
1 [HttpPut("{id}")] 2 3 public IActionResult Update(long id, [FromBody] TodoItem item) 4 5 { 6 7 if (item == null || item.Id != id) 8 9 { 10 11 return BadRequest(); 12 13 } 14 15 16 17 var todo = _context.TodoItems.FirstOrDefault(t => t.Id == id); 18 19 if (todo == null) 20 21 { 22 23 return NotFound(); 24 25 } 26 27 28 29 todo.IsComplete = item.IsComplete; 30 31 todo.Name = item.Name; 32 33 34 35 _context.TodoItems.Update(todo); 36 37 _context.SaveChanges(); 38 39 return new NoContentResult(); 40 41 }
Update is similar to Create, but uses HTTP PUT. The response is 204 (No Content). According to the HTTP spec, a PUT request
Update 與 Create 相似,此處省略。。。。。字。
requires the client to send the entire updated entity, not just the deltas. To support partial updates, use HTTP PATCH.
Delete
1 [HttpDelete("{id}")] 2 3 public IActionResult Delete(long id) 4 5 { 6 7 var todo = _context.TodoItems.First(t => t.Id == id); 8 9 if (todo == null) 10 11 { 12 13 return NotFound(); 14 15 } 16 17 18 19 _context.TodoItems.Remove(todo); 20 21 _context.SaveChanges(); 22 23 return new NoContentResult(); 24 25 }
The response is 204 (No Content).
Next steps
接下來的教程
蒙
2017-07-10 16:34 週一