From d1a05145de47ce9068417669c92d9c4b6bb29555 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:26:44 -0500
Subject: [PATCH 01/20] feat: init package set

---
 CONTRIBUTING.md |  4 ++--
 default.nix     | 35 +++++++++++++++++++++++++++++++++++
 flake.lock      | 27 +++++++++++++++++++++++++++
 flake.nix       | 49 ++++++++++++++++++++++++++++++++++++++++++++++---
 4 files changed, 110 insertions(+), 5 deletions(-)
 create mode 100644 default.nix
 create mode 100644 flake.lock

diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index ea6bcd8d..7ccfe7b3 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -54,8 +54,8 @@ describes the motivation and content of the commit.
 
 ### Commit scopes
 
-Available commit scopes are port names, `nixos`, `home-manager`, `modules`, and
-`tests`. If none of these apply, omit the scope.
+Available commit scopes are port names, `nixos`, `home-manager`, `modules`,
+`pkgs`, and `tests`. If none of these apply, omit the scope.
 
 ### Breaking changes
 
diff --git a/default.nix b/default.nix
new file mode 100644
index 00000000..d14da78f
--- /dev/null
+++ b/default.nix
@@ -0,0 +1,35 @@
+{
+  pkgs ? import <nixpkgs> {
+    inherit system;
+    config = { };
+    overlays = [ ];
+  },
+  lib ? pkgs.lib,
+  system ? builtins.currentSystem,
+}:
+
+let
+  catppuccinPackages = lib.packagesFromDirectoryRecursive {
+    callPackage = lib.callPackageWith (pkgs // catppuccinPackages);
+    directory = ./pkgs;
+  };
+
+  # Filter out derivations not available on/meant for the current system
+  filtered = lib.filterAttrs (lib.const (
+    deriv:
+    let
+      # Only export packages available on the current system, *unless* they are being cross compiled
+      availableOnHost = lib.meta.availableOn pkgs.stdenv.hostPlatform deriv;
+      # `nix flake check` doesn't like broken packages
+      broken = deriv.meta.broken or false;
+      isCross = deriv.stdenv.buildPlatform != deriv.stdenv.targetPlatform;
+      # Make sure we don't remove our functions
+      isFunction = lib.isFunction deriv;
+    in
+    isFunction || (!broken) && availableOnHost || isCross
+  )) catppuccinPackages;
+in
+
+{
+  packages = filtered;
+}
diff --git a/flake.lock b/flake.lock
new file mode 100644
index 00000000..d98d6b86
--- /dev/null
+++ b/flake.lock
@@ -0,0 +1,27 @@
+{
+  "nodes": {
+    "nixpkgs": {
+      "locked": {
+        "lastModified": 1732014248,
+        "narHash": "sha256-y/MEyuJ5oBWrWAic/14LaIr/u5E0wRVzyYsouYY3W6w=",
+        "owner": "NixOS",
+        "repo": "nixpkgs",
+        "rev": "23e89b7da85c3640bbc2173fe04f4bd114342367",
+        "type": "github"
+      },
+      "original": {
+        "owner": "NixOS",
+        "ref": "nixos-unstable",
+        "repo": "nixpkgs",
+        "type": "github"
+      }
+    },
+    "root": {
+      "inputs": {
+        "nixpkgs": "nixpkgs"
+      }
+    }
+  },
+  "root": "root",
+  "version": 7
+}
diff --git a/flake.nix b/flake.nix
index e5bac3b5..88a1289c 100644
--- a/flake.nix
+++ b/flake.nix
@@ -1,8 +1,51 @@
 {
   description = "Soothing pastel theme for Nix";
 
-  outputs = _: {
-    homeManagerModules.catppuccin = import ./modules/home-manager;
-    nixosModules.catppuccin = import ./modules/nixos;
+  inputs = {
+    nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
   };
+
+  outputs =
+    { nixpkgs, self }:
+
+    let
+      inherit (nixpkgs) lib;
+      systems = lib.systems.flakeExposed;
+
+      # flake-utils pollyfill
+      forEachSystem =
+        fn:
+        lib.foldl' (
+          acc: system:
+          lib.recursiveUpdate acc (
+            lib.mapAttrs (lib.const (value: {
+              ${system} = value;
+            })) (fn system)
+          )
+        ) { } systems;
+
+      mergeAttrs = lib.foldl' lib.recursiveUpdate { };
+    in
+
+    mergeAttrs [
+      # Public outputs
+      (forEachSystem (
+        system:
+        let
+          pkgs = nixpkgs.legacyPackages.${system};
+        in
+        {
+          packages =
+            let
+              catppuccinPackages = (import ./default.nix { inherit pkgs; }).packages;
+            in
+            catppuccinPackages // { default = pkgs.emptyFile; };
+        }
+      ))
+
+      {
+        homeManagerModules.catppuccin = import ./modules/home-manager;
+        nixosModules.catppuccin = import ./modules/nixos;
+      }
+    ];
 }

From 211a58ccec38caa0fef62a97630c28efa148d1e1 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Mon, 25 Nov 2024 09:20:54 -0500
Subject: [PATCH 02/20] feat(pkgs): add fetchCatppuccinPort

---
 pkgs/fetchCatppuccinPort/package.nix | 23 +++++++++++++++++++++++
 1 file changed, 23 insertions(+)
 create mode 100644 pkgs/fetchCatppuccinPort/package.nix

diff --git a/pkgs/fetchCatppuccinPort/package.nix b/pkgs/fetchCatppuccinPort/package.nix
new file mode 100644
index 00000000..3743ab5b
--- /dev/null
+++ b/pkgs/fetchCatppuccinPort/package.nix
@@ -0,0 +1,23 @@
+{ lib, fetchFromGitHub }:
+
+lib.makeOverridable (
+  {
+    port,
+    rev,
+    hash,
+    ...
+  }@args:
+
+  let
+    arguments = [ "port" ];
+  in
+
+  fetchFromGitHub (
+    {
+      owner = "catppuccin";
+      repo = port;
+      inherit rev hash;
+    }
+    // lib.removeAttrs args arguments
+  )
+)

From f5f3f55ac438aa763c9bc5e69a8e0c84cc9af5f6 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Tue, 26 Nov 2024 15:12:43 -0500
Subject: [PATCH 03/20] feat(pkgs): add catppuccinInstallHook

---
 pkgs/catppuccinInstallHook/package.nix |  5 +++++
 pkgs/catppuccinInstallHook/script.sh   | 26 ++++++++++++++++++++++++++
 2 files changed, 31 insertions(+)
 create mode 100644 pkgs/catppuccinInstallHook/package.nix
 create mode 100644 pkgs/catppuccinInstallHook/script.sh

diff --git a/pkgs/catppuccinInstallHook/package.nix b/pkgs/catppuccinInstallHook/package.nix
new file mode 100644
index 00000000..c96bd20c
--- /dev/null
+++ b/pkgs/catppuccinInstallHook/package.nix
@@ -0,0 +1,5 @@
+{ makeSetupHook }:
+
+makeSetupHook {
+  name = "catppuccin-install-hook";
+} ./script.sh
diff --git a/pkgs/catppuccinInstallHook/script.sh b/pkgs/catppuccinInstallHook/script.sh
new file mode 100644
index 00000000..78f5b06f
--- /dev/null
+++ b/pkgs/catppuccinInstallHook/script.sh
@@ -0,0 +1,26 @@
+# shellcheck shell=bash
+# shellcheck disable=SC2154
+
+catppuccinInstallPhase() {
+  runHook preInstall
+
+  local targets=()
+  concatTo targets installTargets=themes
+  echoCmd 'install targets' "${targets[@]}"
+
+  if [ "${#targets[@]}" -gt 1 ]; then
+    mkdir -p "$out"
+  fi
+
+  for target in "${targets[@]}"; do
+    if [ -e "$target" ]; then
+      mv "$target" "$out"
+    fi
+  done
+
+  runHook postInstall
+}
+
+if [ -z "${dontCatppuccinInstall:-}" ] && [ -z "${installPhase:-}" ]; then
+  installPhase=catppuccinInstallPhase
+fi

From 2a168a86a887bc21a4bffc0c7de0dd98e84418f7 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 04:12:29 -0500
Subject: [PATCH 04/20] feat(pkgs): add buildCatppuccinPort

---
 pkgs/buildCatppuccinPort/package.nix | 41 ++++++++++++++++++++++++++++
 1 file changed, 41 insertions(+)
 create mode 100644 pkgs/buildCatppuccinPort/package.nix

diff --git a/pkgs/buildCatppuccinPort/package.nix b/pkgs/buildCatppuccinPort/package.nix
new file mode 100644
index 00000000..06b42c62
--- /dev/null
+++ b/pkgs/buildCatppuccinPort/package.nix
@@ -0,0 +1,41 @@
+{
+  lib,
+  stdenvNoCC,
+  catppuccinInstallHook,
+  fetchCatppuccinPort,
+}:
+
+args:
+
+stdenvNoCC.mkDerivation (
+  finalAttrs:
+
+  let
+    args' = if lib.isFunction args then args finalAttrs else args;
+  in
+
+  args'
+  // {
+    version = args'.version or (builtins.substring 0 7 finalAttrs.src.rev);
+
+    src =
+      args'.src or (fetchCatppuccinPort {
+        port = finalAttrs.pname;
+        inherit (finalAttrs) rev hash;
+        fetchSubmodules = finalAttrs.fetchSubmodules or false;
+      });
+
+    nativeBuildInputs = args'.nativeBuildInputs or [ ] ++ [ catppuccinInstallHook ];
+
+    meta = {
+      description = "Soothing pastel theme for ${finalAttrs.pname}";
+      homepage = "https://github.com/catppuccin/${finalAttrs.pname}";
+      license = lib.licenses.mit;
+      maintainers = with lib.maintainers; [
+        getchoo
+        isabelroses
+      ];
+      platform = lib.platforms.all;
+    } // args'.meta or { };
+  }
+)

From 3dc20e94b0644b4549a84b235a7d515de77b2348 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Mon, 25 Nov 2024 12:25:12 -0500
Subject: [PATCH 05/20] feat(pkgs): add catwalk

---
 pkgs/catwalk/package.nix | 45 ++++++++++++++++++++++++++++++++++++++++
 1 file changed, 45 insertions(+)
 create mode 100644 pkgs/catwalk/package.nix

diff --git a/pkgs/catwalk/package.nix b/pkgs/catwalk/package.nix
new file mode 100644
index 00000000..178fe637
--- /dev/null
+++ b/pkgs/catwalk/package.nix
@@ -0,0 +1,45 @@
+{
+  lib,
+  stdenv,
+  buildPackages,
+  fetchCatppuccinPort,
+  installShellFiles,
+  nix-update-script,
+  rustPlatform,
+}:
+
+rustPlatform.buildRustPackage rec {
+  pname = "catwalk";
+  version = "1.3.2";
+
+  src = fetchCatppuccinPort {
+    port = "catwalk";
+    rev = "refs/tags/v${version}";
+    hash = "sha256-Yj9xTQJ0eu3Ymi2R9fgYwBJO0V+4bN4MOxXCJGQ8NjU=";
+  };
+
+  cargoHash = "sha256-05tF3dqrKYJHs1iYyh3F0lsK+OCSIbK1J1PtLmP0jng=";
+
+  nativeBuildInputs = [ installShellFiles ];
+
+  postInstall =
+    let
+      catwalk = stdenv.hostPlatform.emulator buildPackages + " $out/bin/catwalk";
+    in
+    lib.optionalString (stdenv.hostPlatform.emulatorAvailable buildPackages) ''
+      installShellCompletion --cmd catwalk \
+        --bash <(${catwalk} completion bash) \
+        --fish <(${catwalk} completion fish) \
+        --zsh <(${catwalk} completion zsh)
+    '';
+
+  passthru = {
+    updateScript = nix-update-script { };
+  };
+
+  meta = {
+    description = "Soothing pastel previews for the high-spirited!";
+    homepage = "https://catppuccin.com";
+    license = lib.licenses.mit;
+  };
+}

From 5b6b7e7be9e6b672f2a8559f90b6c1adb08e60d5 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:29:21 -0500
Subject: [PATCH 06/20] feat(pkgs): add whiskers

---
 flake.nix                 |  2 +-
 pkgs/whiskers/package.nix | 29 +++++++++++++++++++++++++++++
 2 files changed, 30 insertions(+), 1 deletion(-)
 create mode 100644 pkgs/whiskers/package.nix

diff --git a/flake.nix b/flake.nix
index 88a1289c..ea1666c1 100644
--- a/flake.nix
+++ b/flake.nix
@@ -39,7 +39,7 @@
             let
               catppuccinPackages = (import ./default.nix { inherit pkgs; }).packages;
             in
-            catppuccinPackages // { default = pkgs.emptyFile; };
+            catppuccinPackages // { default = catppuccinPackages.whiskers; };
         }
       ))
 
diff --git a/pkgs/whiskers/package.nix b/pkgs/whiskers/package.nix
new file mode 100644
index 00000000..2826e28f
--- /dev/null
+++ b/pkgs/whiskers/package.nix
@@ -0,0 +1,29 @@
+{
+  lib,
+  fetchCatppuccinPort,
+  nix-update-script,
+  rustPlatform,
+}:
+
+rustPlatform.buildRustPackage rec {
+  pname = "whiskers";
+  version = "2.5.1";
+
+  src = fetchCatppuccinPort {
+    port = "whiskers";
+    rev = "refs/tags/v${version}";
+    hash = "sha256-OLEXy9MCrPQu1KWICsYhe/ayVqxkYIFwyJoJhgiNDz4=";
+  };
+
+  cargoHash = "sha256-ol8qdC+Cf7vG/X/Q7q9UZmxMWL8i49AI8fQLQt5Vw0A=";
+
+  passthru = {
+    updateScript = nix-update-script { };
+  };
+
+  meta = {
+    description = "Soothing port creation tool for the high-spirited!";
+    homepage = "https://catppuccin.com";
+    license = lib.licenses.mit;
+  };
+}

From 896a75b7c1a7cc38321cd6c6d9da61347ff72f0e Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:19:19 -0500
Subject: [PATCH 07/20] feat(pkgs): add paws.py script

---
 default.nix                          | 32 ++++++++----
 pkgs/buildCatppuccinPort/package.nix |  3 +-
 pkgs/paws.py                         | 78 ++++++++++++++++++++++++++++
 pkgs/sources.json                    |  1 +
 4 files changed, 104 insertions(+), 10 deletions(-)
 create mode 100755 pkgs/paws.py
 create mode 100644 pkgs/sources.json

diff --git a/default.nix b/default.nix
index d14da78f..d92c755f 100644
--- a/default.nix
+++ b/default.nix
@@ -9,13 +9,31 @@
 }:
 
 let
