動態產生靜態 HTML 頁面的經典模式:
$Title$、$Content$)標示動態區塊。String.Replace 將標記替換為實際資料。完整類別包含:
_templateFileparameter(範本標記)與 _ASPxFileparameter(替換值),透過 TemplateParamCount 同步長度。StartConvert() → writeFile()(讀取→替換)→ saveFile()(寫入)→ 回傳產生檔名。getFileName() 以「年月日時分秒毫秒+隨機數」確保唯一性。WriteErrFile() 將例外詳細資訊附加寫入日誌檔。public class ASPxToHtml
{
private int _templateParamCount = 0;
private string _templateFilePath = ConfigurationManager.AppSettings["TemplateFilePath"];
private string _htmlFilePath = ConfigurationManager.AppSettings["HtmlFilePath"];
private Encoding _templateEncoding = Encoding.GetEncoding("utf-8"); // 建議改用 UTF-8
private Encoding _outputEncoding = Encoding.GetEncoding("utf-8");
private string[] _templateParams;
private string[] _valueParams;
public int TemplateParamCount
{
get => _templateParamCount;
set
{
if (value < 0) throw new ArgumentException();
_templateParamCount = value;
_templateParams = new string[value];
_valueParams = new string[value];
}
}
// ... 其他屬性省略
}
public string StartConvert()
{
if (_templateParams.Length != _valueParams.Length) return null;
return WriteFile();
}
private string WriteFile()
{
string physicalTemplatePath = HttpContext.Current.Server.MapPath(TemplateFilePath);
string templateContent;
using (var sr = new StreamReader(physicalTemplatePath, _templateEncoding))
templateContent = sr.ReadToEnd();
for (int i = 0; i < TemplateParamCount; i++)
templateContent = templateContent.Replace(_templateParams[i], _valueParams[i]);
return SaveFile(templateContent);
}
private string SaveFile(string content)
{
string physicalOutputDir = HttpContext.Current.Server.MapPath(HtmlFilePath);
Directory.CreateDirectory(physicalOutputDir); // 確保目錄存在
string fileName = GetFileName();
string fullPath = Path.Combine(physicalOutputDir, fileName);
using (var sw = new StreamWriter(fullPath, false, _outputEncoding))
sw.Write(content);
return fileName;
}
private string GetFileName()
{
// 使用 Guid 更簡潔且唯一
return $"{DateTime.Now:yyyyMMddHHmmssfff}_{Guid.NewGuid():N}.html";
}
StreamReader/Writer 改用 ReadToEndAsync/WriteAsync 提升併發效能。HttpContext.Current 的靜態依賴,改注入 IWebHostEnvironment 取得實體路徑,利於單元測試。var generator = new ASPxToHtml(2)
{
TemplateFilePath = "~/Templates/NewsTemplate.html",
HtmlFilePath = "~/GeneratedHtml/News/"
};
generator.SetTemplateParams(new[] { "$Title$", "$Body$" });
generator.SetValueParams(new[] { "最新消息標題", "這是詳細內容..." });
string generatedFile = generator.StartConvert();
// 生成檔案如:20240520143025123_abc123.html