我在用小胡子。我正在生成通知列表。通知 JSON 对象如下所示:
[{"id":1364,"read":true,"author_id":30,"author_name":"Mr A","author_photo":"image.jpg","story":"wants to connect","notified_type":"Friendship","action":"create"}]
留着小胡子,我如何根据
notified_type
&action
...做一个if语句或case语句...
如果
notified_type == "Friendship"
渲染......
如果
notified_type == "Other && action == "invite"
渲染......
这是如何运作的?
刚刚看了一下小胡子文档,他们支持他们声明的“倒置部分”
如果键不存在、为假或为空列表,它们(反转部分)将被渲染
http://mustache.github.io/mustache.5.html#Inverted-Sections
{{#value}}
value is true
{{/value}}
{{^value}}
value is false
{{/value}}
小胡子模板在设计上非常简单; 主页甚至说:
无逻辑模板。
所以一般的方法是在 JavaScript 中做你的逻辑并设置一堆标志:
if(notified_type == "Friendship")
data.type_friendship = true;
else if(notified_type == "Other" && action == "invite")
data.type_other_invite = true;
//...
然后在你的模板中:
{{#type_friendship}}
friendship...
{{/type_friendship}}
{{#type_other_invite}}
invite...
{{/type_other_invite}}
如果你想要一些更高级的功能,但又想保持 Mustache 的大部分简单性,你可以看看 Handlebars:
Handlebars 提供了必要的功能,让您可以毫无挫折地有效构建语义模板。
Mustache 模板与 Handlebars 兼容,因此您可以使用 Mustache 模板,将其导入 Handlebars,然后开始利用额外的 Handlebars 功能。
通常,您使用
#
语法:
{{#a_boolean}}
I only show up if the boolean was true.
{{/a_boolean}}
目标是将尽可能多的逻辑移出模板(这是有道理的)。
我有一个简单而通用的 hack 来执行键/值 if 语句,而不是在小胡子中仅使用布尔值(并且以一种非常可读的方式!):
function buildOptions (object) {
var validTypes = ['string', 'number', 'boolean'];
var value;
var key;
for (key in object) {
value = object[key];
if (object.hasOwnProperty(key) && validTypes.indexOf(typeof value) !== -1) {
object[key + '=' + value] = true;
}
}
return object;
}
有了这个 hack,一个像这样的对象:
var contact = {
"id": 1364,
"author_name": "Mr Nobody",
"notified_type": "friendship",
"action": "create"
};
变身前会是这个样子:
var contact = {
"id": 1364,
"id=1364": true,
"author_name": "Mr Nobody",
"author_name=Mr Nobody": true,
"notified_type": "friendship",
"notified_type=friendship": true,
"action": "create",
"action=create": true
};
您的小胡子模板将如下所示:
{{#notified_type=friendship}}
friendship…
{{/notified_type=friendship}}
{{#notified_type=invite}}
invite…
{{/notified_type=invite}}
基于@françois-dispaux 解决方案,我编写了一个名为
prepMustache
的递归变体浏览多级对象并为所有孩子添加key=value
键,但也:
hasTimexxx
变量 timexxx 大于 00:00:00var123>0
整数变量 var123 大于 0key[i]=value
用于子数组我还将这个函数放在全局范围内,以便在我的 Node-Red 项目中随处使用它。
const prepMustache = (function (object) {
for (const key in object) {
const value = object[key];
const keyWithVal = `${key}=${value}`;
// IS STRING, INT or BOOL
if (typeof value === 'string' || typeof value === 'number' || typeof value === 'boolean') {
object[keyWithVal] = true;
// INT greater than zero
if (typeof value === 'number' && Number.isInteger(value) && value > 0) {
const intKeyWithValue = `${key}>${value}`;
object[intKeyWithValue] = true;
}
// TIME (format 00:00:00) greater than 00:00:00
else if (typeof value === 'string' && /^([0-9]{2}:){2}[0-9]{2}$/.test(value)) {
const timeArray = value.split(':');
const hours = parseInt(timeArray[0]);
const minutes = parseInt(timeArray[1]);
const seconds = parseInt(timeArray[2]);
if (hours > 0 || minutes > 0 || seconds > 0) {
const timeKey = `has${key.charAt(0).toUpperCase() + key.slice(1)}: true`;
object[timeKey] = true;
}
}
}
// IS SUB-ARRAY
else if (Array.isArray(value)) {
value.forEach((val, i) => {
if (typeof val === 'object') {
prepMustache(val);
} else {
const arrKeyWithVal = `${key}[${i}]=${val}`;
object[arrKeyWithVal] = true;
}
});
}
// IS SUB-OBJECT
else if (typeof value === 'object') {
prepMustache(value);
}
}
return object;
});
// Add this for NodeRed global scope only
global.set('prepMustache', prepMustache);
使用:
vars = prepMustache(vars);
使用(节点-红色):
msg.payload = global.get('prepMustache')(msg.payload)