-  catppuccinPackages = lib.packagesFromDirectoryRecursive {
-    callPackage = lib.callPackageWith (pkgs // catppuccinPackages);
-    directory = ./pkgs;
-  };
+  catppuccinPackages =
+    let
+      generated = lib.foldlAttrs (
+        acc: port:
+        { rev, hash }:
+        lib.recursiveUpdate acc {
+          # Save our sources for each port
+          sources.${port} = catppuccinPackages.fetchCatppuccinPort { inherit port rev hash; };
+
+          # And create a default package for them
+          "${port}" = catppuccinPackages.buildCatppuccinPort { pname = port; };
+        }
+      ) { } (lib.importJSON ./pkgs/sources.json);
+
+      collected = lib.packagesFromDirectoryRecursive {
+        callPackage = lib.callPackageWith (pkgs // catppuccinPackages);
+        directory = ./pkgs;
+      };
+    in
+    generated // collected;
+in
 
+{
   # Filter out derivations not available on/meant for the current system
-  filtered = lib.filterAttrs (lib.const (
+  packages = lib.filterAttrs (lib.const (
     deriv:
     let
       # Only export packages available on the current system, *unless* they are being cross compiled
@@ -28,8 +46,4 @@ let
     in
     isFunction || (!broken) && availableOnHost || isCross
   )) catppuccinPackages;
-in
-
-{
-  packages = filtered;
 }
diff --git a/pkgs/buildCatppuccinPort/package.nix b/pkgs/buildCatppuccinPort/package.nix
index 06b42c62..a59cc245 100644
--- a/pkgs/buildCatppuccinPort/package.nix
+++ b/pkgs/buildCatppuccinPort/package.nix
@@ -3,6 +3,7 @@
   stdenvNoCC,
   catppuccinInstallHook,
   fetchCatppuccinPort,
+  sources,
 }:
 
 args:
@@ -19,7 +20,7 @@ stdenvNoCC.mkDerivation (
     version = args'.version or (builtins.substring 0 7 finalAttrs.src.rev);
 
     src =
-      args'.src or (fetchCatppuccinPort {
+      args'.src or sources.${finalAttrs.pname} or (fetchCatppuccinPort {
         port = finalAttrs.pname;
         inherit (finalAttrs) rev hash;
         fetchSubmodules = finalAttrs.fetchSubmodules or false;
diff --git a/pkgs/paws.py b/pkgs/paws.py
new file mode 100755
index 00000000..419f5ce5
--- /dev/null
+++ b/pkgs/paws.py
@@ -0,0 +1,78 @@
+#!/usr/bin/env nix-shell
+#! nix-shell --pure -i python3 -p python3 cacert nix
+import asyncio
+import argparse
+import json
+import subprocess
+from pathlib import Path
+
+# Directory of the current script
+ROOT = Path(__file__).resolve().parent
+
+# Nix command to fetch a port with
+FETCH_COMMAND = [
+	"nix",
+	"--extra-experimental-features",
+	"'nix-command flakes'",
+	"flake",
+	"prefetch",
+	"--json",
+]
+
+SOURCES_FILE = ROOT / "sources.json"
+
+
+def fetch_port(port: str) -> dict:
+	"""Fetch a Catppuccin port"""
+	repository = f"github:catppuccin/{port}"
+	print(f"🔃 Fetching {repository}")
+	command = FETCH_COMMAND + [repository]
+	result = subprocess.run(command, capture_output=True, check=True, text=True)
+	return json.loads(result.stdout)
+
+
+def update_file_with(old_sources: dict, new_sources: dict):
+	"""Update file with new sources only when needed"""
+	if new_sources != old_sources:
+		with open(SOURCES_FILE, "w") as f:
+			json.dump(new_sources, f, indent=2, sort_keys=True)
+	else:
+		print("⚠ No updates made")
+
+
+async def handle_port(sources: dict, port: str, remove=False):
+	"""Handle updating a port in the given sources"""
+	if remove:
+		sources.pop(port, None)
+		print(f"💣 Removed {port}")
+	else:
+		locked = fetch_port(port)["locked"]
+		sources[port] = {"rev": locked["rev"], "hash": locked["narHash"]}
+
+
+async def main():
+	cur_sources = dict()
+	if SOURCES_FILE.exists():
+		with open(SOURCES_FILE, "r") as f:
+			cur_sources = json.load(f)
+
+	parser = argparse.ArgumentParser(prog="paws")
+	parser.add_argument("ports", default=cur_sources.keys(), nargs="*")
+	parser.add_argument("-r", "--remove", action="store_true")
+	args = parser.parse_args()
+
+	assert (
+		not args.remove or len(args.ports) > 0
+	), "Ports must be provided when passing --remove"
+
+	new_sources = cur_sources.copy()
+	await asyncio.gather(
+		*[handle_port(new_sources, port, remove=args.remove) for port in args.ports]
+	)
+
+	update_file_with(cur_sources, new_sources)
+
+	print("✅ Done!")
+
+
+asyncio.run(main())
diff --git a/pkgs/sources.json b/pkgs/sources.json
new file mode 100644
index 00000000..0967ef42
--- /dev/null
+++ b/pkgs/sources.json
@@ -0,0 +1 @@
+{}

From e9a3863ed364115c4e5787fe0241e491ea2f1697 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 04:54:35 -0500
Subject: [PATCH 08/20] feat(pkgs): add all current ports

---
 pkgs/aerc/package.nix           |   7 ++
 pkgs/alacritty/package.nix      |  12 +++
 pkgs/cursors/package.nix        |  52 +++++++++
 pkgs/delta/package.nix          |  10 ++
 pkgs/fcitx5/package.nix         |  12 +++
 pkgs/grub/package.nix           |  12 +++
 pkgs/gtk/package.nix            |  85 +++++++++++++++
 pkgs/k9s/package.nix            |   7 ++
 pkgs/kvantum/package.nix        |  19 ++++
 pkgs/lazygit/package.nix        |   7 ++
 pkgs/micro/package.nix          |   7 ++
 pkgs/nvim/package.nix           |  22 ++++
 pkgs/palette/package.nix        |  10 ++
 pkgs/plymouth/package.nix       |  25 +++++
 pkgs/rofi/package.nix           |   7 ++
 pkgs/sddm/package.nix           |  66 ++++++++++++
 pkgs/sources.json               | 183 +++++++++++++++++++++++++++++++-
 pkgs/spotify-player/package.nix |  10 ++
 pkgs/tmux/package.nix           |  22 ++++
 pkgs/zathura/package.nix        |   7 ++
 20 files changed, 581 insertions(+), 1 deletion(-)
 create mode 100644 pkgs/aerc/package.nix
 create mode 100644 pkgs/alacritty/package.nix
 create mode 100644 pkgs/cursors/package.nix
 create mode 100644 pkgs/delta/package.nix
 create mode 100644 pkgs/fcitx5/package.nix
 create mode 100644 pkgs/grub/package.nix
 create mode 100644 pkgs/gtk/package.nix
 create mode 100644 pkgs/k9s/package.nix
 create mode 100644 pkgs/kvantum/package.nix
 create mode 100644 pkgs/lazygit/package.nix
 create mode 100644 pkgs/micro/package.nix
 create mode 100644 pkgs/nvim/package.nix
 create mode 100644 pkgs/palette/package.nix
 create mode 100644 pkgs/plymouth/package.nix
 create mode 100644 pkgs/rofi/package.nix
 create mode 100644 pkgs/sddm/package.nix
 create mode 100644 pkgs/spotify-player/package.nix
 create mode 100644 pkgs/tmux/package.nix
 create mode 100644 pkgs/zathura/package.nix

diff --git a/pkgs/aerc/package.nix b/pkgs/aerc/package.nix
new file mode 100644
index 00000000..30edace1
--- /dev/null
+++ b/pkgs/aerc/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "aerc";
+
+  installTargets = [ "dist/" ];
+}
diff --git a/pkgs/alacritty/package.nix b/pkgs/alacritty/package.nix
new file mode 100644
index 00000000..ddb5a460
--- /dev/null
+++ b/pkgs/alacritty/package.nix
@@ -0,0 +1,12 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "alacritty";
+
+  dontCatppuccinInstall = true;
+
+  postInstall = ''
+    mkdir -p $out
+    mv *.toml $out/
+  '';
+}
diff --git a/pkgs/cursors/package.nix b/pkgs/cursors/package.nix
new file mode 100644
index 00000000..11785107
--- /dev/null
+++ b/pkgs/cursors/package.nix
@@ -0,0 +1,52 @@
+{
+  lib,
+  buildCatppuccinPort,
+  hyprcursor,
+  inkscape,
+  just,
+  python3,
+  whiskers,
+  xcur2png,
+  xorg,
+  zip,
+}:
+
+buildCatppuccinPort (finalAttrs: {
+  pname = "cursors";
+
+  postPatch = "patchShebangs scripts/ build";
+
+  nativeBuildInputs = [
+    (python3.withPackages (p: [ p.pyside6 ]))
+    hyprcursor
+    inkscape
+    just
+    whiskers
+    xcur2png
+    xorg.xcursorgen
+    zip
+  ];
+
+  buildPhase = ''
+    runHook preBuild
+
+    just all
+
+    runHook postBuild
+  '';
+
+  installPhase = ''
+    runHook preInstall
+
+    mkdir -p $out/share
+    mv dist $out/share/icons
+
+    runHook postInstall
+  '';
+
+  meta = {
+    description = "Catppuccin cursor theme based on Volantes";
+    license = lib.licenses.gpl2;
+    platforms = lib.platforms.linux;
+  };
+})
diff --git a/pkgs/delta/package.nix b/pkgs/delta/package.nix
new file mode 100644
index 00000000..b45d2c29
--- /dev/null
+++ b/pkgs/delta/package.nix
@@ -0,0 +1,10 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "delta";
+
+  installTargets = [
+    "catppuccin.gitconfig"
+    "README.md"
+  ];
+}
diff --git a/pkgs/fcitx5/package.nix b/pkgs/fcitx5/package.nix
new file mode 100644
index 00000000..e5c51848
--- /dev/null
+++ b/pkgs/fcitx5/package.nix
@@ -0,0 +1,12 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "fcitx5";
+
+  dontCatppuccinInstall = true;
+
+  postInstall = ''
+    mkdir -p $out/share/fcitx5
+    mv src/ $out/share/fcitx5/themes/
+  '';
+}
diff --git a/pkgs/grub/package.nix b/pkgs/grub/package.nix
new file mode 100644
index 00000000..12e55895
--- /dev/null
+++ b/pkgs/grub/package.nix
@@ -0,0 +1,12 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "grub";
+
+  dontCatppuccinInstall = true;
+
+  postInstall = ''
+    mkdir -p $out/share/grub
+    mv src $out/share/grub/themes
+  '';
+}
diff --git a/pkgs/gtk/package.nix b/pkgs/gtk/package.nix
new file mode 100644
index 00000000..ba74a90a
--- /dev/null
+++ b/pkgs/gtk/package.nix
@@ -0,0 +1,85 @@
+{
+  lib,
+  buildCatppuccinPort,
+  fetchFromGitHub,
+  git,
+  gtk3,
+  python3,
+  sassc,
+  accents ? [ "mauve" ],
+  allAccents ? true,
+  flavor ? "frappe",
+  size ? "standard",
+  tweaks ? [ ],
+}:
+
+buildCatppuccinPort (finalAttrs: {
+  pname = "gtk";
+  version = "1.0.3";
+
+  src = fetchFromGitHub {
+    owner = "catppuccin";
+    repo = "gtk";
+    rev = "refs/tags/v${finalAttrs.version}";
+    hash = "sha256-8KyZtZqVVz5UKuGdLrUsR2djD3nsJDliHMtvFtUVim8=";
+  };
+
+  postPatch = ''
+    rmdir sources/colloid
+    cp -r ${finalAttrs.finalPackage.colloid} sources/colloid
+    chmod -R +w sources/colloid
+  '';
+
+  nativeBuildInputs = [
+    (python3.withPackages (p: [ p.catppuccin ]))
+    git # `git apply` is used for patches
+    gtk3
+    sassc
+  ];
+
+  dontConfigure = true;
+  dontCatppuccinInstall = true;
+
+  buildFlags =
+    [
+      flavor
+      "--dest"
+      "dist"
+    ]
+    ++ lib.optional allAccents "--all-accents"
+    ++ lib.optionals (accents != [ ]) [
+      "--accent"
+      (toString accents)
+    ]
+    ++ lib.optionals (size != [ ]) [
+      "--size"
+      size
+    ]
+    ++ lib.optionals (tweaks != [ ]) [
+      "--tweaks"
+      (toString tweaks)
+    ];
+
+  postBuild = ''
+    python3 build.py $buildFlags
+  '';
+
+  postInstall = ''
+    mkdir -p $out/share
+    mv dist $out/share/themes
+  '';
+
+  passthru = {
+    colloid = fetchFromGitHub {
+      owner = "vinceliuice";
+      repo = "Colloid-gtk-theme";
+      rev = "1a13048ea1bd4a6cb9b293b537afd16bf267e773";
+      hash = "sha256-zYEoOCNI74Dahlbi5fniuL5PYXcGM4cVM1T2vnnGrcc=";
+    };
+  };
+
+  meta = {
+    description = "Soothing pastel theme for GTK";
+    license = lib.licenses.gpl3Plus;
+  };
+})
diff --git a/pkgs/k9s/package.nix b/pkgs/k9s/package.nix
new file mode 100644
index 00000000..82c7dec6
--- /dev/null
+++ b/pkgs/k9s/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "k9s";
+
+  installTargets = [ "dist" ];
+}
diff --git a/pkgs/kvantum/package.nix b/pkgs/kvantum/package.nix
new file mode 100644
index 00000000..6e349d3e
--- /dev/null
+++ b/pkgs/kvantum/package.nix
@@ -0,0 +1,19 @@
+{
+  lib,
+  buildCatppuccinPort,
+}:
+
+buildCatppuccinPort (finalAttrs: {
+  pname = "kvantum";
+
+  dontCatppuccinInstall = true;
+
+  postInstall = ''
+    mkdir -p $out/share
+    mv themes $out/share/Kvantum/
+  '';
+
+  meta = {
+    platforms = lib.platforms.linux;
+  };
+})
diff --git a/pkgs/lazygit/package.nix b/pkgs/lazygit/package.nix
new file mode 100644
index 00000000..6737c343
--- /dev/null
+++ b/pkgs/lazygit/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "lazygit";
+
+  installTargets = [ "themes-mergable" ];
+}
diff --git a/pkgs/micro/package.nix b/pkgs/micro/package.nix
new file mode 100644
index 00000000..962fea40
--- /dev/null
+++ b/pkgs/micro/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "micro";
+
+  installTargets = [ "src" ];
+}
diff --git a/pkgs/nvim/package.nix b/pkgs/nvim/package.nix
new file mode 100644
index 00000000..9bb6e665
--- /dev/null
+++ b/pkgs/nvim/package.nix
@@ -0,0 +1,22 @@
+{
+  lib,
+  vimUtils,
+  sources,
+}:
+
+let
+  portName = "nvim";
+in
+
+vimUtils.buildVimPlugin rec {
+  pname = "catppuccin-nvim";
+  version = builtins.substring 0 7 src.rev;
+
+  src = sources.${portName};
+
+  meta = {
+    description = "Soothing pastel theme for ${portName}";
+    homepage = "https://github.com/catppuccin/${portName}";
+    license = lib.licenses.mit;
+  };
+}
diff --git a/pkgs/palette/package.nix b/pkgs/palette/package.nix
new file mode 100644
index 00000000..36f6b578
--- /dev/null
+++ b/pkgs/palette/package.nix
@@ -0,0 +1,10 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "palette";
+
+  installTargets = [
+    "README.md"
+    "palette.json"
+  ];
+}
diff --git a/pkgs/plymouth/package.nix b/pkgs/plymouth/package.nix
new file mode 100644
index 00000000..a0d218a5
--- /dev/null
+++ b/pkgs/plymouth/package.nix
@@ -0,0 +1,25 @@
+{
+  lib,
+  buildCatppuccinPort,
+}:
+
+buildCatppuccinPort (finalAttrs: {
+  pname = "plymouth";
+
+  dontCatppuccinInstall = true;
+
+  postPatch = ''
+    substituteInPlace themes/**/*.plymouth \
+      --replace-fail '/usr' '${placeholder "out"}'
+  '';
+
+  postInstall = ''
+    mkdir -p $out/share/plymouth
+    mv themes/ $out/share/plymouth/themes/
+  '';
+
+  meta = {
+    license = lib.licenses.mit;
+    platforms = lib.platforms.linux;
+  };
+})
diff --git a/pkgs/rofi/package.nix b/pkgs/rofi/package.nix
new file mode 100644
index 00000000..95d83a94
--- /dev/null
+++ b/pkgs/rofi/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "rofi";
+
+  installTargets = [ "basic/.local/share/rofi/themes" ];
+}
diff --git a/pkgs/sddm/package.nix b/pkgs/sddm/package.nix
new file mode 100644
index 00000000..daa49e1b
--- /dev/null
+++ b/pkgs/sddm/package.nix
@@ -0,0 +1,66 @@
+{
+  lib,
+  buildCatppuccinPort,
+  just,
+  kdePackages,
+  background ? null,
+  font ? "Noto Sans",
+  fontSize ? "9",
+  loginBackground ? false,
+}:
+
+buildCatppuccinPort (finalAttrs: {
+  pname = "sddm";
+
+  postPatch =
+    ''
+      substituteInPlace pertheme/*.conf \
+        --replace-fail 'Font="Noto Sans"' 'Font="${font}"' \
+        --replace-fail 'FontSize=9' 'FontSize=${toString fontSize}'
+    ''
+    + lib.optionalString (background != null) ''
+      substituteInPlace pertheme/*.conf \
+        --replace-fail 'Background="backgrounds/wall.jpg"' 'Background="${background}"' \
+        --replace-fail 'CustomBackground="false"' 'CustomBackground="true"'
+    ''
+    + lib.optionalString loginBackground ''
+      substituteInPlace pertheme/*.conf \
+        --replace-fail 'LoginBackground="false"' 'LoginBackground="true"'
+    '';
+
+  nativeBuildInputs = [
+    just
+  ];
+
+  propagatedBuildInputs = [
+    kdePackages.qtsvg
+  ];
+
+  dontCatppuccinInstall = true;
+
+  dontWrapQtApps = true;
+
+  buildPhase = ''
+    runHook preBuild
+    just build
+    runHook postBuild
+  '';
+
+  installPhase = ''
+    runHook preInstall
+
+    mkdir -p $out/share/sddm
+    mv dist $out/share/sddm/themes
+
+    runHook postInstall
+  '';
+
+  postFixup = ''
+    mkdir -p $out/nix-support
+    echo ${kdePackages.qtsvg} >> $out/nix-support/propagated-user-env-packages
+  '';
+
+  meta = {
+    platforms = lib.platforms.linux;
+  };
+})
diff --git a/pkgs/sources.json b/pkgs/sources.json
index 0967ef42..307cb878 100644
--- a/pkgs/sources.json
+++ b/pkgs/sources.json
@@ -1 +1,182 @@
-{}
+{
+  "aerc": {
+    "hash": "sha256-OWIkHsKFts/zkrDUtbBPXHVSrHL/F0v3LB1rnlFAKmE=",
+    "rev": "ca404a9f2d125ef12db40db663d43c9d94116a05"
+  },
+  "alacritty": {
+    "hash": "sha256-H8bouVCS46h0DgQ+oYY8JitahQDj0V9p2cOoD4cQX+Q=",
+    "rev": "f6cb5a5c2b404cdaceaff193b9c52317f62c62f7"
+  },
+  "bat": {
+    "hash": "sha256-x1yqPCWuoBSx/cI94eA+AWwhiSA42cLNUOFJl7qjhmw=",
+    "rev": "d2bbee4f7e7d5bac63c054e4d8eca57954b31471"
+  },
+  "bottom": {
+    "hash": "sha256-Vi438I+YVvoD2xzq2t9hJ9R3a+2TlDdbakjFYFtjtXQ=",
+    "rev": "ed09bd5a5dd78d83acdc8ff5fdec40a6340ed1c2"
+  },
+  "btop": {
+    "hash": "sha256-mEGZwScVPWGu+Vbtddc/sJ+mNdD2kKienGZVUcTSl+c=",
+    "rev": "f437574b600f1c6d932627050b15ff5153b58fa3"
+  },
+  "cava": {
+    "hash": "sha256-5AQcCRGaAxP5KFzkJtkKFYq0Ug2xVIEqr2r/k87uWwY=",
+    "rev": "0746f77974330338ee2e1e4d1ef9872eba57eb26"
+  },
+  "cursors": {
+    "hash": "sha256-Mm0fRh/Shem65E/Cl0yyw+efEHOEt/OJ+MzL+3Mcbwc=",
+    "rev": "190cc3c24bde717f21a5aeb96f0d2e81c2a9b889"
+  },
+  "delta": {
+    "hash": "sha256-JvkTvAe1YltgmYSHeewzwg6xU38oGOIYoehXdHwW1zI=",
+    "rev": "0674ec5114c08393d808e2516d153c7e6df00d41"
+  },
+  "dunst": {
+    "hash": "sha256-EadNqtF1m//blHkV660+d4YjDReVFU2Bzhs0Pb43jh4=",
+    "rev": "f02cd2894411c9b4caa207cfd8ed6345f97c0455"
+  },
+  "fcitx5": {
+    "hash": "sha256-1IqFVTEY6z8yNjpi5C+wahMN1kpt0OJATy5echjPXmc=",
+    "rev": "3471b918d4b5aab2d3c3dd9f2c3b9c18fb470e8e"
+  },
+  "fish": {
+    "hash": "sha256-udiU2TOh0lYL7K7ylbt+BGlSDgCjMpy75vQ98C1kFcc=",
+    "rev": "cc8e4d8fffbdaab07b3979131030b234596f18da"
+  },
+  "foot": {
+    "hash": "sha256-eVH3BY2fZe0/OjqucM/IZthV8PMsM9XeIijOg8cNE1Y=",
+    "rev": "962ff1a5b6387bc5419e9788a773a080eea5f1e1"
+  },
+  "fuzzel": {
+    "hash": "sha256-XpItMGsYq4XvLT+7OJ9YRILfd/9RG1GMuO6J4hSGepg=",
+    "rev": "0af0e26901b60ada4b20522df739f032797b07c3"
+  },
+  "gh-dash": {
+    "hash": "sha256-fOCZxrEyWLi+VYnx3QYOP1R+VBhllhOlnO5/5Wg5aq4=",
+    "rev": "acb1b1c22446e34781731ddbfb5e9bd699eccc74"
+  },
+  "gitui": {
+    "hash": "sha256-CRxpEDShQcCEYtSXwLV5zFB8u0HVcudNcMruPyrnSEk=",
+    "rev": "c7661f043cb6773a1fc96c336738c6399de3e617"
+  },
+  "glamour": {
+    "hash": "sha256-a7yR19KcxIS4UPhuhB+X0B+s8D5eytw0/EB0X4z46kA=",
+    "rev": "f410083af1e9b2418bcd73dbbbc987461d4aa292"
+  },
+  "grub": {
+    "hash": "sha256-bDw+W69jeSiE1VBdQqqaeZf7OqCN7q5XYJ5+94PILXE=",
+    "rev": "ffcceb344e2bc86adc8e64437459c1f38adf5b63"
+  },
+  "helix": {
+    "hash": "sha256-/fZBsX179Yri53amryjq2JmUaEa1us6YynlKiwIOncc=",
+    "rev": "2a98f48d45c1394caf1f4499457549218d5f2041"
+  },
+  "hyprland": {
+    "hash": "sha256-xSa/z0Pu+ioZ0gFH9qSo9P94NPkEMovstm1avJ7rvzM=",
+    "rev": "c388ac55563ddeea0afe9df79d4bfff0096b146b"
+  },
+  "imv": {
+    "hash": "sha256-n6obxM5iVSOdlGdI8ZEmYuxudarLoZHqGETrpTcdrok=",
+    "rev": "0317a097b6ec8122b1da6d02f61d0c5158019f6e"
+  },
+  "k9s": {
+    "hash": "sha256-9h+jyEO4w0OnzeEKQXJbg9dvvWGZYQAO4MbgDn6QRzM=",
+    "rev": "fdbec82284744a1fc2eb3e2d24cb92ef87ffb8b4"
+  },
+  "kvantum": {
+    "hash": "sha256-eQmEeKC+L408ajlNg3oKMnDK6Syy2GV6FrR2TN5ZBCg=",
+    "rev": "a87694e0a3c97644dbb34f8835112d17b54ace68"
+  },
+  "lazygit": {
+    "hash": "sha256-b2SoIeXT1BaoxvEeQ0VaPmnBND+7qUe342kOIkyOcAc=",
+    "rev": "d3c95a67ea3f778f7705d8ef814f87ac5213436d"
+  },
+  "mako": {
+    "hash": "sha256-jgiZ+CrM4DX2nZR5BjjD9/Rk5CGGUy3gq9CCvYzp5Vs=",
+    "rev": "92844f144e72f2dc8727879ec141ffdacf3ff6a1"
+  },
+  "micro": {
+    "hash": "sha256-+Jf32S2CHackdmx+UmEKjx71ZCf4VfnxeA3yzz3MSLQ=",
+    "rev": "2802b32308e5b1a827689c095f11ae604bbc85e6"
+  },
+  "mpv": {
+    "hash": "sha256-l5s9WTxNlI4glAYnbfPZ6K8O3knf5zzgDfOKwFxl/jQ=",
+    "rev": "8d82ef42bde7cc7cc4fad7ce690aa90feab46f34"
+  },
+  "newsboat": {
+    "hash": "sha256-czvR3bVZ0NfBmuu0JixalS7B1vf1uEGSTSUVVTclKxI=",
+    "rev": "be3d0ee1ba0fc26baf7a47c2aa7032b7541deb0f"
+  },
+  "nvim": {
+    "hash": "sha256-Oogw5wmYkx/zsMlPE/r6Kt3cy5sC92rwVzf0P9rzqyw=",
+    "rev": "faf15ab0201b564b6368ffa47b56feefc92ce3f4"
+  },
+  "obs": {
+    "hash": "sha256-rU4WTj+2E/+OblAeK0+nzJhisz2V2/KwHBiJVBRj+LQ=",
+    "rev": "d90002a5315db3a43c39dc52c2a91a99c9330e1f"
+  },
+  "palette": {
+    "hash": "sha256-8AZVLJq5fKbMd/YFbqwgpHB7p4iTPTIMmC39R+3ZZ80=",
+    "rev": "b85d36adec22631684ae64ced0a5cdd15462de3b"
+  },
+  "plymouth": {
+    "hash": "sha256-He6ER1QNrJCUthFoBBGHBINouW/tozxQy3R79F5tsuo=",
+    "rev": "e0f58d6fcf3dbc2d35dfc4fec394217fbfa92666"
+  },
+  "polybar": {
+    "hash": "sha256-jMQ+gH1djp2euERZpVW9muHQFI7xYnEQoNpucRj7Gow=",
+    "rev": "20054f39d3b77bd1afc765981a42c3467bf91204"
+  },
+  "rio": {
+    "hash": "sha256-TMhSufhDB3ZQ8/dIDx33NLzNsfjFwnUdRDOV/jF/EGM=",
+    "rev": "13c2fab4d416625d49b54b9c1b97f12e34e85ca1"
+  },
+  "rofi": {
+    "hash": "sha256-zA8Zum19pDTgn0KdQ0gD2kqCOXK4OCHBidFpGwrJOqg=",
+    "rev": "b636a00fd40a7899a8206195464ae8b7f0450a6d"
+  },
+  "sddm": {
+    "hash": "sha256-SnSrxdDSc09LLYavDdekl2EHFzEoS/JncVd8xtgS2WI=",
+    "rev": "f8fbd8f488553af2282356a89ba58b7cbc92be2e"
+  },
+  "spotify-player": {
+    "hash": "sha256-eenf1jB8b2s2qeG7wAApGwkjJZWVNzQj/wEZMUgnn5U=",
+    "rev": "34b3d23806770185b72466d777853c73454b85a6"
+  },
+  "starship": {
+    "hash": "sha256-1w0TJdQP5lb9jCrCmhPlSexf0PkAlcz8GBDEsRjPRns=",
+    "rev": "e99ba6b210c0739af2a18094024ca0bdf4bb3225"
+  },
+  "sway": {
+    "hash": "sha256-H+ZueiYkCoBfS8JENLKhL/efFK6WFNDsbiMbTpGROUs=",
+    "rev": "c072ada05271eec960dc893affe9ac55af63a745"
+  },
+  "swaylock": {
+    "hash": "sha256-AKiOeV9ggvsreC/lq2qXytUsR+x66Q0kpN2F4/Oh2Ao=",
+    "rev": "77246bbbbf8926bdb8962cffab6616bc2b9e8a06"
+  },
+  "tmux": {
+    "hash": "sha256-vBYBvZrMGLpMU059a+Z4SEekWdQD0GrDqBQyqfkEHPg=",
+    "rev": "2c4cb5a07a3e133ce6d5382db1ab541a0216ddc7"
+  },
+  "tofi": {
+    "hash": "sha256-urvt0ZuCe6iEtHwMUl4K6GDLQat/lV0TqgUOlKs8ykE=",
+    "rev": "d6106461867c077a5e1d25236e02b7be7c83839e"
+  },
+  "waybar": {
+    "hash": "sha256-za0y6hcN2rvN6Xjf31xLRe4PP0YyHu2i454ZPjr+lWA=",
+    "rev": "ee8ed32b4f63e9c417249c109818dcc05a2e25da"
+  },
+  "yazi": {
+    "hash": "sha256-UVcPdQFwgBxR6n3/1zRd9ZEkYADkB5nkuom5SxzPTzk=",
+    "rev": "5d3a1eecc304524e995fe5b936b8e25f014953e8"
+  },
+  "zathura": {
+    "hash": "sha256-/vD/hOi6KcaGyAp6Az7jL5/tQSGRzIrf0oHjAJf4QbI=",
+    "rev": "0adc53028d81bf047461bc61c43a484d11b15220"
+  },
+  "zsh-syntax-highlighting": {
+    "hash": "sha256-l6tztApzYpQ2/CiKuLBf8vI2imM6vPJuFdNDSEi7T/o=",
+    "rev": "7926c3d3e17d26b3779851a2255b95ee650bd928"
+  }
+}
\ No newline at end of file
diff --git a/pkgs/spotify-player/package.nix b/pkgs/spotify-player/package.nix
new file mode 100644
index 00000000..8068451c
--- /dev/null
+++ b/pkgs/spotify-player/package.nix
@@ -0,0 +1,10 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "spotify-player";
+
+  installTargets = [
+    "theme.toml"
+    "README.md"
+  ];
+}
diff --git a/pkgs/tmux/package.nix b/pkgs/tmux/package.nix
new file mode 100644
index 00000000..765f1c80
--- /dev/null
+++ b/pkgs/tmux/package.nix
@@ -0,0 +1,22 @@
+{
+  lib,
+  sources,
+  tmuxPlugins,
+}:
+
+let
+  portName = "tmux";
+in
+
+tmuxPlugins.mkTmuxPlugin rec {
+  pluginName = "catppuccin";
+  version = builtins.substring 0 7 src.rev;
+
+  src = sources.${portName};
+
+  meta = {
+    description = "Soothing pastel theme for ${portName}";
+    homepage = "https://github.com/catppuccin/${portName}";
+    license = lib.licenses.mit;
+  };
+}
diff --git a/pkgs/zathura/package.nix b/pkgs/zathura/package.nix
new file mode 100644
index 00000000..221dd624
--- /dev/null
+++ b/pkgs/zathura/package.nix
@@ -0,0 +1,7 @@
+{ buildCatppuccinPort }:
+
+buildCatppuccinPort {
+  pname = "zathura";
+
+  installTargets = [ "src" ];
+}

From aa7e759404989c6f7ed67b01d1beab7414ff0fad Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 16:18:05 -0500
Subject: [PATCH 09/20] feat(modules): use package set for port sources

---
 .github/checkSources.nix                      |  12 -
 .github/workflows/ci.yml                      |  19 -
 .github/workflows/update-locks.yml            |  26 -
 .sources/default.nix                          |  65 ---
 .sources/sources.json                         | 509 ------------------
 dev/add-source.sh                             |  27 -
 dev/flake.nix                                 |  17 -
 flake.nix                                     |  26 +-
 modules/global.nix                            |   2 +-
 modules/home-manager/aerc.nix                 |   3 +-
 modules/home-manager/alacritty.nix            |   1 +
 modules/home-manager/bat.nix                  |   3 +-
 modules/home-manager/bottom.nix               |   3 +-
 modules/home-manager/btop.nix                 |   5 +-
 modules/home-manager/cava.nix                 |   3 +-
 modules/home-manager/cursors.nix              |   5 +-
 modules/home-manager/dunst.nix                |   3 +-
 modules/home-manager/fcitx5.nix               |   2 +-
 modules/home-manager/fish.nix                 |   3 +-
 modules/home-manager/foot.nix                 |   3 +-
 modules/home-manager/fuzzel.nix               |   2 +-
 modules/home-manager/gh-dash.nix              |   2 +-
 modules/home-manager/gitui.nix                |   3 +-
 modules/home-manager/glamour.nix              |   2 +-
 modules/home-manager/gtk.nix                  |   4 +-
 modules/home-manager/helix.nix                |   2 +-
 modules/home-manager/hyprland.nix             |   2 +-
 modules/home-manager/hyprlock.nix             |   2 +-
 modules/home-manager/imv.nix                  |   3 +-
 modules/home-manager/k9s.nix                  |   2 +-
 modules/home-manager/kitty.nix                |   2 +
 modules/home-manager/kvantum.nix              |   9 +-
 modules/home-manager/lazygit.nix              |   2 +-
 modules/home-manager/mako.nix                 |   2 +-
 modules/home-manager/micro.nix                |   4 +-
 modules/home-manager/mpv.nix                  |   2 +-
 modules/home-manager/neovim.nix               |   5 +-
 modules/home-manager/newsboat.nix             |   3 +-
 modules/home-manager/obs.nix                  |   4 +-
 modules/home-manager/polybar.nix              |   3 +-
 modules/home-manager/rio.nix                  |   3 +-
 modules/home-manager/rofi.nix                 |   4 +-
 modules/home-manager/skim.nix                 |   2 +-
 modules/home-manager/spotify-player.nix       |   2 +-
 modules/home-manager/starship.nix             |   3 +-
 modules/home-manager/sway.nix                 |   3 +-
 modules/home-manager/swaylock.nix             |   5 +-
 modules/home-manager/tmux.nix                 |  13 +-
 modules/home-manager/tofi.nix                 |   3 +-
 modules/home-manager/waybar.nix               |   2 +-
 modules/home-manager/yazi.nix                 |   4 +-
 modules/home-manager/zathura.nix              |   3 +-
 modules/home-manager/zellij.nix               |   1 +
 .../home-manager/zsh-syntax-highlighting.nix  |   2 +-
 modules/nixos/fcitx5.nix                      |  10 +-
 modules/nixos/grub.nix                        |   7 +-
 modules/nixos/plymouth.nix                    |   5 +-
 modules/nixos/sddm.nix                        |   4 +-
 modules/nixos/tty.nix                         |   1 +
 59 files changed, 108 insertions(+), 766 deletions(-)
 delete mode 100644 .github/checkSources.nix
 delete mode 100644 .sources/default.nix
 delete mode 100644 .sources/sources.json
 delete mode 100755 dev/add-source.sh

diff --git a/.github/checkSources.nix b/.github/checkSources.nix
deleted file mode 100644
index 50e51e08..00000000
--- a/.github/checkSources.nix
+++ /dev/null
@@ -1,12 +0,0 @@
-let
-  sources = (builtins.fromJSON (builtins.readFile ../.sources/sources.json)).pins;
-
-  isGithubSource = source: source.repository.type or "" == "GitHub";
-  isInOrg = source: source.repository.owner or "" == "catppuccin";
-
-  # all github sources should be from the org
-  isGoodSource = source: isGithubSource source -> isInOrg source;
-  # find the ones that aren't
-  badSources = builtins.filter (source: !(isGoodSource source)) (builtins.attrValues sources);
-in
-if ((builtins.length badSources) == 0) then "OK" else throw "BAD"
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index c5a2afbf..35ce7a9a 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -4,12 +4,10 @@ on:
   push:
     branches: [main]
     paths:
-      - '.sources/**'
       - '**.lock'
       - '**.nix'
   pull_request:
     paths:
-      - '.sources/**'
       - '**.lock'
       - '**.nix'
   workflow_dispatch:
@@ -81,20 +79,3 @@ jobs:
             github:Mic92/nix-fast-build -- \
             --no-nom \
             --flake "./dev#checks.$(nix eval --raw --impure --expr builtins.currentSystem)"
-
-  validate-sources:
-    name: Validate sources
-
-    runs-on: ubuntu-latest
-
-    steps:
-      - name: Checkout repository
-        uses: actions/checkout@v4
-
-      - name: Install Nix
-        uses: cachix/install-nix-action@V27
-
-      - name: Check for external repositories
-        run: |
-          set -e
-          nix eval --file ./.github/checkSources.nix
diff --git a/.github/workflows/update-locks.yml b/.github/workflows/update-locks.yml
index dad5ef9d..4538e663 100644
--- a/.github/workflows/update-locks.yml
+++ b/.github/workflows/update-locks.yml
@@ -29,29 +29,3 @@ jobs:
           commit-msg: "chore: update dev flake inputs"
           pr-title: "chore: update dev flake inputs"
           token: ${{ github.token }}
-
-  ports:
-    name: Update port sources
-
-    runs-on: ubuntu-latest
-
-    permissions:
-      contents: write
-      pull-requests: write
-
-    steps:
-      - name: Checkout repository
-        uses: actions/checkout@v4
-
-      - name: Install Nix
-        uses: cachix/install-nix-action@V27
-
-      - name: Install npins
-        run: nix profile install 'nixpkgs#npins'
-
-      - uses: getchoo/update-npins@v0.1.2
-        with:
-          npins-directory: "./.sources"
-          commit-message: "chore(modules): update ports"
-          pr-title: "chore(modules): update ports"
-          token: ${{ github.token }}
diff --git a/.sources/default.nix b/.sources/default.nix
deleted file mode 100644
index ae291552..00000000
--- a/.sources/default.nix
+++ /dev/null
@@ -1,65 +0,0 @@
-# Generated by npins. Do not modify; will be overwritten regularly
-let
-  data = builtins.fromJSON (builtins.readFile ./sources.json);
-  version = data.version;
-
-  mkSource =
-    spec:
-    assert spec ? type;
-    let
-      path =
-        if spec.type == "Git" then
-          mkGitSource spec
-        else if spec.type == "GitRelease" then
-          mkGitSource spec
-        else if spec.type == "PyPi" then
-          mkPyPiSource spec
-        else if spec.type == "Channel" then
-          mkChannelSource spec
-        else
-          builtins.throw "Unknown source type ${spec.type}";
-    in
-    spec // { outPath = path; };
-
-  mkGitSource =
-    {
-      repository,
-      revision,
-      url ? null,
-      hash,
-      ...
-    }:
-    assert repository ? type;
-    # At the moment, either it is a plain git repository (which has an url), or it is a GitHub/GitLab repository
-    # In the latter case, there we will always be an url to the tarball
-    if url != null then
-      (builtins.fetchTarball {
-        inherit url;
-        sha256 = hash; # FIXME: check nix version & use SRI hashes
-      })
-    else
-      assert repository.type == "Git";
-      builtins.fetchGit {
-        url = repository.url;
-        rev = revision;
-        # hash = hash;
-      };
-
-  mkPyPiSource =
-    { url, hash, ... }:
-    builtins.fetchurl {
-      inherit url;
-      sha256 = hash;
-    };
-
-  mkChannelSource =
-    { url, hash, ... }:
-    builtins.fetchTarball {
-      inherit url;
-      sha256 = hash;
-    };
-in
-if version == 3 then
-  builtins.mapAttrs (_: mkSource) data.pins
-else
-  throw "Unsupported format version ${toString version} in sources.json. Try running `npins upgrade`"
diff --git a/.sources/sources.json b/.sources/sources.json
deleted file mode 100644
index 1bceb47f..00000000
--- a/.sources/sources.json
+++ /dev/null
@@ -1,509 +0,0 @@
-{
-  "pins": {
-    "aerc": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "aerc"
-      },
-      "branch": "main",
-      "revision": "ca404a9f2d125ef12db40db663d43c9d94116a05",
-      "url": "https://github.com/catppuccin/aerc/archive/ca404a9f2d125ef12db40db663d43c9d94116a05.tar.gz",
-      "hash": "0q9a818rwsqx5kvln5zzfan54xaw9yqbbm5hjbrwzdl5q8g28qir"
-    },
-    "alacritty": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "alacritty"
-      },
-      "branch": "main",
-      "revision": "f6cb5a5c2b404cdaceaff193b9c52317f62c62f7",
-      "url": "https://github.com/catppuccin/alacritty/archive/f6cb5a5c2b404cdaceaff193b9c52317f62c62f7.tar.gz",
-      "hash": "1r2z223hza63v5lmzlg3022mlar67j3a2gh41rsaiqwja2wyiihz"
-    },
-    "bat": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "bat"
-      },
-      "branch": "main",
-      "revision": "d2bbee4f7e7d5bac63c054e4d8eca57954b31471",
-      "url": "https://github.com/catppuccin/bat/archive/d2bbee4f7e7d5bac63c054e4d8eca57954b31471.tar.gz",
-      "hash": "0v46lfx9fjg1a36w5n9q424j2v017vhf2gf2znqi985f4lyalp67"
-    },
-    "bottom": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "bottom"
-      },
-      "branch": "main",
-      "revision": "ed09bd5a5dd78d83acdc8ff5fdec40a6340ed1c2",
-      "url": "https://github.com/catppuccin/bottom/archive/ed09bd5a5dd78d83acdc8ff5fdec40a6340ed1c2.tar.gz",
-      "hash": "0x5mcddn1ia8d9dkg54kxmmpgm17c7gxmshwvc1zlmlqizq3fbjn"
-    },
-    "btop": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "btop"
-      },
-      "branch": "main",
-      "revision": "f437574b600f1c6d932627050b15ff5153b58fa3",
-      "url": "https://github.com/catppuccin/btop/archive/f437574b600f1c6d932627050b15ff5153b58fa3.tar.gz",
-      "hash": "1rwpsb252mb6kjgai47ns0ssd7xh7zbpbvanz6p62g8m4z0rjhcq"
-    },
-    "cava": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "cava"
-      },
-      "branch": "main",
-      "revision": "0746f77974330338ee2e1e4d1ef9872eba57eb26",
-      "url": "https://github.com/catppuccin/cava/archive/0746f77974330338ee2e1e4d1ef9872eba57eb26.tar.gz",
-      "hash": "01jvxv797zvamwm82m5i1m9b92hm1bcjdr2w53wi60ws244iq174"
-    },
-    "delta": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "delta"
-      },
-      "branch": "main",
-      "revision": "0674ec5114c08393d808e2516d153c7e6df00d41",
-      "url": "https://github.com/catppuccin/delta/archive/0674ec5114c08393d808e2516d153c7e6df00d41.tar.gz",
-      "hash": "0cnp2ry78mz8l4cf4618gx9v23n26gn7k1w4k5h5nqmm0yy17y96"
-    },
-    "dunst": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "dunst"
-      },
-      "branch": "main",
-      "revision": "f02cd2894411c9b4caa207cfd8ed6345f97c0455",
-      "url": "https://github.com/catppuccin/dunst/archive/f02cd2894411c9b4caa207cfd8ed6345f97c0455.tar.gz",
-      "hash": "07lf6yz3sd0vrs0ls5cm2w6j71kp7snyn5brjkdzz6vms6m4v9qi"
-    },
-    "fcitx5": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "fcitx5"
-      },
-      "branch": "main",
-      "revision": "3471b918d4b5aab2d3c3dd9f2c3b9c18fb470e8e",
-      "url": "https://github.com/catppuccin/fcitx5/archive/3471b918d4b5aab2d3c3dd9f2c3b9c18fb470e8e.tar.gz",
-      "hash": "0rsyrwc74pif9x0f5l3d9bb0s4van0py8qis6qr3zsqq65aqb2nl"
-    },
-    "fish": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "fish"
-      },
-      "branch": "main",
-      "revision": "cc8e4d8fffbdaab07b3979131030b234596f18da",
-      "url": "https://github.com/catppuccin/fish/archive/cc8e4d8fffbdaab07b3979131030b234596f18da.tar.gz",
-      "hash": "1iqmchnz0gglwsxrqcm300754s84gsxrbwmfxh5mdlm16gcr9n5r"
-    },
-    "foot": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "foot"
-      },
-      "branch": "main",
-      "revision": "962ff1a5b6387bc5419e9788a773a080eea5f1e1",
-      "url": "https://github.com/catppuccin/foot/archive/962ff1a5b6387bc5419e9788a773a080eea5f1e1.tar.gz",
-      "hash": "0mhk1p3q7ki84bgdacrcygq5bn36r37p1bis78zysrczil2zflbr"
-    },
-    "fuzzel": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "fuzzel"
-      },
-      "branch": "main",
-      "revision": "0af0e26901b60ada4b20522df739f032797b07c3",
-      "url": "https://github.com/catppuccin/fuzzel/archive/0af0e26901b60ada4b20522df739f032797b07c3.tar.gz",
-      "hash": "163shqaf52gfp26526sizxvxz0j4b2gkifrz5ppqbaqqdcq2v4jy"
-    },
-    "gh-dash": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "gh-dash"
-      },
-      "branch": "main",
-      "revision": "acb1b1c22446e34781731ddbfb5e9bd699eccc74",
-      "url": "https://github.com/catppuccin/gh-dash/archive/acb1b1c22446e34781731ddbfb5e9bd699eccc74.tar.gz",
-      "hash": "1bka75lfazzfkjji75k531a7wm1z1q3dvwc9anzbhn1jn739kq3w"
-    },
-    "gitui": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "gitui"
-      },
-      "branch": "main",
-      "revision": "c7661f043cb6773a1fc96c336738c6399de3e617",
-      "url": "https://github.com/catppuccin/gitui/archive/c7661f043cb6773a1fc96c336738c6399de3e617.tar.gz",
-      "hash": "0ja8wwm3zvnaf16yfwnm86xpql6cg6sw15ylca2c0hd16h86j709"
-    },
-    "glamour": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "glamour"
-      },
-      "branch": "main",
-      "revision": "f410083af1e9b2418bcd73dbbbc987461d4aa292",
-      "url": "https://github.com/catppuccin/glamour/archive/f410083af1e9b2418bcd73dbbbc987461d4aa292.tar.gz",
-      "hash": "0h7az265yx20zhsdrjjy7vqaq7yhjwgq8vpqa2w89i4wsbbr3g3b"
-    },
-    "grub": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "grub"
-      },
-      "branch": "main",
-      "revision": "ffcceb344e2bc86adc8e64437459c1f38adf5b63",
-      "url": "https://github.com/catppuccin/grub/archive/ffcceb344e2bc86adc8e64437459c1f38adf5b63.tar.gz",
-      "hash": "0w9dr21zfzlyc1bsxvldl0xgp5vrkam44pahsn22hyb3mxdkwg3c"
-    },
-    "helix": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "helix"
-      },
-      "branch": "main",
-      "revision": "2a98f48d45c1394caf1f4499457549218d5f2041",
-      "url": "https://github.com/catppuccin/helix/archive/2a98f48d45c1394caf1f4499457549218d5f2041.tar.gz",
-      "hash": "1iwx1q18njkrraccxfmm8rl996fqx8laz9knwzi8mxbvgnql3xpx"
-    },
-    "hyprland": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "hyprland"
-      },
-      "branch": "main",
-      "revision": "c388ac55563ddeea0afe9df79d4bfff0096b146b",
-      "url": "https://github.com/catppuccin/hyprland/archive/c388ac55563ddeea0afe9df79d4bfff0096b146b.tar.gz",
-      "hash": "0cxzxfgbqnkdnvn8nch4z4s7izzlm2jgciq1s8cjmypf8g7vy9n5"
-    },
-    "imv": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "imv"
-      },
-      "branch": "main",
-      "revision": "0317a097b6ec8122b1da6d02f61d0c5158019f6e",
-      "url": "https://github.com/catppuccin/imv/archive/0317a097b6ec8122b1da6d02f61d0c5158019f6e.tar.gz",
-      "hash": "12df3lvsbss433m938fbm9snxv324s8z2j37jjfj6mb2rv21palz"
-    },
-    "k9s": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "k9s"
-      },
-      "branch": "main",
-      "revision": "fdbec82284744a1fc2eb3e2d24cb92ef87ffb8b4",
-      "url": "https://github.com/catppuccin/k9s/archive/fdbec82284744a1fc2eb3e2d24cb92ef87ffb8b4.tar.gz",
-      "hash": "0cs7j1z0xq66w0700qcrc6ynzmw3bdr422p1rnkl7hxq8g4a67zn"
-    },
-    "lazygit": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "lazygit"
-      },
-      "branch": "main",
-      "revision": "d3c95a67ea3f778f7705d8ef814f87ac5213436d",
-      "url": "https://github.com/catppuccin/lazygit/archive/d3c95a67ea3f778f7705d8ef814f87ac5213436d.tar.gz",
-      "hash": "01vhir6243k9wfvlgadv7wsc2s9yb92l67piqsl1dm6kwlhshr3g"
-    },
-    "mako": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "mako"
-      },
-      "branch": "main",
-      "revision": "92844f144e72f2dc8727879ec141ffdacf3ff6a1",
-      "url": "https://github.com/catppuccin/mako/archive/92844f144e72f2dc8727879ec141ffdacf3ff6a1.tar.gz",
-      "hash": "0nz5x66bv0nhmgh2slw647j69x7pqcw0cyclkpv3bq6c5bw9j24f"
-    },
-    "micro": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "micro"
-      },
-      "branch": "main",
-      "revision": "2802b32308e5b1a827689c095f11ae604bbc85e6",
-      "url": "https://github.com/catppuccin/micro/archive/2802b32308e5b1a827689c095f11ae604bbc85e6.tar.gz",
-      "hash": "1d28rhywzwhdg3qzjmgq4xjga7lg19hm4zkcfqjaf7c25pczg5zq"
-    },
-    "mpv": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "mpv"
-      },
-      "branch": "main",
-      "revision": "8d82ef42bde7cc7cc4fad7ce690aa90feab46f34",
-      "url": "https://github.com/catppuccin/mpv/archive/8d82ef42bde7cc7cc4fad7ce690aa90feab46f34.tar.gz",
-      "hash": "0d7ycmfc12pk1ph3rryz97g0xbz8v7rns9q6jhh8x52d7ickv6wp"
-    },
-    "newsboat": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "newsboat"
-      },
-      "branch": "main",
-      "revision": "be3d0ee1ba0fc26baf7a47c2aa7032b7541deb0f",
-      "url": "https://github.com/catppuccin/newsboat/archive/be3d0ee1ba0fc26baf7a47c2aa7032b7541deb0f.tar.gz",
-      "hash": "04ib4lvma5959n943f7myzbc2blmb8n2dd7bkb0xgl2rnpfx2fvk"
-    },
-    "nvim": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "nvim"
-      },
-      "branch": "main",
-      "revision": "faf15ab0201b564b6368ffa47b56feefc92ce3f4",
-      "url": "https://github.com/catppuccin/nvim/archive/faf15ab0201b564b6368ffa47b56feefc92ce3f4.tar.gz",
-      "hash": "0b5bygd3zx1pazq6mxq2kg5xrp9azbx16ky9n3riz4wq17kk121s"
-    },
-    "obs": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "obs"
-      },
-      "branch": "main",
-      "revision": "d90002a5315db3a43c39dc52c2a91a99c9330e1f",
-      "url": "https://github.com/catppuccin/obs/archive/d90002a5315db3a43c39dc52c2a91a99c9330e1f.tar.gz",
-      "hash": "1d7qcca5928q3jqg5nwm7nrn566clx7jn7jhds7gy4xn7x71ckmd"
-    },
-    "palette": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "palette"
-      },
-      "branch": "main",
-      "revision": "b85d36adec22631684ae64ced0a5cdd15462de3b",
-      "url": "https://github.com/catppuccin/palette/archive/b85d36adec22631684ae64ced0a5cdd15462de3b.tar.gz",
-      "hash": "1kb7v7nlgz9dk0634gcki2kpnw5442n6w1gnfz6acz5rk8n5a1ph"
-    },
-    "polybar": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "polybar"
-      },
-      "branch": "main",
-      "revision": "20054f39d3b77bd1afc765981a42c3467bf91204",
-      "url": "https://github.com/catppuccin/polybar/archive/20054f39d3b77bd1afc765981a42c3467bf91204.tar.gz",
-      "hash": "130szcc72vnsl0872qpiiqad1qcspmasana4p2g9v3jxgn03xi4c"
-    },
-    "rio": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "rio"
-      },
-      "branch": "main",
-      "revision": "13c2fab4d416625d49b54b9c1b97f12e34e85ca1",
-      "url": "https://github.com/catppuccin/rio/archive/13c2fab4d416625d49b54b9c1b97f12e34e85ca1.tar.gz",
-      "hash": "0qqhgwqzx59k8hfpbhn5z2qwvg1lywfhyj7pyd87c1s3z2wm5j2c"
-    },
-    "rofi": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "rofi"
-      },
-      "branch": "main",
-      "revision": "b636a00fd40a7899a8206195464ae8b7f0450a6d",
-      "url": "https://github.com/catppuccin/rofi/archive/b636a00fd40a7899a8206195464ae8b7f0450a6d.tar.gz",
-      "hash": "1a1sr451nsfii70j2f5qf8wq4jns0d4477a2kzh3993xdnx1j3yc"
-    },
-    "skim": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "skim"
-      },
-      "branch": "main",
-      "revision": "d39304b5f84721788b19bc40aebcfd7720208d8a",
-      "url": "https://github.com/catppuccin/skim/archive/d39304b5f84721788b19bc40aebcfd7720208d8a.tar.gz",
-      "hash": "1b6cd1wfkprrn7imgf1w1f9a6iqy3bql2ansy7l0k44ps1gwrvxq"
-    },
-    "spotify-player": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "spotify-player"
-      },
-      "branch": "main",
-      "revision": "34b3d23806770185b72466d777853c73454b85a6",
-      "url": "https://github.com/catppuccin/spotify-player/archive/34b3d23806770185b72466d777853c73454b85a6.tar.gz",
-      "hash": "15cz4x432681zwik8dwmjljj628v540c1fz1m4v6nvvw63bdzsbr"
-    },
-    "starship": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "starship"
-      },
-      "branch": "main",
-      "revision": "e99ba6b210c0739af2a18094024ca0bdf4bb3225",
-      "url": "https://github.com/catppuccin/starship/archive/e99ba6b210c0739af2a18094024ca0bdf4bb3225.tar.gz",
-      "hash": "0ys6rwcb3i0h33ycr580z785zv29wl9rmhiaikymdrhgshji63fp"
-    },
-    "sway": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "sway"
-      },
-      "branch": "main",
-      "revision": "c072ada05271eec960dc893affe9ac55af63a745",
-      "url": "https://github.com/catppuccin/sway/archive/c072ada05271eec960dc893affe9ac55af63a745.tar.gz",
-      "hash": "0jrrj68lw6r3dvnd054nmqa9zxrgl6r38i629dgq02i44rx6xrhz"
-    },
-    "swaylock": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "swaylock"
-      },
-      "branch": "main",
-      "revision": "77246bbbbf8926bdb8962cffab6616bc2b9e8a06",
-      "url": "https://github.com/catppuccin/swaylock/archive/77246bbbbf8926bdb8962cffab6616bc2b9e8a06.tar.gz",
-      "hash": "02nql7ry71fxlhj0vsbsxi3jrmfajxmapr9gg0mzp0k0bxwqxa00"
-    },
-    "tmux": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "tmux"
-      },
-      "branch": "main",
-      "revision": "2c4cb5a07a3e133ce6d5382db1ab541a0216ddc7",
-      "url": "https://github.com/catppuccin/tmux/archive/2c4cb5a07a3e133ce6d5382db1ab541a0216ddc7.tar.gz",
-      "hash": "1y0w0kwsjchlm31nml03sics8is8g3k6nzafad6bl66ckayh25mw"
-    },
-    "tofi": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "tofi"
-      },
-      "branch": "main",
-      "revision": "d6106461867c077a5e1d25236e02b7be7c83839e",
-      "url": "https://github.com/catppuccin/tofi/archive/d6106461867c077a5e1d25236e02b7be7c83839e.tar.gz",
-      "hash": "0hfa7jmr83h5m89mv5bzmd0wnq7819g5433wnj2ahyw2kg8yvfxs"
-    },
-    "waybar": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "waybar"
-      },
-      "branch": "main",
-      "revision": "ee8ed32b4f63e9c417249c109818dcc05a2e25da",
-      "url": "https://github.com/catppuccin/waybar/archive/ee8ed32b4f63e9c417249c109818dcc05a2e25da.tar.gz",
-      "hash": "0q4mzqx3w6cywfifs7ij8qzhzvj59dfdzpvqx76vpnhd2zm35bfd"
-    },
-    "yazi": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "yazi"
-      },
-      "branch": "main",
-      "revision": "5d3a1eecc304524e995fe5b936b8e25f014953e8",
-      "url": "https://github.com/catppuccin/yazi/archive/5d3a1eecc304524e995fe5b936b8e25f014953e8.tar.gz",
-      "hash": "0fagrwf4pfc9pbj9j1z401h294gmblsdgzvxx98ir03h05shymsi"
-    },
-    "zathura": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "zathura"
-      },
-      "branch": "main",
-      "revision": "0adc53028d81bf047461bc61c43a484d11b15220",
-      "url": "https://github.com/catppuccin/zathura/archive/0adc53028d81bf047461bc61c43a484d11b15220.tar.gz",
-      "hash": "1cj1z2bh1qw1sbgqmk4i450yv7rgwcz06yhar23ccadsx22gzw7y"
-    },
-    "zsh-syntax-highlighting": {
-      "type": "Git",
-      "repository": {
-        "type": "GitHub",
-        "owner": "catppuccin",
-        "repo": "zsh-syntax-highlighting"
-      },
-      "branch": "main",
-      "revision": "7926c3d3e17d26b3779851a2255b95ee650bd928",
-      "url": "https://github.com/catppuccin/zsh-syntax-highlighting/archive/7926c3d3e17d26b3779851a2255b95ee650bd928.tar.gz",
-      "hash": "1yjgpd44hhyk2mpg5g1scf53dwpjbyqbi2i8zhv98qkk1as77awp"
-    }
-  },
-  "version": 3
-}
\ No newline at end of file
diff --git a/dev/add-source.sh b/dev/add-source.sh
deleted file mode 100755
index 5f62caa6..00000000
--- a/dev/add-source.sh
+++ /dev/null
@@ -1,27 +0,0 @@
-#!/usr/bin/env bash
-set -euo pipefail
-
-_usage="
-A wrapper script around \`npins\` for adding sources to catppuccin/nix
-
-Usage: $(basename "$0") repo_name [branch]
-
-Options:
-
-repo_name           Name of the repository in the Catppuccin org
-branch              Primary branch of the repository (defaults to main if omitted)
-"
-
-repo_name="${1:-}"
-branch_name="${2:-main}"
-
-if [ "${repo_name:-}" = "" ]; then
-    echo "error: a repository name is required!" >&2
-    echo "$_usage"
-    exit 1
-fi
-
-npins add github \
-  catppuccin "$repo_name" \
-  --directory ./.sources \
-  --branch "$branch_name"
diff --git a/dev/flake.nix b/dev/flake.nix
index 210c64b2..771c978f 100644
--- a/dev/flake.nix
+++ b/dev/flake.nix
@@ -191,23 +191,6 @@
             '';
           };
 
-          add-source =
-            pkgs.runCommand "add-source"
-              {
-                nativeBuildInputs = [ pkgs.patsh ];
-                buildInputs = [ pkgs.npins ];
-                meta.mainProgram = "add-source";
-              }
-              ''
-                mkdir -p $out/bin
-
-                patsh \
-                  --store-dir ${builtins.storeDir} \
-                  ${./add-source.sh} $out/bin/add-source
-
-                chmod 755 $out/bin/add-source
-              '';
-
           default = self.packages.${system}.site;
         }
       );
diff --git a/flake.nix b/flake.nix
index ea1666c1..08b6771e 100644
--- a/flake.nix
+++ b/flake.nix
@@ -24,6 +24,21 @@
           )
         ) { } systems;
 
+      mkModule =
+        {
+          name ? "catppuccin",
+          type,
+          file,
+        }:
+        { pkgs, ... }:
+        {
+          _file = "${self.outPath}/flake.nix#${type}Modules.${name}";
+
+          imports = [ file ];
+
+          catppuccin.sources = lib.mkDefault self.packages.${pkgs.stdenv.hostPlatform.system};
+        };
+
       mergeAttrs = lib.foldl' lib.recursiveUpdate { };
     in
 
@@ -44,8 +59,15 @@
       ))
 
       {
-        homeManagerModules.catppuccin = import ./modules/home-manager;
-        nixosModules.catppuccin = import ./modules/nixos;
+        homeManagerModules.catppuccin = mkModule {
+          type = "homeManager";
+          file = ./modules/home-manager;
+        };
+
+        nixosModules.catppuccin = mkModule {
+          type = "nixos";
+          file = ./modules/nixos;
+        };
       }
     ];
 }
diff --git a/modules/global.nix b/modules/global.nix
index 7e30dee5..68a0c4d4 100644
--- a/modules/global.nix
+++ b/modules/global.nix
@@ -34,7 +34,7 @@ in
 
     sources =
       let
-        defaultSources = import ../.sources;
+        defaultSources = (import ../default.nix { inherit pkgs; }).packages;
       in
       lib.mkOption {
         type = lib.types.lazyAttrsOf lib.types.raw;
diff --git a/modules/home-manager/aerc.nix b/modules/home-manager/aerc.nix
index afc6c406..83c11f0a 100644
--- a/modules/home-manager/aerc.nix
+++ b/modules/home-manager/aerc.nix
@@ -6,6 +6,7 @@ let
   cfg = config.catppuccin.aerc;
   themeName = "catppuccin-${cfg.flavor}";
 in
+
 {
   options.catppuccin.aerc = catppuccinLib.mkCatppuccinOption { name = "aerc"; };
 
@@ -20,7 +21,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.aerc = {
-      stylesets.${themeName} = lib.fileContents "${sources.aerc}/dist/${themeName}";
+      stylesets.${themeName} = lib.fileContents "${sources.aerc}/${themeName}";
       extraConfig = {
         ui = {
           styleset-name = themeName;
diff --git a/modules/home-manager/alacritty.nix b/modules/home-manager/alacritty.nix
index 4d8cf0d5..c2d400b4 100644
--- a/modules/home-manager/alacritty.nix
+++ b/modules/home-manager/alacritty.nix
@@ -5,6 +5,7 @@ let
   inherit (config.catppuccin) sources;
   cfg = config.catppuccin.alacritty;
 in
+
 {
   options.catppuccin.alacritty = catppuccinLib.mkCatppuccinOption { name = "alacritty"; };
 
diff --git a/modules/home-manager/bat.nix b/modules/home-manager/bat.nix
index 3a3b1afc..1cda6a17 100644
--- a/modules/home-manager/bat.nix
+++ b/modules/home-manager/bat.nix
@@ -6,6 +6,7 @@ let
   cfg = config.catppuccin.bat;
   themeName = "Catppuccin ${catppuccinLib.mkUpper cfg.flavor}";
 in
+
 {
   options.catppuccin.bat = catppuccinLib.mkCatppuccinOption { name = "bat"; };
 
@@ -24,7 +25,7 @@ in
 
       themes.${themeName} = {
         src = sources.bat;
-        file = "themes/${themeName}.tmTheme";
+        file = "${themeName}.tmTheme";
       };
     };
   };
diff --git a/modules/home-manager/bottom.nix b/modules/home-manager/bottom.nix
index 50886987..5089230d 100644
--- a/modules/home-manager/bottom.nix
+++ b/modules/home-manager/bottom.nix
@@ -5,6 +5,7 @@ let
   inherit (config.catppuccin) sources;
   cfg = config.catppuccin.bottom;
 in
+
 {
   options.catppuccin.bottom = catppuccinLib.mkCatppuccinOption { name = "bottom"; };
 
@@ -19,7 +20,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.bottom = {
-      settings = lib.importTOML "${sources.bottom}/themes/${cfg.flavor}.toml";
+      settings = lib.importTOML "${sources.bottom}/${cfg.flavor}.toml";
     };
   };
 }
diff --git a/modules/home-manager/btop.nix b/modules/home-manager/btop.nix
index 74af8642..ce59d9e3 100644
--- a/modules/home-manager/btop.nix
+++ b/modules/home-manager/btop.nix
@@ -8,8 +8,7 @@ let
   enable = cfg.enable && config.programs.btop.enable;
 
   themeFile = "catppuccin_${cfg.flavor}.theme";
-  themePath = "/themes/${themeFile}";
-  theme = sources.btop + themePath;
+  theme = sources.btop + "/${themeFile}";
 in
 
 {
@@ -26,7 +25,7 @@ in
 
   config = lib.mkIf enable {
     xdg.configFile = {
-      "btop${themePath}".source = theme;
+      "btop/themes/${themeFile}".source = theme;
     };
 
     programs.btop = {
diff --git a/modules/home-manager/cava.nix b/modules/home-manager/cava.nix
index 5d28ac5d..5130e12b 100644
--- a/modules/home-manager/cava.nix
+++ b/modules/home-manager/cava.nix
@@ -7,6 +7,7 @@ let
   cfg = config.catppuccin.cava;
   flavor = "${cfg.flavor}" + lib.optionalString cfg.transparent "-transparent";
 in
+
 {
   options.catppuccin.cava = catppuccinLib.mkCatppuccinOption { name = "cava"; } // {
     transparent = lib.mkEnableOption "transparent version of flavor";
@@ -39,7 +40,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.cava = {
-      settings = catppuccinLib.importINIRaw (sources.cava + "/themes/${flavor}.cava");
+      settings = catppuccinLib.importINIRaw (sources.cava + "/${flavor}.cava");
     };
   };
 }
diff --git a/modules/home-manager/cursors.nix b/modules/home-manager/cursors.nix
index 9fb9c016..0994d01d 100644
--- a/modules/home-manager/cursors.nix
+++ b/modules/home-manager/cursors.nix
@@ -1,12 +1,13 @@
 { catppuccinLib }:
 {
   config,
-  pkgs,
   lib,
   ...
 }:
 
 let
+  inherit (config.catppuccin) sources;
+
   cfg = config.catppuccin.cursors;
 
   # "dark" and "light" can be used alongside the regular accents
@@ -46,7 +47,7 @@ in
   config = lib.mkIf cfg.enable {
     home.pointerCursor = {
       name = "catppuccin-${cfg.flavor}-${cfg.accent}-cursors";
-      package = pkgs.catppuccin-cursors.${cfg.flavor + catppuccinLib.mkUpper cfg.accent};
+      package = sources.cursors;
     };
   };
 }
diff --git a/modules/home-manager/dunst.nix b/modules/home-manager/dunst.nix
index 15cc280d..ad5764bf 100644
--- a/modules/home-manager/dunst.nix
+++ b/modules/home-manager/dunst.nix
@@ -50,8 +50,7 @@ in
       # Using a prefix like this is necessary because drop-ins' precedence depends on lexical order
       # such that later drop-ins override earlier ones
       # This way, users have better control over precedence
-      "dunst/dunstrc.d/${cfg.prefix}-catppuccin.conf".source =
-        sources.dunst + "/themes/${cfg.flavor}.conf";
+      "dunst/dunstrc.d/${cfg.prefix}-catppuccin.conf".source = sources.dunst + "/${cfg.flavor}.conf";
     };
   };
 }
diff --git a/modules/home-manager/fcitx5.nix b/modules/home-manager/fcitx5.nix
index 66cd394b..a5b7b212 100644
--- a/modules/home-manager/fcitx5.nix
+++ b/modules/home-manager/fcitx5.nix
@@ -56,7 +56,7 @@ in
   config = lib.mkIf enable {
     xdg.dataFile = {
       "fcitx5/themes/catppuccin-${cfg.flavor}-${cfg.accent}" = {
-        source = "${sources.fcitx5}/src/catppuccin-${cfg.flavor}-${cfg.accent}";
+        source = "${sources.fcitx5}/usr/share/fcitx5/themes/catppuccin-${cfg.flavor}-${cfg.accent}";
         recursive = true;
       };
     };
diff --git a/modules/home-manager/fish.nix b/modules/home-manager/fish.nix
index adf37673..d3cc3843 100644
--- a/modules/home-manager/fish.nix
+++ b/modules/home-manager/fish.nix
@@ -8,7 +8,6 @@ let
   enable = cfg.enable && config.programs.fish.enable;
 
   themeName = "Catppuccin ${catppuccinLib.mkUpper cfg.flavor}";
-  themePath = "/themes/${themeName}.theme";
 in
 
 {
@@ -24,7 +23,7 @@ in
   };
 
   config = lib.mkIf enable {
-    xdg.configFile."fish${themePath}".source = "${sources.fish}${themePath}";
+    xdg.configFile."fish/themes/${themeName}.theme".source = "${sources.fish}/${themeName}.theme";
 
     programs.fish.shellInit = ''
       fish_config theme choose "${themeName}"
diff --git a/modules/home-manager/foot.nix b/modules/home-manager/foot.nix
index 2e5054f2..16329e49 100644
--- a/modules/home-manager/foot.nix
+++ b/modules/home-manager/foot.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.foot;
 in
+
 {
   options.catppuccin.foot = catppuccinLib.mkCatppuccinOption { name = "foot"; };
 
@@ -21,7 +22,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.foot = {
       settings = {
-        main.include = sources.foot + "/themes/catppuccin-${cfg.flavor}.ini";
+        main.include = sources.foot + "/catppuccin-${cfg.flavor}.ini";
       };
     };
   };
diff --git a/modules/home-manager/fuzzel.nix b/modules/home-manager/fuzzel.nix
index d4079529..8ed78af3 100644
--- a/modules/home-manager/fuzzel.nix
+++ b/modules/home-manager/fuzzel.nix
@@ -26,7 +26,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.fuzzel = {
       settings = {
-        main.include = sources.fuzzel + "/themes/catppuccin-${cfg.flavor}/${cfg.accent}.ini";
+        main.include = sources.fuzzel + "/catppuccin-${cfg.flavor}/${cfg.accent}.ini";
       };
     };
   };
diff --git a/modules/home-manager/gh-dash.nix b/modules/home-manager/gh-dash.nix
index d8e89427..31b33b51 100644
--- a/modules/home-manager/gh-dash.nix
+++ b/modules/home-manager/gh-dash.nix
@@ -5,7 +5,7 @@ let
   inherit (config.catppuccin) sources;
 
   cfg = config.catppuccin.gh-dash;
-  theme = "${sources.gh-dash}/themes/${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}.yml";
+  theme = "${sources.gh-dash}/${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}.yml";
 in
 
 {
diff --git a/modules/home-manager/gitui.nix b/modules/home-manager/gitui.nix
index c8c7b751..e16a6bfd 100644
--- a/modules/home-manager/gitui.nix
+++ b/modules/home-manager/gitui.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.gitui;
 in
+
 {
   options.catppuccin.gitui = catppuccinLib.mkCatppuccinOption { name = "gitui"; };
 
@@ -21,7 +22,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.gitui.theme = builtins.path {
       name = "${cfg.flavor}.ron";
-      path = "${sources.gitui}/themes/catppuccin-${cfg.flavor}.ron";
+      path = "${sources.gitui}/catppuccin-${cfg.flavor}.ron";
     };
   };
 }
diff --git a/modules/home-manager/glamour.nix b/modules/home-manager/glamour.nix
index 6f8f959e..57f468da 100644
--- a/modules/home-manager/glamour.nix
+++ b/modules/home-manager/glamour.nix
@@ -21,7 +21,7 @@ in
 
   config = lib.mkIf cfg.enable {
     home.sessionVariables = {
-      GLAMOUR_STYLE = "${sources.glamour}/themes/catppuccin-${cfg.flavor}.json";
+      GLAMOUR_STYLE = "${sources.glamour}/catppuccin-${cfg.flavor}.json";
     };
   };
 }
diff --git a/modules/home-manager/gtk.nix b/modules/home-manager/gtk.nix
index 44910de7..5bfb4adf 100644
--- a/modules/home-manager/gtk.nix
+++ b/modules/home-manager/gtk.nix
@@ -1,8 +1,8 @@
 { catppuccinLib }:
 {
   config,
-  pkgs,
   lib,
+  pkgs,
   ...
 }:
 
@@ -157,7 +157,7 @@ in
           name =
             "catppuccin-${cfg.flavor}-${cfg.accent}-${cfg.size}"
             + lib.optionalString (cfg.tweaks != [ ]) gtkTweaks;
-          package = pkgs.catppuccin-gtk.override {
+          package = config.catppuccin.sources.gtk.override {
             inherit (cfg) size tweaks;
             accents = [ cfg.accent ];
             variant = cfg.flavor;
diff --git a/modules/home-manager/helix.nix b/modules/home-manager/helix.nix
index c840f099..c01d820b 100644
--- a/modules/home-manager/helix.nix
+++ b/modules/home-manager/helix.nix
@@ -46,7 +46,7 @@ in
       };
 
       themes."catppuccin-${cfg.flavor}" =
-        lib.importTOML "${sources.helix}/themes/${subdir}/catppuccin_${cfg.flavor}.toml";
+        lib.importTOML "${sources.helix}/${subdir}/catppuccin_${cfg.flavor}.toml";
     };
   };
 }
diff --git a/modules/home-manager/hyprland.nix b/modules/home-manager/hyprland.nix
index 7bc9690a..84deb8f5 100644
--- a/modules/home-manager/hyprland.nix
+++ b/modules/home-manager/hyprland.nix
@@ -38,7 +38,7 @@ in
     wayland.windowManager.hyprland = {
       settings = {
         source = [
-          "${sources.hyprland}/themes/${cfg.flavor}.conf"
+          "${sources.hyprland}/${cfg.flavor}.conf"
 
           # Define accents in file to ensure they appear before user vars
           (pkgs.writeText "hyprland-${cfg.accent}-accent.conf" ''
diff --git a/modules/home-manager/hyprlock.nix b/modules/home-manager/hyprlock.nix
index 447fdf5e..356a0df8 100644
--- a/modules/home-manager/hyprlock.nix
+++ b/modules/home-manager/hyprlock.nix
@@ -32,7 +32,7 @@ in
     programs.hyprlock = {
       settings = {
         source = [
-          "${sources.hyprland}/themes/${cfg.flavor}.conf"
+          "${sources.hyprland}/${cfg.flavor}.conf"
 
           # Define accents in file to ensure they appear before user vars
           (pkgs.writeText "hyprland-${cfg.accent}-accent.conf" ''
diff --git a/modules/home-manager/imv.nix b/modules/home-manager/imv.nix
index a8d2f88e..a2b9c0e1 100644
--- a/modules/home-manager/imv.nix
+++ b/modules/home-manager/imv.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.imv;
 in
+
 {
   options.catppuccin.imv = catppuccinLib.mkCatppuccinOption { name = "imv"; };
 
@@ -20,7 +21,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.imv = {
-      settings = catppuccinLib.importINI (sources.imv + "/themes/${cfg.flavor}.config");
+      settings = catppuccinLib.importINI (sources.imv + "/${cfg.flavor}.config");
     };
   };
 }
diff --git a/modules/home-manager/k9s.nix b/modules/home-manager/k9s.nix
index ac1de2af..67c4cd76 100644
--- a/modules/home-manager/k9s.nix
+++ b/modules/home-manager/k9s.nix
@@ -19,7 +19,7 @@ let
   themeName = "catppuccin-${cfg.flavor}" + lib.optionalString cfg.transparent "-transparent";
   themeFile = "${themeName}.yaml";
   themePath = "k9s/skins/${themeFile}";
-  theme = sources.k9s + "/dist/${themeFile}";
+  theme = sources.k9s + "/${themeFile}";
 in
 
 {
diff --git a/modules/home-manager/kitty.nix b/modules/home-manager/kitty.nix
index 523efcc7..430f2e2e 100644
--- a/modules/home-manager/kitty.nix
+++ b/modules/home-manager/kitty.nix
@@ -1,8 +1,10 @@
 { catppuccinLib }:
 { config, lib, ... }:
+
 let
   cfg = config.catppuccin.kitty;
 in
+
 {
   options.catppuccin.kitty = catppuccinLib.mkCatppuccinOption { name = "kitty"; };
 
diff --git a/modules/home-manager/kvantum.nix b/modules/home-manager/kvantum.nix
index c0006ceb..9a8de529 100644
--- a/modules/home-manager/kvantum.nix
+++ b/modules/home-manager/kvantum.nix
@@ -2,7 +2,6 @@
 {
   config,
   lib,
-  pkgs,
   ...
 }:
 
@@ -10,13 +9,9 @@ let
   cfg = config.catppuccin.kvantum;
   enable = cfg.enable && config.qt.enable;
 
-  theme = pkgs.catppuccin-kvantum.override {
-    inherit (cfg) accent;
-    variant = cfg.flavor;
-  };
-
   themeName = "catppuccin-${cfg.flavor}-${cfg.accent}";
 in
+
 {
   options.catppuccin.kvantum =
     catppuccinLib.mkCatppuccinOption {
@@ -76,7 +71,7 @@ in
     ];
 
     xdg.configFile = {
-      "Kvantum/${themeName}".source = "${theme}/share/Kvantum/${themeName}";
+      "Kvantum/${themeName}".source = "${config.catppuccin.sources.kvantum}/share/Kvantum/${themeName}";
       "Kvantum/kvantum.kvconfig" = lib.mkIf cfg.apply {
         text = ''
           [General]
diff --git a/modules/home-manager/lazygit.nix b/modules/home-manager/lazygit.nix
index 62abeebf..e9cbceeb 100644
--- a/modules/home-manager/lazygit.nix
+++ b/modules/home-manager/lazygit.nix
@@ -43,7 +43,7 @@ in
   config = lib.mkIf enable {
     home.sessionVariables = {
       # Ensure that the default config file is still sourced
-      LG_CONFIG_FILE = "${sources.lazygit}/themes-mergable/${cfg.flavor}/${cfg.accent}.yml,${configFile}";
+      LG_CONFIG_FILE = "${sources.lazygit}/${cfg.flavor}/${cfg.accent}.yml,${configFile}";
     };
   };
 }
diff --git a/modules/home-manager/mako.nix b/modules/home-manager/mako.nix
index 2cc5c5d4..36762d81 100644
--- a/modules/home-manager/mako.nix
+++ b/modules/home-manager/mako.nix
@@ -11,7 +11,7 @@ let
 
   cfg = config.catppuccin.mako;
   theme = catppuccinLib.importINI (
-    sources.mako + "/themes/catppuccin-${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}"
+    sources.mako + "/catppuccin-${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}"
   );
 
   # Settings that need to be extracted and put in extraConfig
diff --git a/modules/home-manager/micro.nix b/modules/home-manager/micro.nix
index dcf7b99c..285a8d4c 100644
--- a/modules/home-manager/micro.nix
+++ b/modules/home-manager/micro.nix
@@ -1,5 +1,6 @@
 { catppuccinLib }:
 { config, lib, ... }:
+
 let
   inherit (config.catppuccin) sources;
 
@@ -9,6 +10,7 @@ let
   themePath =
     "catppuccin-${cfg.flavor}" + lib.optionalString cfg.transparent "-transparent" + ".micro";
 in
+
 {
   options.catppuccin.micro = catppuccinLib.mkCatppuccinOption { name = "micro"; } // {
     transparent = lib.mkEnableOption "transparent version of flavor";
@@ -31,7 +33,7 @@ in
     };
 
     xdg.configFile = {
-      "micro/colorschemes/${themePath}".source = "${sources.micro}/src/${themePath}";
+      "micro/colorschemes/${themePath}".source = "${sources.micro}/${themePath}";
     };
   };
 }
diff --git a/modules/home-manager/mpv.nix b/modules/home-manager/mpv.nix
index cef2c051..32b9d8d1 100644
--- a/modules/home-manager/mpv.nix
+++ b/modules/home-manager/mpv.nix
@@ -26,7 +26,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.mpv = {
       config = {
-        include = sources.mpv + "/themes/${cfg.flavor}/${cfg.accent}.conf";
+        include = sources.mpv + "/${cfg.flavor}/${cfg.accent}.conf";
       };
     };
   };
diff --git a/modules/home-manager/neovim.nix b/modules/home-manager/neovim.nix
index 87b1bd75..390b8d80 100644
--- a/modules/home-manager/neovim.nix
+++ b/modules/home-manager/neovim.nix
@@ -1,7 +1,6 @@
 { catppuccinLib }:
 {
   config,
-  pkgs,
   lib,
   ...
 }:
@@ -24,9 +23,9 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.neovim = {
-      plugins = with pkgs.vimPlugins; [
+      plugins = [
         {
-          plugin = catppuccin-nvim;
+          plugin = config.catppuccin.sources.nvim;
           config = ''
             lua << EOF
               local compile_path = vim.fn.stdpath("cache") .. "/catppuccin-nvim"
diff --git a/modules/home-manager/newsboat.nix b/modules/home-manager/newsboat.nix
index 7092cae9..7b014c43 100644
--- a/modules/home-manager/newsboat.nix
+++ b/modules/home-manager/newsboat.nix
@@ -7,6 +7,7 @@ let
   cfg = config.catppuccin.newsboat;
   theme = if cfg.flavor == "latte" then "latte" else "dark";
 in
+
 {
   options.catppuccin.newsboat = catppuccinLib.mkCatppuccinOption { name = "newsboat"; };
 
@@ -21,7 +22,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.newsboat = {
-      extraConfig = lib.fileContents "${sources.newsboat}/themes/${theme}";
+      extraConfig = lib.fileContents "${sources.newsboat}/${theme}";
     };
   };
 }
diff --git a/modules/home-manager/obs.nix b/modules/home-manager/obs.nix
index 1b89b5ae..7f55c046 100644
--- a/modules/home-manager/obs.nix
+++ b/modules/home-manager/obs.nix
@@ -24,8 +24,8 @@ in
 
   config = lib.mkIf enable {
     xdg.configFile = {
-      "obs-studio/themes/Catppuccin.obt".source = "${sources.obs}/themes/Catppuccin.obt";
-      "obs-studio/themes/${themeName}".source = "${sources.obs}/themes/${themeName}";
+      "obs-studio/themes/Catppuccin.obt".source = "${sources.obs}/Catppuccin.obt";
+      "obs-studio/themes/${themeName}".source = "${sources.obs}/${themeName}";
     };
   };
 }
diff --git a/modules/home-manager/polybar.nix b/modules/home-manager/polybar.nix
index e3632e1f..87dd5ef2 100644
--- a/modules/home-manager/polybar.nix
+++ b/modules/home-manager/polybar.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.polybar;
 in
+
 {
   options.catppuccin.polybar = catppuccinLib.mkCatppuccinOption { name = "polybar"; };
 
@@ -20,7 +21,7 @@ in
 
   config = lib.mkIf cfg.enable {
     services.polybar = {
-      extraConfig = lib.fileContents "${sources.polybar}/themes/${cfg.flavor}.ini";
+      extraConfig = lib.fileContents "${sources.polybar}/${cfg.flavor}.ini";
     };
   };
 }
diff --git a/modules/home-manager/rio.nix b/modules/home-manager/rio.nix
index 415d4f14..f7f1508f 100644
--- a/modules/home-manager/rio.nix
+++ b/modules/home-manager/rio.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.rio;
 in
+
 {
   options.catppuccin.rio = catppuccinLib.mkCatppuccinOption { name = "rio"; };
 
@@ -20,7 +21,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.rio = {
-      settings = lib.importTOML "${sources.rio}/themes/catppuccin-${cfg.flavor}.toml";
+      settings = lib.importTOML "${sources.rio}/catppuccin-${cfg.flavor}.toml";
     };
   };
 }
diff --git a/modules/home-manager/rofi.nix b/modules/home-manager/rofi.nix
index c0170e90..d2ebb77e 100644
--- a/modules/home-manager/rofi.nix
+++ b/modules/home-manager/rofi.nix
@@ -5,8 +5,8 @@ let
   inherit (config.catppuccin) sources;
 
   cfg = config.catppuccin.rofi;
-  enable = cfg.enable && config.programs.rofi.enable;
 in
+
 {
   options.catppuccin.rofi = catppuccinLib.mkCatppuccinOption { name = "rofi"; };
 
@@ -24,7 +24,7 @@ in
       theme = {
         "@theme" = builtins.path {
           name = "catppuccin-${cfg.flavor}.rasi";
-          path = "${sources.rofi}/basic/.local/share/rofi/themes/catppuccin-${cfg.flavor}.rasi";
+          path = "${sources.rofi}/catppuccin-${cfg.flavor}.rasi";
         };
       };
     };
diff --git a/modules/home-manager/skim.nix b/modules/home-manager/skim.nix
index 818e5dcc..63345ffb 100644
--- a/modules/home-manager/skim.nix
+++ b/modules/home-manager/skim.nix
@@ -5,9 +5,9 @@ let
   inherit (config.catppuccin) sources;
 
   cfg = config.catppuccin.skim;
-  enable = cfg.enable && config.programs.skim.enable;
   palette = (lib.importJSON "${sources.palette}/palette.json").${cfg.flavor}.colors;
 in
+
 {
   options.catppuccin.skim = catppuccinLib.mkCatppuccinOption { name = "skim"; };
 
diff --git a/modules/home-manager/spotify-player.nix b/modules/home-manager/spotify-player.nix
index 1fb0620e..bd43c20b 100644
--- a/modules/home-manager/spotify-player.nix
+++ b/modules/home-manager/spotify-player.nix
@@ -5,8 +5,8 @@ let
   inherit (config.catppuccin) sources;
 
   cfg = config.catppuccin.spotify-player;
-  enable = cfg.enable && config.programs.spotify-player.enable;
 in
+
 {
   options.catppuccin.spotify-player = catppuccinLib.mkCatppuccinOption {
     name = "spotify-player";
diff --git a/modules/home-manager/starship.nix b/modules/home-manager/starship.nix
index 1362324b..36ed7ecc 100644
--- a/modules/home-manager/starship.nix
+++ b/modules/home-manager/starship.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.starship;
 in
+
 {
   options.catppuccin.starship = catppuccinLib.mkCatppuccinOption { name = "starship"; };
 
@@ -23,7 +24,7 @@ in
       settings = {
         format = lib.mkDefault "$all";
         palette = "catppuccin_${cfg.flavor}";
-      } // lib.importTOML "${sources.starship}/themes/${cfg.flavor}.toml";
+      } // lib.importTOML "${sources.starship}/${cfg.flavor}.toml";
     };
   };
 }
diff --git a/modules/home-manager/sway.nix b/modules/home-manager/sway.nix
index 757e7bed..969fc451 100644
--- a/modules/home-manager/sway.nix
+++ b/modules/home-manager/sway.nix
@@ -5,8 +5,9 @@ let
   inherit (config.catppuccin) sources;
 
   cfg = config.catppuccin.sway;
-  theme = "${sources.sway}/themes/catppuccin-${cfg.flavor}";
+  theme = "${sources.sway}/catppuccin-${cfg.flavor}";
 in
+
 {
   options.catppuccin.sway = catppuccinLib.mkCatppuccinOption { name = "sway"; };
 
diff --git a/modules/home-manager/swaylock.nix b/modules/home-manager/swaylock.nix
index 377c1896..288e4b24 100644
--- a/modules/home-manager/swaylock.nix
+++ b/modules/home-manager/swaylock.nix
@@ -1,9 +1,12 @@
 { catppuccinLib }:
 { config, lib, ... }:
+
 let
   inherit (config.catppuccin) sources;
+
   cfg = config.catppuccin.swaylock;
 in
+
 {
   options.catppuccin.swaylock = catppuccinLib.mkCatppuccinOption {
     name = "swaylock";
@@ -39,7 +42,7 @@ in
 
   config = lib.mkIf cfg.enable {
     programs.swaylock = {
-      settings = catppuccinLib.importINI (sources.swaylock + "/themes/${cfg.flavor}.conf");
+      settings = catppuccinLib.importINI (sources.swaylock + "/${cfg.flavor}.conf");
     };
   };
 }
diff --git a/modules/home-manager/tmux.nix b/modules/home-manager/tmux.nix
index d994c4c9..e3b592e5 100644
--- a/modules/home-manager/tmux.nix
+++ b/modules/home-manager/tmux.nix
@@ -2,22 +2,11 @@
 {
   config,
   lib,
-  pkgs,
   ...
 }:
 
 let
-  inherit (config.catppuccin) sources;
-
   cfg = config.catppuccin.tmux;
-
-  plugin =
-    # TODO @getchoo: upstream this in nixpkgs
-    pkgs.tmuxPlugins.mkTmuxPlugin {
-      pluginName = "catppuccin";
-      version = builtins.substring 0 7 sources.tmux.revision;
-      src = sources.tmux;
-    };
 in
 
 {
@@ -61,7 +50,7 @@ in
     programs.tmux = {
       plugins = [
         {
-          inherit plugin;
+          plugin = config.catppuccin.sources.tmux;
           extraConfig = lib.concatStrings [
             ''
               set -g @catppuccin_flavor '${cfg.flavor}'
diff --git a/modules/home-manager/tofi.nix b/modules/home-manager/tofi.nix
index 157bc220..d3ab6567 100644
--- a/modules/home-manager/tofi.nix
+++ b/modules/home-manager/tofi.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.tofi;
 in
+
 {
   options.catppuccin.tofi = catppuccinLib.mkCatppuccinOption { name = "tofi"; };
 
@@ -21,7 +22,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.tofi = {
       settings = {
-        include = sources.tofi + "/themes/catppuccin-${cfg.flavor}";
+        include = sources.tofi + "/catppuccin-${cfg.flavor}";
       };
     };
   };
diff --git a/modules/home-manager/waybar.nix b/modules/home-manager/waybar.nix
index db73b0b4..25818f3b 100644
--- a/modules/home-manager/waybar.nix
+++ b/modules/home-manager/waybar.nix
@@ -7,7 +7,7 @@ let
   cfg = config.catppuccin.waybar;
   enable = cfg.enable && config.programs.waybar.enable;
 
-  styleFile = "${sources.waybar}/themes/${cfg.flavor}.css";
+  styleFile = "${sources.waybar}/${cfg.flavor}.css";
 in
 
 {
diff --git a/modules/home-manager/yazi.nix b/modules/home-manager/yazi.nix
index e79fd5d0..0c285933 100644
--- a/modules/home-manager/yazi.nix
+++ b/modules/home-manager/yazi.nix
@@ -26,12 +26,12 @@ in
 
   config = lib.mkIf enable {
     programs.yazi = {
-      theme = lib.importTOML "${sources.yazi}/themes/${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}.toml";
+      theme = lib.importTOML "${sources.yazi}/${cfg.flavor}/catppuccin-${cfg.flavor}-${cfg.accent}.toml";
     };
 
     xdg.configFile = {
       "yazi/Catppuccin-${cfg.flavor}.tmTheme".source =
-        "${sources.bat}/themes/Catppuccin ${catppuccinLib.mkUpper cfg.flavor}.tmTheme";
+        "${sources.bat}/Catppuccin ${catppuccinLib.mkUpper cfg.flavor}.tmTheme";
     };
   };
 }
diff --git a/modules/home-manager/zathura.nix b/modules/home-manager/zathura.nix
index b01b3622..277f733a 100644
--- a/modules/home-manager/zathura.nix
+++ b/modules/home-manager/zathura.nix
@@ -6,6 +6,7 @@ let
 
   cfg = config.catppuccin.zathura;
 in
+
 {
   options.catppuccin.zathura = catppuccinLib.mkCatppuccinOption { name = "zathura"; };
 
@@ -21,7 +22,7 @@ in
   config = lib.mkIf cfg.enable {
     programs.zathura = {
       extraConfig = ''
-        include ${sources.zathura + "/src/catppuccin-${cfg.flavor}"}
+        include ${sources.zathura + "/catppuccin-${cfg.flavor}"}
       '';
     };
   };
diff --git a/modules/home-manager/zellij.nix b/modules/home-manager/zellij.nix
index 4c1e586b..7cf0d166 100644
--- a/modules/home-manager/zellij.nix
+++ b/modules/home-manager/zellij.nix
@@ -5,6 +5,7 @@ let
   cfg = config.catppuccin.zellij;
   themeName = "catppuccin-${cfg.flavor}";
 in
+
 {
   options.catppuccin.zellij = catppuccinLib.mkCatppuccinOption { name = "zellij"; };
 
diff --git a/modules/home-manager/zsh-syntax-highlighting.nix b/modules/home-manager/zsh-syntax-highlighting.nix
index 6ddc38d0..06a21b0c 100644
--- a/modules/home-manager/zsh-syntax-highlighting.nix
+++ b/modules/home-manager/zsh-syntax-highlighting.nix
@@ -65,7 +65,7 @@ in
     (lib.mkIf cfg.enable {
       programs.zsh = {
         initExtra = lib.mkBefore ''
-          source '${sources.zsh-syntax-highlighting}/themes/catppuccin_${cfg.flavor}-zsh-syntax-highlighting.zsh'
+          source '${sources.zsh-syntax-highlighting}/catppuccin_${cfg.flavor}-zsh-syntax-highlighting.zsh'
         '';
       };
     })
diff --git a/modules/nixos/fcitx5.nix b/modules/nixos/fcitx5.nix
index 3721ca6f..5e589937 100644
--- a/modules/nixos/fcitx5.nix
+++ b/modules/nixos/fcitx5.nix
@@ -1,20 +1,12 @@
 { catppuccinLib }:
 {
   config,
-  pkgs,
   lib,
   ...
 }:
 
 let
-  inherit (config.catppuccin) sources;
-
   cfg = config.catppuccin.fcitx5;
-
-  theme = pkgs.runCommand "catppuccin-fcitx5" { } ''
-    mkdir -p $out/share/fcitx5/themes/
-    cp -r ${sources.fcitx5}/src/catppuccin-${cfg.flavor}-${cfg.accent}/ $out/share/fcitx5/themes/
-  '';
 in
 
 {
@@ -36,7 +28,7 @@ in
 
   config = lib.mkIf cfg.enable {
     i18n.inputMethod.fcitx5 = {
-      addons = [ theme ];
+      addons = [ config.catppuccin.sources.fcitx5 ];
       settings.addons.classicui.globalSection.Theme = "catppuccin-${cfg.flavor}-${cfg.accent}";
     };
   };
diff --git a/modules/nixos/grub.nix b/modules/nixos/grub.nix
index f709d789..96aacf13 100644
--- a/modules/nixos/grub.nix
+++ b/modules/nixos/grub.nix
@@ -2,7 +2,6 @@
 {
   config,
   lib,
-  pkgs,
   ...
 }:
 
@@ -12,11 +11,9 @@ let
   cfg = config.catppuccin.grub;
 
   # TODO @getchoo: upstream this in nixpkgs maybe? idk if they have grub themes
-  theme = pkgs.runCommand "catppuccin-grub-theme" { } ''
-    mkdir -p "$out"
-    cp -r ${sources.grub}/src/catppuccin-${cfg.flavor}-grub-theme/* "$out"/
-  '';
+  theme = sources.grub + "/share/grub/themes/catppuccin-${cfg.flavor}-grub-theme";
 in
+
 {
   options.catppuccin.grub = catppuccinLib.mkCatppuccinOption { name = "grub"; };
 
diff --git a/modules/nixos/plymouth.nix b/modules/nixos/plymouth.nix
index 69cd1517..2b1625f6 100644
--- a/modules/nixos/plymouth.nix
+++ b/modules/nixos/plymouth.nix
@@ -1,13 +1,14 @@
 { catppuccinLib }:
 {
   config,
-  pkgs,
   lib,
   ...
 }:
+
 let
   cfg = config.catppuccin.plymouth;
 in
+
 {
   options.catppuccin.plymouth = catppuccinLib.mkCatppuccinOption { name = "plymouth"; };
 
@@ -23,7 +24,7 @@ in
   config = lib.mkIf cfg.enable {
     boot.plymouth = {
       theme = "catppuccin-${cfg.flavor}";
-      themePackages = [ (pkgs.catppuccin-plymouth.override { variant = cfg.flavor; }) ];
+      themePackages = [ config.catppuccin.sources.plymouth ];
     };
   };
 }
diff --git a/modules/nixos/sddm.nix b/modules/nixos/sddm.nix
index 4bcda3dc..535651d1 100644
--- a/modules/nixos/sddm.nix
+++ b/modules/nixos/sddm.nix
@@ -15,6 +15,7 @@ let
   cfg = config.catppuccin.sddm;
   enable = cfg.enable && config.services.displayManager.sddm.enable;
 in
+
 {
   options.catppuccin.sddm = catppuccinLib.mkCatppuccinOption { name = "sddm"; } // {
     font = mkOption {
@@ -158,9 +159,8 @@ in
     };
 
     environment.systemPackages = [
-      (pkgs.catppuccin-sddm.override {
+      (config.catppuccin.sources.sddm.override {
         inherit (cfg)
-          flavor
           font
           fontSize
           background
diff --git a/modules/nixos/tty.nix b/modules/nixos/tty.nix
index 5459f82b..ae3dea96 100644
--- a/modules/nixos/tty.nix
+++ b/modules/nixos/tty.nix
@@ -8,6 +8,7 @@ let
   enable = cfg.enable && config.console.enable;
   palette = (lib.importJSON "${sources.palette}/palette.json").${cfg.flavor}.colors;
 in
+
 {
   options.catppuccin.tty = catppuccinLib.mkCatppuccinOption { name = "console"; };
 

From f5c4240fabed374ce0fd604c7c1187c547364acb Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:21:43 -0500
Subject: [PATCH 10/20] docs: update 'adding a port' guide

---
 CONTRIBUTING.md | 12 +++++++-----
 1 file changed, 7 insertions(+), 5 deletions(-)

diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 7ccfe7b3..ddcb8886 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -9,14 +9,16 @@ default to `config.catppuccin.flavor` and `config.catppuccin.accent`, respective
 When you're done, make sure to add your new file to the list in
 `modules/<module>/all-modules.nix`
 
-[npins](https://github.com/andir/npins) is used to track our upstream
-sources to use in modules. This allows us to easily access and auto-update all themes.
-You can add a new repository using a script in our subflake
+Package can be auto-generated from our our upstream sources to use in modules.
+This allows us to easily access, build, and auto-update all themes reliably
+across systems. You can add a new port to this collection using a script in the
+`pkgs/` folder
 
 ```bash
-nix run ./dev#add-source -- port_name branch_if_not_main
+./pkgs/paws.py port_name
 ```
-Alternatively, you can run `npins add github --directory .sources` manually
+Alternatively -- or if your port requires a build step -- you can make your own
+expression with `buildCatppuccinPort`.
 
 After creating your module, add the options to enable it in `test.nix` under the
 `nodes.machine` attrset. This will allow for your configuration to be tested along

From e4092bf99a28eb0280a71b21894a4a85e6703584 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Sat, 23 Nov 2024 18:11:58 -0500
Subject: [PATCH 11/20] chore: set nixfmt as formatter in root flake

---
 flake.nix | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/flake.nix b/flake.nix
index 08b6771e..d19a3518 100644
--- a/flake.nix
+++ b/flake.nix
@@ -50,6 +50,8 @@
           pkgs = nixpkgs.legacyPackages.${system};
         in
         {
+          formatter = pkgs.nixfmt-rfc-style;
+
           packages =
             let
               catppuccinPackages = (import ./default.nix { inherit pkgs; }).packages;

From 0d0905c77dd701d971ea7deaec60761b4bcb664d Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:28:48 -0500
Subject: [PATCH 12/20] chore: add dev shell

---
 default.nix |  2 ++
 flake.nix   |  2 ++
 shell.nix   | 30 ++++++++++++++++++++++++++++++
 3 files changed, 34 insertions(+)
 create mode 100644 shell.nix

diff --git a/default.nix b/default.nix
index d92c755f..f76cb8ba 100644
--- a/default.nix
+++ b/default.nix
@@ -46,4 +46,6 @@ in
     in
     isFunction || (!broken) && availableOnHost || isCross
   )) catppuccinPackages;
+
+  shell = import ./shell.nix { inherit pkgs; };
 }
diff --git a/flake.nix b/flake.nix
index d19a3518..0ac148ac 100644
--- a/flake.nix
+++ b/flake.nix
@@ -50,6 +50,8 @@
           pkgs = nixpkgs.legacyPackages.${system};
         in
         {
+          devShells.default = import ./shell.nix { inherit pkgs; };
+
           formatter = pkgs.nixfmt-rfc-style;
 
           packages =
diff --git a/shell.nix b/shell.nix
new file mode 100644
index 00000000..9eb93c30
--- /dev/null
+++ b/shell.nix
@@ -0,0 +1,30 @@
+{
+  pkgs ? import <nixpkgs> {
+    inherit system;
+    config = { };
+    overlays = [ ];
+  },
+  system ? builtins.currentSystem,
+}:
+
+pkgs.mkShellNoCC {
+  packages = [
+    # GHA lints
+    pkgs.actionlint
+
+    # Nix tools
+    pkgs.deadnix
+    pkgs.nixfmt-rfc-style
+    pkgs.nil
+    pkgs.statix
+
+    # Python tools
+    pkgs.pyright
+    pkgs.ruff
+    pkgs.ruff-lsp
+  ];
+
+  shellHook = ''
+    echo "Welcome to the catppuccin/nix repository! Thanks for contributing and have a wonderful day 🐈"
+  '';
+}

From 4715711403e727a0308299f52a00b891ada95b98 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Sat, 23 Nov 2024 18:15:32 -0500
Subject: [PATCH 13/20] ci: use renovate to update flake.lock

---
 .github/workflows/update-locks.yml | 31 ------------------------------
 renovate.json                      |  5 ++++-
 2 files changed, 4 insertions(+), 32 deletions(-)
 delete mode 100644 .github/workflows/update-locks.yml

diff --git a/.github/workflows/update-locks.yml b/.github/workflows/update-locks.yml
deleted file mode 100644
index 4538e663..00000000
--- a/.github/workflows/update-locks.yml
+++ /dev/null
@@ -1,31 +0,0 @@
-name: Update lockfiles
-
-on:
-  schedule:
-    # run every friday
-    - cron: "0 0 * * 5"
-  workflow_dispatch:
-
-jobs:
-  flake:
-    name: Update flake.lock
-
-    runs-on: ubuntu-latest
-
-    permissions:
-      contents: write
-      pull-requests: write
-
-    steps:
-      - name: Checkout repository
-        uses: actions/checkout@v4
-
-      - name: Install Nix
-        uses: cachix/install-nix-action@V27
-
-      - uses: DeterminateSystems/update-flake-lock@v24
-        with:
-          path-to-flake-dir: "./dev"
-          commit-msg: "chore: update dev flake inputs"
-          pr-title: "chore: update dev flake inputs"
-          token: ${{ github.token }}
diff --git a/renovate.json b/renovate.json
index 4a5b484a..7346f7a4 100644
--- a/renovate.json
+++ b/renovate.json
@@ -3,5 +3,8 @@
   "extends": [
     "config:recommended",
     "schedule:weekly"
-  ]
+  ],
+  "nix": {
+    "enabled": true,
+  }
 }

From c38ee81d85e630f31ccc9a05d19dcac60985abc7 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Thu, 28 Nov 2024 23:59:08 -0500
Subject: [PATCH 14/20] refactor: merge subflake back into main flake
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

this is annoying to maintain

• Added input 'catppuccin-v1_1':
    'https://api.flakehub.com/f/pinned/catppuccin/nix/1.1.1/0193bdc0-b045-7eed-bbec-95611a8ecdf5/source.tar.gz?narHash=sha256-pCWJgwo77KD7EJpwynwKrWPZ//dwypHq2TfdzZWqK68%3D' (2024-12-13)
• Added input 'catppuccin-v1_2':
    'https://api.flakehub.com/f/pinned/catppuccin/nix/1.2.0/0193e5e0-33b7-7149-a362-bfe56b20f64e/source.tar.gz?narHash=sha256-Let3uJo4YDyfqbqaw66dpZxhJB2TrDyZWSFd5rpPLJA%3D' (2024-12-20)
• Added input 'home-manager':
    'github:nix-community/home-manager/1395379a7a36e40f2a76e7b9936cc52950baa1be?narHash=sha256-OOfI0XhSJGHblfdNDhfnn8QnZxng63rWk9eeJ2tCbiI%3D' (2024-12-19)
• Added input 'home-manager/nixpkgs':
    follows 'nixpkgs'
• Added input 'home-manager-stable':
    'github:nix-community/home-manager/80b0fdf483c5d1cb75aaad909bd390d48673857f?narHash=sha256-vykpJ1xsdkv0j8WOVXrRFHUAdp9NXHpxdnn1F4pYgSw%3D' (2024-12-16)
• Added input 'home-manager-stable/nixpkgs':
    follows 'nixpkgs-stable'
• Updated input 'nixpkgs':
    'github:NixOS/nixpkgs/23e89b7da85c3640bbc2173fe04f4bd114342367?narHash=sha256-y/MEyuJ5oBWrWAic/14LaIr/u5E0wRVzyYsouYY3W6w%3D' (2024-11-19)
  → 'github:NixOS/nixpkgs/d3c42f187194c26d9f0309a8ecc469d6c878ce33?narHash=sha256-cHar1vqHOOyC7f1%2BtVycPoWTfKIaqkoe1Q6TnKzuti4%3D' (2024-12-17)
• Added input 'nixpkgs-stable':
    'github:NixOS/nixpkgs/b47fd6fa00c6afca88b8ee46cfdb00e104f50bca?narHash=sha256-nbG9TijTMcfr%2Bau7ZVbKpAhMJzzE2nQBYmRvSdXUD8g%3D' (2024-12-19)
• Added input 'nuscht-search':
    'github:NuschtOS/search/3051be7f403bff1d1d380e4612f0c70675b44fc9?narHash=sha256-Y47y%2BLesOCkJaLvj%2BdI/Oa6FAKj/T9sKVKDXLNsViPw%3D' (2024-12-09)
• Added input 'nuscht-search/flake-utils':
    'github:numtide/flake-utils/11707dc2f618dd54ca8739b309ec4fc024de578b?narHash=sha256-l0KFg5HjrsfsO/JpG%2Br7fRrqm12kzFHyUHqHCVpMMbI%3D' (2024-11-13)
• Added input 'nuscht-search/flake-utils/systems':
    'github:nix-systems/default/da67096a3b9bf56a91d16901293e51ba5b49a27e?narHash=sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768%3D' (2023-04-09)
• Added input 'nuscht-search/ixx':
    'github:NuschtOS/ixx/9fd01aad037f345350eab2cd45e1946cc66da4eb?narHash=sha256-EiOq8jF4Z/zQe0QYVc3%2BqSKxRK//CFHMB84aYrYGwEs%3D' (2024-10-26)
• Added input 'nuscht-search/ixx/flake-utils':
    follows 'nuscht-search/flake-utils'
• Added input 'nuscht-search/ixx/nixpkgs':
    follows 'nuscht-search/nixpkgs'
• Added input 'nuscht-search/nixpkgs':
    follows 'nixpkgs'
---
 .github/workflows/ci.yml      |   8 +-
 .github/workflows/website.yml |   2 +-
 dev/flake.lock                | 218 ----------------------------------
 dev/flake.nix                 | 198 ------------------------------
 docs/package.nix              |  93 +++++++++++++++
 flake.lock                    | 180 +++++++++++++++++++++++++++-
 flake.nix                     | 145 ++++++++++++++++++++--
 7 files changed, 406 insertions(+), 438 deletions(-)
 delete mode 100644 dev/flake.lock
 delete mode 100644 dev/flake.nix
 create mode 100644 docs/package.nix

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 35ce7a9a..d6127f44 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -41,9 +41,7 @@ jobs:
 
       - name: Format changes
         run: |
-          nix run \
-            --inputs-from ./dev \
-            'nixpkgs#nixfmt-rfc-style' -- .
+          nix fmt
 
       - name: Commit changes
         run: |
@@ -75,7 +73,7 @@ jobs:
       - name: Run tests
         run: |
           nix run \
-            --inputs-from ./dev \
+            --inputs-from . \
             github:Mic92/nix-fast-build -- \
             --no-nom \
-            --flake "./dev#checks.$(nix eval --raw --impure --expr builtins.currentSystem)"
+            --flake ".#checks.$(nix eval --raw --impure --expr builtins.currentSystem)"
diff --git a/.github/workflows/website.yml b/.github/workflows/website.yml
index 8805c4ea..5586ade6 100644
--- a/.github/workflows/website.yml
+++ b/.github/workflows/website.yml
@@ -37,7 +37,7 @@ jobs:
           nix build \
             --print-build-logs \
             --show-trace \
-            './dev#site'
+            '.#site'
 
       - name: Get artifact directory
         id: find-path
diff --git a/dev/flake.lock b/dev/flake.lock
deleted file mode 100644
index cea48d79..00000000
--- a/dev/flake.lock
+++ /dev/null
@@ -1,218 +0,0 @@
-{
-  "nodes": {
-    "catppuccin-rolling": {
-      "locked": {
-        "lastModified": 1734601205,
-        "narHash": "sha256-TzJewMe7yoVPUOMM6Mi0ptN6dTwSe9tY1UJKUM6rxpE=",
-        "owner": "catppuccin",
-        "repo": "nix",
-        "rev": "dcc1cbe936d053efca73483cfca81a35d2318c6b",
-        "type": "github"
-      },
-      "original": {
-        "owner": "catppuccin",
-        "repo": "nix",
-        "type": "github"
-      }
-    },
-    "catppuccin-v1_1": {
-      "locked": {
-        "lastModified": 1734055249,
-        "narHash": "sha256-pCWJgwo77KD7EJpwynwKrWPZ//dwypHq2TfdzZWqK68=",
-        "rev": "7221d6ca17ac36ed20588e1c3a80177ac5843fa7",
-        "revCount": 326,
-        "type": "tarball",
-        "url": "https://api.flakehub.com/f/pinned/catppuccin/nix/1.1.1/0193bdc0-b045-7eed-bbec-95611a8ecdf5/source.tar.gz"
-      },
-      "original": {
-        "type": "tarball",
-        "url": "https://flakehub.com/f/catppuccin/nix/1.1.%2A.tar.gz"
-      }
-    },
-    "catppuccin-v1_2": {
-      "locked": {
-        "lastModified": 1734728407,
-        "narHash": "sha256-Let3uJo4YDyfqbqaw66dpZxhJB2TrDyZWSFd5rpPLJA=",
-        "rev": "23ee86dbf4ed347878115a78971d43025362fab1",
-        "revCount": 341,
-        "type": "tarball",
-        "url": "https://api.flakehub.com/f/pinned/catppuccin/nix/1.2.0/0193e5e0-33b7-7149-a362-bfe56b20f64e/source.tar.gz"
-      },
-      "original": {
-        "type": "tarball",
-        "url": "https://flakehub.com/f/catppuccin/nix/1.2.%2A.tar.gz"
-      }
-    },
-    "flake-utils": {
-      "inputs": {
-        "systems": "systems"
-      },
-      "locked": {
-        "lastModified": 1731533236,
-        "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=",
-        "owner": "numtide",
-        "repo": "flake-utils",
-        "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b",
-        "type": "github"
-      },
-      "original": {
-        "owner": "numtide",
-        "repo": "flake-utils",
-        "type": "github"
-      }
-    },
-    "home-manager": {
-      "inputs": {
-        "nixpkgs": [
-          "nixpkgs"
-        ]
-      },
-      "locked": {
-        "lastModified": 1734043726,
-        "narHash": "sha256-e9YAMReFV1fDPcZLFC2pa4k/8TloSXeX0z2VysNMAoA=",
-        "owner": "nix-community",
-        "repo": "home-manager",
-        "rev": "3066cc58f552421a2c5414e78407fa5603405b1e",
-        "type": "github"
-      },
-      "original": {
-        "owner": "nix-community",
-        "repo": "home-manager",
-        "type": "github"
-      }
-    },
-    "home-manager-stable": {
-      "inputs": {
-        "nixpkgs": [
-          "nixpkgs-stable"
-        ]
-      },
-      "locked": {
-        "lastModified": 1733951536,
-        "narHash": "sha256-Zb5ZCa7Xj+0gy5XVXINTSr71fCfAv+IKtmIXNrykT54=",
-        "owner": "nix-community",
-        "repo": "home-manager",
-        "rev": "1318c3f3b068cdcea922fa7c1a0a1f0c96c22f5f",
-        "type": "github"
-      },
-      "original": {
-        "owner": "nix-community",
-        "ref": "release-24.11",
-        "repo": "home-manager",
-        "type": "github"
-      }
-    },
-    "ixx": {
-      "inputs": {
-        "flake-utils": [
-          "nuscht-search",
-          "flake-utils"
-        ],
-        "nixpkgs": [
-          "nuscht-search",
-          "nixpkgs"
-        ]
-      },
-      "locked": {
-        "lastModified": 1729958008,
-        "narHash": "sha256-EiOq8jF4Z/zQe0QYVc3+qSKxRK//CFHMB84aYrYGwEs=",
-        "owner": "NuschtOS",
-        "repo": "ixx",
-        "rev": "9fd01aad037f345350eab2cd45e1946cc66da4eb",
-        "type": "github"
-      },
-      "original": {
-        "owner": "NuschtOS",
-        "ref": "v0.0.6",
-        "repo": "ixx",
-        "type": "github"
-      }
-    },
-    "nixpkgs": {
-      "locked": {
-        "lastModified": 1733759999,
-        "narHash": "sha256-463SNPWmz46iLzJKRzO3Q2b0Aurff3U1n0nYItxq7jU=",
-        "owner": "NixOS",
-        "repo": "nixpkgs",
-        "rev": "a73246e2eef4c6ed172979932bc80e1404ba2d56",
-        "type": "github"
-      },
-      "original": {
-        "owner": "NixOS",
-        "ref": "nixos-unstable",
-        "repo": "nixpkgs",
-        "type": "github"
-      }
-    },
-    "nixpkgs-stable": {
-      "locked": {
-        "lastModified": 1733808091,
-        "narHash": "sha256-KWwINTQelKOoQgrXftxoqxmKFZb9pLVfnRvK270nkVk=",
-        "owner": "NixOS",
-        "repo": "nixpkgs",
-        "rev": "a0f3e10d94359665dba45b71b4227b0aeb851f8e",
-        "type": "github"
-      },
-      "original": {
-        "owner": "NixOS",
-        "ref": "nixos-24.11",
-        "repo": "nixpkgs",
-        "type": "github"
-      }
-    },
-    "nuscht-search": {
-      "inputs": {
-        "flake-utils": [
-          "flake-utils"
-        ],
-        "ixx": "ixx",
-        "nixpkgs": [
-          "nixpkgs"
-        ]
-      },
-      "locked": {
-        "lastModified": 1733773348,
-        "narHash": "sha256-Y47y+LesOCkJaLvj+dI/Oa6FAKj/T9sKVKDXLNsViPw=",
-        "owner": "NuschtOS",
-        "repo": "search",
-        "rev": "3051be7f403bff1d1d380e4612f0c70675b44fc9",
-        "type": "github"
-      },
-      "original": {
-        "owner": "NuschtOS",
-        "repo": "search",
-        "type": "github"
-      }
-    },
-    "root": {
-      "inputs": {
-        "catppuccin-rolling": "catppuccin-rolling",
-        "catppuccin-v1_1": "catppuccin-v1_1",
-        "catppuccin-v1_2": "catppuccin-v1_2",
-        "flake-utils": "flake-utils",
-        "home-manager": "home-manager",
-        "home-manager-stable": "home-manager-stable",
-        "nixpkgs": "nixpkgs",
-        "nixpkgs-stable": "nixpkgs-stable",
-        "nuscht-search": "nuscht-search"
-      }
-    },
-    "systems": {
-      "locked": {
-        "lastModified": 1681028828,
-        "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
-        "owner": "nix-systems",
-        "repo": "default",
-        "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
-        "type": "github"
-      },
-      "original": {
-        "owner": "nix-systems",
-        "repo": "default",
-        "type": "github"
-      }
-    }
-  },
-  "root": "root",
-  "version": 7
-}
diff --git a/dev/flake.nix b/dev/flake.nix
deleted file mode 100644
index 771c978f..00000000
--- a/dev/flake.nix
+++ /dev/null
@@ -1,198 +0,0 @@
-{
-  description = "Soothing pastel theme for Nix";
-
-  inputs = {
-    nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
-
-    # NOTE: This is only to deduplicate inputs
-    flake-utils = {
-      url = "github:numtide/flake-utils";
-    };
-
-    nuscht-search = {
-      url = "github:NuschtOS/search";
-      inputs = {
-        nixpkgs.follows = "nixpkgs";
-        flake-utils.follows = "flake-utils";
-      };
-    };
-
-    catppuccin-rolling = {
-      url = "github:catppuccin/nix";
-    };
-
-    catppuccin-v1_1 = {
-      url = "https://flakehub.com/f/catppuccin/nix/1.1.*.tar.gz";
-    };
-
-    catppuccin-v1_2 = {
-      url = "https://flakehub.com/f/catppuccin/nix/1.2.*.tar.gz";
-    };
-
-    nixpkgs-stable.url = "github:NixOS/nixpkgs/nixos-24.11";
-
-    home-manager = {
-      url = "github:nix-community/home-manager";
-      inputs.nixpkgs.follows = "nixpkgs";
-    };
-
-    home-manager-stable = {
-      url = "github:nix-community/home-manager/release-24.11";
-      inputs.nixpkgs.follows = "nixpkgs-stable";
-    };
-  };
-
-  outputs =
-    {
-      self,
-      nuscht-search,
-      nixpkgs,
-      nixpkgs-stable,
-      home-manager,
-      home-manager-stable,
-      ...
-    }@inputs:
-
-    let
-      inherit (nixpkgs) lib;
-      systems = [
-        "x86_64-linux"
-        "aarch64-linux"
-        "x86_64-darwin"
-        "aarch64-darwin"
-      ];
-
-      nixpkgsFor = nixpkgs.lib.genAttrs systems (system: {
-        unstable = nixpkgs.legacyPackages.${system};
-        stable = nixpkgs-stable.legacyPackages.${system};
-      });
-
-      forAllSystems = nixpkgs.lib.genAttrs systems;
-
-      # Versions of the modules we want to index in our search
-      searchVersions =
-        map
-          (versionName: {
-            inherit versionName;
-            catppuccin = inputs."catppuccin-${lib.replaceStrings [ "." ] [ "_" ] versionName}";
-          })
-          [
-            "v1.1"
-            "v1.2"
-            "rolling"
-          ];
-
-      # And the latest stable from that
-      latestStableVersion =
-        let
-          latest = lib.foldl' (
-            latest:
-            { versionName, ... }:
-            if (versionName != "rolling" && lib.versionOlder latest (lib.removePrefix "v" versionName)) then
-              versionName
-            else
-              latest
-          ) "0" searchVersions;
-        in
-        assert lib.assertMsg (latest != "0") "Unable to determine latest stable version!";
-        latest;
-    in
-
-    {
-      apps = forAllSystems (system: {
-        serve = {
-          type = "app";
-          program = lib.getExe self.packages.${system}.site.serve;
-        };
-      });
-
-      checks = forAllSystems (
-        system:
-
-        let
-          pkgs = nixpkgsFor.${system};
-
-          callUnstable = lib.flip pkgs.unstable.callPackage { inherit home-manager; };
-          callStable = lib.flip pkgs.stable.callPackage { home-manager = home-manager-stable; };
-        in
-
-        lib.optionalAttrs pkgs.unstable.stdenv.hostPlatform.isDarwin {
-          darwin-test-unstable = callUnstable ../tests/darwin.nix;
-          darwin-test-stable = callStable ../tests/darwin.nix;
-        }
-        // lib.optionalAttrs pkgs.unstable.stdenv.hostPlatform.isLinux {
-          nixos-test-unstable = callUnstable ../tests/nixos.nix;
-          nixos-test-stable = callStable ../tests/nixos.nix;
-        }
-      );
-
-      formatter = forAllSystems (system: nixpkgsFor.${system}.unstable.nixfmt-rfc-style);
-
-      packages = forAllSystems (
-        system:
-
-        let
-          pkgs = nixpkgsFor.${system}.unstable;
-
-          mkSite = pkgs.callPackage ../docs/mk-site.nix { };
-          mkSearchInstance = pkgs.callPackage ../docs/mk-search.nix {
-            inherit (nuscht-search.packages.${system}) mkMultiSearch;
-          };
-
-          search-instances = lib.listToAttrs (
-            map (
-              { catppuccin, versionName }:
-              {
-                name = versionName;
-                value = mkSearchInstance { inherit catppuccin versionName; };
-              }
-            ) searchVersions
-          );
-
-          redirectTo =
-            endpoint:
-            pkgs.writeText "index.html" ''
-              <meta http-equiv="refresh" content="0;url=${endpoint}">
-            '';
-        in
-
-        search-instances
-        // {
-          site = mkSite {
-            pname = "catppuccin-nix-site";
-            version = self.shortRev or self.dirtyShortRev or "unknown";
-
-            src = ../docs;
-
-            postPatch = "ln -sf ${inputs.catppuccin-rolling + "/CHANGELOG.md"} src/NEWS.md";
-
-            postInstall = ''
-              ln -sf ${
-                pkgs.linkFarm "search-engines" (
-                  [
-                    {
-                      name = "stable.html";
-                      path = redirectTo "/search/${latestStableVersion}/";
-                    }
-                    {
-                      name = "index.html";
-                      path = redirectTo "/search/stable.html";
-                    }
-                  ]
-                  ++ map (
-                    { versionName, ... }:
-                    {
-                      name = versionName;
-                      path = search-instances.${versionName};
-                    }
-                  ) searchVersions
-                )
-              } $out/search
-            '';
-          };
-
-          default = self.packages.${system}.site;
-        }
-      );
-    };
-}
diff --git a/docs/package.nix b/docs/package.nix
new file mode 100644
index 00000000..4f98341c
--- /dev/null
+++ b/docs/package.nix
@@ -0,0 +1,93 @@
+{
+  lib,
+  callPackage,
+  linkFarm,
+  writeText,
+
+  nuscht-search,
+  inputs,
+  /*
+    Should be in the format of
+
+    ```
+    {
+      <version name> = <flake input>;
+    }
+    ```
+
+    i.e.,
+
+    ```
+    {
+      "v1.1" = catppuccin_v1_1;
+      "rolling" = self;
+    }
+  */
+  searchVersions ? null,
+}:
+
+assert lib.assertMsg (
+  searchVersions != null
+) "./docs/package.nix: `searchVersions` must be provided";
+
+let
+  inherit (inputs) self;
+
+  mkSite = callPackage ./mk-site.nix { };
+  mkSearchInstance = callPackage ./mk-search.nix {
+    inherit (nuscht-search) mkMultiSearch;
+  };
+
+  # Collect the latest stable version from the `searchVersions` given
+  latestStableVersion =
+    let
+      latest = lib.foldl' (
+        latest: versionName:
+        if (versionName != "rolling" && lib.versionOlder latest (lib.removePrefix "v" versionName)) then
+          versionName
+        else
+          latest
+      ) "0" (lib.attrNames searchVersions);
+    in
+    assert lib.assertMsg (latest != "0") "Unable to determine latest stable version!";
+    latest;
+
+  # Then create a search instance for each one
+  searchInstances = lib.mapAttrs (
+    versionName: catppuccin: mkSearchInstance { inherit catppuccin versionName; }
+  ) searchVersions;
+
+  # Create an html page for redirecting to a given endpoint
+  redirectTo =
+    endpoint:
+    writeText "index.html" ''
+      <meta http-equiv="refresh" content="0;url=${endpoint}">
+    '';
+in
+
+mkSite {
+  pname = "catppuccin-nix-site";
+  version = self.shortRev or self.dirtyShortRev or "unknown";
+
+  src = self + "/docs";
+
+  postPatch = "ln -sf ${self + "/CHANGELOG.md"} src/NEWS.md";
+
+  postInstall = ''
+    ln -sf ${
+      linkFarm "search-engines" (
+        [
+          {
+            name = "stable.html";
+            path = redirectTo "/search/${latestStableVersion}/";
+          }
+          {
+            name = "index.html";
+            path = redirectTo "/search/stable.html";
+          }
+        ]
+        ++ lib.mapAttrsToList (name: path: { inherit name path; }) searchInstances
+      )
+    } $out/search
+  '';
+}
diff --git a/flake.lock b/flake.lock
index d98d6b86..95ff8c77 100644
--- a/flake.lock
+++ b/flake.lock
@@ -1,12 +1,125 @@
 {
   "nodes": {
+    "catppuccin-v1_1": {
+      "locked": {
+        "lastModified": 1734055249,
+        "narHash": "sha256-pCWJgwo77KD7EJpwynwKrWPZ//dwypHq2TfdzZWqK68=",
+        "rev": "7221d6ca17ac36ed20588e1c3a80177ac5843fa7",
+        "revCount": 326,
+        "type": "tarball",
+        "url": "https://api.flakehub.com/f/pinned/catppuccin/nix/1.1.1/0193bdc0-b045-7eed-bbec-95611a8ecdf5/source.tar.gz"
+      },
+      "original": {
+        "type": "tarball",
+        "url": "https://flakehub.com/f/catppuccin/nix/1.1.%2A.tar.gz"
+      }
+    },
+    "catppuccin-v1_2": {
+      "locked": {
+        "lastModified": 1734728407,
+        "narHash": "sha256-Let3uJo4YDyfqbqaw66dpZxhJB2TrDyZWSFd5rpPLJA=",
+        "rev": "23ee86dbf4ed347878115a78971d43025362fab1",
+        "revCount": 341,
+        "type": "tarball",
+        "url": "https://api.flakehub.com/f/pinned/catppuccin/nix/1.2.0/0193e5e0-33b7-7149-a362-bfe56b20f64e/source.tar.gz"
+      },
+      "original": {
+        "type": "tarball",
+        "url": "https://flakehub.com/f/catppuccin/nix/1.2.%2A.tar.gz"
+      }
+    },
+    "flake-utils": {
+      "inputs": {
+        "systems": "systems"
+      },
+      "locked": {
+        "lastModified": 1731533236,
+        "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=",
+        "owner": "numtide",
+        "repo": "flake-utils",
+        "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b",
+        "type": "github"
+      },
+      "original": {
+        "owner": "numtide",
+        "repo": "flake-utils",
+        "type": "github"
+      }
+    },
+    "home-manager": {
+      "inputs": {
+        "nixpkgs": [
+          "nixpkgs"
+        ]
+      },
+      "locked": {
+        "lastModified": 1734622215,
+        "narHash": "sha256-OOfI0XhSJGHblfdNDhfnn8QnZxng63rWk9eeJ2tCbiI=",
+        "owner": "nix-community",
+        "repo": "home-manager",
+        "rev": "1395379a7a36e40f2a76e7b9936cc52950baa1be",
+        "type": "github"
+      },
+      "original": {
+        "owner": "nix-community",
+        "repo": "home-manager",
+        "type": "github"
+      }
+    },
+    "home-manager-stable": {
+      "inputs": {
+        "nixpkgs": [
+          "nixpkgs-stable"
+        ]
+      },
+      "locked": {
+        "lastModified": 1734366194,
+        "narHash": "sha256-vykpJ1xsdkv0j8WOVXrRFHUAdp9NXHpxdnn1F4pYgSw=",
+        "owner": "nix-community",
+        "repo": "home-manager",
+        "rev": "80b0fdf483c5d1cb75aaad909bd390d48673857f",
+        "type": "github"
+      },
+      "original": {
+        "owner": "nix-community",
+        "ref": "release-24.11",
+        "repo": "home-manager",
+        "type": "github"
+      }
+    },
+    "ixx": {
+      "inputs": {
+        "flake-utils": [
+          "nuscht-search",
+          "flake-utils"
+        ],
+        "nixpkgs": [
+          "nuscht-search",
+          "nixpkgs"
+        ]
+      },
+      "locked": {
+        "lastModified": 1729958008,
+        "narHash": "sha256-EiOq8jF4Z/zQe0QYVc3+qSKxRK//CFHMB84aYrYGwEs=",
+        "owner": "NuschtOS",
+        "repo": "ixx",
+        "rev": "9fd01aad037f345350eab2cd45e1946cc66da4eb",
+        "type": "github"
+      },
+      "original": {
+        "owner": "NuschtOS",
+        "ref": "v0.0.6",
+        "repo": "ixx",
+        "type": "github"
+      }
+    },
     "nixpkgs": {
       "locked": {
-        "lastModified": 1732014248,
-        "narHash": "sha256-y/MEyuJ5oBWrWAic/14LaIr/u5E0wRVzyYsouYY3W6w=",
+        "lastModified": 1734424634,
+        "narHash": "sha256-cHar1vqHOOyC7f1+tVycPoWTfKIaqkoe1Q6TnKzuti4=",
         "owner": "NixOS",
         "repo": "nixpkgs",
-        "rev": "23e89b7da85c3640bbc2173fe04f4bd114342367",
+        "rev": "d3c42f187194c26d9f0309a8ecc469d6c878ce33",
         "type": "github"
       },
       "original": {
@@ -16,9 +129,68 @@
         "type": "github"
       }
     },
+    "nixpkgs-stable": {
+      "locked": {
+        "lastModified": 1734600368,
+        "narHash": "sha256-nbG9TijTMcfr+au7ZVbKpAhMJzzE2nQBYmRvSdXUD8g=",
+        "owner": "NixOS",
+        "repo": "nixpkgs",
+        "rev": "b47fd6fa00c6afca88b8ee46cfdb00e104f50bca",
+        "type": "github"
+      },
+      "original": {
+        "owner": "NixOS",
+        "ref": "nixos-24.11",
+        "repo": "nixpkgs",
+        "type": "github"
+      }
+    },
+    "nuscht-search": {
+      "inputs": {
+        "flake-utils": "flake-utils",
+        "ixx": "ixx",
+        "nixpkgs": [
+          "nixpkgs"
+        ]
+      },
+      "locked": {
+        "lastModified": 1733773348,
+        "narHash": "sha256-Y47y+LesOCkJaLvj+dI/Oa6FAKj/T9sKVKDXLNsViPw=",
+        "owner": "NuschtOS",
+        "repo": "search",
+        "rev": "3051be7f403bff1d1d380e4612f0c70675b44fc9",
+        "type": "github"
+      },
+      "original": {
+        "owner": "NuschtOS",
+        "repo": "search",
+        "type": "github"
+      }
+    },
     "root": {
       "inputs": {
-        "nixpkgs": "nixpkgs"
+        "catppuccin-v1_1": "catppuccin-v1_1",
+        "catppuccin-v1_2": "catppuccin-v1_2",
+        "home-manager": "home-manager",
+        "home-manager-stable": "home-manager-stable",
+        "nixpkgs": "nixpkgs",
+        "nixpkgs-stable": "nixpkgs-stable",
+        "nuscht-search": "nuscht-search"
+      }
+    },
+    "systems": {
+      "locked": {
+        "lastModified": 1681028828,
+        "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
+        "owner": "nix-systems",
+        "repo": "default",
+        "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
+        "type": "github"
+      },
+      "original": {
+        "owner": "nix-systems",
+        "repo": "default",
+        "type": "github"
       }
     }
   },
diff --git a/flake.nix b/flake.nix
index 0ac148ac..537ad914 100644
--- a/flake.nix
+++ b/flake.nix
@@ -3,18 +3,79 @@
 
   inputs = {
     nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
+
+    /*
+      Inputs below this are optional and can be removed
+
+      ```
+      {
+        inputs.catppuccin = {
+          url = "github:catppuccin/nix";
+          inputs = {
+            nixpkgs-stable.follows = "";
+            home-manager.follows = "";
+            home-manager-stable.follows = "";
+            nuscht-search.follows = "";
+            catppuccin-v1_1.follows = "";
+            catppuccin-v1_2.follows = "";
+          };
+        };
+      }
+      ```
+    */
+
+    nixpkgs-stable.url = "github:NixOS/nixpkgs/nixos-24.11";
+
+    home-manager = {
+      url = "github:nix-community/home-manager";
+      inputs.nixpkgs.follows = "nixpkgs";
+    };
+
+    home-manager-stable = {
+      url = "github:nix-community/home-manager/release-24.11";
+      inputs.nixpkgs.follows = "nixpkgs-stable";
+    };
+
+    nuscht-search = {
+      url = "github:NuschtOS/search";
+      inputs.nixpkgs.follows = "nixpkgs";
+    };
+
+    # Track some of our minor releases to index in our search
+
+    catppuccin-v1_1 = {
+      url = "https://flakehub.com/f/catppuccin/nix/1.1.*.tar.gz";
+    };
+
+    catppuccin-v1_2 = {
+      url = "https://flakehub.com/f/catppuccin/nix/1.2.*.tar.gz";
+    };
   };
 
   outputs =
-    { nixpkgs, self }:
+    {
+      self,
+      nixpkgs,
+      ...
+    }@inputs:
 
     let
       inherit (nixpkgs) lib;
+
+      # Systems for public outputs
       systems = lib.systems.flakeExposed;
 
+      # Systems for development relatedo otuputs
+      devSystems = [
+        "x86_64-linux"
+        "aarch64-linux"
+        "x86_64-darwin"
+        "aarch64-darwin"
+      ];
+
       # flake-utils pollyfill
       forEachSystem =
-        fn:
+        systems: fn:
         lib.foldl' (
           acc: system:
           lib.recursiveUpdate acc (
@@ -24,6 +85,16 @@
           )
         ) { } systems;
 
