Description
🔎 Search Terms
"declaration order", "sequence of interface declaration", "declaration sequence", "inconsistent type checking"
🕗 Version & Regression Information
This seems to be happening after v4.8.
The TypeScript compiler exhibits inconsistent type checking behavior when the order in which the interfaces are declared is changed. Specifically, changing the order of interface declarations can enable or disable expected type errors, suggesting a bug in how the compiler handles type resolution and caching.
Steps to Reproduce:
Example 1: No type error
type NumberRow = number[];
type StringRow = string[];
interface NumberWrapper {
arr: NumberArray[];
}
interface NumberArray {
value: NumberRow[];
}
interface StringWrapper {
arr: StringArray[];
}
interface StringArray {
value: StringRow[];
}
function f1() {
const numberWrapper: NumberWrapper = {arr: []};
// passes, but should fail
const stringWrapper = numberWrapper as StringWrapper;
}
function f2() {
const numberArray: NumberArray = {value: []};
// passes, but should fail
const stringArray = numberArray as StringArray;
}
function f3() {
const numberRow: NumberRow = [];
// passes, but should fail
const stringRow = numberRow as StringRow;
}
Example 2: Type Error
Changing the order of interface declarations, it now generates the type errors and fails -
type NumberRow = number[];
type StringRow = string[];
interface NumberArray {
value: NumberRow[];
}
interface StringArray {
value: StringRow[];
}
interface NumberWrapper {
arr: NumberArray[];
}
interface StringWrapper {
arr: StringArray[];
}
function f1() {
const numberWrapper: NumberWrapper = {arr: []};
// fails as expected
const stringWrapper = numberWrapper as StringWrapper;
}
function f2() {
const numberArray: NumberArray = {value: []};
// fails as expected
const stringArray = numberArray as StringArray;
}
function f3() {
const numberRow: NumberRow = [];
// fails as expected
const stringRow = numberRow as StringRow;
}
Impact:
This bug can lead to undetected type errors, making it difficult to rely on TypeScript's type system for correctness.
⏯ Playground Link
🙁 Actual behavior
The TypeScript compiler's behavior depends on the declaration order of the interfaces. When NumberArray and StringArray are declared after NumberWrapper and StringWrapper respectively, the compiler does not report the type error. When the declaration order is changed, the compiler correctly reports the error.
🙂 Expected behavior
The TypeScript compiler should consistently report a type error regardless of the sequence of interface declarations.
Additional information about the issue
No response