我将Node.js与Express和EJS模板一起使用,我想动态管理我的HTML Templace ..
这次,我有:
- server.js
- views/
- - template.ejs
- - layout.ejs
在我的server.js中,我使用数据加载模板视图,并使用<% include %>
在模板上加载布局:
server.js
var data = { some: 'stuff'};
res.render('template', data);
template.ejs
<% include layout %>
在这个时刻,代码工作得很好,我有预期的结果。
但是现在,我想要一个数据变量,说布局的文件名,可以在layouts /目录中找到:
- server.js
- views/
- - template.ejs
- - layouts/
- - - home.ejs
- - - login.ejs
server.js
var data = {
layout_view: 'layouts/home'
};
res.render(template, data);
template.ejs
<% include layout_view %>
但是,变量未被过期,只测试变量的名称,而不是值:
错误:ENOENT,没有这样的文件或目录 “C:\用户\亚瑟\桌面\节点WWW \ G变\视图\ layout_view.ejs
如何使用<% include %>
命令和变量加载视图'views / layouts / home.ejs'?
谢谢大家! :)
答案 0 :(得分:0)
这是我在Express 4中使用的布局(使用ejs测试):
/*
Usage:
Set a global/default layout with:
app.set('view layout', 'bar');
Set a layout per-render (overrides global layout) with:
res.render('foo', { layout: 'bar' });
Or disable a layout if a global layout is set with:
res.render('foo', { layout: false });
If no layout is provided using either of the above methods,
then the view will be rendered as-is like normal.
Inside your layout, the variable `body` holds the rendered partial/child view.
Installation:
Call `mpResponse();` before doing `require('express');` in your application.
*/
function mpResponse() {
var expressResponse = require('express/lib/response'),
expressResRender = expressResponse.render;
expressResponse.render = function(view, options, fn) {
options = options || {};
var self = this,
req = this.req,
app = req.app,
layout,
cb;
// support callback function as second arg
if (typeof options === 'function')
fn = options, options = {};
// merge res.locals
options._locals = self.locals;
// default callback to respond
fn = fn || function(err, str) {
if (err) return req.next(err);
self.send(str);
};
if (typeof options.layout === 'string')
layout = options.layout;
else if (options.layout !== false
&& typeof app.get('view layout') === 'string')
layout = app.get('view layout');
if (layout) {
cb = function(err, str) {
if (err) return req.next(err);
options.body = str;
expressResRender.call(self, layout, options, fn);
};
} else
cb = fn;
// render
app.render(view, options, cb);
};
}
答案 1 :(得分:0)
由Ben Fortune解决了评论:
EJS上尚未提供的功能,因此更新文件 ejs.js 和 lib / ejs.js (ligne~155)
旧代码
if (0 == js.trim().indexOf('include')) {
var name = js.trim().slice(7).trim();
if (!filename) throw new Error('filename option is required for includes');
var path = resolveInclude(name, filename);
include = read(path, 'utf8');
include = exports.parse(include, { filename: path, _with: false, open: open, close: close, compileDebug: compileDebug });
buf.push("' + (function(){" + include + "})() + '");
js = '';
}
新代码
if (0 == js.trim().indexOf('include')) {
var name = js.trim().slice(7).trim();
if (!filename) throw new Error('filename option is required for includes');
// If it is not path, but variable name (Added)
var resolvedObj = null;
var objName = name.split(".");
if (objName) {
resolvedObj = options;
for (var idx=0; idx<objName.length; idx++) {
resolvedObj = resolvedObj[objName[idx]];
if ( ! resolvedObj) {break;}
}
}
if(resolvedObj)
var path = resolveInclude(resolvedObj, filename);
else
var path = resolveInclude(name, filename);
include = read(path, 'utf8');
include = exports.parse(include, options); // Added transfer whole options
buf += "' + (function(){" + include + "})() + '";
js = '';
}
<强>来源强>