+      forEachDefaultSystem = forEachSystem systems;
+      forEachDevSystem = forEachSystem devSystems;
+
+      # Versions of the modules we want to index in our search
+      searchVersions = {
+        "v1.1" = inputs.catppuccin-v1_1;
+        "v1.2" = inputs.catppuccin-v1_2;
+        "rolling" = self;
+      };
+
       mkModule =
         {
           name ? "catppuccin",
@@ -44,21 +115,18 @@
 
     mergeAttrs [
       # Public outputs
-      (forEachSystem (
+      (forEachDefaultSystem (
         system:
+
         let
           pkgs = nixpkgs.legacyPackages.${system};
+          catppuccinPackages = (import ./default.nix { inherit pkgs; }).packages;
         in
-        {
-          devShells.default = import ./shell.nix { inherit pkgs; };
-
-          formatter = pkgs.nixfmt-rfc-style;
 
-          packages =
-            let
-              catppuccinPackages = (import ./default.nix { inherit pkgs; }).packages;
-            in
-            catppuccinPackages // { default = catppuccinPackages.whiskers; };
+        {
+          packages = catppuccinPackages // {
+            default = catppuccinPackages.whiskers;
+          };
         }
       ))
 
@@ -73,5 +141,58 @@
           file = ./modules/nixos;
         };
       }
+
+      # Development outputs
+      (forEachDevSystem (
+        system:
+
+        let
+          pkgs = nixpkgs.legacyPackages.${system};
+          pkgsStable = inputs.nixpkgs-stable.legacyPackages.${system};
+        in
+
+        {
+          apps = {
+            serve = {
+              type = "app";
+              program = lib.getExe self.packages.${system}.site.serve;
+            };
+          };
+
+          checks =
+
+            let
+              kernelName = pkgs.stdenv.hostPlatform.parsed.kernel.name;
+
+              callWith = pkgs: lib.flip pkgs.callPackage;
+              callUnstable = callWith pkgs { inherit (inputs) home-manager; };
+              callStable = callWith pkgsStable { home-manager = inputs.home-manager-stable; };
+            in
+
+            {
+              darwin = {
+                test-unstable = callUnstable ./tests/darwin.nix;
+                test-stable = callStable ./tests/darwin.nix;
+              };
+
+              linux = {
+                test-unstable = callUnstable ./tests/nixos.nix;
+                test-stable = callStable ./tests/nixos.nix;
+              };
+            }
+            .${kernelName} or { };
+
+          devShells.default = import ./shell.nix { inherit pkgs; };
+
+          formatter = pkgs.nixfmt-rfc-style;
+
+          packages = {
+            site = pkgs.callPackage ./docs/package.nix {
+              inherit inputs searchVersions;
+              nuscht-search = inputs.nuscht-search.packages.${system};
+            };
+          };
+        }
+      ))
     ];
 }

