Access to Token Stream in Markdown Rendering

hi,

I’m using shortcodes to augment my articles. I’d like to improve the SEO by having HTML render on the server side instead of having to render it using Javascript. Here is an example of what I’m attempting to do in Zola/Rust instead of Javascript

Obviously I can’t render a chart on the server, but for simpler components such as a hero or something else?

I’d like the body of the shortcode to be available in Zola/Rust and then I’d like to apply an HTML template to it accordingly. Is this possible with the current Zola APIs?

Thank you

Obviously I can’t render a chart on the server

Hey, I’m not sure why a tree map couldn’t be rendered using shortcodes? Is it because you have to receive user-supplied information dynamically? Because otherwise you can probably do it. Is it because of recursion? Anyways, maybe with a little clarification that could be done.

(btw there’s no server in Zola, everything is compiled in advance.)

I’d like the body of the shortcode to be available in Zola/Rust and then I’d like to apply an HTML

This part I’m a little unclear about. You can put html in a shortcode body already. So do you want to apple an html template to html? Or maybe I misunderstood.

hi @spence , thank you for reading. Let me expand on my original post

Today, I have implemented echarts using a shortcodes. However the content of that shortcode is a Markdown List. I then take that value an run it through markdownit. Which works well enough for Javascript. However, I’d like to instead render HTML from the shortcode

( Gist with files to reference for the rest of the post )

  • Input: chart__shortcode.md.txt
  • HTML Output: Desired Output.html

I’d like this feature to improve SEO compatibility with more search engines. How can I modify the shortcode token stream to output HTML instead of just the body(Current Output.html) of the shortcode?

I’m still a little confused, but let’s see if I understand you correctly and you tell me where I’m wrong.

The first thing is going from markdown → html in Zola. If you’re just looking to take markdown and produce html using zola there is a filter to do that called markdown (docs). For example

{% set h1 = "# This is an h1 header in markdown" %}
{{ h1 | markdown }}

Will produce the literal text

<h1 id="this-is-an-h1-header-in-markdown">This is an h1 header in markdown</h1>

(and then if you don’t want the just literal html as literal text, but rather rendered html then you can pipe it to safe, e.g. {{ h1 | markdown | safe }})

The second thing is about your example. I’m a little confused by it. Based on its title, chart__shortcode.md.txt looks like it’s supposed to be the shortcode itself, but the syntax is how you’re supposed to call a shortcode from your markdown, i.e. you should be using syntax like that from index.md.

It may be helpful to take a look at the part of the Zola docs where it discusses calling a shortcode with a body argument. Here is the relevant part of the documentation for that.

With that said, I think this is how I would do what I think you’re trying to do.

In your index.md:

# Example Title

I made this escharts thing. This is how it looks:

{% chart__tree_map(name='first-map', min_height=200) %}
- Root
  - Backend Framework
    - Django
    - Rocket.rs
  - Frontend Framework
    - VueJS
    - ReactJS
{% end %}

Then you would have another file called chart__tree_map.html, located at templates/shortcodes/chart__tree_map.html as follows:

<p>This is a demo of accepting markdown as a shortcode body argument and rendering it as html</p>

{% set html = body | markdown %}

<p>The literal html text is as follows:</p>

{{ html }}

<p>And the text renders as follows:</p>

{{ html | safe }}

The third and final thing is that in your example, in Desired Output.html, you don’t just render a direct translation but you also modified the output to have an id that didn’t exist in your input markdown, e.g. <ul id="{{name}}-template">.

You can still do this in the way that I wrote the shortcode above, but you will have to manually do some string processing using some of the other filters to achieve this. Probably split docs, join, and regex_replace are your best friends for this.

I hope that’s helpful!

hi @spence,

Sorry for the delay.

Yeah, what you’ve laid out is exactly what I’m doing, however I’d like to have more control over the markdown filter. For example, I’d like to specify to the markedown filter that I’d like to render a <dl> rather than a <ul> type of list. Is that type of control possible?

The markdown filter is going to act a certain way and that can’t be controlled by at the filter level.

However if you are able to access the html string of the markdown, like how I wrote earlier, then regex replace <ul for <dl should be all you need. For any other elements just apply the same logic.