summaryrefslogtreecommitdiffstats
path: root/pkgs/simple/cgit-about-filter
diff options
context:
space:
mode:
Diffstat (limited to 'pkgs/simple/cgit-about-filter')
-rw-r--r--pkgs/simple/cgit-about-filter/cgit-about-filter.lua93
-rw-r--r--pkgs/simple/cgit-about-filter/default.nix5
2 files changed, 98 insertions, 0 deletions
diff --git a/pkgs/simple/cgit-about-filter/cgit-about-filter.lua b/pkgs/simple/cgit-about-filter/cgit-about-filter.lua
new file mode 100644
index 0000000..1b37643
--- /dev/null
+++ b/pkgs/simple/cgit-about-filter/cgit-about-filter.lua
@@ -0,0 +1,93 @@
+local function resolve(base, relative)
+ if relative:sub(1, 1) == "/" then
+ return relative
+ end
+
+ local combined = base .. "/" .. relative
+
+ local segments = {}
+ for segment in combined:gmatch("[^/]+") do
+ if segment == ".." then
+ if #segments > 0 and segments[#segments] ~= ".." then
+ table.remove(segments)
+ else
+ table.insert(segments, "..")
+ end
+ elseif segment ~= "." and segment ~= "" then
+ table.insert(segments, segment)
+ end
+ end
+
+ local prefix = (base:sub(1, 1) == "/" or relative:sub(1, 1) == "/") and "/" or ""
+ return prefix .. table.concat(segments, "/")
+end
+
+local buffer = ""
+local should_render = true
+local current_dir = "" -- Stores the directory prefix of the file being processed
+local current_file = ""
+
+function filter_open(...)
+ local args = {...}
+ current_file = args[1] or ""
+
+ if current_file == "" then
+ current_file = "README.md"
+ end
+
+ -- Strict route enforcement: Allow README.md OR any file starting with docs/ and ending in .md
+ if current_file == "README.md" or (current_file:sub(1, 5) == "docs/" and current_file:sub(-3) == ".md") then
+ should_render = true
+
+ -- Extract directory context (e.g., "docs/ops.md" -> "docs/")
+ -- If it's the root README.md, current_dir stays an empty string ""
+ if current_file ~= "README.md" then
+ current_dir = current_file:match("(.*/)") or ""
+ else
+ current_dir = ""
+ end
+ else
+ should_render = false
+ end
+
+ buffer = ""
+end
+
+function filter_write(str)
+ if should_render then
+ buffer = buffer .. str
+ end
+end
+
+function filter_close()
+ if not should_render then
+ io.write("<p><em>Error: Access Denied. Only README.md and documentation markdown files are viewable here.</em></p>")
+ return
+ end
+
+ local repo = os.getenv("CGIT_REPO_URL") or ""
+
+ local processed = buffer:gsub("%[([^%]]+)%]%(([^:)]+)%)", function(text, path)
+ -- Ignore protocols (http, https, etc.), absolute paths (/), and anchors (#)
+ if path:sub(1, 1) == "/" or path:sub(1, 1) == "#" or path:match("^%w+:") then
+ return string.format("[%s](%s)", text, path)
+ end
+
+ path = resolve(current_dir, path)
+
+ if path:sub(-3) == ".md" then
+ return string.format("[%s](/%s/about/%s)", text, repo, path)
+ else
+ return string.format("[%s](/%s/tree/%s)", text, repo, path)
+ end
+ end)
+
+ -- Pipe everything into md2html
+ local handle = io.popen("@md2html@ --github", "w")
+ if handle then
+ handle:write(processed)
+ handle:close()
+ else
+ io.write("<p>Error: Could not execute md2html.</p>")
+ end
+end
diff --git a/pkgs/simple/cgit-about-filter/default.nix b/pkgs/simple/cgit-about-filter/default.nix
new file mode 100644
index 0000000..215a44e
--- /dev/null
+++ b/pkgs/simple/cgit-about-filter/default.nix
@@ -0,0 +1,5 @@
+{ lib, md4c, replaceVars }:
+
+replaceVars ./cgit-about-filter.lua {
+ md2html = lib.getExe md4c;
+}