From 23aa8acc55402d0a53fc5d14e0d2563a721f0eb0 Mon Sep 17 00:00:00 2001 From: Barrett Ruth <62671086+barrettruth@users.noreply.github.com> Date: Thu, 5 Mar 2026 09:32:33 -0500 Subject: [PATCH] feat: add `plantuml` preset (#45) Problem: PlantUML (`.puml`) diagrams have no built-in preview support, and Neovim lacks filetype detection for PlantUML files. Solution: Add a `plantuml` preset that compiles to SVG via `plantuml -tsvg`, with an error parser for `Error line N` diagnostics. Register `.puml` and `.pu` extensions via `vim.filetype.add` when the preset is configured. Add `plantuml` to the nix dev shell. --- flake.nix | 1 + lua/preview/init.lua | 6 ++++++ lua/preview/presets.lua | 31 +++++++++++++++++++++++++++++++ 3 files changed, 38 insertions(+) diff --git a/flake.nix b/flake.nix index 91a0ab2..4ae4479 100644 --- a/flake.nix +++ b/flake.nix @@ -32,6 +32,7 @@ pkgs.stylua pkgs.selene pkgs.lua-language-server + pkgs.plantuml ]; }; }); diff --git a/lua/preview/init.lua b/lua/preview/init.lua index 322b893..7cb982b 100644 --- a/lua/preview/init.lua +++ b/lua/preview/init.lua @@ -105,6 +105,12 @@ function M.setup(opts) vim.validate(prefix .. '.detach', provider.detach, 'boolean', true) end + if providers['plantuml'] then + vim.filetype.add({ + extension = { puml = 'plantuml', pu = 'plantuml' }, + }) + end + config = vim.tbl_deep_extend('force', default_config, { debug = debug, providers = providers, diff --git a/lua/preview/presets.lua b/lua/preview/presets.lua index 3591a21..e7c51e3 100644 --- a/lua/preview/presets.lua +++ b/lua/preview/presets.lua @@ -271,6 +271,37 @@ M.asciidoctor = { reload = true, } +---@type preview.ProviderConfig +M.plantuml = { + ft = 'plantuml', + cmd = { 'plantuml' }, + args = function(ctx) + return { '-tsvg', ctx.file } + end, + output = function(ctx) + return (ctx.file:gsub('%.puml$', '.svg')) + end, + error_parser = function(output) + local diagnostics = {} + for line in output:gmatch('[^\r\n]+') do + local lnum = line:match('^Error line (%d+) in file:') + if lnum then + table.insert(diagnostics, { + lnum = tonumber(lnum) - 1, + col = 0, + message = line, + severity = vim.diagnostic.severity.ERROR, + }) + end + end + return diagnostics + end, + clean = function(ctx) + return { 'rm', '-f', (ctx.file:gsub('%.puml$', '.svg')) } + end, + open = true, +} + ---@type preview.ProviderConfig M.quarto = { ft = 'quarto',