Ionic Angular用Capacitor打包iOS应用后无法下载PHP生成的PDF如何解决
iOS Capacitor环境PDF下载失效解决方案
失效原因
iOS端WKWebView对Blob URL的生命周期有严格限制,动态创建a标签的download属性在WebView场景下不被原生支持,同时window.open调用会被Capacitor的路由规则拦截,因此浏览器端可用的下载逻辑无法在iOS原生应用环境生效。
修复步骤
1. 确认HTTP请求配置
确保你调用reportService.runReport的底层HTTP请求已设置responseType: 'blob',避免返回的二进制数据被默认转成字符串导致PDF损坏。
2. 安装配置Capacitor Filesystem原生插件
使用Capacitor官方提供的文件系统原生能力实现本地存储:
- 安装依赖:
npm install @capacitor/filesystem npx cap sync
- iOS权限配置:在Xcode中打开iOS工程,找到
Info.plist文件,添加以下两个配置项:UIFileSharingEnabled设为YES(允许用户在系统「文件」App中查看应用下载的文件)LSSupportsOpeningDocumentsInPlace设为YES(允许其他应用直接打开你下载的PDF文件)
3. 替换原有下载逻辑
修改你的runReport方法代码如下:
import { Filesystem, Directory } from '@capacitor/filesystem'; // 辅助方法:将Blob转为base64格式 const blobToBase64 = (blob: Blob): Promise<string> => { return new Promise((resolve, reject) => { const reader = new FileReader(); reader.readAsDataURL(blob); reader.onloadend = () => resolve(reader.result as string); reader.onerror = reject; }); } runReport(): void { this.loading = true; this.reportService.runReport(this.body) .pipe(finalize(() => this.loading = false)) .subscribe(async response => { const file = new Blob([response.body], { type: 'application/pdf' }); const base64Data = await blobToBase64(file); // 写入文件到应用Documents目录 await Filesystem.writeFile({ path: '-redacted filename-.pdf', data: base64Data, directory: Directory.Documents, }); // 可选:写入完成后直接打开PDF,需要先安装@capacitor/browser插件 // const fileInfo = await Filesystem.getUri({ // path: '-redacted filename-.pdf', // directory: Directory.Documents, // }); // await Browser.open({ url: fileInfo.uri }); }); }
按照上述修改后,PDF会直接写入iOS设备本地的应用文档目录,用户可以在系统「文件」App中找到下载的文件。
内容的提问来源于stack exchange,提问作者David
相关产品推荐
相关产品推荐

