Skip to content

Commit 04103c9

Browse files
committed
fix: get ast-types scope basically working
1 parent f3f363f commit 04103c9

File tree

3 files changed

+69
-3
lines changed

3 files changed

+69
-3
lines changed

src/babel/babelAstTypes.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import * as defaultTypes from '@babel/types'
55
import { memoize, omit, mapValues } from 'lodash'
66
import fork from 'ast-types/fork'
77
import { Fork } from 'ast-types/types'
8-
import nodePathPlugin from 'ast-types/lib/node-path'
98

109
const babelAstTypes: (t?: typeof defaultTypes) => ReturnType<typeof fork> =
1110
memoize((t: typeof defaultTypes = defaultTypes): ReturnType<typeof fork> => {
@@ -14,8 +13,6 @@ const babelAstTypes: (t?: typeof defaultTypes) => ReturnType<typeof fork> =
1413
const { builtInTypes, Type } = types
1514
const { def, or } = Type
1615

17-
fork.use(nodePathPlugin)
18-
1916
def('Node').field('type', builtInTypes.string)
2017
def('Comment')
2118
.field('type', builtInTypes.string)
@@ -118,6 +115,7 @@ const babelAstTypes: (t?: typeof defaultTypes) => ReturnType<typeof fork> =
118115
)
119116
}
120117
}
118+
def('Identifier').bases('Pattern')
121119
}
122120

123121
return fork([babel])

test/astx/bugs_scope.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
import { TransformOptions } from '../../src'
2+
import { astxTestcase } from '../astxTestcase'
3+
import { NodePath as AstTypesNodePath } from 'ast-types/lib/node-path'
4+
import dedent from 'dedent-js'
5+
6+
astxTestcase({
7+
file: __filename,
8+
input: dedent`
9+
const foo = 1;
10+
`,
11+
parsers: ['babel', 'babel/tsx'],
12+
astx: ({ astx, report }: TransformOptions): void => {
13+
const path = astx.find`const foo = 1;`.paths[0]
14+
report((path as AstTypesNodePath).scope !== null)
15+
},
16+
expectedReports: [true],
17+
})

test/astx/scope-testcase.ts

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
import { NodePath as AstTypesNodePath } from 'ast-types/lib/node-path'
2+
import { Astx } from '../../src'
3+
import { astxTestcase } from '../astxTestcase'
4+
import dedent from 'dedent-js'
5+
6+
astxTestcase({
7+
file: __filename,
8+
input: dedent`
9+
const x = 1, y = 2;
10+
function foo() {
11+
const y = 3;
12+
const target = x + y;
13+
}
14+
`,
15+
expected: dedent`
16+
const x = 1, y = 2;
17+
function foo() {
18+
const y = 3;
19+
const target = 1 + 3;
20+
}
21+
`,
22+
parsers: ['babel', 'babel/tsx'],
23+
astx: ({ astx }) => {
24+
for (const { $a, $b } of astx.find`const target = $a + $b`) {
25+
inlineNaively($a)
26+
inlineNaively($b)
27+
}
28+
},
29+
})
30+
31+
/** kludge to gain access to scope */
32+
type AstxWithScope = Astx & {
33+
path: AstTypesNodePath
34+
}
35+
36+
// inspired by jscodeshift
37+
function getDeclarator(a: AstxWithScope) {
38+
const name = a.path.value.name
39+
const bindings = new Astx(
40+
a.context,
41+
a.path.scope?.lookup(name)?.getBindings()[name]
42+
)
43+
return bindings
44+
.closest((astx) => astx.node.type === 'VariableDeclarator')
45+
.at(0)
46+
}
47+
48+
function inlineNaively(a: Astx) {
49+
const val = getDeclarator(a as AstxWithScope).path.get('init').value
50+
a.replace(val)
51+
}

0 commit comments

Comments
 (0)