本文所有的東西都是在dot Net Core 1.1環境+VS2017保證測試通過。
本文接着上次文章接着寫的,不了解上篇文章的可能看着有點吃力。我盡量讓大家都能看懂。這是上篇文章的連接http://www.cnblogs.com/qulianqing/p/6745409.html。請大家先看一下,心里大致有個了解,然后看這篇博客就容易了。
這里說一下實現的步驟:1. 新建一個ASP dot Net MVC項目,在這里我的項目名為TestAPI
2. 在項目的根目錄下添加一個文件夾 名字為Models
3. 在Models文件夾下添加一個Users.cs 類 下面是代碼 和上篇博客的Users.cs一樣 (主要是為了傳輸數據方便)

1 public class Users 2 { 3 [Key] 4 public int ID { get; set; } 5 public string name { get; set; } 6 public string pwd { get; set; } 7 }
4.在右鍵點擊controllers文件夾 選擇添加-->控制器 在彈出的對話框中選擇 mimial Dependencies 之后等待完成。(這里說一下上篇博客有朋友說
選擇 mimial Dependencies會出現錯誤,我今天又試了一遍,還是沒有問題,如果說你的也有問題的話那就選擇full Dependencies)
mini)
5.再次右鍵點擊Controllers文件夾 選擇添加 ->控制器 在彈出的對話框中選擇 第三個,也就是下邊高亮的那一個 點擊添加按鈕
6.點擊添加按鈕之后,又會出現一個對話框,在對話框中選擇點擊模型的下拉框,選擇Uses.cs 。在數據上下文項點擊右邊的那個加號,在彈出的對話框中,選將名稱更改為Users,最后記得視圖的三個選項都要勾選。點擊添加 就完成了。
7.刪除不必要的東西 (1)刪除Views下邊的整個Home文件夾里邊的東西,(2)刪除整個Data文件夾,及內部東西,(3)刪除Controllers文 件夾下的HomeController.cs (4) 打開appsettings.json文件夾 ,刪除ConnectionStrings項及其內容,
(5)打開Startup.cs文件 刪除EF框架自動添加的服務 在ConfigureServices這個方法里邊, 這個字符串 services.AddDbContext<UsesContext>options=>options.UseSqlServer(Configuration.GetConnectionString("*****")));
(6)打開Contollers文件夾下的UserController.cs文件,刪除下邊的系統為我們生成的大部分代碼,刪除完之后就剩下這些

