Node.js, Express, Jade - Грешка: Не могат да се зададат заглавки след изпращането им

Получавам следната грешка, когато се опитвам да създам HTML страница с помощта на Jade. Някой друг имал ли е този проблем. По-долу отбелязах къде точно е причинена грешката.

Грешка

Error: Can't set headers after they are sent.
    at ServerResponse.OutgoingMessage.setHeader (http.js:644:11)
    at ServerResponse.res.setHeader (/Users/dereklo/node_modules/express/node_modules/connect/lib/patch.js:59:22)
    at ServerResponse.res.set.res.header (/Users/dereklo/node_modules/express/lib/response.js:475:10)
    at ServerResponse.res.contentType.res.type (/Users/dereklo/node_modules/express/lib/response.js:350:15)
    at ServerResponse.res.send (/Users/dereklo/node_modules/express/lib/response.js:111:14)
    at res.render.fn (/Users/dereklo/node_modules/express/lib/response.js:672:10)
    at Object.exports.render (/Users/dereklo/node_modules/jade/lib/jade.js:216:5)

Изходен код Node.js/Express/Jade

var http = require('http'),
    express = require('express'),
    jade = require('jade'),
    url = require('url'),
    jsdom = require('jsdom'),
    child_proc = require('child_process'),
    w,
    h,
    scripts = ["/Users/dereklo/Node/pie/d3.min.js",
                "/Users/dereklo/Node/pie/d3.v2.js",
               "/Users/dereklo/Node/pie/d3.layout.min.js",
               "/Users/dereklo/Node/pie/RadialScriptMobileServ.js",
               "/Users/dereklo/Node/pie/RadialScriptMobile.js",
               "/Users/dereklo/Node/pie/canvg.js"];

      //scripts = ["./d3.v2.js",
        //         "./d3.layout.min.js",
          //       "./pie.js"]

    htmlStub = '<!DOCTYPE html><div id="RadialScriptMobileServ"></div>',
   querystring = require("querystring"),
    fs = require("fs"),
    formidable = require("formidable"),
    path = require('path'),
    request = require('request')
    svgsrc = '';



//create an app server
var app = require('express').createServer();
//set path to the views (template) directory
app.set('views', __dirname + '/views');
//set path to static files
app.use(express.static(__dirname + '/../public'));
//handle GET requests on /
app.get('/', function(req, res){



 res.writeHead(200, {'Content-Type': 'text/plain'});

  w = (url.parse(req.url, true).query['width']);
  h = (url.parse(req.url, true).query['height']);

console.log("width: ",w);
console.log("height: ",h);

request("http://dcaps-staging.media.mit.edu:8080/api/reality_analysis_service/get_reality_analysis_data?document_key=radialData&bearer_token=8e2f9e3129", function (err, result, json) {
  json = JSON.parse(json);

   console.log("my radial data: ",json.radialData.data);


    jsdom.env({features:{QuerySelector:true}, html:htmlStub, scripts:scripts, done:function(errors, window) {

    svgsrc = window.insertRadial("#RadialScriptMobileServ",w,h,json).innerHTML;
    console.log(svgsrc);
       res.render('/Users/dereklo/Node/pie/Jade_radial.jade', {pageTitle: 'Franz Enzenhofer'});   // ERROR OCCURRING HERE!


             //  res.write(svgsrc);
                res.end();

     }})
    })

});
//listen on localhost:3000
app.listen(3000);

//console.log('Pie SVG server running at http://127.0.0.1:3000/');

person Apollo    schedule 26.07.2012    source източник


Отговори (3)


Проблемът ми беше, че трябваше да премахна:

res.writeHead(200, {'Content-Type': 'text/plain'});

Сега работи перфектно. Надявам се, че това ще помогне на други, които случайно попаднат на тази публикация...

person Apollo    schedule 26.07.2012

Можете да го направите по два начина. Или добавете друг маршрут над вашия app.get(/ ..) като този:

// global controller
app.get('/*',function(req,res,next){
    res.header('Content-Type': 'text/plain' , 0 );
    next(); // http://expressjs.com/guide.html#passing-route control
});

Или можете да добавите функция за средно оборудване към вашия съществуващ маршрут

addToHeader = function (req, res, next) {
  console.log("add to header called ... " + req.url);
  res.header('Content-Type': 'text/plain', '0');
  next();
}
and then change your routes to sth like this:

app.get('/', addToHeader, function(req,res){
  var stuff = { 'title': 'blah' };
  res.render('mytemplate',stuff);
});
person Mike S.    schedule 26.07.2012

Когато използвате res.render(), не е необходимо да обработвате отговора ръчно (res.end(), res.writeHead() и т.н.).

person Alen Siljak    schedule 06.09.2012