22 Commits

Author SHA1 Message Date
Noah Masur
6933083cda adjust some zellij and helix keybinds 2025-03-27 13:01:53 -04:00
Noah Masur
39d9cb7e5a more lsps and fix syntax var colors 2025-03-24 09:53:30 -04:00
Noah Masur
b270e1643c update readme and tweak helix config 2025-03-23 18:41:37 -04:00
Noah Masur
cdbd94e64e upgrade to nextcloud 31 (without apps) 2025-03-23 20:53:35 +00:00
Noah Masur
9e3b003241 fix: enable calibre-web in preset 2025-03-23 20:47:05 +00:00
Noah Masur
802544575f fixes for read key 2025-03-23 19:11:27 +00:00
Noah Masur
a85180beee fix: enable prometheus stuff 2025-03-23 17:30:59 +00:00
Noah Masur
b901b9abd9 zellij tweaks and session switching 2025-03-23 10:10:56 -04:00
Noah Masur
870ab6894d fixes for swan 2025-03-23 13:30:57 +00:00
Noah Masur
12604f3109 fix flame settings 2025-03-23 00:32:06 +00:00
Noah Masur
59e67fb406 build succeed on swan 2025-03-22 23:45:06 +00:00
Noah Masur
6a7706ca85 some conveniences for helix 2025-03-21 13:51:28 -04:00
Noah Masur
12d0bccb42 integrate helix with fzf shortcuts 2025-03-19 14:16:01 -04:00
Noah Masur
cf7966d73d tweaks for ghostty and zellij 2025-03-19 13:51:42 -04:00
Noah Masur
fa1482dcfc some basic zellij and helix configs 2025-03-18 21:47:40 -04:00
Noah Masur
8e7ccbda59 use ctrl-f to accept autosuggestions 2025-03-17 23:30:59 -04:00
Noah Masur
59c5ca4816 zellij and helix config 2025-03-17 23:30:38 -04:00
Noah Masur
442249c242 replace wezterm with ghostty on dock 2025-03-17 21:44:13 -04:00
Noah Masur
5eb2b003d4 fix helix color for primary selection 2025-03-17 21:40:04 -04:00
Noah Masur
ef6070fe6d update hammerspoon notification dismissal for macos 15 2025-03-17 12:04:21 -04:00
Noah Masur
38906a802d reorg flake lines and remove unnecessary stanzas 2025-03-17 11:38:50 -04:00
Noah Masur
852ecf0b91 tweaks for ghostty, helix, zed 2025-03-17 11:00:19 -04:00
43 changed files with 908 additions and 555 deletions

View File

@@ -9,37 +9,37 @@ configuration may be difficult to translate to a non-Nix system.
## System Features
| Feature | Program | Configuration |
|----------------|-----------------------------------------------------|-----------------------------------------------|
| OS | [NixOS](https://nixos.org) | [Link](./modules/nixos) |
| Display Server | [X11](https://www.x.org/wiki/) | [Link](./modules/nixos/graphical/xorg.nix) |
| Compositor | [Picom](https://github.com/yshui/picom) | [Link](./modules/nixos/graphical/picom.nix) |
| Window Manager | [i3](https://i3wm.org/) | [Link](./modules/nixos/graphical/i3.nix) |
| Panel | [Polybar](https://polybar.github.io/) | [Link](./modules/nixos/graphical/polybar.nix) |
| Font | [Victor Mono](https://rubjo.github.io/victor-mono/) | [Link](./modules/nixos/graphical/fonts.nix) |
| Launcher | [Rofi](https://github.com/davatorium/rofi) | [Link](./modules/nixos/graphical/rofi.nix) |
|----------------|-----------------------------------------------------|-----------------------------------------------------------------------------------|
| OS | [NixOS](https://nixos.org) | [Link](./platforms/nixos) |
| Display Server | [X11](https://www.x.org/wiki/) | [Link](./platforms/nixos/modules/nmasur/profiles/gui.nix) |
| Compositor | [Picom](https://github.com/yshui/picom) | [Link](./platforms/home-manager/modules/nmasur/presets/services/picom.nix) |
| Window Manager | [i3](https://i3wm.org/) | [Link](./platforms/home-manager/modules/nmasur/presets/services/i3.nix) |
| Panel | [Polybar](https://polybar.github.io/) | [Link](./platforms/home-manager/modules/nmasur/presets/services/polybar.nix) |
| Font | [Victor Mono](https://rubjo.github.io/victor-mono/) | [Link](./platforms/home-manager/modules/nmasur/presets/fonts.nix) |
| Launcher | [Rofi](https://github.com/davatorium/rofi) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/rofi/default.nix) |
## User Features
| Feature | Program | Configuration |
|--------------|----------------------------------------------------------------------------------|----------------------------------------------------|
| Dotfiles | [Home-Manager](https://github.com/nix-community/home-manager) | [Link](./modules/common) |
| Terminal | [Kitty](https://sw.kovidgoyal.net/kitty/) | [Link](./modules/common/applications/kitty.nix) |
| Shell | [Fish](https://fishshell.com/) | [Link](./modules/common/shell/fish) |
| Shell Prompt | [Starship](https://starship.rs/) | [Link](./modules/common/shell/starship.nix) |
|--------------|----------------------------------------------------------------------------------|-------------------------------------------------------------------------------|
| Dotfiles | [Home-Manager](https://github.com/nix-community/home-manager) | [Link](./platforms/home-manager) |
| Terminal | [Ghostty](https://sw.kovidgoyal.net/kitty/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/ghostty.nix) |
| Shell | [Fish](https://fishshell.com/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/fish.nix) |
| Shell Prompt | [Starship](https://starship.rs/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/starship.nix) |
| Colorscheme | [Gruvbox](https://github.com/morhetz/gruvbox) | [Link](./colorscheme/gruvbox/default.nix) |
| Wallpaper | [Road](https://gitlab.com/exorcist365/wallpapers/-/blob/master/gruvbox/road.jpg) | [Link](./hosts/tempest/default.nix) |
| Text Editor | [Neovim](https://neovim.io/) | [Link](./modules/common/neovim/config) |
| Browser | [Firefox](https://www.mozilla.org/en-US/firefox/new/) | [Link](./modules/common/applications/firefox.nix) |
| E-Mail | [Aerc](https://aerc-mail.org/) | [Link](./modules/common/mail/aerc.nix) |
| File Manager | [Nautilus](https://wiki.gnome.org/action/show/Apps/Files) | [Link](./modules/common/applications/nautilus.nix) |
| PDF Reader | [Zathura](https://pwmt.org/projects/zathura/) | [Link](./modules/common/applications/media.nix) |
| Video Player | [mpv](https://mpv.io/) | [Link](./modules/common/applications/media.nix) |
| Wallpaper | [Road](https://gitlab.com/exorcist365/wallpapers/-/blob/master/gruvbox/road.jpg) | [Link](./hosts/x86_64-linux/tempest/default.nix) |
| Text Editor | [Neovim](https://neovim.io/) | [Link](./pkgs/applications/editors/neovim/nmasur/neovim/package.nix) |
| Browser | [Firefox](https://www.mozilla.org/en-US/firefox/new/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/firefox.nix) |
| E-Mail | [Aerc](https://aerc-mail.org/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/aerc.nix) |
| File Manager | [Nautilus](https://wiki.gnome.org/action/show/Apps/Files) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/nautilus.nix) |
| PDF Reader | [Zathura](https://pwmt.org/projects/zathura/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/zathura.nix) |
| Video Player | [mpv](https://mpv.io/) | [Link](./platforms/home-manager/modules/nmasur/presets/programs/mpv.nix) |
## macOS Features
| Feature | Program | Configuration |
|----------|---------------------------------------------|--------------------------------------|
| Keybinds | [Hammerspoon](https://www.hammerspoon.org/) | [Link](./modules/darwin/hammerspoon) |
| Keybinds | [Hammerspoon](https://www.hammerspoon.org/) | [Link](./platforms/home-manager/modules/nmasur/presets/services/hammerspoon/) |
# Diagram
@@ -51,15 +51,16 @@ configuration may be difficult to translate to a non-Nix system.
This repo contains a few more elaborate elements of configuration.
- [Neovim config](./modules/common/neovim/default.nix) generated with Nix2Vim
and source-controlled plugins, differing based on installed LSPs, for example.
- [Caddy JSON](./modules/nixos/services/caddy.nix) file (routes, etc.) based
dynamically on enabled services rendered with Nix.
- [Grafana config](./modules/nixos/services/grafana.nix) rendered with Nix.
- Custom [secrets deployment](./modules/nixos/services/secrets.nix) similar to
agenix.
- Base16 [colorschemes](./colorscheme/) applied to multiple applications,
including Firefox userChrome.
- [Neovim config](./pkgs/applications/editors/neovim/nmasur/neovim/package.nix)
generated with Nix2Vim and source-controlled plugins,
differing based on installed LSPs, for example. - [Caddy
JSON](./platforms/nixos/modules/nmasur/presets/services/caddy.nix) file (routes,
etc.) based dynamically on enabled services rendered with Nix. - [Grafana
config](./platforms/nixos/modules/nmasur/presets/services/grafana/grafana.nix)
rendered with Nix. - Custom [secrets
deployment](./platforms/nixos/modules/secrets.nix) similar to agenix. - Base16
[colorschemes](./colorscheme/) applied to multiple applications, including
Firefox userChrome.
---

72
flake.lock generated
View File

@@ -334,6 +334,22 @@
"type": "github"
}
},
"nixpkgs_2": {
"locked": {
"lastModified": 1728538411,
"narHash": "sha256-f0SBJz1eZ2yOuKUr5CA9BHULGXVSn6miBuUWdTyhUhU=",
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "b69de56fac8c2b6f8fd27f2eca01dcda8e0a4221",
"type": "github"
},
"original": {
"owner": "NixOS",
"ref": "nixpkgs-unstable",
"repo": "nixpkgs",
"type": "github"
}
},
"nur": {
"inputs": {
"flake-parts": "flake-parts",
@@ -372,9 +388,28 @@
"nixpkgs-stable": "nixpkgs-stable",
"nur": "nur",
"wsl": "wsl",
"zellij-switch": "zellij-switch",
"zenyd-mpv-scripts": "zenyd-mpv-scripts"
}
},
"rust-overlay": {
"inputs": {
"nixpkgs": "nixpkgs_2"
},
"locked": {
"lastModified": 1736476219,
"narHash": "sha256-+qyv3QqdZCdZ3cSO/cbpEY6tntyYjfe1bB12mdpNFaY=",
"owner": "oxalica",
"repo": "rust-overlay",
"rev": "de30cc5963da22e9742bbbbb9a3344570ed237b9",
"type": "github"
},
"original": {
"owner": "oxalica",
"repo": "rust-overlay",
"type": "github"
}
},
"systems": {
"locked": {
"lastModified": 1689347925,
@@ -405,6 +440,21 @@
"type": "github"
}
},
"systems_3": {
"locked": {
"lastModified": 1681028828,
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
"owner": "nix-systems",
"repo": "default",
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
"type": "github"
},
"original": {
"owner": "nix-systems",
"repo": "default",
"type": "github"
}
},
"treefmt-nix": {
"inputs": {
"nixpkgs": [
@@ -447,6 +497,28 @@
"type": "github"
}
},
"zellij-switch": {
"inputs": {
"nixpkgs": [
"nixpkgs"
],
"rust-overlay": "rust-overlay",
"systems": "systems_3"
},
"locked": {
"lastModified": 1737011317,
"narHash": "sha256-A8VGuw/jIw+NCo5aCYy8MFrWpKzZLf77RApGGMzHxCY=",
"owner": "mostafaqanbaryan",
"repo": "zellij-switch",
"rev": "15b02834c8be735fca0d9fb41f48709f97cc9afc",
"type": "github"
},
"original": {
"owner": "mostafaqanbaryan",
"repo": "zellij-switch",
"type": "github"
}
},
"zenyd-mpv-scripts": {
"flake": false,
"locked": {

View File

@@ -58,48 +58,17 @@
inputs.nixpkgs.follows = "nixpkgs";
};
# # Tree-Sitter Grammars
# tree-sitter-bash = {
# url = "github:tree-sitter/tree-sitter-bash/master";
# flake = false;
# };
# tree-sitter-python = {
# url = "github:tree-sitter/tree-sitter-python/master";
# flake = false;
# };
# tree-sitter-lua = {
# url = "github:MunifTanjim/tree-sitter-lua/main";
# flake = false;
# };
# tree-sitter-ini = {
# url = "github:justinmk/tree-sitter-ini";
# flake = false;
# };
# tree-sitter-puppet = {
# url = "github:amaanq/tree-sitter-puppet";
# flake = false;
# };
# tree-sitter-rasi = {
# url = "github:Fymyte/tree-sitter-rasi";
# flake = false;
# };
# tree-sitter-vimdoc = {
# url = "github:neovim/tree-sitter-vimdoc";
# flake = false;
# };
# MPV Scripts
zenyd-mpv-scripts = {
url = "github:zenyd/mpv-scripts";
flake = false;
};
# # Git alternative
# # Fixes: https://github.com/martinvonz/jj/issues/4784
# jujutsu = {
# url = "github:martinvonz/jj";
# inputs.nixpkgs.follows = "nixpkgs";
# };
# Zellij Switcher
zellij-switch = {
url = "github:mostafaqanbaryan/zellij-switch";
inputs.nixpkgs.follows = "nixpkgs";
};
# Nextcloud Apps
nextcloud-news = {
@@ -130,20 +99,11 @@
{ nixpkgs, ... }@inputs:
let
lib = import ./lib inputs;
# Global configuration for my systems
globals =
hostnames =
let
baseName = "masu.rs";
in
rec {
user = "noah";
fullName = "Noah Masur";
gitName = fullName;
gitEmail = "7386960+nmasur@users.noreply.github.com";
dotfilesRepo = "https://github.com/nmasur/dotfiles";
hostnames = {
{
audiobooks = "read.${baseName}";
books = "books.${baseName}";
budget = "money.${baseName}";
@@ -168,12 +128,11 @@
stream = "stream.${baseName}";
transmission = "transmission.${baseName}";
};
};
in
rec {
inherit lib;
lib = import ./lib inputs;
nixosConfigurations = builtins.mapAttrs (
system: hosts:
@@ -181,28 +140,18 @@
name: module:
lib.buildNixos {
inherit system module;
specialArgs = { inherit (globals) hostnames; };
specialArgs = { inherit hostnames; };
}
) hosts
) lib.linuxHosts;
# darwinConfigurations = {
# aarch64-darwin = {
# lookingglass = lib.buildDarwin {
# system = "aarch64-darwin";
# module = { };
# specialArgs = { };
# };
# };
# };
darwinConfigurations = builtins.mapAttrs (
system: hosts:
builtins.mapAttrs (
name: module:
lib.buildDarwin {
inherit system module;
specialArgs = { inherit (globals) hostnames; };
specialArgs = { inherit hostnames; };
}
) hosts
) lib.darwinHosts;
@@ -220,7 +169,7 @@
name: module:
lib.buildHome {
inherit system module;
specialArgs = { inherit (globals) hostnames; };
specialArgs = { inherit hostnames; };
}
) hosts
) homeModules;
@@ -230,31 +179,18 @@
root = import ./hosts/x86_64-linux/swan/root.nix;
};
# generators = {
# arrow.aws.x86_64-linux = lib.generateImage {
# system = "x86_64-linux";
# format = "amazon";
# specialArgs = { inherit (globals) hostnames; };
# };
# arrow.iso.x86_64-linux = lib.generateImage {
# system = "x86_64-linux";
# format = "iso";
# specialArgs = { inherit (globals) hostnames; };
# };
# };
generators = builtins.mapAttrs (
system: hosts:
builtins.mapAttrs (name: module: {
aws = lib.generateImage {
inherit system module;
format = "amazon";
specialArgs = { inherit (globals) hostnames; };
specialArgs = { inherit hostnames; };
};
iso = lib.generateImage {
inherit system module;
format = "iso";
specialArgs = { inherit (globals) hostnames; };
specialArgs = { inherit hostnames; };
};
}) hosts
) lib.linuxHosts;

View File

@@ -14,6 +14,7 @@ rec {
server.enable = true;
home.enable = true;
nas.enable = true;
shared-media.enable = true;
};
home-manager.users."noah" = {
@@ -24,10 +25,13 @@ rec {
nmasur.profiles = {
common.enable = true;
linux-base.enable = true;
power-user.enable = true;
};
home.stateVersion = "23.05";
};
system.stateVersion = "23.05";
# Not sure what's necessary but too afraid to remove anything
boot.initrd.availableKernelModules = [
"xhci_pci"
@@ -63,7 +67,7 @@ rec {
# Sets root ext4 filesystem instead of declaring it manually
disko = {
enableConfig = true;
devices = (import ../../../disks/root.nix { disk = "/dev/nvme0n1"; });
devices = (import ./root.nix { disk = "/dev/nvme0n1"; });
};
# Allows private remote access over the internet

View File

@@ -17,6 +17,8 @@ rec {
gaming.enable = true;
};
nmasur.presets.services.grub.enable = true;
home-manager.users."noah" = {
nmasur.settings = {
username = nmasur.settings.username;

View File

@@ -66,6 +66,7 @@ lib
overlays = [
inputs.nur.overlays.default
inputs.nix2vim.overlay
inputs.zellij-switch.overlays.default
] ++ (importOverlays ../overlays);
# System types to support.

View File

@@ -33,6 +33,7 @@ in
programs.alacritty.settings.font.normal.family = "VictorMono";
programs.kitty.font.name = "VictorMono Nerd Font Mono";
nmasur.presets.programs.wezterm.font = "VictorMono Nerd Font Mono";
programs.ghostty.settings.font-family = "VictorMono Nerd Font Mono";
services.dunst.settings.global.font = "Hack Nerd Font 14";
};
}

View File

@@ -24,9 +24,12 @@ in
nmasur.presets.programs.fish.fish_user_key_bindings = # fish
''
for mode in insert default visual
# Shift-Enter (defined by terminal)
bind -M insert \x1F accept-autosuggestion
bind -M default \x1F accept-autosuggestion
bind -M $mode \x1F accept-autosuggestion
# Ctrl-f to accept auto-suggestions
bind -M $mode \cf forward-char
end
'';
programs.fish = {

View File

@@ -25,7 +25,13 @@ in
functions = {
edit = {
description = "Open a file in Vim";
body = builtins.readFile ./fish/edit.fish;
body = # fish
''
set vimfile (fzf)
and set vimfile (echo $vimfile | tr -d '\r')
and commandline -r "${builtins.baseNameOf config.home.sessionVariables.EDITOR} \"$vimfile\""
and commandline -f execute
'';
};
fcd = {
description = "Jump to directory";
@@ -51,11 +57,40 @@ in
};
recent = {
description = "Open a recent file in Vim";
body = builtins.readFile ./fish/recent.fish;
body = # fish
''
set vimfile (fd -t f --exec /usr/bin/stat -f "%m%t%N" | sort -nr | cut -f2 | fzf)
and set vimfile (echo $vimfile | tr -d '\r')
and commandline -r "${builtins.baseNameOf config.home.sessionVariables.EDITOR} $vimfile"
and commandline -f execute
'';
};
search-and-edit = {
description = "Search and open the relevant file in Vim";
body = builtins.readFile ./fish/search-and-edit.fish;
body = # fish
''
set vimfile ( \
rg \
--color=always \
--line-number \
--no-heading \
--smart-case \
--iglob "!/Library/**" \
--iglob "!/System/**" \
--iglob "!Users/$HOME/Library/*" \
".*" \
| fzf --ansi \
--height "80%" \
--color "hl:-1:underline,hl+:-1:underline:reverse" \
--delimiter : \
--preview 'bat --color=always {1} --highlight-line {2}' \
--preview-window 'up,60%,border-bottom,+{2}+3/3,~3'
)
and set line_number (echo $vimfile | tr -d '\r' | cut -d':' -f2)
and set vimfile (echo $vimfile | tr -d '\r' | cut -d':' -f1)
and commandline -r "${builtins.baseNameOf config.home.sessionVariables.EDITOR} +$line_number \"$vimfile\""
and commandline -f execute
'';
};
};
shellAbbrs = {
@@ -77,9 +112,6 @@ in
# Ctrl-e
bind -M insert \ce recent
bind -M default \ce recent
# Ctrl-f
bind -M insert \cf fcd
bind -M default \cf fcd
# Ctrl-p
bind -M insert \cp projects
bind -M default \cp projects

View File

@@ -1,4 +0,0 @@
set vimfile (fzf)
and set vimfile (echo $vimfile | tr -d '\r')
and commandline -r "vim \"$vimfile\""
and commandline -f execute

View File

@@ -1,4 +0,0 @@
set vimfile (fd -t f --exec /usr/bin/stat -f "%m%t%N" | sort -nr | cut -f2 | fzf)
and set vimfile (echo $vimfile | tr -d '\r')
and commandline -r "vim $vimfile"
and commandline -f execute

View File

@@ -1,21 +0,0 @@
set vimfile ( \
rg \
--color=always \
--line-number \
--no-heading \
--smart-case \
--iglob "!/Library/**" \
--iglob "!/System/**" \
--iglob "!Users/$HOME/Library/*" \
".*" \
| fzf --ansi \
--height "80%" \
--color "hl:-1:underline,hl+:-1:underline:reverse" \
--delimiter : \
--preview 'bat --color=always {1} --highlight-line {2}' \
--preview-window 'up,60%,border-bottom,+{2}+3/3,~3'
)
and set line_number (echo $vimfile | tr -d '\r' | cut -d':' -f2)
and set vimfile (echo $vimfile | tr -d '\r' | cut -d':' -f1)
and commandline -r "vim +$line_number \"$vimfile\""
and commandline -f execute

View File

@@ -22,10 +22,21 @@ in
enableFishIntegration = true;
enableBashIntegration = true;
enableZshIntegration = true;
installBatSyntax = true;
installBatSyntax = false; # The file doesn't seem to exist in the pkg
settings = {
theme = config.theme.name;
font-size = 16;
macos-titlebar-style = "hidden";
window-decoration = false;
macos-non-native-fullscreen = true;
fullscreen = true;
keybind = [
"super+t=unbind" # Pass super-t to underlying tool (e.g. zellij tabs)
"super+shift+]=unbind"
"super+shift+[=unbind"
"ctrl+tab=unbind"
"ctrl+shift+tab=unbind"
];
};
themes."gruvbox" = {
background = config.theme.colors.base00;

View File

@@ -32,7 +32,7 @@ in
userName = cfg.name;
userEmail = cfg.email;
extraConfig = {
core.pager = "${pkgs.git}/share/git/contrib/diff-highlight/diff-highlight | less -F";
core.pager = "${pkgs.git}/share/git/contrib/diff-highlight/diff-highlight | less --no-init";
interactive.difffilter = "${pkgs.git}/share/git/contrib/diff-highlight/diff-highlight";
pager = {
branch = "false";

View File

@@ -0,0 +1,382 @@
{
config,
pkgs,
lib,
...
}:
let
cfg = config.nmasur.presets.programs.helix;
in
{
options.nmasur.presets.programs.helix.enable = lib.mkEnableOption "Helix text editor";
config = lib.mkIf cfg.enable {
# Use Neovim as the editor for git commit messages
programs.git.extraConfig.core.editor = lib.mkForce "${lib.getExe pkgs.helix}";
programs.jujutsu.settings.ui.editor = lib.mkForce "${lib.getExe pkgs.helix}";
# Set Neovim as the default app for text editing and manual pages
home.sessionVariables = {
EDITOR = lib.mkForce "${lib.getExe pkgs.helix}";
};
# Create quick aliases for launching Helix
programs.fish = {
shellAbbrs = {
h = lib.mkForce "hx";
};
};
programs.helix = {
enable = true;
package = pkgs.helix; # pkgs.evil-helix
languages = {
language-server.nixd = {
command = "${pkgs.nixd}/bin/nixd";
};
language-server.fish-lsp = {
command = "${pkgs.fish-lsp}/bin/fish-lsp";
};
language-server.yaml-language-server = {
command = lib.getExe pkgs.yaml-language-server;
};
language-server.marksman = {
command = lib.getExe pkgs.marksman;
};
language-server.terraform-ls = {
command = "${lib.getExe pkgs.terraform-ls} serve";
};
language-server.bash-language-server = {
command = lib.getExe (
pkgs.bash-language-server.overrideAttrs {
buildInputs = [
pkgs.shellcheck
pkgs.shfmt
];
}
);
};
language = [
{
name = "nix";
auto-format = true;
language-servers = [ "nixd" ];
}
{
name = "markdown";
auto-format = true;
language-servers = [ "marksman" ];
formatter = {
command = lib.getExe pkgs.mdformat;
args = [ "-" ];
};
}
{
name = "tfvars";
auto-format = true;
language-servers = [ "terraform-ls" ];
formatter = {
command = lib.getExe pkgs.terraform;
args = [
"fmt"
"-"
];
};
}
{
name = "hcl";
auto-format = true;
language-servers = [ "terraform-ls" ];
formatter = {
command = lib.getExe pkgs.terraform;
args = [
"fmt"
"-"
];
};
}
{
name = "bash";
auto-format = true;
}
];
};
settings = {
theme = "base16";
keys.normal = {
# Enable and disable inlay hints
space.H = ":toggle lsp.display-inlay-hints";
# Extend selection above
X = "select_line_above";
# Move lines up or down
A-j = [
"extend_to_line_bounds"
"delete_selection"
"paste_after"
];
A-k = [
"extend_to_line_bounds"
"delete_selection"
"move_line_up"
"paste_before"
];
# Copy lines up or down
A-J = [
"extend_to_line_bounds"
"yank"
"paste_after"
];
A-K = [
"extend_to_line_bounds"
"yank"
"paste_before"
];
};
editor = {
# Change cursors depending on the mode
cursor-shape = {
insert = "bar";
normal = "block";
select = "underline";
};
# Text width
soft-wrap = {
enable = true;
};
# View line numbers relative to the current cursors
line-number = "relative";
# Show hidden files
file-picker = {
hidden = false;
git-ignore = true;
git-global = true;
git-exclude = true;
};
# Show whitespace visible to the user
# Waiting for trailing whitespace option ideally
whitespace = {
render = {
# space = "all";
tab = "all";
};
characters = {
# space = "·";
tab = "";
};
};
};
};
themes."${config.programs.helix.settings.theme}" = {
"attributes" = config.theme.colors.base09;
"comment" = {
fg = config.theme.colors.base03;
modifiers = [ "italic" ];
};
"constant" = config.theme.colors.base09;
"constant.character.escape" = config.theme.colors.base0C;
"constant.numeric" = config.theme.colors.base09;
"constructor" = config.theme.colors.base0D;
"debug" = config.theme.colors.base03;
"diagnostic" = {
modifiers = [ "underlined" ];
};
"diff.delta" = config.theme.colors.base09;
"diff.minus" = config.theme.colors.base08;
"diff.plus" = config.theme.colors.base0B;
"error" = config.theme.colors.base08;
"function" = config.theme.colors.base0D;
"hint" = config.theme.colors.base03;
"info" = config.theme.colors.base0D;
"keyword" = config.theme.colors.base0E;
"label" = config.theme.colors.base0E;
"namespace" = config.theme.colors.base0E;
"operator" = config.theme.colors.base05;
"special" = config.theme.colors.base0D;
"string" = config.theme.colors.base0B;
"type" = config.theme.colors.base0A;
"variable" = config.theme.colors.base08;
"variable.other.member" = config.theme.colors.base05;
"warning" = config.theme.colors.base09;
"markup.bold" = {
fg = config.theme.colors.base0A;
modifiers = [ "bold" ];
};
"markup.heading" = config.theme.colors.base0D;
"markup.italic" = {
fg = config.theme.colors.base0E;
modifiers = [ "italic" ];
};
"markup.link.text" = config.theme.colors.base08;
"markup.link.url" = {
fg = config.theme.colors.base09;
modifiers = [ "underlined" ];
};
"markup.list" = config.theme.colors.base08;
"markup.quote" = config.theme.colors.base0C;
"markup.raw" = config.theme.colors.base0B;
"markup.strikethrough" = {
modifiers = [ "crossed_out" ];
};
"diagnostic.hint" = {
underline = {
style = "curl";
};
};
"diagnostic.info" = {
underline = {
style = "curl";
};
};
"diagnostic.warning" = {
underline = {
style = "curl";
};
};
"diagnostic.error" = {
underline = {
style = "curl";
};
};
"ui.background" = {
bg = config.theme.colors.base00;
};
"ui.bufferline.active" = {
fg = config.theme.colors.base00;
bg = config.theme.colors.base03;
modifiers = [ "bold" ];
};
"ui.bufferline" = {
fg = config.theme.colors.base04;
bg = config.theme.colors.base00;
};
"ui.cursor" = {
fg = config.theme.colors.base0A;
modifiers = [ "reversed" ];
};
"ui.cursor.insert" = {
fg = config.theme.colors.base0A;
modifiers = [ "reversed" ];
};
"ui.cursorline.primary" = {
fg = config.theme.colors.base05;
bg = config.theme.colors.base01;
};
"ui.cursor.match" = {
fg = config.theme.colors.base0A;
modifiers = [ "reversed" ];
};
"ui.cursor.select" = {
fg = config.theme.colors.base0A;
modifiers = [ "reversed" ];
};
"ui.gutter" = {
bg = config.theme.colors.base00;
};
"ui.help" = {
fg = config.theme.colors.base06;
bg = config.theme.colors.base01;
};
"ui.linenr" = {
fg = config.theme.colors.base03;
bg = config.theme.colors.base00;
};
"ui.linenr.selected" = {
fg = config.theme.colors.base04;
bg = config.theme.colors.base01;
modifiers = [ "bold" ];
};
"ui.menu" = {
fg = config.theme.colors.base05;
bg = config.theme.colors.base01;
};
"ui.menu.scroll" = {
fg = config.theme.colors.base03;
bg = config.theme.colors.base01;
};
"ui.menu.selected" = {
fg = config.theme.colors.base01;
bg = config.theme.colors.base04;
};
"ui.popup" = {
bg = config.theme.colors.base01;
};
"ui.selection" = {
bg = config.theme.colors.base01;
};
"ui.selection.primary" = {
bg = config.theme.colors.base02;
};
"ui.statusline" = {
fg = config.theme.colors.base04;
bg = config.theme.colors.base01;
};
"ui.statusline.inactive" = {
bg = config.theme.colors.base01;
fg = config.theme.colors.base03;
};
"ui.statusline.insert" = {
fg = config.theme.colors.base00;
bg = config.theme.colors.base0B;
};
"ui.statusline.normal" = {
fg = config.theme.colors.base00;
bg = config.theme.colors.base03;
};
"ui.statusline.select" = {
fg = config.theme.colors.base00;
bg = config.theme.colors.base0F;
};
"ui.text" = config.theme.colors.base05;
"ui.text.focus" = config.theme.colors.base05;
"ui.virtual.indent-guide" = {
fg = config.theme.colors.base03;
};
"ui.virtual.inlay-hint" = {
fg = config.theme.colors.base03;
};
"ui.virtual.ruler" = {
bg = config.theme.colors.base01;
};
"ui.virtual.jump-label" = {
fg = config.theme.colors.base0A;
modifiers = [ "bold" ];
};
"ui.window" = {
bg = config.theme.colors.base01;
};
};
};
};
}

View File

@@ -17,7 +17,10 @@ in
programs.zed-editor = {
enable = true;
extensions = [ "nix" ];
extensions = [
"nix"
"rust"
];
extraPackages = [ pkgs.nixd ];

View File

@@ -0,0 +1,141 @@
{
config,
pkgs,
lib,
...
}:
let
cfg = config.nmasur.presets.programs.zellij;
in
{
options.nmasur.presets.programs.zellij.enable = lib.mkEnableOption "Zellij terminal multiplexer";
config = lib.mkIf cfg.enable {
home.packages = [ pkgs.zellij-switch ];
programs.fish = {
shellAbbrs.z = "zellij";
functions = {
zellij-session = {
# description = "Open a session in Zellij";
body = # fish
''
zoxide query --interactive | xargs -I {} sh -c 'zellij pipe --plugin file:$(which zellij-switch.wasm) -- "--cwd {} --layout default --session $(basename {})"' \\;
'';
};
};
};
xdg.configFile."zellij/layouts/compact-top.kdl".text = # kdl
''
layout {
pane size=1 borderless=true {
plugin location="compact-bar"
}
pane
}
'';
xdg.configFile."zellij/layouts/default.kdl".text = # kdl
''
layout {
pane size=1 borderless=true {
plugin location="tab-bar"
}
pane
pane size=1 borderless=true {
plugin location="status-bar"
}
}
'';
programs.zellij = {
enable = true;
enableBashIntegration = true;
enableFishIntegration = true;
enableZshIntegration = true;
# Not yet available in unstable
# attachExistingSession = true;
# exitShellOnExit = true;
settings = {
# default_layout = "compact-top";
# Remove border
pane_frames = false;
# Scrollback
scrollback_editor = config.home.sessionVariables.EDITOR;
# plugins = {
# autolock = {
# _props = {
# location = "https://github.com/fresh2dev/zellij-autolock/releases/download/0.2.2/zellij-autolock.wasm";
# };
# is_enabled = {
# _args = [ true ];
# };
# triggers = {
# _args = [ "vim|nvim|hx|git|fzf|zoxide|atuin|gh" ];
# };
# reaction_seconds = {
# _args = [ "0.3" ];
# };
# print_to_log = {
# _args = [ true ];
# };
# };
# };
# load_plugins = {
# autolock = { };
# };
keybinds = {
normal = {
};
shared = {
"bind \"Alt Shift p\"" = {
"Run" = {
_args = [
"${pkgs.fish}/bin/fish"
"-c"
"zellij-session"
];
close_on_exit = true;
};
};
"bind \"Super Shift ]\"" = {
"GoToNextTab" = { };
};
"bind \"Super Shift [\"" = {
"GoToPreviousTab" = { };
};
"bind \"Super t\"" = {
"NewTab" = { };
};
};
};
theme = "custom";
themes.custom = {
fg = "${config.theme.colors.base05}";
bg = "${config.theme.colors.base02}";
black = "${config.theme.colors.base00}";
red = "${config.theme.colors.base08}";
green = "${config.theme.colors.base0B}";
yellow = "${config.theme.colors.base0A}";
blue = "${config.theme.colors.base0D}";
magenta = "${config.theme.colors.base0E}";
cyan = "${config.theme.colors.base0C}";
white = "${config.theme.colors.base05}";
orange = "${config.theme.colors.base09}";
};
};
};
};
}

View File

@@ -1,21 +1,96 @@
# Credit: https://github.com/Ptujec/LaunchBar/blob/f7b5a0dba9919c2fec879513f68a044f78748539/Notifications/Dismiss%20all%20notifications.lbaction/Contents/Scripts/default.applescript
# Credit: https://github.com/Ptujec/LaunchBar/blob/a6dca4f21f3474eab0454fdd306bff6bab0d4f16/Notifications/Dismiss%20all%20notifications.lbaction/Contents/Scripts/default.applescript
tell application "System Events"
(*
Close notifications Applescript Action for LaunchBar
by Christian Bender (@ptujec)
2024-10-15
requires macOS 15.2
Copyright see: https://github.com/Ptujec/LaunchBar/blob/master/LICENSE
Helpful:
- https://applehelpwriter.com/2016/08/09/applescript-get-item-number-of-list-item/
- https://www.macscripter.net/t/coerce-gui-scripting-information-into-string/62842/3
- https://forum.keyboardmaestro.com/t/understanding-applescript-ui-scripting-to-click-menus/29039/23?page=2
*)
use AppleScript version "2.4" -- Yosemite (10.10) or later
use scripting additions
use framework "Foundation"
property NSArray : a reference to current application's NSArray
property alertAndBannerSet : {"AXNotificationCenterAlert", "AXNotificationCenterBanner"}
property closeActionSet : {"Close", "Clear All", "Schließen", "Alle entfernen", "Cerrar", "Borrar todo", "关闭", "清除全部", "Fermer", "Tout effacer", "Закрыть", "Очистить все", "إغلاق", "مسح الكل", "Fechar", "Limpar tudo", "閉じる", "すべてクリア", "बंद करें", "सभी हटाएं", "Zamknij", "Wyczyść wszystko"}
on run
tell application "System Events"
try
set _groups to groups of UI element 1 of scroll area 1 of group 1 of window "Notification Center" of application process "NotificationCenter"
set _main_group to group 1 of scroll area 1 of group 1 of group 1 of window 1 of application process "NotificationCenter"
on error eStr number eNum
display notification eStr with title "Error " & eNum sound name "Frog"
return
end try
repeat with _group in _groups
set _actions to actions of _group
set _headings to UI elements of _main_group whose role is "AXHeading"
set _headingscount to count of _headings
end tell
repeat _headingscount times
tell application "System Events" to set _roles to role of UI elements of _main_group
set _headingIndex to its getIndexOfItem:"AXHeading" inList:_roles
set _closeButtonIndex to _headingIndex + 1
tell application "System Events" to click item _closeButtonIndex of UI elements of _main_group
delay 0.4
end repeat
tell application "System Events"
try
set _groups to groups of _main_group
if _groups is {} then
if subrole of _main_group is in alertAndBannerSet then
set _actions to actions of _main_group
repeat with _action in _actions
if description of _action is in {"Schlie§en", "Alle entfernen", "Close", "Clear All"} then
if description of _action is in closeActionSet then
perform _action
end if
end repeat
end if
return
end if
repeat with _group in _groups
set _actions to actions of first item of _groups # always picking the first to avoid index error
repeat with _action in _actions
if description of _action is in closeActionSet then
perform _action
end if
end repeat
end repeat
on error
if subrole of _main_group is in alertAndBannerSet then
set _actions to actions of _main_group
repeat with _action in _actions
if description of _action is in closeActionSet then
perform _action
end if
end repeat
end if
end try
end tell
end tell
end run
on getIndexOfItem:anItem inList:aList
set anArray to NSArray's arrayWithArray:aList
set ind to ((anArray's indexOfObject:anItem) as number) + 1
if ind is greater than (count of aList) then
display dialog "Item '" & anItem & "' not found in list." buttons "OK" default button "OK" with icon 2 with title "Error"
return 0
else
return ind
end if
end getIndexOfItem:inList:

View File

@@ -1,298 +0,0 @@
/* Credit: https://gist.github.com/lancethomps/a5ac103f334b171f70ce2ff983220b4f */
function run(input, parameters) {
const appNames = [];
const skipAppNames = [];
const verbose = true;
const scriptName = "close_notifications_applescript";
const CLEAR_ALL_ACTION = "Clear All";
const CLEAR_ALL_ACTION_TOP = "Clear";
const CLOSE_ACTION = "Close";
const notNull = (val) => {
return val !== null && val !== undefined;
};
const isNull = (val) => {
return !notNull(val);
};
const notNullOrEmpty = (val) => {
return notNull(val) && val.length > 0;
};
const isNullOrEmpty = (val) => {
return !notNullOrEmpty(val);
};
const isError = (maybeErr) => {
return notNull(maybeErr) && (maybeErr instanceof Error || maybeErr.message);
};
const systemVersion = () => {
return Application("Finder").version().split(".").map(val => parseInt(val));
};
const systemVersionGreaterThanOrEqualTo = (vers) => {
return systemVersion()[0] >= vers;
};
const isBigSurOrGreater = () => {
return systemVersionGreaterThanOrEqualTo(11);
};
const V11_OR_GREATER = isBigSurOrGreater();
const APP_NAME_MATCHER_ROLE = V11_OR_GREATER ? "AXStaticText" : "AXImage";
const hasAppNames = notNullOrEmpty(appNames);
const hasSkipAppNames = notNullOrEmpty(skipAppNames);
const hasAppNameFilters = hasAppNames || hasSkipAppNames;
const appNameForLog = hasAppNames ? ` [${appNames.join(",")}]` : "";
const logs = [];
const log = (message, ...optionalParams) => {
let message_with_prefix = `${new Date().toISOString().replace("Z", "").replace("T", " ")} [${scriptName}]${appNameForLog} ${message}`;
console.log(message_with_prefix, optionalParams);
logs.push(message_with_prefix);
};
const logError = (message, ...optionalParams) => {
if (isError(message)) {
let err = message;
message = `${err}${err.stack ? (" " + err.stack) : ""}`;
}
log(`ERROR ${message}`, optionalParams);
};
const logErrorVerbose = (message, ...optionalParams) => {
if (verbose) {
logError(message, optionalParams);
}
};
const logVerbose = (message) => {
if (verbose) {
log(message);
}
};
const getLogLines = () => {
return logs.join("\n");
};
const getSystemEvents = () => {
let systemEvents = Application("System Events");
systemEvents.includeStandardAdditions = true;
return systemEvents;
};
const getNotificationCenter = () => {
try {
return getSystemEvents().processes.byName("NotificationCenter");
} catch (err) {
logError("Could not get NotificationCenter");
throw err;
}
};
const getNotificationCenterGroups = (retryOnError = false) => {
try {
let notificationCenter = getNotificationCenter();
if (notificationCenter.windows.length <= 0) {
return [];
}
if (!V11_OR_GREATER) {
return notificationCenter.windows();
}
return notificationCenter.windows[0].uiElements[0].uiElements[0].uiElements();
} catch (err) {
logError("Could not get NotificationCenter groups");
if (retryOnError) {
logError(err);
log("Retrying getNotificationCenterGroups...");
return getNotificationCenterGroups(false);
} else {
throw err;
}
}
};
const isClearButton = (description, name) => {
return description === "button" && name === CLEAR_ALL_ACTION_TOP;
};
const matchesAnyAppNames = (value, checkValues) => {
if (isNullOrEmpty(checkValues)) {
return false;
}
let lowerAppName = value.toLowerCase();
for (let checkValue of checkValues) {
if (lowerAppName === checkValue.toLowerCase()) {
return true;
}
}
return false;
};
const matchesAppName = (role, value) => {
if (role !== APP_NAME_MATCHER_ROLE) {
return false;
}
if (hasAppNames) {
return matchesAnyAppNames(value, appNames);
}
return !matchesAnyAppNames(value, skipAppNames);
};
const notificationGroupMatches = (group) => {
try {
let description = group.description();
if (V11_OR_GREATER && isClearButton(description, group.name())) {
return true;
}
if (V11_OR_GREATER && description !== "group") {
return false;
}
if (!V11_OR_GREATER) {
let matchedAppName = !hasAppNameFilters;
if (!matchedAppName) {
for (let elem of group.uiElements()) {
if (matchesAppName(elem.role(), elem.description())) {
matchedAppName = true;
break;
}
}
}
if (matchedAppName) {
return notNull(findCloseActionV10(group, -1));
}
return false;
}
if (!hasAppNameFilters) {
return true;
}
let firstElem = group.uiElements[0];
return matchesAppName(firstElem.role(), firstElem.value());
} catch (err) {
logErrorVerbose(`Caught error while checking window, window is probably closed: ${err}`);
logErrorVerbose(err);
}
return false;
};
const findCloseActionV10 = (group, closedCount) => {
try {
for (let elem of group.uiElements()) {
if (elem.role() === "AXButton" && elem.title() === CLOSE_ACTION) {
return elem.actions["AXPress"];
}
}
} catch (err) {
logErrorVerbose(`(group_${closedCount}) Caught error while searching for close action, window is probably closed: ${err}`);
logErrorVerbose(err);
return null;
}
log("No close action found for notification");
return null;
};
const findCloseAction = (group, closedCount) => {
try {
if (!V11_OR_GREATER) {
return findCloseActionV10(group, closedCount);
}
let checkForPress = isClearButton(group.description(), group.name());
let clearAllAction;
let closeAction;
for (let action of group.actions()) {
let description = action.description();
if (description === CLEAR_ALL_ACTION) {
clearAllAction = action;
break;
} else if (description === CLOSE_ACTION) {
closeAction = action;
} else if (checkForPress && description === "press") {
clearAllAction = action;
break;
}
}
if (notNull(clearAllAction)) {
return clearAllAction;
} else if (notNull(closeAction)) {
return closeAction;
}
} catch (err) {
logErrorVerbose(`(group_${closedCount}) Caught error while searching for close action, window is probably closed: ${err}`);
logErrorVerbose(err);
return null;
}
log("No close action found for notification");
return null;
};
const closeNextGroup = (groups, closedCount) => {
try {
for (let group of groups) {
if (notificationGroupMatches(group)) {
let closeAction = findCloseAction(group, closedCount);
if (notNull(closeAction)) {
try {
closeAction.perform();
return [true, 1];
} catch (err) {
logErrorVerbose(`(group_${closedCount}) Caught error while performing close action, window is probably closed: ${err}`);
logErrorVerbose(err);
}
}
return [true, 0];
}
}
return false;
} catch (err) {
logError("Could not run closeNextGroup");
throw err;
}
};
try {
let groupsCount = getNotificationCenterGroups(true).filter(group => notificationGroupMatches(group)).length;
if (groupsCount > 0) {
logVerbose(`Closing ${groupsCount}${appNameForLog} notification group${(groupsCount > 1 ? "s" : "")}`);
let startTime = new Date().getTime();
let closedCount = 0;
let maybeMore = true;
let maxAttempts = 2;
let attempts = 1;
while (maybeMore && ((new Date().getTime() - startTime) <= (1000 * 30))) {
try {
let closeResult = closeNextGroup(getNotificationCenterGroups(), closedCount);
maybeMore = closeResult[0];
if (maybeMore) {
closedCount = closedCount + closeResult[1];
}
} catch (innerErr) {
if (maybeMore && closedCount === 0 && attempts < maxAttempts) {
log(`Caught an error before anything closed, trying ${maxAttempts - attempts} more time(s).`)
attempts++;
} else {
throw innerErr;
}
}
}
} else {
throw Error(`No${appNameForLog} notifications found...`);
}
} catch (err) {
logError(err);
logError(err.message);
getLogLines();
throw err;
}
return getLogLines();
}

View File

@@ -42,6 +42,7 @@ local function worklayout()
-- set the layout
local left = {
{ "WezTerm", nil, WORK_ONLY_MONITOR, u(0, 0, 1 / 2, 1), nil, nil, visible = true },
{ "Ghostty", nil, WORK_ONLY_MONITOR, u(0, 0, 1 / 2, 1), nil, nil, visible = true },
}
local right = {
{ "Slack", nil, WORK_ONLY_MONITOR, u(1 / 2, 0, 1 / 2, 1), nil, nil, visible = true },

View File

@@ -31,6 +31,8 @@ in
# Used for aerc
xdg.enable = lib.mkDefault pkgs.stdenv.isDarwin;
programs.fish.shellAbbrs.t = "trash";
# Add homebrew paths to CLI path
home.sessionPath = [
"/opt/homebrew/bin/"

View File

@@ -18,6 +18,8 @@ in
nmasur.presets.programs = {
zed-editor.enable = lib.mkDefault true;
ghostty.enable = lib.mkDefault true;
helix.enable = lib.mkDefault true;
zellij.enable = lib.mkDefault true;
};
home.packages = [
@@ -29,10 +31,11 @@ in
pkgs.charm # Manage account and filesystem
pkgs.pop # Send emails from a TUI
pkgs.yazi # TUI file explorer
];
programs.gh-dash.enable = lib.mkDefault true;
programs.helix.enable = lib.mkDefault true;
programs.himalaya.enable = lib.mkDefault true;
};

View File

@@ -15,25 +15,26 @@ in
home.packages = [
pkgs.age # Encryption
pkgs.bc # Calculator
pkgs.bottom # System monitor (top)
pkgs.delta # Fancy diffs
pkgs.difftastic # Other fancy diffs
pkgs.doggo # DNS client (dig)
pkgs.du-dust # Disk usage tree (ncdu)
pkgs.dua # File sizes (du)
pkgs.duf # Basic disk information (df)
pkgs.jless # JSON viewer
pkgs.jo # JSON output
pkgs.mpd # TUI slideshows
pkgs.nmasur.jqr # FZF fq JSON tool
pkgs.nmasur.osc # Clipboard over SSH
pkgs.qrencode # Generate qr codes
pkgs.nmasur.ren-find # Rename files
pkgs.nmasur.rep-grep # Replace text in files
pkgs.pandoc # Convert text documents
pkgs.qrencode # Generate qr codes
pkgs.spacer # Output lines in terminal
pkgs.tealdeer # Cheatsheets
pkgs.tree # Print tree in terminal
pkgs.vimv-rs # Batch rename files
pkgs.dua # File sizes (du)
pkgs.du-dust # Disk usage tree (ncdu)
pkgs.duf # Basic disk information (df)
pkgs.pandoc # Convert text documents
pkgs.mpd # TUI slideshows
pkgs.doggo # DNS client (dig)
pkgs.bottom # System monitor (top)
pkgs.nmasur.jqr # FZF fq JSON tool
];
programs.fish.shellAliases = {

View File

@@ -6,6 +6,7 @@
}:
let
inherit (config.nmasur.settings) username;
cfg = config.nmasur.presets.services.dock;
in
@@ -49,9 +50,9 @@ in
"/System/Applications/Messages.app"
"/System/Applications/Mail.app"
"/Applications/zoom.us.app"
"${config.home-manager.users.${username}.programs.ghostty.package}/Applications/Ghostty.app"
"${pkgs.discord}/Applications/Discord.app"
"${pkgs.obsidian}/Applications/Obsidian.app"
"${pkgs.wezterm}/Applications/WezTerm.app"
];
};
};

View File

@@ -36,6 +36,7 @@ in
homebrew.casks = [
"scroll-reverser" # Different scroll style for mouse vs. trackpad
"notunes" # Don't launch Apple Music with the play button
"topnotch" # Darkens the menu bar to complete black
];
};

View File

@@ -60,28 +60,23 @@ in
services = {
bazarr = {
enable = true;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
};
jellyseerr.enable = true;
prowlarr.enable = true;
sabnzbd = {
enable = true;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
# The config file must be editable within the application
# It contains server configs and credentials
configFile = "/data/downloads/sabnzbd/sabnzbd.ini";
};
sonarr = {
enable = true;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
};
radarr = {
enable = true;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
};
readarr = {
enable = true;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
};
};
@@ -96,7 +91,6 @@ in
{
# Group means that routes with the same name are mutually exclusive,
# so they are split between the appropriate services.
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -112,7 +106,6 @@ in
];
}
{
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -127,7 +120,6 @@ in
];
}
{
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -142,7 +134,6 @@ in
];
}
{
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -158,7 +149,6 @@ in
];
}
{
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -178,7 +168,6 @@ in
];
}
{
group = "download";
match = [
{
host = [ hostnames.download ];
@@ -193,7 +182,6 @@ in
];
}
{
group = "download";
match = [ { host = [ hostnames.download ]; } ];
handle = [
{
@@ -255,7 +243,7 @@ in
prefix = "API_KEY=";
};
secrets.readarrApiKey = {
source = ./radarr-api-key.age;
source = ./readarr-api-key.age;
dest = "/var/private/readarr-api";
prefix = "API_KEY=";
};

View File

@@ -0,0 +1,17 @@
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IHNzaC1lZDI1NTE5IE1nSGFPdyBRRXo3
ZmpER1kyWC9JUld3WVVTS0owb1RRZFhzNHRtT0dickJhbnQ1UWxRCjBIR3JxbGho
c2h0bk8vV2lta2NzcXl0OXZYTzJ0ZkhNV3lPTVl0ZjQ0b00KLT4gc3NoLWVkMjU1
MTkgWXlTVU1RIHlMWW4zNnJCTGNwcFRxOTQrTldzRFlENGd1TG4yRFJSQlhnSHVL
TGlWdzAKMlZ4L0thbFZQWjZ0c3pJaE1XNmRtZmNKVTIxeTkwMFFGYWxKZTRMV3h0
VQotPiBzc2gtZWQyNTUxOSBuanZYNUEgbm5pVE0zYzNQTW15c01DRk1HeDRLVlRW
aGpkVUFHdG13THNDL1JlbEUyawp6SWQ5Nm1veDdwbCtDbjZPUkhQU0hkRXE1b1RY
ZkxHY0ZqMFdvcGJ6WitvCi0+IHNzaC1lZDI1NTE5IENxSU9VQSBWeE1LaU5TRkpK
bElLQWNidHZQeTF6Yk80ZzVlL005RTEyZzlDR2dTSGg0CkdZK2VDSGtMTE43VWRY
ZnA0cDRKc016OVYvZGpDcDFad3o5YmpoOGhVNGsKLT4gc3NoLWVkMjU1MTkgejFP
Y1p3IDBEV3pWVEI3QjFRUnRjK0VPZFF6U09iTHljOE9jZ1lka1lpbU9BSEtOeFUK
RlF0WEFBMElzU1pOdDBEenUrWEhsaFkrTWpUc0gzb1hVRjVpUGpyc25FcwotLS0g
aXhPbUtHWXc4MXJ4bUtZOWlkdVNOMmo1N1U2NXlxdU5VVXltZXh5aDRyWQoCjoWs
rOf41MK9789YHLzXMZNbMoWt9tHGfOGZKOyPhYFq/j2d88ZLtzEHAuHKvQ561ffK
Si0uTiTcTCyhCr/rsQ==
-----END AGE ENCRYPTED FILE-----

View File

@@ -19,10 +19,6 @@ in
services.audiobookshelf = {
enable = true;
# Setting a generic group to make it easier for the different programs
# that make use of the same files
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
# This is the default /var/lib/audiobookshelf
dataDir = "audiobookshelf";
};

View File

@@ -26,7 +26,7 @@ in
config = lib.mkIf cfg.enable {
services.calibre-web = {
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
enable = true;
openFirewall = true;
options = {
reverseProxyAuth.enable = false;

View File

@@ -68,7 +68,7 @@ in
# Tell Caddy to use Cloudflare DNS for ACME challenge validation
services.caddy.package = pkgs.caddy.withPlugins {
plugins = [ "github.com/caddy-dns/cloudflare@v0.0.0-20250228175314-1fb64108d4de" ];
hash = "sha256-3nvVGW+ZHLxQxc1VCc/oTzCLZPBKgw4mhn+O3IoyiSs=";
hash = "sha256-YYpsf8HMONR1teMiSymo2y+HrKoxuJMKIea5/NEykGc=";
};
nmasur.presets.services.caddy.tlsPolicies = [
{

View File

@@ -94,9 +94,6 @@ in
secrets.cloudflared = {
source = cfg.tunnel.credentialsFile;
dest = "${config.secretsDirectory}/cloudflared";
owner = "cloudflared";
group = "cloudflared";
permissions = "0440";
};
systemd.services.cloudflared-secret = {
requiredBy = [ "cloudflared-tunnel-${cfg.tunnel.id}.service" ];

View File

@@ -13,7 +13,6 @@ in
services.immich = {
enable = true;
port = 2283;
group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
database.enable = true;
redis.enable = true;
machine-learning.enable = true;

View File

@@ -18,10 +18,11 @@ in
config = lib.mkIf cfg.enable {
services.jellyfin.group = lib.mkIf config.nmasur.profiles.shared-media.enable "shared";
users.users.jellyfin = {
isSystemUser = true;
};
services.jellyfin.enable = true;
# users.users.jellyfin = {
# isSystemUser = true;
# };
nmasur.presets.services.caddy.routes = [
# Prevent public access to Prometheus metrics.
@@ -77,9 +78,6 @@ in
"video"
]; # Access to /dev/dri
# Fix issue where Jellyfin-created directories don't allow access for media group
systemd.services.jellyfin.serviceConfig.UMask = lib.mkForce "0007";
# Requires MetricsEnable is true in /var/lib/jellyfin/config/system.xml
nmasur.presets.services.prometheus-exporters.scrapeTargets = [ "127.0.0.1:8096" ];
};

View File

@@ -34,11 +34,11 @@ in
];
services.prometheus = {
exporters.node.enable = config.prometheus.exporters.enable;
exporters.node.enable = true;
exporters.node.enabledCollectors = [ ];
exporters.node.disabledCollectors = [ "cpufreq" ];
exporters.systemd.enable = config.prometheus.exporters.enable;
exporters.process.enable = config.prometheus.exporters.enable;
exporters.systemd.enable = true;
exporters.process.enable = true;
exporters.process.settings.process_names = [
# Remove nix store path from process name
{

View File

@@ -3,8 +3,8 @@
{
config,
pkgs,
lib,
pkgs-stable,
...
}:
@@ -37,7 +37,7 @@ in
services.vmagent = {
enable = true;
package = pkgs-stable.vmagent;
package = pkgs.stable.vmagent;
prometheusConfig = prometheusConfig;
remoteWrite = {
url = "https://${hostnames.prometheus}/api/v1/write";

View File

@@ -17,7 +17,7 @@ in
services.nextcloud = {
enable = true;
package = pkgs.nextcloud30; # Required to specify
package = pkgs.nextcloud31; # Required to specify
configureRedis = true;
datadir = "/data/nextcloud";
database.createLocally = true;
@@ -42,10 +42,10 @@ in
calendar = config.services.nextcloud.package.packages.apps.calendar;
contacts = config.services.nextcloud.package.packages.apps.contacts;
# These apps are defined and pinned by overlay in flake.
news = pkgs.nextcloudApps.news;
external = pkgs.nextcloudApps.external;
cookbook = pkgs.nextcloudApps.cookbook;
snappymail = pkgs.nextcloudApps.snappymail;
# news = pkgs.nextcloudApps.news;
# external = pkgs.nextcloudApps.external;
# cookbook = pkgs.nextcloudApps.cookbook;
# snappymail = pkgs.nextcloudApps.snappymail;
};
phpOptions = {
"opcache.interned_strings_buffer" = "16";
@@ -220,7 +220,7 @@ in
# Log metrics to prometheus
networking.hosts."127.0.0.1" = [ hostnames.content ];
services.prometheus.exporters.nextcloud = {
enable = config.prometheus.exporters.enable;
enable = true;
username = config.services.nextcloud.config.adminuser;
url = "https://${hostnames.content}";
passwordFile = config.services.nextcloud.config.adminpassFile;

View File

@@ -19,7 +19,7 @@ in
boot.kernelPackages = pkgs.linuxPackages; # Defaults to latest LTS
boot.kernelParams = [ "nohibernate" ]; # ZFS does not work with hibernation
boot.supportedFilesystems = [ "zfs" ];
services.prometheus.exporters.zfs.enable = config.prometheus.exporters.enable;
services.prometheus.exporters.zfs.enable = true;
nmasur.presets.services.prometheus-exporters.scrapeTargets = [
"127.0.0.1:${builtins.toString config.services.prometheus.exporters.zfs.port}"
];

View File

@@ -23,6 +23,7 @@ in
};
services = {
nix.enable = lib.mkDefault true;
prometheus-exporters.enable = lib.mkDefault true;
};
};

View File

@@ -30,7 +30,7 @@ in
litestream.enable = lib.mkDefault true;
minecraft-server.enable = lib.mkDefault true;
n8n.enable = lib.mkDefault true;
nix-autoupgrade.enable = lib.mkDefault true; # On by default for communications
nix-autoupgrade.enable = lib.mkDefault false; # On by default for communications
ntfy-sh.enable = lib.mkDefault true;
postgresql.enable = lib.mkDefault true;
thelounge.enable = lib.mkDefault true;

View File

@@ -17,9 +17,9 @@ in
config = lib.mkIf cfg.enable {
nmasur.presets.services = {
grub.enable = lib.mkDefault true;
# Configure physical power buttons
logind.enable = lib.mkDefault true;
avahi.enable = lib.mkDefault true;
};
# Enable automatic timezone updates based on location

View File

@@ -21,5 +21,20 @@ in
# Give the human user access to the shared group
users.users.${username}.extraGroups = [ config.users.groups.shared.name ];
services = {
audiobookshelf.group = "shared";
bazarr.group = "shared";
jellyfin.group = "shared";
radarr.group = "shared";
readarr.group = "shared";
sabnzbd.group = "shared";
sonarr.group = "shared";
immich.group = "shared";
calibre-web.group = "shared";
};
# Fix issue where Jellyfin-created directories don't allow access for media group
systemd.services.jellyfin.serviceConfig.UMask = lib.mkForce "0007";
};
}

View File

@@ -31,7 +31,6 @@ in
passwordHash = lib.mkOption {
type = lib.types.str;
description = ''Hashed password created from htpasswd -nBC 10 "" | tr -d ':\n' '';
default = "$2y$10$ze1cMob0k6pnXRjLowYfZOVZWg4G.dsPtH3TohbUeEbI0sdkG9.za";
};
};
@@ -39,7 +38,7 @@ in
environment.etc."filebrowser/.filebrowser.json".text = builtins.toJSON settings;
systemd.services.filebrowser = lib.mkIf config.filebrowser.enable {
systemd.services.filebrowser = {
description = "Filebrowser cloud file services";
after = [ "network.target" ];
wantedBy = [ "multi-user.target" ];
@@ -58,9 +57,6 @@ in
path = [ pkgs.getent ]; # Fix: getent not found in $PATH
};
# Configure Cloudflare DNS to point to this machine
services.cloudflare-dyndns.domains = [ hostnames.files ];
};
}