What I'm trying to achieve
Server is a Node.js application. I'd like to share code with the client as Jade template helpers (for functions) or globals (for objects/variables). New helpers and globals should be available in every client template. This question is NOT about adding helpers to Jade when jade is used server-side.
Server是Node.js应用程序。我想与客户端共享代码作为Jade模板助手(用于函数)或全局变量(用于对象/变量)。每个客户端模板都应该有新的帮助器和全局变量。这个问题不是关于在服务器端使用jade时向Jade添加帮助程序。
The code
I wrote a RequireJS wrapper for Jade compile()
function, passing the locals
object (filled with properties to share) inside options
:
我为Jade compile()函数编写了一个RequireJS包装器,在选项中传递locals对象(填充了要共享的属性):
// ./wrappers/jade.js
define(['jade', 'moment', 'lodash'], function (Jade, moment, _) {
return {
compile: function (str, options) {
options.locals = _.extend({
moment: moment, // moment function
bar: 'foo', // Custom bar variable
foo: function () { return 'bar'; } // Custom foo function
}, options.locals);
return Jade.compile(str, options);
}
};
});
Problems and oddities
When I try to use moment
it works fine:
当我尝试使用时刻它工作正常:
p!= moment().format() //- Works: <p>2013-07-10T13:57:12+02:00</p>
However, accessing the custom variable bar
gives me no errors but an empty <p>
:
但是,访问自定义变量栏不会给我带来任何错误,只有空
:
p #{bar} //- No errors but: <p></p>
When I try to call the custom function foo()
it gives me an error ("undefined is not a function"):
当我尝试调用自定义函数foo()时,它给出了一个错误(“undefined不是函数”):
p= foo() //- Uncaught TypeError: undefined is not a function
So, how am I supposed to use the locals options in the (client) Jade compile()
function, for sharing code between the server and the client?
那么,我应该如何使用(客户端)Jade compile()函数中的locals选项来共享服务器和客户端之间的代码?
Updates
Update 1: as per @explunit comment, renaming the property moment
into localmoment
(inside options.locals
), gives me an error undefined is not a function with the template p= localmoment().format()
. I can't understand why...
更新1:根据@explunit注释,将属性时刻重命名为localmoment(在options.locals中),给我一个错误undefined不是模板p = localmoment()。format()的函数。我不明白为什么......
Update 2: the solution proposed by @Isaac Suttell (expression function instead of anonymus one) doesn't work, I'm getting the same error with p= foo()
.
更新2:@Isaac Suttell提出的解决方案(表达式函数而不是anonymus one)不起作用,我在p = foo()时得到了同样的错误。
2 个解决方案
#1
3
The call to moment().format()
only works because moment
is a global variable, so it's not being passed in at all into your template.
对moment()。format()的调用只能起作用,因为moment是一个全局变量,所以它根本不会传入你的模板。
The only way i know to get a function in to the template is trough the model it self. There might be better ways but i got this to work.
我知道将函数放入模板的唯一方法就是通过自己的模型。可能有更好的方法,但我让这个工作。
define(['jade', 'moment', 'lodash'], function (Jade, moment, _) {
return {
compile: function (str, options) {
var compileFunction = Jade.compile(str, options);
return function(){
// augment the model with the functions/vars you need
arguments[0] = _.extend(arguments[0] || {}, {
foo: function() { return "bar"; },
bar: "foo"
});
return compileFunction.apply(null, arguments)
}
}
};
});
Then if you define your template like this
然后,如果您像这样定义模板
p #{bar}
p= foo()
Everything should work nicely.
一切都应该很好地工作。
#2
0
Try defining your function as expression function instead of an anonymous function:
尝试将函数定义为表达式函数而不是匿名函数:
define(['jade', 'moment'], function (Jade, moment) {
return {
compile: function (str, options) {
var bar = function () { return 'bar'; }; // Function defined here instead
options.locals = _.extend({
'moment': moment,
'foo': bar
}, options.locals);
return Jade.compile(str, options);
};
}
);
#1
3
The call to moment().format()
only works because moment
is a global variable, so it's not being passed in at all into your template.
对moment()。format()的调用只能起作用,因为moment是一个全局变量,所以它根本不会传入你的模板。
The only way i know to get a function in to the template is trough the model it self. There might be better ways but i got this to work.
我知道将函数放入模板的唯一方法就是通过自己的模型。可能有更好的方法,但我让这个工作。
define(['jade', 'moment', 'lodash'], function (Jade, moment, _) {
return {
compile: function (str, options) {
var compileFunction = Jade.compile(str, options);
return function(){
// augment the model with the functions/vars you need
arguments[0] = _.extend(arguments[0] || {}, {
foo: function() { return "bar"; },
bar: "foo"
});
return compileFunction.apply(null, arguments)
}
}
};
});
Then if you define your template like this
然后,如果您像这样定义模板
p #{bar}
p= foo()
Everything should work nicely.
一切都应该很好地工作。
#2
0
Try defining your function as expression function instead of an anonymous function:
尝试将函数定义为表达式函数而不是匿名函数:
define(['jade', 'moment'], function (Jade, moment) {
return {
compile: function (str, options) {
var bar = function () { return 'bar'; }; // Function defined here instead
options.locals = _.extend({
'moment': moment,
'foo': bar
}, options.locals);
return Jade.compile(str, options);
};
}
);