{ pkgs, lib, ... }: let inherit (import ./const.nix) fontSize homedir gpgid; locale = "en_US.UTF-8"; in { nixpkgs.overlays = [ (import ../overlay.nix) ]; home = { stateVersion = "18.09"; sessionVariables = { GPGID = gpgid; EDITOR = lib.mkDefault "vim"; LANG = locale; # LC_ALL = locale; # bash prints an error when I try to set this LANGUAGE = locale; PATH = "${homedir}/bin:${homedir}/.local/bin:$PATH"; PAGER = "less"; # "bat --theme=ansi"; #XTERM_LOCALE = locale; PYTHONSTARTUP = "${homedir}/.pythonrc"; FD_OPTIONS = "--follow --exclude .git"; BAT_PAGER = "less -R"; FORGIT_FZF_DEFAULT_OPTS = '' --exact --border --cycle --reverse ''; }; # From the command line: # setxkbmap -option caps:ctrl_modifier keyboard.options = [ "caps:ctrl_modifier" ]; file = { yubikeys = { source = ./authorized_yubikeys; target = ".yubico/authorized_yubikeys"; }; editorconfig = { source = ./editorconfig; target = ".editorconfig"; }; pythonrc = { source = ./pythonrc; target = ".pythonrc"; }; pdbrc = { source = ./pythonrc; target = ".pdbrc"; }; # Idk why this doesn't work, less says it can't use my lesskey file #less = { # source = ./lesskey; # target = ".less"; #}; userstyles = { source = ./userstyles.css; target = ".userstyles.css"; }; }; }; fonts.fontconfig.enable = true; programs.home-manager.enable = true; programs.bat = { enable = true; config = { theme = "catppuccin"; }; themes = { catppuccin = builtins.readFile (pkgs.fetchFromGitHub { owner = "catppuccin"; repo = "bat"; rev = "d714cc1d358ea51bfc02550dabab693f70cccea0"; hash = "sha256-Q5B4NDrfCIK3UAMs94vdXnR42k4AXCqZz6sRn8bzmf4="; } + "/themes/Catppuccin Latte.tmTheme"); }; }; programs.starship = { # export PS1='$(printf "%3.*s" $? $?)ϟ ' enable = true; settings = { format = lib.concatStrings [ #"$username" "$hostname" "$directory" "$git_branch" "$git_state" "$git_status" "$cmd_duration" "$line_break" "$character" ]; directory.style = "blue"; character = { success_symbol = "[ϟ](white)"; error_symbol = "[ϟ](red)"; }; git_branch = { format = "[$branch]($style)"; style = "bright-black"; }; git_status = { format = ''[[(*$conflicted$untracked$modified$staged$renamed$deleted)](218) ($ahead_behind$stashed)]($style)''; style = "cyan"; conflicted = "​"; untracked = "​"; modified = "​"; staged = "​"; renamed = "​"; deleted = "​"; stashed = "≡"; }; git_state = { format = "\([$state( $progress_current/$progress_total)]($style)\) "; style = "bright-black"; }; cmd_duration = { format = "[$duration]($style) "; style = "yellow"; }; }; }; programs.readline = { enable = true; variables = { keyseq-timeout = 1200; colored-stats = true; colored-completion-prefix = true; expand-tilde = true; }; bindings = { # wrap a command in '$(...| fzf)' "\\C-xf" = ''"\C-e | fzf)\C-a(\C-a$\C-b\C-a"''; "\\e\\C-f" = "dump-functions"; # help "\\e\\C-o" = "dabbrev-expand"; # expand "\\e\\C-v" = "dump-variables"; # help "\\em" = "beginning-of-line"; # emacs-like history navigation "\\en" = "next-history"; "\\ep" = "previous-history"; # groq-specific stuff "\\er" = "redraw-current-line"; "\\C-xt" = ''"$(_bake_targets)\e\C-e\er"''; }; extraConfig = '' $if Guile "\C-o": "()\C-b" $endif ''; }; programs.fzf = { enable = true; enableBashIntegration = true; colors = { # https://github.com/catppuccin/fzf # TODO: use catppuccin/nix, and switch based on xtheme # catppuccin-mocha "bg+" = "#313244"; "bg" = "#1e1e2e"; "hl" = "#f38ba8"; "fg" = "#cdd6f4"; "header" = "#f38ba8"; "info" = "#cba6f7"; "pointer" = "#f5e0dc"; "marker" = "#b4befe"; "fg+" = "#cdd6f4"; "hl+" = "#f38ba8"; # these are no longer supported # "prompt" = "#cba6f7"; # "spinner" = "#f5e0dc"; # these are new colors, but doesn't work for me # https://github.com/catppuccin/fzf/issues/10 # "selected-bg" = "#45475a"; # catppucin-latte: # "bg+" = "#ccd0da"; # "bg" = "#eff1f5"; # "hl" = "#d20f39"; # "fg" = "#4c4f69"; # "header" = "#d20f39"; # "info" = "#8839ef"; # "pointer" = "#dc8a78 "; # "marker" = "#dc8a78"; # "fg+" = "#4c4f69"; # "hl+" = "#d20f39"; # "selected-bg" = "#51576d"; # "selected-hl" = "#e78284"; # "prompt" = "#8839ef"; # "spinner" = "#dc8a78"; }; defaultCommand = "rg --files"; changeDirWidgetCommand = "fd --type d"; # M-c changeDirWidgetOptions = ["--preview 'tree -C {} | head -100'"]; fileWidgetCommand = "fd --type f"; fileWidgetOptions = ["--preview 'head -n100 {}'"]; historyWidgetOptions = ["--sort" "--exact"]; tmux.enableShellIntegration = true; tmux.shellIntegrationOptions = [ "-p 70%" ]; }; programs.git = { enable = true; userName = "Ben Sima"; userEmail = "ben@bsima.me"; ignores = [ "*~" "*.swp" ]; package = pkgs.gitAndTools.gitFull; signing = { key = gpgid; # for some reason this fails... #gpgPath = # let # script = pkgs.writeScriptBin "my-ots-git-gpg-wrapper" '' # #!/usr/bin/env bash # set -euxo pipefail # ${pkgs.opentimestamps-client}/bin/ots-git-gpg-wrapper --gpg-program ${pkgs.gnupg}/bin/gpg $@ # ''; # in # "${script}/bin/my-ots-git-gpg-wrapper"; }; aliases = { authors = "shortlog -s -n"; slog = "log --stat"; glog = ''log --decorate --all --graph --pretty=format:"%Cred%h%Creset %an: %s - %Creset %C(yellow)%d%Creset %Cgreen(%cr)%Creset" --abbrev-commit --date=relative''; logbr = "log -r origin/HEAD..HEAD"; mylog = ''!git log --author=$USER --decorate --pretty=format:"%Cred%h%Creset %s%Creset%C(yellow)%d%Creset %Cgreen(%cr)%Creset" --abbrev-commit --date=relative''; mrd = "!cat <(git shortlog origin/HEAD..HEAD) <(git diff --stat origin/HEAD...HEAD)"; extend = "!git commit --fixup $1 && git rebase --autosquash $1~"; mr = lib.concatStringsSep " " [ "!git push" "-o merge_request.create" "-o merge_request.merge_when_pipeline_succeeds" "-o merge_request.label=ReleaseUpdate::NotRequired" "-o merge_request.assign=$USER" # disable these two args bc gitlab just uses the commit message anyway # ''-o merge_request.title="$(git log -n1 --format=%s)"'' # ''-o merge_request.description="$(git log -n --format=%b)"'' ]; }; extraConfig = { commit.template = "${./git-commit-template}"; commit.verbose = "true"; fetch.showForcedUpdate = "false"; init.defaultBranch = "main"; log.date = "local"; merge.tool = "fugitive"; mergetool.fugitive.cmd = ''vim -f -c "Gvdiffsplit!" "$MERGED"''; pull.rebase = "true"; push.default = "current"; remote.pushDefault = "origin"; sendemail = { #smtpuser = "ben@bsima.me"; #smtpserverport = 587; smtpserver = "${homedir}/bin/sendmail"; chainreplyto = false; composeencoding = "UTF-8"; annotate = "yes"; cccmd = "git-contacts"; }; }; }; programs.jujutsu = { enable = true; }; programs.tmux = { enable = true; aggressiveResize = false; baseIndex = 0; clock24 = true; customPaneNavigationAndResize = false; disableConfirmationPrompt = false; escapeTime = 0; historyLimit = 10000; keyMode = "emacs"; newSession = false; resizeAmount = 5; reverseSplit = false; secureSocket = false; sensibleOnTop = true; #shell = "${pkgs.bash}/bin/bash"; shortcut = "a"; terminal = "xterm-256color"; tmuxinator.enable = false; tmuxp.enable = false; extraConfig = '' # Automatically set window title set-window-option -g automatic-rename on set-option -g set-titles on set -g xterm-keys on setw -g mouse on ## Panes # Split panes bind-key | split-window -h -c "#{pane_current_path}" bind-key - split-window -v -c "#{pane_current_path}" # Send/join panes bind-key j command-prompt -p "join pane from:" "join-pane -s '%%'" bind-key s command-prompt -p "send pane to:" "join-pane -t '%%'" # Use Alt-vim keys without prefix key to switch panes bind -n M-h select-pane -L bind -n M-j select-pane -D bind -n M-k select-pane -U bind -n M-l select-pane -R # Use Alt-vim capitalized keys without prefix key to resize panes bind -n M-H resize-pane -L bind -n M-J resize-pane -D bind -n M-K resize-pane -U bind -n M-L resize-pane -R # Shift arrow to switch windows bind -n S-Left previous-window bind -n S-Right next-window # Set current window pane to 80 columns bind-key E resize-pane -x 80 # cycle pane layout bind-key N next-layout bind-key P previous-layout # Toggle synchronizing panes bind-key y setw synchronize-panes ## Text manipulation # vim-like copy/paste setw -g mode-keys vi bind [ copy-mode bind ] paste-buffer # copy/paste with xclip bind-key -Tcopy-mode-vi y send-keys -X copy-pipe-and-cancel 'xclip -sel clip -i' # select buffer to paste from bind Space choose-buffer # status line text set -g status-left-length 30 set -g status-left '#S | #(whoami)@#(hostname) | ' set -g status-right '~%Y.%m.%d..%H.%M' set -g renumber-windows on # white-ish background with dark-grey text set -g status-style bg=colour0,fg=colour13 # highlight current window set -g window-status-current-style fg=colour0,bg=colour13 set -g window-status-format '#I) #W ' set -g window-status-current-format '#I) #W ' # special thing for groq's SFT thing set -g update-environment "SFT_AUTH_SOCK SSH_AUTH_SOCK SSH_CONNECTION" ''; plugins = with pkgs.tmuxPlugins; [ extrakto tmux-fzf ]; }; programs.direnv = { enable = true; enableBashIntegration = true; nix-direnv.enable = true; }; programs.vim = { enable = true; #vimAlias = true; #viAlias = true; #vimdiffAlias = true; plugins = with pkgs.vimPlugins; [ base16-vim catppuccin-vim editorconfig-vim vim-sensible vim-fugitive vim-sexp-mappings-for-regular-people # vim-ripgrep # not in nixpkgs :( rainbow_parentheses vim-plug # just in case vim-addon-local-vimrc fzf-vim (pkgs.vimUtils.buildVimPlugin { pname = "photon.vim"; version = "2022.03.14"; src = pkgs.fetchFromGitHub { owner = "axvr"; repo = "photon.vim"; rev = "32b42c8a12bf9588259b76f3df6807960e0d7386"; sha256 = "sha256-kM7WP03uE20yr0nCusB3ncHzgtEYxqNzoNoQGen9p+o="; }; meta.homepage = "https://github.com/axvr/photon.vim"; }) (pkgs.vimUtils.buildVimPlugin { pname = "skull-vim"; version = "2022.03.14"; src = pkgs.fetchFromGitHub { owner = "kadekillary"; repo = "skull-vim"; rev = "abb9d7120c63aad6f9acc26d31c948a93f352e94"; sha256 = "sha256-tu5aDRjHZtXKoyQBbMEhzjGrRl4GZD121ybs7oNylvs="; }; meta.homepage = "https://github.com/kadekillary/skull-vim"; }) ]; extraConfig = builtins.readFile ./vimrc; }; programs = { info.enable = true; man.enable = true; nix-index = { enable = true; enableBashIntegration = true; }; bash = { enable = true; #profileExtra = '' # # put SSH_AUTH_SOCK here? #''; initExtra = '' #DIR=~/.nix-profile/etc/profile.d #[[ -f "$DIR/nix.sh" ]] && . "$DIR/nix.sh" #[[ -f "$DIR/hm-session-vars.sh" ]] && . "$DIR/hm-session-vars.sh" [[ -f "${homedir}/.bashrc.local" ]] && . "${homedir}/.bashrc.local" source "${pkgs.forgit}/share/bash/forgit.plugin.zsh" function fcd() { local dir; echo "exit with ^D" while : do dir="$(ls -a1p | grep '/$' | grep -v '^./$' | fzf --height 40% --reverse --no-multi --preview 'pwd' --preview-window=up,1,border-none --no-info)" if [[ -z "$dir" ]]; then break else echo -n "$dir " cd "$dir" ls fi done } function up() { N=$1 P=$PWD for (( i=1; i<=$N; i++ )) do P+="/.." done cd "$P" } function regex() { gawk 'match($0,/'$1'/, ary) {print ary['\$\{2:-'0'}']}'; } # my old prompt, before i switched to starship #export PS1='$(printf "%3.*s" $? $?)ϟ ' # kill a process with fzf fkill() { local pid pid=$(ps -ef | sed 1d | fzf -m --bind "ctrl-a:select-all"| awk '{print $2}') if [ "x$pid" != "x" ] then echo $pid | xargs kill -9 fi } # https://gist.github.com/junegunn/8b572b8d4b5eddd8b85e5f4d40f17236 is_in_git_repo() { git rev-parse HEAD > /dev/null 2>&1 } fzf_down() { fzf --height 50% --min-height 20 --border \ --bind 'ctrl-/:change-preview-window(hidden|90%|)' \ --bind 'pgup:preview-page-up' \ --bind 'pgdn:preview-page-down' \ "$@" } _gf() { is_in_git_repo || return git -c color.status=always status --short | fzf_down -m --ansi --nth 2..,.. \ --preview '(git diff --color=always -- {-1} | sed 1,4d; cat {-1}) | head -500' | cut -c4- | sed 's/.* -> //' } _gp() { is_in_git_repo || return stg series | fzf_down -m --ansi --preview 'stg show -O --color=always {2}' | cut -d' ' -f2 } _gb() { is_in_git_repo || return git branch -a --color=always | grep -v '/HEAD\s' | sort | fzf_down --ansi --multi --tac --preview-window right:70% \ --preview 'git log --oneline --graph --date=short --color=always --pretty="format:%C(auto)%cd %h%d %s" $(sed s/^..// <<< {} | cut -d" " -f1) | head -'$LINES | sed 's/^..//' | cut -d' ' -f1 | sed 's#^remotes/##' } _gt() { is_in_git_repo || return git tag --sort -version:refname | fzf_down --multi --preview-window right:70% \ --preview 'git show --color=always {} | head -'$LINES } _gh() { is_in_git_repo || return git log --date=short --format="%C(green)%C(bold)%cd %C(auto)%h%d %s (%an)" --graph --color=always | fzf_down --ansi --no-sort --reverse --multi --exact \ --bind 'ctrl-s:toggle-sort' \ --header 'Press CTRL-S to toggle sort' \ --preview 'grep -o "[a-f0-9]\{7,\}" <<< {} | xargs git show --color=always | head -'$LINES | grep -o "[a-f0-9]\{7,\}" } _gr() { is_in_git_repo || return git remote -v | awk '{print $1 "\t" $2}' | uniq | fzf_down --tac \ --preview 'git log --oneline --graph --date=short --pretty="format:%C(auto)%cd %h%d %s" {1} | head -200' | cut -d$'\t' -f1 } bind '"\er": redraw-current-line' bind '"\C-g\C-f": "$(_gf)\e\C-e\er"' bind '"\C-g\C-p": "$(_gp)\e\C-e\er"' bind '"\C-g\C-b": "$(_gb)\e\C-e\er"' bind '"\C-g\C-t": "$(_gt)\e\C-e\er"' bind '"\C-g\C-h": "$(_gh)\e\C-e\er"' bind '"\C-g\C-r": "$(_gr)\e\C-e\er"' bind '"\C- ": "$(p)\e\C-e\er"' ''; shellAliases = { ".." = "__HM_SESS_VARS_SOURCED= ."; day = "date +%a"; ddate = "date +%Y.%m.%d"; dday = "date +%A"; dr = "direnv reload"; e = "emacsclient -nw"; # emacs in a terminal f = "fossil"; g = "git"; ga = "git add -A"; gb = "git branch"; gc = "git commit"; gca = "git commit -a"; gco = "git checkout"; gd = "git diff"; gl = "git pull --prune"; gp = "git push origin HEAD"; gs = "git status -sb"; hs = "NIX_PATH=$HOME/.nix-defexpr/channels$\{NIX_PATH:+:\}$NIX_PATH home-manager switch"; ll = "ls -lah"; q = "que"; qd = ''que pub/bsnotify - <<< "done"''; rm = "rm -i"; s = '' INITIAL_QUERY="" && \ RG_PREFIX="rg --column --line-number --no-heading --color=always --smart-case " && \ FZF_DEFAULT_COMMAND="$RG_PREFIX '$INITIAL_QUERY'" && \ fzf --bind "change:reload:$RG_PREFIX {q} || true" \ --ansi --phony --query "$INITIAL_QUERY" \ --height=50% --layout=reverse ''; showpath = ''echo $PATH | sed "s/:/\n/g"''; tdate = "date +%Y.%m.%d..%H.%M"; ttime = "date +%H.%M"; typeless = "history | tail -n 20000 | sed 's/.* //' | sort | uniq -c | sort -g | tail -n 100"; v = "vim $(fzf --preview='bat --color=always {}' --preview-window right:70%)"; "v." = "vim ."; }; }; }; }