feat: implement hybrid declarative state with automatic Nix sync
Some checks failed
Check / eval-and-lint (push) Has been cancelled
Some checks failed
Check / eval-and-lint (push) Has been cancelled
This commit is contained in:
@@ -22,4 +22,8 @@ esac
|
||||
hyprctl keyword misc:disable_scale_notification true
|
||||
hyprctl keyword monitor "$ACTIVE_MONITOR,${WIDTH}x${HEIGHT}@${REFRESH_RATE},auto,$NEW_SCALE"
|
||||
hyprctl keyword misc:disable_scale_notification false
|
||||
|
||||
# Persist the choice declaratively
|
||||
nomarchy-state-write "hyprland.scale" "$NEW_SCALE"
|
||||
|
||||
notify-send -u low " Display scaling set to ${NEW_SCALE}x"
|
||||
|
||||
@@ -25,7 +25,6 @@ else
|
||||
hyprctl keyword general:border_size 0
|
||||
fi
|
||||
|
||||
TMP_JSON=$(mktemp)
|
||||
jq --argjson state "$NEW_STATE" '.hyprland = $state' "$STATE_FILE" > "$TMP_JSON" && mv "$TMP_JSON" "$STATE_FILE"
|
||||
nomarchy-state-write hyprland "$NEW_STATE" --type json
|
||||
|
||||
echo "Toggled gaps to $NEW_STATE declaratively."
|
||||
|
||||
@@ -99,3 +99,11 @@ LOCK_FILE="${STATE_FILE}.lock"
|
||||
|
||||
# Clean up lock file
|
||||
rm -f "$LOCK_FILE"
|
||||
|
||||
# If we just updated the main home state file, sync it to the Nix configuration.
|
||||
# This bridges the gap between runtime UI changes and declarative Nix.
|
||||
if [[ "$STATE_FILE" == "$HOME/.config/nomarchy/state.json" ]]; then
|
||||
if command -v nomarchy-sync-nix-state >/dev/null 2>&1; then
|
||||
nomarchy-sync-nix-state
|
||||
fi
|
||||
fi
|
||||
|
||||
67
features/scripts/utils/nomarchy-sync-nix-state
Executable file
67
features/scripts/utils/nomarchy-sync-nix-state
Executable file
@@ -0,0 +1,67 @@
|
||||
#!/usr/bin/env bash
|
||||
set -e
|
||||
|
||||
# Nomarchy Nix State Sync
|
||||
# Bridges the gap between runtime UI changes (state.json) and declarative
|
||||
# Nix configuration (nomarchy-state.nix).
|
||||
|
||||
STATE_JSON="$HOME/.config/nomarchy/state.json"
|
||||
NIX_STATE_FILE="/etc/nixos/nomarchy-state.nix"
|
||||
|
||||
# If state.json is missing, nothing to sync
|
||||
if [ ! -f "$STATE_JSON" ]; then
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Determine destination.
|
||||
# If we are in the repo, we sync to ./nomarchy-state.nix (dev mode).
|
||||
# Otherwise, we sync to /etc/nixos/nomarchy-state.nix (real install).
|
||||
if [ -f "flake.nix" ] || [ -d ".git" ]; then
|
||||
DEST="./nomarchy-state.nix"
|
||||
elif [ -w "/etc/nixos" ]; then
|
||||
DEST="$NIX_STATE_FILE"
|
||||
else
|
||||
# Nowhere to sync to
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Generate the Nix attribute set from JSON.
|
||||
# We use jq to extract the keys and format them as Nix assignments.
|
||||
# Note: font in state.json maps to fonts.monospace in Nix.
|
||||
|
||||
{
|
||||
echo "# DO NOT EDIT MANUALLY - Managed by Nomarchy scripts."
|
||||
echo "# This file mirrors your UI choices (theme, font, etc.) into the declarative"
|
||||
echo "# Nix configuration. It is imported by your home.nix."
|
||||
echo "{"
|
||||
echo " nomarchy = {"
|
||||
|
||||
# Core UI strings
|
||||
echo " theme = \"$(jq -r '.theme // empty' "$STATE_JSON")\";"
|
||||
echo " fonts.monospace = \"$(jq -r '.font // empty' "$STATE_JSON")\";"
|
||||
echo " panelPosition = \"$(jq -r '.panelPosition // empty' "$STATE_JSON")\";"
|
||||
echo " wallpaper = \"$(jq -r '.wallpaper // empty' "$STATE_JSON")\";"
|
||||
|
||||
# Hyprland layout (numbers)
|
||||
echo " hyprland = {"
|
||||
echo " scale = \"$(jq -r '.hyprland.scale // "auto"' "$STATE_JSON")\";"
|
||||
echo " gaps_in = $(jq -r '.hyprland.gaps_in // 5' "$STATE_JSON");"
|
||||
echo " gaps_out = $(jq -r '.hyprland.gaps_out // 10' "$STATE_JSON");"
|
||||
echo " border_size = $(jq -r '.hyprland.border_size // 2' "$STATE_JSON");"
|
||||
echo " };"
|
||||
|
||||
# Toggles (booleans)
|
||||
echo " toggles = {"
|
||||
echo " suspend = $(jq -r '.suspend // true' "$STATE_JSON");"
|
||||
echo " screensaver = $(jq -r '.screensaver // true' "$STATE_JSON");"
|
||||
echo " idle = $(jq -r '.idle // true' "$STATE_JSON");"
|
||||
echo " nightlight = $(jq -r '.nightlight // false' "$STATE_JSON");"
|
||||
echo " waybar = $(jq -r '.waybar // true' "$STATE_JSON");"
|
||||
echo " };"
|
||||
|
||||
echo " };"
|
||||
echo "}"
|
||||
} > "$DEST.tmp"
|
||||
|
||||
# Final atomic move
|
||||
mv "$DEST.tmp" "$DEST"
|
||||
@@ -19,8 +19,7 @@ else
|
||||
notify-send -u low " Screensaver disabled"
|
||||
fi
|
||||
|
||||
TMP_JSON=$(mktemp)
|
||||
jq --argjson val "$NEW_VALUE" '.screensaver = $val' "$STATE_FILE" > "$TMP_JSON" && mv "$TMP_JSON" "$STATE_FILE"
|
||||
nomarchy-state-write screensaver "$NEW_VALUE" --type bool
|
||||
|
||||
echo "Screensaver state set to $NEW_VALUE. Updating environment..."
|
||||
|
||||
|
||||
@@ -22,7 +22,6 @@ else
|
||||
notify-send -u low " Top bar disabled"
|
||||
fi
|
||||
|
||||
TMP_JSON=$(mktemp)
|
||||
jq --argjson val "$NEW_VALUE" '.waybar = $val' "$STATE_FILE" > "$TMP_JSON" && mv "$TMP_JSON" "$STATE_FILE"
|
||||
nomarchy-state-write waybar "$NEW_VALUE" --type bool
|
||||
|
||||
echo "Waybar state set to $NEW_VALUE."
|
||||
|
||||
@@ -61,13 +61,10 @@ echo "Step 4: Choose your monitor scaling"
|
||||
echo "Recommended: 'auto' for most screens, '2' for 4K/HiDPI."
|
||||
SCALE=$(gum choose "auto" "1" "1.25" "1.5" "2")
|
||||
if [[ -n "$SCALE" ]]; then
|
||||
# Write to nested hyprland.scale key
|
||||
STATE_DIR="$HOME/.config/nomarchy"
|
||||
mkdir -p "$STATE_DIR"
|
||||
TMP_FILE=\$(mktemp)
|
||||
jq ".hyprland.scale = \"$SCALE\"" "\$STATE_FILE" > "\$TMP_FILE" && mv "\$TMP_FILE" "\$STATE_FILE"
|
||||
nomarchy-state-write "hyprland.scale" "$SCALE"
|
||||
fi
|
||||
|
||||
|
||||
# Skip system-modifying steps in the Live ISO environment
|
||||
if [[ "$USER" == "nixos" ]]; then
|
||||
echo ""
|
||||
|
||||
Reference in New Issue
Block a user