为啥我的 PDF 生成进程会锁定我站点中的其他 ajax 进程?
Posted
技术标签:
【中文标题】为啥我的 PDF 生成进程会锁定我站点中的其他 ajax 进程?【英文标题】:Why does my PDF generation process lock other ajax process in my site?为什么我的 PDF 生成进程会锁定我站点中的其他 ajax 进程? 【发布时间】:2013-10-10 11:32:45 【问题描述】:我有一个需要定期生成大型报告的 MVC3 应用程序。用户可以选择他们的标准并启动报告。现在我正在使用 javascript window.open() 方法打开一个新选项卡/窗口。在生成报告时,用户无法使用该站点。一切都等到生成报告。 生成报告的代码是:
private FileStreamResult doSpecReport(List<int> idProjItems)
PdfDocument outputDocument = new PdfDocument(); // returning to the user
foreach(var id in idProjItems)
var item = _entities.ProjectEquipmentItems.First(f => f.idProjectEquipmentItem == id);
var cutsheetPath = item.CutSheet;
Dictionary<string, string> dictionary = new Dictionary<string, string>();
dictionary.Add("p_idEquipmentItem", id.ToString());
var fs = GetReporthtml("NameOfReport", dictionary); // Returns FileStreamResult from crystal
var inputDocument1 = CompatiblePdfReader.Open(fs.FileStream); // add report to output doc
int count = inputDocument1.PageCount;
for(int idx = 0; idx < count; idx++)
PdfPage page = inputDocument1.Pages[idx];
outputDocument.AddPage(page);
if (!string.IsNullOrEmpty(cutsheetPath))
cutsheetPath = Path.Combine(Server.MapPath("~/Files/CutSheetFiles/"), cutsheetPath);
if (File.Exists(cutsheetPath))
var inputDocument2 = CompatiblePdfReader.Open(cutsheetPath);//, PdfDocumentOpenMode.Import);
count = inputDocument2.PageCount;
for(int idx = 0; idx < count; idx++)
PdfPage page = inputDocument2.Pages[idx];
outputDocument.AddPage(page);
var ms = new MemoryStream();
outputDocument.Save(ms, false);
ms.Position = 0;
return new FileStreamResult(ms, "application/pdf")
FileDownloadName = "Report.pdf"
;
我不确定我是否做错了什么,我不明白为什么这个过程会占用浏览器的所有资源。感谢您的帮助。
更新:调用 doSpecReport 的代码版本。围绕成功的代码不起作用。
$.ajax(
url: url,
data: qdata,
type: "POST",
success: function (result) // this doesn't actually work.
var obj = $('<object type="application/pdf" border="2"></object>');
obj.attr('data', 'data:application/pdf;base64,' + result);
$(".mask").hide();
$('#divContainer').append(obj);
);
【问题讨论】:
这看起来像 C# 代码,而不是 JavaScript;最终用户系统上的浏览器除了等待服务器返回之外什么都不做……如果您希望浏览器在服务器处理时保持响应,则需要使用某种异步调用。 .. 你是对的,javascript标签是由于我打开调用此代码的窗口的方式。我在想可能有一些方法可以修改该代码,以确保该代码在不同的线程中运行。并且通过 ajax 发送请求仍然持有网站的人质。 您能否发布您尝试用于异步调用的实际 JavaScript 代码? 编辑了我的问题以添加代码。 【参考方案1】:您必须在服务器端生成一个临时文件位置并返回位置 url。您不能使用二进制 PDF 设置 HTML 文档内容。您能否生成报告并将其存储在临时位置并在响应中传递其 url 链接。假设 doSpecReport 生成一个名为 mypdf.pdf 的临时 pdf 文件,
然后在你的成功块中,你可以将它添加到对象数据属性中,使最终对象看起来像this
<object type="application/pdf" data="/my_pdf.pdf?#zoom=85&scrollbar=0&toolbar=0&navpanes=0" id="pdf_content">
</object>
【讨论】:
我真正的问题是,即使我这样做了,而且我已经这样做了,网站在整个过程完成之前不会响应。我想在另一个窗口中生成报告,然后能够在该网站工作时使用该网站。我不想将文件写入磁盘。我们将在 IIS 中实现一个指向报表服务器样式项目的新站点。 只是为了澄清 - 当您说您的网站没有响应时。我假设,您被锁定在 JavaScript 端而不是服务器端。正确的?您甚至在客户端遇到过成功障碍吗?如果您想在另一个窗口中生成报告 - 为什么要做 $.ajaxPost?为什么不使用 window.open() 和服务器知道如何服务的随机 url。 我对完成工作并返回 pdf 的 url 做了一个 window.open。虽然这个窗口正在运行并且没有返回我的 pdf,但我的网站被锁定,这意味着如果我想移动到不同的页面,我不能。如果我对启动 ajaxPost 的页面执行 window.open,则会出现同样的问题。 您使用的是 ASP .net 开发服务器吗?此服务器 cannot process more than one request at a time. 。我想这就是原因,你什么都做不了。 好的@smash51,感谢您的耐心等待。它变得有趣了。 :) 你能做几件事吗?我认为您的 IIS Express 没有处理多个请求。你在使用ASP.NET session states。我有一种感觉,它的服务器。有没有其他方法可以确认服务器是否正在并行处理多个请求。以上是关于为啥我的 PDF 生成进程会锁定我站点中的其他 ajax 进程?的主要内容,如果未能解决你的问题,请参考以下文章