Skip to content

[Bug]:JS transform 误转义 API 路径字符串 #903

@Acid-Lemon

Description

@Acid-Lemon

weapp-tailwindcss 版本

4.1.4

tailwindcss 版本

4.1.3

框架 & 小程序平台

uni-app vue3 vite 编译到 微信小程序

最小复现bug的代码仓库链接

No response

复现bug的步骤

环境版本:

  • weapp-tailwindcss: 4.1.4
  • tailwindcss: 4.1.3

在任意已安装 weapp-tailwindcss@4.1.4 的项目中,新建一个最小复现脚本,例如 repro.cjs

const { createContext } = require('weapp-tailwindcss/core');

(async () => {
  const raw = 'call_api("order/get_order_amount", {}, "POST")';

  const result = await createContext().transformJs(raw, {
    runtimeSet: new Set(['order/get_order_amount']),
  });

  console.log(result.code);
})();

执行:

node repro.cjs

实际输出:

call_api("ordersget_order_amount", {}, "POST")

期望输出:

call_api("order/get_order_amount", {}, "POST")

说明:

order/get_order_amount 是普通业务 API 路径,不是 Tailwind 工具类。当前 JS transform 在该字符串命中 runtimeSet 后,会将其中的 / 转义,导致业务请求路径被改写。

在实际 UniApp 小程序项目中,该问题会表现为源码中:

call_api('order/get_order_amount', { order_id }, 'POST')

构建为微信小程序后变成:

call_api("ordersget_order_amount", { order_id }, "POST")

最终请求路径从:

/api/mini/order/get_order_amount

变成:

/api/mini/ordersget_order_amount

后端收到 404。

预期是什么?

JS 中的普通业务字符串不应被改写,尤其是接口路径、路由路径、文件路径这类非 Tailwind class 语义的字符串。

对于如下输入:call_api("order/get_order_amount", {}, "POST")

期望 transformJs 后仍然保持为:call_api("order/get_order_amount", {}, "POST")

也就是说,order/get_order_amount 不应被转换为 ordersget_order_amount。

如果当前默认行为是“只要命中 Tailwind runtimeSet 就会转义 JS 字符串”,也希望能提供更安全的默认策略,或在文档中明确提示:类似 xxx/yyy 的业务路径可能被识别并转义,需要使用 jsPreserveClass / weappTwIgnore 规避。

运行环境

System:
    OS: Windows 11 10.0.26200
    CPU: (32) x64 Intel(R) Core(TM) i9-14900HX
    Memory: 6.98 GB / 31.67 GB
  Binaries:
    Node: 22.20.0 - C:\nvm4w\nodejs\node.EXE
    Yarn: 1.22.22 - C:\Users\xxxxx\AppData\Roaming\npm\yarn.CMD
    npm: 11.6.2 - C:\Users\xxxxx\AppData\Roaming\npm\npm.CMD
    pnpm: 9.15.4 - C:\Users\xxxxx\AppData\Roaming\npm\pnpm.CMD
  npmPackages:
    @dcloudio/types: ^3.4.14 => 3.4.14 
    @dcloudio/uni-app: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-app-harmony: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-app-plus: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-automator: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-cli-shared: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-components: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-h5: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-alipay: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-baidu: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-jd: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-kuaishou: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-lark: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-qq: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-toutiao: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-weixin: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-mp-xhs: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-quickapp-webview: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/uni-stacktracey: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @dcloudio/vite-plugin-uni: 3.0.0-4050720250324001 => 3.0.0-4050720250324001 
    @tailwindcss/postcss: ^4.1.3 => 4.1.3 
    @uni-helper/vite-plugin-uni-components: ^0.2.0 => 0.2.0 
    @vue/runtime-core: ^3.5.13 => 3.5.13 
    @vue/tsconfig: ^0.7.0 => 0.7.0 
    @weapp-tailwindcss/merge: ^1.1.0 => 1.1.0 
    nutui-uniapp: ^1.8.4 => 1.8.4 
    pinia: ^3.0.2 => 3.0.2 
    sass: ^1.91.0 => 1.91.0 
    sass-loader: ^16.0.5 => 16.0.5 
    tailwindcss: ^4.1.3 => 4.1.3 
    typescript: ^5.8.3 => 5.8.3 
    unplugin-auto-import: ^19.2.0 => 19.2.0 
    vite: 6.3.4 => 6.3.4 
    vue: ^3.5.13 => 3.5.13 
    vue-i18n: 11.1.10 => 11.1.10 
    vue-tsc: ^2.2.8 => 2.2.8 
    weapp-ide-cli: ^2.0.10 => 2.0.10 
    weapp-tailwindcss: ^4.1.4 => 4.1.4

其他附加信息

补充信息:

这个问题不是 UniApp 或微信开发者工具单独导致的,使用 weapp-tailwindcss/corecreateContext().transformJs() 可以最小复现。

项目中实际遇到的情况是:

源码:$.call_api('order/get_order_amount', { order_id }, 'POST')

构建后的微信小程序产物:n.call_api("ordersget_order_amount", { order_id: e }, "POST")

后端日志中实际收到的请求路径:POST /api/mini/ordersget_order_amount

因此接口 404。

目前项目中可以通过 jsPreserveClass 临时规避:

UnifiedViteWeappTailwindcssPlugin({
  rem2rpx: true,
  jsPreserveClass: keyword => /^[a-z0-9_]+(?:\/[a-z0-9_]+)+$/.test(keyword),
})

加上该配置后,重新构建微信小程序产物,order/get_order_amount 可以保持不变。

我理解文档中已经说明可以使用 weappTwIgnore 或 ignoreTaggedTemplateExpressionIdentifiers 精确忽略部分 JS 字符串。但这个 case 中的问题是普通业务 API 路径被默认转义,调用点可能很多,逐个加 weappTwIgnore 容易遗漏。希望能考虑在默认 JS transform 策略中减少对非 class 语义字符串的误伤,或者在文档中明确提示 API path / route path / file path 这类字符串可能需要使用 jsPreserveClass 保护。

Metadata

Metadata

Assignees

Labels

bugSomething isn't working

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions