;;; SPDX-License-Identifier: GPL-3.0-or-later ;;; SPDX-FileCopyrightText: 2024-2025 Marek Paśnikowski (define-module (deployment systems aisaka) #:use-module ((gnu bootloader) #:prefix gnu:bootloader:) #:use-module ((gnu bootloader grub) #:prefix gnu:bootloader:grub:) #:use-module ((gnu services) #:prefix gnu:services:) #:use-module ((gnu services dns) #:prefix gnu:services:dns:) #:use-module ((gnu services web) #:prefix gnu:services:web:) #:use-module ((gnu system) #:prefix gnu:system:) #:use-module ((gnu system file-systems) #:prefix gnu:system:file-systems:) #:use-module ((gnu system shadow) #:prefix gnu:system:shadow:) #:use-module ((nongnu packages linux) #:prefix nongnu:packages:linux:) #:use-module ((nongnu system linux-initrd) #:prefix nongnu:system:linux-initrd:) #:use-module ((sovereign devices) #:prefix sovereign:devices:) #:use-module ((sovereign devices amd64) #:prefix sovereign:devices:amd64:) #:use-module ((sovereign packages jekyll) #:prefix sovereign:packages:jekyll:) #:use-module ((sovereign systems) #:prefix sovereign:systems:) #:use-module ((suweren commons sudoers) #:prefix suweren-commons-sudoers:) #:use-module ((suweren home) #:prefix suweren:home:) #:use-module ((suweren system) #:prefix suweren:system:) #:use-module ((suweren update) #:prefix suweren:update:) #:use-module ((users id1000) #:prefix users:id1000:) #:use-module ((users vmail) #:prefix users:vmail:)) (gnu:services:dns:define-zone-entries marekpasnikowski.pl.zone ("@" "3600" "IN" "A" "81.190.248.246") ("@" "3600" "IN" "NS" "ns.marekpasnikowski.pl.") ("ns" "3600" "IN" "A" "81.190.248.246") ("@" "3600" "IN" "NS" "ns1.marekpasnikowski.pl.") ("ns1" "3600" "IN" "A" "81.190.248.246") ("@" "3600" "IN" "MX" "10 mx1.forwardemail.net.") ("@" "3600" "IN" "MX" "10 mx2.forwardemail.net.") ("@" "3600" "IN" "TXT" "\"forward-email-port=49152\"") ("@" "3600" "IN" "TXT" "\"forward-email=marekpasnikowski.pl\"") ("@" "3600" "IN" "TXT" "\"v=spf1 ip4:81.190.248.246 -all\"") ("_caldavs._tcp" "3600" "IN" "SRV" "10 0 443 radicale.marekpasnikowski.pl") ("_carddavs._tcp" "3600" "IN" "SRV" "10 0 443 radicale.marekpasnikowski.pl") ("_dmarc" "3600" "IN" "TXT" "\"v=DMARC1; p=reject; sp=reject; pct=100; aspf=s; adkim=s; fo=1; rua=mailto:abuse@marekpasnikowski.pl; ruf=mailto:abuse@marekpasnikowski.pl\"") ("dkim._domainkey" "3600" "IN" "TXT" "\"v=DKIM1; d=marekpasnikowski.pl; t=s; k=rsa; p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAo/b/WV5EUxqAhBgJ4v5K3sP8QI+IwziRJ/F9SDO3p3QOMjZd9AGVt2/AztZ4EmcOJnTlbQnLE/DKCOq4HAdxSZjIqj5AXyMddvWiO78+ugdame/flV0tjdDGNflx65Twap3qgJ9jzhvJfZ1BDuh2WC06fn2pyFl1TCETEGp6ZDkI41FW5GH8l9Jk7hhCmr+Mau0EpE7V42lBdireItOA1e7jQcub50584QATme4rYxA7WR4AeIsknOkUo4q8vkVrssoP11nSg/sNM9RGn1QDfVMJRX0twtgGnJ8N5QE4Ia9DvXL4Y0PNMC0/frp13pB6m1VQP/Z4jfDy+TQzEdSRaQIDAQAB\"") ("git" "3600" "IN" "A" "81.190.248.246") ("radicale" "3600" "IN" "A" "81.190.248.246") ("test" "3600" "IN" "A" "81.190.248.246") ("www" "3600" "IN" "A" "81.190.248.246") ("vault" "3600" "IN" "A" "81.190.248.246")) (define master-zone (gnu:services:dns:knot-zone-configuration (domain "marekpasnikowski.pl") (zone (gnu:services:dns:zone-file (entries marekpasnikowski.pl.zone) (origin "marekpasnikowski.pl") (ns "ns.marekpasnikowski.pl.") (mail "marek.marekpasnikowski.pl.") (serial 2025031000))))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (define radicale-keys "/secrets/radicale/keys") (define dovecot-keys "/secrets/dovecot") (define (nginx-accounts) (use-modules (gnu packages) (guix gexp)) (list ((@ (gnu system accounts) user-group) (name "nginx") (system? #t)) ((@ (gnu system accounts) user-account) (name "nginx") (group "nginx") (supplementary-groups '("git")) (system? #t) (comment "nginx server user") (home-directory "/var/empty") (shell (file-append (specification->package "shadow") "/sbin/nologin"))))) (define (nginx-service-type*) (use-modules (gnu services) (gnu services web) (gnu system shadow)) ((@ (gnu services) service-type) (inherit nginx-service-type) (extensions (map (lambda (extension) (if (eq? ((@ (gnu services) service-extension-target) extension) account-service-type) ((@ (gnu services) service-extension) account-service-type (const (nginx-accounts))) extension)) ((@ (gnu services) service-type-extensions) nginx-service-type))))) (define nginx-service-type* (nginx-service-type*)) (define system-name "aisaka") ;;;??????????????????????????????????????????????????????????????????? (define (certbot) (use-modules (gnu services certbot)) ((@ (gnu services) service) ((@ (gnu services) service-type) (inherit certbot-service-type) (extensions (map (lambda (extension) (if (eq? ((@ (gnu services) service-extension-target) extension) nginx-service-type) ((@ (gnu services) service-extension) nginx-service-type* (@@ (gnu services certbot) certbot-nginx-server-configurations)) extension)) ((@ (gnu services) service-type-extensions) certbot-service-type)))) ((@ (gnu services certbot) certbot-configuration) (certificates (list ((@ (gnu services certbot) certificate-configuration) (deploy-hook (program-file "nginx-deploy-hook" ((@ (guix gexp) gexp) (let ((pid (call-with-input-file "/var/run/nginx/pid" read))) (kill pid SIGHUP))))) (domains (list "marekpasnikowski.pl" "git.marekpasnikowski.pl" "radicale.marekpasnikowski.pl" "test.marekpasnikowski.pl" "www.marekpasnikowski.pl"))))) (email "marek@marekpasnikowski.pl") (webroot "/srv/www/marek/marekpasnikowski.pl")))) (define (cgit-izumi) (use-modules (gnu packages version-control) (gnu services cgit) (gnu services version-control)) ((@ (gnu services) service) ((@ (gnu services) service-type) (inherit cgit-service-type) (extensions (map (lambda (extension) (if (eq? ((@ (gnu services) service-extension-target) extension) nginx-service-type) ((@ (gnu services) service-extension) nginx-service-type* cgit-configuration-nginx-config) extension)) ((@ (gnu services) service-type-extensions) cgit-service-type)))) ((@ (gnu services cgit) cgit-configuration) (nginx (list ((@ (gnu services web) nginx-server-configuration) (locations (list (git-http-nginx-location-configuration ((@ (gnu services version-control) git-http-configuration) (git-root "/var/lib/gitolite/repositories") (uri-path "/git"))) ((@ (gnu services web) nginx-location-configuration) (body (list "fastcgi_param HTTP_HOST $server_name ;" "fastcgi_param PATH_INFO $uri ;" "fastcgi_param QUERY_STRING $args ;" "fastcgi_param SCRIPT_FILENAME $document_root/lib/cgit/cgit.cgi ;" "fastcgi_pass 127.0.0.1:9000 ;")) (uri "@cgit")) ((@ (gnu services web) nginx-location-configuration) (body (list "root /srv/www/marek/marekpasnikowski.pl/ ;")) (uri "/.well-known")))) (listen (list "192.168.10.2:443 ssl")) (root cgit) (server-name (list "git.marekpasnikowski.pl")) (ssl-certificate "/etc/letsencrypt/live/marekpasnikowski.pl/fullchain.pem") (ssl-certificate-key "/etc/letsencrypt/live/marekpasnikowski.pl/privkey.pem") (try-files (list "$uri" "@cgit"))))) (repositories (list ((@ (gnu services cgit) repository-cgit-configuration) (hide? #t) (path "/srv/git/marek/packages")))) (repository-directory "/var/lib/gitolite/repositories")))) (define (etc-mailname) (gnu:services:simple-service 'etc-files etc-service-type (list `("mailname" ,(plain-file "mailname" "marekpasnikowski.pl\n"))))) (define (fcgiwrap) ((@ (gnu services) service) fcgiwrap-service-type ((@ (gnu services web) fcgiwrap-configuration) (user "git") (group "git")))) (define file-system-efi (gnu:system:file-systems:file-system (device (gnu:system:file-systems:file-system-label "AISAKA")) (mount-point "/boot/efi") (type "vfat") (flags (list)) (options #f) (mount? #t) (mount-may-fail? #t) (needed-for-boot? #f) (check? #t) (skip-check-if-clean? #f) (repair 'preen) (create-mount-point? #f) (dependencies (list)) (shepherd-requirements (list)) (location (current-source-location)))) (define file-system-root (gnu:system:file-systems:file-system (device (gnu:system:file-systems:file-system-label "aisaka-root")) (mount-point "/") (type "ext4") (flags (list)) (options #f) (mount? #t) (mount-may-fail? #f) (needed-for-boot? #t) (check? #t) (skip-check-if-clean? #f) (repair 'preen) (create-mount-point? #f) (dependencies (list)) (shepherd-requirements (list)) (location (current-source-location)))) (define (gitolite) ((@ (gnu services) service) gitolite-service-type ((@ (gnu services version-control) gitolite-configuration) (rc-file ((@ (gnu services version-control) gitolite-rc-file) (umask #o0027))) (admin-pubkey (plain-file "gitolite-admin.pub" "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIK4THTYnHCc/ihCJNKJtGTNu1zCnLndbMHnxnrxzJk+N marek@izumi\n"))))) (define (home-services) (use-modules (channels) (gnu home services) (gnu packages base) (gnu packages emacs-xyz) (gnu packages gawk) (guix build-system emacs) (guix git-download) ((guix licenses) #:prefix license:)) ((@ (gnu services) service) (@ (gnu services guix) guix-home-service-type) `(("marek" ,((@ (gnu home) home-environment) (packages (map specification->package+output (list "dconf-editor" "emacs" "emacs-org-modern" "emacs-org-roam" "emacs-paredit" "git" "gnupg" "gnome-tweaks" "noweb" "pinentry" "pwgen" "unzip" "zip"))) (services (append suweren:home:%suweren-home-services ;; (list izumi-channels-service-type) (list (gnu:services:simple-service 'emacs-home-profile home-profile-service-type (append (list emacs-guix emacs-nix-mode) (list (let ((commit* "wip-algo-tn")) ((@ (guix packages) package) (name "emacs-org-fc") (version (git-version "0.1.2" "0" commit*)) (source ((@ (guix packages) origin) (method git-fetch) (uri ((@ (guix git-download) git-reference) (url "https://git.marekpasnikowski.pl/org-fc.git") (commit commit*))) (file-name (git-file-name name version)) (sha256 ((@ (guix packages) base32) '"1i8ii1garx2pdg08a12yzsd0fhwdzcpxp9m97zj8m5s275i8ccaj")))) (build-system emacs-build-system) (arguments (list #:include ((@ (guix gexp) gexp) (cons* "\\.awk$" "\\.org$" %default-include)) #:exclude ((@ (guix gexp) gexp) (cons "^test/" %default-exclude)) #:tests? #t #:test-command ((@ (guix gexp) gexp) (list "emacs" "--batch" "-L" "." "-L" "tests/" "-l" "tests/org-fc-filter-test.el" "-l" "tests/org-fc-indexer-test.el" "-l" "tests/org-fc-review-data-test.el" "-f" "ert-run-tests-batch-and-exit")) #:phases ((@ (guix gexp) gexp) (modify-phases %standard-phases (add-after 'unpack 'qualify-paths (lambda* (#:key inputs #:allow-other-keys) (substitute* "org-fc-awk.el" (("\"find ") (string-append "\"" (search-input-file inputs "/bin/find") " ")) (("\"gawk ") (string-append "\"" (search-input-file inputs "/bin/gawk") " ")) (("\"xargs ") (string-append "\"" (search-input-file inputs "/bin/xargs") " "))))))))) (inputs (list findutils gawk)) (propagated-inputs (list emacs-hydra)) (home-page "https://www.leonrische.me/fc/index.html") (synopsis "Spaced repetition system for Emacs Org mode") (description (string-append "Org-fc is a spaced-repetition system for Emacs' Org mode.\n" "It allows you to mark headlines in a file as flashcards, turning pieces of\n" "knowledge you want to learn into a question-answer test. These cards are\n" "reviewed at regular interval. After each review, the next review interval is\n" "calculated based on how well you remembered the contents of the card.\n")) (license license:gpl3+)))))) (gnu:services:simple-service 'home-files home-files-service-type (list (list ".gitconfig" ((@ (guix gexp) local-file) "gitconfig")) (list ".config/git/ignore" ;; https://github.com/github/gitignore/blob/main/Global/Emacs.gitignore ((@ (guix gexp) local-file) "git-ignore.conf")))) (gnu:services:simple-service 'environment-variables home-environment-variables-service-type `(("EDITOR" . "emacsclient -nw"))))))))))) (define system-keyboard-layout ((@ (gnu system keyboard) keyboard-layout) "pl")) (define (nginx-izumi) ((@ (gnu services) service) nginx-service-type* ((@ (gnu services web) nginx-configuration) (shepherd-requirement (list 'networking)) (server-blocks (list ;; Portal ((@ (gnu services web) nginx-server-configuration) (locations (list ((@ (gnu services web) nginx-location-configuration) (uri "/.well-known" ) (body (list "root /srv/www/marek/marekpasnikowski.pl ;"))))) (listen (list "192.168.10.2:443 ssl")) (root "/home/marek/Publiczne/www") (server-name (list "marekpasnikowski.pl")) (ssl-certificate "/etc/letsencrypt/live/marekpasnikowski.pl/fullchain.pem") (ssl-certificate-key "/etc/letsencrypt/live/marekpasnikowski.pl/privkey.pem")) ;; WWW (gnu:services:web:nginx-server-configuration (listen (list "192.168.10.2:443 ssl")) (root "/home/marek/Publiczne/www") (server-name (list "www.marekpasnikowski.pl"))) ;; Test (gnu:services:web:nginx-server-configuration (locations (list (gnu:services:web:nginx-location-configuration (body (list "if ($ssl_client_verify != SUCCESS) {return 403;}")) (uri "/")))) (listen (list "192.168.10.2:443 ssl")) (root "/home/marek/Publiczne/test") (server-name (list "test.marekpasnikowski.pl")) (raw-content (list "ssl_client_certificate /home/marek/CA/intermediate-authority.cert.pem;" "ssl_verify_client optional;"))) ;; Radicale ((@ (gnu services web) nginx-server-configuration) (locations (list ((@ (gnu services web) nginx-location-configuration) (body (list "proxy_pass http://localhost:5232/ ;" "proxy_set_header X-Script-Name \"\" ;" "proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for ;" "proxy_set_header Host $http_host ;" "proxy_pass_header Authorization ;")) (uri "/")) ((@ (gnu services web) nginx-location-configuration) (body (list "root /srv/www/marek/marekpasnikowski.pl ;")) (uri "/.well-known")))) (listen (list "192.168.10.2:443 ssl")) (server-name (list "radicale.marekpasnikowski.pl")))))))) (define (openssh) (use-modules (gnu services ssh)) ((@ (gnu services) service) openssh-service-type)) (define (radicale) (use-modules (gnu services mail)) ((@ (gnu services) service) radicale-service-type ((@ (gnu services mail) radicale-configuration) (auth ((@ (gnu services mail) radicale-auth-configuration) (type 'htpasswd) (htpasswd-filename radicale-keys) (htpasswd-encryption 'plain))) (storage ((@ (gnu services mail) radicale-storage-configuration) (filesystem-folder "/data/radicale/collections")))))) (define swap-device-izumi-1-label ((@ (gnu system file-systems) file-system-label) "izumi-swap-f")) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (define system-bootloader (gnu:bootloader:bootloader-configuration (bootloader gnu:bootloader:grub:grub-efi-bootloader) (targets (list "/boot/efi")) (keyboard-layout sovereign:devices:pl-keyboard-layout))) (define system-file-systems (list file-system-root file-system-efi)) (define system-groups (list ((@ (gnu system accounts) user-group) (name "vmail") (system? #t)))) (define system-services (list users:id1000:dkim-service users:id1000:dovecot-service users:id1000:smtp-service (service gnu:services:dns:knot-service-type (gnu:services:dns:knot-configuration (listen-v4 "192.168.10.2") (zones (list master-zone)))) (certbot) (cgit-izumi) (etc-mailname) (fcgiwrap) (gitolite) (home-services) (nginx-izumi) (openssh) (radicale))) (define system-users (list users:id1000:uid1000-account users:vmail:vmail-account)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (define-public operating-system* (gnu:system:operating-system (bootloader system-bootloader) (kernel nongnu:packages:linux:linux) (keyboard-layout system-keyboard-layout) (initrd nongnu:system:linux-initrd:microcode-initrd) (firmware (list nongnu:packages:linux:linux-firmware)) (host-name system-name) (file-systems (append system-file-systems gnu:system:file-systems:%base-file-systems)) (users (append system-users gnu:system:shadow:%base-user-accounts)) (groups (append system-groups gnu:system:shadow:%base-groups)) (packages (append gnu:system:%base-packages (list sovereign:packages:jekyll:custom-jekyll))) (timezone "Europe/Warsaw") (locale sovereign:systems:pl-locale) (locale-definitions sovereign:systems:%sovereign-locale-definitions) (services (append system-services sovereign:systems:%sovereign-services)) (sudoers-file sovereign:systems:%sovereign-sudoers-specification)))