js 实现tmpl
在JavaScript中实现一个简单的模板引擎(tmpl)可以通过多种方式完成。以下是几种常见的方法,涵盖基础字符串替换和更高级的解析逻辑:
方法一:基于字符串替换的简单模板引擎
使用正则表达式和字符串替换实现变量插值:
function tmpl(template, data) {
return template.replace(/\{\{(\w+)\}\}/g, (match, key) => {
return data[key] !== undefined ? data[key] : match;
});
}
// 示例用法
const template = 'Hello, {{name}}!';
const data = { name: 'World' };
console.log(tmpl(template, data)); // 输出: Hello, World!
方法二:支持表达式和条件逻辑
通过Function构造函数动态生成函数,支持更复杂的表达式:
function tmpl(template, data) {
const keys = Object.keys(data);
const values = keys.map(key => data[key]);
const func = new Function(...keys, `return \`${template}\`;`);
return func(...values);
}
// 示例用法
const template = 'Result: ${a + b}';
const data = { a: 1, b: 2 };
console.log(tmpl(template, data)); // 输出: Result: 3
方法三:使用标签模板字面量
利用ES6的标签模板功能实现无依赖模板引擎:
function tmpl(strings, ...values) {
return strings.reduce((result, str, i) => {
return result + str + (values[i] || '');
}, '');
}
// 示例用法
const name = 'World';
console.log(tmpl`Hello, ${name}!`); // 输出: Hello, World!
方法四:支持循环和嵌套对象
通过递归和更复杂的正则匹配处理嵌套数据:

function tmpl(template, data) {
return template.replace(/\{\{([^{}]+)\}\}/g, (match, path) => {
const keys = path.trim().split('.');
let value = data;
keys.forEach(key => {
value = value ? value[key] : '';
});
return value !== undefined ? value : match;
});
}
// 示例用法
const template = 'User: {{user.name}}, Age: {{user.age}}';
const data = { user: { name: 'Alice', age: 25 } };
console.log(tmpl(template, data)); // 输出: User: Alice, Age: 25
注意事项
- 安全性:避免直接使用
eval或new Function处理不可信的模板内容,可能导致XSS攻击。 - 性能:复杂模板建议预编译为函数,减少运行时解析开销。
- 扩展性:可根据需求添加过滤器、循环控制等特性(如
{{#each items}})。
如果需要更完整的解决方案,可参考现有库如lodash.template或ejs的实现逻辑。