From 48c8d80a82d4e2dd87d91844a3e0d93f6c53cacc Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Mon, 25 Nov 2024 13:39:19 -0500
Subject: [PATCH 15/20] ci: split format job

---
 .github/workflows/ci.yml     | 37 -----------------------------
 .github/workflows/format.yml | 45 ++++++++++++++++++++++++++++++++++++
 2 files changed, 45 insertions(+), 37 deletions(-)
 create mode 100644 .github/workflows/format.yml

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index d6127f44..4580d90d 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -13,43 +13,6 @@ on:
   workflow_dispatch:
 
 jobs:
-  format:
-    name: Format Nix files
-
-    if: github.repository_owner == 'Catppuccin' && github.event_name == 'push' || github.event_name == 'workflow_dispatch'
-
-    runs-on: ubuntu-latest
-
-    steps:
-      - name: Checkout repository
-        uses: actions/checkout@v4
-        with:
-          token: ${{ secrets.PUSH_TOKEN }}
-
-      - name: Set Git user info
-        run: |
-          git config user.name 'github-actions[bot]'
-          git config user.email 'github-actions[bot]@users.noreply.github.com'
-
-      - name: Get short revision
-        id: rev
-        run:
-          echo "rev=$(git rev-parse --short HEAD)" >> "$GITHUB_OUTPUT"
-
-      - name: Install Nix
-        uses: cachix/install-nix-action@V27
-
-      - name: Format changes
-        run: |
-          nix fmt
-
-      - name: Commit changes
-        run: |
-          if ! git diff --color=always --exit-code; then
-            git commit -am "style: format ${{ steps.rev.outputs.rev }}"
-            git push
-          fi
-
   test:
     name: Test Modules
 
