TypeScript
TypeScript copied to clipboard
Allow disabling ambient types
Suggestion
I understand that this is something that there will be a range of opinions on.
What I'd like is an option to restrict ambient types so that even if a library has shipped with ambient types, they aren't exposed. Ideally, this would also prevent those libraries from modifying global types.
🔍 Search Terms
I searched for:
- Ambient types
- Global types
Related:
- https://github.com/microsoft/TypeScript/issues/50424
Possibly related:
- https://github.com/microsoft/TypeScript/issues/14306
- https://github.com/microsoft/TypeScript/issues/17042
✅ Viability Checklist
My suggestion meets these guidelines:
- [X] This wouldn't be a breaking change in existing TypeScript/JavaScript code
- [X] This wouldn't change the runtime behavior of existing JavaScript code
- [X] This could be implemented without emitting different JS based on the types of the expressions
- [X] This isn't a runtime feature (e.g. library functionality, non-ECMAScript syntax with JavaScript output, new syntax sugar for JS, etc.)
- [X] This feature would agree with the rest of TypeScript's Design Goals.
⭐ Suggestion
An option in TS Config to prevent library-provided ambient types from polluting the global namespace.
📃 Motivating Example
The rationale for this:
- They don’t feel like a good fit in modern module-based JavaScript, where globals are discouraged.
- They create confusion - “Where is this type coming from? Is it the right type?”
- They create inconsistency - ex. some engineers import type from
Reactand some rely on the ambient types. - There is a high chance of collisions or confusingly similar names in the global space.
Further, I commented on this issue (related) and noted that we've actually encountered bugs because some of these libraries also modify global types.
- https://github.com/microsoft/TypeScript/issues/50424#issuecomment-1233765480
💻 Use Cases
As an example, we hit an issue last year where global types were being modified by libraries, which caused type issues that were hard to diagnose and fix.
- https://github.com/cloudflare/workers-types
- https://github.com/octokit/webhooks.js (the offending code was commented out in a later release)
Sounds like a duplicate of #50424.
It's not really clear how you could make this work in a general case.
Consider the case where you have some generic type with a type constraint:
type F<T extends Foo> = ...
Let's say the library code instantiates F with a global type that you've augmented to match Foo, but which previously wouldn't have matched. Presumably, now this has to be a type error, but it shouldn't be an error because it's code that depends on an invariant that the library itself set up in the first place. That seems really awkward and also not possible for you to fix on your side.
We've looked at the problem of global pollution a lot and not yet found any solutions that don't incur these or other similar kinds of problems. See also #31894 and related discussions
Thanks, I'm happy to close this off as a duplicate if you'd like.
I realise that this is a hard problem to solve, and I understand the issues that you've raised here.
Thinking about other rules with similar problems, exactOptionalPropertyTypes comes to mind. I've seen a lot of libraries updating code to support that option, and library authors seem very positive/receptive to those requests. If the error could prompt users to ask for/contribute a fix in these scenarios, that would help too.
This issue has been marked as a 'Duplicate' and has seen no recent activity. It has been automatically closed for house-keeping purposes.