Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
75 changes: 75 additions & 0 deletions .github/workflows/macos-validation.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
name: MacOS validation

on:
pull_request:
push:
branches:
- macos-support-validation

jobs:
macos:
name: Validate MacOS support
runs-on: macos-14

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Prepare scripts
run: |
chmod +x install.sh install_macos.sh install_ubuntu.sh test-macos.sh

- name: Validate shell syntax
run: |
bash -n install.sh install_macos.sh install_ubuntu.sh test-macos.sh
bash -n zsh/install.sh hyfetch/install.sh vim/install.sh kitty/install.sh
bash -n kubectl/install.sh github-cli/install.sh gitlab-cli/install.sh nvm/install.sh

- name: Validate Brewfile
run: |
ruby -c Brewfile
brew bundle list --file=Brewfile

- name: Install CI validation dependencies
run: brew install stow

- name: Run MacOS validation script
run: ./test-macos.sh

- name: Run safe stow dry-runs
run: |
set -euo pipefail

TEST_HOME="$(mktemp -d)"
mkdir -p "$TEST_HOME/.config"

dry_run_home_module() {
local module="$1"
echo "Dry-running home stow for ${module}"
(
cd "$module"
stow -n -v -t "$TEST_HOME" .
)
}

dry_run_config_module() {
local module="$1"
echo "Dry-running .config stow for ${module}"
(
cd "$module"
stow -n -v -t "$TEST_HOME/.config" .config
)
}

dry_run_home_module zsh
dry_run_home_module nvm
dry_run_config_module hyfetch
dry_run_config_module vim
dry_run_config_module kitty
dry_run_config_module kubectl
dry_run_home_module kubectl
dry_run_config_module github-cli
dry_run_config_module gitlab-cli

- name: Verify MacOS installer help
run: bash install_macos.sh --help
36 changes: 36 additions & 0 deletions Brewfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
tap "homebrew/bundle"
tap "int128/kubelogin"

# Core tools used by the dotfiles installers
brew "stow"
brew "git"
brew "curl"
brew "wget"
brew "unzip"

# Shell and terminal workflow
brew "zsh"
brew "fzf"

# Editors and search tools
brew "neovim"
brew "ripgrep"
brew "fd"

# DevOps and cloud tooling
brew "kubectl"
brew "int128/kubelogin/kubelogin"
brew "gh"
brew "glab"
brew "nvm"

# Optional CLI tools used by modules
brew "hyfetch"
brew "mas"

# Desktop applications
cask "kitty"
cask "docker"
cask "slack"
cask "powershell"
cask "font-hack-nerd-font"
84 changes: 68 additions & 16 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
# Ubuntu 24 LTS Dotfiles
# Cross-Platform Dotfiles

This repository contains configuration files and setup scripts for Ubuntu 24 LTS. It uses GNU Stow for managing dotfiles and provides a streamlined way to set up a development environment.
This repository contains configuration files and setup scripts for Ubuntu 24 LTS and MacOS. It uses GNU Stow for managing dotfiles and provides a streamlined way to set up a development environment.

## Overview

This project aims to provide a consistent and reproducible setup for Ubuntu 24 LTS systems, focusing on development tools and system configurations. The setup is managed through GNU Stow, which creates symbolic links to the appropriate locations in the home directory.
This project aims to provide a consistent and reproducible setup for Ubuntu 24 LTS and MacOS systems, focusing on development tools and system configurations. The setup is managed through GNU Stow, which creates symbolic links to the appropriate locations in the home directory.

## Manual Setup Steps

Expand Down Expand Up @@ -54,9 +54,9 @@ For Framework Laptop 13 (AMD Ryzen™ AI 300 Series), update the firmware using
- Keep the laptop plugged in throughout the entire process
- Do not close the lid during the update process

### System Preparation
### Ubuntu System Preparation

After completing the manual steps above:
After completing the manual steps above on Ubuntu:

1. **Update the system:**
```bash
Expand All @@ -74,11 +74,34 @@ After completing the manual steps above:
cd dotfiles
```

### MacOS System Preparation

On MacOS, the installer uses Homebrew and a `Brewfile` for package management:

1. **Install Xcode command line tools:**
```bash
xcode-select --install
```

2. **Clone this repository:**
```bash
git clone <repository-url>
cd dotfiles
```

3. **Run the installer:**
```bash
./install.sh --all
```

If Homebrew is missing, the MacOS installer will bootstrap it from the official installer before running `brew bundle`.

## Prerequisites

- Ubuntu 24 LTS
- Ubuntu 24 LTS or MacOS
- GNU Stow
- Basic development tools
- Homebrew on MacOS
- Framework Laptop firmware updated (if applicable)

## Project Structure
Expand All @@ -89,8 +112,12 @@ Each directory in this repository represents a specific tool or configuration se
.
├── README.md # This file
├── CHANGELOG.md # Project evolution and changes
├── install.sh # Main installation script
├── install.sh # OS dispatcher for Ubuntu and MacOS
├── install_ubuntu.sh # Ubuntu installation script
├── install_macos.sh # MacOS installation script
├── Brewfile # Homebrew bundle for MacOS packages
├── test-all.sh # Test script for all configurations
├── test-macos.sh # Lightweight MacOS validation script
├── test-docker.sh # Script to test in Docker environment
├── Dockerfile # Docker configuration for testing
├── docker-compose.yml # Docker Compose configuration
Expand All @@ -103,6 +130,10 @@ Each directory in this repository represents a specific tool or configuration se