diff --git a/.github/workflows/format.yml b/.github/workflows/format.yml
new file mode 100644
index 00000000..16220ae4
--- /dev/null
+++ b/.github/workflows/format.yml
@@ -0,0 +1,45 @@
+name: Format
+
+on:
+  push:
+    branches: [ main ]
+    paths:
+      - "**.nix"
+      - ".github/workflows/format.yml"
+  workflow_dispatch:
+
+jobs:
+  nix:
+    name: Nix files
+
+    runs-on: ubuntu-latest
+
+    steps:
+      - name: Checkout repository
+        uses: actions/checkout@v4
+        with:
+          token: ${{ secrets.PUSH_TOKEN }}
+
+      - name: Set Git user info
+        run: |
+          git config user.name 'github-actions[bot]'
+          git config user.email 'github-actions[bot]@users.noreply.github.com'
+
+      - name: Get short revision
+        id: rev
+        run:
+          echo "rev=$(git rev-parse --short HEAD)" >> "$GITHUB_OUTPUT"
+
+      - name: Install Nix
+        uses: cachix/install-nix-action@V27
+
+      - name: Format changes
+        run: |
+          nix fmt
+
+      - name: Commit changes
+        run: |
+          if ! git diff --color=always --exit-code; then
+            git commit -am "style: format ${{ steps.rev.outputs.rev }}"
+            git push
+          fi

