From 41782922e63ecde1074eab37159294f820529dc0 Mon Sep 17 00:00:00 2001 From: Daniel Tschinder Date: Fri, 13 Jul 2018 14:29:30 +0200 Subject: [PATCH] fix: resolve value to a proper node instead of an array --- .../__tests__/propTypeHandler-test.js | 8 +--- .../__tests__/getMemberExpressionRoot-test.js | 2 +- src/utils/__tests__/resolveHOC-test.js | 8 ++-- .../resolveObjectKeysToArray-test.js | 16 ++++---- src/utils/__tests__/resolveToValue-test.js | 38 +++++++++++-------- src/utils/resolveToValue.js | 3 +- tests/setupTestFramework.js | 16 ++++++-- 7 files changed, 52 insertions(+), 39 deletions(-) diff --git a/src/handlers/__tests__/propTypeHandler-test.js b/src/handlers/__tests__/propTypeHandler-test.js index adb9953c026..fd0a4de8232 100644 --- a/src/handlers/__tests__/propTypeHandler-test.js +++ b/src/handlers/__tests__/propTypeHandler-test.js @@ -49,12 +49,8 @@ describe('propTypeHandler', () => { propTypeHandler(documentation, definition); - expect(getPropTypeMock.mock.calls[0][0].node).toEqualASTNode( - fooPath.node, - ); - expect(getPropTypeMock.mock.calls[1][0].node).toEqualASTNode( - xyzPath.node, - ); + expect(getPropTypeMock.mock.calls[0][0]).toEqualASTNode(fooPath); + expect(getPropTypeMock.mock.calls[1][0]).toEqualASTNode(xyzPath); }); it('finds definitions via React.PropTypes', () => { diff --git a/src/utils/__tests__/getMemberExpressionRoot-test.js b/src/utils/__tests__/getMemberExpressionRoot-test.js index f9041adf29d..77eaad8d472 100644 --- a/src/utils/__tests__/getMemberExpressionRoot-test.js +++ b/src/utils/__tests__/getMemberExpressionRoot-test.js @@ -17,6 +17,6 @@ import getMemberExpressionRoot from '../getMemberExpressionRoot'; describe('getMemberExpressionRoot', () => { it('returns the root of a member expression', () => { const root = getMemberExpressionRoot(expression('foo.bar.baz')); - expect(root.node).toEqualASTNode(expression('foo').node); + expect(root).toEqualASTNode(expression('foo')); }); }); diff --git a/src/utils/__tests__/resolveHOC-test.js b/src/utils/__tests__/resolveHOC-test.js index dcadd305198..82cf03e0ccb 100644 --- a/src/utils/__tests__/resolveHOC-test.js +++ b/src/utils/__tests__/resolveHOC-test.js @@ -31,19 +31,19 @@ describe('resolveHOC', () => { it('resolves simple hoc', () => { const path = parse(['hoc(42);'].join('\n')); - expect(resolveHOC(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveHOC(path)).toEqualASTNode(builders.literal(42)); }); it('resolves simple hoc w/ multiple args', () => { const path = parse(['hoc1(arg1a, arg1b)(42);'].join('\n')); - expect(resolveHOC(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveHOC(path)).toEqualASTNode(builders.literal(42)); }); it('resolves nested hocs', () => { const path = parse( ['hoc2(arg2b, arg2b)(', ' hoc1(arg1a, arg2a)(42)', ');'].join('\n'), ); - expect(resolveHOC(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveHOC(path)).toEqualASTNode(builders.literal(42)); }); it('resolves really nested hocs', () => { @@ -56,6 +56,6 @@ describe('resolveHOC', () => { ');', ].join('\n'), ); - expect(resolveHOC(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveHOC(path)).toEqualASTNode(builders.literal(42)); }); }); diff --git a/src/utils/__tests__/resolveObjectKeysToArray-test.js b/src/utils/__tests__/resolveObjectKeysToArray-test.js index 1de1ccb2ddb..9b4fc826691 100644 --- a/src/utils/__tests__/resolveObjectKeysToArray-test.js +++ b/src/utils/__tests__/resolveObjectKeysToArray-test.js @@ -27,7 +27,7 @@ describe('resolveObjectKeysToArray', () => { ['var foo = { bar: 1, foo: 2 };', 'Object.keys(foo);'].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('bar'), builders.literal('foo'), @@ -40,7 +40,7 @@ describe('resolveObjectKeysToArray', () => { ['var foo = { "bar": 1, 5: 2 };', 'Object.keys(foo);'].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('bar'), builders.literal('5'), @@ -53,7 +53,7 @@ describe('resolveObjectKeysToArray', () => { ['var foo = { ["bar"]: 1, [5]: 2};', 'Object.keys(foo);'].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('bar'), builders.literal('5'), @@ -70,7 +70,7 @@ describe('resolveObjectKeysToArray', () => { ].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('boo'), builders.literal('foo'), @@ -86,7 +86,7 @@ describe('resolveObjectKeysToArray', () => { ), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('boo'), builders.literal('foo'), @@ -103,7 +103,7 @@ describe('resolveObjectKeysToArray', () => { ].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('boo'), builders.literal('foo'), @@ -121,7 +121,7 @@ describe('resolveObjectKeysToArray', () => { ].join('\n'), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([ builders.literal('boo'), builders.literal('foo'), @@ -137,7 +137,7 @@ describe('resolveObjectKeysToArray', () => { ), ); - expect(resolveObjectKeysToArray(path).node).toEqualASTNode( + expect(resolveObjectKeysToArray(path)).toEqualASTNode( builders.arrayExpression([builders.literal('x')]), ); }); diff --git a/src/utils/__tests__/resolveToValue-test.js b/src/utils/__tests__/resolveToValue-test.js index 29770f2933c..4bffc13ddbd 100644 --- a/src/utils/__tests__/resolveToValue-test.js +++ b/src/utils/__tests__/resolveToValue-test.js @@ -24,14 +24,14 @@ describe('resolveToValue', () => { it('resolves simple variable declarations', () => { const path = parse(['var foo = 42;', 'foo;'].join('\n')); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(42)); }); it('resolves object destructuring', () => { const path = parse(['var {foo: {bar: baz}} = bar;', 'baz;'].join('\n')); // Node should be equal to bar.foo.bar - expect(resolveToValue(path).node).toEqualASTNode( + expect(resolveToValue(path)).toEqualASTNode( builders.memberExpression( builders.memberExpression( builders.identifier('bar'), @@ -45,19 +45,19 @@ describe('resolveToValue', () => { it('handles SpreadElements properly', () => { const path = parse(['var {foo: {bar}, ...baz} = bar;', 'baz;'].join('\n')); - expect(resolveToValue(path).node).toEqualASTNode(path.node); + expect(resolveToValue(path)).toEqualASTNode(path); }); it('returns the original path if it cannot be resolved', () => { const path = parse(['function foo() {}', 'foo()'].join('\n')); - expect(resolveToValue(path).node).toEqualASTNode(path.node); + expect(resolveToValue(path)).toEqualASTNode(path); }); it('resolves variable declarators to their init value', () => { const path = utils.parse('var foo = 42;').get('body', 0, 'declarations', 0); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(42)); }); it('resolves to class declarations', () => { @@ -84,33 +84,41 @@ describe('resolveToValue', () => { it('resolves to assigned values', () => { const path = parse(['var foo;', 'foo = 42;', 'foo;'].join('\n')); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(42)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(42)); }); }); describe('ImportDeclaration', () => { it('resolves default import references to the import declaration', () => { const path = parse(['import foo from "Foo"', 'foo;'].join('\n')); + const value = resolveToValue(path); - expect(resolveToValue(path).node.type).toBe('ImportDeclaration'); + expect(Array.isArray(value.value)).toBe(false); + expect(value.node.type).toBe('ImportDeclaration'); }); it('resolves named import references to the import declaration', () => { const path = parse(['import {foo} from "Foo"', 'foo;'].join('\n')); + const value = resolveToValue(path); - expect(resolveToValue(path).node.type).toBe('ImportDeclaration'); + expect(Array.isArray(value.value)).toBe(false); + expect(value.node.type).toBe('ImportDeclaration'); }); it('resolves aliased import references to the import declaration', () => { const path = parse(['import {foo as bar} from "Foo"', 'bar;'].join('\n')); + const value = resolveToValue(path); - expect(resolveToValue(path).node.type).toBe('ImportDeclaration'); + expect(Array.isArray(value.value)).toBe(false); + expect(value.node.type).toBe('ImportDeclaration'); }); it('resolves namespace import references to the import declaration', () => { const path = parse(['import * as bar from "Foo"', 'bar;'].join('\n')); + const value = resolveToValue(path); - expect(resolveToValue(path).node.type).toBe('ImportDeclaration'); + expect(Array.isArray(value.value)).toBe(false); + expect(value.node.type).toBe('ImportDeclaration'); }); }); @@ -118,7 +126,7 @@ describe('resolveToValue', () => { it("resolves a MemberExpression to it's init value", () => { const path = parse(['var foo = { bar: 1 };', 'foo.bar;'].join('\n')); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(1)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(1)); }); it('resolves a MemberExpression in the scope chain', () => { @@ -126,7 +134,7 @@ describe('resolveToValue', () => { ['var foo = 1;', 'var bar = { baz: foo };', 'bar.baz;'].join('\n'), ); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(1)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(1)); }); it('resolves a nested MemberExpression in the scope chain', () => { @@ -138,7 +146,7 @@ describe('resolveToValue', () => { ].join('\n'), ); - expect(resolveToValue(path).node).toEqualASTNode(builders.literal(1)); + expect(resolveToValue(path)).toEqualASTNode(builders.literal(1)); }); it('returns the last resolvable MemberExpression', () => { @@ -150,7 +158,7 @@ describe('resolveToValue', () => { ].join('\n'), ); - expect(resolveToValue(path).node).toEqualASTNode( + expect(resolveToValue(path)).toEqualASTNode( builders.memberExpression( builders.identifier('foo'), builders.identifier('bar'), @@ -163,7 +171,7 @@ describe('resolveToValue', () => { ['var foo = {};', 'foo.bar = 1;', 'foo.bar;'].join('\n'), ); - expect(resolveToValue(path).node).toEqualASTNode(path.node); + expect(resolveToValue(path)).toEqualASTNode(path); }); }); }); diff --git a/src/utils/resolveToValue.js b/src/utils/resolveToValue.js index 93cd406e7d9..1d9f6293b88 100644 --- a/src/utils/resolveToValue.js +++ b/src/utils/resolveToValue.js @@ -135,7 +135,8 @@ export default function resolveToValue(path: NodePath): NodePath { types.ImportNamespaceSpecifier.check(node) || types.ImportSpecifier.check(node) ) { - return path.parentPath; + // go up two levels as first level is only the array of specifiers + return path.parentPath.parentPath; } else if (types.AssignmentExpression.check(node)) { if (node.operator === '=') { return resolveToValue(path.get('right')); diff --git a/tests/setupTestFramework.js b/tests/setupTestFramework.js index 38ebbd21a65..0aad6e09f69 100644 --- a/tests/setupTestFramework.js +++ b/tests/setupTestFramework.js @@ -17,16 +17,24 @@ const matchers = { ); } + // Use value here instead of node, as node has some magic and always returns + // the next Node it finds even if value is an array + const receivedNode = received.value; + let expectedNode = expected; + if (expected instanceof recast.types.NodePath) { + expectedNode = expected.value; + } + return { - pass: recast.types.astNodesAreEquivalent(received, expected), + pass: recast.types.astNodesAreEquivalent(receivedNode, expectedNode), message: () => { - const diffString = diff(expected, received); + const diffString = diff(expectedNode, receivedNode); return ( 'Expected value to be (using ast-types):\n' + - ` ${utils.printExpected(expected)}\n` + + ` ${utils.printExpected(expectedNode)}\n` + 'Received:\n' + - ` ${utils.printReceived(received)}` + + ` ${utils.printReceived(receivedNode)}` + (diffString ? `\n\nDifference:\n\n${diffString}` : '') ); },