This note explains the details of publishing notes in SiYuan using Hugo and the Hugo Bootstrap Theme.

Notes in SiYuan can be exported to Markdown. However, the exported markdown files need to be tweaked in various ways to enable publishing them with Hugo. The tweaks are applied through a set of Python scripts that

  • Create _index.md​ files as needed by Hugo
  • Fix any inter-note links in the exported markdown files. SiYuan typically does not export such links to markdown, even if they exist within SiYuan
  • Add a ‘Backlinks’ section to each note that is referenced by other notes. SiYuan does not include backlinks in the exported markdown
  • Copy any image files in the notes to the appropriate location for publishing with Hugo

SiYuan should be configure as follows: Go to Settings > Export and

  • Enable “Export markdown with YAML front-matter”
  • Set Ref to “Anchor text with block URI”

To use the scripts, clone the repository into a local folder. Within that folder, create a folder named notes/​ into which the .zip file produced by SiYuan markdown export should be copied and its contents extracted. Find the authorization token in Siyuan > Settings > About and use it to replace the string “setmefillmechangeme” in siyuan-export.sh​. Then run the siyuan-export.sh​ script that calls the other Python scripts in the repository. After all scripts are run, the contents of the notes/​ folder can be copied to the desired Hugo site folders.

WARNING: The scripts are poorly written. I am not a programmer and I copy/paste’d code from StackOverflow and various tutorials until it did what I needed and then I stopped working on it. You will need to deeply understand what the scripts do, and how they work, in order to use them. Hopefully, the following documentation will help.

Creating _index.md files

Relevant script: create-index-files.py

Hugo is pretty special in the sense that it needs files named index.md​and _index.md​ for organizing content. See more details here. Briefly, if the markdown notes exported by SiYuan have a structure where both a folder named foo/​ exists alongside a file named foo.md​, then the way I am publishing notes with Hugo requires the foo.md​to be moved and renamed to foo/_index.md​.​​

index-files

Additionally, for the way I am publishing the notes, the top level file in the notes directory needs to be created/renamed to _index.md​.

All of this is accomplished by the create-index-files.py script as follows

  • The script goes through the directory tree of markdown notes exported by SiYuan. Every time it sees a folder foo/​ in the same directory as the file foo.md​, it moves foo.md​ to foo/_index.md
  • It opens the top level _index.md​ file and adds to it a bunch of frontmatter variables needed for publishing the notes via the Hugo Bootstrap Theme, creating a menu item in the navigation bar at the top of the site, etc.

Relevant script: process-siyuan-links.py

In SiYuan, if your notes have links to other notes, or paragraphs/headings etc. in other notes ( ‘block refs’ in SiYuan terminology), these inter-note links are not exported properly by SiYuan markdown export. So the exported markdown files will contain text like [Link text](siyuan://blocks/block-id)​ instead of text like [Link text](/path/to/file.md)​. (Note: This requires SiYuan Settings > Export > Ref to be configure to ‘Anchor text with block URL’)

So the process-siyuan-links.py script figures out how to get the desired links to markdown files based on the block ids in the exported link text. It works as follows:

  • For each markdown file in the exported notes, it detects instances of text that matches the pattern [Link text](siyuan://blocks/block-id)

  • It then uses the SiYuan JSON API to look up the human readable path (hpath) of the file corresponding to (or containing) the block-id in the link.

    • If the block-id corresponds to an entire file (In SiYuan terminology, the block ref is to a block of type doc​), the script replaces the matched pattern text with a Hugo formatted ref link to the corresponding file.
    • If the block-id corresponds to a block inside some doc, e.g. to some specific heading or paragraph or list item etc. inside the doc, then the script replaces the matched pattern text with a Hugo formatted ref link to the specific heading, paragraph, or list item etc. in the corresponding file. To do so, it also creates an HTML anchor text like <a name="block-id"></a>​ at the appropriate place in the target file.
  • While doing the above, the script accounts for the fact that some markdown files in the SiYuan markdown export may have been renamed/moved to _index.md​ by the create-index-files.py script.

The process-siyuan-links.py requires that SiYuan is running on the computer it is executing on. This enables it to access the SiYuan JSON API.

Relevant script: add-backlinks.py

This script appends a ‘Backlinks’ section to each markdown file. The section contains hyperlinks to all the documents that reference it (i.e. have a link to it).

  • This script takes as input a folder of markdown files which contain links between them (i.e. the output of the process-siyuan-links.py script mentioned above).
  • It then opens each markdown file, and creates a record (in a sqlite database table) of all the outgoing links to other markdown files.
  • Then, it goes through the database table, opens each file which has at least one backlink to it, and appends a ‘Backlinks’ section containing a list of hyperlinks to the documents that link to it.

Copy images

Relevant script: copy-images.py

If a note in SiYuan contains images, then SiYuan markdown export places the image files in assets​ folders in the exported directory structure. This script copies all relevant image files in all relevant assets​ folders to a specified destination folder. The intention is that this destination folder is then placed at the appropriate location in the HUGO site sources.

The script works as follows:

  • Open each markdown file and find all instances of a markdown image link pattern: ![Optional Alt text](path/to/image.ext "Optional title")
  • If the referenced image file path/to/image.ext​ exists, the script then copies the image file to the specified destination folder
  • The script also adjusts the file path in the markdown image link to point to the correct folder within the Hugo site sources