你知道什么是标签函数么?

大家好,我卡颂。

JS中有一类特殊的函数 ------ 标签函数,用于自定义模版字符串的处理逻辑。

不同于一般函数形如fn(argA, argB)的执行方式,标签函数可以直接跟在模版字符串前面,比如:

js 复制代码
tagFn`hello ${name}`

本文来聊聊标签函数都有哪些有意思的应用。

欢迎围观朋友圈、加入人类高质量前端交流群,带飞

内置的标签函数

JS中只有一个内置标签函数 ------ String.raw,用于获取模字符串的原始字符串形式,即:

  • 处理替换(例如替换${name}为变量实际的值)

  • 不处理转义序列(例如 \n)

对于如下代码:

js 复制代码
const name = 'Ka Song';

const s1 = `Hello \n ${name}`
const s2 = String.raw`Hello \n ${name}`

console.log分别打印s1s2的结果如下:

之所以s1有换行符,而s2没有,是因为默认情况,模版字符串会处理转义字符(比如这里的\n),而String.raw不会处理。

要实现一个简易的String.raw也很简单,比如下面的myRaw,其中:

  • strings参数是保存原始字符串的数组

  • values参数是保存所有替换变量的数组

js 复制代码
function myRaw(strings, ...values) {
    let result = '';
    for (let i = 0; i < strings.length; i++) {
        result += strings.raw[i] || strings[i];
        if (i < values.length) {
            result += values[i];
        }
    }
    return result;
}

对于模版字符串你好${1}我是${2}${3}谢谢

  • strings参数如下:
js 复制代码
["你好", "我是", "", "谢谢"]
  • values参数如下:
js 复制代码
[1, 2, 3]

myRaw方法会依次从stringsvalues中取值拼接字符串。

身份标签

标签函数的一个有意思的应用场景是定义身份标签 ,也就是告诉编译器接下来这段模版字符串是什么语言

举个例子,我们在JS文件中定义两个变量(markupstyle),IDE此时只认为这是两个普通的模版字符串(没有语法高亮):

现在,我们将String.raw分别重命名为htmlcss

js 复制代码
const html = String.raw;
const css = String.raw;

IDE有了提示信息后,就能根据提示中的语言对模版字符串进行高亮了:

自定义标签函数

刚才我们已经实现了String.raw的简易版本,在此基础上做一点修改,就能实现一个将模版字符串转换为大写形式的标签函数:

js 复制代码
function upperCase(strings, ...values) {
  let result = "";
  for (let i = 0; i < strings.length; i++) {
    result += strings[i];
    if (i < values.length) {
      result += values[i];
    }
  }
  return result.toUpperCase();
}

使用方式如下:

js 复制代码
let x = "Hello";
let y = "kasong";
const result = upperCase`${x}, ${y}!`; 

输出:

复制代码
HELLO, KASONG!

大体来说,标签函数的应用场景可以分为几类:

1. 语法校验

比如,对于HTML字符串,可以使用标签函数来自动转义模板字符串中的特殊字符,以防止XSS(跨站脚本攻击)。下面是一个代码示例:

js 复制代码
function safeHtml(strings, ...values) {
  let result = strings[0];
  for (let i = 1; i < strings.length; i++) {
    let val = String(values[i - 1]);
    result += val.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;");
    result += strings[i];
  }
  return result;
}

使用方式如下:

js 复制代码
let userSuppliedInput = "<img src=x onerror=alert('XSS')>";
const result = safeHtml`<div>${userSuppliedInput}</div>`;

输出:

html 复制代码
<div>&lt;img src=x onerror=alert('XSS')&gt;</div>

对于后端应用,可以创建一个标签函数,用于转义SQL语法中不安全的部分,防止SQL注入。

2. 国际化和本地化

标签函数可以用于处理模板字符串中的文本,使其根据用户的语言和地区进行适当的转换。

3. 创建DSL

标签函数可以用于解析模板字符串中的特定语法,从而创建DSL(领域特定语言)。

比如,可以实现一个css标签函数,解析字符串中的css语法。使用方式如下:

js 复制代码
const style = css`color: ${color}; font-size: ${fontSize}px;`;

总结

标签函数属于ES6特性,所以整体兼容性很不错:

当我们需要处理模版字符串时,可以考虑自定义一个标签函数。

相关推荐
崔庆才丨静觅5 小时前
hCaptcha 验证码图像识别 API 对接教程
前端
passerby60616 小时前
完成前端时间处理的另一块版图
前端·github·web components
掘了6 小时前
「2025 年终总结」在所有失去的人中,我最怀念我自己
前端·后端·年终总结
崔庆才丨静觅6 小时前
实用免费的 Short URL 短链接 API 对接说明
前端
崔庆才丨静觅6 小时前
5分钟快速搭建 AI 平台并用它赚钱!
前端
崔庆才丨静觅7 小时前
比官方便宜一半以上!Midjourney API 申请及使用
前端
Moment7 小时前
富文本编辑器在 AI 时代为什么这么受欢迎
前端·javascript·后端
崔庆才丨静觅7 小时前
刷屏全网的“nano-banana”API接入指南!0.1元/张量产高清创意图,开发者必藏
前端
剪刀石头布啊7 小时前
jwt介绍
前端
爱敲代码的小鱼7 小时前
AJAX(异步交互的技术来实现从服务端中获取数据):
前端·javascript·ajax