microsoft / TypeScript

TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
https://www.typescriptlang.org
Apache License 2.0
99.38k stars 12.32k forks source link

TS hangs up entire computer, type of variables stuck at "Loading..." #58373

Open slyofzero opened 2 months ago

slyofzero commented 2 months ago

πŸ”Ž Search Terms

TS intellisense not working, TS hangs up entire PC, Type inference not working

πŸ•— Version & Regression Information

⏯ Reproduction steps

To reproduce this issue please clone the following repository - https://github.com/slyofzero/TONBuyBot Install the packages using pnpm - pnpm i Visit the file - ./src/bot/commands/index.ts

πŸ’» Code

The file code in question is very tame -

import { teleBot } from "@/index";
import { startBot } from "./start";
import { log, errorHandler } from "@/utils/handlers";
import { settings } from "./settings";
import { setEmojiCommand } from "./setEmoji";
import { stopBot } from "./stop";
import { setGifCommand } from "./setGif";

export function initiateBotCommands() {
  teleBot.api
    .setMyCommands([
      { command: "start", description: "Start the bot" },
      { command: "stop", description: "Stop the bot" },
      { command: "settings", description: "To customize the bot" },
      { command: "setemoji", description: "To set an emoji" },
      { command: "setgif", description: "To set a GIF" },
    ])
    .catch((e) => errorHandler(e));

  teleBot.command("start", (ctx) => startBot(ctx));
  teleBot.command("stop", (ctx) => stopBot(ctx));
  teleBot.command("settings", (ctx) => settings(ctx));
  teleBot.command("setemoji", (ctx) => setEmojiCommand(ctx));

  teleBot.hears(/\/setgif/, (ctx) => setGifCommand(ctx, true));
  // @ts-expect-error CTX type invalid
  teleBot.on(":animation", (ctx) => setGifCommand(ctx));

  log("Bot commands up");
}

The above code is used to setup a telegram bot's commands using grammy.js

πŸ™ Actual behavior

Update - The issue only occurs when I open the ./src/bot/commands/index.ts file of the repository I share above in reproduction steps.

Uptil yesterday night VSCode and Typescript Intellisense worked fine but now types of variables upon hovering are indefinitely stuck at "Loading..."

image

This is followed by a high spike in CPU and RAM usage

image

The icon to the bottom right showing TS server status keeps spinning followed followed by the spike in CPU and RAM usage mentioned above.

image

Because of all these issues, using the computer with the project on is next to impossible. Typescript syntax errors, Intellisense, or Type inference, nothing works. I first tried uninstalling and reinstalling VSCode but that didn't fix it. I formatted by hard drive and reinstalled my OS but the problem still persists. I have gone through the below two issues that sounds similar to my problem but haven't found a fix yet.

https://github.com/microsoft/TypeScript/issues/35512 https://github.com/microsoft/vscode/issues/87870

πŸ™‚ Expected behavior

The expected behaviour would be smooth Intellisense, type inference, and an average usage of CPU and RAM not affecting other functionalities of my PC.

Additional information about the issue

I have tried this issue on two different devices and two different OS and been able to reproduce on both.

First device was an i3, 8GB RAM Dell Inspiron 5482 with Windows 10 Second device is an AMD Ryzen 7 6800, 32GB RAM, 8GB RTX 3070, Lenovo Legion 5 Pro with Windows 11

RyanCavanaugh commented 2 months ago

We need a way to reproduce this

slyofzero commented 2 months ago

We need a way to reproduce this

I have updated the original issue with reproduction steps and additional information about how I have tested it

RyanCavanaugh commented 2 months ago

tsc is also not terminating in a reasonable amount of time. Bisecting...

RyanCavanaugh commented 2 months ago

Bisects to #57345

RyanCavanaugh commented 2 months ago

Using just grammy as a dependency:

import { Bot } from "grammy";
export const teleBot = new Bot("");
teleBot.on(":animation", c => c);
RyanCavanaugh commented 2 months ago

