美文网首页
babel插件的使用和AST抽象语法树

babel插件的使用和AST抽象语法树

作者: 戴发夹的格格巫 | 来源:发表于2020-06-17 15:14 被阅读0次

    AST抽象语法树

    代码都可以拆解成抽象语法树,语法树解析网站:https://astexplorer.net/

    作用:AST不依赖于具体的文法,不依赖于语言的细节,我们将源代码转化为AST后,可以对AST做很多的操作,包括一些你想不到的操作,这些操作实现了各种各样形形色色的功能,

    简介:抽象语法树(abstract syntax code,AST)是源代码的抽象语法结构的树状表示,树上的每个节点都表示源代码中的一种结构,这所以说是抽象的,是因为抽象语法树并不会表示出真实语法出现的每一个细节,比如说,嵌套括号被隐含在树的结构中,并没有以节点的形式呈现。抽象语法树并不依赖于源语言的语法,也就是说语法分析阶段所采用的上下文无文文法,因为在写文法时,经常会对文法进行等价的转换(消除左递归,回溯,二义性等),这样会给文法分析引入一些多余的成分,对后续阶段造成不利影响,甚至会使合个阶段变得混乱。因些,很多编译器经常要独立地构造语法分析树,为前端,后端建立一个清晰的接口。

    抽象语法树在很多领域有广泛的应用,比如浏览器,智能编辑器,编译器。

    AST具体的一些介绍可以查看此处https://www.codercto.com/a/47843.html

    babel插件处理语法树

    babel-traverse 获取可以获取节点路径Path

    path的属性和方法

    ── 属性

      - node  当前节点  

    - parent  父节点 

     - parentPath 父path

      - scope  作用域  

    - context  上下文

    ── 方法 

     - get  当前节点  

    - findParent  向父节点搜寻节点 

     - getSibling 获取兄弟节点

      - replaceWith  用AST节点替换该节点 

     - replaceWithMultiple 用多个AST节点替换该节点  

    - insertBefore  在节点前插入节点  

    - insertAfter 在节点后插入节点 

     - remove  删除节点

    获取同级路径

    如果一个路径是在一个 Function/Program中的列表里面,它就有同级节点。

    使用path.inList来判断路径是否有同级节点,

    使用path.getSibling(index)来获得同级路径,

    使用 path.key获取路径所在容器的索引,

    使用 path.container获取路径的容器(包含所有同级节点的数组)

    使用 path.listKey获取容器的key

    babel插件的使用 查看此处https://blog.csdn.net/weixin_33826609/article/details/93164633#toc-babel-traverse

    使用demo实现m-modal ,change事件的添加合并

    function varExp(value, path) {  

        var exp = $util.parseMmodal(path)

        if (exp.type === $.MERGE && exp.FunNode.value.body){

          // 获取原onchange事件

          let funBody = exp.FunNode.value.body

          // 删除原onchange事件

          if (path.inList){

            let siblingNode = path.container

            siblingNode.forEach((item,index) => {

              if(item.key.name === 'onChange'){

                path.getSibling(index).remove()

              }

            })

          }

          return t.objectProperty(  

            t.stringLiteral('onChange'), 

            t.arrowFunctionExpression(

                [t.identifier('v')],

                t.BlockStatement(

                  [t.expressionStatement(

                    t.AssignmentExpression(

                      "=",t.identifier(value),t.identifier('v.value')

                    )

                  ), 

                    t.expressionStatement(

                    funBody

                  )

                 ]

                )     

            )

          ) 

        } 

        return t.objectProperty(  //抽象语法树,解析对象数,拷贝或者创建一个对象

          t.stringLiteral('onChange'),  //拷贝或者创建change事件

          t.arrowFunctionExpression(

              [t.identifier('v')],

              {

                   type: 'BinaryExpression',

                   left: t.identifier(value), 

                   "operator": "=",

                   "right":  t.identifier('v.value')

               }

          )

        ) 

     }

    相关文章

      网友评论

          本文标题:babel插件的使用和AST抽象语法树

          本文链接:https://www.haomeiwen.com/subject/ulinohtx.html