Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 7 additions & 3 deletions src/services/findAllReferences.ts
Original file line number Diff line number Diff line change
Expand Up @@ -356,7 +356,7 @@ namespace ts.FindAllReferences.Core {

/** Core find-all-references algorithm for a normal symbol. */
function getReferencedSymbolsForSymbol(symbol: Symbol, node: Node, sourceFiles: ReadonlyArray<SourceFile>, checker: TypeChecker, cancellationToken: CancellationToken, options: Options): SymbolAndEntries[] {
symbol = skipPastExportOrImportSpecifier(symbol, node, checker);
symbol = skipPastExportOrImportSpecifierOrUnion(symbol, node, checker);

// Compute the meaning from the location and the symbol it references
const searchMeaning = getIntersectingMeaningFromDeclarations(getMeaningFromLocation(node), symbol.declarations);
Expand Down Expand Up @@ -405,7 +405,7 @@ namespace ts.FindAllReferences.Core {
}

/** Handle a few special cases relating to export/import specifiers. */
function skipPastExportOrImportSpecifier(symbol: Symbol, node: Node, checker: TypeChecker): Symbol {
function skipPastExportOrImportSpecifierOrUnion(symbol: Symbol, node: Node, checker: TypeChecker): Symbol {
const { parent } = node;
if (isExportSpecifier(parent)) {
return getLocalSymbolForExportSpecifier(node as Identifier, symbol, parent, checker);
Expand All @@ -415,7 +415,11 @@ namespace ts.FindAllReferences.Core {
return checker.getImmediateAliasedSymbol(symbol);
}

return symbol;
// If the symbol is declared as part of a declaration like `{ type: "a" } | { type: "b" }`, use the property on the union type to get more references.
return firstDefined(symbol.declarations, decl =>
isTypeLiteralNode(decl.parent) && isUnionTypeNode(decl.parent.parent)
? checker.getPropertyOfType(checker.getTypeFromTypeNode(decl.parent.parent), symbol.name)
: undefined) || symbol;
}

/**
Expand Down
16 changes: 16 additions & 0 deletions tests/cases/fourslash/findAllRefsUnionProperty.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
/// <reference path='fourslash.ts'/>

////type T =
//// | { [|{| "isWriteAccess": true, "isDefinition": true |}type|]: "a" }
//// | { [|{| "isWriteAccess": true, "isDefinition": true |}type|]: "b" };
////declare const t: T;
////if (t.[|type|] !== "failure") {
//// t.[|type|];
////}

const ranges = test.ranges();
const [r0, r1, r2, r3] = ranges;
verify.referenceGroups(ranges, [
{ definition: '(property) type: "a"', ranges: [r0, r2, r3] }, // TODO: this have type `"a" | "b"`
{ definition: '(property) type: "b"', ranges: [r1] },
]);