Before

Identifiers:                57697
Symbols:                    37871
Types:                       9556
Instantiations:            240994
Memory used:               84999K
Assignability cache size:   18439
Identity cache size:          128
Subtype cache size:             0
Strict subtype cache size:      0
I/O Read time:              0.01s
Parse time:                 0.19s
ResolveModule time:         0.02s
ResolveTypeReference time:  0.00s
ResolveLibrary time:        0.01s
Program time:               0.25s
Bind time:                  0.07s
Check time:                 0.34s

After

Identifiers:                  53327
Symbols:                      38110
Types:                       535156
Instantiations:              243474
Memory used:               2670146K
Assignability cache size:     35533
Identity cache size:            116
Subtype cache size:               0
Strict subtype cache size:       42
I/O Read time:                0.01s
Parse time:                   0.14s
ResolveModule time:           0.02s
ResolveTypeReference time:    0.01s
ResolveLibrary time:          0.01s
Program time:                 0.21s
Bind time:                    0.07s
Check time:                  30.54s
RyanCavanaugh commented 2 months ago

Basically stuck here:

import { Filter, FilterQuery } from "grammy";
import { Context } from "grammy/out/context.js";
// Uncomment constraint to repro
type MiddlewareFn<C /*extends Context*/> = (ctx: C) => void;
declare function on<Q extends FilterQuery>(middleware: MiddlewareFn<Filter<Context, Q>>): void;
Andarist commented 2 months ago

and there go my weekend plans... 😭

RyanCavanaugh commented 2 months ago

@ahejlsberg assigning to you since #57343 also was, but sounds like @Andarist might be working on it?

slyofzero commented 2 months ago

Bisects to #57345

what seems to be the issue here? grammy.js is at fault?

fatcerberus commented 2 months ago

Bisects to https://github.com/microsoft/TypeScript/pull/57345

what seems to be the issue here? grammy.js is at fault?

No, TS is. It's a regression caused by a change that was made in the linked PR (#57345), which was found via git bisect. grammy just happens to be the module that triggers the bug.

ahejlsberg commented 2 months ago

@RyanCavanaugh I'm unable to reproduce with the examples here and here. The second example (after uncommenting the constraint) shows this:

Files:              53
Lines:           48693
Identifiers:     51490
Symbols:         34834
Types:            3750
Instantiations:  87521
Memory used:    70217K
I/O read:        0.01s
I/O write:       0.00s
Parse time:      0.23s
Bind time:       0.07s
Check time:      0.14s
Emit time:       0.01s
Total time:      0.45s

This is with the compiler in main branch, following tsc -init and npm i grammy. Am I missing something?

RyanCavanaugh commented 2 months ago

@ahejlsberg Try this? https://github.com/RyanCavanaugh/repro-58373

Relevant numbers on main

Files:                           59
Lines of Library:             36690
Lines of Definitions:         13738
Identifiers:                  53544
Symbols:                      36350
Types:                       532823
Instantiations:              235429
Memory used:               2693736K
Assignability cache size:     35030
Check time:                  27.66s
Total time:                  27.95s
ahejlsberg commented 2 months ago

Ok, I can reproduce with your repo. The difference is you're using an older version of grammy, 1.20.3. Current version on NPM is 1.22.4 and it doesn't have a problem.

ahejlsberg commented 2 months ago

See https://github.com/grammyjs/grammY/pull/553. Looks like this is a known issue that was fixed by in the latest grammy. I'd still be interested in knowing why #57345 slowed down the old types, but appears there's a simple workaround.

Andarist commented 1 month ago

I'm still working on minimizing this further but I want to share a single-file repro created based on the code from grammy. Some parts of this probably no longer make sense (I remove bits that make sense for what their types want to achieve but which are not relevant for the repro):

