2017-02-22 59 views
0

我想在每次調用express express時執行一個函數。在渲染express之前執行函數獲取路由器NodeJS

我知道我可以簡單地將函數放在app.get函數中,但我想多次調用相同的函數。

這裏是我的router.js文件

var Setting = require('../models/setting'); 
module.exports = function(app, passport) { 

// ===================================== 
// HOME PAGE (with login links) ======== 
// ===================================== 
app.get('/', function(req, res) { 
    Setting.findOne(function(err, setting) { 
     if (err) 
      throw err; 
     // console.log(setting); 
     res.render('index', { title: 'eduBird | Reach the glory', setting: setting }); // load the index file 
    }); 
}); 

// ===================================== 
// LOGIN =============================== 
// ===================================== 
// show the login form 
app.get('/login', sabSettings, function(req, res) { 

    // render the page and pass in any flash data if it exists 
    res.render('login', { 
     message: req.flash('loginMessage'), 
     errors: req.flash('error'), 
     title: 'Login | eduBird', 
     setting: setting 
    }); 
}); 

// process the login form 

app.post('/login', passport.authenticate('local-login', { 
    successRedirect: '/profile', 
    failureRedirect: '/login', 
    failureFlash: true 
})); 

// ===================================== 
// SIGNUP ============================== 
// ===================================== 
// show the signup form 
app.get('/signup', function(req, res) { 

    // render the page and pass in any flash data if it exists 
    res.render('signup', { 
     message: req.flash('signupMessage'), 
     errors: req.flash('error'), 
     title: 'Register | eduBird', 
     setting: req.setting 
    }); 
}); 

// process the signup form 
app.post('/signup', passport.authenticate('local-signup', { 
    successRedirect: '/profile', 
    failureRedirect: '/signup', 
    failureFlash: true 
})); 

// app.post('/signup', function(req, res) { 
//  console.log(req); 
// }); 

// ===================================== 
// PROFILE SECTION ===================== 
// ===================================== 
// we will want this protected so you have to be logged in to visit 
// we will use route middleware to verify this (the isLoggedIn function) 
app.get('/profile', isLoggedIn, sabSettings, function(req, res) { 
    res.render('profile', { 
     user: req.user, // get the user out of session and pass to template 
     title: req.user.local.name + "'s profile | eduBird", 
     setting: req.setting 
    }); 
}); 

// ===================================== 
// LOGOUT ============================== 
// ===================================== 
app.get('/logout', function(req, res) { 
    req.logout(); 
    res.redirect('/'); 
}); 
}; 

// route middleware to make sure a user is logged in 
function isLoggedIn(req, res, next) { 

// if user is authenticated in the session, carry on 
if (req.isAuthenticated()) 
    return next(); 

    // if they aren't redirect them to the home page 
    res.redirect('/login'); 
    }; 

function sabSettings(next) { 
Setting.findOne(function(err, setting) { 
    if (err) 
     throw err; 
    console.log('sabSetting function executed'); 
    console.log(setting); 
    console.log('~~~~~~~~~~~'); 
    // return setting; 
    return next(setting); 
}); 
}; 

在這裏,我曾使用過的正在執行罰款isLoggedIn的例子,但相同的是不能爲sabSettings()工作,這將通過所有設置的配置從數據庫到我的/login,/signup,/profile和/或/所有的路線。

console.log(setting)的所有數據返回到我的控制檯,但我得到一個錯誤,指出:

throw er; // Unhandled 'error' event 
^

TypeError: next is not a function 
    at C:\Users\animeshweb\Desktop\projects\eb-v2\routes\routes.js:106:16 

你可以看到,我在app.get('/')嵌入功能得到相同的,但我想這函數在任何我想要的地方執行,所以我需要一個單獨的函數。

更新

更新我routes.js的要求:

function sabSettings(req, res, next) { 
Setting.findOne(function(err, setting) { 
    if (err) 
     next(err); 
    console.log('sabSetting function executed'); 
    console.log(setting); 
    console.log('~~~~~~~~~~~'); 
    req.setting = setting; 
    next(); 
}); 

};

我上面也做了Setting = require(myModelURL),這對route.get'/'工作正常。

*這是我的看法/ layout.pug file`

link(rel='icon', type='image/png', href=setting.logo.logo16 sizes='16x16') 
link(rel='icon', type='image/png', href=setting.logo.logo32 sizes='32x32') 
link(rel='icon', type='image/png', href=setting.logo.logo128 sizes='128x128') 

同樣在adminlayout0.pug工作正常

感謝。

回答

1

您聲明sabSettings錯誤。中間件是三個參數讓你的聲明應該是這樣的:

function sabSetting(req, res, next) { 
    // function logic here 
} 

既然你叫next的說法是錯誤的位置,當你嘗試調用它不是一個功能。我不知道你爲什麼試圖做return next(setting)。這將告訴Express,您正在報告請求中的錯誤。如果你試圖把setting價值的地方,請求處理程序的其他部分可以使用它,那麼你可能希望把它放在req對象,如:

req.setting = setting; // put setting on the req object for other code to use 
next();     // continue routing 

此外,你不應該做的一箇中間件功能中的throw err。這根本不會做任何有用的事情,你的請求可能永遠不會完成。相反,你應該在得到它時處理錯誤。當出現錯誤時,您可以在中間件內分支到備用策略,或者您可以簡單地通過next(err)res.status(500).send(...)返回失敗的請求。

然後,您將需要改變你的res.render()這樣:

res.render('index', { title: 'eduBird | Reach the glory', setting: req.setting }); 

setting變量現在存儲在req對象上,這樣就是你需要參考它。

在你指的是setting的任何地方改變它。

+0

更新我的'sabsetting()'那些提到: 功能sabSettings(REQ,水庫,下一個){ Setting.findOne(函數(ERR,設定){ 如果(ERR) 的console.log( ''sabSetting function executed'); console.log(setting); console.log('~~~~~~~~~~~'); req.setting = setting; next(); }) ; }; 但是它仍然顯示'無法讀取未定義的屬性'標識'的錯誤,我在問題中添加了我的.pug視圖。 –

+0

我剛剛更新了我的問題,還有更多我錯過了route.js'sabsetting()'? –

+0

@AnimeshSingh - 你看過'setting'變量,看看它是否有所需的'setting.logo'屬性嗎?而且,當你調用'res.render()'時,你需要傳遞'setting:req.setting'而不是'setting:setting',因爲這是你存儲'setting'變量的地方。 – jfriend00