Skip to content

Commit

Permalink
feat: per-page components (#1429)
Browse files Browse the repository at this point in the history
Co-authored-by: nobkd <44443899+nobkd@users.noreply.github.com>
Co-authored-by: Sébastien Chopin <seb@nuxtjs.com>
Co-authored-by: nobkd <44443899+nobkd@users.noreply.github.com>
  • Loading branch information
3 people committed Aug 16, 2022
1 parent 5d3ffee commit e95d512
Show file tree
Hide file tree
Showing 8 changed files with 77 additions and 4 deletions.
26 changes: 26 additions & 0 deletions docs/content/4.api/1.components/2.content-renderer.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,9 @@ Other types will currently be passed to default slot via `v-slot="{ data }"` or
- `excerpt`{lang=ts}: Whether or not to render the excerpt.
- Type: `Boolean`{lang=ts}
- Default: `false`{lang=ts}
- `components`{lang=ts}: The map of custom components to use for rendering. This prop will pass to markdown renderer and will not affect other file types.
- Type: `Object`{lang=ts}
- Default: `{}`{lang=ts}

## Slots

Expand Down Expand Up @@ -57,3 +60,26 @@ const { data } = await useAsyncData('page-data', () => queryContent('/hello').fi
</main>
</template>
```

::alert
Note that when you use default slot and `<ContentRendererMarkdown>` in your template you need to pass `components` to `<ContentRendererMarkdown>`.

```html [pages/[...slug].vue]
<script setup lang="ts">
const { data } = await useAsyncData('page-data', () => queryContent('/hello').findOne())
const components = {
p: 'CustomParagraph'
}
</script>

<template>
<main>
<ContentRenderer :value="data">
<h1>{{ data.title }}</h1>
<ContentRendererMarkdown :value="data" :components="components" />
</ContentRenderer>
</main>
</template>
```
::
15 changes: 12 additions & 3 deletions src/runtime/components/ContentRendererMarkdown.vue
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,13 @@ export default defineComponent({
tag: {
type: String,
default: 'div'
},
/**
* The map of custom components to use for rendering.
*/
components: {
type: Object,
default: () => ({})
}
},
async setup (props) {
Expand All @@ -53,14 +60,15 @@ export default defineComponent({
await resolveContentComponents(props.value.body, {
tags: {
...tags,
...props.value?.tags || {}
...props.value?._components || {},
...props.components
}
})
return { tags }
},
render (ctx) {
const { tags, tag, value } = ctx
const { tags, tag, value, components } = ctx
if (!value) {
return null
Expand All @@ -75,7 +83,8 @@ export default defineComponent({
...(value as ParsedContentMeta),
tags: {
...tags,
...value?.tags || {}
...value?._components || {},
...components
}
}
Expand Down
11 changes: 11 additions & 0 deletions test/__snapshots__/basic.test.ts.snap
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,17 @@ exports[`Basic usage > Get contents index > basic-index-body 1`] = `
"tag": "h1",
"type": "element",
},
{
"children": [
{
"type": "text",
"value": "Hello World",
},
],
"props": {},
"tag": "p",
"type": "element",
},
],
"toc": {
"depth": 2,
Expand Down
10 changes: 10 additions & 0 deletions test/features/renderer-markdown.ts
Original file line number Diff line number Diff line change
Expand Up @@ -52,5 +52,15 @@ export const testMarkdownRenderer = () => {
expect(rendered).toContain('This is an alert for success')
expect(rendered).toContain('This is an alert for danger')
})

test('per-page custom component', async () => {
const html = await $fetch('/_partial/custom-paragraph')
expect(html).contains('[Paragraph]')
})

test('renderer custom component', async () => {
const html = await $fetch('/features/custom-paragraph')
expect(html).contains('[Paragraph]')
})
})
}
5 changes: 5 additions & 0 deletions test/fixtures/basic/components/content/CustomProseP.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<template>
<p>
[Paragraph] <slot />
</p>
</template>
6 changes: 6 additions & 0 deletions test/fixtures/basic/content/_partial/custom-paragraph.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
_components:
p : CustomProseP
---

This is a paragraph.
5 changes: 4 additions & 1 deletion test/fixtures/basic/content/index.md
Original file line number Diff line number Diff line change
@@ -1 +1,4 @@
# Index
# Index


Hello World
3 changes: 3 additions & 0 deletions test/fixtures/basic/pages/features/custom-paragraph.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<template>
<ContentDoc :path="'/'" :components="{ p: 'CustomProseP' }" />
</template>

0 comments on commit e95d512

Please sign in to comment.