-
-
Notifications
You must be signed in to change notification settings - Fork 1.7k
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
Support ES Module output in npm package. #862 #863
Conversation
Hello @paulirwin, |
@thiagodp I appreciate the input, but this project already uses Rollup, so changing that is outside the scope of this PR. |
@paulirwin Ok. JFI, Microbundle is based on Rollup, and you could continue using the existing plug-ins. |
@paulirwin any update on this? Would be a great addition to the library |
@tdekoning I also would like to see this PR merged 😉 |
I'd also really like to see this merged please 🙏 |
Any update on this? It would help resolve some issues I am having. |
Tagging the two people listed in the markdown-it org: @puzrin @rlidwka It appears the community is longing to get this fix merged into the project. I'd be happy to address any feedback with it if there's anything preventing this from getting merged. Let me know how I can be of any assistance. Thanks! |
Would very much like to see this PR merged. Happy to help take this through if help is needed. |
As a workaround, I'm using this: https://github.com/esm-bundle/markdown-it |
I am generally a patient person when it comes to things like this, but this PR has been open for over a year and is fairly simple. It has been over two months since I pinged the owners of this repo, with no response. There have been no merged PRs since August of 2022 as far as I can tell. Seriously asking, is this project dead? |
How could it not being merged for SOOOOO LONG? It will be uncomfortable to see a mixed usage of esm & native javascriprt in any node.js project, and it will also cause confusion for IDEs. |
Marked has ESM builds, FYI: https://www.npmjs.com/package/marked or in browser: import { marked } from "https://cdn.jsdelivr.net/npm/marked/lib/marked.esm.js" |
OMG I simply didn't do too much searching, THANK YOU A LOT!!!
…---Original---
From: "Travis ***@***.***>
Date: Fri, Jun 30, 2023 02:39 AM
To: ***@***.***>;
Cc: ***@***.******@***.***>;
Subject: Re: [markdown-it/markdown-it] Support ES Module output in npmpackage. #862 (PR #863)
Mark has ESM builds, FYI: https://www.npmjs.com/package/marked
or in browser:
import { marked } from "https://cdn.jsdelivr.net/npm/marked/lib/marked.esm.js"
—
Reply to this email directly, view it on GitHub, or unsubscribe.
You are receiving this because you commented.Message ID: ***@***.***>
|
@treeder Unfortunately this is a transitive dependency for me so that isn't an option for all cases 😦 |
In 2023, we'll also want an "exports": {
"require": "./index.js",
"import": "./dist/esm/markdown-it.mjs"
}, That makes sure resolution that doesn't use the non-standard (Just verified that this PR still applies cleanly, but node will load the CJS code when you import it. With the above change to package.json, it loads the ESM code, and everything seems to work.) Further edit: Actually, adding this will forbid importing modules directly from the package by path, which is maybe a style you intend to support, given that there are separate minified files. Which modules are users expected to want to load directly? |
This would be great to have supported! |
@paulirwin @marijnh "exports": {
".": {
"import": "./dist/esm/markdown-it.mjs",
"require": "./index.js"
},
"./*": {
"require": "./*",
"import": "./*"
}
}, will be this PR eventually merged? |
Re: @marijnh (I am forever indebted to you for your excellent work on ProseMirror, btw. Thank you for that library!)
This is good to know, thanks! I don't spend a lot of time in Node directly and only use this package via Angular. Should
I don't have any particular intentions if this was addressed to me, other than ensuring that optimization in Angular builds works. I am a little out-of-the-loop of current Node package conventions and standards. I know at one point in the past, it was fairly common to include minified builds with your package like markdown-it has done prior to my PR. Is that no longer the case? If so, that would certainly simplify the Rollup config and build. I'm eager to learn from the community here on any ways I can improve this PR. Re: @adrian-branescu
What does the second export with the
I am encouraged to see recent activity in September of this year on this project. It would be great if this could get merged at some point. Obviously as the PR author I would love to see it merged, but alas I am not a contributor to this repo. It sounds like I do need to brush the dust off of it before it is merged, though, with the addition of |
That should be fine, and help some tools that still use the old convention.
Once you have an I would hope updating this PR and prodding a bit more will lead to a new release. |
See the thread at markdown-it#863 This adds exports which is the new standard way of defining what can be required/imported from a Node package. Additionally, it specifies the type of the package to be a module.
@marijnh @adrian-branescu Thank you! I have made those changes to this PR. Quick testing of a new Node package that references it by file path seems to work fine at least for constructing a MarkdownIt. If either of you can help validate that I did this correctly and sufficiently, that would be appreciated. |
@paulirwin @marijnh external: [
/node_modules/
] in order to prevent including in the bundle the external dependencies (along with the whole graph of transitive dependencies) from package.json: "dependencies": {
"argparse": "^2.0.1",
"entities": "~3.0.1",
"linkify-it": "^3.0.1",
"mdurl": "^1.0.1",
"uc.micro": "^1.0.5"
}, In this way, one can use this NPM package in Node.js and Web apps with a bundler like Webpack, Rollup, Vite etc without having those dependencies included multiple times in the final app bundle. |
Correction! I thought you were talking about the |
If I'm understanding this correctly, this would be an existing problem with the current rollup CJS output, is that correct? If so it seems like that warrants its own PR and could be merged independently. |
Thanks. With that change this patch works for me (I tried: importing as ESM, requiring as CommonJS, requiring a specific dist/ file.) |
Yes, this problem replicates on the master branch too. On your branch, there are >2000 lines of external source code added besides package own source code: # find lib/ -name '*.js' | xargs wc -l
6185 total
# cat dist/markdown-it.js | wc -l
8356
# cat dist/esm/markdown-it.mjs | wc -l
8675 These may be duplicated in a Web App that makes use of the same dependencies like this package because the app bundler has no idea that they were already included in this package bundle. |
@adrian-branescu Thanks for the info, I could see where the addition of this could exacerbate that problem. If there's consensus from others that the |
@puzrin Are you okay with releasing this? Or giving some feedback on what would be needed before it gets released? |
We closed most of pending issues/prs, and I'm rewriting to es6 to solve the rest. Need advice, what is preferable:
Could you help? |
It doesn't matter much, but if you want to keep supporting the old behavior of requiring |
@marijnh thank you very much for info! I tend use |
See
Since change is huge, and I have no solid experience with esm development, I'm open to any suggestions, what should be improved. Hope to spread the same changes to all other maintained repos. |
Use Class syntaxSo, using // function MarkdownIt
class MarkdownIt {
/*
function MarkdownIt(presetName, options) {
// ...
}
*/
constructor(presetName, options) {
// ...
}
/*
MarkdownIt.prototype.set = function (options) {
// ...
}
*/
set(options) {
// ...
}
/*
MarkdownIt.prototype.configure = function (presets) {
// ...
}
*/
configure(presets) {
// ...
}
} Use let/constInstead of declaring variables with |
@SReject The problem with classes is, that existing implementation uses hack for the call without Also not sure, if should I use rollup+babel for the es6 modules build, or leave that for upper-level use. |
Its generally considered an anti-pattern now-a-days to use class-factory functions. For those that wish it, its best to export the class definition as default, then the factory function as a seperate export: class MarkdownIt {
// ...
}
const factory = (...args) => new MarkdownIt(...args)
export {
MarkdownIt as default
factory as MarkdownIt
}; // import the class, use it w/ 'new'
import MarkdownIt from 'markdown-it';
const thing = new MarkdownIt();
// or
// Import the factory function, use it without 'new'
import { MarkdownIt } from 'markdown-it';
const thing = MarkdownIt();
// or
// Import both
import MarkdownItClass, { MarkdownIt as MarkdownItFactory } from 'markdown-it';
const thing1 = new MarkdownItClass();
const thing2 = MarkdownItFactory(); |
What is the reason to force every user to type Right now in Aside: Callable constructors can be done with ES6 classes. And I've did that for argparse: But honestly, I think it's better to keep it as function+prototype for now, until ecmascript spec guys finally manage to come up with callable constructors out of the box without complexities like Reflect. |
Just for clarity, when I say 'class-factory functions' I mean functions that serve a duel purpose of being both a constructor and a function that returns an instance. Now working backwards from your post...
Looking at proposals, this is sadly not going to happen any time soon. The one proposal to rectify such has been withdrawn in favor of decorators. The original reasoning for not having callable class constructors is the committee's views on separation of intents: (paraphrased) "A function should be callable, a class should be an instantable".
This is a true and not true. While I disagree with the commitee's opinion in regards to callable class constructors, the current state of ES should inform modern coding practices; that being there should be a distinction of intents.
There is none nor am I suggesting such. In the example I provided, I showed how to have both. As an aside, I definitely like your |
This distinction of intents is not relevant for this library. In fact, the only case I've seen so far where the behavior is different is Thus, I consider it a bug in ES6 spec. And until it gets fixed, we cannot use ES6 classes. |
I'm closing this, since master rewritten to ESM, and have fallback to CJS (generated on publish, or via It will take some time (up to 1-2 weeks) to check other issues and transform plugins. But you can write any thoughts if something else should be fixed. |
Published v14 with native ESM support. |
Adds ES Module (ESM) output in the Rollup config (in addition to the existing UMD output), and adds a helpful
npm run build
script. Fixes #862Per the
CONTRIBUTING.md
file, I am not including the ESM build here, but I can easily add that if you would like.Example Angular component using the ESM build (add to package.json as a file-path dependency) which does not have the warning about optimization bailouts:
Template HTML: