1import lume from "lume/mod.ts";
2import date from "lume/plugins/date.ts";
3import picture from "lume/plugins/picture.ts";
4import source_maps from "lume/plugins/source_maps.ts";
5import toml from "lume/plugins/toml.ts";
6
7// URL Management
8import slugify_urls from "lume/plugins/slugify_urls.ts";
9import resolveUrls from "lume/plugins/resolve_urls.ts";
10
11// File Generation
12import feed from "lume/plugins/feed.ts";
13import metas from "lume/plugins/metas.ts";
14import robots from "lume/plugins/robots.ts";
15import sitemap from "lume/plugins/sitemap.ts";
16
17// Optimization
18import brotli from "lume/plugins/brotli.ts";
19import gzip from "lume/plugins/gzip.ts";
20import minify_html from "lume/plugins/minify_html.ts";
21import svgo from "lume/plugins/svgo.ts";
22import transform_images from "lume/plugins/transform_images.ts";
23
24// Markdown-it plugins
25import { BiDirectionalLinks } from "@nolebase/markdown-it-bi-directional-links";
26import { default as mdItObsidianCallouts } from "markdown-it-obsidian-callouts";
27
28// Additional external plugins
29import toc from "https://deno.land/x/lume_markdown_plugins@v0.8.0/toc.ts";
30import anchor from "npm:markdown-it-anchor";
31import slugify from "npm:@sindresorhus/slugify";
32
33// CSS
34// // Base dependencies
35import tailwindcss from "lume/plugins/tailwindcss.ts";
36// // Fonts
37import googleFonts from "lume/plugins/google_fonts.ts";
38// // Optimization
39import lightningcss from "lume/plugins/lightningcss.ts";
40
41// Custom Plugins
42import validateHTML from "./plugins/validateHTML.ts";
43import openInEditor from "./plugins/openInEditor.ts";
44
45// Disabled Plugins:
46// import nav from "lume/plugins/nav.ts";
47// import og_images from "lume/plugins/og_images.ts";
48// import pagefind from "lume/plugins/pagefind.ts";
49// import purgecss from "lume/plugins/purgecss.ts";
50// import relations from "lume/plugins/relations.ts";
51// import sri from "lume/plugins/sri.ts";
52
53// To Add:
54// https://deno.land/x/lume_markdown_plugins@v0.8.0 (footnotes plugins)
55// https://deno.land/x/lume_shiki@0.0.16
56
57const site = lume({
58 src: "./src",
59 location: new URL("https://pyrox.dev"),
60}, {
61 markdown: {
62 plugins: [
63 [BiDirectionalLinks, {
64 dir: Deno.cwd() + "/src/",
65 stillRenderNoMatched: false,
66 }],
67 mdItObsidianCallouts,
68 [anchor, {
69 permalink: anchor.permalink.headerLink(),
70 slugify: (s: string) => slugify(s),
71 }],
72 ],
73 },
74});
75
76// Copy Static Files
77site.add(".css");
78site.add("static/.well-known", ".well-known");
79site.add(".woff2");
80// Tailwind CSS
81site.use(tailwindcss());
82
83// Fonts
84site.use(
85 googleFonts({
86 subsets: ["latin", "latin-ext"],
87 folder: "/static/fonts/",
88 cssFile: "/static/fonts.css",
89 fonts:
90 "https://fonts.googleapis.com/css2?family=IBM+Plex+Serif:ital,wght@0,300;0,400;0,500;0,600;0,700;1,300;1,400;1,500;1,600;1,700&family=Inter:ital,opsz,wght@0,14..32,100..900;1,14..32,100..900",
91 }),
92);
93
94site.use(metas());
95site.use(picture());
96site.use(transform_images());
97// site.use(relations());
98site.use(sitemap());
99site.use(slugify_urls());
100site.use(svgo());
101site.use(toml());
102site.use(
103 date({
104 formats: {
105 SHORT_DATE: "yyyy-MM-dd",
106 POST_DATE: "dd MMM, yyyy",
107 },
108 }),
109);
110site.use(toc({
111 anchor: false,
112}));
113site.use(resolveUrls());
114
115// RSS/JSON Feed Generation
116site.use(
117 feed({
118 output: ["/blog.rss", "/blog.json"],
119 query: "category=blog",
120 info: {
121 title: "dish blog",
122 description: "dish's thoughts on many things",
123 published: new Date(),
124 lang: "en",
125 generator: true,
126 authorName: "dish",
127 authorUrl: "https://blog.pyrox.dev",
128 },
129 items: {
130 title: "=title",
131 description: "=summary",
132 published: "=published",
133 updated: "=updated",
134 content: "$.e-content",
135 lang: "=lang",
136 image: "=banner",
137 authorName: "=author.name",
138 authorUrl: "=author.url",
139 },
140 }),
141);
142
143// CSS postprocessing
144// site.use(purgecss());
145site.use(lightningcss({
146 options: {
147 minify: true,
148 },
149}));
150
151// Source Map Generation
152// Applies to CSS and JS
153site.use(source_maps());
154
155site.use(validateHTML());
156
157// Minify HTML Output
158site.use(minify_html({
159 options: {
160 do_not_minify_doctype: true,
161 keep_closing_tags: false,
162 keep_html_and_head_opening_tags: true,
163 keep_spaces_between_attributes: true,
164 ensure_spec_compliant_unquoted_attribute_values: true,
165 keep_comments: false,
166 },
167}));
168
169// robots.txt generation
170site.use(
171 robots({
172 disallow: [
173 "AI2Bot",
174 "Amazonbot",
175 "Applebot-Extended",
176 "Bytespider",
177 "ChatGPT-User",
178 "ClaudeBot",
179 "Diffbot",
180 "DuckAssistBot",
181 "FacebookBot",
182 "GPTBot",
183 "Google-Extended",
184 "Meta-ExternalAgent",
185 "Meta-ExternalFetcher",
186 "OAI-SearchBot",
187 "Operator",
188 "PanguBot",
189 "PerplexityBot",
190 "SemrushBot",
191 "SemrushBot-OCOB",
192 "Timpibot",
193 "Webzio-Extended",
194 "YouBot",
195 "cohere-training-data-crawler",
196 "omgili",
197 "t3versions",
198 ],
199 }),
200);
201
202// Compress everything with Brotli/Gzip
203site.use(
204 brotli({
205 quality: 11,
206 extensions: [
207 ".html",
208 ".css",
209 ".js",
210 ".mjs",
211 ".svg",
212 ".json",
213 ".xml",
214 ".txt",
215 ".rss",
216 ".map",
217 ],
218 }),
219);
220site.use(
221 gzip({
222 extensions: [
223 ".html",
224 ".css",
225 ".js",
226 ".mjs",
227 ".svg",
228 ".json",
229 ".xml",
230 ".txt",
231 ".rss",
232 ".map",
233 ],
234 }),
235);
236
237// Open in Editor in Dev mode
238site.data("production", Deno.env.get("PRODUCTION") == "true");
239if (Deno.env.get("PRODUCTION") == "false") {
240 site.use(openInEditor());
241 site.add("static/scripts/open-in-editor.js");
242}
243
244// Get current commit as a version number
245// Taken from https://github.com/pixeldesu/pixelde.su/blob/main/_config.ts
246const commitCmd = new Deno.Command("git", { args: ["rev-parse", "HEAD"] });
247const { stdout } = await commitCmd.output();
248const commitHash = new TextDecoder().decode(stdout);
249site.data("commit", commitHash);
250
251export default site;