From bfa084fe7fc113bb917c782c3e0caf74aad25d2c Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 19:30:29 +0100 Subject: [PATCH 01/20] feat: add nemo file manager and extensions to workstation configuration --- config/ansible/tasks/workstations/workstation.yml | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/config/ansible/tasks/workstations/workstation.yml b/config/ansible/tasks/workstations/workstation.yml index 6035aa5..453ce04 100644 --- a/config/ansible/tasks/workstations/workstation.yml +++ b/config/ansible/tasks/workstations/workstation.yml @@ -43,6 +43,15 @@ # Statistics HUD for gaming - mangohud # Used for VSCode Extensions - - nodejs + - nodejs + # File Manager + - nemo + # File Manager Extensions + - nemo-compare + - nemo-data + - nemo-fileroller + - nemo-font-manager + - nemo-gtkhash + - nemo-python state: present become: true From 82ee7361bda0e8dcd4328bfe18cf10207500cd33 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 19:35:55 +0100 Subject: [PATCH 02/20] feat: add dependency check in dotf script and modify package installation command --- bin/dotf | 4 +++- bin/helpers/functions.py | 9 +-------- config/ansible/tasks/global/openssh-server.yml | 1 - 3 files changed, 4 insertions(+), 10 deletions(-) diff --git a/bin/dotf b/bin/dotf index 9668d81..c4f6d9a 100755 --- a/bin/dotf +++ b/bin/dotf @@ -12,7 +12,9 @@ DOTFILES_PATH = DOTFILES_ROOT # For compatibility with the original scripts # Import helper functions sys.path.append(DOTFILES_BIN) -from helpers.functions import printfe, logo +from helpers.functions import printfe, ensure_dependencies + +ensure_dependencies() def run_script(script_path, args): """Run an action script with the given arguments""" diff --git a/bin/helpers/functions.py b/bin/helpers/functions.py index 1401f00..8581707 100644 --- a/bin/helpers/functions.py +++ b/bin/helpers/functions.py @@ -109,16 +109,9 @@ def ensure_dependencies(): printfe("cyan", "Installing missing dependencies...") for package in missing_packages: printfe("blue", f"Installing {package}...") - success, output = run_command(['pip', 'install', '--user', package]) + success, output = run_command(['pip', 'install', '--user', package, '--break-system-packages']) if success: printfe("green", f"Successfully installed {package}") - # Attempt to import the newly installed package - if package == 'pyfiglet': - try: - global pyfiglet - import pyfiglet - except ImportError: - printfe("red", f"Failed to import {package} after installation") else: printfe("red", f"Failed to install {package}: {output}") diff --git a/config/ansible/tasks/global/openssh-server.yml b/config/ansible/tasks/global/openssh-server.yml index 0f9e500..d81b417 100644 --- a/config/ansible/tasks/global/openssh-server.yml +++ b/config/ansible/tasks/global/openssh-server.yml @@ -12,7 +12,6 @@ group: root mode: '0644' validate: '/usr/sbin/sshd -t -f %s' - notify: Restart SSH service register: ssh_config - name: Ensure SSH service is enabled and running From 6cb059ebce9f1215b7cf2c6252fbddb37d5fae40 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 19:56:36 +0100 Subject: [PATCH 03/20] refactor: clean up .bashrc by removing commented-out zoxide initialization and reorganizing fzf history search function --- .bashrc | 43 ++++++++----------- .../home-manager/packages/common/packages.nix | 1 - 2 files changed, 19 insertions(+), 25 deletions(-) diff --git a/.bashrc b/.bashrc index 7f395bd..8e3861a 100644 --- a/.bashrc +++ b/.bashrc @@ -109,11 +109,6 @@ if [ -f "$HOME/.nix-profile/etc/profile.d/hm-session-vars.sh" ]; then . "$HOME/.nix-profile/etc/profile.d/hm-session-vars.sh" fi -# zoxide if available -if command -v zoxide &> /dev/null; then - eval "$(zoxide init bash)" -fi - # Check if we are running from zellij, if not then launch it launch_zellij_conditionally() { if [ -z "$ZELLIJ" ]; then @@ -139,27 +134,27 @@ launch_zellij_conditionally() { # launch_zellij_conditionally # Source ble.sh if it exists -if [[ -f "${HOME}/.nix-profile/share/blesh/ble.sh" ]]; then - source "${HOME}/.nix-profile/share/blesh/ble.sh" +# if [[ -f "${HOME}/.nix-profile/share/blesh/ble.sh" ]]; then +# source "${HOME}/.nix-profile/share/blesh/ble.sh" - # Custom function for fzf history search - function fzf_history_search() { - local selected - selected=$(history | fzf --tac --height=40% --layout=reverse --border --info=inline \ - --query="$READLINE_LINE" \ - --color 'fg:#ebdbb2,bg:#282828,hl:#fabd2f,fg+:#ebdbb2,bg+:#3c3836,hl+:#fabd2f' \ - --color 'info:#83a598,prompt:#bdae93,spinner:#fabd2f,pointer:#83a598,marker:#fe8019,header:#665c54' \ - | sed 's/^ *[0-9]* *//') - if [[ -n "$selected" ]]; then - READLINE_LINE="$selected" - READLINE_POINT=${#selected} - fi - ble-redraw-prompt - } +# # Custom function for fzf history search +# function fzf_history_search() { +# local selected +# selected=$(history | fzf --tac --height=40% --layout=reverse --border --info=inline \ +# --query="$READLINE_LINE" \ +# --color 'fg:#ebdbb2,bg:#282828,hl:#fabd2f,fg+:#ebdbb2,bg+:#3c3836,hl+:#fabd2f' \ +# --color 'info:#83a598,prompt:#bdae93,spinner:#fabd2f,pointer:#83a598,marker:#fe8019,header:#665c54' \ +# | sed 's/^ *[0-9]* *//') +# if [[ -n "$selected" ]]; then +# READLINE_LINE="$selected" +# READLINE_POINT=${#selected} +# fi +# ble-redraw-prompt +# } - # Bind Ctrl+R to our custom function - bind -x '"\C-r": fzf_history_search' -fi +# # Bind Ctrl+R to our custom function +# bind -x '"\C-r": fzf_history_search' +# fi # Display a welcome message for interactive shells if [ -t 1 ]; then diff --git a/config/home-manager/packages/common/packages.nix b/config/home-manager/packages/common/packages.nix index d9b860d..92cffe1 100644 --- a/config/home-manager/packages/common/packages.nix +++ b/config/home-manager/packages/common/packages.nix @@ -49,7 +49,6 @@ # File and directory operations eza # Modern ls bat # Modern cat - zoxide # Smarter cd command broot # Interactive directory navigator du-dust # Modern du duf # Modern df From 9bc865e151bb128186037aff6e92e6eae061bbfc Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 19:59:34 +0100 Subject: [PATCH 04/20] feat: enhance ensure_ansible_collections function to check and install missing Ansible collections --- bin/actions/update.py | 46 +++++++++++++++++++++++++++++++++++++------ 1 file changed, 40 insertions(+), 6 deletions(-) diff --git a/bin/actions/update.py b/bin/actions/update.py index 85d2264..e2e6a0a 100755 --- a/bin/actions/update.py +++ b/bin/actions/update.py @@ -28,15 +28,47 @@ def ensure_ansible_collections(): ] printfe("cyan", "Checking for required Ansible collections...") - status, output = run_command(["ansible-galaxy", "collection", "list"], shell=False) - if not status: - printfe("red", "Failed to list Ansible collections") - return False + # Get default collections paths from Ansible config + collections_paths = [] + try: + status, output = run_command(["ansible-config", "dump", "COLLECTIONS_PATHS"], shell=False) + if status and output.strip(): + # Extract paths from output which is in format "COLLECTIONS_PATHS(default) = ['/path1', '/path2']" + import re + paths_match = re.search(r'\[(.*)\]', output) + if paths_match: + paths_str = paths_match.group(1) + # Split by comma, strip quotes and whitespace + collections_paths = [p.strip().strip("'\"") for p in paths_str.split(',')] + except Exception as e: + printfe("yellow", f"Failed to get collections paths: {e}") - # Check each required collection and install if missing + # Add default paths if we couldn't get them from config + if not collections_paths: + collections_paths = [ + os.path.expanduser("~/.ansible/collections"), + "/usr/share/ansible/collections" + ] + + # Check if each required collection is installed + missing_collections = [] for collection in required_collections: - if collection not in output: + collection_found = False + namespace, name = collection.split('.') + + for path in collections_paths: + collection_path = os.path.join(path, "ansible_collections", namespace, name) + if os.path.exists(collection_path): + collection_found = True + break + + if not collection_found: + missing_collections.append(collection) + + # Install missing collections + if missing_collections: + for collection in missing_collections: printfe("yellow", f"Installing {collection} collection...") status, install_output = run_command(["ansible-galaxy", "collection", "install", collection], shell=False) if not status: @@ -44,6 +76,8 @@ def ensure_ansible_collections(): printfe("yellow", f"Continuing anyway, but playbook might fail if it requires {collection}") else: printfe("green", f"Successfully installed {collection} collection") + else: + printfe("green", "All required collections are already installed.") return True From 6f2ec615ceccf2b139bee818c624306fb2003bd4 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:01:25 +0100 Subject: [PATCH 05/20] feat: add pip availability check in ensure_dependencies function --- bin/helpers/functions.py | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/bin/helpers/functions.py b/bin/helpers/functions.py index 8581707..198463e 100644 --- a/bin/helpers/functions.py +++ b/bin/helpers/functions.py @@ -94,6 +94,12 @@ def ensure_dependencies(): required_packages = [ 'pyfiglet', # For ASCII art generation ] + + # Check if pip is available + success, _ = run_command(['pip', '--version']) + if not success: + printfe("red", "Pip is required to install missing dependencies, try again after running `dotf update`") + return False missing_packages = [] for package in required_packages: From ee064f521b3fb4293fa379318824c1b2aa9bab37 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:23:15 +0100 Subject: [PATCH 06/20] feat: enhance command execution with error handling and add Ansible task for Docker repository checkout --- bin/helpers/functions.py | 8 +++++++- config/ansible/tasks/servers/server.yml | 9 +++++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/bin/helpers/functions.py b/bin/helpers/functions.py index 198463e..f6a0af3 100644 --- a/bin/helpers/functions.py +++ b/bin/helpers/functions.py @@ -5,6 +5,7 @@ import sys import subprocess import math import random +import shutil try: import pyfiglet except ImportError: @@ -79,15 +80,20 @@ def logo(continue_after=False): sys.exit(0) except Exception as e: printfe("red", f"Error displaying logo: {e}") - def run_command(command, shell=False): """Run a shell command and return the result""" try: + if not shell and not shutil.which(command[0]): + return False, f"Command '{command[0]}' not found" + result = subprocess.run(command, shell=shell, check=True, text=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) return True, result.stdout.strip() except subprocess.CalledProcessError as e: return False, e.stderr.strip() + except FileNotFoundError: + return False, f"Command '{command[0]}' not found" + return False, e.stderr.strip() def ensure_dependencies(): """Check and install required dependencies for the dotfiles system""" diff --git a/config/ansible/tasks/servers/server.yml b/config/ansible/tasks/servers/server.yml index 83be04c..533c9c5 100644 --- a/config/ansible/tasks/servers/server.yml +++ b/config/ansible/tasks/servers/server.yml @@ -4,3 +4,12 @@ - openssh-server state: present become: true + +- name: Ensure checkout docker /mnt/services repository + ansible.builtin.git: + repo: "https://git.mvl.sh/vleeuwenmenno/services.git" + dest: "/mnt/services" + update: true + version: "main" + register: git_result + changed_when: git_result.changed From 132b7b1b66a21f8bc11721661833e23684700fef Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:28:05 +0100 Subject: [PATCH 07/20] fix: replace lastlog2 with lastlog for SSH login information and clean up related dependencies --- bin/actions/hello.py | 3 +-- bin/helpers/functions.py | 2 +- config/ansible/tasks/global/global.yml | 1 - config/home-manager/packages/common/packages.nix | 3 +++ 4 files changed, 5 insertions(+), 4 deletions(-) diff --git a/bin/actions/hello.py b/bin/actions/hello.py index c2a65fd..4664723 100755 --- a/bin/actions/hello.py +++ b/bin/actions/hello.py @@ -12,8 +12,7 @@ from helpers.functions import printfe, logo, _rainbow_color, COLORS def get_last_ssh_login(): """Get information about the last SSH login""" try: - # Using lastlog2 to get the last login information - result = subprocess.run(['lastlog2', '-u', os.environ.get("USER", "")], + result = subprocess.run(['lastlog', '-u', os.environ.get("USER", "")], capture_output=True, text=True) if result.returncode == 0: lines = result.stdout.strip().split('\n') diff --git a/bin/helpers/functions.py b/bin/helpers/functions.py index f6a0af3..f00b97f 100644 --- a/bin/helpers/functions.py +++ b/bin/helpers/functions.py @@ -80,6 +80,7 @@ def logo(continue_after=False): sys.exit(0) except Exception as e: printfe("red", f"Error displaying logo: {e}") + def run_command(command, shell=False): """Run a shell command and return the result""" try: @@ -93,7 +94,6 @@ def run_command(command, shell=False): return False, e.stderr.strip() except FileNotFoundError: return False, f"Command '{command[0]}' not found" - return False, e.stderr.strip() def ensure_dependencies(): """Check and install required dependencies for the dotfiles system""" diff --git a/config/ansible/tasks/global/global.yml b/config/ansible/tasks/global/global.yml index b6b8d3e..bd340c6 100644 --- a/config/ansible/tasks/global/global.yml +++ b/config/ansible/tasks/global/global.yml @@ -39,7 +39,6 @@ - python3 - python3-pip - python3-venv - - lastlog2 # Used for displaying last login information state: present become: true diff --git a/config/home-manager/packages/common/packages.nix b/config/home-manager/packages/common/packages.nix index 92cffe1..e5946bd 100644 --- a/config/home-manager/packages/common/packages.nix +++ b/config/home-manager/packages/common/packages.nix @@ -32,6 +32,9 @@ pipx devbox + # OS independent and secure pty/tty and utmp/wtmp/lastlog + libptytty + # Development SDKs/Toolkits gcc pkg-config From 612a8bf7b1c4a93e588622413b870cad0cd85025 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:30:07 +0100 Subject: [PATCH 08/20] feat: update Ansible tasks to specify shell executable for improved compatibility --- bin/actions/update.py | 1 + config/ansible/tasks/global/docker.yml | 1 + config/ansible/tasks/global/pipx.yml | 2 ++ 3 files changed, 4 insertions(+) diff --git a/bin/actions/update.py b/bin/actions/update.py index e2e6a0a..37175f9 100755 --- a/bin/actions/update.py +++ b/bin/actions/update.py @@ -174,6 +174,7 @@ def main(): printfe("cyan", "Running Ansible playbook...") ansible_cmd = [ + "/usr/bin/env", "ansible-playbook", "-i", f"{dotfiles_path}/config/ansible/inventory.ini", f"{dotfiles_path}/config/ansible/main.yml", diff --git a/config/ansible/tasks/global/docker.yml b/config/ansible/tasks/global/docker.yml index e4a22e3..121a3d6 100644 --- a/config/ansible/tasks/global/docker.yml +++ b/config/ansible/tasks/global/docker.yml @@ -14,6 +14,7 @@ - name: Install Docker CE ansible.builtin.shell: bash -c 'set -o pipefail && sh /tmp/get-docker.sh' args: + executable: /bin/bash creates: /usr/bin/docker when: docker_check.rc != 0 diff --git a/config/ansible/tasks/global/pipx.yml b/config/ansible/tasks/global/pipx.yml index 6fbb0ba..20397f5 100644 --- a/config/ansible/tasks/global/pipx.yml +++ b/config/ansible/tasks/global/pipx.yml @@ -1,5 +1,7 @@ - name: List installed pipx packages ansible.builtin.shell: set -o pipefail && pipx list --short | awk '{print $1}' + args: + executable: /bin/bash register: installed_pipx_packages changed_when: false From 1cb4a9acc4d47d7af4bc3d341f6be7357bc13968 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:33:01 +0100 Subject: [PATCH 09/20] fix: add fallback to lastlog2 for SSH login retrieval and remove unnecessary libptytty dependency --- bin/actions/hello.py | 6 ++++++ config/home-manager/packages/common/packages.nix | 3 --- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/bin/actions/hello.py b/bin/actions/hello.py index 4664723..187e1af 100755 --- a/bin/actions/hello.py +++ b/bin/actions/hello.py @@ -14,6 +14,12 @@ def get_last_ssh_login(): try: result = subprocess.run(['lastlog', '-u', os.environ.get("USER", "")], capture_output=True, text=True) + + # If lastlog didn't work try lastlog2 + if result.returncode != 0: + result = subprocess.run(['lastlog2', os.environ.get("USER", "")], + capture_output=True, text=True) + if result.returncode == 0: lines = result.stdout.strip().split('\n') if len(lines) >= 2: # Header line + data line diff --git a/config/home-manager/packages/common/packages.nix b/config/home-manager/packages/common/packages.nix index e5946bd..92cffe1 100644 --- a/config/home-manager/packages/common/packages.nix +++ b/config/home-manager/packages/common/packages.nix @@ -32,9 +32,6 @@ pipx devbox - # OS independent and secure pty/tty and utmp/wtmp/lastlog - libptytty - # Development SDKs/Toolkits gcc pkg-config From 8611e203c657c234ca84ee9e16dbffe6f3ec9e4e Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:35:35 +0100 Subject: [PATCH 10/20] feat: add force option to pipx task for ensuring package installation --- config/ansible/tasks/global/pipx.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/config/ansible/tasks/global/pipx.yml b/config/ansible/tasks/global/pipx.yml index 20397f5..ca56836 100644 --- a/config/ansible/tasks/global/pipx.yml +++ b/config/ansible/tasks/global/pipx.yml @@ -16,6 +16,7 @@ community.general.pipx: name: "{{ item }}" state: present + force: true loop: "{{ desired_pipx_packages }}" - name: Remove undesired pipx packages From f7787c592b72663b87f6bebe9b82f5d1080ca368 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:41:49 +0100 Subject: [PATCH 11/20] feat: update Ansible collection retrieval to use ansible-galaxy for improved accuracy --- bin/actions/update.py | 71 ++++++++++++++++++++++++------------------- 1 file changed, 40 insertions(+), 31 deletions(-) diff --git a/bin/actions/update.py b/bin/actions/update.py index 37175f9..82b4ad1 100755 --- a/bin/actions/update.py +++ b/bin/actions/update.py @@ -29,41 +29,50 @@ def ensure_ansible_collections(): printfe("cyan", "Checking for required Ansible collections...") - # Get default collections paths from Ansible config - collections_paths = [] - try: - status, output = run_command(["ansible-config", "dump", "COLLECTIONS_PATHS"], shell=False) - if status and output.strip(): - # Extract paths from output which is in format "COLLECTIONS_PATHS(default) = ['/path1', '/path2']" - import re - paths_match = re.search(r'\[(.*)\]', output) - if paths_match: - paths_str = paths_match.group(1) - # Split by comma, strip quotes and whitespace - collections_paths = [p.strip().strip("'\"") for p in paths_str.split(',')] - except Exception as e: - printfe("yellow", f"Failed to get collections paths: {e}") + # Get list of installed collections using ansible-galaxy + status, output = run_command(["ansible-galaxy", "collection", "list"], shell=False) + if not status: + printfe("yellow", f"Failed to list Ansible collections: {output}") + printfe("yellow", "Will try to install all required collections.") + installed_collections = [] + else: + # Parse output to get installed collections + installed_collections = [] + + # Split output into lines and process + lines = output.splitlines() + collection_section = False + + for line in lines: + line = line.strip() + + # Skip empty lines + if not line: + continue + + # Check if we've reached the collection listing section + if line.startswith("Collection"): + collection_section = True + continue + + # Skip the separator line after the header + if collection_section and line.startswith("--"): + continue + + # Process collection entries + if collection_section and " " in line: + # Format is typically: "community.general 10.4.0" + parts = line.split() + if len(parts) >= 1: + collection_name = parts[0] + installed_collections.append(collection_name) - # Add default paths if we couldn't get them from config - if not collections_paths: - collections_paths = [ - os.path.expanduser("~/.ansible/collections"), - "/usr/share/ansible/collections" - ] + printfe("cyan", f"Found installed collections: {', '.join(installed_collections) if installed_collections else 'none'}") - # Check if each required collection is installed + # Check which required collections are missing missing_collections = [] for collection in required_collections: - collection_found = False - namespace, name = collection.split('.') - - for path in collections_paths: - collection_path = os.path.join(path, "ansible_collections", namespace, name) - if os.path.exists(collection_path): - collection_found = True - break - - if not collection_found: + if collection not in installed_collections: missing_collections.append(collection) # Install missing collections From 6eac725e9d458192758cfb71b226e7ad439feea5 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:57:26 +0100 Subject: [PATCH 12/20] feat: update .bashrc and symlink configuration for improved shell functionality --- .bashrc | 62 ++++++-------------- config/ansible/tasks/global/symlinks.yml | 1 + config/home-manager/packages/common/bash.nix | 2 - config/ssh/config | 2 +- 4 files changed, 21 insertions(+), 46 deletions(-) diff --git a/.bashrc b/.bashrc index 8e3861a..e1bcacb 100644 --- a/.bashrc +++ b/.bashrc @@ -109,52 +109,28 @@ if [ -f "$HOME/.nix-profile/etc/profile.d/hm-session-vars.sh" ]; then . "$HOME/.nix-profile/etc/profile.d/hm-session-vars.sh" fi -# Check if we are running from zellij, if not then launch it -launch_zellij_conditionally() { - if [ -z "$ZELLIJ" ]; then - # Don't launch zellij in tmux, vscode, screen or zeditor. - if [ ! -t 1 ] || [ -n "$TMUX" ] || [ -n "$VSCODE_STABLE" ] || [ -n "$STY" ] || [ -n "$ZED_TERM" ]; then - return - fi - - # Launch zellij - zellij - - # Exit if zellij exits properly with a zero exit code - if [ $? -eq 0 ]; then - exit $? - fi - - echo "Zellij exited with a non-zero exit code, falling back to regular shell." - return - fi -} - -# Disabled for now, I don't like the way it behaves but I don't want to remove it either -# launch_zellij_conditionally - # Source ble.sh if it exists -# if [[ -f "${HOME}/.nix-profile/share/blesh/ble.sh" ]]; then -# source "${HOME}/.nix-profile/share/blesh/ble.sh" +if [[ -f "${HOME}/.nix-profile/share/blesh/ble.sh" ]]; then + source "${HOME}/.nix-profile/share/blesh/ble.sh" -# # Custom function for fzf history search -# function fzf_history_search() { -# local selected -# selected=$(history | fzf --tac --height=40% --layout=reverse --border --info=inline \ -# --query="$READLINE_LINE" \ -# --color 'fg:#ebdbb2,bg:#282828,hl:#fabd2f,fg+:#ebdbb2,bg+:#3c3836,hl+:#fabd2f' \ -# --color 'info:#83a598,prompt:#bdae93,spinner:#fabd2f,pointer:#83a598,marker:#fe8019,header:#665c54' \ -# | sed 's/^ *[0-9]* *//') -# if [[ -n "$selected" ]]; then -# READLINE_LINE="$selected" -# READLINE_POINT=${#selected} -# fi -# ble-redraw-prompt -# } + # Custom function for fzf history search + function fzf_history_search() { + local selected + selected=$(history | fzf --tac --height=40% --layout=reverse --border --info=inline \ + --query="$READLINE_LINE" \ + --color 'fg:#ebdbb2,bg:#282828,hl:#fabd2f,fg+:#ebdbb2,bg+:#3c3836,hl+:#fabd2f' \ + --color 'info:#83a598,prompt:#bdae93,spinner:#fabd2f,pointer:#83a598,marker:#fe8019,header:#665c54' \ + | sed 's/^ *[0-9]* *//') + if [[ -n "$selected" ]]; then + READLINE_LINE="$selected" + READLINE_POINT=${#selected} + fi + ble-redraw-prompt + } -# # Bind Ctrl+R to our custom function -# bind -x '"\C-r": fzf_history_search' -# fi + # Bind Ctrl+R to our custom function + bind -x '"\C-r": fzf_history_search' +fi # Display a welcome message for interactive shells if [ -t 1 ]; then diff --git a/config/ansible/tasks/global/symlinks.yml b/config/ansible/tasks/global/symlinks.yml index 161f983..7360955 100644 --- a/config/ansible/tasks/global/symlinks.yml +++ b/config/ansible/tasks/global/symlinks.yml @@ -14,6 +14,7 @@ - { src: "$DOTFILES_PATH/config/ssh/config", dest: "~/.ssh/config" } - { src: "$DOTFILES_PATH/config/ssh/config.d", dest: "~/.ssh/config.d" } - { src: "$DOTFILES_PATH/config/starship.toml", dest: "~/.config/starship.toml" } + - { src: "$DOTFILES_PATH/.bashrc", dest: "~/.bashrc.extra" } - name: Create gitconfig symlink ansible.builtin.file: diff --git a/config/home-manager/packages/common/bash.nix b/config/home-manager/packages/common/bash.nix index d788fdf..aa9aab9 100644 --- a/config/home-manager/packages/common/bash.nix +++ b/config/home-manager/packages/common/bash.nix @@ -4,8 +4,6 @@ let dotfilesPath = builtins.getEnv "DOTFILES_PATH"; in { - home.file.".bashrc.extra".source = "${dotfilesPath}/.bashrc"; - programs.bash = { enable = true; enableCompletion = true; diff --git a/config/ssh/config b/config/ssh/config index a43e15c..e108375 100644 --- a/config/ssh/config +++ b/config/ssh/config @@ -1,5 +1,5 @@ Host * - IdentityFile $DOTFILES_PATH/secrets/ssh_keys/mennos-2025.pem + IdentityFile ~/.dotfiles/secrets/ssh_keys/mennos-2025.pem IdentityAgent ~/.1password/agent.sock AddKeysToAgent yes ForwardAgent yes From bec0970a4a37f38f3600b8d21557af174944b384 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:59:58 +0100 Subject: [PATCH 13/20] feat: update pipx package installation to include ansible-lint and ansible-core --- config/ansible/tasks/global/pipx.yml | 2 -- setup.sh | 4 +++- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/config/ansible/tasks/global/pipx.yml b/config/ansible/tasks/global/pipx.yml index ca56836..75682e1 100644 --- a/config/ansible/tasks/global/pipx.yml +++ b/config/ansible/tasks/global/pipx.yml @@ -8,8 +8,6 @@ - name: Define desired pipx packages ansible.builtin.set_fact: desired_pipx_packages: - - ansible - - ansible-lint - shyaml - name: Install/Upgrade pipx packages diff --git a/setup.sh b/setup.sh index 03db50d..4f0e2be 100755 --- a/setup.sh +++ b/setup.sh @@ -267,7 +267,9 @@ setup_ansible() { ensure_pipx log_info "Installing Ansible..." - pipx install ansible || die "Failed to install Ansible" + attempt_package_install "ansible" + attempt_package_install "ansible-lint" + attempt_package_install "ansible-core" } check_command_availibility() { From ceca79f39bc459d7d168c57533f895ef8157b8c7 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 21:01:41 +0100 Subject: [PATCH 14/20] refactor: remove obsolete pipx task and clean up ensure_ansible_collections function --- bin/actions/update.py | 15 ++------------- config/ansible/tasks/global/pipx.yml | 24 ------------------------ 2 files changed, 2 insertions(+), 37 deletions(-) delete mode 100644 config/ansible/tasks/global/pipx.yml diff --git a/bin/actions/update.py b/bin/actions/update.py index 82b4ad1..3e8fd84 100755 --- a/bin/actions/update.py +++ b/bin/actions/update.py @@ -66,9 +66,7 @@ def ensure_ansible_collections(): if len(parts) >= 1: collection_name = parts[0] installed_collections.append(collection_name) - - printfe("cyan", f"Found installed collections: {', '.join(installed_collections) if installed_collections else 'none'}") - + # Check which required collections are missing missing_collections = [] for collection in required_collections: @@ -166,16 +164,7 @@ def main(): dotfiles_path = os.environ.get("DOTFILES_PATH", os.path.expanduser("~/.dotfiles")) hostname = os.uname().nodename username = os.environ.get("USER", os.environ.get("USERNAME", "user")) - - # Check if ansible is installed - status, _ = run_command(["which", "ansible-playbook"], shell=False) - if not status: - printfe("yellow", "Ansible is not installed, installing it with pipx...") - status, output = run_command(["pipx", "install", "--include-deps", "ansible", "ansible-lint"], shell=False) - if not status: - printfe("red", f"Failed to install Ansible: {output}") - return 1 - + # Ensure required collections are installed if not ensure_ansible_collections(): printfe("red", "Failed to ensure required Ansible collections are installed") diff --git a/config/ansible/tasks/global/pipx.yml b/config/ansible/tasks/global/pipx.yml deleted file mode 100644 index 75682e1..0000000 --- a/config/ansible/tasks/global/pipx.yml +++ /dev/null @@ -1,24 +0,0 @@ -- name: List installed pipx packages - ansible.builtin.shell: set -o pipefail && pipx list --short | awk '{print $1}' - args: - executable: /bin/bash - register: installed_pipx_packages - changed_when: false - -- name: Define desired pipx packages - ansible.builtin.set_fact: - desired_pipx_packages: - - shyaml - -- name: Install/Upgrade pipx packages - community.general.pipx: - name: "{{ item }}" - state: present - force: true - loop: "{{ desired_pipx_packages }}" - -- name: Remove undesired pipx packages - community.general.pipx: - name: "{{ item }}" - state: absent - loop: "{{ installed_pipx_packages.stdout_lines | difference(desired_pipx_packages) }}" From 3bcf78d4eb528ce7d867f1f763c91c8b6d443a63 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 21:02:32 +0100 Subject: [PATCH 15/20] refactor: remove pipx references from Ansible tasks and setup script --- config/ansible/tasks/global/global.yml | 4 ---- .../home-manager/packages/common/packages.nix | 3 +-- setup.sh | 18 ------------------ 3 files changed, 1 insertion(+), 24 deletions(-) diff --git a/config/ansible/tasks/global/global.yml b/config/ansible/tasks/global/global.yml index bd340c6..4e70b1b 100644 --- a/config/ansible/tasks/global/global.yml +++ b/config/ansible/tasks/global/global.yml @@ -31,7 +31,6 @@ name: - git - vim - - pipx - trash-cli - curl - wget @@ -41,6 +40,3 @@ - python3-venv state: present become: true - -- name: Include pipx tasks - ansible.builtin.import_tasks: tasks/global/pipx.yml diff --git a/config/home-manager/packages/common/packages.nix b/config/home-manager/packages/common/packages.nix index 92cffe1..bb425ce 100644 --- a/config/home-manager/packages/common/packages.nix +++ b/config/home-manager/packages/common/packages.nix @@ -28,8 +28,7 @@ wget fastfetch - # Package management - pipx + # Package management devbox # Development SDKs/Toolkits diff --git a/setup.sh b/setup.sh index 4f0e2be..17382f6 100755 --- a/setup.sh +++ b/setup.sh @@ -247,25 +247,7 @@ EOF fi } -ensure_pipx() { - if ! command -v pipx >/dev/null 2>&1; then - log_info "Installing pipx..." - - attempt_package_install "pipx" - - # On Arch Linux, install pipx using pacman - if command -v pacman >/dev/null 2>&1; then - sudo pacman -S python-pipx || die "Failed to install pipx" - fi - - # ensurepath - sudo pipx ensurepath || die "Failed to ensure pipx path" - fi -} - setup_ansible() { - ensure_pipx - log_info "Installing Ansible..." attempt_package_install "ansible" attempt_package_install "ansible-lint" From 3936d7a95ed2b9d1f9ad64574b3f469011e9bc87 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:15:14 +0000 Subject: [PATCH 16/20] feat: enhance Ansible tasks for server and workstation setup with Docker support --- config/ansible/tasks/servers/server.yml | 40 ++++++++++++++++++- .../tasks/workstations/workstation.yml | 2 +- 2 files changed, 39 insertions(+), 3 deletions(-) diff --git a/config/ansible/tasks/servers/server.yml b/config/ansible/tasks/servers/server.yml index 533c9c5..1aad24a 100644 --- a/config/ansible/tasks/servers/server.yml +++ b/config/ansible/tasks/servers/server.yml @@ -1,15 +1,51 @@ -- name: Ensure common packages are installed +- name: Ensure server common packages are installed ansible.builtin.package: name: - openssh-server + - docker.io state: present become: true -- name: Ensure checkout docker /mnt/services repository +- name: Update/Checkout /mnt/services repository ansible.builtin.git: repo: "https://git.mvl.sh/vleeuwenmenno/services.git" dest: "/mnt/services" update: true version: "main" + become: true register: git_result changed_when: git_result.changed + +- name: Ensure /mnt/services ownership to users + ansible.builtin.file: + path: "/mnt/services" + group: "users" + recurse: true + state: directory + become: true + +- name: Find all docker-compose.yml files in /mnt/services subdirectories + ansible.builtin.find: + paths: /mnt/services + patterns: docker-compose.yml + recurse: true + register: docker_compose_files + become: true + +- name: Pull latest Docker images for each service + ansible.builtin.command: + cmd: docker compose pull + chdir: "{{ item.path | dirname }}" + loop: "{{ docker_compose_files.files }}" + become: true + register: docker_pull_results + changed_when: docker_pull_results.rc == 0 and (docker_pull_results.stdout | default('') is search('Pulling|Downloaded')) + +- name: Restart Docker services with updated images + ansible.builtin.command: + cmd: docker compose up -d + chdir: "{{ item.path | dirname }}" + loop: "{{ docker_compose_files.files }}" + become: true + register: docker_up_results + changed_when: docker_up_results.rc == 0 and (docker_up_results.stdout | default('') is search('Creating|Recreating')) diff --git a/config/ansible/tasks/workstations/workstation.yml b/config/ansible/tasks/workstations/workstation.yml index 453ce04..239a507 100644 --- a/config/ansible/tasks/workstations/workstation.yml +++ b/config/ansible/tasks/workstations/workstation.yml @@ -32,7 +32,7 @@ - name: Include MegaSync tasks ansible.builtin.import_tasks: tasks/workstations/megasync.yml -- name: Ensure common packages are installed +- name: Ensure workstation common packages are installed ansible.builtin.package: name: ###### THE FOLLOWING PACKAGES ARE DISABLED DUE TO MISSING ON UBUNTU REPOS ###### From 26481a2b4eab2173da91868d01a1a342d6c48477 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 20:28:09 +0000 Subject: [PATCH 17/20] feat: add mount point check for /mnt/services and conditionally update repository --- config/ansible/tasks/servers/server.yml | 36 +++++++------------------ 1 file changed, 9 insertions(+), 27 deletions(-) diff --git a/config/ansible/tasks/servers/server.yml b/config/ansible/tasks/servers/server.yml index 1aad24a..141ca4c 100644 --- a/config/ansible/tasks/servers/server.yml +++ b/config/ansible/tasks/servers/server.yml @@ -2,10 +2,16 @@ ansible.builtin.package: name: - openssh-server - - docker.io state: present become: true +- name: Check if /mnt/services is a mount point + ansible.builtin.shell: mountpoint -q /mnt/services || echo "not_mounted" + register: mnt_services_check + changed_when: false + ignore_errors: true + become: true + - name: Update/Checkout /mnt/services repository ansible.builtin.git: repo: "https://git.mvl.sh/vleeuwenmenno/services.git" @@ -15,6 +21,7 @@ become: true register: git_result changed_when: git_result.changed + when: mnt_services_check.rc == 0 - name: Ensure /mnt/services ownership to users ansible.builtin.file: @@ -23,29 +30,4 @@ recurse: true state: directory become: true - -- name: Find all docker-compose.yml files in /mnt/services subdirectories - ansible.builtin.find: - paths: /mnt/services - patterns: docker-compose.yml - recurse: true - register: docker_compose_files - become: true - -- name: Pull latest Docker images for each service - ansible.builtin.command: - cmd: docker compose pull - chdir: "{{ item.path | dirname }}" - loop: "{{ docker_compose_files.files }}" - become: true - register: docker_pull_results - changed_when: docker_pull_results.rc == 0 and (docker_pull_results.stdout | default('') is search('Pulling|Downloaded')) - -- name: Restart Docker services with updated images - ansible.builtin.command: - cmd: docker compose up -d - chdir: "{{ item.path | dirname }}" - loop: "{{ docker_compose_files.files }}" - become: true - register: docker_up_results - changed_when: docker_up_results.rc == 0 and (docker_up_results.stdout | default('') is search('Creating|Recreating')) + when: mnt_services_check.rc == 0 From f03a028741c9a4678a7475929d3b273982a4eb0e Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 21:38:01 +0100 Subject: [PATCH 18/20] refactor: remove redundant logging for Ansible installation in setup script --- setup.sh | 1 - 1 file changed, 1 deletion(-) diff --git a/setup.sh b/setup.sh index 17382f6..724aecf 100755 --- a/setup.sh +++ b/setup.sh @@ -248,7 +248,6 @@ EOF } setup_ansible() { - log_info "Installing Ansible..." attempt_package_install "ansible" attempt_package_install "ansible-lint" attempt_package_install "ansible-core" From 53aca071e4aab34d524da06f7356572090471b02 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 21:42:49 +0100 Subject: [PATCH 19/20] feat: add force option to git module in server.yml for repository updates --- config/ansible/tasks/servers/server.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/config/ansible/tasks/servers/server.yml b/config/ansible/tasks/servers/server.yml index 141ca4c..f4d9ab6 100644 --- a/config/ansible/tasks/servers/server.yml +++ b/config/ansible/tasks/servers/server.yml @@ -18,6 +18,7 @@ dest: "/mnt/services" update: true version: "main" + force: true become: true register: git_result changed_when: git_result.changed @@ -30,4 +31,4 @@ recurse: true state: directory become: true - when: mnt_services_check.rc == 0 + when: mnt_services_check.rc == 0 \ No newline at end of file From 0a79d2f3e3dd087d88a919e3df9d534dcf5a1844 Mon Sep 17 00:00:00 2001 From: Menno van Leeuwen Date: Mon, 10 Mar 2025 21:48:55 +0100 Subject: [PATCH 20/20] feat: implement checks for existing services repository and handle initial clone or update --- config/ansible/tasks/servers/server.yml | 28 ++++++++++++++++++++++--- 1 file changed, 25 insertions(+), 3 deletions(-) diff --git a/config/ansible/tasks/servers/server.yml b/config/ansible/tasks/servers/server.yml index f4d9ab6..bc95a38 100644 --- a/config/ansible/tasks/servers/server.yml +++ b/config/ansible/tasks/servers/server.yml @@ -12,7 +12,29 @@ ignore_errors: true become: true -- name: Update/Checkout /mnt/services repository +- name: Check if services git repo already exists + ansible.builtin.stat: + path: "/mnt/services/.git" + register: git_dir_check + become: true + when: mnt_services_check.rc == 0 + +- name: Clean /mnt/services directory + ansible.builtin.shell: find /mnt/services -mindepth 1 -maxdepth 1 -exec rm -rf {} \; + become: true + when: mnt_services_check.rc == 0 and not git_dir_check.stat.exists|default(false) + +- name: Clone /mnt/services repository (initial clone) + ansible.builtin.git: + repo: "https://git.mvl.sh/vleeuwenmenno/services.git" + dest: "/mnt/services" + version: "main" + become: true + register: git_result + changed_when: git_result.changed + when: mnt_services_check.rc == 0 and not git_dir_check.stat.exists|default(false) + +- name: Update /mnt/services repository (if already exists) ansible.builtin.git: repo: "https://git.mvl.sh/vleeuwenmenno/services.git" dest: "/mnt/services" @@ -22,7 +44,7 @@ become: true register: git_result changed_when: git_result.changed - when: mnt_services_check.rc == 0 + when: mnt_services_check.rc == 0 and git_dir_check.stat.exists|default(false) - name: Ensure /mnt/services ownership to users ansible.builtin.file: @@ -31,4 +53,4 @@ recurse: true state: directory become: true - when: mnt_services_check.rc == 0 \ No newline at end of file + when: mnt_services_check.rc == 0