From 8d5e90095c8adab5e15ba42666dd9a5299bcbc72 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Fri, 29 Nov 2024 02:23:49 -0500
Subject: [PATCH 16/20] ci: build package set

---
 .github/workflows/ci.yml | 52 ++++++++++++++++++++++++++++++++--------
 .gitignore               |  2 +-
 flake.nix                | 29 ++++++++++++++++++++++
 3 files changed, 72 insertions(+), 11 deletions(-)

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 4580d90d..9f28a970 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -2,24 +2,49 @@ name: CI
 
 on:
   push:
-    branches: [main]
+    branches: [ main ]
     paths:
-      - '**.lock'
       - '**.nix'
+      - 'flake.lock'
   pull_request:
     paths:
-      - '**.lock'
       - '**.nix'
+      - 'flake.lock'
   workflow_dispatch:
 
 jobs:
-  test:
+  packages:
+    name: Build Packages
+
+    strategy:
+      fail-fast: false
+      matrix:
+        os: [ macos-latest, macos-13, ubuntu-latest ]
+
+    runs-on: ${{ matrix.os }}
+
+    steps:
+      - name: Checkout repository
+        uses: actions/checkout@v4
+
+      - name: Install Nix
+        uses: cachix/install-nix-action@V27
+
+      - name: Setup cache
+        uses: DeterminateSystems/magic-nix-cache-action@v8
+
+      - name: Run build
+        run: |
+          nix run .#build-outputs -- 'packages'
+
+  modules:
     name: Test Modules
