Laravel中如何通过Ajax请求下载控制器生成的PDF
Laravel + dompdf 实现Ajax请求后直接下载PDF(不存储服务器)
一、控制器响应处理
不能返回JSON格式,需要直接返回PDF二进制内容并设置正确的HTTP响应头,让浏览器识别为可下载文件:
public function generatePdf(Request $request) { // 1. 接收并处理前端传入的参数 $formData = $request->validate([ // 这里根据你的表单字段添加验证规则 ]); // 2. 初始化dompdf并渲染PDF $dompdf = new Dompdf(); // 加载PDF模板视图(也可以直接传入HTML字符串) $html = view('pdf.custom-template', $formData)->render(); $dompdf->loadHtml($html); $dompdf->setPaper('A4', 'portrait'); $dompdf->render(); // 3. 获取PDF二进制输出内容 $pdfContent = $dompdf->output(); // 4. 返回下载响应 return response()->make($pdfContent, 200, [ 'Content-Type' => 'application/pdf', 'Content-Disposition' => 'attachment; filename="自定义文件名.pdf"', ]); }
二、前端JavaScript处理
普通Ajax默认会把响应当成文本解析,必须指定responseType为blob来处理二进制数据,再通过创建临时URL触发下载:
// 绑定表单提交事件 $('#pdf-generate-form').on('submit', function(e) { e.preventDefault(); const formData = $(this).serialize(); $.ajax({ url: '/your-route-path', // 替换为你的控制器路由 method: 'POST', data: formData, xhrFields: { responseType: 'blob' // 关键:告诉浏览器接收二进制Blob数据 }, success: function(blob) { // 创建临时下载链接 const downloadUrl = window.URL.createObjectURL(blob); // 创建a标签触发下载 const link = document.createElement('a'); link.href = downloadUrl; link.download = '自定义文件名.pdf'; document.body.appendChild(link); link.click(); // 清理临时资源 window.URL.revokeObjectURL(downloadUrl); document.body.removeChild(link); }, error: function() { alert('PDF生成失败,请重试'); } }); });
关键说明
- 控制器无需存储PDF文件,所有生成过程在内存中完成,直接返回二进制内容
- 前端必须设置
responseType: 'blob',否则会导致PDF文件损坏 - 通过
Content-Disposition头指定下载文件名和附件类型,确保浏览器触发下载而非在线预览
内容的提问来源于stack exchange,提问作者T5k
相关产品推荐
相关产品推荐

