diff --git a/AST抽象语法树/5.AST操作之API用法-path路径/README.md b/AST抽象语法树/5.AST操作之API用法-path路径/README.md new file mode 100644 index 0000000..637dd3f --- /dev/null +++ b/AST抽象语法树/5.AST操作之API用法-path路径/README.md @@ -0,0 +1,227 @@ +# AST操作之API用法-path路径 + +## path 路径 + +在`@babel/traverse`模块中,path对象表示一个节点(node)在AST树中的位置,提供了一些属性和方法, +用于访问节点的属性、子节点、父节点、兄弟节点等,并且可以对AST树进行修改。 + +**下面是一些常见的 path 对象的 API:** + +| api | 功能 | +|--------------------------|--------------------------------------------------------------------| +| path.node | 获取当前路径对应的节点。 | +| path.parent | 获取当前路径对应节点的父节点。 | +| path.parentPath | 获取当前路径对应节点的父路径。 | +| path.get(key) | 获取当前路径下指定属性名(key)对应的子路径。例如,path.get("body") 获取当前路径下名为 "body" 的子路径。 | +| path.getSibling(index) | 获取当前路径对应节点的兄弟节点的路径。通过指定索引(index)可以获取相应的兄弟路径。 | +| path.getFunctionParent() | 获取当前路径对应节点的最近的函数父节点的路径。 | +| path.traverse(visitor) | 遍历当前路径下的所有子节点,并应用指定的 visitor。 | +| path.replaceWith(node) | 用指定的节点替换当前路径对应的节点。 | +| path.remove() | 从 AST 中移除当前路径对应的节点。 | +| path.insertBefore(nodes) | 在当前路径对应节点之前插入一个或多个节点。 | +| path.insertAfter(nodes) | 在当前路径对应节点之后插入一个或多个节点。 | + +**当前路径所对应的源代码** + +需求:打印当前路径所对应的源代码 + +```javascript +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; + +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + VariableDeclaration(path) + { + console.log(path.toString()); + }, +} + +traverse(ast, visitor); +``` + +打印内容: + +```javascript +var a = 123; +``` + +**打印当前路径所对应的某个节点信息** + +需求:打印type、start、end、loc、sourceType、interpreter、body等信息 + +![debugger](./img/1.png) + +编写代码 + +```javascript +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; + +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + Program(path) + { + console.log(path.node.type); + console.log(path.node.start); + console.log(path.node.end); + console.log(path.node.loc); + console.log(path.node.sourceType); + console.log(path.node.interpreter); + console.log(path.node.body); + console.log(path.node.directives); + }, +} + +traverse(ast, visitor); +``` + +打印内容: + +```javascript +Program +0 +12 +SourceLocation { + start: Position { line: 1, column: 0, index: 0 }, + end: Position { line: 1, column: 12, index: 12 }, + filename: undefined, + identifierName: undefined +} +script +null +[ + Node { + type: 'VariableDeclaration', + start: 0, + end: 12, + loc: SourceLocation { + start: [Position], + end: [Position], + filename: undefined, + identifierName: undefined + }, + declarations: [ [Node] ], + kind: 'var' + } +] +[] +``` + +**判断path是什么type,使用path.isXXX 这个方法** + +需求:遍历所有节点,输出节点类型为NumericLiteral的value值 + +```javascript +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; + +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + enter(path) + { + if(path.isNumericLiteral()) + { + console.log(path.type); + console.log(path.node.value); + } + + }, +} + +traverse(ast, visitor); +``` + +打印内容: + +```javascript +NumericLiteral +123 +``` + +**获取path的上一级路径path.parentPath;** + +需求:获取上一级路径节点类型 + +```javascript +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; + +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + enter(path) + { + if(path.isNumericLiteral()) + { + console.log('当前节点类型:'+path.type); + console.log('上层节点类型:'+path.parentPath.type); + } + }, +} + +traverse(ast, visitor); +``` + +打印内容: + +```javascript +当前节点类型:NumericLiteral +上层节点类型:VariableDeclarator +``` + +**删除path,使用remove方法** + +需求:删除变量值 + +```javascript +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; +const generator = require("@babel/generator").default; +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + enter(path) + { + if(path.isNumericLiteral()) + { + path.remove() + } + }, +} + +traverse(ast, visitor); + +// 写入文件 +let {code} = generator(ast); +console.log(code) +fs.writeFile('decode.js', code, (err) => {}); +``` +打印内容: + +```javascript +var a; +``` \ No newline at end of file diff --git a/AST抽象语法树/5.AST操作之API用法-path路径/decode.js b/AST抽象语法树/5.AST操作之API用法-path路径/decode.js new file mode 100644 index 0000000..3e62046 --- /dev/null +++ b/AST抽象语法树/5.AST操作之API用法-path路径/decode.js @@ -0,0 +1 @@ +var a; \ No newline at end of file diff --git a/AST抽象语法树/5.AST操作之API用法-path路径/decode_obfuscator.js b/AST抽象语法树/5.AST操作之API用法-path路径/decode_obfuscator.js new file mode 100644 index 0000000..0b61e8a --- /dev/null +++ b/AST抽象语法树/5.AST操作之API用法-path路径/decode_obfuscator.js @@ -0,0 +1,25 @@ +const fs = require('fs'); +const {parse} = require("@babel/parser"); +const traverse = require("@babel/traverse").default; +const generator = require("@babel/generator").default; +let encode_file = "./encode.js"; + +let js_code = fs.readFileSync(encode_file, {encoding: "utf-8"}); +let ast = parse(js_code); + +const visitor = { + enter(path) + { + if(path.isNumericLiteral()) + { + path.remove() + } + }, +} + +traverse(ast, visitor); + +// 写入文件 +let {code} = generator(ast); +console.log(code) +fs.writeFile('decode.js', code, (err) => {}); diff --git a/AST抽象语法树/5.AST操作之API用法-path路径/encode.js b/AST抽象语法树/5.AST操作之API用法-path路径/encode.js new file mode 100644 index 0000000..9d69cb3 --- /dev/null +++ b/AST抽象语法树/5.AST操作之API用法-path路径/encode.js @@ -0,0 +1 @@ +var a = 123; \ No newline at end of file diff --git a/AST抽象语法树/5.AST操作之API用法-path路径/img/1.png b/AST抽象语法树/5.AST操作之API用法-path路径/img/1.png new file mode 100644 index 0000000..51b9e27 Binary files /dev/null and b/AST抽象语法树/5.AST操作之API用法-path路径/img/1.png differ diff --git a/AST抽象语法树/README.md b/AST抽象语法树/README.md new file mode 100644 index 0000000..23a6fb9 --- /dev/null +++ b/AST抽象语法树/README.md @@ -0,0 +1,5 @@ +# 参考文档 + +深入学习 JavaScript 转译器 Babel ,AST还原混淆代码 +https://blog.csdn.net/weixin_52057903/article/details/129131582 +