1.0.55 • Published 2 years ago

gogocode v1.0.55

Weekly downloads
4
License
MIT
Repository
github
Last release
2 years ago

GOGOCODE

全网最简单易上手,可读性最强的 AST 处理工具!

官网:https://gogocode.io

简介:阿里妈妈出的新工具,给批量修改项目代码减轻了痛苦

Install

    npm install gogocode

快速开始

对于下面的代码

const code = `
  const moment = require('moment');
  var a = 1;
  const b = 2;
  function log (x, y = 'World') {
    console.log('a')
    console.log(a, x, y);
  }
`;

创建一个 AST 实例

const $ = require('gogocode');
const AST = $(code);

  • 小明想将 所有的 a 变量名替换为 c,只需要
$(code).replace('a', 'c')

  • 小明改主意了,只想把 var a = 1 里的变量名改为 c,需要两步:

    • 取变量 a 的定义赋值,

      $(code).find('var a = 1');
    • a 变量名替换为 c,并输出整体代码

      $(code)
        .find('var a = 1')
        .attr('declarations.0.id.name', 'c')
        .root()
        .generate();

这是直接操作AST的方式,有没有更简单的方法呢?有!

$(code).replace(`var a = 1`, `var c = 1`)

replace确实用起来爽,但当你在分析转换代码时遇到replace覆盖不到的场景时,请用GoGoCode提供的其他api来精准操作AST吧!


  • 小明又改主意了,想把所有定义语句的 a 都改成 c,只需要将目标语句改一下写成:
$(code).replace(`var a = $_$`, `var c = $_$`)

看到这里,你应该已经理解 findreplace 的第一参有点类似‘jquery 选择器’,而这里的选择器是你需要查找的代码片段,无论想要匹配多么复杂的代码都可以匹配到,其中 $_$ 通配符可以匹配任意确定代码,代码选择器及通配符详细介绍 看这里


  • 小明想试试将代码里的 var 改为 letrequire 改为 import,他发现用 GoGoCode 真的可以像字符串的 replace 一样简单!
$(code)
.replace('var $_$1 = $_$2', 'let $_$1 = $_$2');
.replace('const $_$1 = require($_$2)', 'import $_$1 from $_$2')

关于如何书写选择器,以及replace详解,请见GoGoCode详细文档


API

获取节点

所有的节点获取操作都会返回一个新的AST实例,实例中可能包含多个AST节点路径,如find()siblings()等,某些api返回的实例只会存在一个AST节点路径,如next()

AST.find(selector, options)

入参说明类型默认值
selector代码选择器,可以是代码也可以将代码中的部分内容挖空替换为通配符string
optionsignoreSequence匹配时是否忽略顺序忽略顺序的情况:{a:$_$}匹配{b:1, a:2}需要严格按照顺序匹配的情况:function($_$, b){} 匹配function(a, b){}booleanfalse
parseOptions同构造函数的parseOptions

当selector中存在 $_$ 通配符时,返回的AST实例中存在 match 属性,也就是被 $_$ 匹配到的AST节点,按照$$紧接着的key做聚合 如:`$('const a = { key: 1, value: "gogo" }').find('const $$1 = $_$2')`

下图是是 $_$1$_$2 分别匹配到的节点以及对应的输出

.parent(level)

获取某个父节点

入参说明类型默认值
level自内向外第n层父元素number0

.parents()

获取所有父节

.root()

获取根节点,对于js来说是type为'File'的节点,对于html来说是nodeType为'document'的节点 通常对AST进行操作之后需要获取root元素之后再输出

.siblings()

获取所有兄弟节点

.prev()

获取前一个节点

.prevAll()

获取当前节点之前的同级节点

.next()

获取后一个节点

.nextAll()

获取当前节点之后的同级节点

.each(callback)

以每一个匹配的元素作为上下文来执行一个函数。

入参说明类型默认值
callback对于每个匹配的元素所要执行的函数执行函数时,会给函数传递当前节点nodeindexfunction

.eq(index)

获取当前链式操作中第N个AST对象

入参说明类型默认值
index需要获取的AST对象的位置number0

操作节点

.attr()

获取或修改AST节点的属性,入参可分三种情况:

  1. 返回属性名称对应的节点或属性值
入参说明类型默认值举例
attrNameast节点的属性名称,支持多层属性,通过.连接stringdeclarationsdeclarations.0.id.name
  1. 修改属性名称对应的节点或属性值
入参说明类型举例
attrNameast节点的属性名称,支持多层属性,通过.连接stringdeclarations declarations.0.id.name
attrValue将第一个入参获取到的节点或属性修改为该入参 注意:字符串不会被解析为ast节点而是直接替换原有属性node string
  1. 修改多个属性名称对应的节点或属性值
入参类型默认值举例
attrMapattrNamestringdeclarations declarations.0.id.name
attrValuenodestring
AST.attr('init', initNode)

AST.attr({ 
  init: initNode,
  'program.body.0.params.0.name': 'a'
})

AST.attr('program.body.0.params.0.name')

.has(selector, options)

判断是否有某个子节点,返回值为boolean类型 入参同.find()

.clone()

返回由当前节点深度复制的新节点

.replace(selector, replacer)

在当前节点内部用replacer替换selector匹配到的代码,返回当前节点

