FG
💻 Software🌐 Web & Full-StackMicrosoft

Support `.mjs` output

Freshover 4 years ago
Mar 14, 20260 views
Confidence Score75%
75%

Problem

Experimental support for ES modules just landed in Node 8.5 (changelog, PR). Since ES modules have some parsing and semantic differences, Node decided to use the `mjs` extension for ES modules (while `js` is for the "script" target and commonjs modules). The current Typescript version (`2.5.2`) supports ES modules emission but uses the `js` extension by default. It means that to use it with Node, a post-compilation step is required to change the extension from `js` to `mjs`. This adds undesirable complexity to use native ES modules support with Node. A solution would be to add a compiler option to output `.mjs` files when emitting ES modules. Edit (2018-03-22): The propositions below are a bit outdated. I recommend reading the issue to see the progression. See this comment for my current proposition. Notes: - It is possible that new parse goals will be added in the next versions of the ES spec. Letting the user provide the extension explicitly (as opposed to a boolean switch) would allow to be forward compatible with other new extension. - It should still be possible to emit ES modules with the `.js` extension, many tools rely on the `js` extension. - Another solution would be to have a different extension for the source files: `.mts` files would compile to `.mjs`, this would be similar to `.tsx` and `.jsx`.

Unverified for your environment

Select your OS to check compatibility.

1 Fix

Canonical Fix
High Confidence Fix
74% confidence92% success rate9 verificationsLast verified Mar 14, 2026

Solution: Support `.mjs` output

Low Risk

Thank you very much for clarifying your comment. I understand that adding any new feature is a burden since it means that it then must be supported for a long time, but I believe that the benefits of the `mjs` support are worth it: it won't turn `tsc` in a complex build tool but help TS users. The long term goal of the Node team is to allow users to author their code using ES modules without payi

74

Trust Score

9 verifications

92% success
  1. 1

    Thank you very much for clarifying your comment.

    I understand that adding any new feature is a burden since it means that it then must be supported for a long time, but I believe that the benefits of the `mjs` support are worth it: it won't turn `tsc` in a complex build tool but help TS users.

  2. 2

    The long term goal of the Node team is to allow users to author their code using

    The long term goal of the Node team is to allow users to author their code using ES modules without paying a cost due to the commonJs modules and script target. This is one of the reasons why the proposals to require `"use module"` or an `export` statement (even an empty one) were dropped in favour of using a new extension. See the Node EPS discussions in https://github.com/nodejs/node-eps/issues/57 and https://github.com/nodejs/node-eps/pull/60. If a post-compilation step to rename the files is still required in two years only because `.mjs` was introduced later then it will just add another

  3. 3

    Complex build tools have their place for assets management, dead-code eliminatio

    Complex build tools have their place for assets management, dead-code elimination, bundling, minification, etc. These all fall out of scope for TS, but being able to produce runnable code does not. Big projects have their own workflows and use the TS library (either directly or through plugins for other task runners), adding the renaming step is not a big deal for them. On the other hand, a sizeable chunk of projects using Typescript are small/medium sized libraries. These libraries usually only need a single tool: `tsc`. If they want to support native ES modules, they'll currently have to com

  4. 4

    It raises the barrier to entry because newcomers can no longer simply use `tsc -

    Now, a related problem is that it may cause some inconsistencies and duplication: different projects will use different ways to rename their file. I discovered `renamer` thanks to the message above, but I would have written a gulp task otherwise. Someone else would have used a POSIX-only shell command with broken edge cases or rolled their own helper Node script. To be honest, I think that most good projects would have a good implementation but this lack of standard way to deal with file renames _when no build system is already there_ may increase the "barrier to entry" problem. Finally, once

Validation

Resolved in microsoft/TypeScript GitHub issue #18442. Community reactions: 102 upvotes.

Verification Summary

Worked: 9
Partial: 2
Failed: 1
Last verified Mar 14, 2026

Sign in to verify this fix

Environment

Submitted by

AC

Alex Chen

2450 rep

Tags

typescriptcompilersuggestionin-discussiondomain:-es-modules