首先,寫這篇博文的目的是給未來自己看的,希望以后每天都讀一下,這樣就不會犯錯誤了。
前兩天,在開發項目的時候,寫一個功能,就是使用 Ajax 異步加載一些信息,這個在平常開發過程中,我們一般都會遇到,在 Controller 中寫一個異步 Action 方法,使用 HttpGet 或 HttpPost,然后在方法中處理一些操作,最后返回拼接的 Html 字符串,View 中的操作就是寫一個 Ajax 腳本進行調用,貼一點示例代碼:
Controller 中的 Action 方法:
public class CommonAjaxController : Controller
{
[HttpGet]
public async Task<ContentResult> GetAjaxInfo(int para)
{
var item = await .......GetInfo(para);
StringBuilder resultHtml = new StringBuilder();
foreach (var item in news)
{
resultHtml.Append("< li >< a href = \"/n/\{item.Url}/\" target = \"_blank\" >\{item.Title}< / a > < / li >");
}
return Content(resultHtml.ToString());
}
}
View 中的 Ajax 腳本:
$(function () {
$.ajax({
url: '/CommonAjax/GetAjaxInfo',
type: 'GET',
datatype: "json",
contentType: "application/json; charset=utf-8",
data: { para: para },
success: function (data) {
if (data) {
$("#div_id").html(data);
}
}
});
});
什么問題呢?就是我不管怎么調試,最后 div_id 中填充的 data 始終是字符串格式,也就是沒有轉換的 html 格式,說實話,這個問題,我當時“掙扎”了很久,我以為是 Controller 中的 Action 只能返回格式化的字符串,然后就各種搜索關鍵字,花了很長時間,最后也沒有一個結果,因為是通過 Ajax 腳本填充的,不是通過 ViewData 之類的東西傳遞,所以你不能直接使用 View 中的 Html.Raw() 進行 Html 格式轉換,所以轉換操作必須在 Action 方法中,但關鍵是,沒有這之類的解決方式,這個問題,大概花了我幾個小時的時候,我隱約記得之前這樣寫的方式是沒問題的,為此我有查看了下之前項目中相類似的代碼,確實沒什么問題,為此我更郁悶了。。。
哎,往事不堪回首,最后發現,原因出在我“復制粘貼”的 Html 字符串上,不知道為什么,我是使用瀏覽器的查看元素功能,然后復制現有的 Html 代碼,拷貝在 VS2015 中,當時沒怎么注意,你可以仔細看下 GetAjaxInfo 中的 Html 字符,會發現中間莫名多了一個“空格”,哎,哎,哎,當我發現是這個問題的時候,我的第一想法是:窗戶在哪里???我要跳下去。
當然,一個問題場景證明不了自己有多“二”,就在今天,又是類似的問題,哎!
我使用 ASP.NET 5,在 Action 中給 ViewData 賦一個值,然后在 View 中進行展示,Html 中訪問 ViewData 沒有什么問題,但是當我在 JS 腳本中訪問,就出現了問題,示例代碼:
Controller 中的 Action 方法:
public async Task<IActionResult> About()
{
using (var context=new BloggingContext())
{
ViewData["data"] = await context.Blogs.FirstOrDefaultAsync();
}
//ViewData["data"] = await Task<string>.Run(() => { return "data"; });
//ViewData["data"] = "data";
ViewBag.Message = "Your application description page. XISHUAI";
return View();
}
View 代碼
@{
ViewBag.Title = "About";
}
<h2>@ViewBag.Title.</h2>
<h3>@ViewBag.Message</h3>
<h1>@ViewData["data"]</h1>
<p>Use this area to provide additional information.</p>
<script type="text/javascript">
alert(@ViewData["data"])
window.onload = function () {
alert(@ViewData["data"]);
}
</script>
上面是我后來的測試代碼,可能有些亂,但寫出來都是有原因的,這一次我鉆什么“洞”了呢?答案是:async 的 Action 只能給 ViewData 賦值,然后 JS 腳本才能訪問到。聽起來可能有點暈,為什么我會這樣認為呢?因為之前我寫類似的代碼,ViewData["data"] 是通過 await 獲取訪問到的數據,而今天我寫的 Action 方法,ViewData["data"] 是同步賦值的,但這種寫法就不行,所以我把“嫌疑”放在了它身上,然后有去搜索“async Action ViewData”之類的關鍵詞,但卻沒搜到什么有“價值”的東西,現在想想,能搜到的話,就真的奇怪了,為了重現這個“問題”,我又搞了個測試項目進行操作,最后發現同步賦值的 JS 也不能訪問了,當時做到這,真是要死的感覺,然后花了兩個小時進行再思考,沒辦法,一點頭緒都沒有,然后肚子餓了,下班吃東西,在路上,以至于吃飯的時候,我都在思考這個問題,在想到底是哪方面出了問題?最后,還是一點頭緒都沒有。
回到住的地方,倒了杯茶,然后再“思考”,不知道抽了什么筋,把 alert(@ViewData["data"]) 改成 alert("@ViewData["data"]"),你猜怎么著???居然訪問到了,我的天哪???自己到底是有多”二“啊,哎!
總結下自己寫代碼的方式,或者是尋找解決問題的方式:
- 一定要細心。
- 反復 CodeReview 自己寫的代碼,不要過于“相信”自己。
- 如果陷在一個問題,試著跳出這個問題,散散步,或者喝一杯茶,也許就會發現問題所在了。
謹記謹記。。。
文章列表