+    needs: packages
 
     strategy:
       fail-fast: false
       matrix:
-        os: [macos-latest, ubuntu-latest]
+        os: [ macos-latest, ubuntu-latest ]
 
     runs-on: ${{ matrix.os }}
 
@@ -35,8 +60,15 @@ jobs:
 
       - name: Run tests
         run: |
-          nix run \
-            --inputs-from . \
-            github:Mic92/nix-fast-build -- \
-            --no-nom \
-            --flake ".#checks.$(nix eval --raw --impure --expr builtins.currentSystem)"
+          nix run .#build-outputs -- 'checks'
+
+  release-gate:
+    name: Release Gate
+    needs: [ modules, packages ]
+
+    runs-on: ubuntu-latest
+
+    steps:
+      - name: Exit with error
+        if: ${{ contains(needs.*.result, 'failure') || contains(needs.*.result, 'cancelled') }}
+        run: exit 1
diff --git a/.gitignore b/.gitignore
index b272df7c..591b2ba3 100644
--- a/.gitignore
+++ b/.gitignore
@@ -5,4 +5,4 @@
 result
 result-*
 repl-result-*
-
+gcroot/
diff --git a/flake.nix b/flake.nix
index 537ad914..fc2cbf55 100644
--- a/flake.nix
+++ b/flake.nix
@@ -153,6 +153,35 @@
 
         {
           apps = {
+            build-outputs = {
+              type = "app";
+              program = lib.getExe (
+                pkgs.writeShellApplication {
+                  name = "build-outputs";
+
+                  runtimeInputs = [ pkgs.nix-fast-build ];
+
+                  text = ''
+                    usage="Usage: $0 <flake_attribute>"
+
+                    attribute="''${1:-}"
+                    if [ -z "$attribute" ]; then
+                      echo -n "$usage"
+                      exit 1
+                    fi
+
+                    args=(
+                      "--no-nom"
+                      "--skip-cached"
+                      "--flake" "${self.outPath}#$attribute.${system}"
+                    )
+
+                    nix-fast-build "''${args[@]}"
+                  '';
+                }
+              );
+            };
+
             serve = {
               type = "app";
               program = lib.getExe self.packages.${system}.site.serve;

From cf6a9d7751e1a5cd404fc155d95214f7eb541e5d Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Thu, 19 Dec 2024 05:02:56 -0500
Subject: [PATCH 17/20] ci: use cachix

---
 .github/workflows/ci.yml      | 14 ++++++++++----
 .github/workflows/website.yml |  7 +++++--
 2 files changed, 15 insertions(+), 6 deletions(-)

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 9f28a970..9eb3df19 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -30,8 +30,11 @@ jobs:
       - name: Install Nix
         uses: cachix/install-nix-action@V27
 
-      - name: Setup cache
-        uses: DeterminateSystems/magic-nix-cache-action@v8
+      - name: Install Cachix
+        uses: cachix/cachix-action@v15
+        with:
+          name: catppuccin
+          authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}
 
       - name: Run build
         run: |
@@ -55,8 +58,11 @@ jobs:
       - name: Install Nix
         uses: cachix/install-nix-action@V27
 
-      - name: Setup cache
-        uses: DeterminateSystems/magic-nix-cache-action@v8
+      - name: Install Cachix
+        uses: cachix/cachix-action@v15
+        with:
+          name: catppuccin
+          authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}
 
       - name: Run tests
         run: |
diff --git a/.github/workflows/website.yml b/.github/workflows/website.yml
index 5586ade6..ee10afd6 100644
--- a/.github/workflows/website.yml
+++ b/.github/workflows/website.yml
@@ -29,8 +29,11 @@ jobs:
       - name: Install Nix
         uses: cachix/install-nix-action@V27
 
-      - name: Setup cache
-        uses: DeterminateSystems/magic-nix-cache-action@v8
+      - name: Install Cachix
+        uses: cachix/cachix-action@v15
+        with:
+          name: catppuccin
+          authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}
 
       - name: Run build
         run: |