入参解释类型
selector代码选择器,可以是代码也可以将代码中的部分内容挖空替换为通配符stringvar $_$1 = $_$2
replacer替换代码,同代码选择器通配符顺序与selector的保持一致也可以是确定的ast节点stringnodelet $_$1 = $_$2
optionsignoreSequence匹配时是否忽略顺序object
parseOptions解析入参object

AST.replace(`Component`, `module.exports = Magix.View.extend`);

AST.replace(
  `export default function calculateData($_$1){$_$2}`, 
  `function calculateData($_$1){$_$2}`
)

AST.replace(
  `navigateToOutside({url: $_$})`, 
  `jm.attachUrlParams($_$)`, 
  options: { ignoreSequence: true }
)

.replaceBy(replacerAST)

用replacerAST替换当前节点,返回新节点

入参类型
replacerASTAST node string

.after(ast)

在当前节点后面插入一个同级别的节点,返回当前节点

入参类型
astAST node string

.before()

在当前节点前面插入一个同级别的节点,返回当前节点

入参类型
astAST node string

.append(attr, ast)

在当前节点内部某个数组属性的末尾插入一个子节点,返回当前节点

入参类型
attr当前节点的数组属性名称
astAST node string
  • 为什么需要传入attr

因为某些节点中多个属性都为数组,如函数,存在入参params和函数体body两个数组子节点,必须通过attr来判断插入节点的位置

AST
.find('function $_$() {}')
.append('params', 'b')
.prepend('body', 'b = b || 1;')

.prepend()

在当前节点内部某个数组属性的首位插入一个子节点,返回当前节点

.empty()

清空当前节点所有子节点,返回当前节点

.remove()

移除当前节点,返回根节点

.generate()

将AST对象输出为代码

1.0.55

2 years ago

1.0.54

2 years ago

1.0.51

2 years ago

1.0.50

2 years ago

1.0.53

2 years ago

1.0.52

2 years ago

1.0.49

2 years ago

1.0.43

2 years ago

1.0.42

2 years ago

1.0.41

2 years ago

1.0.48

2 years ago

1.0.46

2 years ago

1.0.45

2 years ago

1.0.39

2 years ago

1.0.40

2 years ago

1.0.38

2 years ago

1.0.37

3 years ago

1.0.36

3 years ago

1.0.35

3 years ago

1.0.33

3 years ago

1.0.32

3 years ago

1.0.34

3 years ago

1.0.31

3 years ago

1.0.29

3 years ago

1.0.28

3 years ago

1.0.30

3 years ago

1.0.27

3 years ago

1.0.26

3 years ago

1.0.25

3 years ago

1.0.24

3 years ago

1.0.23

3 years ago

1.0.22

3 years ago

1.0.21

3 years ago

1.0.19

3 years ago

1.0.18

3 years ago

1.0.20

3 years ago

1.0.17

3 years ago

1.0.16

3 years ago

1.0.15

3 years ago

1.0.14

3 years ago

1.0.9

3 years ago

1.0.11

3 years ago

1.0.10

3 years ago

1.0.13

3 years ago

1.0.12

3 years ago

1.0.8

3 years ago

1.0.7

3 years ago

1.0.6

3 years ago

1.0.5

3 years ago

1.0.4

3 years ago

1.0.2

3 years ago

1.0.3

3 years ago

1.0.1

3 years ago

1.0.0

3 years ago

0.2.27

3 years ago

0.2.29

3 years ago

0.2.28

3 years ago

0.2.26

3 years ago

0.2.25

3 years ago

0.2.24

3 years ago

0.2.23

3 years ago

0.2.22

3 years ago

0.2.21

3 years ago

0.2.20

3 years ago

0.2.19

3 years ago

0.2.18

3 years ago

0.2.17

3 years ago

0.2.16

3 years ago

0.2.15

3 years ago

0.2.14

3 years ago

0.2.13

3 years ago

0.2.12

3 years ago

0.2.11

3 years ago

0.2.10

3 years ago

0.2.9

3 years ago

0.2.7

3 years ago

0.2.6

3 years ago

0.2.8

3 years ago

0.2.5

3 years ago

0.2.3

3 years ago

0.2.4

3 years ago

0.2.1

3 years ago

0.2.2

3 years ago

0.2.0

3 years ago

0.1.8

3 years ago

0.1.7

3 years ago

0.1.6

3 years ago

0.1.5

3 years ago

0.1.2

3 years ago

0.1.4

3 years ago

0.1.3

3 years ago

0.1.1

3 years ago

0.1.0

3 years ago

0.0.29

3 years ago

0.0.28

3 years ago

0.0.26

3 years ago

0.0.27

3 years ago

0.0.24

3 years ago

0.0.25

3 years ago

0.0.21

3 years ago

0.0.22

3 years ago

0.0.23

3 years ago

0.0.20

3 years ago

0.0.19

4 years ago

0.0.18

4 years ago

0.0.17

4 years ago

0.0.16

4 years ago

0.0.15

4 years ago

0.0.13

4 years ago

0.0.10

4 years ago

0.0.11

4 years ago

0.0.12

4 years ago

0.0.9

4 years ago

0.0.8

4 years ago

0.0.7

4 years ago

0.0.6

4 years ago

0.0.5

4 years ago

0.0.4

4 years ago

0.0.3

4 years ago

0.0.2

4 years ago

0.0.1

4 years ago