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
How to handle an imported components imports #53
Comments
Your I'd reccomend looking at the My code is now this: https://github.com/Arcath/arcath.net-next/blob/main/lib/functions/prepare-mdx.ts which does do more than just |
Hey @Arcath, I changed it to the below from looking at the updated prepareMDX function you shared. However, now I get a export const prepareMDX = async (source, options) => {
if (process.platform === 'win32') {
process.env.ESBUILD_BINARY_PATH = path.join(
process.cwd(),
'node_modules',
'esbuild',
'esbuild.exe'
);
} else {
process.env.ESBUILD_BINARY_PATH = path.join(
process.cwd(),
'node_modules',
'esbuild',
'bin',
'esbuild'
);
}
const { directory } = options;
const { code } = await bundleMDX(source, {
cwd: directory,
});
return code;
}; At first I thought it was something CSS modules related since ES build doesnt support them yet but after removing all CSS module imports the issue still persists |
Is your sample repo up-to-date? Would love to have a look at this issue. I'm wondering if your css modules should be passed as globals? something like: // bundler
const { code } = await bundleMDX(source, {
cwd: directory,
globals: {
'form-with-styles': 'FormWithStyles'
}
});
//display
import {getMDXComponent} from 'mdx-bundler/client'
import FormWithStyles from './form-with-styles'
const Component = getMDXComponent(code, {FormWithStyles})
//mdx
import FormWithStyles from 'form-with-styles'
# Content
<FormWithStyles /> This would exclude the css and component from the bundle and let you drop it in at runtime. Saving the need to bundle it when presumably the gatsby bundle has it already. |
Hey @Arcath I've only just seen that you replied! Apologies about that. I've just updated that branch so it is up to date with what I had for you 😁 |
@Adam-Collier this error can be solved easily. You basically cannot export Node.js modules into client-side code & it throws error if you're using a Barrel file. |
I got this working to a point. So there where 3 issues I needed to sort:
1 was easy, just renamed 2 needed the post object to supply some extra details: // bring all of the data together
const postData = {
...data,
slug,
title,
content,
name,
directory: join(root, baseDir, name),
publicDirectory: join(root, 'public', baseDir, name)
}; Then pass these to const { code } = await bundleMDX(source, {
cwd: directory,
globals: {
'next/link': '_next_link'
},
esbuildOptions: options => {
options.write = true
options.outdir = publicDirectory
return options
}
}); 3 was solved in the above code by saying const Component = useMemo(() => getMDXComponent(source, {'_next_link': Link}), [source]); That got it working, although the outputted css is not linked anywhere. Might be better to lift Looking at how you do css I don't think you'll get away from having your mdx bundles output css. |
Hey @Arcath thanks for taking the time to look into this! Ok cool, that all makes sense, I'll try and get something working with it. When it comes to outputting CSS would it make more sense to use Styled Components or some other css-in-js solution? (I was thinking of moving away from styles components anyway) |
I think I'm struggling with the same issue re: CSS modules. Setting the |
@Adam-Collier If you have any css generated by esbuild its going to output a .css file in your bundle which I don't think Next.JS will be happy with. As far as I am aware Next.JS only lets you import css in the _app.js file. I'd say your best bet is to supply any css components at run time so they are not in the bundle and thus wouldn't output any css. |
Hi @Arcath - this thread was already helpful, but I still have some trouble understanding: Lets say I want to blog about Three.js using React-Three-Fiber, example Component: The Box: import { useRef, useState } from "react";
import { useFrame } from "@react-three/fiber";
import { Box as NativeBox } from "@react-three/drei";
export default function Box(props) {
const mesh = useRef(null);
const [hovered, setHover] = useState(false);
const [active, setActive] = useState(false);
useFrame(() => (mesh.current.rotation.x = mesh.current.rotation.y += 0.01));
const color = props.color || "#720b23";
return (
<NativeBox
args={[1, 1, 1]}
{...props}
ref={mesh}
scale={active ? [6, 6, 6] : [5, 5, 5]}
onClick={() => setActive(!active)}
onPointerOver={() => setHover(true)}
onPointerOut={() => setHover(false)}
>
<meshStandardMaterial
attach="material"
color={hovered ? "#2b6c76" : color}
/>
</NativeBox>
);
} The Component: import React from "react";
import { Canvas } from "@react-three/fiber";
import Box from "src/components/labs/ripple/Box";
import { OrbitControls } from "@react-three/drei";
function AnimationCanvas({ color }) {
return (
<Canvas camera={{ position: [100, 10, 0], fov: 35 }}>
<ambientLight intensity={2} />
<pointLight position={[40, 40, 40]} />
<Box position={[10, 0, 0]} color={color} />
<Box position={[-10, 0, 0]} color={color} />
<Box position={[0, 10, 0]} color={color} />
<Box position={[0, -10, 0]} color={color} />
<OrbitControls />
</Canvas>
);
}
const Boxes = ({ color }) => {
return <AnimationCanvas color={color} />;
};
export default Boxes; In my MDX, I would write something like ---
title: "Post with some React Three Fiber"
publishedAt: "2021-07-13"
summary: "Test Summary"
description: "Test Description"
draft: "false"
tags: ["React"]
seoImage: "some link"
---
import Boxes from "../../components/Boxes"
# This should be h1
Commodo ut qui proident anim minim adipisicing irure elit
> Sit laborum est ullamco id occaecat sunt laborum ullamco.
## This should be h2
<Boxes /> So I have to add
const { code } = await bundleMDX(source, {
cwd: directory,
globals: {
'@react-three/fiber': '_react_three_fiber',
'@react-three/drei': '_react_three_drei',
'three': '_three',
},
files: {
"../../components/Boxes": "here the file content as string"
},
esbuildOptions: options => {
options.write = true
options.outdir = publicDirectory
return options
}
});
import fiber from '@react-three/fiber';
import drei from '@react-three/drei';
import THREE from 'three';
const Component = useMemo(
() =>
getMDXComponent(source, {
_react_three_fiber: fiber,
_react_three_drei: drei,
_three: THREE,
}),
[source]
); Would that be correct? I will create a repo and try around, and I will share the link a bit later - thanks in advance for taking the time |
I'm facing the same issue where I'm trying to use a component in an MDX file, which in turn imports other components and a CSS module. So: // This is the MDX File
import Arrow from './Arrow.jsx'
<Arrow /> // This is the component file
import { motion } from "framer-motion"
import styles from "./Arrow.module.css"
const Arrow = () => {
return (
<div className={styles.arrow}>➔</div>
)
}
export default Arrow Did anyone find a definitive solution to this use case? Or is it best to use CSS in JS instead of CSS modules here? Would prefer to use modules since that's what I'm using everywhere else on my blog... |
In my case it throw
// index.mdx
import Topography from './Topography';
<Topography /> export const ROOT = process.cwd();
const getCompiledMDX = async (content: string) => {
// ...
try {
return await bundleMDX({
source: content,
xdmOptions(options) {
options.remarkPlugins = [
...(options.remarkPlugins ?? []),
...remarkPlugins,
];
options.rehypePlugins = [
...(options.rehypePlugins ?? []),
...rehypePlugins,
];
return options;
},
cwd: POSTS_PATH,
});
} catch (error: any) {
throw new Error(error);
}
// ...
} |
@FradSer same error here. Don't really know what to do about it. |
@melosomelo same error and I gave up. |
@FradSer, I opened an issue about it. I managed to make it work through some esbuild configurations, but idk if it's a very solid solution. Waiting on a response. |
Hi guys, thank you for the great project! I'm currently trying to get mdx-bundler set up with Next.js and I'm running into some issues when it comes to importing components. The imported component in the MDX file is fine but if that import has it's own imports it throws an error. Is there a way to tacke this? I'll show you what I have below
mdx-bundler
version: 4.0.1node
version: v14.16.0npm
version: 6.14.11So I have some code to prepare and get the components like in @Arcath's post https://www.arcath.net/2021/03/mdx-bundler
which allows me to import the component in postdir > componentsdir
but say I am trying to import this form component
An error is thrown because the Button component is trying to be imported from my src/components directory and the styles css module is being from that same directory
This is a screenshot of the error:
and the repo can be found here:
https://github.com/Adam-Collier/portfolio-site/tree/render_mdx
(I am currently migrating over from Gatsby so everything is a bit of a mess atm but it should be easy enough to navigate to a blog page that errors)
I appreciate any guidance you have on this and I hope you can help
The text was updated successfully, but these errors were encountered: