ToB企服应用市场:ToB评测及商务社交产业平台
标题:
.net core使用Html模板转PDF文件并下载的业务类封装
[打印本页]
作者:
欢乐狗
时间:
2023-6-16 17:43
标题:
.net core使用Html模板转PDF文件并下载的业务类封装
前言:我这里文件下载的模板选型优先考虑html模板,上手容易,前后端通用,有了模板后就需要有转换了,html转PDF采用第三方包:SelectPdf,下面是代码核心类:
1-PDFService:
using Microsoft.AspNetCore.Hosting;
using SelectPdf;
namespace MeShop.Domain.PDF
{
/// <summary>
/// PDF业务类
/// </summary>
public class PDFService
{
private readonly IHostingEnvironment hostingEnvironment;
public PDFService(IHostingEnvironment hostingEnvironment)
{
this.hostingEnvironment = hostingEnvironment;
}
/// <summary>
/// 将Html替换参数后转成PDF字节流
/// </summary>
/// <param name="htmlFilePath">html模板文件路径</param>
/// <param name="saveFileName">PDF文件名</param>
/// <param name="replaceParamDic">变量替换字典</param>
/// <returns></returns>
public async Task<string> HtmlToPDFFile(string htmlFilePath, string saveFileName, Dictionary<string, string> replaceParamDic)
{
HtmlToPdf Renderer = new HtmlToPdf();
//设置Pdf参数
//设置页面方式-横向 PdfPageOrientation.Portrait 竖向
Renderer.Options.PdfPageOrientation = PdfPageOrientation.Landscape;
//设置页面大小,30种页面大小可以选择
Renderer.Options.PdfPageSize = PdfPageSize.A4;
//上下左右边距设置
Renderer.Options.MarginTop = 10;
Renderer.Options.MarginBottom = 10;
Renderer.Options.MarginLeft = 10;
Renderer.Options.MarginRight = 10;
//设置更多额参数可以去HtmlToPdfOptions里面选择设置
//根据html内容导出PDF
string docHtml = await File.ReadAllTextAsync(htmlFilePath, Encoding.UTF8);
foreach (var item in replaceParamDic)
{
docHtml = docHtml.Replace(item.Key, item.Value);
}
PdfDocument pdfDocument = Renderer.ConvertHtmlString(docHtml);
string saveFilePath = @$"{this.hostingEnvironment.ContentRootPath}\staticfiles\Download\{saveFileName}";
if (File.Exists(saveFilePath))
{
File.Delete(saveFilePath);
}
pdfDocument.Save(saveFilePath);
return saveFilePath;
}
/// <summary>
/// 读取文件字节流
/// </summary>
/// <param name="filePath">资源文件(包含路径)</param>
/// <param name="isDeleteSourceFile">是否删除资源文件</param>
/// <returns></returns>
public async Task<byte[]> GetByteByFile(string? filePath, bool isDeleteSourceFile = false)
{
byte[]? myByteArray = null;
if (filePath != null && File.Exists(filePath))
{
using (FileStream fileStream = new FileStream(filePath, FileMode.Open))
{
fileStream.Seek(0, SeekOrigin.Begin);
myByteArray = new byte[fileStream.Length];
await fileStream.ReadAsync(myByteArray, 0, (int)fileStream.Length);
}
if (isDeleteSourceFile)
{
File.Delete(filePath);
}
}
return myByteArray ?? new byte[0];
}
/// <summary>
/// 压缩多个文件为zip文件
/// </summary>
/// <param name="zipFileName">zip压缩文件名</param>
/// <param name="filePaths">资源文件列表(包含路径)</param>
/// <param name="isDeleteSourceFile">是否删除资源文件</param>
/// <returns></returns>
public string CompressFileToZip(string zipFileName, string[] filePaths, bool isDeleteSourceFile = false)
{
string? zipFilePath = null;
if (!string.IsNullOrWhiteSpace(zipFileName) && filePaths.Length > 0)
{
string zipDirectoryPath = @$"{this.hostingEnvironment.ContentRootPath}\staticfiles\Download\{DateTime.Now.ToString("yyyyMMddHHmmssfff")}";
if (!Directory.Exists(zipDirectoryPath))
{
Directory.CreateDirectory(zipDirectoryPath);
}
zipFilePath = @$"{this.hostingEnvironment.ContentRootPath}\staticfiles\Download\{zipFileName}";
if (File.Exists(zipFilePath))
{
File.Delete(zipFilePath);
}
foreach (var filePath in filePaths)
{
string? fileName = filePath.Split('\\').LastOrDefault();
string copyFilePath = @$"{zipDirectoryPath}\{fileName}";
if (isDeleteSourceFile)
{
File.Move(filePath, copyFilePath);
}
else
{
File.Copy(filePath, copyFilePath);
}
}
CompressionHelper.Compression(zipDirectoryPath, zipFilePath);
//压缩完成后,删除压缩使用文件夹及其子项
Directory.Delete(zipDirectoryPath, true);
}
return zipFilePath ?? "";
}
}
}
复制代码
2-控制器方法示例:
[HttpGet("DownloadSettlement")]
public async Task<JsonModel<byte[]>> DownloadSettlement(string settlementIDS)
{
byte[]? byteArray = null;
string[] settlementIDArray = settlementIDS.Split(',');
string templateHtmlPath = @$"{this.hostingEnvironment.ContentRootPath}\staticfiles\agentusersettlement.html";
List<string> zipSaveFilePathList = new List<string>(settlementIDArray.Length);
Base_shop baseShop = await this.shopService.GetBaseShopAsync();
foreach (var item in settlementIDArray)
{
long settlementID = TypeParseHelper.StrToInt64(item);
ResponseAgentUserSettlementDetail? detail = await this.agentUserSettlementService.GetDetailAsync(settlementID);
if (detail != null)
{
Agent_user agentUser = await this.agentUserService.GetAsync(detail.AgentUserID) ?? new Agent_user();
Dictionary<string, string> replaceDic = new Dictionary<string, string>()
{
{"@InvoiceNumber@",$"{detail.UpdateTime.ToString("yyyyMMdd")}{detail.ID}" },
{"@UpdateTime@",$"{detail.UpdateTime.ToString("yyyyMMdd")}" },
{"@AgentUserCompanyName@",$"{agentUser.CompanyName}" },
{"@AgentUserCompanyAddress@",$"{agentUser.CompanyAddress}" },
{"@BeginDate@",$"{detail.BeginDate.ToString("yyyy/MM/dd")}" },
{"@EndDate@",$"{detail.EndDate.ToString("yyyy/MM/dd")}" },
{"@TotalPoint@",$"{detail.TotalPoint.ToString("F3")}" },
{"@AccountCompanyName@",$"{baseShop.CompanyName}" },
{"@AccountCompanyAddress@",$"{baseShop.CompanyAddress}" },
{"@AccountEmail@",$"{baseShop.ServiceEmail}" }
};
zipSaveFilePathList.Add(await this.pdfService.HtmlToPDFFile(templateHtmlPath, $"{settlementID}.pdf", replaceDic));
//设置导出状态
await this.agentUserSettlementService.SetExportStateAsync(settlementID, (int)EState.启用);
}
}
if (zipSaveFilePathList.Count == 1)
{
byteArray = await this.pdfService.GetByteByFile(zipSaveFilePathList.FirstOrDefault());
}
else
{
string zipFilePath = this.pdfService.CompressFileToZip($"{settlementIDS.Replace(',', '_')}.zip", zipSaveFilePathList.ToArray(), true);
byteArray = await this.pdfService.GetByteByFile(zipFilePath);
}
return base.SuccessResult(byteArray ?? new byte[0]);
}
复制代码
3-前台JS下载文件字节流示例:
[code][/code]
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!
欢迎光临 ToB企服应用市场:ToB评测及商务社交产业平台 (https://dis.qidao123.com/)
Powered by Discuz! X3.4