mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-06-15 22:15:05 -05:00
@@ -21,11 +21,15 @@ namespace ts {
|
||||
return node;
|
||||
}
|
||||
switch (node.kind) {
|
||||
case SyntaxKind.CallExpression: {
|
||||
const updated = visitNonOptionalCallExpression(node as CallExpression, /*captureThisArg*/ false);
|
||||
Debug.assertNotNode(updated, isSyntheticReference);
|
||||
return updated;
|
||||
}
|
||||
case SyntaxKind.PropertyAccessExpression:
|
||||
case SyntaxKind.ElementAccessExpression:
|
||||
case SyntaxKind.CallExpression:
|
||||
if (node.flags & NodeFlags.OptionalChain) {
|
||||
const updated = visitOptionalExpression(node as OptionalChain, /*captureThisArg*/ false, /*isDelete*/ false);
|
||||
if (isOptionalChain(node)) {
|
||||
const updated = visitOptionalExpression(node, /*captureThisArg*/ false, /*isDelete*/ false);
|
||||
Debug.assertNotNode(updated, isSyntheticReference);
|
||||
return updated;
|
||||
}
|
||||
@@ -94,6 +98,15 @@ namespace ts {
|
||||
// If `node` is an optional chain, then it is the outermost chain of an optional expression.
|
||||
return visitOptionalExpression(node, captureThisArg, /*isDelete*/ false);
|
||||
}
|
||||
if (isParenthesizedExpression(node.expression) && isOptionalChain(skipParentheses(node.expression))) {
|
||||
// capture thisArg for calls of parenthesized optional chains like `(foo?.bar)()`
|
||||
const expression = visitNonOptionalParenthesizedExpression(node.expression, /*captureThisArg*/ true, /*isDelete*/ false);
|
||||
const args = visitNodes(node.arguments, visitor, isExpression);
|
||||
if (isSyntheticReference(expression)) {
|
||||
return setTextRange(factory.createFunctionCallCall(expression.expression, expression.thisArg, args), node);
|
||||
}
|
||||
return factory.updateCallExpression(node, expression, /*typeArguments*/ undefined, args);
|
||||
}
|
||||
return visitEachChild(node, visitor, context);
|
||||
}
|
||||
|
||||
|
||||
@@ -188,4 +188,11 @@ describe("unittests:: evaluation:: optionalCall", () => {
|
||||
assert.strictEqual(result.output[1], 2);
|
||||
assert.strictEqual(result.output[2], result.o);
|
||||
});
|
||||
it("(o?.f)()", async () => {
|
||||
const result = evaluator.evaluateTypeScript(`
|
||||
export const foo = { bar() { return this } };
|
||||
export const output = (foo?.bar)();
|
||||
`);
|
||||
assert.strictEqual(result.output, result.foo);
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user