## Installation

The root `install.sh` detects the operating system and dispatches to:
- `install_ubuntu.sh` on Linux/Ubuntu
- `install_macos.sh` on MacOS

### Interactive Installation

To install configurations interactively:
Expand All @@ -113,13 +144,12 @@ To install configurations interactively:

The installation process includes:
1. Checking and installing required dependencies
2. Managing existing `.config` directory:
- If `.config` exists, you'll be prompted to:
- Create a backup (recommended) - backups are stored in the `backup` directory
- Overwrite existing configuration
- Exit installation
- If `.config` doesn't exist, it will be created
3. Installing selected configurations with proper backups
2. Ensuring the repository backup directory and `$HOME/.config` exist
3. Installing selected configurations with module-level backups where the module supports them

The root installers do not move or overwrite an existing `$HOME/.config` directory. Existing module configuration is handled by each module installer before it calls Stow; modules may back up, remove a repository-managed symlink, or fail with a clear conflict that requires manual review.

On MacOS, package installation is handled by Homebrew through `Brewfile`. Linux-only modules are skipped by the MacOS installer.

### Update System Packages

Expand All @@ -145,7 +175,7 @@ To install all configurations automatically in a specific order:
./install.sh --all
```

This will install all modules in the following predefined order:
On Ubuntu, this will install all modules in the following predefined order:
1. **apt-packages** - System packages and WireGuard VPN
2. **certs** - SSL/TLS certificates
3. **zsh** - Enhanced shell configuration
Expand All @@ -161,6 +191,20 @@ This will install all modules in the following predefined order:
13. **nvm** - Node Version Manager
14. **gitlab-cli** - GitLab command-line interface

On MacOS, this will install Homebrew packages from `Brewfile` and then install these shared modules:
1. **zsh** - Enhanced shell configuration
2. **hyfetch** - System information display
3. **vim** - Neovim text editor
4. **kitty** - Terminal emulator
5. **kubectl** - Kubernetes CLI tools
6. **github-cli** - GitHub command-line interface
7. **gitlab-cli** - GitLab command-line interface
8. **nvm** - Node Version Manager

The MacOS installer intentionally skips Linux-specific modules: `apt-packages`, `snap-config`, `flatpak-config`, `appimaged`, `certs`, `docker`, `slack`, and `powershell`.

For MacOS, `Brewfile` installs app casks such as Docker Desktop, Slack, Kitty, and PowerShell. Those casks only install the applications; they do not run the Linux module configuration scripts. Add a dedicated MacOS module later if an app needs Mac-specific configuration beyond installation.

### Individual Module Installation

To install specific tool configurations:
Expand All @@ -171,7 +215,7 @@ stow [tool_name]

Note: Each module's installation script will:
1. Check for existing configuration
2. Create a backup if needed
2. Create a backup if implemented by that module
3. Install any missing dependencies
4. Apply the configuration using stow

Expand All @@ -184,6 +228,14 @@ To test all configurations locally:
./test-all.sh
```

To run the lightweight MacOS validation checks:

```bash
./test-macos.sh
```

This validates MacOS installer syntax, the `Brewfile`, and the expected shared module layout. When run on MacOS with Homebrew available, it also asks `brew bundle` to validate the bundle file.

### Docker Testing
To test the configuration in a Docker environment:

Expand Down
25 changes: 18 additions & 7 deletions github-cli/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ set -e
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
BACKUP_DIR="$SCRIPT_DIR/../backup"
MODULE_NAME="github-cli"
OS_TYPE="$(uname -s)"

# Catppuccin Mocha color scheme
# Base colors
Expand Down Expand Up @@ -61,29 +62,39 @@ package_installed() {

# Function to install GitHub CLI via apt
install_github_cli() {
if [ "$OS_TYPE" = "Darwin" ]; then
print_status "Installing GitHub CLI via Homebrew..."
if ! command -v brew >/dev/null 2>&1; then
print_error "Homebrew is required to install GitHub CLI on MacOS"
exit 1
fi
brew install gh
return 0
fi

print_status "Installing GitHub CLI via apt..."

# Add GitHub CLI repository if not already added
if [ ! -f "/etc/apt/sources.list.d/github-cli.list" ]; then
print_status "Adding GitHub CLI repository..."

# Download and install the signing key
curl -fsSL https://cli.github.com/packages/githubcli-archive-keyring.gpg | sudo dd of=/usr/share/keyrings/githubcli-archive-keyring.gpg

# Add the repository
echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/githubcli-archive-keyring.gpg] https://cli.github.com/packages stable main" | sudo tee /etc/apt/sources.list.d/github-cli.list > /dev/null

# Update package list
print_status "Updating package list..."
sudo apt-get update
else
print_status "GitHub CLI repository already configured"
fi

# Install GitHub CLI
print_status "Installing GitHub CLI..."
sudo apt-get install -y gh

# Verify installation
if command -v gh &> /dev/null; then
print_success "GitHub CLI installed successfully!"
Expand Down Expand Up @@ -145,4 +156,4 @@ print_success "$MODULE_NAME configuration installed successfully!"
print_status "Next steps:"
print_status "1. Run 'gh auth login' to authenticate with GitHub"
print_status "2. Configure your Git username and email if not already set"
print_status "3. Test the installation with 'gh --help'"
print_status "3. Test the installation with 'gh --help'"
Loading
Loading