Подтвердить что ты не робот

Отображение Pdf в браузере с помощью express js

app.post('/asset', function(request, response){
  var tempFile="/home/applmgr/Desktop/123456.pdf";
  fs.readFile(tempFile, function (err,data){
     response.contentType("application/pdf");
     response.send(data);
  });
});

Я новый bie для expressjs, я не могу отправить ответ с объектом данных. Бинарный контент отображается в браузере. Дайте мне советы, как справиться с этим?

4b9b3361

Ответ 1

Я проверил ваш код, и он работает для меня в хроме с одним изменением: Измените app.post на app.get

EDIT: поскольку вы, кажется, думаете, что сервер POST-only - хорошая идея, прочитайте следующее: http://net.tutsplus.com/tutorials/other/a-beginners-introduction-to-http-and-rest/ Прокрутите вниз до HTTP-глаголов и проверьте разницу между GET и POST.:)

Некоторые быстрые исследования показывают, что другие браузеры могут иметь другие проблемы, например, IE может ожидать, что URL-адрес закончится в .pdf. Поскольку я нахожусь на своем Mac, я не могу проверить это для вас;)

Ответ 2

Указание того, как обрабатывается загрузка файла, сводится к заголовку Content-disposition. Вы также можете указать имя файла здесь. Мы также устанавливаем Content-type, чтобы браузер знал, что делать с предоставленным ему файлом.

Экспресс .js Пример:

app.post('/url/to/hit', function(req, res, next) {
  var stream = fs.readStream('/location/of/pdf');
  var filename = "WhateverFilenameYouWant.pdf"; 
  // Be careful of special characters

  filename = encodeURIComponent(filename);
  // Ideally this should strip them

  res.setHeader('Content-disposition', 'inline; filename="' + filename + '"');
  res.setHeader('Content-type', 'application/pdf');

  stream.pipe(res);
});

Теперь, если вы посмотрите более внимательно на Content-disposition, вы заметите, что поле inline; определяет, как браузер реагирует на файл. Если вы хотите принудительно загружать файлы, вы можете сделать это, установив inline; в attachment;

Я также узнал (будучи сожженным пару раз), что если вы установите специальные символы в своем имени файла, это может сломаться. Поэтому я encodeURIComponent() имя файла, чтобы этого не произошло.

Надеюсь, что помогает другим пытаться понять то же самое!

Изменить

В то время, когда я отправлял это изначально и сейчас, я выяснил, как правильно кодировать параметр Content-disposition filename. Согласно спецификации, имя файла должно быть закодировано RFC5987. Я закончил поиск фрагмента кода кода из MDN, который правильно обрабатывает кодировку здесь (encodeURIComponent() не является полностью правильным форматом для этого поля).

Фрагмент MDN

var fileName = 'my file(2).txt';
var header = "Content-Disposition: attachment; filename*=UTF-8''" 
             + encodeRFC5987ValueChars(fileName);

console.log(header); 
// logs "Content-Disposition: attachment; filename*=UTF-8''my%20file%282%29.txt"

function encodeRFC5987ValueChars (str) {
    return encodeURIComponent(str).
        // Note that although RFC3986 reserves "!", RFC5987 does not,
        // so we do not need to escape it
        replace(/['()]/g, escape). // i.e., %27 %28 %29
        replace(/\*/g, '%2A').
            // The following are not required for percent-encoding per RFC5987, 
            // so we can allow for a little better readability over the wire: |`^
            replace(/%(?:7C|60|5E)/g, unescape);
}

Еще одно примечание к этому, браузеры не полностью соответствуют спецификации. Некоторые символы по-прежнему будут возвращаться некорректно из загрузки (по крайней мере, когда я ее протестировал).

Вы можете обойти эту проблему, обновив работу ваших загрузок. Если URL-адрес загрузки заканчивается с именем файла (и вы не добавляете атрибут filename в заголовок), он будет правильно получать имя файла из кодированного значения URL. IE 'http://subdomain.domain-url.com/some/path/to/downloads/' + encodeURIComponent("You're there, download this!.pdf")

Jeeze, и все, чтобы указать имя файла для ваших загрузок!

Ответ 3

Мое решение для отправки PDF непосредственно в браузер:

app.get('/my/pdf', function (req, res) {
    var doc = new Pdf();
    doc.text("Hello World", 50, 50);

    doc.output( function(pdf) {
        res.type('application/pdf');
        res.end(pdf, 'binary');
    });
});

res.end() со вторым параметром 'binary' сделал трюк в моем случае. В противном случае выражение интерпретирует его как строку

Ответ 4

Это так же просто, как следующий код:

var express = require('express'),
    fs = require('fs'),
    app = express();

app.get('/', function (req, res) {
    var filePath = "/files/my_pdf_file.pdf";

    fs.readFile(__dirname + filePath , function (err,data){
        res.contentType("application/pdf");
        res.send(data);
    });
});

app.listen(3000, function(){
    console.log('Listening on 3000');
});

Для полного репо:

Клон node -cheat pdf_browser, запустите node app, а затем npm install express.

Счастливая помощь!

Ответ 5

На самом деле экспресс имеет функцию для отправки файлов на удаленный. Все, что тебе нужно:

app.get('/home', function(req, res) {
  res.sendFile(__dirname + "/static/pdf/Rabbi.pdf");
})

Здесь сервер отправит файл "Rabbi.pdf", и он откроется в браузере так же, как вы открываете pdf в браузере. Я поместил файл в "статическую" папку, но вы можете разместить его где угодно, зная, что sendFile() принимает в качестве аргумента абсолютный путь (а не относительный).