From b7e18381b1ab47c62412e71922fa0946951fe0d7 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Thu, 19 Dec 2024 18:53:50 -0500
Subject: [PATCH 18/20] ci: run ci when workflow files change

---
 .github/workflows/ci.yml      | 4 ++++
 .github/workflows/format.yml  | 1 +
 .github/workflows/website.yml | 4 ++++
 3 files changed, 9 insertions(+)

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 9eb3df19..b8f51293 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -6,10 +6,14 @@ on:
     paths:
       - '**.nix'
       - 'flake.lock'
+
+      - '.github/workflows/ci.yml'
   pull_request:
     paths:
       - '**.nix'
       - 'flake.lock'
+
+      - '.github/workflows/ci.yml'
   workflow_dispatch:
 
 jobs:
diff --git a/.github/workflows/format.yml b/.github/workflows/format.yml
index 16220ae4..2222467f 100644
--- a/.github/workflows/format.yml
+++ b/.github/workflows/format.yml
@@ -5,6 +5,7 @@ on:
     branches: [ main ]
     paths:
       - "**.nix"
+
       - ".github/workflows/format.yml"
   workflow_dispatch:
 
diff --git a/.github/workflows/website.yml b/.github/workflows/website.yml
index ee10afd6..5915461b 100644
--- a/.github/workflows/website.yml
+++ b/.github/workflows/website.yml
@@ -8,12 +8,16 @@ on:
       - 'CHANGELOG.md'
       - '**.lock'
       - '**.nix'
+
+      - '.github/workflows/website.yml'
   pull_request:
     paths:
       - 'docs/**'
       - 'CHANGELOG.md'
       - '**.lock'
       - '**.nix'
+
+      - '.github/workflows/website.yml'
   workflow_dispatch:
 
 jobs:

From eca86f3baec22c2668151aa8591e0e344b714c15 Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Thu, 19 Dec 2024 20:59:37 -0500
Subject: [PATCH 19/20] chore(tests): move to modules folder

---
 flake.nix                             | 8 ++++----
 {tests => modules/tests}/common.nix   | 0
 {tests => modules/tests}/darwin.nix   | 0
 {tests => modules/tests}/home.nix     | 2 +-
 {tests => modules/tests}/nixos.nix    | 2 +-
 {tests => modules/tests}/username.txt | 0
 6 files changed, 6 insertions(+), 6 deletions(-)
 rename {tests => modules/tests}/common.nix (100%)
 rename {tests => modules/tests}/darwin.nix (100%)
 rename {tests => modules/tests}/home.nix (98%)
 rename {tests => modules/tests}/nixos.nix (98%)
 rename {tests => modules/tests}/username.txt (100%)

diff --git a/flake.nix b/flake.nix
index fc2cbf55..9862afa8 100644
--- a/flake.nix
+++ b/flake.nix
@@ -200,13 +200,13 @@
 
             {
               darwin = {
-                test-unstable = callUnstable ./tests/darwin.nix;
-                test-stable = callStable ./tests/darwin.nix;
+                test-unstable = callUnstable ./modules/tests/darwin.nix;
+                test-stable = callStable ./modules/tests/darwin.nix;
               };
 
               linux = {
-                test-unstable = callUnstable ./tests/nixos.nix;
-                test-stable = callStable ./tests/nixos.nix;
+                test-unstable = callUnstable ./modules/tests/nixos.nix;
+                test-stable = callStable ./modules/tests/nixos.nix;
               };
             }
             .${kernelName} or { };
diff --git a/tests/common.nix b/modules/tests/common.nix
similarity index 100%
rename from tests/common.nix
rename to modules/tests/common.nix
diff --git a/tests/darwin.nix b/modules/tests/darwin.nix
similarity index 100%
rename from tests/darwin.nix
rename to modules/tests/darwin.nix
diff --git a/tests/home.nix b/modules/tests/home.nix
similarity index 98%
rename from tests/home.nix
rename to modules/tests/home.nix
index c530453d..ee2100ac 100644
--- a/tests/home.nix
+++ b/modules/tests/home.nix
@@ -2,7 +2,7 @@
 
 {
   imports = [
-    ../modules/home-manager
+    ../home-manager
     ./common.nix
   ];
 
diff --git a/tests/nixos.nix b/modules/tests/nixos.nix
similarity index 98%
rename from tests/nixos.nix
rename to modules/tests/nixos.nix
index 5198e49d..9358d712 100644
--- a/tests/nixos.nix
+++ b/modules/tests/nixos.nix
@@ -17,7 +17,7 @@ testers.runNixOSTest {
     {
       imports = [
         home-manager.nixosModules.default
-        ../modules/nixos
+        ../nixos
         ./common.nix
       ];
 
diff --git a/tests/username.txt b/modules/tests/username.txt
similarity index 100%
rename from tests/username.txt
rename to modules/tests/username.txt

From ff3b784b23b1627c96c884a2ccea0d89d837c49c Mon Sep 17 00:00:00 2001
From: seth <getchoo@tuta.io>
Date: Thu, 26 Dec 2024 05:17:12 -0500
Subject: [PATCH 20/20] revert: "ci: remove backport workflow"

Refs: 630b559cc1cb4c0bdd525af506935323e4ccd5d1.
---
 .github/workflows/backport.yml | 35 ++++++++++++++++++++++++++++++++++
 1 file changed, 35 insertions(+)
 create mode 100644 .github/workflows/backport.yml

diff --git a/.github/workflows/backport.yml b/.github/workflows/backport.yml
new file mode 100644
index 00000000..c4adb7b1
--- /dev/null
+++ b/.github/workflows/backport.yml
@@ -0,0 +1,35 @@
+# Based on https://github.com/NixOS/nixpkgs/blob/c81ecdf95b3a0f73ded448f14416cd66beeb5e1a/.github/workflows/backport.yml
+name: Backport
+
+on:
+  pull_request_target:
+    types: [closed, labeled]
+
+# WARNING:
+# When extending this action, be aware that $GITHUB_TOKEN allows write access to
+# the GitHub repository. This means that it should not evaluate user input in a
+# way that allows code injection.
+
+jobs:
+  backport:
+    name: Backport Pull Request
+
+    if: ${{ github.repository_owner == 'catppuccin' && github.event.pull_request.merged == true && (github.event_name != 'labeled' || startsWith('backport', github.event.label.name)) }}
+
+    runs-on: ubuntu-latest
+
+    permissions:
+      contents: write
+      pull-requests: write
+
+    steps:
+      - name: Checkout repository
+        uses: actions/checkout@v4
+        with:
+          ref: ${{ github.event.pull_request.head.sha }}
+
+      - name: Create backport PRs
+        uses: korthout/backport-action@v3
+        with:
+          pull_description: |-
+            Bot-based backport to `${target_branch}`, triggered by a label in #${pull_number}.