Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixed crash related to index type deferral on generic mapped types with name types #60528

Open
wants to merge 16 commits into
base: main
Choose a base branch
from

Conversation

Andarist
Copy link
Contributor

@Andarist Andarist commented Nov 17, 2024

fixes #60476
fixes #56239

@typescript-bot typescript-bot added the For Uncommitted Bug PR for untriaged, rejected, closed or missing bug label Nov 17, 2024
Comment on lines +67 to +68
!!! error TS2322: Type 'Mapped6<K>[`_${K}`]' is not assignable to type '`_${string}`'.
!!! error TS2322: Type 'Mapped6<K>[`_${string}`]' is not assignable to type '`_${string}`'.
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this change is a fix. The new error matches what was reported by TS 5.0: TS playground

Comment on lines +49 to +55
type Mapped7<K extends string> = {
[P in K as [P] extends [`_${string}`] ? P : never]: P;
};

function f7<K extends string>(obj: Mapped7<K>, key: keyof Mapped7<K>) {
let s: `_${string}` = obj[key];
}
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test case is an extra thing that gets fixed here. This is based on Mapped5+f5 from this file. The only difference between them is that this one is using [P] extends [...] and not P extends ....

This didn't work because the index type deferral was previously dependent on hasDistributiveNameType. I don't quite see a reason why those 2 would type check differently though. Effectively P is always instantiated with a non-union type.

Comment on lines -42089 to -42092
// skip index type deferral on remapping mapped types
const objectIndexType = isGenericMappedType(objectType) && getMappedTypeNameTypeKind(objectType) === MappedTypeNameTypeKind.Remapping
? getIndexTypeForMappedType(objectType, IndexFlags.None)
: getIndexType(objectType, IndexFlags.None);
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This reverts my own change from #55140 . I think now the check wasn't exhaustive anyway and this is now better handled by getSimplifiedIndexType

@Andarist
Copy link
Contributor Author

@jakebailey could u run the extended test suite here? :)

