diff --git a/nixos-apps/cutesealfanpage.love/.envrc b/nixos-apps/cutesealfanpage.love/.envrc new file mode 100644 index 0000000..3550a30 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/.envrc @@ -0,0 +1 @@ +use flake diff --git a/nixos-apps/cutesealfanpage.love/.gitconfig b/nixos-apps/cutesealfanpage.love/.gitconfig new file mode 100644 index 0000000..2aa6b15 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/.gitconfig @@ -0,0 +1,3 @@ +[user] + email = admin@cutesealfanpage.love + name = Alice diff --git a/nixos-apps/cutesealfanpage.love/.gitignore b/nixos-apps/cutesealfanpage.love/.gitignore new file mode 100644 index 0000000..ceae7a0 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/.gitignore @@ -0,0 +1,15 @@ +# Haykll site +_cache +_site +result + +# Haskell stuff +site +dist +*.dyn_hi +*.dyn_o +*.hi +*.o + +# Direnv lorri stuff +.direnv diff --git a/nixos-apps/cutesealfanpage.love/.vscode/settings.json b/nixos-apps/cutesealfanpage.love/.vscode/settings.json new file mode 100644 index 0000000..2cf55ee --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/.vscode/settings.json @@ -0,0 +1,21 @@ +{ + "git.ignoreLimitWarning": true, + "cSpell.words": [ + "cutesealfanpage", + "Dhall", + "Fanpage", + "fmap", + "Hakyll", + "Lookie", + "mappend", + "Monoid", + "Namecheap", + "NOINLINE", + "pandoc", + "runghc", + "uncurry", + "unlines", + "utct" + ], + "nix.serverPath": "nil" +} \ No newline at end of file diff --git a/nixos-apps/cutesealfanpage.love/README.md b/nixos-apps/cutesealfanpage.love/README.md new file mode 100644 index 0000000..f540f19 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/README.md @@ -0,0 +1,39 @@ +# Cute Seal Fanpage + +> An experiment using [Nix](https://nixos.org/), [Hakyll](https://jaspervdj.be/hakyll/), [Haskell](https://www.haskell.org/), and [shell scripts](https://en.wikipedia.org/wiki/Bourne_shell) to automate a simple website deployment pipeline. + +## Why Seals? + +It's an in-joke. + +## What's all this code? + +seal-blog/ + +- devops/ + - build.sh + - Uses a [nix-shell](https://nixos.wiki/wiki/Development_environment_with_nix-shell) expression to build the Hakyll executable + + - configuration.nix + - The [configuration file for the NixOS](https://nixos.org/manual/nixos/stable/index.html#ch-configuration) production server. This takes care of installing all the necessary software, setup [Nginx](https://www.nginx.com/), and get [ACME certs](https://en.wikipedia.org/wiki/Automated_Certificate_Management_Environment) for verification. + + - newSealPost.sh + - Script to be called daily by a cron job on the server. Generates the post for the day, builds and commits. + +- website/ + - A basic Hakyll site, slightly modified to serve seals. Most of the site is generated from the `site.hs` file. Check the [Hakyll](https://jaspervdj.be/hakyll/) documentation for more info. + +## Work to be done + +- The blog post generation and the hosting of the website are currently intertwined when they should be separated + - Seal post generator just makes posts + - Hakyll blog imports or calls the post generator + - The deployed server/nix config file has a cron job for adding a new blog and committing every day +- Need to move the blog and post generation inside nixos-apps on my beefier server + - The configuration file here is for it's own Linode, the current small one running, but I have a better setup for that now + - Pull out the useful parts for my deployed server, remove anything not necessary for a small config file + - Also switch to using caddy if not already +- Experiment with `*` A records + - For the seal blog + - Instead of having `www` and `git` and `...` subdomains spelled out in Namecheap + - Just have a `*` record and have caddy do the filtering diff --git a/nixos-apps/cutesealfanpage.love/about.rst b/nixos-apps/cutesealfanpage.love/about.rst new file mode 100644 index 0000000..b28b97c --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/about.rst @@ -0,0 +1,6 @@ +--- +title: About Me +--- +I collect the seal photos + +Haven't missed a day yet! diff --git a/nixos-apps/cutesealfanpage.love/config.dhall b/nixos-apps/cutesealfanpage.love/config.dhall new file mode 100644 index 0000000..47e7088 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/config.dhall @@ -0,0 +1,102 @@ +{ sealImagesPath = "images" +, postsOutputPath = "posts" +, startDate = 2022-04-20 +, seed = +137 +, adjectives1 = + [ "absorbing" + , "adorable" + , "alluring" + , "ambrosial" + , "amiable" + , "appealing" + , "attractive" + , "beautiful" + , "bewitching" + , "captivating" + , "charismatic" + , "charming" + , "choice" + , "cute" + , "dainty" + , "darling" + , "dear" + , "delectable" + , "delicate" + , "delicious" + , "delightful" + , "desirable" + , "dishy" + , "dreamy" + , "electrifying" + , "elegant" + , "enamoring" + , "engaging" + , "engrossing" + , "enthralling" + , "entrancing" + , "eye-catching" + , "fascinating" + , "fetching" + , "glamorous" + , "graceful" + , "heavenly" + , "infatuating" + , "inviting" + , "irresistible" + , "likable" + , "lovable" + , "lovely" + , "magnetizing" + , "nice" + , "pleasant" + , "precious" + , "pretty" + , "provocative" + , "rapturous" + , "ravishing" + , "seducing" + , "seductive" + , "suave" + , "sweet" + , "tantalizing" + , "tempting" + , "titillating" + , "winning" + , "winsome" + ] +, adjectives2 = + [ "ample" + , "bearish" + , "big" + , "butterball" + , "buxom" + , "chunky" + , "fatty" + , "flabby" + , "fleshy" + , "full-figured" + , "hefty" + , "husky" + , "pleasingly plump" + , "plump" + , "plumpish" + , "podgy" + , "portly" + , "pudgy" + , "roly-poly" + , "rotund" + , "round" + , "stout" + , "tubby" + , "zaftig" + ] +, looks = + [ "Look at" + , "Gaze upon" + , "Check out" + , "Witness!" + , "Look upon and tremble at" + , "Lookie here at" + , "Whoa! See" + ] +} diff --git a/nixos-apps/cutesealfanpage.love/contact.markdown b/nixos-apps/cutesealfanpage.love/contact.markdown new file mode 100644 index 0000000..a74fd5c --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/contact.markdown @@ -0,0 +1,6 @@ +--- +title: Contact +--- +If you have a seal or seal photos, I'd love to post them! + +Send yours to admin AT cutesealfanpage.love diff --git a/nixos-apps/cutesealfanpage.love/css/default.css b/nixos-apps/cutesealfanpage.love/css/default.css new file mode 100644 index 0000000..381ff73 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/css/default.css @@ -0,0 +1,141 @@ +html { + font-size: 62.5%; +} + +body { + font-size: 1.6rem; + color: #000; +} + +header { + border-bottom: 0.2rem solid #000; +} + +nav { + text-align: right; +} + +nav a { + font-size: 1.8rem; + font-weight: bold; + color: black; + text-decoration: none; + text-transform: uppercase; +} + +footer { + margin-top: 3rem; + padding: 1.2rem 0; + border-top: 0.2rem solid #000; + font-size: 1.2rem; + color: #555; +} + +h1 { + font-size: 2.4rem; +} + +h2 { + font-size: 2rem; +} + +article .header { + font-size: 1.4rem; + font-style: italic; + color: #555; +} + +.logo a { + font-weight: bold; + color: #000; + text-decoration: none; +} + +@media (max-width: 319px) { + body { + width: 90%; + margin: 0; + padding: 0 5%; + } + header { + margin: 4.2rem 0; + } + nav { + margin: 0 auto 3rem; + text-align: center; + } + footer { + text-align: center; + } + .logo { + text-align: center; + margin: 1rem auto 3rem; + } + .logo a { + font-size: 2.4rem; + } + nav a { + display: block; + line-height: 1.6; + } +} + +@media (min-width: 320px) { + body { + width: 90%; + margin: 0; + padding: 0 5%; + } + header { + margin: 4.2rem 0; + } + nav { + margin: 0 auto 3rem; + text-align: center; + } + footer { + text-align: center; + } + .logo { + text-align: center; + margin: 1rem auto 3rem; + } + .logo a { + font-size: 2.4rem; + } + nav a { + display: inline; + margin: 0 0.6rem; + } +} + +@media (min-width: 640px) { + body { + width: 60rem; + margin: 0 auto; + padding: 0; + } + header { + margin: 0 0 3rem; + padding: 1.2rem 0; + } + nav { + margin: 0; + text-align: right; + } + nav a { + margin: 0 0 0 1.2rem; + display: inline; + } + footer { + text-align: right; + } + .logo { + margin: 0; + text-align: left; + } + .logo a { + float: left; + font-size: 1.8rem; + } +} diff --git a/nixos-apps/cutesealfanpage.love/flake.lock b/nixos-apps/cutesealfanpage.love/flake.lock new file mode 100644 index 0000000..ff026eb --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/flake.lock @@ -0,0 +1,85 @@ +{ + "nodes": { + "nixpkgs": { + "locked": { + "lastModified": 1691421349, + "narHash": "sha256-RRJyX0CUrs4uW4gMhd/X4rcDG8PTgaaCQM5rXEJOx6g=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "011567f35433879aae5024fc6ec53f2a0568a6c4", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-23.05", + "repo": "nixpkgs", + "type": "github" + } + }, + "root": { + "inputs": { + "nixpkgs": "nixpkgs", + "spg": "spg", + "utils": "utils" + } + }, + "spg": { + "inputs": { + "nixpkgs": [ + "nixpkgs" + ], + "utils": [ + "utils" + ] + }, + "locked": { + "lastModified": 1691530010, + "narHash": "sha256-4xtMxEstoQ0iM/BOgGhla08xL/DFjS0+Q8nLOl9Gmls=", + "ref": "refs/heads/main", + "rev": "f25dd9c99382fd4e945e4d0d034254fc552d9aca", + "revCount": 14, + "type": "git", + "url": "https://git.ewanick.com/bill/sealPostGenerator.git" + }, + "original": { + "type": "git", + "url": "https://git.ewanick.com/bill/sealPostGenerator.git" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + }, + "utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1689068808, + "narHash": "sha256-6ixXo3wt24N/melDWjq70UuHQLxGV8jZvooRanIHXw0=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "919d646de7be200f3bf08cb76ae1f09402b6f9b4", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/nixos-apps/cutesealfanpage.love/flake.nix b/nixos-apps/cutesealfanpage.love/flake.nix new file mode 100644 index 0000000..617176c --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/flake.nix @@ -0,0 +1,59 @@ +{ + description = "A Nix flake for my long-running seal blog"; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-23.05"; + + utils.url = "github:numtide/flake-utils"; + + spg.url = "git+https://git.ewanick.com/bill/sealPostGenerator.git"; + spg.inputs.nixpkgs.follows = "nixpkgs"; + spg.inputs.utils.follows = "utils"; + }; + + outputs = { self, nixpkgs, utils, ... }@inputs: + utils.lib.eachDefaultSystem (system: + let + pkgs = nixpkgs.legacyPackages.${system}; + + ghc' = pkgs.haskellPackages.ghcWithHoogle (self: with self; [ + hakyll + ]); + in + rec { + apps.generateSealPosts = { + type = "app"; + program = "${inputs.spg.packages.${system}.default}/bin/generateSealPosts"; + }; + + apps.hakyll-site = { + type = "app"; + program = "${packages.default}/bin/site"; + }; + + apps.default = apps.hakyll-site; + + packages.default = pkgs.stdenv.mkDerivation { + name = "site"; + src = self; + buildPhase = '' + ${ghc'}/bin/ghc \ + -O2 \ + -static \ + -o site \ + site.hs + ''; + installPhase = "mkdir -p $out/bin; install -t $out/bin site"; + }; + + devShells.default = pkgs.mkShell { + name = "hakyll-shell"; + + buildInputs = with pkgs.haskellPackages; [ + ghc' + hlint + haskell-language-server + ]; + }; + }); +} diff --git a/nixos-apps/cutesealfanpage.love/index.html b/nixos-apps/cutesealfanpage.love/index.html new file mode 100644 index 0000000..089fdf2 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/index.html @@ -0,0 +1,16 @@ +--- +title: Seal Blog! +--- + +
Welcome to my seal blog!
+ +Here's a list of recent posts for your reading pleasure:
+ +…or you can find more in the archives.
diff --git a/nixos-apps/cutesealfanpage.love/site.hs b/nixos-apps/cutesealfanpage.love/site.hs new file mode 100644 index 0000000..07e3cd8 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/site.hs @@ -0,0 +1,68 @@ +-------------------------------------------------------------------------------- +{-# LANGUAGE OverloadedStrings #-} +import Data.Monoid (mappend) +import Hakyll + + +-------------------------------------------------------------------------------- +main :: IO () +main = hakyll $ do + match "images/*" $ do + route idRoute + compile copyFileCompiler + + match "css/*" $ do + route idRoute + compile compressCssCompiler + + match (fromList ["about.rst", "contact.markdown"]) $ do + route $ setExtension "html" + compile $ pandocCompiler + >>= loadAndApplyTemplate "templates/default.html" defaultContext + >>= relativizeUrls + + match "posts/*" $ do + route $ setExtension "html" + compile $ pandocCompiler + >>= loadAndApplyTemplate "templates/post.html" postCtx + >>= loadAndApplyTemplate "templates/default.html" postCtx + >>= relativizeUrls + + create ["archive.html"] $ do + route idRoute + compile $ do + posts <- recentFirst =<< loadAll "posts/*" + let archiveCtx = + listField "posts" postCtx (return posts) `mappend` + constField "title" "Archives" `mappend` + defaultContext + + makeItem "" + >>= loadAndApplyTemplate "templates/archive.html" archiveCtx + >>= loadAndApplyTemplate "templates/default.html" archiveCtx + >>= relativizeUrls + + + match "index.html" $ do + route idRoute + compile $ do + posts <- fmap (take 20) . recentFirst =<< loadAll "posts/*" + -- posts <- recentFirst =<< loadAll "posts/*" + let indexCtx = + listField "posts" postCtx (return posts) `mappend` + constField "title" "Home" `mappend` + defaultContext + + getResourceBody + >>= applyAsTemplate indexCtx + >>= loadAndApplyTemplate "templates/default.html" indexCtx + >>= relativizeUrls + + match "templates/*" $ compile templateBodyCompiler + + +-------------------------------------------------------------------------------- +postCtx :: Context String +postCtx = + dateField "date" "%B %e, %Y" `mappend` + defaultContext diff --git a/nixos-apps/cutesealfanpage.love/templates/archive.html b/nixos-apps/cutesealfanpage.love/templates/archive.html new file mode 100644 index 0000000..b43eeb2 --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/templates/archive.html @@ -0,0 +1,2 @@ +Here you can find all my previous posts: +$partial("templates/post-list.html")$ diff --git a/nixos-apps/cutesealfanpage.love/templates/default.html b/nixos-apps/cutesealfanpage.love/templates/default.html new file mode 100644 index 0000000..d092fdc --- /dev/null +++ b/nixos-apps/cutesealfanpage.love/templates/default.html @@ -0,0 +1,33 @@ + + + + + + +