Skip to content

Instantly share code, notes, and snippets.

@waynemsmith
Last active January 21, 2026 07:42
Show Gist options
  • Select an option

  • Save waynemsmith/a18ca838e03c88843cf49f921d23ef82 to your computer and use it in GitHub Desktop.

Select an option

Save waynemsmith/a18ca838e03c88843cf49f921d23ef82 to your computer and use it in GitHub Desktop.
Ops Workstation Setup Guide - Concurrent Systems

Ops Workstation Setup

Canonical laptop configuration for ops team members.

Prerequisites

Before starting, ensure you have:

  1. USB memory stick - 8GB+ for bootable Fedora installer
  2. GitHub account - create at github.com if needed
  3. Org membership - ask your team lead to add you to Concurrent-Systems org
  4. Deskguard access - ask your team lead to grant you access to the deskguard repo

Once you have access, proceed with the setup below.

Hardware Specs

Spec Minimum Recommended
RAM 16GB 32GB
Storage 256GB SSD 512GB SSD
Display 14" 15.6"

No vendor preference - Linux-friendly laptops work well (ThinkPad, HP ProBook, Dell Latitude).

OS Install

Fedora Xfce Spin - lightweight, stable, good hardware support.

Why Xfce Spin? Fedora "Spins" are alternative versions with different desktop environments. The default Fedora Workstation uses GNOME (heavier, more RAM). Xfce Spin uses the Xfce desktop - lighter, faster, ideal for ops laptops. Same Fedora underneath, just a different UI.

  1. Download ISO from Fedora Spins (Fedora 43 as of Jan 2026)

Linux users: Follow steps 2-5 below. Windows/Mac users: Use Fedora Media Writer instead (handles steps 2-5 automatically), then skip to step 6.

  1. Verify checksum (from the directory where you downloaded the ISO):

    curl -sL https://download.fedoraproject.org/pub/fedora/linux/releases/43/Spins/x86_64/iso/Fedora-Spins-43-1.6-x86_64-CHECKSUM | grep Xfce | sha256sum -c

    Should output: Fedora-Xfce-Live-43-1.6.x86_64.iso: OK

  2. Find your USB device:

    lsblk

    Identify your USB (e.g., sdb or sdc). Careful - wrong device will destroy data!

  3. Write ISO to USB:

    sudo dd if=Fedora-Xfce-Live-43-1.6.x86_64.iso of=/dev/sdX bs=4M status=progress oflag=sync

    Replace sdX with your USB device (e.g., sdb).

  4. Verify USB write:

    sudo cmp -n $(stat -c %s Fedora-Xfce-Live-43-1.6.x86_64.iso) Fedora-Xfce-Live-43-1.6.x86_64.iso /dev/sdX && echo "USB verified OK"

    Must show USB verified OK before proceeding.

  5. Boot from USB:

    • Reboot and press F9 (HP), F12, or Esc repeatedly for boot menu
    • Select USB device
    • Media check should pass (we verified the USB)
  6. UEFI settings (if needed): Disable Secure Boot, enable virtualization (VT-x/AMD-V).

  7. Install Fedora:

    • Select "Install to Hard Drive"
    • Language: English
    • Installation Destination: Select your drive, "Use entire disk" (wipes everything - no dual boot)
    • Encryption: Check "Encrypt my data" - enter a strong passphrase (4-5 random words)
      • Write this passphrase down immediately - required at every boot
      • Store in KeePassXC after setup
    • Create user: {firstname}{lastinit} (e.g., omaira) with your full name
    • Set a strong password (remember it!)
    • Wait for completion, reboot, remove USB when prompted
  8. Set hostname (after first boot into Fedora):

    sudo hostnamectl set-hostname {username}-{machinetype}
    # Example: sudo hostnamectl set-hostname omaira-probook

If boot fails with "media check FAIL": Re-download ISO, verify checksum, try a different USB stick.

If stuck during install: Take a photo of the screen, reboot back to previous OS (remove USB), share photo for help.

Post-Install Setup

System Update

Update all packages first. Reboot after this step if kernel was updated:

sudo dnf upgrade -y
sudo reboot

Note: First reboot after kernel updates may occasionally kernel panic. If this happens, hard restart - it typically resolves on second boot.

Install Packages

# Enable Docker CE repo (dnf5 syntax for Fedora 41+)
sudo dnf config-manager addrepo --from-repofile=https://download.docker.com/linux/fedora/docker-ce.repo

# Install core tools
sudo dnf install -y git gh docker-ce docker-ce-cli containerd.io \
    kubernetes-client vim curl jq keepassxc firefox

# Start Docker
sudo systemctl enable --now docker
sudo usermod -aG docker $USER

# Apply docker group without logging out
newgrp docker

Verify docker works:

docker run hello-world

Critical Passphrase Storage

Secret Where to Store Why
LUKS disk passphrase Paper in physical safe If forgotten, can't boot - KeePassXC is on encrypted disk
KeePassXC master password Memory + paper in safe Same reason - needed to access everything else
SSH key passphrases KeePassXC (local) If lost, regenerate keys and submit new PR

Never store LUKS or KeePassXC master password only on the encrypted machine - you won't be able to access it if you forget.

KeePassXC Setup

Set up your password manager before generating SSH keys - you'll need it to store passphrases.

Create Personal Database

mkdir -p ~/.keys
chmod 700 ~/.keys
keepassxc &
  • File → New Database
  • Save as ~/.keys/personal.kdbx
  • Set a strong master password (memorize this one)

Recommended Database Structure

Create this group and entry structure:

personal.kdbx
├── SSH Keys/
│   ├── GitHub      (passphrase for ~/.ssh/id_github)
│   ├── CS-Jump     (passphrase for ~/.ssh/id_csjump)
│   └── Sites       (passphrase for ~/.ssh/id_sites)
└── Sites/
    └── Master Secret   (your secret suffix for node passwords)

To create:

  1. Right-click Root → New Group → name it SSH Keys
  2. Create another group Sites
  3. Add a Master Secret entry with a generated passphrase

Node Password Pattern

Every node MUST have a unique password. Never reuse the same password across nodes.

Use a derived pattern so you only need to remember one secret:

{nodename}-{master-secret}

For example, if your master secret is purpleElephant42:

  • movtog-cspr01 → movtog-cspr01-purpleElephant42
  • movngr-cspr02 → movngr-cspr02-purpleElephant42
  • movivy-cstst01 → movivy-cstst01-purpleElephant42

This gives you:

  • Unique password per node (security requirement)
  • Only one secret to store in KeePassXC
  • If one node is compromised, other nodes remain protected
  • Easy to construct when prompted

How to Generate Passphrases

For each SSH key passphrase, use KeePassXC's generator:

  1. Create new entry in SSH Keys group
  2. Set Title (e.g., GitHub)
  3. Click the dice icon next to Password
  4. Select "Passphrase" tab
  5. Word count: 4-5 words
  6. Click "Apply Password"
  7. Save the entry

You'll use this process for each SSH key you create below.

Naming Conventions

Item Convention Example
Username {firstname}{lastinit} omaira
Hostname {username}-{machinetype} omaira-probook

Machine types: probook, thinkpad, latitude, xps, macbook, etc.

Use your username consistently for git commits, SSH keys, and server accounts.

Git/GitHub Setup

GitHub Account Options

You can either use your existing personal GitHub account or create a new one for work.

Option A: Use your personal account (recommended for most devs)

  • Your contributions appear on your profile (career value)
  • Add your company email as a secondary email in GitHub Settings → Emails
  • Use the company email for git config (commits linked to your account)
  • On leaving: company removes org access, you keep your profile

Option B: Create a new work account

  • Clean separation between work and personal
  • Use company email as the primary email
  • On leaving: account can be transferred or removed
  • No contribution history carries over

Either option is fine. Most developers prefer Option A to maintain a single profile. GitHub supports multiple emails per account specifically for this use case.

Configure Git

git config --global user.name "Your Full Name"
git config --global user.email "[email protected]"
git config --global init.defaultBranch main

