Skip to content

Commit 27eecbc

Browse files
committed
Support @deprecated on namespace aliases (ImportEqualsDeclaration)
Fixes #62340 When a namespace re-exports a type using `export import Bar = example.Bar` with a `@deprecated` JSDoc comment, the deprecation warning was not being reported when accessing `JSX.Bar` as a type. The issue was that in `checkTypeReferenceOrImport`, the `resolvedSymbol` is the resolved target of the alias, not the alias itself. To detect deprecation on the alias, we now also resolve the entity name without resolving aliases and check if the alias symbol itself is deprecated.
1 parent db3ae1b commit 27eecbc

File tree

2 files changed

+62
-0
lines changed

2 files changed

+62
-0
lines changed

src/compiler/checker.ts

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42740,6 +42740,22 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
4274042740
);
4274142741
}
4274242742
}
42743+
// Also check if the type reference is an alias that is deprecated (e.g., ImportEqualsDeclaration with @deprecated)
42744+
if (node.kind !== SyntaxKind.ImportType) {
42745+
const name = getTypeReferenceName(node as TypeReferenceType);
42746+
if (name) {
42747+
const aliasSymbol = resolveEntityName(name, SymbolFlags.Type, /*ignoreErrors*/ true, /*dontResolveAlias*/ true);
42748+
if (aliasSymbol && aliasSymbol !== unknownSymbol && aliasSymbol !== symbol && aliasSymbol.flags & SymbolFlags.Alias) {
42749+
if (isDeprecatedSymbol(aliasSymbol) && aliasSymbol.declarations) {
42750+
addDeprecatedSuggestion(
42751+
getDeprecatedSuggestionNode(node),
42752+
aliasSymbol.declarations,
42753+
aliasSymbol.escapedName as string,
42754+
);
42755+
}
42756+
}
42757+
}
42758+
}
4274342759
}
4274442760
}
4274542761

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
/// <reference path="fourslash.ts" />
2+
3+
// @Filename: /example.ts
4+
//// export type Bar = string | number;
5+
//// /** @deprecated */
6+
//// export type Baz = string | number;
7+
8+
// @Filename: /foo.ts
9+
//// import * as example from './example';
10+
////
11+
//// export namespace JSX {
12+
//// /** @deprecated */
13+
//// export type Foo = string | number;
14+
////
15+
//// /** @deprecated */
16+
//// export import Bar = example.Bar;
17+
////
18+
//// export import Baz = example.Baz;
19+
//// }
20+
////
21+
//// export type X = JSX.[|Foo|]; // Should be deprecated (Foo itself is deprecated)
22+
//// export type Y = JSX.[|Bar|]; // Should be deprecated (Bar alias is deprecated)
23+
//// export type Z = JSX.[|Baz|]; // Should be deprecated (example.Baz is deprecated)
24+
25+
goTo.file('/foo.ts');
26+
const ranges = test.ranges();
27+
verify.getSuggestionDiagnostics([
28+
{
29+
"message": "'Foo' is deprecated.",
30+
"code": 6385,
31+
"range": ranges[0],
32+
"reportsDeprecated": true,
33+
},
34+
{
35+
"message": "'Bar' is deprecated.",
36+
"code": 6385,
37+
"range": ranges[1],
38+
"reportsDeprecated": true,
39+
},
40+
{
41+
"message": "'Baz' is deprecated.",
42+
"code": 6385,
43+
"range": ranges[2],
44+
"reportsDeprecated": true,
45+
},
46+
]);

0 commit comments

Comments
 (0)