ASP .Net Core Api生成靜態頁面的思路和方法
阿新 • • 發佈:2020-08-20
ASP .Net Core Api生成靜態頁面的思路和方法
在正常網站開發中,我們經常會用到靜態頁面,尤其是針對SEO開發的網站。關於靜態頁面或者靜態的網站的優勢,想必不用贅述了。
- 能夠提高訪問速度,增加使用者體驗。
- 有利於SEO搜尋引擎收錄(有人說沒有用了,不過目前來看,還是有用的)
- 靜態網頁有利於網站的穩定性(避免程式出現問題,頁面無法訪問)
目錄
建立靜態模板頁(html頁面)
在Api專案檔案下建立一個Template檔案(名稱隨意),在檔案下建立一個html頁面模板。在html檔案中,在我們需要插入資料的位置,採用一個特定字串來代替該資料。使用該模板的時候,用Replace方法,將資料進行替換。模板如下所示:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> // {title} 就可以用從表單或者資料庫獲取來的Title來代替 <title> {title} </title> <meta name="Generator" content="vue.netcore"> <meta id="viewport" name="viewport" content="width=device-width,initial-scale=1,minimum-scale=1,maximum-scale=1,user-scalable=no,viewport-fit=cover"> <meta name="Author" content=""> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <meta name="Keywords" content=""> <meta name="Description" content=""> <style> body { position: relative; height: 100%; max-width: 880px; margin: 0 auto; padding: 15px; } .title h2 { text-align: center; font-weight: 700; color: #4d4f53; letter-spacing: 1px; line-height: 54px; padding-bottom: 8px; margin-bottom: 13px; border-bottom: 1px dashed #ccc; } .title .source { text-align: center; } .title .date, .title .author, .title .count { letter-spacing: 1px; margin-left: 50px; font-size: 14px; color: #8c8b8b; } #count { font-size: 14px; color: #8c8b8b; } .tm-content { margin-top: 40px; font-size: 18px; letter-spacing: 1px; } </style> </head> <body> <div class="title"> <h2> {title} </h2> <div class="source"> <span class="author">來源:vol-core</span> <span class="date">釋出時間:{date}</span> <span class="count">瀏覽次數:</span><span id="count">0</span> </div> </div> <div class="tm-content"> {content} </div> </body> </html> <script> var count = 0; window.onload = function () { var params = window.location.href.split("?"); if (!params || params.length <= 1) { return; } params[1].split("&").forEach(function (item) { var query = item.split("="); if (query.length > 0 && query[0] == "c") { document.getElementById("count").innerText = (~~query[1]) + 1; } }) } </script>
建立基於I/O操作的幫助類。(讀寫html檔案)
關於幫助類,沒有什麼過多解釋,就是I/O讀寫檔案,直接上程式碼。
using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text; namespace Utilities { public class FileHelper { public static string ReadFile(string fullName) { // Encoding code = Encoding.GetEncoding(); //Encoding.GetEncoding("gb2312"); //判斷路徑是否正確,如果獲取格式不正確,先用Replace做修改 //string temp = fullName.MapPath().ReplacePath(); string str = ""; if (!File.Exists(fullName)) { return str; } StreamReader sr = null; try { sr = new StreamReader(fullName); str = sr.ReadToEnd(); // 讀取檔案 } catch { } sr?.Close(); sr?.Dispose(); return str; } /// <summary> /// /// </summary> /// <param name="path">路徑 </param> /// <param name="fileName">檔名</param> /// <param name="content">寫入的內容</param> /// <param name="appendToLast">是否將內容新增到未尾,預設不新增</param> public static void WriteFile(string path, string fileName, string content, bool appendToLast = false) { //判斷路徑是否正確,如果獲取格式不正確,先用Replace做修改 //path = path.ReplacePath(); //fileName = fileName.ReplacePath(); if (!Directory.Exists(path))//如果不存在就建立file資料夾 Directory.CreateDirectory(path); using (FileStream stream = File.Open(path + fileName, FileMode.OpenOrCreate, FileAccess.Write)) { byte[] by = Encoding.Default.GetBytes(content); if (appendToLast) { stream.Position = stream.Length; } else { stream.SetLength(0); } stream.Write(by, 0, by.Length); } } } }
獲取資料,生成靜態頁面。(讀取模板,替換資料,輸出html頁面)
- 單頁面生成靜態,通過form表單獲取資料,也可根據id從資料庫中獲取
- Controller中
/// <summary>
/// 生成靜態頁面
/// </summary>
/// <param name="news"></param>
/// <returns></returns>
[HttpPost, Route("createPage")]
[ApiActionPermission("App_News", ActionPermissionOptions.Add)]
public async Task<IActionResult> CreatePage([FromBody]App_News news)
{
return Json(await Service.CreatePage(news));
}
- Server中
//WebResponseContent 是自定義的返回值類 在文末有程式碼
public async Task<WebResponseContent> CreatePage(App_News news)
{
WebResponseContent webResponseContent = WebResponseContent.Instance;
if (news == null)
{
return webResponseContent.Error("未獲取到資料");
}
if (!await repository.ExistsAsync(x => x.Id == news.Id))
{
return webResponseContent.Error("請求的資料已發生變化,請重新整理頁面重新提交");
}
string template = FileHelper.ReadFile(@"Template\\news.html");
if (string.IsNullOrEmpty(template))
{
return webResponseContent.Error("未獲取到頁面的模板,請確認模板是否存在");
}
string filePath;
string fileName;
string urlPath;
if (!string.IsNullOrEmpty(news.DetailUrl) && news.DetailUrl.IndexOf("/") != -1 && news.DetailUrl.Split(".").Length == 2)
{
var file = news.DetailUrl.Split("/");
fileName = file[file.Length - 1];
filePath = news.DetailUrl.Replace(fileName, "");
urlPath = filePath;
}
else
{
string day = DateTime.Now.ToString("yyyyMMdd");
fileName = DateTime.Now.ToString("HHmmsss") + new Random().Next(1000, 9999) + ".html";
urlPath = $"static/news/{day}/";
filePath = urlPath.MapPath(true);
}
string content = template.Replace("{title}", news.Title).Replace("{date}", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")).Replace("{content}", news.Content);
FileHelper.WriteFile((filePath.IndexOf("wwwroot") == -1 ? "wwwroot/" : "") + filePath, fileName, content);
//更新資料庫的url
news.DetailUrl = $"{urlPath}{fileName}";
repository.Update(news, x => new { news.DetailUrl, news.Content }, true);
return webResponseContent.OK("面釋出成功,可預覽看效果", new { url = news.DetailUrl });
}
- 多頁面批量生成
- 獲取資料
在前端通過複選框選中多行資料,通過非同步傳遞"id拼接字串"(如:1,2,3)。
後臺接受字串,對字串Split(",");獲取到int[]陣列。
通過for迴圈,建立靜態頁面。
*生成靜態頁面
在遍歷int[]陣列中,和生成單頁面方法一樣。
附加
- WebResponseContent 自定義類
using VOL.Core.Enums;
using VOL.Core.Extensions;
namespace VOL.Core.Utilities
{
public class WebResponseContent
{
public WebResponseContent()
{
}
public WebResponseContent(bool status)
{
this.Status = status;
}
public bool Status { get; set; }
public string Code { get; set; }
public string Message { get; set; }
//public string Message { get; set; }
public object Data { get; set; }
public WebResponseContent OK()
{
this.Status = true;
return this;
}
public static WebResponseContent Instance
{
get { return new WebResponseContent(); }
}
public WebResponseContent OK(string message = null,object data=null)
{
this.Status = true;
this.Message = message;
this.Data = data;
return this;
}
public WebResponseContent OK(ResponseType responseType)
{
return Set(responseType, true);
}
public WebResponseContent Error(string message = null)
{
this.Status = false;
this.Message = message;
return this;
}
public WebResponseContent Error(ResponseType responseType)
{
return Set(responseType, false);
}
public WebResponseContent Set(ResponseType responseType)
{
bool? b = null;
return this.Set(responseType, b);
}
public WebResponseContent Set(ResponseType responseType, bool? status)
{
return this.Set(responseType, null, status);
}
public WebResponseContent Set(ResponseType responseType, string msg)
{
bool? b = null;
return this.Set(responseType, msg, b);
}
public WebResponseContent Set(ResponseType responseType, string msg, bool? status)
{
if (status != null)
{
this.Status = (bool)status;
}
this.Code = ((int)responseType).ToString();
if (!string.IsNullOrEmpty(msg))
{
Message = msg;
return this;
}
Message = responseType.GetMsg();
return this;
}
}
}