Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: 改善 find 方法以更好的查找所需内容 #119

Open
wll8 opened this issue Dec 23, 2021 · 1 comment
Open

feat: 改善 find 方法以更好的查找所需内容 #119

wll8 opened this issue Dec 23, 2021 · 1 comment

Comments

@wll8
Copy link

wll8 commented Dec 23, 2021

初学 ggc, 我的理解是它提供了一种基于特征来操作内容的方法来避免 ast 的繁琐操作, 提此 issues 是希望选择器更直观易用, 愚议轻拍, 手动狗头~

用例

假设以下场景: 获取 vue 中 export default 下的 data 对象

当 data 是函数的时候, 使用 find 查找到第一层内容

  let code
  let dataObj
  code = `
    export default {
      data() {
        const fn = () => {}
        return {
          a: 123,
          b(){
            const fn = () => {}
            return {
              a: 456,
            }
          }
        }
      }
    }
  `
  dataObj = $(code).find(`export default {}`).find(`return $_$obj`).match
    .obj[0].value
  console.log(`dataObj`, dataObj)
dataObj {
  a: 123,
  b(){
    const fn = () => {}
    return {
      a: 456,
    }
  }
}

但是, 当 data 不是函数且孙级作用域下有相似特征但其实不符合条件时也被查找到了, 导致用例失败

  code = `
    export default {
      data: {
        a: 123,
        b(){
          const fn = () => {}
          return {
            a: 456,
          }
        }
      }
    }
  `
{
  a: 456,
}

为了避免这种情况, 我们不得不编写额外的逻辑来单独处理此问题

jquery 是如何方便的查找到想要的内容呢?

有以下考虑: 在 jq 中因为是基于 dom 操作的, 有强大的 css 选择器/xpath 可用, 并且 jq 本身也扩展了一些选择器.
这使得要查找例如 父元素/子元素/首个/每个/属性/类型 都不在话下, 且不需要额外的学习成本

但是在 ast 中是否有类似的选择器可用吗? 如果没有, 那么 ast 可以用 json 表示的话, 是可以利用 json 社区的选择器?
参考:

伪代码 - 类 css 选择器

目前的 find 方法支持 string | node 参数. 如果考虑兼容现有参数的模式下, 是否可以使用数组来进行选择器优化?
例: 获取 vue 中 export default 下的 data 对象

  $(code).find([`export default {}`, `>`, `return $_$obj`])

可以注意到, 以上代码其实类似于 css 选择器的 div > p:

$(code).find([
  `export default {}`, // 特征
  `>`, // 关系符, 表示只在父作用域下查找下一个特征
  `return $_$obj` // 特征
])

当然要实现一个功能特性可能要考虑比较多的其他情况, 以上修改方式可能造成 ggc 的代码修改过多.

伪代码 - 为 find 添加新选项.

这应该是 ggc 修改代码较少的方法.

$(code)
  .find(`export default {}`)
  .find(`return $_$obj`, {
    scopeDeep: 1, // 作用域级别1
    scopeDeep: `>`, // 或作用域关系表示符
  })
@wll8 wll8 changed the title 改善 find 方法以更好的查找所需内容 feat: 改善 find 方法以更好的查找所需内容 Dec 23, 2021
@wll8
Copy link
Author

wll8 commented Dec 23, 2021

补充用例: 例如以下代码, 要求限定在第一个 x() 的作用域下找 return {}

  • 期望: 找不到才对
  • 实际: 由于孙作用域里也有一个符合规则的 x(){return {}} 所以查找错了
  const code = `
    function x() {
      const o = {
        a: 123,
        b(){
          const fn = function x() {}
          function x() {
            return {
              a: 456,
              b(){
                const fn = function x() {}
                return {
                  a: 789,
                }
              }
            }
          }
        }
      }
    }
  `
  const dataObj = $(code).find(`function x() {}`).find(`return $_$obj`).match
    .obj[0].value
  console.log(`basebase`, dataObj)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant