让 ast-grep 听你的:指定语言解析 Vue/TSX/JSX 全流程

接上一篇博客: ast-grep:结构化搜索与重构利器ast-grep 的主要论点是在文本 grep 与重量级 AST 工具之间建立一座 - 掘金

在多语言项目里,文件扩展名未必等于想要的解析语法:比如 .vue 内嵌 <script setup lang="tsx">,但默认解析器可能把整文件当成 Vue 语法,导致 TS/TSX 规则匹配不到。ast-grep 提供两条路可以"强制"指定解析语言:

  1. 命令行临时指定 --lang
  2. 在规则/配置文件里用 language 覆盖。 本文给出可直接复用的命令、配置示例,以及在 Vue/Pug 场景下的避坑方案。

方法一:命令行临时指定语言

适合一次性查询或快速验证模式。

基本用法

bash 复制代码
sg run --lang tsx -p 'defineProps($P)' src/views/yufukuan/Yufukuan.vue
  • --lang tsx:强制把输入文件按 TSX 解析,即使扩展名是 .vue
  • -p 'defineProps($P)':模式示例,可替换成任意 TS/TSX 语法模式。

如果模板干扰解析

  • 现有 tree-sitter-vue 对 lang="pug" 模板不做 AST 解析,命令会把模板当作文本,可能触发 ERROR。
  • 解决思路:
    1. 仅喂 <script> 部分:先用脚本提取 <script>,再通过 stdin 传给 sg。

      bash 复制代码
      node -e "const fs=require('fs');const txt=fs.readFileSync('src/views/yufukuan/Yufukuan.vue','utf8');const m=txt.match(/<script[\\s\\S]*?<\\/script>/);if(m)process.stdout.write(m[0]);" \
        | sg run --lang tsx --stdin -p 'defineProps($P)'
    2. 临时改模板为普通 HTML(不改需求时就别这么做),确认解析器可工作后再回滚。

只想做文本级匹配

如果解析器对模板报错,可以降级用模板严格度或纯文本:

bash 复制代码
sg run --lang vue --strictness template -p 'handlerEditInst' src/views/**/*.vue

这不会给出 AST 结构,但可在 VSCode/CLI 内快速找关键词。

方法二:在规则/配置里指定语言

适合需要多次复用的规则或集成到 sg scan 的场景。

规则文件示例

新建规则 rules/vue-script-tsx.yml

yaml 复制代码
id: vue-script-tsx-define-props
language: tsx            # 这里强制按 TSX 解析
rule:
  pattern: "defineProps($P)"

要让规则只作用于指定路径,可以配合 files 或在运行时用 --globs

bash 复制代码
sg scan --config sgconfig.yml --globs "src/**/*.vue" --rules vue-script-tsx-define-props

说明:

  • language 字段覆盖扩展名默认解析器。
  • 模式仍需符合该语言语法;若模板残留会导致 ERROR,可结合"只喂脚本"或在规则里增加条件过滤。

针对 JS/JSX 的示例

yaml 复制代码
id: vue-script-jsx-import-check
language: jsx
rule:
  pattern: "import $A from '$B'"

运行:

bash 复制代码
sg scan --config sgconfig.yml --globs "src/**/*.vue" --rules vue-script-jsx-import-check

常见问题与处理

  • "Pattern contains an ERROR node":
    • 解析器在遇到模板/非目标语法时产生错误。尝试提取 <script> 后再解析,或临时移除 Pug 语法测试。
  • "matched nothing" 且无错误:
    • 确认模式语法合法;用 --debug-query=pattern 查看解析结果。
  • VSCode 插件无结果但 CLI 正常:
    • VSCode 也依赖同一解析器,对 Pug/TSX 一样受限。可在插件里用文本模式,或等待支持更好的解析器。

实操建议(Vue 项目)

  1. 先在 CLI 验证:

    bash 复制代码
    sg run --lang tsx -p 'defineProps($P)' src/views/foo.vue
  2. 若模板导致 ERROR,先用脚本提取 <script> 再搜。

  3. 需要重复用的查询,写进 rules/*.yml,加上 language: tsx/js/jsx,通过 sg scan --globs "src/**/*.vue" 运行。

  4. 如果必须结构化解析模板层(Pug),要么把模板改为 HTML,要么寻找/自建支持 Pug 的 Vue 解析器重新编译 vue.so

结语

ast-grep 支持在命令行和规则层双重覆写解析语言,这让你可以在混合文件中对脚本部分进行结构化搜索。但解析器能力是天花板:当模板/脚本语法不被支持时(如 Pug + TSX),需要先裁剪输入或更换解析器,否则只能退化为文本匹配。按照本文的命令与配置示例,可以快速在 Vue 项目里对脚本逻辑做 TS/TSX/JSX 级别的精确查询,而不必等待默认解析器完善。***

相关推荐
德育处主任1 分钟前
在小程序做海报的话,Painter就很给力
前端·微信小程序·canvas
匠心码员1 分钟前
Git Commit 提交规范:让每一次提交都清晰可读
前端
CDwenhuohuo2 分钟前
uniapp去掉手机状态栏 全屏展示
开发语言·javascript·uni-app
骑斑马的李司凌2 分钟前
调试时卡半天?原来127.0.0.1和localhost的区别这么大!
前端
哈哈O哈哈哈3 分钟前
Electron + Vue 3 + Node.js 的跨平台桌面应用示例项目
前端
ycbing4 分钟前
设计并实现一个 MCP Server
前端
千寻girling4 分钟前
面试官: “ 说一下怎么做到前端图片尺寸的响应式适配 ”
前端·javascript·面试
大橘喵喵重4 分钟前
FastAPI 实现国际化(i18n)和多语言支持的完整方案
后端
少莫千华5 分钟前
【Web API】RESTful API接口规范
前端·后端·json·api·restful·rest
用户2345267009825 分钟前
AI会不会悄悄把漏洞甚至后门写进你的代码里
后端·ai编程