Как работать с IF-заявлением в шаблоне с усами?
Я использую усы. Я создаю список уведомлений. Объект 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"}]
С усами, как я могу сделать заявление if или case case на основе notified_type
& action
...
Если notified_type == "Friendship"
оказывать......
Если notified_type == "Other && action == "invite"
делают.....
Как это работает?
5 ответов
Шаблоны усов по дизайну очень просты; домашняя страница даже говорит:
Шаблоны без логики.
Таким образом, общий подход заключается в том, чтобы сделать вашу логику в 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}}
Если вам нужна более продвинутая функциональность, но вы хотите сохранить большую часть простоты усов, вы можете взглянуть на Handlebars:
Рули обеспечивают необходимую мощность, позволяющую эффективно создавать семантические шаблоны без каких-либо разочарований.
Шаблоны усов совместимы с Handlebars, поэтому вы можете взять шаблон Mustache, импортировать его в Handlebars и начать пользоваться дополнительными функциями Handlebars.
Просто посмотрел документы на усы, и они поддерживают "перевернутые разделы", в которых они заявляют
они (инвертированные секции) будут отображаться, если ключ не существует, имеет значение false или является пустым списком
http://mustache.github.io/mustache.5.html
{{#value}}
value is true
{{/value}}
{{^value}}
value is false
{{/value}}
В общем, вы используете #
синтаксис:
{{#a_boolean}}
I only show up if the boolean was true.
{{/a_boolean}}
Цель состоит в том, чтобы убрать как можно больше логики из шаблона (что имеет смысл).
У меня есть простой и общий хак для выполнения оператора ключ / значение 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;
}
С этим хаком, такой объект:
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:00 -
var123>0
для целочисленной переменной var123 больше 0 -
key[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}>0`;
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);
используйте (Node-Red):
msg.payload = global.get('prepMustache')(msg.payload)