wiki
wiki copied to clipboard
feat: [nav] tag to render a list of child pages
This PR introduces a [nav] tag that can be added when editing content pages in any of the editors (raw html, visual, markdown).
When the page is rendered, the [nav] tag is replaced with a dynamic list of all the child pages of the current page.

This is a feature that's been on my wish list for the wiki and has been requested before by other members of the community, https://js.wiki/feedback/p/sub-pages-list. We love the wiki at my company, so a couple of us had a look at what we could do to implement this.
The feature works by analysing the page HTML contents, to check if an element or text node contains the [nav] string.
If the strings exists, we start by finding the page id using the path of the current page. We have to do a string match on the path of the pages from the results to get the id. Then, using that page id, we run another query to get all the child pages of the parent page matching that id.
Unfortunately this does require two graphql queries, but these are the same queries that the sidenav runs when clicking through the folders, so I'm guessing this is the only/most efficient way of doing it.
From there, we replace the [nav] tag with the page list HTML.
I'd love some feedback on the PR. The functionality is very basic for now. In the future I'd like to add things like optionally rendering children of children, or rendering a page list of a different parent page by specifying the path in the tag, but for version 1 I'd like to keep it simple, what do you think?
The [nav] tag works a treat, but there is a brief delay after loading the page while the graphql queries run, so you might see [nav] for a split second before the page list is rendered. Could this code be moved somewhere else, other than page.vue to avoid this?
Is page.vue in the themes folder the best place for this, or should it be moved somewhere else?
I'm not too fond of the way it's implemented. You shouldn't be analyzing the HTML content directly. This goes against the whole principle of using Vue. [nav] should instead be a Vue component transformed at render time to something like <child-nav>, which will get picked up automatically by Vue and replaced with the ChildNav.vue component on the browser-side.
You're also referencing a graphQL variable which is incorrect. You should be using this.$apollo instead which is available inside any component.
Thanks for the feedback. It's my first time working with Vue, so I suspected this probably wasn't the right approach. I'll rework this based on your comments.
We would love to have access to this feature ! Nice work @jlucki, can't wait to use it !
I'm struggling to get the wiki to pick up this new component. I've got child-nav.vue in /client/components
I'm importing it with Vue.component('ChildNav', () => import(/* webpackChunkName: "childNav" */ './components/child-nav.vue')) in client-app.js
In child-nav.vue I've got
<template>
<p>hello world</p>
</template>
On the page, I have added {childNav}. When the page renders, this disappears but my hello world message isn't appearing.
I've tried modifying existing components but any changes I make don't seem to be taking effect. Is there a step I'm missing for the wiki to pick up component changes? yarn dev compiles with no issues.
Hi, is there a plan, when this feature could be merged? We'd need such a feature as well :)
@blubber-bernd A proper implementation of this feature will be available in v3.
Any news on this one @jlucki @NGPixel ? I would like to see this feature in action in v2
I would love to implement this properly but I couldn't figure out how to wire up the component and couldn't find any docs/examples on how to do it either. If anyone's got some pointers in reply to this, https://github.com/requarks/wiki/pull/5613#issuecomment-1327385732, I'd be happy to take another stab.