Note: Use your real full name (e.g., "Khurram Shahzad"), not a username or handle. Use your company email regardless of which GitHub account option you choose. This ensures commits are traceable to the organisation.

Multiple Email Identities

If you contribute to open source or have personal hobby projects (or contractors working with multiple clients), use Git's conditional includes to automatically switch emails based on directory:

~/.gitconfig:

[user]
    name = Your Full Name
    email = [email protected]

[includeIf "gitdir:~/g/"]
    path = ~/.gitconfig-cs

~/.gitconfig-cs:

[user]
    email = [email protected]

Now any repo under ~/g/ uses your CS email automatically, while personal projects elsewhere use your personal email. Add additional includeIf blocks for other organisations as needed.

Initial GitHub Authentication

First, authenticate with GitHub CLI:

gh auth login

Select:

  • GitHub.com
  • HTTPS
  • Login with a web browser

This stores an OAuth token in ~/.config/gh/hosts.yml. The gh CLI uses this token for API calls (issues, PRs, etc). Later, you'll set up SSH keys for git operations.

Clone Deskguard

mkdir -p ~/github
gh repo clone Concurrent-Systems/deskguard ~/github/deskguard
cd ~/github/deskguard

SSH Keys

Now generate all your SSH keys. For each key, use KeePassXC to generate a passphrase and save it.

Generate All Keys

Replace {username} and {machine} with your values (e.g., omaira and probook):

# GitHub key
ssh-keygen -t ed25519 -C "{username}-{machine}-github" -f ~/.ssh/id_github

# Bastion key
ssh-keygen -t ed25519 -C "{username}-{machine}-csjump" -f ~/.ssh/id_csjump

# Sites key
ssh-keygen -t ed25519 -C "{username}-{machine}-sites" -f ~/.ssh/id_sites

Save each passphrase in KeePassXC under SSH Keys/:

  • GitHub
  • CS-Jump
  • Sites

Generate SSH Config

The script creates your entire ~/.ssh/config with proper permissions:

cd ~/github/deskguard
python3 ssh-config-gen.py {username}

Upload GitHub Key

Add your GitHub SSH key to your account:

gh ssh-key add ~/.ssh/id_github.pub --title "{username}-{machine}"

Add Keys to ssh-agent

Add to ~/.bashrc for persistence:

echo '
# Start ssh-agent if not running
if [ -z "$SSH_AUTH_SOCK" ]; then
    eval "$(ssh-agent -s)"
fi' >> ~/.bashrc

source ~/.bashrc

Add your keys (you'll be prompted for passphrases):

ssh-add ~/.ssh/id_github
ssh-add ~/.ssh/id_csjump
ssh-add ~/.ssh/id_sites

macOS users: Use ssh-add --apple-use-keychain instead - see SSH-KEYS.md.

Test GitHub SSH

Should show: Hi {username}! You've successfully authenticated...

Submit Infrastructure Keys

Submit your public keys for provisioning on the servers:

cd ~/github/deskguard
python3 ssh-config-gen.py {username} --submit-keys

This validates your keys, copies them to keys/{username}/, and pushes to main.

Wait for your team lead to confirm your keys have been provisioned on the servers.

Test Infrastructure Access

Once provisioned:

ssh cs-jump echo "Jump host OK"

Run Deskguard

Run the security audit and submit your assessment:

cd ~/github/deskguard
git checkout main
git pull
python3 deskguard.py --username {firstname}-{lastname} --submit

This runs security checks and automatically creates a PR with your report.

Clone Infra (Optional)

After your SSH keys are provisioned, you can clone the main infra repo:

mkdir -p ~/g
git clone [email protected]:Concurrent-Systems/infra.git ~/g/infra
cd ~/g/infra
git submodule update --init software/deskguard

You'll get access to additional submodules as needed for your role.

Notes

  • No VPN needed - all access via SSH ProxyJump through cs-jump
  • Standard toolset: git, docker, kubectl, vim, curl, jq
  • For ops CLI tools, use the infra repo (run commands from repo root)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment