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

Add note about usage of ESM in source config file #1394

Open
wants to merge 3 commits into
base: docs
Choose a base branch
from

Conversation

karlhorky
Copy link

Hi there, thanks for ts-node, it's super useful!

Quick PR to communicate that it's possible to use ESM as a module format in source files

Ref: jestjs/jest#11453 (comment)

@cspotcode
Copy link
Collaborator

Can this be rolled into this page?
https://typestrong.org/ts-node/docs/imports
Can we improve the way the two pages are linked?

It's actually common knowledge in TS that you can use native import/export syntax regardless of the "module" option. We don't want to be in the business of explaining TS fundamentals, since that will always be handled better by TypeScript's own documentation.

With that in mind, can we link to TypeScript's documentation? Do they have a page explaining this?

@karlhorky
Copy link
Author

karlhorky commented Jul 18, 2021

It's actually common knowledge in TS that you can use native import/export syntax regardless of the "module" option

The general guidance is: TS should always be written with native ECMAScript module syntax

Interesting assertions, I haven't found anything to support this except some slightly similar language in this one other blog post: https://dev.to/darraghor/don-t-make-these-mistakes-using-ecmascript-es6-modules-in-your-next-node-js-application-4ki2

I have personally almost always written TS with standard ESM-style import and export up until now, except for some type definition files where I used the import x = require('x') syntax.


This is the closest TS documentation page to what I think you are looking for, but I don't see anything about recommending usage of ESM-style import and export: https://www.typescriptlang.org/docs/handbook/2/modules.html


As for moving it to the https://typestrong.org/ts-node/docs/imports/ page instead, I'm not sure that this information would have been useful for me on that page - I would have looked for it right beside the place with the overrides. To be clear, I have not been confused about ts-node itself - only about the wording and appearance of this moduleTypes configuration:

{
  "ts-node": {
    "moduleTypes": {
      "webpack.config.ts": "cjs",

My thoughts are: To see a moduleType of cjs right next to a path to a TS file seems like it could be confusing to read.

I suppose another option would be a different wording of the configuration option (moduleOutputs instead of moduleTypes):

{
  "ts-node": {
    "moduleOutputs": {
      "webpack.config.ts": "cjs",

But who knows - maybe you're right and this is a non-problem for everyone except me 🤷‍♂️

@cspotcode
Copy link
Collaborator

Interesting assertions, I haven't found anything to support this except some slightly similar language in this one other blog post:

The strength of my wording comes from answering beginner questions over the years. To make it simple for people, answers tend to migrate towards stronger and stronger recommendations over time. I can see how the word "always" might be triggering, because one can easily find exceptions to the rule.

I have personally almost always written TS with standard ESM-style import and export up until now, except for some type definition files where I used the import x = require('x') syntax.

It sounds like we're mostly on the same page. This is what I was thinking, that most TS users already write using import and export syntax.

Up into recently, TS on node was always compiled to CommonJS because that is the only thing that node supported.

I suppose another option would be a different wording of the configuration option (moduleOutputs instead of moduleTypes):

I opted for moduleTypes because we're not merely controlling the compiler's output, we're also telling node how to execute that output. This is a separate mechanism typically governed by node's package.json "type" field; hence moduleTypes. Node also refers to ES modules and CommonJS modules as the two module "formats." (link)

For some nitty-gritty details about why and how we are required to tell node which format to use, node docs here

To see a moduleType of cjs right next to a path to a TS file seems like it could be confusing to read.

I suppose this depends on if the reader knows that node uses a lot of CommonJS. To me, seeing node and "CommonJS" in the same sentence makes sense.

Webpack also has their own documentation; can we link to that? I believe it has complete examples of webpack.config.ts, showing the import and export syntax.

@cspotcode
Copy link
Collaborator

For what it's worth, I think the wording on https://typestrong.org/ts-node/docs/imports needs to be improved. The opening sentence is confusing. The following is too informal but might be an improvement:

The general guidance is: TS should almost always be written with ECMAScript module syntax, import and export statements.
The question is whether or not we ask typescript to transform that syntax into CommonJS or not

This is copied from earlier posts but tweaked based on your feedback.

@cspotcode
Copy link
Collaborator

As a meta note, although I'm disagreeing and debating certain points, I appreciate the opportunity to discuss this, because documentation is hard and I don't have any editors helping me out. Thank you.

@karlhorky
Copy link
Author

Webpack also has their own documentation; can we link to that? I believe it has complete examples of webpack.config.ts, showing the import and export syntax.

Yep, that is actually the content of this PR: https://webpack.js.org/configuration/configuration-languages/#typescript

@@ -41,6 +41,29 @@ When multiple patterns match the same file, the last pattern takes precedence.
* `esm` overrides matches files to compile and execute as native ECMAScript modules.
* `package` resets either of the above to default behavior, which obeys `package.json` `"type"` and `tsconfig.json` `"module"` options.

**Note:** This does not mean that you have to write CommonJS in your source `webpack.config.ts` file
- here you can continue writing imports and exports in ESM syntax.
Copy link
Collaborator

Choose a reason for hiding this comment

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

How about wordsmithing this a bit to focus on "syntax" and avoid negatives, so we're saying something like "you can still use ECMAScript import / export syntax in your .ts file."

Following that by a link to webpack's documentation page makes sense.

Copy link
Collaborator

Choose a reason for hiding this comment

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

What do you think about merging this entire page into the "CommonJS vs native ECMAScript modules" page? Maybe giving that page a better title, like "Module Formats: CommonJS and ECMAScript modules"?

I'm wondering if we can have a single page that comprehensively describes the differences between CommonJS and ECMAScript modules, explains that you can almost always use import and export syntax, and explains moduleTypes overrides.

Copy link
Author

Choose a reason for hiding this comment

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

How about wordsmithing this a bit to focus on "syntax" and avoid negatives, so we're saying something like "you can still use ECMAScript import / export syntax in your .ts file."

Following that by a link to webpack's documentation page makes sense.

I'm wondering if we can have a single page that comprehensively describes the differences between CommonJS and ECMAScript modules, explains that you can almost always use import and export syntax, and explains moduleTypes overrides.

Nice, I think these two together makes for a really nice change. Then anyone confused can read everything about the module formats, because the information is right next to it.

Copy link
Collaborator

Choose a reason for hiding this comment

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

Ok cool. If I get to this before you, I think I'll take a stab at some of this refactoring -- pushing my changes to this branch -- and ask you for a review to make sure it's all still intuitive.

};

export default config;
```
Copy link
Collaborator

Choose a reason for hiding this comment

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

I hesitate to duplicate this rather than linking to webpack's documentation. webpack might be updating it soon. Also, webpack is not the only tool we want to integrate with.

Copy link
Collaborator

Choose a reason for hiding this comment

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

How about we create a webpack page under "Recipes"? That way, we can afford to give very specific webpack advice and examples, and we can link to the moduleTypes page.

Copy link
Author

Choose a reason for hiding this comment

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

Well, if we just follow your other suggestion from above and link to the webpack config, would that resolve this in a different way?

Copy link
Collaborator

Choose a reason for hiding this comment

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

I guess the only thing we'd be saying that webpack's website isn't, is we'd be giving an example moduleTypes config. I dunno if webpack's website will eventually add the same.

Copy link
Author

Choose a reason for hiding this comment

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

Right, I think I understand - you mean because if it was a recipe, both the moduleTypes config and the actual webpack config would just be in one place, got it. That's true - if we linked to the docs instead, then the moduleTypes config would be on the ts-node website and the webpack config would be on the webpack docs website, separated by that link.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants