2017-09-11 4 views
0

Ich arbeite an einer MEAN-Stack-App und ich versuche, eine PDF aus dem Backend (Express) im Frontend (Angular) anzuzeigen. Aber jedes Mal wird die Datei während der Übertragung beschädigt. Hat jemand eine Idee? Hier ist meine Codes (vereinfacht):Express Angular - Dienen PDF

Backend:

import * as express from "express"; 
import * as fs from "fs"; 

myController.getPdf(req:express.Request, res:express.Response):void { 
    res.setHeader('Content-Type', 'application/pdf'); 
    res.setHeader('Content-Length', fs.statSync('myPdf.pdf').size); 
    fs.createReadStream('myPdf.pdf).pipe(res); 
} 

Frontend:

import {Http,ResponseContentType} from "@angular/http"; 

constructor(@Inject(Http) private _http:Http) {} 

this._http.get('ENDPOINT', {responseType: ResponseContentType.ArrayBuffer}) 
    .map(response => { 
     window.open(URL.createObjectURL(
      new Blob([response],{type:'application/pdf'}) 
))}); 

Edit: Middle:

import * as compression from "compression"; 
import * as zlib from "zbil"; 
import * as express from "express"; 
import * as bodyParser from "body-parser"; 
import * as session from "express-session"; 
import * as passport from "passport"; 
import * as morgan from "morgan"; 
import * as helmet from "helmet"; 

application: express.Application; 
let _root = process.cwd(); 

application.use(compression({ 
    level: zlib.Z_BEST__COMPRESSION, 
    threshold: "1kb" 
})); 
application.use(express.static(_root + "/node_modules/")); 
application.use(express.static(_root + "/jspm_packages/")); 
application.use(express.static(_root + "/client/dev/")); 
application.use(bodyParser.json()); 
application.use(session({ 
    secret: 'abcd', 
    saveUnitialized: true, 
    resave: true, 
})); 
application.use(passport.initialize()); 
application.use(passport.session()); 
application.use(morgan("dev")); 
application.use(helmet()); 

Antwort

0

Ich denke, Ihre "Content-Length" Header ist nicht gültig. Größenmethoden des Dateisystems geben die Zeichenfolgenlänge in Zeichen zurück.

Einige UTF-8-Zeichen enthalten mehrere Bytes.

Der bessere Weg wäre die Verwendung von Buffer.byteLength (string, [encoding]) von http://nodejs.org/api/buffer.html. Es ist eine Klassenmethode, sodass Sie keine Pufferinstanz erstellen müssen.

+0

Hmm ... auch mit dieser Änderung, die Datei in der Ausgabe noch nicht lesbar ist. Ich habe die verwendeten Middlewares hinzugefügt, vielleicht ist einer von ihnen mit meiner Übertragung unordentlich? –

1

Verstanden!

Die Verwendung von fs.statSync ('myFile.pdf'). Größe als Content-Length hat gut funktioniert.

Das Problem war am anderen Ende: die Antwort auf der Blob() Funktion abgebildet werden mußte:

this._http.get(ENDPOINT, {responseType: ResponseContentType.ArrayBuffer}) 
    .map(response => { 
     window.open(URL.createObjectURL(
      new Blob(response.blob(), {type:'application/pdf'})); 
    });