repro ```ts type NotUndefined = string | number | boolean | object; type SnakeToCamelCase = S extends `${infer L}_${infer R}` ? `${L}${R}` : S; type AliasProps = { [K in string & keyof U as SnakeToCamelCase]: U[K]; }; interface Update { update_id: number; } type RenamedUpdate = AliasProps; declare class Context implements RenamedUpdate { updateid: number; } declare const UPDATE_KEYS: { readonly message: { readonly new_chat_members: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; readonly left_chat_member: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; readonly group_chat_created: {}; readonly supergroup_chat_created: {}; readonly migrate_to_chat_id: {}; readonly migrate_from_chat_id: {}; readonly successful_payment: {}; readonly users_shared: {}; readonly chat_shared: {}; readonly connected_website: {}; readonly write_access_allowed: {}; readonly passport_data: {}; readonly forum_topic_created: {}; readonly forum_topic_edited: { readonly name: {}; readonly icon_custom_emoji_id: {}; }; readonly forum_topic_closed: {}; readonly forum_topic_reopened: {}; readonly general_forum_topic_hidden: {}; readonly general_forum_topic_unhidden: {}; readonly forward_origin: { readonly user: {}; readonly hidden_user: {}; readonly chat: {}; readonly channel: {}; }; readonly is_topic_message: {}; readonly is_automatic_forward: {}; readonly text: {}; readonly animation: {}; readonly audio: {}; readonly document: {}; readonly photo: {}; readonly sticker: { readonly is_video: {}; readonly is_animated: {}; readonly premium_animation: {}; }; readonly story: {}; readonly video: {}; readonly video_note: {}; readonly voice: {}; readonly contact: {}; readonly dice: {}; readonly game: {}; readonly poll: {}; readonly venue: {}; readonly location: {}; readonly entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption_entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption: {}; readonly has_media_spoiler: {}; readonly new_chat_title: {}; readonly new_chat_photo: {}; readonly delete_chat_photo: {}; readonly message_auto_delete_timer_changed: {}; readonly pinned_message: {}; readonly invoice: {}; readonly proximity_alert_triggered: {}; readonly video_chat_scheduled: {}; readonly video_chat_started: {}; readonly video_chat_ended: {}; readonly video_chat_participants_invited: {}; readonly web_app_data: {}; }; readonly edited_message: { readonly new_chat_members: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; readonly left_chat_member: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; readonly group_chat_created: {}; readonly supergroup_chat_created: {}; readonly migrate_to_chat_id: {}; readonly migrate_from_chat_id: {}; readonly successful_payment: {}; readonly users_shared: {}; readonly chat_shared: {}; readonly connected_website: {}; readonly write_access_allowed: {}; readonly passport_data: {}; readonly forum_topic_created: {}; readonly forum_topic_edited: { readonly name: {}; readonly icon_custom_emoji_id: {}; }; readonly forum_topic_closed: {}; readonly forum_topic_reopened: {}; readonly general_forum_topic_hidden: {}; readonly general_forum_topic_unhidden: {}; readonly forward_origin: { readonly user: {}; readonly hidden_user: {}; readonly chat: {}; readonly channel: {}; }; readonly is_topic_message: {}; readonly is_automatic_forward: {}; readonly text: {}; readonly animation: {}; readonly audio: {}; readonly document: {}; readonly photo: {}; readonly sticker: { readonly is_video: {}; readonly is_animated: {}; readonly premium_animation: {}; }; readonly story: {}; readonly video: {}; readonly video_note: {}; readonly voice: {}; readonly contact: {}; readonly dice: {}; readonly game: {}; readonly poll: {}; readonly venue: {}; readonly location: {}; readonly entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption_entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption: {}; readonly has_media_spoiler: {}; readonly new_chat_title: {}; readonly new_chat_photo: {}; readonly delete_chat_photo: {}; readonly message_auto_delete_timer_changed: {}; readonly pinned_message: {}; readonly invoice: {}; readonly proximity_alert_triggered: {}; readonly video_chat_scheduled: {}; readonly video_chat_started: {}; readonly video_chat_ended: {}; readonly video_chat_participants_invited: {}; readonly web_app_data: {}; }; readonly channel_post: { readonly channel_chat_created: {}; readonly forward_origin: { readonly user: {}; readonly hidden_user: {}; readonly chat: {}; readonly channel: {}; }; readonly is_topic_message: {}; readonly is_automatic_forward: {}; readonly text: {}; readonly animation: {}; readonly audio: {}; readonly document: {}; readonly photo: {}; readonly sticker: { readonly is_video: {}; readonly is_animated: {}; readonly premium_animation: {}; }; readonly story: {}; readonly video: {}; readonly video_note: {}; readonly voice: {}; readonly contact: {}; readonly dice: {}; readonly game: {}; readonly poll: {}; readonly venue: {}; readonly location: {}; readonly entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption_entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption: {}; readonly has_media_spoiler: {}; readonly new_chat_title: {}; readonly new_chat_photo: {}; readonly delete_chat_photo: {}; readonly message_auto_delete_timer_changed: {}; readonly pinned_message: {}; readonly invoice: {}; readonly proximity_alert_triggered: {}; readonly video_chat_scheduled: {}; readonly video_chat_started: {}; readonly video_chat_ended: {}; readonly video_chat_participants_invited: {}; readonly web_app_data: {}; }; readonly edited_channel_post: { readonly channel_chat_created: {}; readonly forward_origin: { readonly user: {}; readonly hidden_user: {}; readonly chat: {}; readonly channel: {}; }; readonly is_topic_message: {}; readonly is_automatic_forward: {}; readonly text: {}; readonly animation: {}; readonly audio: {}; readonly document: {}; readonly photo: {}; readonly sticker: { readonly is_video: {}; readonly is_animated: {}; readonly premium_animation: {}; }; readonly story: {}; readonly video: {}; readonly video_note: {}; readonly voice: {}; readonly contact: {}; readonly dice: {}; readonly game: {}; readonly poll: {}; readonly venue: {}; readonly location: {}; readonly entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption_entities: { readonly mention: {}; readonly hashtag: {}; readonly cashtag: {}; readonly bot_command: {}; readonly url: {}; readonly email: {}; readonly phone_number: {}; readonly bold: {}; readonly italic: {}; readonly underline: {}; readonly strikethrough: {}; readonly spoiler: {}; readonly code: {}; readonly pre: {}; readonly text_link: {}; readonly text_mention: {}; readonly custom_emoji: {}; }; readonly caption: {}; readonly has_media_spoiler: {}; readonly new_chat_title: {}; readonly new_chat_photo: {}; readonly delete_chat_photo: {}; readonly message_auto_delete_timer_changed: {}; readonly pinned_message: {}; readonly invoice: {}; readonly proximity_alert_triggered: {}; readonly video_chat_scheduled: {}; readonly video_chat_started: {}; readonly video_chat_ended: {}; readonly video_chat_participants_invited: {}; readonly web_app_data: {}; }; readonly inline_query: {}; readonly chosen_inline_result: {}; readonly callback_query: { readonly data: {}; readonly game_short_name: {}; }; readonly shipping_query: {}; readonly pre_checkout_query: {}; readonly poll: {}; readonly poll_answer: {}; readonly my_chat_member: { readonly from: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; }; readonly chat_member: { readonly from: { readonly me: {}; readonly is_bot: {}; readonly is_premium: {}; readonly added_to_attachment_menu: {}; }; }; readonly chat_join_request: {}; readonly message_reaction: { readonly old_reaction: { readonly emoji: {}; readonly custom_emoji: {}; }; readonly new_reaction: { readonly emoji: {}; readonly custom_emoji: {}; }; }; readonly message_reaction_count: { readonly reactions: { readonly emoji: {}; readonly custom_emoji: {}; }; }; }; type KeyOf = string & keyof T; type S = typeof UPDATE_KEYS; type L1S = KeyOf; type L2S = L1 extends unknown ? `${L1}:${KeyOf}` : never; type L3S = L1 extends unknown ? L3S_ : never; type L3S_< L1 extends L1S, L2 extends KeyOf = KeyOf, > = L2 extends unknown ? `${L1}:${L2}:${KeyOf}` : never; type L123 = L1S | L2S | L3S; type CollapseL1< Q extends string, L extends L1Shortcuts = Exclude, > = | Q | (L extends string ? Q extends (typeof L1_SHORTCUTS)[L][number] ? L : never : never); type CollapseL2< Q extends string, L extends L2Shortcuts = Exclude, > = | Q | (L extends string ? Q extends (typeof L2_SHORTCUTS)[L][number] ? L : never : never); declare const L1_SHORTCUTS: { readonly "": readonly ["message", "channel_post"]; readonly msg: readonly ["message", "channel_post"]; readonly edit: readonly ["edited_message", "edited_channel_post"]; }; declare const L2_SHORTCUTS: { readonly "": readonly ["entities", "caption_entities"]; readonly media: readonly ["photo", "video"]; readonly file: readonly [ "photo", "animation", "audio", "document", "video", "video_note", "voice", "sticker", ]; }; type L1Shortcuts = KeyOf; type L2Shortcuts = KeyOf; type InjectShortcuts = Q extends `${infer L1}:${infer L2}:${infer L3}` ? `${CollapseL1}:${CollapseL2}:${L3}` : Q extends `${infer L1}:${infer L2}` ? `${CollapseL1}:${CollapseL2}` : CollapseL1; type FilterQuery = InjectShortcuts; type ExpandL1 = S extends L1Shortcuts ? (typeof L1_SHORTCUTS)[S][number] : S; type ExpandL2 = S extends L2Shortcuts ? (typeof L2_SHORTCUTS)[S][number] : S; type ExpandShortcuts = Q extends `${infer L1}:${infer L2}:${infer L3}` ? `${ExpandL1}:${ExpandL2}:${L3}` : Q extends `${infer L1}:${infer L2}` ? `${ExpandL1}:${ExpandL2}` : ExpandL1; type FilteredContextCore = Record<"update", U> & AliasProps>; type FilteredContext = C & FilteredContextCore; type PerformQuery = U extends unknown ? FilteredContext : never; type Filter = PerformQuery< C, RunQuery> >; type L1Equivalents = { message: "from"; edited_message: "from" | "edit_date"; channel_post: "sender_chat"; edited_channel_post: "sender_chat" | "edit_date"; }; type TwinsFromL1 = L1 extends KeyOf ? L1Equivalents[L1] : L2; type L2Equivalents = {} type TwinsFromL2 = L1 extends KeyOf ? L2 extends KeyOf ? L2Equivalents[L1][L2] : L2 : L2; type AddTwins = | TwinsFromL1 | TwinsFromL2 type L2ShallowFragment = Record< AddTwins, NotUndefined >; type L2Fragment = L2 extends unknown ? Record, NotUndefined> : never; type L2Discriminator = [L2] extends [ never, ] ? L2ShallowFragment : Combine, L2>; type L1Parts = Q extends `${infer L1}:${string}` ? L1 : Q; type L2Parts< Q extends string, L1 extends string, > = Q extends `${L1}:${infer L2}:${string}` ? L2 : Q extends `${L1}:${infer L2}` ? L2 : never; type L1Fragment = L1 extends unknown ? Record>> : never; type L1Discriminator = Combine< L1Fragment, L1 >; type Combine = U extends unknown ? U & Partial, undefined>> : never; type RunQuery = L1Discriminator>; type MiddlewareFn = (ctx: C) => void; declare function on( middleware: MiddlewareFn>, ): void; ```

I will continue working on this - so far, what I was able to notice is that AliasProps being a renaming mapped type impacts this.