Base64 String to pdf JavaScript React Native 然后下载

Posted

技术标签:

【中文标题】Base64 String to pdf JavaScript React Native 然后下载【英文标题】:Base64 String to pdf JavaScript React Native then download 【发布时间】:2021-09-05 14:53:39 【问题描述】:

我有一个base64字符串如下:

我希望将此 base64 字符串(或任何 base64 字符串)转换为 pdf,然后在 React Native 中下载。我正在为此使用博览会。我找遍了整个地方,找不到答案。

【问题讨论】:

【参考方案1】:

如果你只想在 react-native 中显示 pdf。react-native-pdf 包可以完成这项工作。使用这样的源 obj。

const source = uri:"data:application/pdf;base64,JVBERi0xLjcKJc...";

如果你想下载base64到pdf文件,也很简单。

var RNFetchBlob = require('react-native-fetch-blob').default;

const DocumentDir = RNFetchBlob.fs.dirs.DocumentDir;
let pdfLocation = DocumentDir + '/' + 'test.pdf';
RNFetchBlob.fs.writeFile(pdfLocation, pdf_base64Str, 'base64');
export async function downloadFile(url)
    let binary = await getPdfBinary(url);
    const base64Str = base64_encode(binary);
    const DocumentDir = RNFetchBlob.fs.dirs.DocumentDir;
    let pdfLocation = DocumentDir + '/' + 'test.pdf';
    RNFetchBlob.fs.writeFile(pdfLocation, base64Str, 'base64');

很抱歉,我没有注意到您正在使用 expo。因为我从来没有在博览会上写过关于文件系统部分的代码。经过多次尝试,它终于奏效了。但仅适用于安卓。我想您可能希望将 pdf 文件保存到外部存储路径,以便用户可以在文件应用程序中看到它。但是对于 ios,很难做到这一点。一种可能的方法是使用共享对话框。如果您只是想将pdf文件保存到应用程序中的文档文件夹(用户看不到),FileSystem.writeAsStringAsync就足够了!希望对您有帮助!

import * as  FileSystem from 'expo-file-system';
import  Platform  from 'react-native';

async function getPdfBinary(url) 
    return new Promise((resolve, reject) => 
        var xhr = new XMLHttpRequest();
        xhr.open("GET", url, true);
        xhr.responseType = "arraybuffer"; // get the binary 
        xhr.setRequestHeader('content-type', 'application/json');
        xhr.onload = function (event) 
            var arrayBuffer = xhr.response;
            var byteArray = new Uint8Array(arrayBuffer);
            var len = byteArray.byteLength;
            var binary = ""
            for (var i = 0; i < len; i++) 
                binary += String.fromCharCode(byteArray[i]);
            
            resolve(binary);
        
        xhr.send();
    )


function base64_encode(str) 
    var c1, c2, c3;
    var base64EncodeChars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    var i = 0,
        len = str.length,
        string = '';

    while (i < len) 
        c1 = str.charCodeAt(i++) & 0xff;
        if (i == len) 
            string += base64EncodeChars.charAt(c1 >> 2);
            string += base64EncodeChars.charAt((c1 & 0x3) << 4);
            string += "==";
            break;
        
        c2 = str.charCodeAt(i++);
        if (i == len) 
            string += base64EncodeChars.charAt(c1 >> 2);
            string += base64EncodeChars.charAt(((c1 & 0x3) << 4) | ((c2 & 0xF0) >> 4));
            string += base64EncodeChars.charAt((c2 & 0xF) << 2);
            string += "=";
            break;
        
        c3 = str.charCodeAt(i++);
        string += base64EncodeChars.charAt(c1 >> 2);
        string += base64EncodeChars.charAt(((c1 & 0x3) << 4) | ((c2 & 0xF0) >> 4));
        string += base64EncodeChars.charAt(((c2 & 0xF) << 2) | ((c3 & 0xC0) >> 6));
        string += base64EncodeChars.charAt(c3 & 0x3F)
    
    return string



const downloadForAos = async (pdfBase64Str) => 
    const folder = FileSystem.StorageAccessFramework.getUriForDirectoryInRoot("test");
    const permissions = await FileSystem.StorageAccessFramework.requestDirectoryPermissionsAsync(folder);
    if (!permissions.granted) return;

    let filePath = await FileSystem.StorageAccessFramework.createFileAsync(permissions.directoryUri, "test.pdf", "application/pdf");
    // let filePath = "content://com.android.externalstorage.documents/tree/primary%3Atest/document/primary%3Atest%2Ftest.txt";
    console.log(pdfBase64Str, "====");
    try 
        await FileSystem.StorageAccessFramework.writeAsStringAsync(filePath, pdfBase64Str,  encoding: FileSystem.EncodingType.Base64 );
        alert("download success!")
     catch (err) 
        console.log(err);
    


const downloadForIos = async () => 
    alert("try do it by yourself")


export async function downloadPdf(url) 
    let binary = await getPdfBinary(url);
    console.log(binary, "=====")
    const base64Str = base64_encode(binary);
    if (Platform.OS === "ios") 
        downloadForIos(base64Str);
     else 
        downloadForAos(base64Str);
    


【讨论】:

你的图片不是base64,你应该把它编码成base64。如果你有原始文件,我认为应该更容易。 我的图片是一个字符串。那你知道它是什么类型吗? 我知道。如果你用文本编辑器打开一个 pdf 文件,你会看到这样的字符串。你从哪里得到这个? 我从后端得到这个。 没有。也许您可以在后端执行此操作。在 python 中,读取文件,然后对其进行 base64 编码。在 react-native 中,直接获取 base64 字符串!

以上是关于Base64 String to pdf JavaScript React Native 然后下载的主要内容,如果未能解决你的问题,请参考以下文章

为啥Bitmap to Base64 String在android的webview上显示黑色背景?

javascript [base64 string to image file]如何在node.js#Node.js中写入图像

使用AJAX将PDF作为base64文件上载到服务器

vue.base64转pdf加载太慢

为啥我用Base64加密后,不能将它解密?

在 Android / Java 中使用 JSON / Base64 编码文件