我正在尝试通过
.mdx
文件将自定义组件传递到我的 mdx-components.js
帖子,但自定义组件未呈现。
这是我根据
NextJS 文档制作的
mdx-components.js
文件:
// my-blog/mdx-components.js
import UnderlineHoverLink from "./app/_components/Links/UnderlineHoverLink";
export function useMDXComponents(components) {
return {
a: ({ href, children }) => (
<UnderlineHoverLink href={href}>{children}</UnderlineHoverLink>
),
...components,
};
}
这是我渲染
.mdx
文件的页面:
// my-blog/app/(routes)/posts/[slug]/page.js:
import { getPostBySlug } from "@/app/_lib/mdx";
const getPageContent = async (slug) => {
const { meta, content } = await getPostBySlug(slug);
return { meta, content };
};
export async function generateMetadata({ params }) {
const { meta } = await getPageContent(params.slug);
return { title: meta.title };
}
const Page = async ({ params }) => {
console.log(params);
const { content } = await getPageContent(params.slug);
return content;
};
export default Page;
这是我从文件系统获取内容的地方,其中
.mdx
文件是:
// my-blog/app/_lib/mdx/index.js
import fs from "fs";
import path from "path";
import { compileMDX } from "next-mdx-remote/rsc";
const rootDirectory = path.join(process.cwd(), "content/posts");
export const getPostBySlug = async (slug) => {
const realSlug = slug.replace(/\.mdx$/, "");
const filePath = path.join(rootDirectory, `${realSlug}.mdx`);
const fileContent = fs.readFileSync(filePath, { encoding: "utf8" });
const { frontmatter, content } = await compileMDX({
source: fileContent,
options: { parseFrontmatter: true },
});
return { meta: { ...frontmatter, slug: realSlug }, content };
};
根据NextJS文档:
在 mdx-components.tsx 中添加样式和组件将影响应用程序中的所有 MDX 文件。
我一直在密切关注文档,但我似乎无法渲染我的自定义链接。谁能帮我解决问题吗?
我检查了浏览器中的输出 html,看看自定义链接是否正在呈现,但其他样式是否覆盖了它。但看起来自定义链接未呈现。我尝试删除
mdx-components.js
文件以查看它是否根本没有被加载,但是 NextJS 抛出了一个错误,所以我知道该文件正在加载。
我最终找到了解决方案。当使用compileMDX函数编译mdx markdown时,您可以将组件作为参数传递。现在我的文件看起来像这样:
// my-blog/app/_lib/mdx/index.js
import fs from "fs";
import path from "path";
import { compileMDX } from "next-mdx-remote/rsc";
import { useMDXComponents } from "@/mdx-components";
const rootDirectory = path.join(process.cwd(), "content/posts");
export const getPostBySlug = async (slug) => {
const realSlug = slug.replace(/\.mdx$/, "");
const filePath = path.join(rootDirectory, `${realSlug}.mdx`);
const fileContent = fs.readFileSync(filePath, { encoding: "utf8" });
const { frontmatter, content } = await compileMDX({
source: fileContent,
components: useMDXComponents(),
options: { parseFrontmatter: true },
});
return { meta: { ...frontmatter, slug: realSlug }, content };
};