Merge branch 'master' of git.mvl.sh:vleeuwenmenno/dotfiles
This commit is contained in:
@@ -6,3 +6,6 @@ mennos-desktop ansible_connection=local
|
||||
mennos-vps ansible_connection=local
|
||||
mennos-server ansible_connection=local
|
||||
mennos-rtlsdr-pc ansible_connection=local
|
||||
|
||||
[wsl]
|
||||
mennos-desktopw ansible_connection=local
|
||||
|
||||
@@ -2,18 +2,18 @@
|
||||
- name: Configure all hosts
|
||||
hosts: all
|
||||
handlers:
|
||||
- name: Import handler tasks
|
||||
ansible.builtin.import_tasks: handlers/main.yml
|
||||
- name: Import handler tasks
|
||||
ansible.builtin.import_tasks: handlers/main.yml
|
||||
gather_facts: true
|
||||
|
||||
tasks:
|
||||
- name: Include global tasks
|
||||
ansible.builtin.import_tasks: tasks/global/global.yml
|
||||
- name: Include global tasks
|
||||
ansible.builtin.import_tasks: tasks/global/global.yml
|
||||
|
||||
- name: Include workstation tasks
|
||||
ansible.builtin.import_tasks: tasks/workstations/workstation.yml
|
||||
when: inventory_hostname in ['mennos-laptop', 'mennos-desktop']
|
||||
- name: Include workstation tasks
|
||||
ansible.builtin.import_tasks: tasks/workstations/workstation.yml
|
||||
when: inventory_hostname in ['mennos-laptop', 'mennos-desktop']
|
||||
|
||||
- name: Include server tasks
|
||||
ansible.builtin.import_tasks: tasks/servers/server.yml
|
||||
when: inventory_hostname in ['mennos-vps', 'mennos-server', 'mennos-rtlsdr-pc']
|
||||
- name: Include server tasks
|
||||
ansible.builtin.import_tasks: tasks/servers/server.yml
|
||||
when: inventory_hostname in ['mennos-vps', 'mennos-server', 'mennos-rtlsdr-pc', 'mennos-desktopw']
|
||||
|
||||
@@ -28,6 +28,12 @@ smart_aliases:
|
||||
check_host: "192.168.1.253"
|
||||
timeout: "2s"
|
||||
|
||||
rtlsdr:
|
||||
primary: "rtlsdr-local"
|
||||
fallback: "rtlsdr"
|
||||
check_host: "192.168.1.252"
|
||||
timeout: "2s"
|
||||
|
||||
# Background SSH Tunnel Definitions
|
||||
tunnels:
|
||||
# Example: Desktop database tunnel
|
||||
|
||||
@@ -30,10 +30,10 @@ type LoggingConfig struct {
|
||||
|
||||
// SmartAlias represents a smart SSH alias configuration
|
||||
type SmartAlias struct {
|
||||
Primary string `yaml:"primary"` // SSH config host to use when local
|
||||
Fallback string `yaml:"fallback"` // SSH config host to use when remote
|
||||
Primary string `yaml:"primary"` // SSH config host to use when local
|
||||
Fallback string `yaml:"fallback"` // SSH config host to use when remote
|
||||
CheckHost string `yaml:"check_host"` // IP to ping for connectivity test
|
||||
Timeout string `yaml:"timeout"` // Ping timeout (default: "2s")
|
||||
Timeout string `yaml:"timeout"` // Ping timeout (default: "2s")
|
||||
}
|
||||
|
||||
// TunnelDefinition represents a tunnel configuration
|
||||
@@ -47,36 +47,39 @@ type TunnelDefinition struct {
|
||||
|
||||
// TunnelState represents runtime state of an active tunnel
|
||||
type TunnelState struct {
|
||||
Name string `json:"name"`
|
||||
Source string `json:"source"` // "config" or "adhoc"
|
||||
Type string `json:"type"` // local, remote, dynamic
|
||||
LocalPort int `json:"local_port"`
|
||||
RemoteHost string `json:"remote_host"`
|
||||
RemotePort int `json:"remote_port"`
|
||||
SSHHost string `json:"ssh_host"`
|
||||
SSHHostResolved string `json:"ssh_host_resolved"` // After smart alias resolution
|
||||
PID int `json:"pid"`
|
||||
Status string `json:"status"`
|
||||
StartedAt time.Time `json:"started_at"`
|
||||
LastSeen time.Time `json:"last_seen"`
|
||||
CommandLine string `json:"command_line"`
|
||||
Name string `json:"name"`
|
||||
Source string `json:"source"` // "config" or "adhoc"
|
||||
Type string `json:"type"` // local, remote, dynamic
|
||||
LocalPort int `json:"local_port"`
|
||||
RemoteHost string `json:"remote_host"`
|
||||
RemotePort int `json:"remote_port"`
|
||||
SSHHost string `json:"ssh_host"`
|
||||
SSHHostResolved string `json:"ssh_host_resolved"` // After smart alias resolution
|
||||
PID int `json:"pid"`
|
||||
Status string `json:"status"`
|
||||
StartedAt time.Time `json:"started_at"`
|
||||
LastSeen time.Time `json:"last_seen"`
|
||||
CommandLine string `json:"command_line"`
|
||||
}
|
||||
|
||||
// Config represents the YAML configuration structure
|
||||
type Config struct {
|
||||
Logging LoggingConfig `yaml:"logging"`
|
||||
SmartAliases map[string]SmartAlias `yaml:"smart_aliases"`
|
||||
Tunnels map[string]TunnelDefinition `yaml:"tunnels"`
|
||||
Logging LoggingConfig `yaml:"logging"`
|
||||
SmartAliases map[string]SmartAlias `yaml:"smart_aliases"`
|
||||
Tunnels map[string]TunnelDefinition `yaml:"tunnels"`
|
||||
}
|
||||
|
||||
const (
|
||||
realSSHPath = "/usr/bin/ssh"
|
||||
defaultSSHPath = "/usr/bin/ssh"
|
||||
wslSSHPath = "ssh.exe"
|
||||
wslDetectPath = "/mnt/c/Windows/System32/cmd.exe"
|
||||
)
|
||||
|
||||
var (
|
||||
configDir string
|
||||
tunnelsDir string
|
||||
config *Config
|
||||
configDir string
|
||||
tunnelsDir string
|
||||
config *Config
|
||||
sshPath string // Will be set based on WSL2 detection
|
||||
|
||||
// Global flags
|
||||
tunnelMode bool
|
||||
@@ -92,10 +95,10 @@ var (
|
||||
)
|
||||
|
||||
var rootCmd = &cobra.Command{
|
||||
Use: "ssh",
|
||||
Short: "Smart SSH utility with tunnel management",
|
||||
Long: "A transparent SSH wrapper that provides smart alias resolution and background tunnel management",
|
||||
Run: handleSSH,
|
||||
Use: "ssh",
|
||||
Short: "Smart SSH utility with tunnel management",
|
||||
Long: "A transparent SSH wrapper that provides smart alias resolution and background tunnel management",
|
||||
Run: handleSSH,
|
||||
DisableFlagParsing: true,
|
||||
}
|
||||
|
||||
@@ -103,13 +106,16 @@ var tunnelCmd = &cobra.Command{
|
||||
Use: "tunnel [tunnel-name]",
|
||||
Short: "Manage background SSH tunnels",
|
||||
Long: "Create, list, and manage persistent SSH tunnels in the background",
|
||||
Run: func(cmd *cobra.Command, args []string) {
|
||||
Run: func(cmd *cobra.Command, args []string) {
|
||||
handleTunnelManual(append([]string{"--tunnel"}, args...))
|
||||
},
|
||||
Args: cobra.MaximumNArgs(1),
|
||||
Args: cobra.MaximumNArgs(1),
|
||||
}
|
||||
|
||||
func init() {
|
||||
// Detect and set SSH path based on environment (WSL2 vs native Linux)
|
||||
sshPath = detectSSHPath()
|
||||
|
||||
// Initialize config directory
|
||||
homeDir, err := os.UserHomeDir()
|
||||
if err != nil {
|
||||
@@ -141,6 +147,13 @@ func init() {
|
||||
// Initialize logging
|
||||
initLogging(config.Logging)
|
||||
|
||||
// Log SSH path detection (after logging is initialized)
|
||||
if isWSL2() {
|
||||
log.Debug().Str("ssh_path", sshPath).Msg("WSL2 detected, using Windows SSH")
|
||||
} else {
|
||||
log.Debug().Str("ssh_path", sshPath).Msg("Native Linux environment, using Linux SSH")
|
||||
}
|
||||
|
||||
// Global flags
|
||||
rootCmd.PersistentFlags().BoolVarP(&tunnelMode, "tunnel", "T", false, "Enable tunnel mode")
|
||||
rootCmd.Flags().BoolVarP(&tunnelOpen, "open", "O", false, "Open a tunnel")
|
||||
@@ -169,6 +182,22 @@ func init() {
|
||||
}
|
||||
}
|
||||
|
||||
// detectSSHPath determines the correct SSH binary path based on the environment
|
||||
func detectSSHPath() string {
|
||||
if isWSL2() {
|
||||
// In WSL2, use Windows SSH
|
||||
return wslSSHPath
|
||||
}
|
||||
// Default to Linux SSH
|
||||
return defaultSSHPath
|
||||
}
|
||||
|
||||
// isWSL2 checks if we're running in WSL2 by looking for Windows System32
|
||||
func isWSL2() bool {
|
||||
_, err := os.Stat(wslDetectPath)
|
||||
return err == nil
|
||||
}
|
||||
|
||||
func main() {
|
||||
// Check if this is a tunnel command first
|
||||
args := os.Args[1:]
|
||||
@@ -563,7 +592,7 @@ func openTunnel(name string) error {
|
||||
log.Debug().Strs("command", cmdArgs).Msg("Starting SSH tunnel")
|
||||
|
||||
// Start SSH process
|
||||
cmd := exec.Command(realSSHPath, cmdArgs[1:]...)
|
||||
cmd := exec.Command(sshPath, cmdArgs[1:]...)
|
||||
|
||||
// Capture stderr to see any SSH errors
|
||||
var stderr bytes.Buffer
|
||||
@@ -708,7 +737,9 @@ func createAdhocTunnel() (TunnelDefinition, error) {
|
||||
}
|
||||
|
||||
func buildSSHCommand(tunnel TunnelDefinition, sshHost string) []string {
|
||||
args := []string{"ssh", "-f", "-N"}
|
||||
// Use the detected SSH path basename for the command
|
||||
sshBinary := filepath.Base(sshPath)
|
||||
args := []string{sshBinary, "-f", "-N"}
|
||||
|
||||
switch tunnel.Type {
|
||||
case "local":
|
||||
@@ -1056,18 +1087,37 @@ func findSSHProcessByPort(port int) int {
|
||||
|
||||
// executeRealSSH executes the real SSH binary with given arguments
|
||||
func executeRealSSH(args []string) {
|
||||
// Check if real SSH exists
|
||||
if _, err := os.Stat(realSSHPath); os.IsNotExist(err) {
|
||||
log.Error().Str("path", realSSHPath).Msg("Real SSH binary not found")
|
||||
fmt.Fprintf(os.Stderr, "Error: Real SSH binary not found at %s\n", realSSHPath)
|
||||
log.Debug().Str("ssh_path", sshPath).Strs("args", args).Msg("Executing real SSH")
|
||||
|
||||
// In WSL2, we need to use exec.Command instead of syscall.Exec for Windows binaries
|
||||
if isWSL2() {
|
||||
cmd := exec.Command(sshPath, args...)
|
||||
cmd.Stdin = os.Stdin
|
||||
cmd.Stdout = os.Stdout
|
||||
cmd.Stderr = os.Stderr
|
||||
|
||||
err := cmd.Run()
|
||||
if err != nil {
|
||||
if exitErr, ok := err.(*exec.ExitError); ok {
|
||||
os.Exit(exitErr.ExitCode())
|
||||
}
|
||||
log.Error().Err(err).Msg("Failed to execute SSH")
|
||||
fmt.Fprintf(os.Stderr, "Error executing SSH: %v\n", err)
|
||||
os.Exit(1)
|
||||
}
|
||||
os.Exit(0)
|
||||
}
|
||||
|
||||
// For native Linux, check if SSH exists
|
||||
if _, err := os.Stat(sshPath); os.IsNotExist(err) {
|
||||
log.Error().Str("path", sshPath).Msg("Real SSH binary not found")
|
||||
fmt.Fprintf(os.Stderr, "Error: Real SSH binary not found at %s\n", sshPath)
|
||||
os.Exit(1)
|
||||
}
|
||||
|
||||
log.Debug().Str("ssh_path", realSSHPath).Strs("args", args).Msg("Executing real SSH")
|
||||
|
||||
// Execute the real SSH binary
|
||||
// Using syscall.Exec to replace current process (like exec in shell)
|
||||
err := syscall.Exec(realSSHPath, append([]string{"ssh"}, args...), os.Environ())
|
||||
// Execute the real SSH binary using syscall.Exec (Linux only)
|
||||
// This replaces the current process (like exec in shell)
|
||||
err := syscall.Exec(sshPath, append([]string{"ssh"}, args...), os.Environ())
|
||||
if err != nil {
|
||||
log.Error().Err(err).Msg("Failed to execute SSH")
|
||||
fmt.Fprintf(os.Stderr, "Error executing SSH: %v\n", err)
|
||||
|
||||
@@ -53,6 +53,7 @@
|
||||
- io.mango3d.LycheeSlicer
|
||||
|
||||
# Utilities
|
||||
- com.fastmail.Fastmail
|
||||
- com.ranfdev.DistroShelf
|
||||
- io.missioncenter.MissionCenter
|
||||
- io.gitlab.elescoute.spacelaunch
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
// #############################################
|
||||
// ## Theming ##
|
||||
// #############################################
|
||||
"formatter": "prettier",
|
||||
"context_servers": {
|
||||
"mcp-server-context7": {
|
||||
"source": "extension",
|
||||
@@ -96,7 +97,7 @@
|
||||
"hide_mouse": "on_typing",
|
||||
"on_last_window_closed": "quit_app",
|
||||
"ensure_final_newline_on_save": true,
|
||||
"format_on_save": "prettier",
|
||||
"format_on_save": "on",
|
||||
"tab_size": 2,
|
||||
"inlay_hints": {
|
||||
"enabled": true,
|
||||
|
||||
@@ -26,6 +26,7 @@ def main():
|
||||
printfe("red", f"Error reading help file: {e}")
|
||||
return 1
|
||||
|
||||
print(help_text)
|
||||
println(" ", "cyan")
|
||||
return 0
|
||||
|
||||
|
||||
59
bin/dotf
59
bin/dotf
@@ -5,10 +5,12 @@ import signal
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
|
||||
def signal_handler(sig, frame):
|
||||
print('Exiting.')
|
||||
print("Exiting.")
|
||||
sys.exit(0)
|
||||
|
||||
|
||||
signal.signal(signal.SIGINT, signal_handler)
|
||||
|
||||
# Script constants
|
||||
@@ -22,43 +24,54 @@ from helpers.functions import printfe, ensure_dependencies
|
||||
|
||||
ensure_dependencies()
|
||||
|
||||
|
||||
def run_script(script_path, args):
|
||||
"""Run an action script with the given arguments"""
|
||||
if not os.path.isfile(script_path) or not os.access(script_path, os.X_OK):
|
||||
printfe("red", f"Error: Script not found or not executable: {script_path}")
|
||||
return 1
|
||||
|
||||
result = subprocess.run([script_path] + args, env={**os.environ, "DOTFILES_PATH": DOTFILES_PATH})
|
||||
result = subprocess.run(
|
||||
[script_path] + args, env={**os.environ, "DOTFILES_PATH": DOTFILES_PATH}
|
||||
)
|
||||
return result.returncode
|
||||
|
||||
|
||||
def update(args):
|
||||
"""Run the update action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/update.py", args)
|
||||
|
||||
|
||||
def hello(args):
|
||||
"""Run the hello action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/hello.py", args)
|
||||
|
||||
|
||||
def help(args):
|
||||
"""Run the help action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/help.py", args)
|
||||
|
||||
|
||||
def service(args):
|
||||
"""Run the service/docker action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/service.py", args)
|
||||
|
||||
|
||||
def lint(args):
|
||||
"""Run the lint action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/lint.py", args)
|
||||
|
||||
|
||||
def timers(args):
|
||||
"""Run the timers action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/timers.py", args)
|
||||
|
||||
|
||||
def source(args):
|
||||
"""Run the source action"""
|
||||
return run_script(f"{DOTFILES_BIN}/actions/source.py", args)
|
||||
|
||||
|
||||
def ensure_git_hooks():
|
||||
"""Ensure git hooks are correctly set up"""
|
||||
hooks_dir = os.path.join(DOTFILES_ROOT, ".git/hooks")
|
||||
@@ -66,14 +79,19 @@ def ensure_git_hooks():
|
||||
|
||||
# Validate target directory exists
|
||||
if not os.path.isdir(target_link):
|
||||
printfe("red", f"Error: Git hooks source directory does not exist: {target_link}")
|
||||
printfe(
|
||||
"red", f"Error: Git hooks source directory does not exist: {target_link}"
|
||||
)
|
||||
return 1
|
||||
|
||||
# Handle existing symlink
|
||||
if os.path.islink(hooks_dir):
|
||||
current_link = os.readlink(hooks_dir)
|
||||
if current_link != target_link:
|
||||
printfe("yellow", "Incorrect git hooks symlink found. Removing and recreating...")
|
||||
printfe(
|
||||
"yellow",
|
||||
"Incorrect git hooks symlink found. Removing and recreating...",
|
||||
)
|
||||
os.remove(hooks_dir)
|
||||
else:
|
||||
return 0
|
||||
@@ -82,6 +100,7 @@ def ensure_git_hooks():
|
||||
if os.path.isdir(hooks_dir) and not os.path.islink(hooks_dir):
|
||||
printfe("yellow", "Removing existing hooks directory...")
|
||||
import shutil
|
||||
|
||||
shutil.rmtree(hooks_dir)
|
||||
|
||||
# Create new symlink
|
||||
@@ -93,6 +112,7 @@ def ensure_git_hooks():
|
||||
printfe("red", f"Failed to create git hooks symlink: {e}")
|
||||
return 1
|
||||
|
||||
|
||||
def main():
|
||||
# Ensure we're in the correct directory
|
||||
if not os.path.isdir(DOTFILES_ROOT):
|
||||
@@ -114,13 +134,42 @@ def main():
|
||||
"service": service,
|
||||
"lint": lint,
|
||||
"timers": timers,
|
||||
"source": source
|
||||
"source": source,
|
||||
}
|
||||
|
||||
if command in commands:
|
||||
return commands[command](args)
|
||||
else:
|
||||
# For invalid commands, show error after logo
|
||||
if command != "help":
|
||||
from helpers.functions import logo
|
||||
|
||||
logo(continue_after=True)
|
||||
print()
|
||||
printfe("red", f"✗ Error: Unknown command '{command}'")
|
||||
|
||||
# Provide helpful hints for common mistakes
|
||||
if command == "ls":
|
||||
printfe("yellow", " Hint: Did you mean 'dotf service ls'?")
|
||||
elif command == "list":
|
||||
printfe("yellow", " Hint: Did you mean 'dotf service list'?")
|
||||
|
||||
print()
|
||||
# Now print help text without logo
|
||||
dotfiles_path = os.environ.get(
|
||||
"DOTFILES_PATH", os.path.expanduser("~/.dotfiles")
|
||||
)
|
||||
try:
|
||||
with open(
|
||||
f"{dotfiles_path}/bin/resources/help.txt", "r", encoding="utf-8"
|
||||
) as f:
|
||||
print(f.read())
|
||||
except OSError as e:
|
||||
printfe("red", f"Error reading help file: {e}")
|
||||
return 1
|
||||
return 1
|
||||
return help([])
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
sys.exit(main())
|
||||
|
||||
0
config/autostart/Nextcloud.desktop
Normal file → Executable file
0
config/autostart/Nextcloud.desktop
Normal file → Executable file
0
config/autostart/equibop.desktop
Normal file → Executable file
0
config/autostart/equibop.desktop
Normal file → Executable file
@@ -39,6 +39,7 @@
|
||||
export STARSHIP_ENABLE_RIGHT_PROMPT="true"
|
||||
export STARSHIP_ENABLE_BASH_COMPLETION="true"
|
||||
export XDG_DATA_DIRS="/usr/share:/var/lib/flatpak/exports/share:${config.home.homeDirectory}/.local/share/flatpak/exports/share"
|
||||
export BUN_INSTALL="$HOME/.bun"
|
||||
|
||||
# Source .profile (If exists)
|
||||
if [ -f "${config.home.homeDirectory}/.profile" ]; then
|
||||
@@ -136,6 +137,11 @@
|
||||
bind -x '"\C-r": fzf_history_search'
|
||||
fi
|
||||
|
||||
# In case this is WSL, let's add various Windows executables as aliases
|
||||
if [ -f "/mnt/c/Windows/System32/cmd.exe" ]; then
|
||||
alias ssh-add="ssh-add.exe"
|
||||
fi
|
||||
|
||||
# Display welcome message for interactive shells
|
||||
if [ -t 1 ]; then
|
||||
command -v helloworld &> /dev/null && helloworld
|
||||
@@ -189,10 +195,6 @@
|
||||
# Kubernetes aliases
|
||||
"kubectl" = "minikube kubectl --";
|
||||
|
||||
# Editor aliases
|
||||
"zeditor" = "${config.home.homeDirectory}/.local/bin/zed";
|
||||
"zed" = "${config.home.homeDirectory}/.local/bin/zed";
|
||||
|
||||
# SSH alias
|
||||
"ssh" = "${config.home.homeDirectory}/.local/bin/smart-ssh";
|
||||
|
||||
@@ -212,6 +214,7 @@
|
||||
export PATH="$PATH:${config.home.homeDirectory}/.cargo/bin"
|
||||
export PATH="$PATH:${config.home.homeDirectory}/.dotfiles/bin"
|
||||
export PATH="/usr/bin:$PATH"
|
||||
export PATH="$BUN_INSTALL/bin:$PATH"
|
||||
|
||||
# PKG_CONFIG_PATH
|
||||
if [ -d /usr/lib/pkgconfig ]; then
|
||||
|
||||
@@ -1,8 +1,80 @@
|
||||
[General]
|
||||
clientVersion=3.16.0-1 (Debian built)
|
||||
desktopEnterpriseChannel=daily
|
||||
isVfsEnabled=false
|
||||
launchOnSystemStartup=true
|
||||
optionalServerNotifications=true
|
||||
overrideLocalDir=
|
||||
overrideServerUrl=
|
||||
promptDeleteAllFiles=false
|
||||
showCallNotifications=true
|
||||
showChatNotifications=true
|
||||
|
||||
[Accounts]
|
||||
0\Folders\1\ignoreHiddenFiles=false
|
||||
0\Folders\1\journalPath=.sync_42a4129584d0.db
|
||||
0\Folders\1\localPath=/home/menno/Nextcloud/
|
||||
0\Folders\1\paused=false
|
||||
0\Folders\1\targetPath=/
|
||||
0\Folders\1\version=2
|
||||
0\Folders\1\virtualFilesMode=off
|
||||
0\Folders\2\ignoreHiddenFiles=false
|
||||
0\Folders\2\journalPath=.sync_65a742b0aa83.db
|
||||
0\Folders\2\localPath=/home/menno/Desktop/
|
||||
0\Folders\2\paused=false
|
||||
0\Folders\2\targetPath=/Desktop
|
||||
0\Folders\2\version=2
|
||||
0\Folders\2\virtualFilesMode=off
|
||||
0\Folders\3\ignoreHiddenFiles=false
|
||||
0\Folders\3\journalPath=.sync_65289e64a490.db
|
||||
0\Folders\3\localPath=/home/menno/Documents/
|
||||
0\Folders\3\paused=false
|
||||
0\Folders\3\targetPath=/Documents
|
||||
0\Folders\3\version=2
|
||||
0\Folders\3\virtualFilesMode=off
|
||||
0\Folders\4\ignoreHiddenFiles=false
|
||||
0\Folders\4\journalPath=.sync_283a65eecb9c.db
|
||||
0\Folders\4\localPath=/home/menno/Music/
|
||||
0\Folders\4\paused=false
|
||||
0\Folders\4\targetPath=/Music
|
||||
0\Folders\4\version=2
|
||||
0\Folders\4\virtualFilesMode=off
|
||||
0\Folders\5\ignoreHiddenFiles=false
|
||||
0\Folders\5\journalPath=.sync_884042991bd6.db
|
||||
0\Folders\5\localPath=/home/menno/3D Objects/
|
||||
0\Folders\5\paused=false
|
||||
0\Folders\5\targetPath=/3D Objects
|
||||
0\Folders\5\version=2
|
||||
0\Folders\5\virtualFilesMode=off
|
||||
0\Folders\6\ignoreHiddenFiles=false
|
||||
0\Folders\6\journalPath=.sync_90ea5e3c7a33.db
|
||||
0\Folders\6\localPath=/home/menno/Videos/
|
||||
0\Folders\6\paused=false
|
||||
0\Folders\6\targetPath=/Videos
|
||||
0\Folders\6\version=2
|
||||
0\Folders\6\virtualFilesMode=off
|
||||
0\authType=webflow
|
||||
0\dav_user=menno
|
||||
0\displayName=Menno van Leeuwen
|
||||
0\encryptionCertificateSha256Fingerprint=@ByteArray()
|
||||
0\networkDownloadLimit=0
|
||||
0\networkDownloadLimitSetting=-2
|
||||
0\networkProxyHostName=
|
||||
0\networkProxyNeedsAuth=false
|
||||
0\networkProxyPort=0
|
||||
0\networkProxySetting=0
|
||||
0\networkProxyType=2
|
||||
0\networkProxyUser=
|
||||
0\networkUploadLimit=0
|
||||
0\networkUploadLimitSetting=-2
|
||||
0\serverColor=@Variant(\0\0\0\x43\x1\xff\xff\x1c\x1c$$<<\0\0)
|
||||
0\serverHasValidSubscription=false
|
||||
0\serverTextColor=@Variant(\0\0\0\x43\x1\xff\xff\xff\xff\xff\xff\xff\xff\0\0)
|
||||
0\serverVersion=32.0.0.13
|
||||
0\url=https://drive.mvl.sh
|
||||
0\version=13
|
||||
0\webflow_user=menno
|
||||
version=13
|
||||
|
||||
[Settings]
|
||||
geometry=@ByteArray(\x1\xd9\xd0\xcb\0\x3\0\0\0\0\0\0\0\0\x4\xe\0\0\x2\x37\0\0\x6W\0\0\0\0\0\0\x4\xe\0\0\x2\x37\0\0\x6W\0\0\0\x1\0\0\0\0\x14\0\0\0\0\0\0\0\x4\xe\0\0\x2\x37\0\0\x6W)
|
||||
|
||||
12
flake.lock
generated
12
flake.lock
generated
@@ -41,11 +41,11 @@
|
||||
},
|
||||
"nixpkgs": {
|
||||
"locked": {
|
||||
"lastModified": 1760423683,
|
||||
"narHash": "sha256-Tb+NYuJhWZieDZUxN6PgglB16yuqBYQeMJyYBGCXlt8=",
|
||||
"lastModified": 1760862643,
|
||||
"narHash": "sha256-PXwG0TM7Ek87DNx4LbGWuD93PbFeKAJs4FfALtp7Wo0=",
|
||||
"owner": "nixos",
|
||||
"repo": "nixpkgs",
|
||||
"rev": "a493e93b4a259cd9fea8073f89a7ed9b1c5a1da2",
|
||||
"rev": "33c6dca0c0cb31d6addcd34e90a63ad61826b28c",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
@@ -77,11 +77,11 @@
|
||||
"nixpkgs": "nixpkgs_2"
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1751283143,
|
||||
"narHash": "sha256-I3DMLT0qg5xxjS7BrmOBIK6pG+vZqOhKivEGnkDIli8=",
|
||||
"lastModified": 1760894497,
|
||||
"narHash": "sha256-u2unItzVvUe3Y2opdJrISGtHSmQLVnDOIfhWvSBrw74=",
|
||||
"owner": "brizzbuzz",
|
||||
"repo": "opnix",
|
||||
"rev": "1a807befe8f418da0df24c54b9633c395d840d0e",
|
||||
"rev": "92974503378ca6ec6206b74cd3a78377a5796cbb",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
|
||||
@@ -45,6 +45,7 @@
|
||||
"mennos-server" = mkHomeConfig "x86_64-linux" "mennos-server" true;
|
||||
"mennos-rtlsdr-pc" = mkHomeConfig "x86_64-linux" "mennos-rtlsdr-pc" true;
|
||||
"mennos-laptop" = mkHomeConfig "x86_64-linux" "mennos-laptop" false;
|
||||
"mennos-desktopw" = mkHomeConfig "x86_64-linux" "mennos-desktopw" true;
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
39
setup.sh
39
setup.sh
@@ -166,6 +166,13 @@ validate_hostname() {
|
||||
return 0
|
||||
}
|
||||
|
||||
is_wsl() {
|
||||
if grep -qEi "(Microsoft|WSL)" /proc/version &> /dev/null; then
|
||||
return 0
|
||||
fi
|
||||
return 1
|
||||
}
|
||||
|
||||
update_home_manager_flake() {
|
||||
local hostname="$1"
|
||||
local isServer="$2"
|
||||
@@ -290,7 +297,15 @@ prepare_hostname() {
|
||||
fi
|
||||
|
||||
log_info "Setting hostname to $hostname..."
|
||||
sudo hostnamectl set-hostname "$hostname" || die "Failed to set hostname"
|
||||
|
||||
# WSL doesn't support hostnamectl reliably, use /etc/hostname instead
|
||||
if is_wsl; then
|
||||
log_info "Detected WSL environment, using alternative hostname method..."
|
||||
echo "$hostname" | sudo tee /etc/hostname > /dev/null || die "Failed to set hostname"
|
||||
sudo hostname "$hostname" || log_warning "Failed to set hostname for current session (will take effect on restart)"
|
||||
else
|
||||
sudo hostnamectl set-hostname "$hostname" || die "Failed to set hostname"
|
||||
fi
|
||||
|
||||
echo "$hostname" > "$hostname_file" || die "Failed to save hostname"
|
||||
log_success "Hostname set successfully."
|
||||
@@ -301,7 +316,14 @@ warning_prompt() {
|
||||
log_error "Please ensure you have a backup of your data before proceeding."
|
||||
log_error "This script will modify system files and may require sudo permissions."
|
||||
echo ""
|
||||
log_info "This script has been tested on Ubuntu 22.04, 24.04, 24.10, Pop!_OS 24.04 Alpha 7, Debian 12, Fedora 41 and CachyOS."
|
||||
|
||||
if is_wsl; then
|
||||
log_info "WSL environment detected."
|
||||
log_info "This script has been tested on Ubuntu under WSL2."
|
||||
else
|
||||
log_info "This script has been tested on Ubuntu 22.04, 24.04, 24.10, Pop!_OS 24.04 Alpha 7, Debian 12, Fedora 41 and CachyOS."
|
||||
fi
|
||||
|
||||
log_info "Setup starts in 10 seconds, to abort use Ctrl+C to exit NOW."
|
||||
echo ""
|
||||
sleep 10
|
||||
@@ -397,6 +419,11 @@ check_compatibility() {
|
||||
local distro
|
||||
distro=$(awk -F= '/^NAME/{print $2}' /etc/os-release | tr -d '"')
|
||||
|
||||
# Special handling for WSL
|
||||
if is_wsl; then
|
||||
log_info "Running in WSL environment."
|
||||
fi
|
||||
|
||||
case "$distro" in
|
||||
Fedora*)
|
||||
log_success "Detected Fedora. Proceeding with setup..."
|
||||
@@ -413,9 +440,11 @@ check_compatibility() {
|
||||
;;
|
||||
Debian*)
|
||||
log_success "Detected Debian. Proceeding with setup..."
|
||||
log_warning "Debian has known issues with ZFS kernel modules, you might need to manually install it to make ZFS work."
|
||||
log_warning "Continueing in 5 seconds..."
|
||||
sleep 5
|
||||
if ! is_wsl; then
|
||||
log_warning "Debian has known issues with ZFS kernel modules, you might need to manually install it to make ZFS work."
|
||||
log_warning "Continueing in 5 seconds..."
|
||||
sleep 5
|
||||
fi
|
||||
check_command_availibility "apt"
|
||||
;;
|
||||
Pop!_OS*)
|
||||
|
||||
Reference in New Issue
Block a user