@@ -18350,7 +18356,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
function shouldDeferIndexType(type: Type, indexFlags = IndexFlags.None) {
return !!(type.flags & TypeFlags.InstantiableNonPrimitive ||
isGenericTupleType(type) ||
isGenericMappedType(type) && (!hasDistributiveNameType(type) || getMappedTypeNameTypeKind(type) === MappedTypeNameTypeKind.Remapping) ||
isGenericMappedType(type) && getNameTypeFromMappedType(type) ||
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As mentioned in the comment here:

Effectively P is always instantiated with a non-union type.

Because of that, it's not safe to skip index type deferral for any remapping mapped type as P could be used multiple times by the mapping (and the compiler shouldn't allow for a cross-product of `${P}_${P}`). Checking getMappedTypeNameTypeKind can run into an infinite loop here and it seems the easiest to just avoid checking that and assume that all generic mapped types with name types have to have deferred index types. I compensate for that by simplifying them in relationship checking etc.

// want to perform the reduction when the name type of a mapped type is distributive with respect to the type variable
// introduced by the 'in' clause of the mapped type. Note that non-generic types are considered to be distributive because
// they're the same type regardless of what's being distributed over.
function hasDistributiveNameType(mappedType: MappedType) {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Alternatively, maybe this could be kept but repurposed slightly. It would have to check if used template literal types don't refer to the type variable introduced by 'in' clause more than once. I don't think this is something the compiler would usually do in any other place so I'm hesitant to say that this would be a better solution.

@typescript-bot typescript-bot added For Backlog Bug PRs that fix a backlog bug and removed For Uncommitted Bug PR for untriaged, rejected, closed or missing bug labels Nov 25, 2024
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this one got fixed here because now keyof { [K in keyof TActors as K & string]: { src: K; logic: TActors[K]; }; } gets recognized as a deferred index type and thus the logic added in #56742 can kick in

@jakebailey
Copy link
Member

@typescript-bot test it

@typescript-bot
Copy link
Collaborator

typescript-bot commented Nov 25, 2024

Starting jobs; this comment will be updated as builds start and complete.

Command Status Results
test top400 ✅ Started ✅ Results
user test this ✅ Started ✅ Results
run dt ✅ Started ✅ Results
perf test this faster ✅ Started 👀 Results

@typescript-bot
Copy link
Collaborator

Hey @jakebailey, the results of running the DT tests are ready.

Everything looks the same!

You can check the log here.

@typescript-bot
Copy link
Collaborator

@jakebailey Here are the results of running the user tests with tsc comparing main and refs/pull/60528/merge:

Everything looks good!

@typescript-bot
Copy link
Collaborator

@jakebailey
The results of the perf run you requested are in!

Here they are:

tsc

Comparison Report - baseline..pr
Metric baseline pr Delta Best Worst p-value
Compiler-Unions - node (v18.15.0, x64)
Errors 34 34 ~ ~ ~ p=1.000 n=6
Symbols 62,363 62,363 ~ ~ ~ p=1.000 n=6
Types 50,395 50,395 ~ ~ ~ p=1.000 n=6
Memory used 194,308k (± 0.93%) 194,269k (± 1.00%) ~ 192,991k 196,885k p=0.298 n=6
Parse Time 1.30s (± 0.93%) 1.30s (± 0.76%) ~ 1.29s 1.31s p=0.498 n=6
Bind Time 0.72s (± 0.57%) 0.72s ~ ~ ~ p=0.405 n=6
Check Time 9.79s (± 0.58%) 9.81s (± 0.20%) ~ 9.78s 9.83s p=0.377 n=6
Emit Time 2.73s (± 0.50%) 2.74s (± 0.82%) ~ 2.72s 2.78s p=0.455 n=6
Total Time 14.53s (± 0.33%) 14.56s (± 0.28%) ~ 14.51s 14.63s p=0.297 n=6
angular-1 - node (v18.15.0, x64)
Errors 37 37 ~ ~ ~ p=1.000 n=6
Symbols 947,936 947,936 ~ ~ ~ p=1.000 n=6
Types 410,955 410,955 ~ ~ ~ p=1.000 n=6
Memory used 1,226,022k (± 0.00%) 1,226,004k (± 0.00%) ~ 1,225,956k 1,226,075k p=0.521 n=6
Parse Time 6.64s (± 0.70%) 6.64s (± 0.52%) ~ 6.60s 6.70s p=0.687 n=6
Bind Time 1.88s (± 0.62%) 1.89s (± 0.43%) ~ 1.88s 1.90s p=0.666 n=6
Check Time 31.89s (± 0.25%) 31.88s (± 0.25%) ~ 31.77s 32.01s p=0.872 n=6
Emit Time 15.21s (± 0.48%) 15.18s (± 0.37%) ~ 15.11s 15.26s p=0.872 n=6
Total Time 55.62s (± 0.23%) 55.60s (± 0.21%) ~ 55.42s 55.75s p=1.000 n=6
mui-docs - node (v18.15.0, x64)
Errors 0 0 ~ ~ ~ p=1.000 n=6
Symbols 2,499,542 2,499,542 ~ ~ ~ p=1.000 n=6
Types 909,373 904,500 -4,873 (- 0.54%) ~ ~ p=0.001 n=6
Memory used 2,317,371k (± 0.00%) 2,315,068k (± 0.00%) -2,303k (- 0.10%) 2,315,018k 2,315,104k p=0.005 n=6
Parse Time 9.27s (± 0.22%) 9.25s (± 0.26%) ~ 9.23s 9.29s p=0.160 n=6
Bind Time 2.16s (± 0.70%) 2.17s (± 0.39%) ~ 2.16s 2.18s p=0.282 n=6
Check Time 74.80s (± 0.46%) 74.51s (± 0.35%) ~ 74.24s 74.96s p=0.128 n=6
Emit Time 0.28s (± 3.64%) 0.28s (± 1.99%) ~ 0.27s 0.28s p=0.138 n=6
Total Time 86.51s (± 0.38%) 86.19s (± 0.29%) ~ 85.97s 86.64s p=0.093 n=6
self-build-src - node (v18.15.0, x64)
Errors 0 0 ~ ~ ~ p=1.000 n=6
Symbols 1,225,251 1,225,247 -4 (- 0.00%) ~ ~ p=0.001 n=6
Types 266,545 266,545 ~ ~ ~ p=1.000 n=6
Memory used 2,354,376k (± 0.03%) 2,353,612k (± 0.02%) ~ 2,352,828k 2,354,390k p=0.128 n=6
Parse Time 5.25s (± 0.76%) 5.23s (± 0.70%) ~ 5.20s 5.29s p=0.336 n=6
Bind Time 1.77s (± 0.66%) 1.77s (± 0.99%) ~ 1.74s 1.79s p=0.680 n=6
Check Time 35.24s (± 0.34%) 35.21s (± 0.10%) ~ 35.18s 35.27s p=0.689 n=6
Emit Time 2.99s (± 1.55%) 2.99s (± 3.60%) ~ 2.90s 3.20s p=0.295 n=6
Total Time 45.26s (± 0.21%) 45.21s (± 0.24%) ~ 45.12s 45.43s p=0.470 n=6
self-build-src-public-api - node (v18.15.0, x64)
Errors 0 0 ~ ~ ~ p=1.000 n=6
Symbols 1,225,251 1,225,247 -4 (- 0.00%) ~ ~ p=0.001 n=6
Types 266,545 266,545 ~ ~ ~ p=1.000 n=6
Memory used 3,028,994k (± 9.77%) 3,149,608k (± 0.01%) ~ 3,149,245k 3,150,170k p=0.689 n=6
Parse Time 6.97s (± 1.66%) 7.01s (± 0.83%) ~ 6.95s 7.10s p=0.630 n=6
Bind Time 2.15s (± 2.09%) 2.13s (± 2.80%) ~ 2.07s 2.23s p=0.335 n=6
Check Time 42.88s (± 0.46%) 42.71s (± 0.28%) ~ 42.56s 42.86s p=0.149 n=6
Emit Time 3.48s (± 1.83%) 3.42s (± 2.67%) ~ 3.31s 3.54s p=0.173 n=6
Total Time 55.49s (± 0.48%) 55.30s (± 0.15%) ~ 55.22s 55.39s p=0.066 n=6
self-compiler - node (v18.15.0, x64)
Errors 0 0 ~ ~ ~ p=1.000 n=6
Symbols 262,223 262,219 -4 (- 0.00%) ~ ~ p=0.001 n=6
Types 106,606 106,606 ~ ~ ~ p=1.000 n=6
Memory used 439,827k (± 0.01%) 439,787k (± 0.03%) ~ 439,671k 439,935k p=0.378 n=6
Parse Time 3.55s (± 0.81%) 3.56s (± 0.82%) ~ 3.51s 3.60s p=1.000 n=6
Bind Time 1.33s (± 0.91%) 1.33s (± 0.79%) ~ 1.31s 1.34s p=0.868 n=6
Check Time 19.01s (± 0.30%) 18.96s (± 0.50%) ~ 18.83s 19.09s p=0.422 n=6
Emit Time 1.54s (± 0.95%) 1.53s (± 0.89%) ~ 1.52s 1.55s p=0.363 n=6
Total Time 25.43s (± 0.33%) 25.38s (± 0.40%) ~ 25.26s 25.55s p=0.378 n=6
ts-pre-modules - node (v18.15.0, x64)
Errors 70 70 ~ ~ ~ p=1.000 n=6
Symbols 226,062 226,062 ~ ~ ~ p=1.000 n=6
Types 94,488 94,488 ~ ~ ~ p=1.000 n=6
Memory used 371,622k (± 0.01%) 371,597k (± 0.01%) ~ 371,549k 371,683k p=0.230 n=6
Parse Time 2.89s (± 0.99%) 2.88s (± 0.75%) ~ 2.86s 2.91s p=0.685 n=6
Bind Time 1.59s (± 1.46%) 1.58s (± 0.52%) ~ 1.57s 1.59s p=0.452 n=6
Check Time 16.48s (± 0.40%) 16.47s (± 0.60%) ~ 16.29s 16.57s p=1.000 n=6
Emit Time 0.00s 0.00s ~ ~ ~ p=1.000 n=6
Total Time 20.96s (± 0.32%) 20.94s (± 0.52%) ~ 20.76s 21.05s p=1.000 n=6
vscode - node (v18.15.0, x64)
Errors 4 4 ~ ~ ~ p=1.000 n=6
Symbols 3,166,401 3,166,401 ~ ~ ~ p=1.000 n=6
Types 1,091,207 1,091,207 ~ ~ ~ p=1.000 n=6
Memory used 3,247,963k (± 0.01%) 3,248,358k (± 0.01%) ~ 3,248,055k 3,248,863k p=0.173 n=6
Parse Time 14.03s (± 0.28%) 14.14s (± 0.44%) +0.11s (+ 0.78%) 14.06s 14.22s p=0.013 n=6
Bind Time 4.50s (± 0.30%) 4.51s (± 0.35%) ~ 4.49s 4.53s p=0.369 n=6
Check Time 87.66s (± 1.56%) 87.19s (± 2.22%) ~ 85.72s 90.56s p=0.378 n=6
Emit Time 27.66s (± 2.27%) 26.67s (± 6.81%) ~ 22.97s 27.63s p=0.575 n=6
Total Time 133.86s (± 0.93%) 132.51s (± 0.74%) ~ 131.61s 134.42s p=0.173 n=6
webpack - node (v18.15.0, x64)
Errors 0 0 ~ ~ ~ p=1.000 n=6
Symbols 288,617 288,617 ~ ~ ~ p=1.000 n=6
Types 117,107 117,107 ~ ~ ~ p=1.000 n=6
Memory used 440,737k (± 0.03%) 440,707k (± 0.05%) ~ 440,551k 441,094k p=0.378 n=6
Parse Time 4.05s (± 0.46%) 4.08s (± 0.75%) ~ 4.03s 4.12s p=0.107 n=6
Bind Time 1.76s (± 1.05%) 1.74s (± 1.49%) ~ 1.70s 1.77s p=0.106 n=6
Check Time 18.80s (± 0.62%) 18.85s (± 0.47%) ~ 18.76s 18.97s p=0.686 n=6
Emit Time 0.00s 0.00s ~ ~ ~ p=1.000 n=6
Total Time 24.62s (± 0.53%) 24.67s (± 0.33%) ~ 24.58s 24.80s p=0.471 n=6
xstate-main - node (v18.15.0, x64)
Errors 8 8 ~ ~ ~ p=1.000 n=6
Symbols 551,583 551,583 ~ ~ ~ p=1.000 n=6
Types 184,808 184,808 ~ ~ ~ p=1.000 n=6
Memory used 491,911k (± 0.01%) 491,926k (± 0.01%) ~ 491,885k 491,970k p=0.630 n=6
Parse Time 3.40s (± 0.66%) 3.42s (± 0.69%) ~ 3.39s 3.45s p=0.333 n=6
Bind Time 1.18s (± 0.88%) 1.17s (± 0.70%) ~ 1.16s 1.18s p=0.546 n=6
Check Time 19.54s (± 0.26%) 19.59s (± 0.42%) ~ 19.48s 19.73s p=0.294 n=6
Emit Time 0.00s 0.00s ~ ~ ~ p=1.000 n=6
Total Time 24.13s (± 0.27%) 24.19s (± 0.28%) ~ 24.10s 24.30s p=0.199 n=6
System info unknown
Hosts
  • node (v18.15.0, x64)
Scenarios
  • Compiler-Unions - node (v18.15.0, x64)
  • angular-1 - node (v18.15.0, x64)
  • mui-docs - node (v18.15.0, x64)
  • self-build-src - node (v18.15.0, x64)
  • self-build-src-public-api - node (v18.15.0, x64)
  • self-compiler - node (v18.15.0, x64)
  • ts-pre-modules - node (v18.15.0, x64)
  • vscode - node (v18.15.0, x64)
  • webpack - node (v18.15.0, x64)
  • xstate-main - node (v18.15.0, x64)
Benchmark Name Iterations
Current pr 6
Baseline baseline 6

Developer Information:

Download Benchmarks

@typescript-bot
Copy link
Collaborator

@jakebailey Here are the results of running the top 400 repos with tsc comparing main and refs/pull/60528/merge:

Everything looks good!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
For Backlog Bug PRs that fix a backlog bug
Projects
Status: Not started
3 participants