From cc933b31fd23bb06e95bf41f848a1c99353d44ae Mon Sep 17 00:00:00 2001 From: Xe Iaso Date: Fri, 25 Nov 2022 19:01:10 -0500 Subject: Start version 3 (#573) * Start version 3 * Change version to 3.0.0 in Cargo.toml * Add metadata for series * Change types for signal boosts * Add start of LaTeX resume generation at Nix time * Add start of proper author tagging for posts in JSONFeed and ldjson * Convert templates to use Maud * Add start of dynamic resume generation from dhall * Make patrons page embed thumbnails TODO: * [ ] Remove the rest of the old templates * [ ] Bring in Xeact for the share on mastodon button * [ ] Site update post Signed-off-by: Xe * fix nix builds Signed-off-by: Xe Iaso * fix dhall build Signed-off-by: Xe Iaso * fix non-flakes build Signed-off-by: Xe Iaso * make new mastodon share button Signed-off-by: Xe Iaso * remove the rest of the ructe templates that I can remove Signed-off-by: Xe Iaso * refactor blogposts to its own file Signed-off-by: Xe Iaso * move resume to be generated by nix Signed-off-by: Xe Iaso * write article Signed-off-by: Xe Iaso * blog/site-update-v3: hero image Signed-off-by: Xe Iaso * add site update series tag to site updates Signed-off-by: Xe Iaso Signed-off-by: Xe Signed-off-by: Xe Iaso --- Cargo.lock | 18 +- Cargo.toml | 4 +- ...a-tool-to-aid-forgetfulness-2022-01-12.markdown | 2 +- blog/anbernic-win600-review.markdown | 2 +- blog/fear-07-24-2018.markdown | 2 +- blog/one-day-2018-11-01.markdown | 2 +- blog/site-update-2020-07-16.markdown | 1 + blog/site-update-2021-12-19.markdown | 1 + blog/site-update-axum-2022-03-21.markdown | 1 + blog/site-update-hero-images.markdown | 1 + ...e-update-let-there-be-light-2021-03-13.markdown | 3 +- blog/site-update-mastodon-quoting.markdown | 1 + blog/site-update-patron-page-fixed.markdown | 1 + blog/site-update-rss-bandwidth-2021-01-14.markdown | 1 + blog/site-update-salary-transparency.markdown | 3 +- blog/site-update-v3.markdown | 417 +++++++++++++++ blog/sonic-frontiers.markdown | 2 +- ...the-service-is-already-down-2018-10-13.markdown | 2 +- config.dhall | 12 +- default.nix | 67 +-- dhall/Prelude.dhall | 3 + dhall/authors.dhall | 64 ++- dhall/authors/xe.dhall | 19 + dhall/latex/.gitignore | 5 + dhall/latex/resume.cls | 131 +++++ dhall/latex/resume.dhall | 110 ++++ dhall/package.dhall | 78 +++ dhall/resume.dhall | 91 +++- dhall/seriesDescriptions.dhall | 135 +++++ dhall/signalboost.dhall | 186 ++----- dhall/types/Author.dhall | 16 +- dhall/types/Config.dhall | 18 +- dhall/types/Link.dhall | 4 +- dhall/types/Person.dhall | 25 +- dhall/types/Resume.dhall | 10 +- dhall/types/SeriesDescription.dhall | 3 + dhall/types/package.dhall | 1 + flake.lock | 38 +- flake.nix | 79 ++- src/app/config.rs | 90 +++- src/app/mod.rs | 8 +- src/frontend/build.sh | 6 + src/frontend/deno.json | 8 + src/frontend/import_map.json | 8 + src/frontend/mastodon_share_button.tsx | 55 ++ src/frontend/xeact/jsx-runtime.js | 16 + src/frontend/xeact/xeact.js | 88 ++++ src/frontend/xeact/xeact.ts | 9 + src/handlers/blog.rs | 66 ++- src/handlers/gallery.rs | 28 +- src/handlers/mod.rs | 77 ++- src/handlers/talks.rs | 28 +- src/main.rs | 12 +- src/post/mod.rs | 24 +- src/post/schemaorg.rs | 14 + src/signalboost.rs | 12 +- src/tmpl/asciiart.txt | 45 ++ src/tmpl/blog.rs | 215 ++++++++ src/tmpl/mod.rs | 573 ++++++++++++++++++++- src/tmpl/nag.rs | 2 +- static/js/.gitignore | 1 + static/js/conversation.js | 36 -- static/js/hnwarn.js | 35 -- static/js/xeact-html.min.js | 1 - static/js/xeact.min.js | 1 - static/resume/.gitignore | 1 + static/resume/resume.md | 171 ------ templates/blogindex.rs.html | 94 ---- templates/blogpost.rs.html | 162 ------ templates/contact.rs.html | 53 -- templates/error.rs.html | 13 - templates/feeds.rs.html | 17 - templates/footer.rs.html | 16 - templates/galleryindex.rs.html | 23 - templates/gallerypost.rs.html | 124 ----- templates/gitea.rs.html | 14 - templates/header.rs.html | 102 ---- templates/index.rs.html | 87 ---- templates/notfound.rs.html | 11 - templates/patrons.rs.html | 20 - templates/resume.rs.html | 13 - templates/salary_transparency.rs.html | 44 -- templates/series.rs.html | 17 - templates/series_posts.rs.html | 18 - templates/signalboost.rs.html | 46 -- templates/talkindex.rs.html | 23 - templates/talkpost.rs.html | 124 ----- 87 files changed, 2439 insertions(+), 1771 deletions(-) create mode 100644 blog/site-update-v3.markdown create mode 100644 dhall/Prelude.dhall create mode 100644 dhall/authors/xe.dhall create mode 100644 dhall/latex/.gitignore create mode 100644 dhall/latex/resume.cls create mode 100644 dhall/latex/resume.dhall create mode 100644 dhall/package.dhall create mode 100644 dhall/seriesDescriptions.dhall create mode 100644 dhall/types/SeriesDescription.dhall create mode 100755 src/frontend/build.sh create mode 100644 src/frontend/deno.json create mode 100644 src/frontend/import_map.json create mode 100644 src/frontend/mastodon_share_button.tsx create mode 100644 src/frontend/xeact/jsx-runtime.js create mode 100644 src/frontend/xeact/xeact.js create mode 100644 src/frontend/xeact/xeact.ts create mode 100644 src/post/schemaorg.rs create mode 100644 src/tmpl/asciiart.txt create mode 100644 src/tmpl/blog.rs create mode 100644 static/js/.gitignore delete mode 100644 static/js/conversation.js delete mode 100644 static/js/hnwarn.js delete mode 100644 static/js/xeact-html.min.js delete mode 100644 static/js/xeact.min.js create mode 100644 static/resume/.gitignore delete mode 100644 static/resume/resume.md delete mode 100644 templates/blogindex.rs.html delete mode 100644 templates/blogpost.rs.html delete mode 100644 templates/contact.rs.html delete mode 100644 templates/error.rs.html delete mode 100644 templates/feeds.rs.html delete mode 100644 templates/footer.rs.html delete mode 100644 templates/galleryindex.rs.html delete mode 100644 templates/gallerypost.rs.html delete mode 100644 templates/gitea.rs.html delete mode 100644 templates/header.rs.html delete mode 100644 templates/index.rs.html delete mode 100644 templates/notfound.rs.html delete mode 100644 templates/patrons.rs.html delete mode 100644 templates/resume.rs.html delete mode 100644 templates/salary_transparency.rs.html delete mode 100644 templates/series.rs.html delete mode 100644 templates/series_posts.rs.html delete mode 100644 templates/signalboost.rs.html delete mode 100644 templates/talkindex.rs.html delete mode 100644 templates/talkpost.rs.html diff --git a/Cargo.lock b/Cargo.lock index 04429dc..091b113 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1551,14 +1551,14 @@ dependencies = [ [[package]] name = "mio" -version = "0.8.3" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "713d550d9b44d89174e066b7a6217ae06234c10cb47819a88290d2b353c31799" +checksum = "e5d732bc30207a6423068df043e3d02e0735b155ad7ce1a6f76fe2baa5b158de" dependencies = [ "libc", "log", "wasi 0.11.0+wasi-snapshot-preview1", - "windows-sys 0.36.1", + "windows-sys 0.42.0", ] [[package]] @@ -2812,16 +2812,16 @@ checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c" [[package]] name = "tokio" -version = "1.19.2" +version = "1.22.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c51a52ed6686dd62c320f9b89299e9dfb46f730c7a48e635c19f21d116cb1439" +checksum = "d76ce4a75fb488c605c54bf610f221cea8b0dafb53333c1a67e8ee199dcd2ae3" dependencies = [ + "autocfg", "bytes", "libc", "memchr", "mio", "num_cpus", - "once_cell", "parking_lot", "pin-project-lite", "signal-hook-registry", @@ -2929,9 +2929,9 @@ dependencies = [ [[package]] name = "tower-layer" -version = "0.3.1" +version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "343bc9466d3fe6b0f960ef45960509f84480bf4fd96f92901afe7ff3df9d3a62" +checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" [[package]] name = "tower-service" @@ -3428,7 +3428,7 @@ dependencies = [ [[package]] name = "xesite" -version = "2.5.0" +version = "3.0.0" dependencies = [ "axum", "axum-extra", diff --git a/Cargo.toml b/Cargo.toml index 8523d23..c2c2dfe 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,8 +1,8 @@ [package] name = "xesite" -version = "2.5.0" +version = "3.0.0" authors = ["Xe Iaso "] -edition = "2018" +edition = "2021" build = "src/build.rs" repository = "https://github.com/Xe/site" license = "zlib" diff --git a/blog/a-tool-to-aid-forgetfulness-2022-01-12.markdown b/blog/a-tool-to-aid-forgetfulness-2022-01-12.markdown index fad70cd..6cb032b 100644 --- a/blog/a-tool-to-aid-forgetfulness-2022-01-12.markdown +++ b/blog/a-tool-to-aid-forgetfulness-2022-01-12.markdown @@ -1,7 +1,7 @@ --- title: A Tool to Aid Forgetfulness date: 2022-01-12 -series: stories +series: short-story --- The Egyptian God Thoth lived in the Egyptian city of Naucratis. Thoth was the diff --git a/blog/anbernic-win600-review.markdown b/blog/anbernic-win600-review.markdown index eeeafde..1a4a7bc 100644 --- a/blog/anbernic-win600-review.markdown +++ b/blog/anbernic-win600-review.markdown @@ -1,7 +1,7 @@ --- title: Anbernic Win600 Review date: 2022-08-19 -series: review +series: reviews tags: - anbernic - win600 diff --git a/blog/fear-07-24-2018.markdown b/blog/fear-07-24-2018.markdown index cf47527..8e06d5a 100644 --- a/blog/fear-07-24-2018.markdown +++ b/blog/fear-07-24-2018.markdown @@ -3,7 +3,7 @@ title: Fear date: 2018-07-24 thanks: CelestialBoon, no really this guy is amazing and doesn't get enough credit, I'm so grateful for him. for: Twilight Sparkle -series: stories +series: short-story --- _I must not fear._ diff --git a/blog/one-day-2018-11-01.markdown b/blog/one-day-2018-11-01.markdown index 20e969a..c3d2826 100644 --- a/blog/one-day-2018-11-01.markdown +++ b/blog/one-day-2018-11-01.markdown @@ -2,7 +2,7 @@ title: "One Day" date: 2018-11-01 for: "Nicole" -series: stories +series: short-story --- In the beginning there was the void. All was the void and the void was all. diff --git a/blog/site-update-2020-07-16.markdown b/blog/site-update-2020-07-16.markdown index 431ee4d..b89e427 100644 --- a/blog/site-update-2020-07-16.markdown +++ b/blog/site-update-2020-07-16.markdown @@ -3,6 +3,7 @@ title: "Site Update: Rewrite in Rust" date: 2020-07-16 tags: - rust +series: site-update --- Hello there! You are reading this post thanks to a lot of effort, research and diff --git a/blog/site-update-2021-12-19.markdown b/blog/site-update-2021-12-19.markdown index f92693e..d563c57 100644 --- a/blog/site-update-2021-12-19.markdown +++ b/blog/site-update-2021-12-19.markdown @@ -1,6 +1,7 @@ --- title: "Site Updates: Better Contrast Ratio and Using Xeact" date: 2021-12-19 +series: site-update --- Happy holidays all! As the year rolls to a close I wanted to take a moment to diff --git a/blog/site-update-axum-2022-03-21.markdown b/blog/site-update-axum-2022-03-21.markdown index f20e547..1529050 100644 --- a/blog/site-update-axum-2022-03-21.markdown +++ b/blog/site-update-axum-2022-03-21.markdown @@ -1,6 +1,7 @@ --- title: "Site Update: Axum" date: 2022-03-21 +series: site-update --- I have made a bunch of huge changes to my website that hopefully you won't diff --git a/blog/site-update-hero-images.markdown b/blog/site-update-hero-images.markdown index 41cbafe..ac31db5 100644 --- a/blog/site-update-hero-images.markdown +++ b/blog/site-update-hero-images.markdown @@ -1,6 +1,7 @@ --- title: "Site Update: Hero Images" date: 2022-06-08 +series: site-update --- For a while I've been wondering how I can add dramatic flair to my website with diff --git a/blog/site-update-let-there-be-light-2021-03-13.markdown b/blog/site-update-let-there-be-light-2021-03-13.markdown index aaa7a68..9c1572e 100644 --- a/blog/site-update-let-there-be-light-2021-03-13.markdown +++ b/blog/site-update-let-there-be-light-2021-03-13.markdown @@ -3,6 +3,7 @@ title: "Site Update: Let There Be Light" date: 2021-03-13 tags: - a11y +series: site-update --- In the beginning there was darkness. Darkness was all, and darkness was where the author of this site was comfortable with. However, we live in a time of (supposed) enlightenment. Thanks to the magic of CSS media queries, if you have your computer set to prefer light mode, you will get the light mode version of this website. @@ -13,4 +14,4 @@ In the beginning there was darkness. Darkness was all, and darkness was where th -According to [caniuse.com](https://caniuse.com/?search=prefers-color-scheme) I should _probably_ be fine with this. Please contact me if this acts up for you in an odd way. It shouldn't, but knowing the internet I probably messed something up somewhere. \ No newline at end of file +According to [caniuse.com](https://caniuse.com/?search=prefers-color-scheme) I should _probably_ be fine with this. Please contact me if this acts up for you in an odd way. It shouldn't, but knowing the internet I probably messed something up somewhere. diff --git a/blog/site-update-mastodon-quoting.markdown b/blog/site-update-mastodon-quoting.markdown index 72bb865..72dd50c 100644 --- a/blog/site-update-mastodon-quoting.markdown +++ b/blog/site-update-mastodon-quoting.markdown @@ -7,6 +7,7 @@ tags: - sonicfrontiers - robocadey - noxp +series: site-update --- diff --git a/blog/site-update-patron-page-fixed.markdown b/blog/site-update-patron-page-fixed.markdown index a9974d9..f82de36 100644 --- a/blog/site-update-patron-page-fixed.markdown +++ b/blog/site-update-patron-page-fixed.markdown @@ -1,6 +1,7 @@ --- title: "Site Update: I Fixed the Patron Page" date: 2022-05-18 +series: site-update --- So I fixed [the patron page](https://xeiaso.net/patrons) and the diff --git a/blog/site-update-rss-bandwidth-2021-01-14.markdown b/blog/site-update-rss-bandwidth-2021-01-14.markdown index ff4f611..82dd029 100644 --- a/blog/site-update-rss-bandwidth-2021-01-14.markdown +++ b/blog/site-update-rss-bandwidth-2021-01-14.markdown @@ -4,6 +4,7 @@ date: 2021-01-14 tags: - devops - optimization +series: site-update --- Well, so I think I found out where my Kubernetes cluster cost came from. For diff --git a/blog/site-update-salary-transparency.markdown b/blog/site-update-salary-transparency.markdown index 7b4a536..33b9550 100644 --- a/blog/site-update-salary-transparency.markdown +++ b/blog/site-update-salary-transparency.markdown @@ -1,7 +1,8 @@ --- title: "Site Update: Salary Transparency Page Added" date: 2022-06-14 -author: Sephie +author: sephiraloveboo +series: site-update --- diff --git a/blog/site-update-v3.markdown b/blog/site-update-v3.markdown new file mode 100644 index 0000000..1ee41b6 --- /dev/null +++ b/blog/site-update-v3.markdown @@ -0,0 +1,417 @@ +--- +title: "Site Update: Version 3.0" +date: 2022-11-26 +author: Heartmender +series: site-update +tags: + - dhall + - LaTeX + - rust + - typescript + - Xeact +--- + + + +Hey all! Welcome to Xesite 3.0! Over the last few days I've taken a huge chunk +out of my backlog and I have redone _a lot_ of this website. My hope is that +this will make it faster, more reliable and ultimately make things a lot easier +for everyone. There's a lot of improvements here so I'm just going to start +going over them one by one. + +## Project name changed + +This website has historically been named `site`. It's had a lot of work put into +it over the years and I've never really referred to it by anything but "the +website" or "my blog". However I've noticed a change in my notes and I think I +should make this official. The project behind this website is now officially +called `xesite`. + +What about all of the custom HTML tags? +Aren't they all called `xeblog-$NAME`? Are you going to change +those? + +The custom HTML tags are an +implementation detail, not something that is exposed to end users. Plus, those +are now in my muscle memory so I can't really change those if I wanted +to. + +## Blogpost series have metadata + +When I implemented series support in the blog, it was kind of a hack. Series are +intended to function kind of like tags, but more for tagging things that +progress in a logical series. As an example, take a look at the page for my +[site-to-site WireGuard VPN](https://xeiaso.net/blog/series/site-to-site-wireguard) +series. It shows a little description for the series and in the future I will +likely add other metadata like a series image. + +This is powered by my new `SeriesDescription` Dhall record type. + +For context, +[Dhall](https://dhall-lang.org) is a Haskell-like non-Turing-complete +configuration language that you can think of like JSON or YAML but with +functions, imports, and static types. + +I've never really covered how Dhall works on this blog before, so I'll take a +look at this and the `seriesDescriptions.dhall` file to show off how damn cool +Dhall is. + +One of the most unique features of Dhall as a configuration language is its +record completion operator `::`. This allows you to specify a record (read: +object)'s type and also a set of _default values_ for that record. Let's take a +look at the `SeriesDescription` record type: + +```dhall +-- dhall/types/SeriesDescription.dhall +{ Type = { name : Text, details : Text } +, default = { name = "", details = "" } +} +``` + +If I wanted to use this from inside my Dhall configuration, I would need to: + +* Import the type +* Create a value with the `::` operator + +The description for the `site-to-site-wireguard` series could look something +like this: + +```dhall +-- dhall/series/site-to-site-wireguard.dhall +let xesite = ../types/package.dhall + +let SeriesDescription = xesite.SeriesDescription + +in SeriesDescription::{ + , name = "site-to-site-wireguard" + , details = "Instructions on setting up your own VPN with WireGuard." + } +``` + +You declare your imports with URLs or filesystem paths and other aliases using +`let`, and then you declare what to do with those variables after `in`. If +you've never used Haskell or Lisp before, you can imagine `let` creating a block +of scope just like an extra layer of curly braces in JavaScript or other C-like +languages: + +```javascript +{ + let foo = "bar"; + console.log(foo); +} + +// foo isn't usable from here +``` + +As you can imagine, this gets [way more +elaborate](https://github.com/Xe/site/blob/main/dhall/signalboost.dhall) when +you get more detail into the mix. However, it's all really easy to understand. +It's just different than you might be expecting at first glance. + +If you've never really used Dhall before, I really suggest taking a look at it. +It's what I use for the configuration of all of my tools when I'm allowed to +make those decisions. It's also got the ability to read from environment +variables, which can make it easier to safely turn a bunch of raw strings from +the environment into a more sensible datatype. + +## New type for the Signal Boost data file + +One of my most successful parts of this site is the [signal boost +page](https://xeiaso.net/signalboost). It was the first place I used Dhall on +this website, and is one of the most contributed to things I've ever had in one +of my own projects. + +When I designed the schema forever ago, I apparently decided that people should +only have one of a few types of links. I thought a Twitter and GitHub link +should be sufficient. The Dhall type used to look something like this: + +```dhall +{ Type = + { name : Text + , tags : List Text + , gitLink : Optional Text + , twitter : Optional Text + , linkedin : Optional Text + , fediverse : Optional Text + , coverLetter : Optional Text + , website : Optional Text + } +, default = + { name = "" + , tags = [] : List Text + , gitLink = None Text + , twitter = None Text + , linkedin = None Text + , fediverse = None Text + , coverLetter = None Text + , website = None Text + } +} +``` + +I was wrong. That is _not_ generic enough. Recently I got [this pull +request](https://github.com/Xe/site/pull/567/files) that made me really rethink +how I'm doing this. I don't want to limit people to a set number of links and +then deal with that, I want things to be generic enough that people can link to +whatever they want. I ended up settling on this: + +```dhall +let Link = ./Link.dhall + +in { Type = { name : Text, tags : List Text, links : List Link.Type } + , default = + { name = "", tags = [] : List Text, links = [] : List Link.Type } + } +``` + +This lets people link to _whatever they want_, such as like this: + +```dhall +-- dhall/signalboost/XeIaso.dhall +let xesite = ../types/package.dhall + +let Link = xesite.Link + +let Person = xesite.Person + +in Person::{ + , name = "Xe Iaso" + , tags = + [ "Go" + , "Rust" + , "Dhall" + , "Nix" + , "NixOS" + ] + , links = + [ Link::{ url = "https://github.com/Xe", title = "GitHub" } + , Link::{ url = "https://xeiaso.net", title = "Blog" } + ] + } +``` + +You can easily imagine how this would make things a lot simpler in practice. +Instead of having to have specific fields for every kind of link someone could +have, there's a list of links with a custom target and title. I hope this will +make things simpler in practice. + +I have also removed a lot of the older entries with people that I have +determined to be employed. If I am mistaken, please submit a pull request with +corrections. + +## Resume is now a PDF + +I've hosted [my resume](https://xeiaso.net/resume) on my blog for years. It's +been a Markdown file (originally generated from a JSON document back when JSON +resume was a thing) for the longest time. Whenever someone wanted a copy of my +resume, I usually shoved that markdown file into Pandoc and gave them the +resulting PDF. This has not scaled. + +Recently I changed how [my salary transpareny page +works](https://xeiaso.net/blog/site-update-salary-transparency) and in the +process I put all of my job history information (including salaries) into a +giant heckin' Dhall document. It was always my intention to come back around and +use this data for the resume page, but I've been stuck on the exact best way to +do this. + +On Wednesday I had a bad idea. By the end of the day Thursday, I had it working. +One of the features Dhall has is a string interpolation operator. If you write a +document like this: + +```dhall +let bar = "bar" +in "foo${bar}" +``` + +Dhall will return `foobar`. This means that you can use Dhall for both +structured data _and text templating_. I've also been maintaining a separate +immigration-friendly resume for a few years using Overleaf and LaTeX (turns out +border agencies don't like it when you use a professional pseudonym on your +resume, who knew). The bad idea was to shove the template into Dhall somehow so +that Dhall would puke out LaTeX source code which would then be fed into a LaTeX +compiler to turn into a PDF. + +Of course, if I was going to do this, I couldn't just choose pdfTeX as my LaTeX +compiler of choice. That's not on-brand enough. It just so turns out that there +is an international-character friendly LaTeX compiler named +[XeTeX](https://en.wikipedia.org/wiki/XeTeX). I'm not kidding. It is so on-brand +of me to use this that it _hurts_. + +So I took all of the madness in my trollish heart and poured it into my emacs +frame. I eventually ended up with +[`resume.dhall`](https://github.com/Xe/site/blob/v3/dhall/latex/resume.dhall). +When you run `dhall text` on that file, you get all of that data transformed +into LaTeX source code [like +this](https://gist.github.com/Xe/59eccf3750697aba51512e571d971207). + +However having a bunch of LaTeX source code isn't useful by itself (unless you +are also an immortal and can read LaTeX like I can). I wanted the resume to +build itself so I _cannot forget how this works_. When thinking about build +systems that are largely that ignorable, I usually turn to +[Nix](https://nixos.org). So I wrote a Nix package for building my resume and +shoved it into the resulting package for my blog. It looks something like this: + +```nix +# tex is texlive-medium plus a bunch of packages I need + +resumePDF = pkgs.stdenv.mkDerivation { + pname = "xesite-resume-pdf"; + inherit (bin) version; + inherit src; + buildInputs = with pkgs; [ dhall tex ]; + + phases = "installPhase"; + + installPhase = '' + mkdir -p $out/static/resume + cp -rf ${pkgs.dhallPackages.Prelude}/.cache .cache + chmod -R u+w .cache + export XDG_CACHE_HOME=.cache + export DHALL_PRELUDE=${pkgs.dhallPackages.Prelude}/binary.dhall; + + ln -s $src/dhall/latex/resume.cls + dhall text --file $src/dhall/latex/resume.dhall > resume.tex + + xelatex ./resume.tex + cp resume.pdf $out/static/resume/resume.pdf + ''; +}; +``` + +Now if I want to build my resume by itself, I can run this command: + +```console +$ nix build .#resumePDF +``` + +This should make it a lot easier to deal with recruiters! + +## I rewrote basically all of the templates with Maud + +When I ported my website from [Go to +Rust](https://xeiaso.net/blog/site-update-2020-07-16) back in 2020 I needed a +library like Go's [html/template](https://pkg.go.dev/html/template) to template +out the HTML that my site uses. At the time there were many options I could pick +from, but I ended up choosing [ructe](https://github.com/kaj/ructe) because it +would compile the templates into my application binary instead of having to ship +those with my website. This also means that the _optimizer_ can chew through my +templates and make them _even faster_ than html/template. Native code will +_always_ be faster than interpreted code. + +This worked for a while, but I started running into ergonomics problems as I +continued to use ructe. The great part about ructe is that because the templates +are compiled to Rust anyways, you can use any Rust logic or types you want. The +horrible part about ructe is that your editor autocomplete and type checking +logic doesn't work. Debugging compile failures of your templates requires that +you understand how the generated code works. This isn't really as much of an +issue as I'm making it sound like, but it's a papercut nonetheless. + +A while ago I found the Rust library [Maud](https://maud.lambda.xyz/). It's a +procedural macro that uses a Rust-like syntax to emit HTML. It kinda looks like +HTML if you squint. Compare these two identical documents: + +```html +

Hi there this is a test!

+``` + +```rust +html! { + p { "Hi there this is a test!" } +} +``` + +It also lets you use [splices](https://maud.lambda.xyz/splices-toggles.html) to +add the value of variables to templates and [standard control +structures](https://maud.lambda.xyz/control-structures.html) to handle Option +values or whatever. + +I've wanted to move my site over to use them generically (and I've actually done +most of the work to use them already for a lot of the shortcodes like the +conversation snippets), so I took the time to do that. One of the easy to notice +differences is the HTML of any page on the site. Before there was a lot of +newlines and how everything is crammed into as few lines as possible. + +Shockingly, doing all of these changes seems to have had _no noticeable_ +difference in how browsers render my website. I'm surprised too. + +As of right now the only things left using ructe are my RSS/Atom feeds and the +first implementation of conversation snippets. I am honestly afraid to change +that last one, so I'm leaving it as-is because it works and I don't want to +touch it. + +Maybe this will make things load faster? I don't know. I'm not an HTML-ologist. + +## Pictures on the Patrons page + +My [patrons page](https://xeiaso.net/patrons) has traditionally had a list of +names. I thought I'd take advantage of rewriting the templates to make it a bit +nicer looking, so I grabbed the avatar field out of everyone's entries and told +my HTML template to put it in a fancy grid. This probably doesn't look nice on +phones, but it looks great on my desktop and iPad so it's probably good enough. + +## Everything builds using flakes + +I've maintained two builds of my site for a while. The Nix flakes one that I use +in testing and the legacy Nix build that I use because I still haven't converted +all of my projects on the server that runs this website to use flakes yet. + +My site uses [flake-compat](https://github.com/edolstra/flake-compat) to build +the flakes build with a non-flakes environment. This is intended to make things +easier, but I will still have CI build both the flakes and non-flakes build just +in case. + +## Xesite finally uses Xeact properly + +I've tried to use Xeact a few times on my blog. Nearly all of those attempts +have been failures. I think this time will be different. I've had a share on +Mastodon button on the bottom of every page for a few years. The old button used +to use the browser `prompt()` function to query for your Mastodon instance and +then it would pop a new tab to a precomposed toot that would mention me (so I +can track usage of it). + +More people use this than you'd think. Even more since [all of the everything +with Twitter](https://xeiaso.net/blog/rip-twitter) started to happen. While I +was rejiggering all of the backend stuff with templates, I thought I'd mix in +Xeact more properly and use [Xeact's JSX +support](https://xeiaso.net/blog/xeact-jsx) to automagically compile things. + +I ended up with the "Share on Mastodon" dropdown you'll see at the footer of +this article. It's implemented using [this TypeScript +file](https://github.com/Xe/site/blob/main/src/frontend/mastodon_share_button.tsx). +I'm happy with this so far, it does everything the old one did but just a bit +better. It does use some invisible HTML elements to pass variables from the HTML +template to the Xeact component, which I would love to change to JSON in a +`