繁体   English   中英

从 Express.js sendFile() 接收响应是损坏的 PDF

[英]Receiving a response from Express.js sendFile() is a corrupted PDF

我正在处理的流程需要从客户端向服务器发送 POST 请求,服务器会生成一个 PDF 文件并将其返回以供下载。 服务器正确生成 PDF 但是当我在客户端收到它时它已损坏(白色空白页面)。

如何正确接收? 还是问题出在服务器端?

服务器

    async createDraft(req, res) {
        try {
            Log.debug("Server.createDraft", "Trying to create draft file");

            const authorized = await this.isAuthorized(req);

            if(!authorized)
                return res.status(301).redirect(this.cognito.getFederatedLoginURL());

            const questionnaire = await this.db.getQuestionnaire(req.params.id);
            const fileName      = getDraftFileName(questionnaire);

            await create(req.body, fileName, questionnaire.id);
            Log.debug("Server.createDraft", "Successfully created draft");

            const file = path.join(__dirname, `../static/${fileName}`);

            if(fs.existsSync(file))
                return res.status(200).sendFile(file);


            res.status(500);
            console.log("File not found");
            return res.send("File not found");
        } catch(e) {
            Log.info("Server.createDraft", `Error while answering POST /draft - ${e.message}...`);
            return badRequest(res, e.message);
        }
    }




const create = async (data, fileName, id) => {
    const output   = path.join(__dirname, "../../static/");
    const filePath = path.join(__dirname, "../draft/");
    const tmp      = path.join(__dirname, "../../tmp/");
    const content  = `${tmp}draft-${id}.html`;
    const cover    = `${tmp}cover-${id}.html`;

    await Q.all([
        Q.nfcall(fs.writeFile, content, data.content),
        Q.nfcall(fs.writeFile, cover, data.cover)
    ]);
    await Q.all([
        Q.nfcall(exec, `wkhtmltopdf --enable-local-file-access --encoding 'UTF-8' toc --xsl-style-sheet ${filePath}toc.xsl --header-html ${filePath}header.html --header-spacing 10 --footer-html ${filePath}footer.html --footer-spacing 10 ${content} --header-html ${filePath}header.html --header-spacing 10 --footer-html ${filePath}footer.html --footer-spacing 10 ${output}content-${fileName}`),
        Q.nfcall(exec, `wkhtmltopdf --enable-local-file-access --encoding 'UTF-8' -T 0 -B 0 cover ${cover} ${output}cover-${fileName}`)
    ]);
    await Q.nfcall(exec, `pdftk ${output}cover-${fileName} ${output}content-${fileName} cat output ${output}${fileName}`);


    await Q.all([
        Q.nfcall(fs.unlink, `${tmp}draft-${id}.html`),
        Q.nfcall(fs.unlink, `${tmp}cover-${id}.html`),
        Q.nfcall(fs.unlink, `${output}content-${fileName}`),
        Q.nfcall(fs.unlink, `${output}cover-${fileName}`)
    ]);
};

客户


// eslint-disable-next-line max-statements
export const exportDraft = async (tree, data) => {
    try {
        tree.set("loading", true);
        tree.commit();

        document.getElementById("cover-title").innerHTML = data.draft.secoDraft;

        const path = window.location.pathname.split("/");
        const id   = parseInt(path[ path.length - 1 ], 10);

        const res = await axios({
            url:          `${window.location.origin}/draft/${id}`,
            method:       "POST",
            responseType: "blob",
            data:         {
                cover: `<!DOCTYPE html>
                    <html>
                        <head>
                            <meta charset="UTF-8">
                            <link rel="stylesheet" type="text/css" href="../src/draft/wysiwyg.css" />
                            <link rel="stylesheet" type="text/css" href="../src/draft/test.css" />
                        </head>
                        <body>
                            ${document.getElementById("cover").innerHTML}
                        </body>
                    </html>`,
                content: `<!DOCTYPE html>
                    <html>
                        <head>
                            <meta charset="UTF-8">
                            <link rel="stylesheet" type="text/css" href="../src/draft/wysiwyg.css" />
                            <link rel="stylesheet" type="text/css" href="../src/draft/test.css" />
                        </head>
                        <body>
                            ${document.getElementById("draft").innerHTML}
                        </body>
                    </html>
                `
            },
            json: true
        });

        console.log(res);
        tree.set("loading", false);
        const file = new Blob([res], { type: "application/pdf" });

        return saveAs(file, "PDF-Draft.pdf");
    } catch(e) {
        tree.set("loading", false);
        return add(tree, "error", e.message);
    }
};

使用 res.data 提取 pdf 数据解决了问题

        const file = new Blob([res.data], { type: "application/pdf" });

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM