如何在node.js中的页面渲染之前加载变量?

时间:2013-07-02 19:22:57

标签: node.js express

我的问题是如何在页面呈现之前确保我的变量被加载?我使用带有express和everyauth的node.js。

这是代码:

app.get('/', function(req, res) {
   app.locals.rep = global.repos;
   res.render('index'); 
});

目前,页面已加载,但包含该变量的段落为空,我收到错误:“无法读取属性'...'未定义[...]”。当我刷新页面时,内容会流入。

index.jade

extends layout
block content
  h1= title
  - if (!everyauth.loggedIn)
    a(href="/auth/github") Login with github
  - else
    h3
      a(href='/logout') Logout
      h3 GitHub User Data
      - each r in rep
        p= r.name
        p= r.description

这是我设置repos变量的地方:

  

var repos;
  global.repos = [];

     

everyauth.github
    .appId(config.gh_clientId)
    .appSecret(config.gh_secret)
    .findOrCreateUser(function(sess,accessToken,accessTokenExtra,ghUser){

if (typeof usersByGhId[ghUser.id] === 'undefined') {

  usersByGhId[ghUser.id] = addUser('github', ghUser);

  var options = { 
            host: "api.github.com", 
            path: "/users/cmarius02/repos",
            method: "GET",
            headers: {
               "User-Agent": "github-connect" 
            }
  };

  var request= https.request(options, function(response){
    var body='';
    response.on("data", function(chunk){
      body+=chunk.toString("utf8");
    });

    response.on("end", function(){
      var json=JSON.parse(body);

      // console.log(json);  

      global.repos = [];
      for (var k in json)
        if ({}.hasOwnProperty.call(json, k)) {
          global.repos.push({
            name: json[k].name,
            description: json[k].description
          });
        }
    });
  });
  request.end();
  return usersByGhId[ghUser.id];

} else {
  return usersByGhId[ghUser.id];
}   })
     

.redirectPath( '/');

这是我在node.js的第一天,所以请耐心等待。提前谢谢。

2 个答案:

答案 0 :(得分:1)

我使用护照代替Everyauth,但我认为方法应该类似

Express使用中间件来链接代码,每个中间件都负责调用下一个代码(即使他们不知道它是哪个)

我这样做:

    app.all ('*', function (req,res,next) {
      // Add the user from the session
      if req.user?
          res.locals.session_user = req.user
      // Add the flash messages
      res.locals.flash_messages = req.flash()

      next()
    });

    app.get('/', function(req, res) {
      res.render('index'); 
    });

app.all表示该路线将匹配get,put和post请求。 *是一个匹配所有路由的正则表达式,因此第一个回调将在所有路由之前调用

req.user由护照填写,我想Everyauth有类似的东西。

res.locals允许您将信息传递给视图。然后,在视图中,你可以只引用元素作为this.session_user(我不使用jade,但你明白了。)

另请注意,使用相同的方法,我将请求之间的闪烁传递给视图。

订单很重要!而next()向您保证,您的实际路线将不会被处理,直到前一个路线没有解决。如果需要,可以在该方法的另一个回调中调用next。

答案 1 :(得分:0)

通过使用Express中间件,您可以通过执行以下操作来覆盖渲染:

  app.use(function(req, res, next) {
    // Grap render
    var _render = res.render;

    // Override logic
    res.render = function(view, options, cb) {
      // Add logic (Example)
      if (!options.foo) {
        options.bar = true
      }

      // Original call
      _render.call(this, view, options, cb)
    }
    next()
  })