hugo-cms.nvim lives entirely inside neovim. The first few steps from an empty directory to your first post, I walk through here from the start. If you’ve never worked with Hugo, the Hugo intro is the place to begin. Here I’m assuming hugo is installed and you have a rough idea of what a Hugo site is.
Leader Keys, Up Front
The plugin doesn’t set any keymaps itself. Every command runs through :Hugo …, and you can bind them to whatever keys you like. The README example uses <leader>h…, which I’ll assume throughout: <leader>hn for :Hugo new, <leader>ho for :Hugo open, and so on. Which letters you pick is up to you.
Create the Hugo Site
A fresh site starts with hugo new site <name>. That gives you the standard directory layout and a hugo.toml (or hugo.yaml if you append --format yaml). Add a theme, usually as a Git submodule:
git submodule add --depth=1 https://github.com/<theme-repo> themes/<name>
Activate the theme in the config:
theme: <name>
Run git init and make a first commit, so you have something to roll back to. If your config is split under config/_default/ instead of sitting at the project root, hugo-cms.nvim picks that up automatically.
Register the Site
In the editor: :Hugo site register (<leader>hS). Two prompts:
Site path: ~/sites/myblog
Display name: My Blog
The first registered site becomes the active one. :Hugo site switch toggles between registered sites, :Hugo site unregister removes one without touching anything on disk.
:Hugo site with no argument opens a picker over all subcommands, in case you don’t want to memorise them.
The list of registered sites and all path patterns are stored at $XDG_DATA_HOME/nvim/hugo-cms/sites.json (typically ~/.local/share/nvim/hugo-cms/sites.json). Back that file up if you want to carry the setup to another machine.
A Theme-Neutral Archetype
Archetypes are the templates for new content, they live at archetypes/<name>/index.md (or <name>.md for single-file content). hugo-cms.nvim is archetype-driven, it only writes into front-matter fields that already exist in the archetype. Theme-specific fields belong in the archetype, not in plugin options.
A solid blog-post archetype as a bundle (archetypes/post/index.md):
---
title: "{{ replace .File.ContentBaseName "-" " " | title }}"
date: "{{ .Date }}"
draft: true
description: ""
slug: ""
tags: []
categories: []
cover:
image: ""
alt: ""
relative: true
caption: ""
hidden: false
---
description is the meta description for search engines and social previews, often forgotten. The empty string is a reminder, the plugin leaves it alone otherwise. slug is the URL override, empty in the default archetype, set per language once you translate. cover.alt is accessibility and SEO in one, screen readers and search engines read the alt text. The plugin only prompts for alt text when the field already exists in the front matter, which is why it belongs in the archetype. tags and categories as empty lists so the front matter parses cleanly before you ever run :Hugo tags or :Hugo categories.
If you prefer single-file posts (a plain .md without a bundle), put the analogue in archetypes/post.md. hugo-cms.nvim figures out from the archetype’s shape whether new posts come out as single files or bundles.
Write the First Post
Hugo itself has the command hugo new content/<path>/<slug>.md, which creates a file from the matching archetype with title and date filled in. The plugin builds on top of that, runs the path through a picker and remembers your path pattern.
With the site active: :Hugo new (<leader>hn). Three prompts:
Archetype: post
Title: My first post
Path: blog/{year}/my-first-post
For the archetype, the plugin shows a picker over everything in archetypes/. Picking post runs the post archetype.
Title is free text. The slug is derived from it, with diacritics transliterated (Über mich → ueber-mich). The title field in the front matter keeps whatever you typed.
Path is prefilled from the archetype’s path pattern plus the derived slug. You can still tweak the slug before hitting enter.
The first time you use a given archetype, the plugin asks for its path pattern. The pattern decides where posts from that archetype land. Examples:
| Pattern | Result for title “Hello” |
|---|---|
posts/{year}/ | content/posts/2026/hello.md |
blog/{year}/{month}/ | content/blog/2026/04/hello.md |
notes/ | content/notes/hello.md (flat) |
Available placeholders are {year}, {month} and {day}, all zero-padded. The pattern is stored per site and per archetype. :Hugo site pattern lets you change it later if you decide to restructure.
After confirming, a bundle archetype gives you a content/blog/2026/my-first-post/ folder with index.md, the front matter is filled with your title and the current date, the body is empty. You can start writing.
What the plugin doesn’t do: the actual Markdown writing. That’s an editor job like any other .md file. If you want inline rendering or live preview in the buffer, take a look at markview.nvim.
Where Things Go From Here
That gets you a site registered with hugo-cms.nvim and the first post in place. How to find posts again, manage tags and categories, and toggle the draft flag is the topic of the post on managing content.