using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text.RegularExpressions; using DocumentFormat.OpenXml.Packaging; using DocumentFormat.OpenXml.Wordprocessing; using Furion.DependencyInjection; namespace YD_Event.Core.Certificate { /// /// DOCX模板解析器 /// public class DocxTemplateParser : ITransient { private const string PlaceholderPattern = @"\{\{([^}]+)\}\}"; /// /// 从DOCX文件中提取占位符 /// /// DOCX文件流 /// 占位符列表 public List ExtractPlaceholders(Stream docxStream) { var placeholders = new HashSet(); using (var document = WordprocessingDocument.Open(docxStream, false)) { var body = document.MainDocumentPart?.Document?.Body; if (body == null) return new List(); // 解析段落中的占位符 foreach (var paragraph in body.Elements()) { var text = ExtractTextFromParagraph(paragraph); var foundPlaceholders = ExtractPlaceholdersFromText(text); foreach (var placeholder in foundPlaceholders) { placeholders.Add(placeholder); } } // 解析表格中的占位符 foreach (var table in body.Elements()) { var tablePlaceholders = ExtractPlaceholdersFromTable(table); foreach (var placeholder in tablePlaceholders) { placeholders.Add(placeholder); } } // 解析页眉页脚中的占位符 ExtractPlaceholdersFromHeaderFooter(document, placeholders); } return placeholders.OrderBy(x => x).ToList(); } /// /// 从文本中提取占位符 /// /// 文本内容 /// 占位符列表 private List ExtractPlaceholdersFromText(string text) { var placeholders = new List(); var matches = Regex.Matches(text, PlaceholderPattern); foreach (Match match in matches) { var placeholder = match.Groups[1].Value.Trim(); if (!string.IsNullOrWhiteSpace(placeholder)) { placeholders.Add(placeholder); } } return placeholders; } /// /// 从段落中提取文本 /// /// 段落元素 /// 文本内容 private string ExtractTextFromParagraph(Paragraph paragraph) { return string.Join("", paragraph.Elements().Select(run => string.Join("", run.Elements().Select(text => text.Text)))); } /// /// 从表格中提取占位符 /// /// 表格元素 /// 占位符列表 private List ExtractPlaceholdersFromTable(Table table) { var placeholders = new HashSet(); foreach (var row in table.Elements()) { foreach (var cell in row.Elements()) { foreach (var paragraph in cell.Elements()) { var text = ExtractTextFromParagraph(paragraph); var cellPlaceholders = ExtractPlaceholdersFromText(text); foreach (var placeholder in cellPlaceholders) { placeholders.Add(placeholder); } } } } return placeholders.ToList(); } /// /// 从页眉页脚中提取占位符 /// /// Word文档对象 /// 占位符集合 private void ExtractPlaceholdersFromHeaderFooter(WordprocessingDocument document, HashSet placeholders) { // 暂时跳过页眉页脚处理,因为API兼容性问题 // 实际项目中需要根据具体的DocumentFormat.OpenXml版本调整 } /// /// 验证占位符格式 /// /// 占位符 /// 是否有效 public bool IsValidPlaceholder(string placeholder) { return !string.IsNullOrWhiteSpace(placeholder) && Regex.IsMatch(placeholder, @"^[a-zA-Z_][a-zA-Z0-9_]*$"); } /// /// 获取占位符类型 /// /// 占位符 /// 占位符类型 public string GetPlaceholderType(string placeholder) { if (string.IsNullOrWhiteSpace(placeholder)) return "Text"; var lowerPlaceholder = placeholder.ToLowerInvariant(); if (lowerPlaceholder.Contains("date") || lowerPlaceholder.Contains("time")) return "Date"; if (lowerPlaceholder.Contains("qr") || lowerPlaceholder.Contains("qrcode")) return "QRCode"; if (lowerPlaceholder.Contains("image") || lowerPlaceholder.Contains("img") || lowerPlaceholder.Contains("photo")) return "Image"; return "Text"; } } }