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

Is there a CLI? #2270

Closed
4 tasks done
Twipped opened this issue Mar 14, 2023 · 7 comments
Closed
4 tasks done

Is there a CLI? #2270

Twipped opened this issue Mar 14, 2023 · 7 comments

Comments

@Twipped
Copy link
Contributor

Twipped commented Mar 14, 2023

Initial checklist

Problem

I wanted to create an npm script in one of my projects to compile some MDX files, but after digging through the docs and the issues, it seems there's no existing way to do this from the shell?

Solution

Some kind of really elementary @mdx/cli package would be very helpful.

Alternatives

I did find the babel instructions, so I'll probably go that route. It'd be nice if that babel plugin in the example was available as a published package to make it easier to use as a drop-in.

@ChristianMurphy
Copy link
Member

Heya @Twipped! 👋

Is there a CLI?

No, not currently

I wanted to create an npm script in one of my projects to compile some MDX files

Thanks for sharing!
Some follow up questions to help better understand your goal:

  • What framework are you compiling to? React, Preact, Vue, etc
  • How would those generated file(s) be consumed? By another build tool? Directly in browser?

it seems there's no existing way to do this from the shell?

Yes and no.
There is not a predefined MDX CLI yet. Most of the interest from the community thus far has been in having integrations into existing front end build tools: webpack, rollup, vite, etc.

There is a unified util to build CLIs: https://github.com/unifiedjs/unified-args which could potentially be leveraged.
There is likely some discussion to be had on what a compile CLI could look like, and if it even makes sense given the many ways mdx can be configured and used.

It's also worth cross referencing here, this is some ongoing work for an mdx-analyzer CLI, which would be more validation focused mdx-js/mdx-analyzer#292

@wooorm
Copy link
Member

wooorm commented Mar 15, 2023

I wanted to create an npm script in one of my projects to compile some MDX files

How would that work? What is the input? What is the output? What does this CLI do exactly?
I’m wondering why you’d want to use a separate tool that only compiles, and not something that bundles (rollup/esbuild/webpack/etc)?

@Twipped
Copy link
Contributor Author

Twipped commented Mar 15, 2023

What framework are you compiling to?

My own, actually. It's a JSX template engine for use in a static site builder. I have MDX fixtures as part of my test suite and I wanted an easy way to convert them to js modules to be imported and evaluated in the tests. I did work out how to make babel do it, but a shell command would have saved me some time.

(btw, @wooorm, your property-information package has been quite useful with this, thanks for that!)

@wooorm
Copy link
Member

wooorm commented Mar 15, 2023

Why do you need babel, and why isn’t compile from @mdx-js/mdx enough? I get that it’s still a couple lines of Node code instead of a bash script to fs.readdir/fs.readfile/compile/fs.writefile, but that’s what I’d think is enough for your use case?

I see you’re also turning esm (mdx files are esm) into cjs, I guess Babel does that for you? That’s interesting though because our CLI could not do that (or at least, I’d think that would be out of scope).


For the project you’re working on, two things that come to my mind:

  • It seems a bit like @remcohaszing’s mini-jsx, which does have some “framework” capabilities, and I think renders DOM nodes

  • You could also generate our own AST, as a jsx runtime: https://github.com/syntax-tree/hastscript#jsx. ASTs are kinda exactly like a VDOM, which is why it might work. This is a bit meta, because MDX uses that AST internally too on the typically “server” side (though it could be anywhere), which is something to ignore for this: this AST generated with hastscript would be used on the “client” side (could be anywhere tho). Then some render function would use that AST to generate something else (DOM with hast-util-to-dom, string of HTML with hast-util-to-html)!

@Twipped
Copy link
Contributor Author

Twipped commented Mar 15, 2023

Why do you need babel

Did you mean to ask why I need a CLI? I'm using babel because I didn't have another option.

I get that it’s still a couple lines of Node code instead of a bash script

Yes, that's exactly the reason. Why write a separate script to do what could be done in a single shell command? That's basically why I asked, because the idea seemed so obvious to me that I assumed I must be missing something. Have a tool that takes a string and spits out another string? It seemed natural to include a bin to do that with stdio.

our CLI could not do that

True, which was something I did not notice until after I made this Issue. I would have had to pipe the output through babel anyway, but at least I could have used my existing babel config for converting the JSX, rather than adding another plugin.

It seems a bit like mini-jsx

Similar, yes. This is focused on static html compilation, however, with no browser DOM at all.

My first approach was, indeed, building some sort of AST that could be stringified into HTML, but shortly into it I realized that was a completely unnecessary step. I didn't need to manipulate the AST once it was generated, it was just going straight to serialization, so why bother with the AST at all when I can serialize directly from the Element classes.

I was initially inspired by template-jsx, but I needed it to be asynchronous so that I could perform IO within components, and I wanted to be able to do context passing so that I could implement things like Helmet or Emotion, where child elements can use & manipulate state further up the render tree.

@Twipped
Copy link
Contributor Author

Twipped commented Mar 29, 2023

I'm gonna close this, since the actual question has been answered. It would be nice if there was an official babel plugin published to do this, rather than just a guide on how to make your own.

@Twipped Twipped closed this as completed Mar 29, 2023
@wooorm
Copy link
Member

wooorm commented Mar 29, 2023

I am not sure why there needs to be an official babel plugin. It could live in userland too, for the folks that need it. Not everything has to be maintained by/in “core”. A lot of things can flourish in userland in my opinion! :)
But I’ll keep my ear to the ground, to see if there’s more folks needing it as a package instead of a small copy/pasted module!


As for a CLI, I think that’s covered in mdx-js/mdx-analyzer#292. It’s still a vague idea tho, so more discussion on what it should look like can go there!

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

No branches or pull requests

3 participants