1 public class UsersController : Controller 2 { 3 // GET: Users 4 public async Task<IActionResult> Index() 5 { 6 7 } 8 // GET: Users/Details/5 9 public async Task<IActionResult> Details(int? id) 10 { 11 12 } 13 // GET: Users/Create 14 public IActionResult Create() 15 { 16 17 } 18 // POST: Users/Create 19 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 20 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 21 [HttpPost] 22 [ValidateAntiForgeryToken] 23 public async Task<IActionResult> Create([Bind("ID,name,pwd")] Users users) 24 { 25 26 } 27 // GET: Users/Edit/5 28 public async Task<IActionResult> Edit(int? id) 29 { 30 31 } 32 // POST: Users/Edit/5 33 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 34 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 35 [HttpPost] 36 [ValidateAntiForgeryToken] 37 public async Task<IActionResult> Edit(int id, [Bind("ID,name,pwd")] Users users) 38 { 39 40 } 41 // GET: Users/Delete/5 42 public async Task<IActionResult> Delete(int? id) 43 { 44 45 } 46 47 // POST: Users/Delete/5 48 [HttpPost, ActionName("Delete")] 49 [ValidateAntiForgeryToken] 50 public async Task<IActionResult> DeleteConfirmed(int id) 51 { 52 53 } 54 55 }
進行到這里我們的基礎環境就搭建完畢了,我們這里只用系統為我們生成的View 其他的都不用要,在這里我們的Views文件夾下的Users文件夾的東西我們沒有動
二、接下來重點來了
我們要在Controllers調用我們上次寫的WebAPI
首先我們依次從index到Create到Update 到Delete依次為大家詳解(最后附完整的代碼,如果代碼閱讀能力強的同學,可以直接跳到最后閱讀全部的代碼)
准備工作,首先我們聲明兩個全局變量,具體用途在注釋中已經說明
1 //這個baseURL是我的webApi的地址 2 private static string baseURL = "http://localhost:56853/api/users"; 3 //用於存放所有的用戶 4 private static IList<Users> _context;
構造函數 獲取所有的用戶信息就是把數據存在 _context 中 方便查找
1 public UsersController() 2 { 3 //實例化對象 4 _context = new List<Users>(); 5 //獲取所有的用戶的信息 6 _context = GetAllUserList(); 7 8 }
在這里我取數據的使用用的是HttpClient取的遠程的API數據,由於取的是JSon字符串數組,我要把它轉化為JSon數組,然后再通過JSonConvert進行每一個對象的轉化

1 /// <summary> 2 /// 獲取所有用戶的List 3 /// </summary> 4 private IList<Users> GetAllUserList() 5 { 6 IList<Users> userslist = new List<Users>(); 7 var JsonString = GetALLUserInfoFromAPI(); 8 JArray UsersArray = JArray.Parse(JsonString); 9 for (int i = 0; i < UsersArray.Count; i++) 10 { 11 userslist.Add(StringConvertToUser(UsersArray[i].ToString())); 12 } 13 return userslist; 14 }

1 /// <summary> 2 /// 通過api獲取所有的用戶的信息 3 /// </summary> 4 /// <returns>JSON String</returns> 5 private string GetALLUserInfoFromAPI() 6 { 7 HttpClient client = new HttpClient(); 8 var con = client.GetStringAsync(baseURL); 9 return con.Result; 10 }

1 /// <summary> 2 /// 將Json對象的字符串轉化為users對象 3 /// </summary> 4 /// <param name="JsonString">json對象的字符串</param> 5 /// <returns>Users對象</returns> 6 private Users StringConvertToUser(string JsonString) 7 { 8 return JsonConvert.DeserializeObject<Users>(JsonString); 9 }
1.index 界面是用來顯示數據的。通過上邊的操作,我們已經把所有的數據存到 _context 變量中去了,所以在Index中我們只需要調用就可以了。
1 public async Task<IActionResult> Index() 2 { 3 return View(_context); 4 }
運行結果:
2.接下來我們接着說Create和Rdit和Delete 由於Create和Edit都是向服務器提交數據的,Delete向遠程API路由一個ID就結束了。這里我原本准備全文都用HttpClient的可是HttpClient的PostAsync方法實在是不會用,昨天搞了一天都沒有結果,於是下邊的我換成了WebRequest,我把他們提取到一個方法里了,具體看下邊的代碼。尤其是我下邊注釋的行代碼,不然瀏覽器會報415讓你摸不着頭腦,這個是我自己試出來的,可能會有更好的方法吧。只是我還不知道。
1 /// <summary> 2 /// 處理數據 3 /// </summary> 4 /// <param name="Data">User實體類</param> 5 /// <param name="Url">遠程API的URL</param> 6 /// <param name="RequestMethod">請求的方法</param> 7 /// <returns></returns> 8 private async Task<string> HandleData(Users Data, string Url, string RequestMethod) 9 { 10 string UsersJson = UsersConvertToJson(Data); 11 var request = WebRequest.CreateHttp(Url); 12 request.Accept = "application/json"; 13 //下邊這行不設置會出現無法識別mediaType 415 這個錯誤 14 request.ContentType = "application/json"; 15 request.Method = RequestMethod; 16 //向request提交數據 17 using (StreamWriter writer = new StreamWriter(await request.GetRequestStreamAsync())) 18 { 19 writer.Write(UsersJson); 20 } 21 //獲取響應 22 var reponse = await request.GetResponseAsync(); 23 //返回響應數據 24 using (StreamReader reader = new StreamReader(reponse.GetResponseStream())) 25 { 26 return reader.ReadToEnd(); 27 } 28 }

1 private string UsersConvertToJson(Users u) 2 { 3 return JsonConvert.SerializeObject(u); 4 }
具體用法 Create

1 /// <summary> 2 /// 傳遞數據到遠程API的數據庫中 3 /// </summary> 4 /// <param name="u"></param> 5 /// <returns></returns> 6 private async Task<string> CreateAsync(Users u) 7 { 8 string url = baseURL; 9 string requestMethod = "post"; 10 return await HandleData(u, url, requestMethod); 11 } 12 13 14 15 // GET: Users/Create 16 public IActionResult Create() 17 { 18 return View(); 19 } 20 21 // POST: Users/Create 22 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 23 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 24 [HttpPost] 25 [ValidateAntiForgeryToken] 26 public async Task<IActionResult> Create([Bind("ID,name,pwd")] Users users) 27 { 28 if (ModelState.IsValid) 29 { 30 31 await CreateAsync(users); 32 return RedirectToAction("Index"); 33 } 34 return View(); 35 }
具體用法 Edit

1 private async Task<string> UpdateAsync(Users u) 2 { 3 string url = baseURL + @"/" + u.ID; 4 string requestMethod = "put"; 5 return await HandleData(u, url, requestMethod); 6 } 7 8 9 10 // GET: Users/Edit/5 11 public async Task<IActionResult> Edit(int? id) 12 { 13 if (id == null) 14 { 15 return BadRequest(); 16 } 17 var users = _context.FirstOrDefault(u => u.ID == id); 18 if (users == null) 19 { 20 return NotFound(); 21 } 22 return View(users); 23 } 24 25 // POST: Users/Edit/5 26 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 27 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 28 [HttpPost] 29 [ValidateAntiForgeryToken] 30 public async Task<IActionResult> Edit(int id, [Bind("ID,name,pwd")] Users users) 31 { 32 33 if (ModelState.IsValid) 34 { 35 if (id != users.ID) 36 { 37 return BadRequest(); 38 } 39 try 40 { 41 await UpdateAsync(users); 42 return RedirectToAction("Index"); 43 } 44 catch 45 { 46 if (UsersExist(users.ID)) 47 { 48 return NotFound(); 49 } 50 throw; 51 } 52 53 } 54 return View(); 55 }

1 private bool UsersExist(int iD) 2 { 3 return _context.Any(u => u.ID == iD); 4 }
具體用法 Delete

1 private async Task<string> DeleteAsync(Users u) 2 { 3 string url = baseURL + @"/" + u.ID; 4 string requestMethod = "delete"; 5 return await HandleData(u, url, requestMethod); 6 } 7 8 9 10 // GET: Users/Delete/5 11 public async Task<IActionResult> Delete(int? id) 12 { 13 if (id == null) 14 { 15 return BadRequest(); 16 } 17 var users = _context.FirstOrDefault(u => u.ID == id); 18 if (users == null) 19 { 20 return NotFound(); 21 } 22 23 return View(users); 24 } 25 26 // POST: Users/Delete/5 27 [HttpPost, ActionName("Delete")] 28 [ValidateAntiForgeryToken] 29 public async Task<IActionResult> DeleteConfirmed(int id) 30 { 31 var users = _context.SingleOrDefault(u => u.ID == id); 32 await DeleteAsync(users); 33 return RedirectToAction("Index"); 34 }
到這里調用遠程API的東西都完成了,我在這里完善了一下 Details這個View

1 // GET: Users/Details/5 2 public async Task<IActionResult> Details(int? id) 3 { 4 if (id == null) 5 { 6 return BadRequest(); 7 } 8 var users = _context.FirstOrDefault(u => u.ID == id); 9 if (users == null) 10 { 11 return NotFound(); 12 } 13 return View(users); 14 }
下邊這是測試結果
到這里全部都完成了,並且測試完畢
這是UsersContellers.cs 類的全部代碼

1 using Microsoft.AspNetCore.Mvc; 2 using Newtonsoft.Json; 3 using Newtonsoft.Json.Linq; 4 using System; 5 using System.Collections.Generic; 6 using System.IO; 7 using System.Linq; 8 using System.Net; 9 using System.Net.Http; 10 using System.Net.Http.Headers; 11 using System.Text; 12 using System.Threading.Tasks; 13 using TestAPI.Models; 14 15 namespace TestAPI.Controllers 16 { 17 public class UsersController : Controller 18 { 19 #region 成員變量 20 //這個baseURL是我的webApi的地址 21 private static string baseURL = "http://localhost:56853/api/users"; 22 //用於存放所有的用戶 23 private static IList<Users> _context; 24 25 #endregion 26 27 #region 構造函數 28 public UsersController() 29 { 30 //實例化對象 31 _context = new List<Users>(); 32 //獲取所有的用戶的信息 33 _context = GetAllUserList(); 34 35 } 36 37 #endregion 38 39 #region 類內方法 40 41 42 /// https://docs.microsoft.com/en-us/aspnet/web-api/overview/advanced/calling-a-web-api-from-a-net-client 43 44 45 46 /// <summary> 47 /// 通過api獲取所有的用戶的信息 48 /// </summary> 49 /// <returns>JSON String</returns> 50 private string GetALLUserInfoFromAPI() 51 { 52 HttpClient client = new HttpClient(); 53 var con = client.GetStringAsync(baseURL); 54 return con.Result; 55 } 56 57 private string UsersConvertToJson(Users u) 58 { 59 return JsonConvert.SerializeObject(u); 60 } 61 /// <summary> 62 /// 傳遞數據到遠程API的數據庫中 63 /// </summary> 64 /// <param name="u"></param> 65 /// <returns></returns> 66 private async Task<string> CreateAsync(Users u) 67 { 68 string url = baseURL; 69 string requestMethod = "post"; 70 return await HandleData(u, url, requestMethod); 71 } 72 73 private async Task<string> UpdateAsync(Users u) 74 { 75 string url = baseURL + @"/" + u.ID; 76 string requestMethod = "put"; 77 return await HandleData(u, url, requestMethod); 78 } 79 /// <summary> 80 /// 處理數據 81 /// </summary> 82 /// <param name="Data">User實體類</param> 83 /// <param name="Url">遠程API的URL</param> 84 /// <param name="RequestMethod">請求的方法</param> 85 /// <returns></returns> 86 private async Task<string> HandleData(Users Data, string Url, string RequestMethod) 87 { 88 string UsersJson = UsersConvertToJson(Data); 89 var request = WebRequest.CreateHttp(Url); 90 request.Accept = "application/json"; 91 //下邊這行不設置會出現無法識別mediaType 415 這個錯誤 92 request.ContentType = "application/json"; 93 request.Method = RequestMethod; 94 //向request提交數據 95 using (StreamWriter writer = new StreamWriter(await request.GetRequestStreamAsync())) 96 { 97 writer.Write(UsersJson); 98 } 99 //獲取響應 100 var reponse = await request.GetResponseAsync(); 101 //返回響應數據 102 using (StreamReader reader = new StreamReader(reponse.GetResponseStream())) 103 { 104 return reader.ReadToEnd(); 105 } 106 } 107 private async Task<string> DeleteAsync(Users u) 108 { 109 string url = baseURL + @"/" + u.ID; 110 string requestMethod = "delete"; 111 return await HandleData(u, url, requestMethod); 112 } 113 private bool UsersExist(int iD) 114 { 115 return _context.Any(u => u.ID == iD); 116 } 117 118 /// <summary> 119 /// 獲取所有用戶的List 120 /// </summary> 121 private IList<Users> GetAllUserList() 122 { 123 IList<Users> userslist = new List<Users>(); 124 var JsonString = GetALLUserInfoFromAPI(); 125 JArray UsersArray = JArray.Parse(JsonString); 126 for (int i = 0; i < UsersArray.Count; i++) 127 { 128 userslist.Add(StringConvertToUser(UsersArray[i].ToString())); 129 } 130 return userslist; 131 } 132 /// <summary> 133 /// 將Json對象的字符串轉化為users對象 134 /// </summary> 135 /// <param name="JsonString">json對象的字符串</param> 136 /// <returns>Users對象</returns> 137 private Users StringConvertToUser(string JsonString) 138 { 139 return JsonConvert.DeserializeObject<Users>(JsonString); 140 } 141 #endregion 142 143 #region Index 144 // GET: Users 145 public async Task<IActionResult> Index() 146 { 147 return View(_context); 148 } 149 150 151 152 #endregion 153 154 #region Details 155 156 // GET: Users/Details/5 157 public async Task<IActionResult> Details(int? id) 158 { 159 if (id == null) 160 { 161 return BadRequest(); 162 } 163 var users = _context.FirstOrDefault(u => u.ID == id); 164 if (users == null) 165 { 166 return NotFound(); 167 } 168 return View(users); 169 } 170 171 #endregion 172 173 #region Create 174 175 // GET: Users/Create 176 public IActionResult Create() 177 { 178 return View(); 179 } 180 181 // POST: Users/Create 182 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 183 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 184 [HttpPost] 185 [ValidateAntiForgeryToken] 186 public async Task<IActionResult> Create([Bind("ID,name,pwd")] Users users) 187 { 188 if (ModelState.IsValid) 189 { 190 191 await CreateAsync(users); 192 return RedirectToAction("Index"); 193 } 194 return View(); 195 } 196 197 #endregion 198 199 #region Edit 200 201 // GET: Users/Edit/5 202 public async Task<IActionResult> Edit(int? id) 203 { 204 if (id == null) 205 { 206 return BadRequest(); 207 } 208 var users = _context.FirstOrDefault(u => u.ID == id); 209 if (users == null) 210 { 211 return NotFound(); 212 } 213 return View(users); 214 } 215 216 // POST: Users/Edit/5 217 // To protect from overposting attacks, please enable the specific properties you want to bind to, for 218 // more details see http://go.microsoft.com/fwlink/?LinkId=317598. 219 [HttpPost] 220 [ValidateAntiForgeryToken] 221 public async Task<IActionResult> Edit(int id, [Bind("ID,name,pwd")] Users users) 222 { 223 224 if (ModelState.IsValid) 225 { 226 if (id != users.ID) 227 { 228 return BadRequest(); 229 } 230 try 231 { 232 await UpdateAsync(users); 233 return RedirectToAction("Index"); 234 } 235 catch 236 { 237 if (UsersExist(users.ID)) 238 { 239 return NotFound(); 240 } 241 throw; 242 } 243 244 } 245 return View(); 246 } 247 248 249 #endregion 250 251 #region Delete 252 253 254 // GET: Users/Delete/5 255 public async Task<IActionResult> Delete(int? id) 256 { 257 if (id == null) 258 { 259 return BadRequest(); 260 } 261 var users = _context.FirstOrDefault(u => u.ID == id); 262 if (users == null) 263 { 264 return NotFound(); 265 } 266 267 return View(users); 268 } 269 270 // POST: Users/Delete/5 271 [HttpPost, ActionName("Delete")] 272 [ValidateAntiForgeryToken] 273 public async Task<IActionResult> DeleteConfirmed(int id) 274 { 275 var users = _context.SingleOrDefault(u => u.ID == id); 276 await DeleteAsync(users); 277 return RedirectToAction("Index"); 278 } 279 #endregion 280 281 } 282 }
這是git地址 https://github.com/1483523635/dotNetCoreAPIDemoTest
關於HttpClient的學習微軟官網上有一篇 https://docs.microsoft.com/en-us/aspnet/web-api/overview/advanced/calling-a-web-api-from-a-net-client 這個我看了一下時間是2014年的,昨天還能看今天就看不到了,可能是要更新吧
這是HttpClient的API說明 https://msdn.microsoft.com/en-us/library/system.net.http.httpclient(v=vs.118).aspx
關於HttpClient的PostAsync方法誰有好的用法,歡迎告訴我,讓我學習一下。