-
Notifications
You must be signed in to change notification settings - Fork 12.8k
TypeScript adds exports {}
into code
#41513
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
Comments
I was thinking a better approach would have been to add a flag to the I don't know all the ins and outs of TypeScript and the decisions made but this decision seems highly irregular for code that should also work in the browser and in Service Worker scripts. |
TypeScript does not follow SemVer. |
@MartinJohns Oh, I didn't know that. Like I said. I don't follow everything which is done in the TypeScript world, otherwise I would have to be a full time employee. But it is nice to know. I think at this point most people assume SemVer for projects. So, that is a bit disheartening to hear that TypeScript doesn't follow SemVer. |
Almost every update had a breaking change. Whether they call it TypeScript 41.0 or TypeScript 4.1 doesn't really make much of a difference. You can read about the heated discussion at #14116. |
According to this page, they should if you include navigator.serviceWorker.register('/outputFile.js', {
type: 'module'
}); |
I'll check it out tonight. Regardless, this would be more of a work around. TypeScript should not be adding additional unneeded and unexpected code to our code base. This seems more like a tooling problem and should be an config setting change. |
This is what Firefox says when adding the
And in Chrome:
So, long term this really needs to be fixed since it is clearly a bug on TypeScript's side. |
Aside: Even if we did follow semver, this wouldn't warrant a major version bump, because it's a change that increases our compliance with the ECMAScript spec. Anyway the file you wrote was a module (since it had an You're free to suggest a new compiler option but this is the intentional behavior. |
It only had a type import. How else are we supposed to import types? Do we need to make all our types globals? |
Type imports are not the same as importing actual JavaScript files. Regardless, I don't think TypeScript should be creating random code in our code base. Even if it is a module if I don't want to export anything I should have some random If the way forward is to make everything global, that is fine. The behavior of injecting random code into our code bases doesn't seem right though. |
It's not "random"; it's preserving the moduleness of the file. You wrote code that didn't contribute to the global scope because the containing file was a module, then TypeScript emitted a file that did contribute to the global scope -- that's an obvious, obvious defect. |
I wrote code that imported types only. It is not a module though. It's unfortunate that TypeScript no longer supports importing types for files that are not modules. If that is what you think is best that's fine. I think it is unfortunate that is all. I don't think TypeScript should be adding that type of code into our code bases. If someone want to It would be nice if there was a clean way to import types without having to resort to the global scope. Granted I'll have to test that out to see if that will work. It seems like TypeScript is breaking its mission here by catering to some developers over others though. |
It's not great, but there's this: type Type = import("./path").Type |
Thanks I'll try it out. I was thinking that part of what bothers me about this is that adding And I tested this out: <script type=module>
console.log("cats!")
</script> This is a perfectly valid module code. No need to have My vote is to have to have a setting to opt in to have But you guys to whatever you like. I just think this seems dirty, it's not a clean solution to the problem. I think as a temporary solution to this I'll just stay on 3.9.* until, hopefully, this is fixed in a later version of TypeScript. |
I did some more testing and these seem to be valid module scripts (they work just fine in Firefox):
console.log("I like dogs")
<script type=module>
import { } from "./index.js"
console.log("Cats!")
</script> Result in console:
So, |
@jon49 , according to the explanation by RyanCavanaugh above, the old behaviour in TypeScript 3.9 is actually a bug, the current new behaviour in TypeScript 4.0 (where So don't count for this to be reverted. The best we can hope for is a new compiler switch. I guess we have to change our workflow now, we can no longer simply link a transpiled js file directly in a web page. |
According to ECMAScript, if I understand it correctly. It says you don't even need anything in a module. So, the I tried Changing the settings in the Service Workers don't support modules yet, at least not in Chrome, see: https://bugs.chromium.org/p/chromium/issues/detail?id=824647 So, basically, if you want to share types in your code, and you want to keep those types local to where they you created them and you are not using modules you need to go old school, like in
And then export those types to a global type file like this:
import { MyType as MyType_ } from "../some-dir/my-file.d.ts"
global {
declare namespace SomeDir {
type MyType = MyType_
}
} Which is pretty onerous. So, I hope you can see why I'm pushing against this so hard. Now, this is my current solution which keeps me on the latest param([string] $Path)
$stream = [IO.File]::Open($Path, [IO.FileMode]::Open)
$stream.Position = $stream.Length - 12
$bytes = 0..12 | % { $stream.ReadByte() }
if ("$bytes" -eq "101 120 112 111 114 116 32 123 125 59 13 10 -1") {
$stream.SetLength($stream.Length - 12)
Write-Host "Removed from $Path"
}
$stream.Close()
$stream.Dispose() Personally, I consider this to be a bug on My vote is that a setting be added which would be |
Service workers and web workers are close to supporting modules, but don't yet. Not all browsers are 100% compliant with the module spec. In my case TS 4.0 is adding Why is TS adding an I find the " I don't really care whether this is opt-in or default behaviour with an opt-out, either would be fine, but the current solution appears to be either:
None of these is a good option. |
This issue has been marked 'Working as Intended' and has seen no recent activity. It has been automatically closed for house-keeping purposes. |
Actually let's just track this at #41567 since there's a good discussion already about the scenario and implications of such a flag |
Rewrote the Service Worker in TypeScript! It *kind of* works great, but not quite. I wish the TypeScript team made tooling for Workers a bit better, as it seems harder to work with than it should be. This rewrite was all from last night, and it took a few hours to learn how to get things right (I didn't get around to commiting it until now though). There aren't any type errors anymore, but I'm also unsure if it will run sucessfully yet. I don't have a device/OS to test the Web Share Target API support anymore, since my Chromebook runs Ubuntu now :) While it's not fully functional yet, this is a step in the right direction for type-safe Service Worker code! I mostly rewrote it with my new programming styles, expanding things out for readability, and making use of async-await where it was previously just `.then()` calls and such. Some help to get it working: https://github.com/NicholasPeretti/service-worker-ts-example https://stackoverflow.com/questions/89332/how-do-i-recover-a-dropped-stash-in-git (I had an oopsie XD) Edit: Tried testing out the worker in the browser, and modern TypeScript now includes empty `export {}` instances in the resulting JS, which breaks declaring the file as a module, as you can't have `export {}` in a non-module script. The only way I got close to this was to name the file `.mts`, but I'm not sure if I like that or not. But hey, it may work. With that being a possible solution, I found all of these sources along the way also: https://stackoverflow.com/questions/56356655/structuring-a-typescript-project-with-workers https://github.com/jakearchibald/typescript-worker-example (now outdated, unfortunately, thanks to this new TypeScript change) microsoft/TypeScript#41513 https://www.devextent.com/create-service-worker-typescript/ (almost works! falls down to the same issue sadly) microsoft/TypeScript#14877 microsoft/TypeScript#11781
Adding type="module" on the script tag fixed it for me |
When importing with just types no
export {}
should be added. And I would also opine that if a person wants to emitexport {}
they should actually write that into their code themselves or be able to add a hook into the compiler which says to do that. This breaks my browser code. We shouldn't have magical code like this in the compiler. And service workers do not understand the keywordexport
.Code
Expected behavior:
Actual behavior:
Related Issues:
#38696
#38713
https://stackoverflow.com/questions/64798609/typescript-appends-export-to-end-of-file-in-typescript-4-but-not-typescript-3
The text was updated successfully, but these errors were encountered: