Compare commits

..

No commits in common. "master" and "WIP-router0-nfmnk-tunnels" have entirely different histories.

274 changed files with 7041 additions and 9207 deletions

6
.envrc
View file

@ -1,5 +1,5 @@
if ! has nix_direnv_version || ! nix_direnv_version 3.0.6; then
source_url "https://raw.githubusercontent.com/nix-community/nix-direnv/3.0.6/direnvrc" "sha256-RYcUJaRMf8oF5LznDrlCXbkOQrywm0HDv1VjYGaJGdM="
if ! has nix_direnv_version || ! nix_direnv_version 3.0.4; then
source_url "https://raw.githubusercontent.com/nix-community/nix-direnv/3.0.4/direnvrc" "sha256-DzlYZ33mWF/Gs8DDeyjr8mnVmQGx7ASYqA5WlxwvBG4="
fi
use flake .#develop
use_flake .#develop

5
.gitignore vendored
View file

@ -4,8 +4,3 @@
.env
**/result
.direnv/
# nixago: ignore-linked-files
/treefmt.toml
/debug-logs

10
.gitlab-ci.yml Normal file
View file

@ -0,0 +1,10 @@
stages:
- build
build:
stage: build
tags:
- nix
script:
# Test the nix-shell
- just run-with-channels 'nix-shell --run "echo OK"'

View file

@ -15,108 +15,106 @@ keys:
- &sj-vps-htz0 age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
- &sj-srv1 age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
- &srv0-dmz0 age13cyvxrd28j68f97q2dwsn62q5dy8tdxtq86ql2dxv2ncwfrf63dsmkj7n3
- &router0-dmz0 age1qju6ms625tlgcjwc9p447seu2p8gu0cr63e5gv5y0wx9mvgmre9slxzzs0
- &router0-ifog age1dktk5glcuu34u9t6kp3g2vqyj7dy0elray38t8n75mwa6l0s0vdst2cy00
- &router0-hosthatch age1v458x2q70yt0a6m6cq5ehemphtrzfzyhmeg3r872vsyyf65asgwstmqqk4
- &hstk0 age10xwq7a4y256yhv02j0u80te0vt4krgfjc68r0uw07t96z7ggmpwqtv38a0
- &router0-dmz0 age1k7cejd9tqz6a3expd63wkn7kmeawhhrp9vy5vevhjn6eavhdwywqeh7j86
- &router0-nfmnk age1x8fcjgaknfh5m2s4f0r2mjtfdjkuyj74y39jmh28k2pp5hmn25nschlra9
- &sj-bm-hostkey0 age1dw43sxtdxptzgyhsxhrj36x5gn7376gqk45t7wtyt3s97v7ux39sdmdd44
creation_rules:
- path_regex: ^(.+/|)secrets/[^/]+$
key_groups:
- pgp:
- *steveej
age:
- *steveej-t14
- *steveej-x13s
- *elias-e525
- *justyna-p300
- pgp:
- *steveej
age:
- *steveej-t14
- *steveej-x13s
- *elias-e525
- *justyna-p300
- *srv0-dmz0
- *router0-dmz0
- *srv0-dmz0
- *router0-dmz0
- *sj-vps-htz0
- *sj-srv1
- *hstk0
- *router0-ifog
- *router0-hosthatch
- *sj-vps-htz0
- *sj-srv1
- *sj-bm-hostkey0
- *router0-nfmnk
- path_regex: ^secrets/steveej-t14/.+$
key_groups:
- pgp:
- *steveej
age:
- *steveej-t14
- pgp:
- *steveej
age:
- *steveej-t14
- path_regex: ^secrets/desktop/.+$
key_groups:
- pgp:
- *steveej
age:
- *steveej-t14
- *steveej-x13s
- pgp:
- *steveej
age:
- *steveej-t14
- *steveej-x13s
- path_regex: ^secrets/servers/.+$
key_groups:
- pgp:
- *steveej
age:
- *sj-vps-htz0
- *sj-srv1
- pgp:
- *steveej
age:
- *sj-vps-htz0
- *sj-srv1
- path_regex: ^nix/os/containers/.+_secrets.+$
key_groups:
- pgp:
- *steveej
age:
- *sj-vps-htz0
- *sj-srv1
- pgp:
- *steveej
age:
- *sj-vps-htz0
- *sj-srv1
- path_regex: ^secrets/holochain-infra/.+$
key_groups:
- pgp:
- *steveej
age:
- *srv0-dmz0
- pgp:
- *steveej
age:
- *srv0-dmz0
- path_regex: ^secrets/router0-dmz0/.+$
key_groups:
- pgp:
- *steveej
age:
- *router0-dmz0
- path_regex: ^secrets/router0-ifog/.+$
- pgp:
- *steveej
age:
- *router0-dmz0
- path_regex: ^secrets/router0-nfmnk/.+$
key_groups:
- pgp:
- *steveej
age:
- *router0-ifog
- path_regex: ^secrets/router0-hosthatch/.+$
key_groups:
- pgp:
- *steveej
age:
- *router0-hosthatch
- pgp:
- *steveej
age:
- *router0-nfmnk
- path_regex: ^secrets/sj-vps-htz0/.+$
key_groups:
- pgp:
- *steveej
age:
- *sj-vps-htz0
- pgp:
- *steveej
age:
- *sj-vps-htz0
- path_regex: ^secrets/sj-srv1/.+$
key_groups:
- pgp:
- *steveej
age:
- *sj-srv1
- path_regex: ^secrets/hstk0/.+$
- pgp:
- *steveej
age:
- *sj-srv1
- path_regex: ^secrets/sj-bm-hostkey0/.+$
key_groups:
- pgp:
- *steveej
age:
- *hstk0
- pgp:
- *steveej
age:
- *sj-bm-hostkey0
- path_regex: ^secrets/steveej-x13s/.+$
key_groups:
- pgp:
- *steveej
age:
- *steveej-x13s
- pgp:
- *steveej
age:
- *steveej-x13s
- path_regex: ^secrets/work-holo/.+$
key_groups:
- pgp:
- *steveej
age:
- *steveej-x13s
- pgp:
- *steveej
age:
- *steveej-x13s
- *sj-bm-hostkey0
- path_regex: ^secrets/sj-bm-hostkey0/.+$
key_groups:
- pgp:
- *steveej
age:
- *sj-bm-hostkey0

22
.vscode/settings.json vendored
View file

@ -1,20 +1,6 @@
{
"editor.defaultFormatter": "ibecker.treefmt-vscode",
"editor.formatOnSave": true,
"nix.enableLanguageServer": true,
"nix.serverPath": "nil",
"nix.serverSettings": {
// settings for 'nil' LSP
"nil": {
"autoArchive": true,
"diagnostics": {
"ignored": ["unused_binding", "unused_with"]
},
"formatting": {
"command": ["treefmt", "--stdin", ".nil.nix"]
}
}
},
"treefmt.command": "treefmt",
"treefmt.config": ""
"nixEnvSelector.nixFile": "${workspaceRoot}/shell.nix",
"[nix]": {
"editor.defaultFormatter": "jnoortheen.nix-ide"
},
}

440
Justfile
View file

@ -2,320 +2,310 @@
# echo "{{invocation_directory()}}/nix/variables/versions.tmpl.nix"
_usage:
just -l
just -l
# Re-render the default versions
update-default-versions:
nix flake update
nix flake update
_get_nix_path versionsPath:
echo $(set -x; nix-build --no-link --show-trace {{ invocation_directory() }}/nix/default.nix -A channelSources --argstr versionsPath {{ versionsPath }})
echo $(set -x; nix-build --no-link --show-trace {{invocation_directory()}}/nix/default.nix -A channelSources --argstr versionsPath {{versionsPath}})
_device recipe dir +moreargs="":
#!/usr/bin/env bash
set -ex
unset NIX_PATH
source $(just -v _get_nix_path {{ invocation_directory() }}/{{ dir }}/versions.nix)
$(set -x; nix-build --no-link --show-trace $(dirname {{ dir }})/default.nix -A recipes.{{ recipe }} --argstr dir {{ dir }} {{ moreargs }})
#!/usr/bin/env bash
set -ex
unset NIX_PATH
source $(just -v _get_nix_path {{invocation_directory()}}/{{dir}}/versions.nix)
$(set -x; nix-build --no-link --show-trace $(dirname {{dir}})/default.nix -A recipes.{{recipe}} --argstr dir {{dir}} {{moreargs}})
_render_templates:
#!/usr/bin/env bash
set -ex
if ! ip route get 1.1.1.1; then
echo No route to WAN. Skipping template rendering...
else
source $(just -v _get_nix_path {{ invocation_directory() }}/nix/variables/versions.nix)
# nix/scripts/pre-eval-fixed.sh nix/home-manager/profiles/dotfiles/vcsh{.tmpl,}.nix
fi
#!/usr/bin/env bash
set -ex
if ! ip route get 1.1.1.1; then
echo No route to WAN. Skipping template rendering...
else
source $(just -v _get_nix_path {{invocation_directory()}}/nix/variables/versions.nix)
# nix/scripts/pre-eval-fixed.sh nix/home-manager/profiles/dotfiles/vcsh{.tmpl,}.nix
fi
rebuild-remote-device device +rebuildargs="dry-activate":
#!/usr/bin/env bash
set -ex
nix run .#colmena -- apply --impure --on {{ device }} {{ rebuildargs }}
#!/usr/bin/env bash
set -ex
nix run .#colmena -- apply --impure --on {{device}} {{rebuildargs}}
# Rebuild this device's NixOS
rebuild-this-device +rebuildargs="dry-activate":
nix run .#colmena -- apply-local --impure --sudo {{ rebuildargs }}
nix run .#colmena -- apply-local --impure --sudo {{rebuildargs}}
# Re-render the versions of a remote device and rebuild its environment
update-remote-device devicename +rebuildargs='build':
#!/usr/bin/env bash
set -e
#!/usr/bin/env bash
set -e
(
set -xe
cd nix/os/devices/{{ devicename }}
nix flake update
)
(
set -xe
cd nix/os/devices/{{devicename}}
nix flake update
)
just -v rebuild-remote-device {{ devicename }} {{ rebuildargs }}
just -v rebuild-remote-device {{devicename}} {{rebuildargs}}
git commit -v nix/os/devices/{{ devicename }}/flake.{nix,lock} -m "nix/os/devices/{{ devicename }}: bump versions"
git commit -v nix/os/devices/{{devicename}}/flake.{nix,lock} -m "nix/os/devices/{{devicename}}: bump versions"
# Re-render the versions of the current device and rebuild its environment
update-this-device rebuild-mode='switch' +moreargs='':
#!/usr/bin/env bash
set -e
#!/usr/bin/env bash
set -e
(
set -xe
cd nix/os/devices/$(hostname -s)
nix flake update
)
(
set -xe
cd nix/os/devices/$(hostname -s)
nix flake update
)
just -v rebuild-this-device {{ rebuild-mode }} {{ moreargs }}
just -v rebuild-this-device {{rebuild-mode}} {{moreargs}}
git commit -v nix/os/devices/$(hostname -s)/flake.{nix,lock} -m "nix/os/devices/$(hostname -s): bump versions"
git commit -v nix/os/devices/$(hostname -s)/flake.{nix,lock} -m "nix/os/devices/$(hostname -s): bump versions"
# Rebuild an offline system
rebuild-disk device:
#!/usr/bin/env bash
set -xe
#!/usr/bin/env bash
set -xe
just -v disk-mount {{ device }}
trap "set +e; just -v disk-umount {{ device }}" EXIT
just -v disk-install {{ device }}
just -v disk-mount {{device}}
trap "set +e; just -v disk-umount {{device}}" EXIT
just -v disk-install {{device}}
# Re-render the versions of the given offline system and reinstall it in offline-mode
update-disk dir:
#!/usr/bin/env bash
set -exuo pipefail
#!/usr/bin/env bash
set -exuo pipefail
dir={{ dir }}
dir={{dir}}
template={{ dir }}/versions.tmpl.nix
outfile={{ dir }}/versions.nix
template={{dir}}/versions.tmpl.nix
outfile={{dir}}/versions.nix
if ! test -e ${template}; then
template="$(just _DEFAULT_VERSION_TMPL)"
fi
if ! test -e ${template}; then
template="$(just _DEFAULT_VERSION_TMPL)"
fi
esh -o ${outfile} ${template}
if ! test "$(git diff ${outfile})"; then
echo Already on latest versions
exit 0
fi
esh -o ${outfile} ${template}
if ! test "$(git diff ${outfile})"; then
echo Already on latest versions
exit 0
fi
export SYSREBUILD_LOG=.{{ dir }}_sysrebuild.log
just -v rebuild-disk {{ dir }} || {
echo ERROR: Update of {{ dir }} failed, reverting ${outfile}...
exit 1
}
export SYSREBUILD_LOG=.{{dir}}_sysrebuild.log
just -v rebuild-disk {{dir}} || {
echo ERROR: Update of {{dir}} failed, reverting ${outfile}...
exit 1
}
git commit -v ${outfile} -m "${dir}: bump versions"
git commit -v ${outfile} -m "${dir}: bump versions"
# Iterate on a qtile config by running it inside Xephyr. (un-/grab the mouse with Ctrl + Shift-L)
hm-iterate-qtile:
#!/usr/bin/env bash
set -xe
home-manager switch || just -v rebuild-this-device switch
Xephyr -ac -br -resizeable :1 &
XEPHYR_PID=$!
echo ${XEPHYR_PID}
DISPLAY=:1 $(grep qtile ~/.xsession) &
echo "Xephyr started. un-/grab the mouse with Ctrl + Shift-L"
wait $!
kill ${XEPHYR_PID}
#!/usr/bin/env bash
set -xe
home-manager switch || just -v rebuild-this-device switch
Xephyr -ac -br -resizeable :1 &
XEPHYR_PID=$!
echo ${XEPHYR_PID}
DISPLAY=:1 $(grep qtile ~/.xsession) &
echo "Xephyr started. un-/grab the mouse with Ctrl + Shift-L"
wait $!
kill ${XEPHYR_PID}
# !!! DANGERIOUS !!! This wipes the disk which is configured for the given device.
disk-prepare dir:
just -v _device diskPrepare {{ dir }}
just -v _device diskPrepare {{dir}}
disk-relabel dir previous:
just -v _device diskRelabel {{ dir }} --argstr previousDiskId {{ previous }}
just -v _device diskRelabel {{dir}} --argstr previousDiskId {{previous}}
# Mount the target disk specified by device configuration directory. The 'dir' argument points to a device configuration, e.g. 'nix/os/devices/steveej-live-mmc-SL32G_0x259093f6'
disk-mount dir:
just -v _device diskMount {{ dir }}
just -v _device diskMount {{dir}}
# Unmount target disk, specified by device configuration directory
disk-umount dir:
just -v _device diskUmount {{ dir }}
just -v _device diskUmount {{dir}}
# Perform an offline installation on the mounted target disk, specified by device configuration directory
disk-install dir: _render_templates
just -v _device diskInstall {{ dir }}
just -v _device diskInstall {{dir}}
verify-n-unlock sshserver attempts="10":
#!/usr/bin/env bash
set -e
env \
GETPW="just _get_pass_entry Infrastructure/VPS/{{ sshserver }} DRIVE_PW" \
SSHOPTS="$(just _get_pass_entry Infrastructure/VPS/{{ sshserver }} SSHOPTS)" \
VNCSOCK="$(just _get_pass_entry Infrastructure/VPS/{{ sshserver }} VNCSOCK)" \
VNCPW="$(just _get_pass_entry Infrastructure/VPS/{{ sshserver }} VNCPW)" \
\
just _verify-n-unlock {{ sshserver }} {{ attempts }}
#!/usr/bin/env bash
set -e
env \
GETPW="just _get_pass_entry Infrastructure/VPS/{{sshserver}} DRIVE_PW" \
SSHOPTS="$(just _get_pass_entry Infrastructure/VPS/{{sshserver}} SSHOPTS)" \
VNCSOCK="$(just _get_pass_entry Infrastructure/VPS/{{sshserver}} VNCSOCK)" \
VNCPW="$(just _get_pass_entry Infrastructure/VPS/{{sshserver}} VNCPW)" \
\
just _verify-n-unlock {{sshserver}} {{attempts}}
_verify-n-unlock sshserver attempts:
#!/usr/bin/env bash
set -e
: ${VNCSOCK:?VNCSOCK must be set}
: ${VNCPW:?VNCPW must be set}
#!/usr/bin/env bash
set -e
: ${VNCSOCK:?VNCSOCK must be set}
: ${VNCPW:?VNCPW must be set}
export MAGICK_ARGS="-filter Catrom -density 72 -resample 300 -contrast -normalize -despeckle -type grayscale -sharpen 1 -posterize 3 -negate -gamma 100 -blur 1x65535"
export TESS_ARGS="-c debug_file=/dev/null --psm 4"
export MAGICK_ARGS="-filter Catrom -density 72 -resample 300 -contrast -normalize -despeckle -type grayscale -sharpen 1 -posterize 3 -negate -gamma 100 -blur 1x65535"
export TESS_ARGS="-c debug_file=/dev/null --psm 4"
function send() {
local what="${1:?need something to send}"
ssh -4 ${SSHOPTS:?need sshopts} root@{{ sshserver }} "echo -e ${what}>> /dev/tty0" &>/dev/null
}
function send() {
local what="${1:?need something to send}"
ssh -4 ${SSHOPTS:?need sshopts} root@{{sshserver}} "echo -e ${what}>> /dev/tty0" &>/dev/null
}
function expect() {
local what="${1:?need something to expect}"
vncdo --server=${VNCSOCK} --password=${VNCPW} --disable-desktop-resizing --nocursor capture $PWD/screenshot.bmp
convert ${MAGICK_ARGS} screenshot.bmp screenshot.tiff
tesseract ${TESS_ARGS} screenshot.tiff screenshot
grep --quiet "${what}" screenshot.txt
}
function expect() {
local what="${1:?need something to expect}"
vncdo --server=${VNCSOCK} --password=${VNCPW} --disable-desktop-resizing --nocursor capture $PWD/screenshot.bmp
convert ${MAGICK_ARGS} screenshot.bmp screenshot.tiff
tesseract ${TESS_ARGS} screenshot.tiff screenshot
grep --quiet "${what}" screenshot.txt
}
function send_and_expect() {
local send="${1:?need something to send}"
local expect="${2:?need something to expect}"
if ! send "${send}"; then
echo warning: cannot send > /dev/stderr
return -1
fi
expect "${expect}"
}
function send_and_expect() {
local send="${1:?need something to send}"
local expect="${2:?need something to expect}"
if ! send "${send}"; then
echo warning: cannot send > /dev/stderr
return -1
fi
expect "${expect}"
}
trap 'E=$?; set +e; rm screenshot.*; echo Exiting...; kill $(jobs -p | cut -d " " -f 4); exit $E' EXIT
trap 'E=$?; set +e; rm screenshot.*; echo Exiting...; kill $(jobs -p | cut -d " " -f 4); exit $E' EXIT
for i in `seq 1 {{ attempts }}`; do
echo Attempt $i...
expect="$(pwgen -0 12)"
send="'\0033\0143'${expect}"
if send_and_expect "${send}" "${expect}"; then
pipe=$(mktemp -u)
mkfifo ${pipe}
exec 3<>${pipe}
rm ${pipe}
for i in `seq 1 {{attempts}}`; do
echo Attempt $i...
expect="$(pwgen -0 12)"
send="'\0033\0143'${expect}"
if send_and_expect "${send}" "${expect}"; then
pipe=$(mktemp -u)
mkfifo ${pipe}
exec 3<>${pipe}
rm ${pipe}
echo Verification succeeded at attempt $i. Unlocking remote drive...
ssh -4 ${SSHOPTS} root@{{ sshserver }} "cryptsetup-askpass" <&3 &>/dev/null &
eval ${GETPW} | head -n1 >&3
echo Verification succeeded at attempt $i. Unlocking remote drive...
ssh -4 ${SSHOPTS} root@{{sshserver}} "cryptsetup-askpass" <&3 &>/dev/null &
eval ${GETPW} | head -n1 >&3
for j in `seq 1 120`; do
sleep 0.5
if expect '— success'; then
echo Unlock successful.
exit 0
fi
done
for j in `seq 1 120`; do
sleep 0.5
if expect '— success'; then
echo Unlock successful.
exit 0
fi
done
echo Unlock failed...
exit 1
fi
done
echo Verification failed {{ attempts }} times. Giving up...
exit 1
echo Unlock failed...
exit 1
fi
done
echo Verification failed {{attempts}} times. Giving up...
exit 1
_get_pass_entry path key:
pass show {{ path }}| grep -E "^{{ key }}:" | sed -E 's/^[^:]+: *//g'
pass show {{path}}| grep -E "^{{key}}:" | sed -E 's/^[^:]+: *//g'
run-with-channels +cmds:
#!/usr/bin/env bash
source $(just -v _get_nix_path {{ invocation_directory() }}/nix/variables/versions.nix)
{{ cmds }}
#!/usr/bin/env bash
source $(just -v _get_nix_path {{invocation_directory()}}/nix/variables/versions.nix)
{{cmds}}
install-config config root:
sudo just run-with-channels nixos-install -I nixos-config={{ invocation_directory() }}/{{ config }} --root {{ root }} --no-root-passwd
sudo just run-with-channels nixos-install -I nixos-config={{invocation_directory()}}/{{config}} --root {{root}} --no-root-passwd
# Switch between gpg-card capable devices which have a copy of the same key
switch-gpg-card key-id="6EEFA706CB17E89B":
#!/usr/bin/env bash
#
# Derived from https://github.com/drduh/YubiKey-Guide/issues/19.
#
# Connect the new device and then run this script to make it known to gnupg.
#
set -xe
if [[ -n "{{key-id}}" ]]; then
KEY_ID="{{key-id}}"
else
KEY_ID=$(gpg --card-status | rg sec | rg -o '[0-9A-Z]{16}')
fi
switch-gpg-card:
#!/usr/bin/env bash
#
# Derived from https://github.com/drduh/YubiKey-Guide/issues/19.
#
# Connect the new device and then run this script to make it known to gnupg.
#
set -xe
KEY_ID=$(gpg --card-status | rg sec | rg -o '[0-9A-Z]{16}')
# export pubkey and ownertrust
gpg2 --output "${KEY_ID}".pubkey --export "${KEY_ID}"
# if this fails the trust in the key is missing and can be fixed with `gpg --edit-key ${KEY_ID}`
gpg2 --export-ownertrust | rg "${KEY_ID}" > "${KEY_ID}".ownertrust
# export pubkey and ownertrust
gpg2 --output "${KEY_ID}".pubkey --export "${KEY_ID}"
# if this fails the trust in the key is missing and can be fixed with `gpg --edit-key ${KEY_ID}`
gpg2 --export-ownertrust | rg "${KEY_ID}" > "${KEY_ID}".ownertrust
# delete the key
gpg --yes --delete-secret-and-public-keys "${KEY_ID}"
# delete the key
gpg --yes --delete-secret-and-public-keys "${KEY_ID}"
# import pubkey and ownertrust back and cleanup
gpg2 --import "${KEY_ID}".pubkey
gpg2 --import-ownertrust < "${KEY_ID}".ownertrust
rm "${KEY_ID}".{pubkey,ownertrust}
# import pubkey and ownertrust back and cleanup
gpg2 --import "${KEY_ID}".pubkey
gpg2 --import-ownertrust < "${KEY_ID}".ownertrust
rm "${KEY_ID}".{pubkey,ownertrust}
# refresh the gpg agent
gpg-connect-agent "scd serialno" "learn --force" /bye
gpg --card-status
# refresh the gpg agent
gpg-connect-agent "scd serialno" "learn --force" /bye
gpg --card-status
# Connect to `remote` UUID, and turn it into a short name
uuid-to-device-name remote:
#!/usr/bin/env bash
set -e -o pipefail
ssh {{ remote }} 'nix run nixpkgs.dmidecode -c dmidecode -s system-uuid' | xxhsum --quiet -H1 | awk '{print $1}'
#!/usr/bin/env bash
set -e -o pipefail
ssh {{remote}} 'nix run nixpkgs.dmidecode -c dmidecode -s system-uuid' | xxhsum --quiet -H1 | awk '{print $1}'
test-connection:
#! /usr/bin/env nix-shell
#! nix-shell -p curl zsh
#! nix-shell -i zsh
#! nix-shell --pure
#! /usr/bin/env nix-shell
#! nix-shell -p curl zsh
#! nix-shell -i zsh
#! nix-shell --pure
while true; do
FAILURE="false"
output=$(
echo "$(date)\n---"
for url in \
"https://172.16.0.1:65443/0.7/gui/#/login/" \
"https://192.168.0.1" \
"http://172.172.171.9" \
"https://172.172.171.10:65443" \
"https://172.172.171.11:65443" \
"https://172.172.171.13:443" \
"https://172.172.171.14:443" \
"http://172.172.171.15:22" \
"http://172.172.171.16:22" \
"https://crates.io" \
"https://holo.host" \
; \
do
print "trying ${url}": $(
curl_output=$(curl --http0.9 -k --head --connect-timeout 0.5 ${url} 2>&1)
# if [ $? -ne 0 ]; then
if [[ "$curl_output" == *timeout* ]]; then
echo failure: $(echo ${curl_output} | tail -n1)
# BUG: outer FAILURE is not set by this
FAILURE="true"
else
echo success
fi
)
done
)
clear
echo ${output}
while true; do
FAILURE="false"
output=$(
echo "$(date)\n---"
for url in \
"https://172.16.0.1:65443/0.7/gui/#/login/" \
"https://192.168.0.1" \
"http://172.172.171.9" \
"https://172.172.171.10:65443" \
"https://172.172.171.11:65443" \
"https://172.172.171.13:443" \
"https://172.172.171.14:443" \
"http://172.172.171.15:22" \
"http://172.172.171.16:22" \
"https://crates.io" \
"https://holo.host" \
; \
do
print "trying ${url}": $(
curl_output=$(curl --http0.9 -k --head --connect-timeout 0.5 ${url} 2>&1)
# if [ $? -ne 0 ]; then
if [[ "$curl_output" == *timeout* ]]; then
echo failure: $(echo ${curl_output} | tail -n1)
# BUG: outer FAILURE is not set by this
FAILURE="true"
else
echo success
fi
)
done
)
clear
echo ${output}
if [[ ${FAILURE} == "true" ]]; then
echo something failed
tracepath -m5 -n1 172.16.0.1
tracepath -m5 -n1 192.168.0.1
fi
if [[ ${FAILURE} == "true" ]]; then
echo something failed
tracepath -m5 -n1 172.16.0.1
tracepath -m5 -n1 192.168.0.1
fi
sleep 5
done
sleep 5
done
cachix-use name:
nix run nixpkgs/nixos-unstable#cachix -- use {{ name }} -m nixos -d nix/os/
nix run nixpkgs/nixos-unstable#cachix -- use {{name}} -m nixos -d nix/os/
update-sops-keys:
for file in $(egrep -lr '"?sops"?:') secrets; do sops updatekeys -y $file; done
deploy-router0-dmz0:
NIX_SSHOPTS="-o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null -o CheckHostIP=no" nixos-rebuild switch --impure --flake .\#router0-dmz0 --target-host root@192.168.20.1
ttyusb:
screen -fa /dev/ttyUSB0 115200
for file in $(egrep -lr '"?sops"?:') secrets; do sops updatekeys -y $file; done

View file

@ -1,5 +1,4 @@
# steveej's infra
This repository helps me to manage all computer infrastructure.
This is mostly achieved with the help of [Nix](https://nixos.org).
@ -20,7 +19,7 @@ In the unlikely case that you actually read this and have any questions please d
- [ ] development environments
- [x] (Semi-) automatic synchronization of important repositories
- [x] Modification strategy
The approach is to use vcsh for the dotfiles
The approach is to use vcsh for the dotfiles
- [x] dotfiles
- [x] Toplevel Justfile for simple actions
- [x] mount/umount disks
@ -40,46 +39,39 @@ In the unlikely case that you actually read this and have any questions please d
- [x] sj-pve0
- [x] use an existing secret management framework
- [x] adapt (or abandon?) _just_ recipes
- [x] `rebuild-this-device`
- [x] `update-this-device`
- [x] `rebuild-remote-device`
- [x] `update-remote-device`
- [x] `rebuild-this-device`
- [x] `update-this-device`
- [x] `rebuild-remote-device`
- [x] `update-remote-device`
evaluate, and understand a path to using these tools in a pull-based fashion:
evaluate, and understand a path to using these tools in a pull-based fashion:
- [x] [colmena](https://github.com/zhaofengli/colmena)
- bootstrapping: https://github.com/zhaofengli/colmena/issues/68
* bootstrapping: https://github.com/zhaofengli/colmena/issues/68
- [ ] deploy-rs
- [x] 🚧 find a better alternative for the qtile-desktop
current issues:
- floating windows often get lost in the background
- plugging in-/out- screen crashes the desktop
evaluate:
- [x] ~~🚧 gnome3 + pop-shell~~
- [x] ~~leftwm + eww (+ wayland?)~~
current issues:
- floating windows often get lost in the background
- plugging in-/out- screen crashes the desktop
evaluate:
- [x] ~~🚧 gnome3 + pop-shell~~
- [x] ~~leftwm + eww (+ wayland?)~~
- [ ] (Re-)document bootstrap process
- [ ] `apt install sudo cryptsetup` as a requirements on a deb admin machine
- [ ] a new machine
- [ ] an install media
- [ ] Design disaster recovery
- [ ] Automatic synchronization of other state files - see https://gitlab.com/steveeJ/nix-expressions/issues/2
- [ ] Recycle _\_archived_
- [ ] Recycle *\_archived*
- [ ] container migrations
- [ ] ensure DDNS is updated _before_ the containers are started
## Bugs
## Bugs
- [ ] home-manager leaves ~/.gnupg at 0755
## Usage
_(These are reminders for my future self)_
*(These are reminders for my future self)*
```
just --list
@ -88,17 +80,15 @@ just --list
## Bootstrap
### A new machine
* ensure the dotfiles repo has a branch with the new machine's hostname
- ensure the dotfiles repo has a branch with the new machine's hostname
- boot with an install media and go through setup
* boot with an install media and go through setup
#### Post-Install Setup
- `chmod --recursive g-rwx,o-rwx ~/.gnupg`
- `gpg2 --edit-card; fetch`
- clone password-manager and infra repositories
- gpg2: ultimately trust my own key
* `chmod --recursive g-rwx,o-rwx ~/.gnupg`
* `gpg2 --edit-card; fetch`
* clone password-manager and infra repositories
* gpg2: ultimately trust my own key
## Swapping out a disk

View file

@ -4,9 +4,6 @@
# Having pkgs default to <nixpkgs> is fine though, and it lets you use short
# commands such as:
# nix-build -A mypackage
{
pkgs ? import <nixpkgs> { },
}:
{
pkgs = import ./nix/pkgs { inherit pkgs; };
{pkgs ? import <nixpkgs> {}}: {
pkgs = import ./nix/pkgs {inherit pkgs;};
}

1066
flake.lock generated

File diff suppressed because it is too large Load diff

605
flake.nix
View file

@ -1,18 +1,18 @@
# flake.nix
{
inputs = {
# TODO: where has this been used?
# dotfiles = {
# url = "git+https://forgejo.www.stefanjunker.de/steveej/dotfiles.git";
# flake = false;
# };
dotfiles = {
url = "gitlab:steveeJ/dotfiles";
flake = false;
};
# flake and infra basics
nixpkgs-2211.url = "github:nixos/nixpkgs/nixos-22.11";
radicalePkgs.follows = "nixpkgs-2211";
nixpkgs-2411.url = "github:nixos/nixpkgs/nixos-24.11";
nixpkgs-2305.url = "github:nixos/nixpkgs/nixos-23.05";
nixpkgs-2311.url = "github:nixos/nixpkgs/nixos-23.11";
nixpkgs-unstable.url = "github:nixos/nixpkgs/nixos-unstable";
nixpkgs.follows = "nixpkgs-2411";
nixpkgs.follows = "nixpkgs-2311";
flake-parts.url = "github:hercules-ci/flake-parts";
get-flake.url = "github:ursi/get-flake";
@ -41,13 +41,14 @@
url = "github:nix-community/fenix";
inputs.nixpkgs.follows = "nixpkgs";
};
crane.url = "github:ipetkov/crane";
sops-nix = {
url = "github:Mic92/sops-nix";
crane = {
url = "github:ipetkov/crane";
inputs.nixpkgs.follows = "nixpkgs";
};
sops-nix.url = "github:Mic92/sops-nix";
sops-nix.inputs.nixpkgs.follows = "nixpkgs";
# applications
aphorme_launcher = {
url = "github:Iaphetes/aphorme_launcher/main";
@ -70,9 +71,13 @@
flake = false;
};
salut = {
url = "gitlab:snakedye/salut";
flake = false;
};
prs = {
# url = "gitlab:timvisee/prs/v0.5.2";
url = "gitlab:timvisee/prs/07f17a93d19fb6bc92c9c7f3ae3f5cc750b1f973";
url = "gitlab:timvisee/prs/master";
flake = false;
};
@ -81,348 +86,266 @@
flake = false;
};
# nixpkgs-logseq.url = "github:steveej-forks/nixpkgs/logseq-linux-arm64-selfbuilt-appimage";
### inputs for thinkpad x13s
# see https://github.com/jhovold/linux/wiki/X13s for status updates
linux_x13s.url = "github:jhovold/linux/wip/sc8280xp-v6.7";
linux_x13s.flake = false;
brainwart_x13s-nixos = {
url = "github:BrainWart/x13s-nixos/flake";
flake = false;
};
adamcstephens_stop-export = {
flake = false;
url = "git+https://codeberg.org/adamcstephens/stop-export.git";
};
# alsa-ucm-conf = {
# flake = false;
# url = "github:alsa-project/alsa-ucm-conf/master";
# };
logseq_0_10_5_aarch64_appimage = {
flake = false;
url = "https://www.stefanjunker.de/downloads/Logseq-0.10.5.AppImage";
};
espanso = {
flake = false;
url = "github:espanso/espanso/db97658d1d80697a635b57801696c594eacf057b";
};
nix4vscode = {
url = "github:nix-community/nix4vscode";
# inputs.nixpkgs.follows = "nixpkgs";
};
nixvim = {
# TODO: pin to nixos-24.11 once available
url = "github:nix-community/nixvim";
inputs.nixpkgs.follows = "nixpkgs";
};
treefmt-nix = {
url = "github:numtide/treefmt-nix";
inputs.nixpkgs.follows = "nixpkgs";
};
nixago = {
url = "github:jmgilman/nixago";
inputs.nixpkgs.follows = "nixpkgs";
};
nur = {
url = "github:nix-community/NUR";
inputs.nixpkgs.follows = "nixpkgs";
};
nixpkgs-gimp.url = "github:jtojnar/nixpkgs/gimp-meson";
};
outputs =
inputs@{
self,
flake-parts,
nixpkgs,
...
}:
let
inherit (nixpkgs) lib;
outputs = inputs @ {
self,
flake-parts,
nixpkgs,
...
}: let
inherit (nixpkgs) lib;
systems = [
"x86_64-linux"
"aarch64-linux"
];
in
flake-parts.lib.mkFlake { inherit inputs; } (
{ withSystem, ... }:
{
flake.colmena =
lib.lists.foldl (sum: cur: lib.attrsets.recursiveUpdate sum cur)
{ meta.nixpkgs = import inputs.nixpkgs.outPath { system = builtins.elemAt systems 0; }; }
# FIXME: this doesn't seem to work to apply overlays into a node's nixpkgs import
# try this instead: https://github.com/zhaofengli/colmena/issues/60#issuecomment-1510496861
systems = [
"x86_64-linux"
"aarch64-linux"
];
in
flake-parts.lib.mkFlake {inherit inputs;}
({withSystem, ...}: {
flake.colmena =
lib.lists.foldl (sum: cur: lib.attrsets.recursiveUpdate sum cur)
{
meta.nixpkgs = import inputs.nixpkgs.outPath {
system = builtins.elemAt systems 0;
};
}
# FIXME: this doesn't seem to work to apply overlays into a node's nixpkgs import
# try this instead: https://github.com/zhaofengli/colmena/issues/60#issuecomment-1510496861
(builtins.map
(nodeName:
import ./nix/os/devices/${nodeName} {
inherit nodeName;
repoFlake = self;
repoFlakeWithSystem = withSystem;
nodeFlake = self.inputs.get-flake ./nix/os/devices/${nodeName};
}) [
"steveej-t14"
"steveej-x13s"
"steveej-x13s-rmvbl"
# "elias-e525"
# "justyna-p300"
# "srv0-dmz0"
# # "router0-dmz0"
"router0-nfmnk"
"sj-srv1"
"sj-bm-hostkey0"
# "retro"
]);
# this makes nixos-anywhere work
flake.nixosConfigurations = let
colmenaHive = (inputs.colmena.lib.makeHive self.outputs.colmena).nodes;
router0-dmz0 = (inputs.get-flake ./nix/os/devices/router0-dmz0).nixosConfigurations;
retro = (inputs.get-flake ./nix/os/devices/retro).nixosConfigurations;
in (
colmenaHive
// {
router0-dmz0 = router0-dmz0.native;
# for now deploy directly with:
# nixos-rebuild switch --flake .\#router0-dmz0_cross --build-host localhost --target-host root@192.168.10.1
router0-dmz0_cross = router0-dmz0.cross;
# nixos-install --flake .\#retro_cross
retro_cross = retro.cross;
steveej-x13s_cross = (inputs.get-flake ./nix/os/devices/steveej-x13s).nixosConfigurations.cross;
steveej-x13s-rmvbl_cross = (inputs.get-flake ./nix/os/devices/steveej-x13s-rmvbl).nixosConfigurations.cross;
}
);
inherit systems;
perSystem = {
self',
inputs',
system,
config,
lib,
pkgs,
...
}: {
imports = [
./nix/modules/flake-parts/perSystem/default.nix
];
packages = let
dcpj4110dw = pkgs.callPackage (self + /nix/pkgs/dcpj4110dw) {};
craneLib =
inputs.crane.lib.${system}.overrideToolchain
inputs'.fenix.packages.stable.toolchain;
craneLibOfiPass =
inputs.crane.lib.${system}.overrideToolchain
(
builtins.map
(
nodeName:
import ./nix/os/devices/${nodeName} {
inherit nodeName;
repoFlake = self;
repoFlakeWithSystem = withSystem;
nodeFlake = self.inputs.get-flake (self + "/nix/os/devices/${nodeName}");
}
)
[
"steveej-t14"
"steveej-x13s"
"steveej-x13s-rmvbl"
# "elias-e525"
# "justyna-p300"
# "srv0-dmz0"
# "router0-dmz0"
"router0-ifog"
"router0-hosthatch"
"sj-srv1"
]
inputs'.fenix.packages.stable.toolchain
# .override {
# date = "1.60.0";
# }
);
in {
dcpj4110dwDriver = dcpj4110dw.driver;
dcpj4110dwCupswrapper = dcpj4110dw.cupswrapper;
flake.lib = {
inherit withSystem;
# broken as of 2023-04-27 because it doesn't load without a config
# aphorme_launcher = craneLib.buildPackage {src = inputs.aphorme_launcher;};
# yofi = inputs'.yofi.packages.default;
# ofi-pass = craneLibOfiPass.buildPackage {src = inputs.ofi-pass;};
inherit (inputs'.colmena.packages) colmena;
# jay = pkgs.callPackage (self + /nix/pkgs/jay.nix) {
# src = inputs.jay;
# rustPlatform = pkgs.makeRustPlatform {
# cargo = inputs'.fenix.packages.stable.toolchain;
# rustc = inputs'.fenix.packages.stable.toolchain;
# };
# };
salut = craneLib.buildPackage {
src = inputs.salut;
nativeBuildInputs = [
pkgs.pkg-config
];
buildInputs = [
pkgs.libxkbcommon
pkgs.fontconfig
];
};
prs =
pkgs.callPackage
({
pkgs,
dbus,
glib,
gpgme,
gtk3,
libxcb,
libxkbcommon,
installShellFiles,
pkg-config,
python3,
}:
craneLib.buildPackage {
pname = "prs";
version = inputs.prs.shortRev;
src = inputs.prs;
nativeBuildInputs = [gpgme installShellFiles pkg-config python3];
buildInputs = [
dbus
glib
gpgme
gtk3
libxcb
libxkbcommon
];
cargoExtraArgs = "--features backend-gpgme";
postInstall = ''
for shell in bash fish zsh; do
installShellCompletion --cmd prs --$shell <($out/bin/prs internal completions $shell --stdout)
done
'';
})
{};
nomad = inputs'.nixpkgs-unstable.legacyPackages.nomad_1_6;
ledger-live-desktop-wrapped = pkgs.writeShellScriptBin "ledger-live-desktop-wrapped" ''
set -x
pkill -9 wayland-proxy-v
export NIXOS_OZONE_WL=""
${pkgs.wayland-proxy-virtwl}/bin/wayland-proxy-virtwl \
--wayland-display=wayland-3 \
--xwayland-binary=${pkgs.xwayland}/bin/Xwayland \
--x-display=3 \
&
# --x-unscale=3 \
#--verbose \
export PROXYPID="$!"
trap "kill -9 \$PROXYPID" EXIT
# trap "pkill -9 wayland-proxy-v" EXIT
env \
WAYLAND_DISPLAY=wayland-3 \
DISPLAY=:3 \
ledger-live-desktop
'';
syncthing-container-webui = pkgs.writeShellScriptBin "reverse-port-forward-syncthing-container" ''
ssh root@${self.colmena.sj-vps-htz0.deployment.targetHost} -L 8385:syncthing.containers:8384
'';
logseq =
pkgs.callPackage ./nix/pkgs/logseq
(lib.attrsets.optionalAttrs pkgs.stdenv.isAarch64 {
overrideSrc = self.inputs.logseq_0_10_5_aarch64_appimage;
});
rperf = craneLib.buildPackage {
src = inputs.rperf;
nativeBuildInputs = [
pkgs.pkg-config
];
buildInputs = [
];
};
};
# this makes nixos-anywhere work
flake.nixosConfigurations =
let
colmenaHive = (inputs.colmena.lib.makeHive self.outputs.colmena).nodes;
router0-dmz0 = (inputs.get-flake (self + "/nix/os/devices/router0-dmz0")).nixosConfigurations;
in
colmenaHive
// {
router0-dmz0 = router0-dmz0.native;
formatter = pkgs.alejandra;
# for now deploy directly with:
# nixos-rebuild switch --flake .\#router0-dmz0_cross --build-host localhost --target-host root@192.168.10.1
router0-dmz0_cross = router0-dmz0.cross;
steveej-x13s_cross =
(inputs.get-flake (self + "./nix/os/devices/steveej-x13s")).nixosConfigurations.cross;
steveej-x13s-rmvbl_cross =
(inputs.get-flake ./nix/os/devices/steveej-x13s-rmvbl).nixosConfigurations.cross;
devShells = let
all = import ./nix/devShells.nix {
inherit
self'
inputs'
pkgs
;
};
in (all // {default = all.develop;});
};
inherit systems;
perSystem =
{
self',
inputs',
system,
config,
lib,
pkgs,
...
}:
{
imports = [ ./nix/modules/flake-parts/perSystem/default.nix ];
packages =
let
dcpj4110dw = pkgs.callPackage (self + /nix/pkgs/dcpj4110dw) { };
craneLibFn = (inputs.crane.mkLib inputs.nixpkgs.legacyPackages.${system}).overrideToolchain;
craneLib = craneLibFn inputs'.fenix.packages.stable.toolchain;
_prsPackage =
{
lib,
rustPlatform,
installShellFiles,
pkg-config,
python3,
glib,
gpgme,
gtk3,
stdenv,
cargoHash ? "sha256-T57RqIzurpYLHyeFhvqxmC+DoB6zUf+iTu1YkMmwtp8=",
src,
version,
makeWrapper,
skim,
}:
rustPlatform.buildRustPackage rec {
pname = "prs";
inherit src version cargoHash;
nativeBuildInputs = [
gpgme
installShellFiles
pkg-config
python3
makeWrapper
];
cargoBuildFlags = [
"--no-default-features"
"--features=alias,backend-gpgme,clipboard,notify,select-fzf-bin,select-skim-bin,tomb,totp"
];
buildInputs = [
glib
gpgme
gtk3
];
postInstall = lib.optionalString (stdenv.buildPlatform.canExecute stdenv.hostPlatform) ''
for shell in bash fish zsh; do
installShellCompletion --cmd prs --$shell <($out/bin/prs internal completions $shell --stdout)
done
'';
postFixup = ''
wrapProgram $out/bin/prs \
--prefix PATH : ${lib.makeBinPath [ skim ]}
'';
meta = with lib; {
description = "Secure, fast & convenient password manager CLI using GPG and git to sync";
homepage = "https://gitlab.com/timvisee/prs";
changelog = "https://gitlab.com/timvisee/prs/-/blob/v${version}/CHANGELOG.md";
license = with licenses; [
lgpl3Only # lib
gpl3Only # everything else
];
maintainers = with maintainers; [ dotlambda ];
mainProgram = "prs";
};
};
local-xwayland = pkgs.writeShellScriptBin "local-xwayland" ''
set -x
${pkgs.wayland-proxy-virtwl}/bin/wayland-proxy-virtwl \
--wayland-display=wayland-3 \
--xwayland-binary=${pkgs.xwayland}/bin/Xwayland \
--x-display=0 \
# --x-unscale=3 \
--verbose
'';
in
{
dcpj4110dwDriver = dcpj4110dw.driver;
dcpj4110dwCupswrapper = dcpj4110dw.cupswrapper;
inherit (inputs'.colmena.packages) colmena;
prs = pkgs.callPackage _prsPackage {
src = inputs.prs;
version = inputs.prs.shortRev;
cargoHash = "sha256-oXuAKOHIfwUvcS0qXDTe68DN+MUNS4TAKV986vxdeh8=";
};
nomad = inputs'.nixpkgs-unstable.legacyPackages.nomad_1_6;
ledger-live-desktop-wrapped = pkgs.writeShellScriptBin "ledger-live-desktop-wrapped" ''
set -x
pkill -9 wayland-proxy-v
export NIXOS_OZONE_WL=""
${pkgs.wayland-proxy-virtwl}/bin/wayland-proxy-virtwl \
--wayland-display=wayland-3 \
--xwayland-binary=${pkgs.xwayland}/bin/Xwayland \
--x-display=3 \
&
# --x-unscale=3 \
#--verbose \
export PROXYPID="$!"
trap "kill -9 \$PROXYPID" EXIT
# trap "pkill -9 wayland-proxy-v" EXIT
env \
WAYLAND_DISPLAY=wayland-3 \
DISPLAY=:3 \
ledger-live-desktop
'';
syncthing-container-webui = pkgs.writeShellScriptBin "reverse-port-forward-syncthing-container" ''
ssh root@${self.colmena.sj-vps-htz0.deployment.targetHost} -L 8385:syncthing.containers:8384
'';
rperf = craneLib.buildPackage {
src = inputs.rperf;
nativeBuildInputs = [ pkgs.pkg-config ];
buildInputs = [ ];
};
inherit local-xwayland;
inherit (inputs'.nixpkgs-gimp.legacyPackages) gimp;
};
formatter =
let
settingsNix = {
projectRootFile = ".git/config";
package = inputs'.nixpkgs-unstable.legacyPackages.treefmt2;
programs = {
nixfmt.enable = true;
deadnix.enable = true;
statix.enable = true;
shfmt.enable = true;
shellcheck.enable = true;
prettier.enable = true;
just = {
enable = true;
includes = [
"*/Justfile"
"Justfile"
];
};
} // pkgs.lib.optionalAttrs (pkgs.system != "riscv64-linux") { shellcheck.enable = true; };
settings = {
global.excludes = [
"LICENSE"
"secrets/"
".git-crypt/"
# unsupported extensions
"*.{enc,gif,png,svg,tape,mts,lock,mod,sum,toml,env,envrc,gitignore}"
];
formatter = {
deadnix = {
priority = 1;
options = [ "--no-underscore" ];
};
nixfmt = {
priority = 2;
};
statix = {
priority = 3;
};
prettier = {
options = [
"--tab-width"
"2"
];
includes = [ "*.{css,html,js,json,jsx,md,mdx,scss,ts,yaml}" ];
};
};
};
};
eval = inputs.treefmt-nix.lib.evalModule pkgs settingsNix;
in
eval.config.build.wrapper.overrideAttrs (_: {
passthru = {
inherit (eval.config) package settings;
};
});
devShells =
let
all = import ./nix/devShells.nix {
inherit
self
self'
inputs'
pkgs
;
};
in
all
// {
default = all.develop;
};
};
}
);
flake.nixosModules = {
# thinkpad-x13s = { pkgs, config, lib, options, ... } @ args: (import ./nix/os/modules/hardware.thinkpad-x13s.nix (args // { inherit self; }));
};
});
}

View file

@ -1,6 +1,6 @@
#!/usr/bin/env bash
set -xe
[ -n "$NAME" ]
[ ! -z "$NAME" ]
nix-build . --show-trace -A "$NAME"
docker image rm "$NAME":latest --force

View file

@ -1,10 +1,6 @@
{
pkgs ? import <nixpkgs> { },
}:
let
baseEnv = [ "SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt" ];
in
rec {
{pkgs ? import <nixpkgs> {}}: let
baseEnv = ["SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt"];
in rec {
base = pkgs.dockerTools.buildImage rec {
name = "base";
@ -25,70 +21,59 @@ rec {
interactive_base = pkgs.dockerTools.buildImage {
name = "interactive_base";
fromImage = base;
contents = with pkgs; [
procps
zsh
coreutils
neovim
];
contents = with pkgs; [procps zsh coreutils neovim];
config = {
Cmd = [ "/bin/zsh" ];
};
config = {Cmd = ["/bin/zsh"];};
};
s3ql =
let
entrypoint = pkgs.writeScript "entrypoint" ''
#!${pkgs.stdenv.shell}
s3ql = let
entrypoint = pkgs.writeScript "entrypoint" ''
#!${pkgs.stdenv.shell}
if [ -z "$S3QL_BUCKET" ]; then
echo S3QL_BUCKET not set
exit 1
fi
if [ -z "$S3QL_BUCKET" ]; then
echo S3QL_BUCKET not set
exit 1
fi
if [ -z "$S3QL_STORAGE_URL" ]; then
echo S3QL_STORAGE_URL not set
exit 1
fi
if [ -z "$S3QL_STORAGE_URL" ]; then
echo S3QL_STORAGE_URL not set
exit 1
fi
if [ -z "$S3QL_CACHESIZE" ]; then
echo S3QL_CACHESIZE not set
exit 1
fi
if [ -z "$S3QL_CACHESIZE" ]; then
echo S3QL_CACHESIZE not set
exit 1
fi
set -x
set -x
if [ "$S3QL_SKIP_FSCK" != "1" ]; then
fsck.s3ql \
--authfile $S3QL_AUTHINFO2 \
--log none \
--cachedir $S3QL_CACHE_DIR \
$S3QL_STORAGE_URL
fi
exec mount.s3ql \
--cachedir "$S3QL_CACHE_DIR" \
--authfile "$S3QL_AUTHINFO2" \
--cachesize "$S3QL_CACHESIZE" \
--fg \
--compress lzma-6 \
--threads 4 \
if [ "$S3QL_SKIP_FSCK" != "1" ]; then
fsck.s3ql \
--authfile $S3QL_AUTHINFO2 \
--log none \
--allow-root \
"$S3QL_STORAGE_URL" \
/bucket
--cachedir $S3QL_CACHE_DIR \
$S3QL_STORAGE_URL
fi
# FIXME: touch .isbucket after mount
'';
in
exec mount.s3ql \
--cachedir "$S3QL_CACHE_DIR" \
--authfile "$S3QL_AUTHINFO2" \
--cachesize "$S3QL_CACHESIZE" \
--fg \
--compress lzma-6 \
--threads 4 \
--log none \
--allow-root \
"$S3QL_STORAGE_URL" \
/bucket
# FIXME: touch .isbucket after mount
'';
in
pkgs.dockerTools.buildImage {
name = "s3ql";
fromImage = interactive_base;
contents = [
pkgs.s3ql
pkgs.fuse
];
contents = [pkgs.s3ql pkgs.fuse];
runAsRoot = ''
#!${pkgs.stdenv.shell}
@ -99,58 +84,57 @@ rec {
'';
config = {
Env = baseEnv ++ [
"HOME=/home/s3ql"
"S3QL_CACHE_DIR=/var/cache/s3ql"
"S3QL_AUTHINFO2=/etc/s3ql/authinfo2"
"CONTAINER_ENTRYPOINT=${entrypoint}"
];
Cmd = [ entrypoint ];
Env =
baseEnv
++ [
"HOME=/home/s3ql"
"S3QL_CACHE_DIR=/var/cache/s3ql"
"S3QL_AUTHINFO2=/etc/s3ql/authinfo2"
"CONTAINER_ENTRYPOINT=${entrypoint}"
];
Cmd = [entrypoint];
Volumes = {
"/var/cache/s3ql" = { };
"/etc/s3ql/authinfo2" = { };
"/buckets" = { };
"/tmp" = { };
"/var/cache/s3ql" = {};
"/etc/s3ql/authinfo2" = {};
"/buckets" = {};
"/tmp" = {};
};
};
};
syncthing =
let
entrypoint = pkgs.writeScript "entrypoint" ''
#!${pkgs.stdenv.shell}
set -x
if [ ! -e /data/.isbucket ]; then
echo ERROR: Bucket not mounted at /data
exit 1
fi
syncthing = let
entrypoint = pkgs.writeScript "entrypoint" ''
#!${pkgs.stdenv.shell}
set -x
if [ ! -e /data/.isbucket ]; then
echo ERROR: Bucket not mounted at /data
exit 1
fi
if [ -z "$SYNCTHING_GUI_ADDRESS" ]; then
echo ERROR: SYNCTHING_GUI_ADDRESS is not set
exit 1
fi
if [ -z "$SYNCTHING_GUI_ADDRESS" ]; then
echo ERROR: SYNCTHING_GUI_ADDRESS is not set
exit 1
fi
if [ ! -w "$SYNCTHING_HOME" ]; then
echo ERROR : SYNCTHING_HOME is not writable
fi
if [ ! -w "$SYNCTHING_HOME" ]; then
echo ERROR : SYNCTHING_HOME is not writable
fi
exec syncthing \
-home $SYNCTHING_HOME \
-gui-address=$SYNCTHING_GUI_ADDRESS \
-no-browser
'';
in
exec syncthing \
-home $SYNCTHING_HOME \
-gui-address=$SYNCTHING_GUI_ADDRESS \
-no-browser
'';
in
pkgs.dockerTools.buildImage {
name = "syncthing";
fromImage = interactive_base;
contents = pkgs.syncthing;
config = {
Env = baseEnv ++ [ "SYNCTHING_HOME=/home/syncthing" ];
Cmd = [ entrypoint ];
Volumes = {
"/data" = { };
};
Env = baseEnv ++ ["SYNCTHING_HOME=/home/syncthing"];
Cmd = [entrypoint];
Volumes = {"/data" = {};};
};
};
}

View file

@ -1,34 +1,26 @@
{ versionsPath }:
let
{versionsPath}: let
channelVersions = import versionsPath;
mkChannelSource =
name:
let
channelVersion = builtins.getAttr name channelVersions;
in
mkChannelSource = name: let
channelVersion = builtins.getAttr name channelVersions;
in
builtins.fetchGit {
# Descriptive name to make the store path easier to identify
inherit name;
inherit (channelVersion) url ref rev;
};
nixPath = builtins.concatStringsSep ":" (
builtins.map (
elemName:
let
elem = builtins.getAttr elemName channelVersions;
elemPath = mkChannelSource elemName;
suffix = if builtins.hasAttr "suffix" elem then elem.suffix else "";
in
builtins.concatStringsSep "=" [
elemName
elemPath
]
+ suffix
) (builtins.attrNames channelVersions)
);
pkgs = import (mkChannelSource "nixpkgs") { };
in
{
nixPath = builtins.concatStringsSep ":" (builtins.map
(elemName: let
elem = builtins.getAttr elemName channelVersions;
elemPath = mkChannelSource elemName;
suffix =
if builtins.hasAttr "suffix" elem
then elem.suffix
else "";
in
builtins.concatStringsSep "=" [elemName elemPath] + suffix)
(builtins.attrNames channelVersions));
pkgs = import (mkChannelSource "nixpkgs") {};
in {
inherit nixPath;
channelSources = pkgs.writeText "channels.rc" ''
export NIX_PATH=${nixPath}

View file

@ -1,10 +1,10 @@
{
self,
self',
inputs',
pkgs,
}:
{
}: let
pkgsUnstable = inputs'.nixpkgs-unstable.legacyPackages;
in {
install = pkgs.mkShell {
name = "infra-install";
packages = with pkgs; [
@ -19,9 +19,10 @@
develop = pkgs.mkShell {
name = "infra-develop";
inputsFrom = [ self'.devShells.install ];
inputsFrom = [
self'.devShells.install
];
packages = with pkgs; [
self'.formatter # .package
inputs'.colmena.packages.colmena
dconf2nix
inputs'.nixos-anywhere.packages.nixos-anywhere
@ -67,7 +68,6 @@
# hedgedoc-cli
xwayland
pulsemixer
(pkgs.writeShellScriptBin "rflk" ''
exec nix run nixpkgs#$@
@ -80,24 +80,9 @@
jq
yq
wireguard-tools
screen
inputs'.nixpkgs-unstable.legacyPackages.kanidm
];
# Set Environment Variables
RUST_BACKTRACE = 1;
KANIDM_URL =
self.nixosConfigurations.sj-srv1.config.containers.webserver.config.services.kanidm.serverSettings.origin;
shellHook = builtins.concatStringsSep "\n" [
# (self.inputs.nixago.lib.${pkgs.system}.make {
# data = self'.formatter.settings;
# output = "treefmt.toml";
# format = "toml";
# }).shellHook
];
};
}

View file

@ -5,14 +5,12 @@
# these come in via home-manager.extraSpecialArgs and are specific to each node
nodeFlake,
repoFlake,
packages',
...
}:
let
pkgsUnstable =
pkgs.pkgsUnstable
or (import nodeFlake.inputs.nixpkgs-unstable { inherit (pkgs) system config overlays; });
in
{
}: let
# pkgsMaster = nodeFlake.inputs.nixpkgs-master.legacyPackages.${pkgs.system};
pkgsUnstable = import nodeFlake.inputs.nixpkgs-unstable {inherit (pkgs) system config;};
in {
imports = [
../profiles/common.nix
# ../profiles/dotfiles.nix
@ -35,41 +33,20 @@ in
../programs/libreoffice.nix
../programs/neovim.nix
../programs/vscode
{ home.packages = [ pkgsUnstable.markdown-oxide ]; }
../programs/obs-studio.nix
];
home.sessionVariables.HM_CONFIG = "graphical-fullblown";
home.sessionVariables.GOPATH = "$HOME/src/go";
home.sessionVariables.PATH = pkgs.lib.concatStringsSep ":" [
"$HOME/.local/bin"
"$PATH"
];
nixpkgs.config.allowInsecurePredicate =
pkg:
builtins.elem (lib.getName pkg) [
"electron-28.3.3"
"electron-27.3.11"
];
home.sessionVariables.PATH = pkgs.lib.concatStringsSep ":" ["$HOME/.local/bin" "$PATH"];
nixpkgs.config.permittedInsecurePackages = [
"electron-28.3.3"
"electron-27.3.11"
];
nixpkgs.config.allowUnfree = [
"electron-28.3.3"
"electron-27.3.11"
];
# nixpkgs.config.allowUnfreePredicate = pkg:
# builtins.elem (lib.getName pkg) [
# "smartgithg"
# "electron-27.3.11"
# ];
home.packages =
(with pkgs; [
[]
++ (with pkgs; [
# Authentication
# cacert
# fprintd
@ -105,13 +82,14 @@ in
# Password Management
gnupg
yubikey-manager
# yubikey-manager
yubikey-manager-qt
yubikey-personalization
yubikey-personalization-gui
# gnome.gnome-keyring
gcr
seahorse
gnome.seahorse
# Language Support
hunspellDicts.en-us
@ -125,13 +103,16 @@ in
aspellDicts.de
# skypeforlinux
# pkgsUnstable.jitsi-meet-electron
thunderbird-128
# betterbird
thunderbird
# FIXME: depends on insecure openssl 1.1.1t
# kotatogram-desktop
pkgsUnstable.tdesktop
pkgsUnstable.signal-desktop-source
tdesktop
signal-desktop
thunderbird
# gnome.cheese
# Virtualization
virt-manager
@ -141,7 +122,7 @@ in
# freerdp
# Audio/Video Players
# ffmpeg
ffmpeg
vlc
# v4l-utils
# audacity
@ -149,8 +130,6 @@ in
yt-dlp
(writeShellScriptBin "youtube-dl-audio" "${yt-dlp}/bin/yt-dlp --extract-audio --audio-format best --audio-quality 9 \${@:?}")
libwebcam
libcamera
snapshot
# Network Tools
tcpdump
@ -161,11 +140,11 @@ in
nethogs
# Code Editing and Programming
# TODO(remove or use): pkgsUnstable.lapce
# TODO(remve or use): pkgsUnstable.helix
pkgsUnstable.lapce
pkgsUnstable.helix
# Image/Graphic/Design Tools
eog
gnome.eog
# gimp
# imagemagick
# exiv2
@ -187,11 +166,10 @@ in
# cdrtools
# Document Processing and Management
nautilus
gnome.nautilus
pcmanfm
# mendeley
evince
xournalpp
# File Synchronzation
maestral
@ -215,7 +193,7 @@ in
# dex
coreutils
lsof
xdg-utils
xdg_utils
xdg-user-dirs
dconf
picocom
@ -244,11 +222,17 @@ in
# libretro.snes9x2010
# retroarchFull
# pkgs.logseq-bin
pkgs.logseq
# (pkgs.callPackage "${repoFlake.inputs.nixpkgs-logseq}/pkgs/by-name/lo/logseq-bin/package.nix" { })
packages'.logseq
# (pkgs.runCommand "logseq-wrapper"
# {
# nativeBuildInputs = [ pkgs.makeWrapper ];
# } ''
# makeWrapper ${pkgs.logseq}/bin/logseq $out/bin/logseq \
# --set NIXOS_OZONE_WL ""
# '')
])
++ (with repoFlake.packages.${pkgs.system}; [ gimp ])
++ (lib.lists.optionals (!pkgs.stdenv.targetPlatform.isAarch64) [
])
++ (lib.lists.optionals (!pkgs.stdenv.targetPlatform.isAarch64) [
pkgsUnstable.ledger-live-desktop

View file

@ -1,8 +1,13 @@
{ pkgs, ... }:
{
home.packages = with pkgs; [
gnome.gnome-tweaks
gnome.gnome-keyring
gnome.seahorse
];
pkgs,
config,
...
}: {
home.packages =
[]
++ (with pkgs; [
gnome.gnome-tweaks
gnome.gnome-keyring
gnome.seahorse
]);
}

View file

@ -1,5 +1,8 @@
{ pkgs, ... }:
{
pkgs,
config,
...
}: {
imports = [
../profiles/common.nix
../profiles/qtile-desktop.nix
@ -13,87 +16,89 @@
../programs/pass.nix
];
home.packages = with pkgs; [
# Nix package related tools
patchelf
nix-index
nix-prefetch-scripts
home.packages =
[]
++ (with pkgs; [
# Nix package related tools
patchelf
nix-index
nix-prefetch-scripts
# Version Control Systems
gitless
# Version Control Systems
gitless
# Process/System Administration
htop
gnome.gnome-tweaks
xorg.xhost
dmidecode
evtest
# Process/System Administration
htop
gnome.gnome-tweaks
xorg.xhost
dmidecode
evtest
# Archive Managers
sshfs-fuse
xarchive
p7zip
zip
unzip
gzip
lzop
# Archive Managers
sshfs-fuse
xarchive
p7zip
zip
unzip
gzip
lzop
# Password Management
gnome.gnome-keyring
gnome.seahorse
# Password Management
gnome.gnome-keyring
gnome.seahorse
# Remote Control Tools
remmina
freerdp
# Remote Control Tools
remmina
freerdp
# Network Tools
openvpn
tcpdump
iftop
iperf
bind
socat
# Network Tools
openvpn
tcpdump
iftop
iperf
bind
socat
# samba
iptables
nftables
wireshark
# samba
iptables
nftables
wireshark
# Code Editors
xclip
xsel
# Code Editors
xclip
xsel
# Image/Graphic/Design Tools
gnome.eog
gimp
inkscape
# Image/Graphic/Design Tools
gnome.eog
gimp
inkscape
# Misc Development Tools
qrcode
jq
cdrtools
# Misc Development Tools
qrcode
jq
cdrtools
# Document Processing and Management
zathura
# Document Processing and Management
zathura
# File Synchronzation
rsync
# File Synchronzation
rsync
# Filesystem Tools
ntfs3g
ddrescue
ncdu
woeusb
unetbootin
pcmanfm
hdparm
testdisk
binwalk
gptfdisk
# Filesystem Tools
ntfs3g
ddrescue
ncdu
woeusb
unetbootin
pcmanfm
hdparm
testdisk
binwalk
gptfdisk
packages'.myPython
packages'.myPython
# Virtualization
virtmanager
];
# Virtualization
virtmanager
]);
}

View file

@ -1,19 +1,14 @@
_: {
mkSimpleTrayService =
{ execStart }:
{
Unit = {
Description = "";
After = [ "graphical-session-pre.target" ];
PartOf = [ "graphical-session.target" ];
};
Install = {
WantedBy = [ "graphical-session.target" ];
};
Service = {
ExecStart = execStart;
};
{}: let
in {
mkSimpleTrayService = {execStart}: {
Unit = {
Description = "";
After = ["graphical-session-pre.target"];
PartOf = ["graphical-session.target"];
};
Install = {WantedBy = ["graphical-session.target"];};
Service = {ExecStart = execStart;};
};
}

View file

@ -1,5 +1,8 @@
{ pkgs, lib, ... }:
{
pkgs,
lib,
...
}: {
home.stateVersion = lib.mkDefault "23.11";
# TODO: re-enable this with the appropriate version?
@ -10,27 +13,10 @@
nixpkgs.config = {
allowBroken = false;
allowUnfree = true;
allowUnsupportedSystem = true;
allowInsecurePredicate =
pkg:
builtins.elem (lib.getName pkg) [
"electron-32.3.3"
"electron"
];
permittedInsecurePackages = [
"electron-32.3.3"
"electron"
"nix-2.15.3"
];
allowUnfreePredicate =
pkg:
builtins.elem (lib.getName pkg) [
"obsidian"
"vivaldi"
"aspell-dict-en-science"
];
};
home.keyboard = {
@ -53,45 +39,47 @@
programs.command-not-found.enable = true;
programs.fzf.enable = true;
home.packages = with pkgs; [
coreutils
home.packages =
[]
++ (with pkgs; [
coreutils
vcsh
vcsh
htop
iperf3
nethogs
htop
iperf3
nethogs
# Authentication
cacert
openssl
mkpasswd
# Authentication
cacert
openssl
mkpasswd
just
ripgrep
du-dust
just
ripgrep
du-dust
elfutils
exfat
file
tree
pwgen
proot
elfutils
exfat
file
tree
pwgen
proot
parted
pv
tmux
wget
curl
parted
pv
tmux
wget
curl
# git helpers
git-crypt
gitFull
pastebinit
gist
mr
# git helpers
git-crypt
gitFull
pastebinit
gist
mr
usbutils
pciutils
];
usbutils
pciutils
]);
}

View file

@ -1,4 +1,45 @@
_: {
{
repoFlake,
pkgs,
config,
repoHttps ? "https://gitlab.com/steveeJ/dotfiles.git",
repoSsh ? "git@gitlab.com:/steveeJ/dotfiles.git",
...
}: let
repoBareLocal =
pkgs.runCommand "fetchbare"
{
outputHashMode = "recursive";
outputHashAlgo = "sha256";
outputHash = "0000000000000000000000000000000000000000000000000000";
} ''
(
set -xe
export GIT_SSL_CAINFO=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
export SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
${pkgs.git}/bin/git clone --mirror ${repoHttps} $out
)
'';
vcshActivationScript = pkgs.writeScript "activation-script" ''
export HOST=$(hostname -s)
function set_remotes {
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url origin $1
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url --push origin $2
}
if ! test -d $HOME/.config/vcsh/repo.d/dotfiles.git; then
echo Cloning dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh clone -b $HOST ${repoBareLocal} dotfiles
set_remotes ${repoHttps} ${repoSsh}
else
set_remotes ${repoBareLocal} ${repoSsh}
echo Updating dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh pull $HOST || true
set_remotes ${repoHttps} ${repoSsh}
fi
'';
in {
# TODO: fix the dotfiles
# home.activation.vcsh = config.lib.dag.entryAfter["linkGeneration"] ''
# $DRY_RUN_CMD ${vcshActivationScript}

View file

@ -3,40 +3,38 @@
repoHttps ? "https://gitlab.com/steveeJ/dotfiles.git",
repoSsh ? "git@gitlab.com:/steveeJ/dotfiles.git",
...
}:
let
}: let
repoBareLocal =
pkgs.runCommand "fetchbare"
{
outputHashMode = "recursive";
outputHashAlgo = "sha256";
outputHash = "0000000000000000000000000000000000000000000000000000";
}
''
(
set -xe
export GIT_SSL_CAINFO=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
export SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
${pkgs.git}/bin/git clone --mirror ${repoHttps} $out
)
'';
{
outputHashMode = "recursive";
outputHashAlgo = "sha256";
outputHash = "0000000000000000000000000000000000000000000000000000";
} ''
(
set -xe
export GIT_SSL_CAINFO=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
export SSL_CERT_FILE=${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt
${pkgs.git}/bin/git clone --mirror ${repoHttps} $out
)
'';
in
pkgs.writeScript "activation-script" ''
export HOST=$(hostname -s)
pkgs.writeScript "activation-script" ''
export HOST=$(hostname -s)
function set_remotes {
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url origin $1
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url --push origin $2
}
function set_remotes {
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url origin $1
${pkgs.vcsh}/bin/vcsh dotfiles remote set-url --push origin $2
}
if ! test -d $HOME/.config/vcsh/repo.d/dotfiles.git; then
echo Cloning dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh clone -b $HOST ${repoBareLocal} dotfiles
set_remotes ${repoHttps} ${repoSsh}
else
set_remotes ${repoBareLocal} ${repoSsh}
echo Updating dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh pull $HOST || true
set_remotes ${repoHttps} ${repoSsh}
fi
''
if ! test -d $HOME/.config/vcsh/repo.d/dotfiles.git; then
echo Cloning dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh clone -b $HOST ${repoBareLocal} dotfiles
set_remotes ${repoHttps} ${repoSsh}
else
set_remotes ${repoBareLocal} ${repoSsh}
echo Updating dotfiles for $HOST...
${pkgs.vcsh}/bin/vcsh pull $HOST || true
set_remotes ${repoHttps} ${repoSsh}
fi
''

View file

@ -1,6 +1,16 @@
{ packages', ... }:
{
imports = [ ../profiles/wayland-desktop.nix ];
pkgs,
config,
lib,
nodeFlake,
packages',
...
}: let
pkgsUnstable = pkgs.callPackage nodeFlake.inputs.nixpkgs-unstable.outPath {};
in {
imports = [
../profiles/wayland-desktop.nix
];
home.packages = [
# experimental WMs

View file

@ -1,6 +1,13 @@
{ pkgs, ... }:
{
imports = [ ../profiles/wayland-desktop.nix ];
pkgs,
config,
lib,
...
}: let
in {
imports = [
../profiles/wayland-desktop.nix
];
services = {
gnome-keyring.enable = false;
@ -16,85 +23,87 @@
# Hidden=true
# '';
services.gpg-agent.pinentryPackage = pkgs.pinentry-gnome3;
services.gpg-agent.pinentryFlavor = "gnome3";
dconf.settings =
let
manualKeybindings = [
{
binding = "Print";
command = "flameshot gui";
name = "flameshot";
}
dconf.settings = let
manualKeybindings = [
{
binding = "Print";
command = "flameshot gui";
name = "flameshot";
}
{
binding = "<Super>t";
command = "alacritty";
name = "alacritty";
}
];
{
binding = "<Super>t";
command = "alacritty";
name = "alacritty";
}
];
numWorkspaces = 10;
customKeybindingBaseName = "org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom";
customKeybindingsNames = builtins.genList (i: "/${customKeybindingBaseName}${toString i}/") (
(builtins.length manualKeybindings) + numWorkspaces # for sending to the workspace
numWorkspaces = 10;
customKeybindingBaseName = "org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom";
customKeybindingsNames =
builtins.genList (i: "/${customKeybindingBaseName}${toString i}/")
(
(builtins.length manualKeybindings)
+ numWorkspaces # for sending to the workspace
);
workspacesKeyBindingsOffset = builtins.length manualKeybindings;
workspacesKeyBindingsOffset = builtins.length manualKeybindings;
# with this we can make use of all number keys [0-9]
mapToNumber =
i:
if i < 10 then
i
else if i == 10 then
0
else
throw "i exceeds 10: ${i}";
in
# with this we can make use of all number keys [0-9]
mapToNumber = i:
if i < 10
then i
else if i == 10
then 0
else throw "i exceeds 10: ${i}";
in
{
"org/gnome/settings-daemon/plugins/media-keys" = {
custom-keybindings = customKeybindingsNames;
screenreader = "@as []";
screensaver = [ "<Alt><Super>l" ];
screensaver = ["<Alt><Super>l"];
};
# disable the builtin <Super>[1-9] functionality
"org/gnome/shell/keybindings" = builtins.listToAttrs (
(builtins.genList (i: {
name = "switch-to-application-${toString (i + 1)}";
value = [ ];
}) numWorkspaces)
"org/gnome/shell/keybindings" = builtins.listToAttrs ((builtins.genList
(i: {
name = "switch-to-application-${toString (i + 1)}";
value = [];
})
numWorkspaces)
++ [
{
name = "toggle-overview";
value = [ ];
value = [];
}
]
);
]);
# remap it to switching to the workspaces
"org/gnome/desktop/wm/keybindings" = builtins.listToAttrs (
builtins.genList (i: {
"org/gnome/desktop/wm/keybindings" = builtins.listToAttrs (builtins.genList
(i: {
name = "switch-to-workspace-${toString (i + 1)}";
value = [ "<Super>${toString (mapToNumber (i + 1))}" ];
}) numWorkspaces
);
value = [
"<Super>${toString (mapToNumber (i + 1))}"
];
})
numWorkspaces);
}
// builtins.listToAttrs (
builtins.genList (i: {
// builtins.listToAttrs (builtins.genList
(i: {
name = "${customKeybindingBaseName}${toString i}";
value = builtins.elemAt manualKeybindings i;
}) (builtins.length manualKeybindings)
)
// builtins.listToAttrs (
builtins.genList (i: {
})
(builtins.length manualKeybindings))
// builtins.listToAttrs (builtins.genList
(i: {
name = "${customKeybindingBaseName}${toString (workspacesKeyBindingsOffset + i)}";
value = {
binding = "<Control><Super>${toString (mapToNumber (i + 1))}";
command = "wmctrl -r :ACTIVE: -t ${toString i}";
name = "Send to workspace ${toString (i + 1)}";
};
}) numWorkspaces
);
})
numWorkspaces);
}

View file

@ -1,22 +1,28 @@
{ pkgs, config, ... }:
{
pkgs,
config,
...
}: let
in {
home.file.".nix-channels".text = "";
home.activation.removeExistingNixChannels = config.lib.dag.entryBefore [ "checkLinkTargets" ] ''
$DRY_RUN_CMD ${pkgs.writeScript "activation-script" ''
set -ex
if test -f $HOME/.nix-channels; then
echo Uninstalling available channels...
if test -f $HOME/.nix-channel; then
while read url channel; do
nix-channel --remove $channel
done < $HOME/.nix-channel
home.activation.removeExistingNixChannels = config.lib.dag.entryBefore ["checkLinkTargets"] ''
$DRY_RUN_CMD ${
pkgs.writeScript "activation-script" ''
set -ex
if test -f $HOME/.nix-channels; then
echo Uninstalling available channels...
if test -f $HOME/.nix-channel; then
while read url channel; do
nix-channel --remove $channel
done < $HOME/.nix-channel
fi
echo Moving existing file away...
touch $HOME/.nix-channels.dummy
mv --backup=numbered $HOME/.nix-channels.dummy $HOME/.nix-channels
rm $HOME/.nix-channels
fi
echo Moving existing file away...
touch $HOME/.nix-channels.dummy
mv --backup=numbered $HOME/.nix-channels.dummy $HOME/.nix-channels
rm $HOME/.nix-channels
fi
''};
''
};
'';
}

View file

@ -1,14 +1,14 @@
{ pkgs, ... }:
let
{
pkgs,
config,
...
}: let
inherit (import ../lib.nix {}) mkSimpleTrayService;
audio = pkgs.writeShellScript "audio" ''
export PATH=${
with pkgs;
lib.makeBinPath [
pulseaudio
findutils
gnugrep
]
lib.makeBinPath [pulseaudio findutils gnugrep]
}:$PATH
export MUTEFILE=''${TEMPDIR:-/tmp}/.qtilemute
@ -33,7 +33,7 @@ let
terminalCommand = "${pkgs.alacritty}/bin/alacritty";
dpmsScript = pkgs.writeShellScript "dpmsScript" ''
export PATH=${with pkgs; lib.makeBinPath [ xorg.xset ]}:$PATH
export PATH=${with pkgs; lib.makeBinPath [xorg.xset]}:$PATH
set -xe
@ -56,7 +56,7 @@ let
'';
screenLockCommand = pkgs.writeShellScript "screenLock" ''
export PATH=${with pkgs; lib.makeBinPath [ i3lock ]}:$PATH
export PATH=${with pkgs; lib.makeBinPath [i3lock]}:$PATH
revert() {
${dpmsScript} default
@ -251,8 +251,7 @@ let
def print_new_window(window):
print("new window: ", window)
'';
in
{
in {
services = {
gnome-keyring.enable = true;
blueman-applet.enable = true;
@ -287,7 +286,7 @@ in
networkmanagerapplet
gnome-icon-theme
gnome.gnome-themes-extra
adwaita-icon-theme
gnome.adwaita-icon-theme
lxappearance
xorg.xcursorthemes
pavucontrol

View file

@ -1,64 +1,62 @@
/*
TODO: create helper scripts for sharing of a screen portion
```
# this will create a new output named HEADLESS-<n>. <n> increments by 1 with each invocation even if the output is `unplug`ged.
swaymsg create_output
# find the name and the workspace number
swaymsg -t get_outputs | jq '.[] | select(.name | test("HEADLESS-.*")) | (.name, .current_workspace)'
swaymsg output HEADLESS-1 mode 1920@108060Hz
# mirror the headless workspace on the current one
nix run nixpkgs\#wl-mirror -- HEADLESS-1
# shift windows to the workspace and switch the focus to it
*/
{
pkgs,
config,
lib,
# packages',
repoFlakeInputs',
...
}:
let
}: let
inherit (import ../lib.nix {}) mkSimpleTrayService;
lockCmd = "${pkgs.swaylock}/bin/swaylock -efF --color '#000000'";
displayOffCmd = "${pkgs.sway}/bin/swaymsg 'output * power off'";
displayOnCmd = "${pkgs.sway}/bin/swaymsg 'output * power on'";
swapOutputWorkspaces = ../../../scripts/sway-swapoutputworkspaces.sh;
in
{
in {
imports = [
../profiles/wayland-desktop.nix
../programs/waybar.nix
# ../programs/salut.nix
];
# TODO: autostart
# environment.loginShellInit = ''
# if [[ "$(tty)" == /dev/tty1 ]]; then
# echo starting sway..
# exec sway
# fi
# '';
services = {
# TODO: doesn't work with 2 screens
# flameshot.enable = true;
};
services.dunst = {
enable = true;
};
services.gpg-agent.pinentryPackage = pkgs.pinentry-gnome3;
services.gpg-agent.pinentryFlavor = "gnome3";
home.packages = [
pkgs.swayidle
pkgs.swaylock
## themes
pkgs.adwaita-icon-theme
pkgs.gnome.adwaita-icon-theme
pkgs.hicolor-icon-theme
pkgs.gnome-icon-theme
## fonts
# pkgs.nerd-fonts # TODO: reinstall selected ones
pkgs.dejavu_fonts # just a basic good fond
pkgs.font-awesome_5 # needed by i3status-rust
pkgs.nerdfonts
pkgs.font-awesome
pkgs.roboto
pkgs.ttf_bitstream_vera
pkgs.noto-fonts
pkgs.noto-fonts-cjk
pkgs.noto-fonts-cjk-sans
pkgs.noto-fonts-cjk-serif
pkgs.noto-fonts-emoji
@ -73,146 +71,125 @@ in
pkgs.dina-font
pkgs.monoid
pkgs.hermit
### found on colemickens' repo
# found on colemickens' repo
pkgs.gelasio # metric-compatible with Georgia
pkgs.powerline-symbols
pkgs.iosevka-comfy.comfy-fixed
## experimental stuff
# experimental stuff
pkgs.fuzzel
];
# TODO: configure kanshi to always set the 5K resolution
# DP-1 "Philips Consumer Electronics Company PHL 499P9 AU02419010010 (DP-1 via DP)"
# Make: Philips Consumer Electronics Company
# Model: PHL 499P9
# Serial: AU02419010010
# Physical size: 1190x340 mm
# Enabled: yes
# Modes:
# 3840x1080 px, 59.967999 Hz (preferred)
# 5120x1440 px, 59.977001 Hz (current)
wayland.windowManager.sway = {
enable = true;
systemd.enable = true;
xwayland = false;
config =
let
modifier = "Mod4";
inherit (config.wayland.windowManager.sway.config)
left
right
up
down
;
in
{
inherit modifier;
bars = [ ];
config = let
modifier = "Mod4";
inherit (config.wayland.windowManager.sway.config) left right up down;
in {
inherit modifier;
bars = [];
input = {
"type:keyboard" =
{
xkb_layout = config.home.keyboard.layout;
xkb_variant = config.home.keyboard.variant;
}
// lib.attrsets.optionalAttrs (builtins.length (config.home.keyboard.options or [ ]) > 0) {
xkb_options = builtins.concatStringsSep "," config.home.keyboard.options;
};
"type:touchpad" = {
natural_scroll = "enabled";
input = {
"type:keyboard" =
{
xkb_layout = config.home.keyboard.layout;
xkb_variant = config.home.keyboard.variant;
}
// lib.attrsets.optionalAttrs (builtins.length (config.home.keyboard.options or []) > 0) {
xkb_options = builtins.concatStringsSep "," config.home.keyboard.options;
};
# alternatively run this command
# swaymsg input "1386:914:Wacom_Intuos_Pro_S_Pen" tool_mode "* relative"
# and then switch to a different VT (alt+ctrl+f2) and back
"1386:914:Wacom_Intuos_Pro_S_Pen" = {
tool_mode = "* relative";
};
"type:touchpad" = {
natural_scroll = "enabled";
};
keybindings = lib.mkOptionDefault {
# as of 2023-05-21 the `!!` arg parsing mode was broken for me on yofi
# "${modifier}+d" = "exec ${packages'.yofi}/bin/yofi binapps";
"${modifier}+d" = "exec ${pkgs.fuzzel}/bin/fuzzel --show-actions";
# only 1-9 exist on the default config
"${modifier}+0" = "workspace number 0";
"${modifier}+Shift+0" = "move container to workspace number 0";
# disable splitting for now as i sometimes trigger it accidentally and then get stuck with it
"${modifier}+b" = "nop";
"${modifier}+v" = "nop";
# move workspace to output
"${modifier}+Control+Shift+${left}" = "move workspace to output left";
"${modifier}+Control+Shift+${right}" = "move workspace to output right";
"${modifier}+Control+Shift+${up}" = "move workspace to output up";
"${modifier}+Control+Shift+${down}" = "move workspace to output down";
# move workspace to output with arrow keys
"${modifier}+Control+Shift+Left" = "move workspace to output left";
"${modifier}+Control+Shift+Right" = "move workspace to output right";
"${modifier}+Control+Shift+Up" = "move workspace to output up";
"${modifier}+Control+Shift+Down" = "move workspace to output down";
# TODO: i've been hitting this one accidentally way too often. find a better place.
# "${modifier}+Shift+e" = "exec ${pkgs.sway}/bin/swaymsg exit";
"${modifier}+q" = "kill";
"${modifier}+Shift+q" = "exec ${pkgs.sway}/bin/swaymsg -t get_tree | ${pkgs.jq}/bin/jq 'recurse(.nodes[], .floating_nodes[]) | select(.focused).pid' | ${pkgs.findutils}/bin/xargs -L1 kill -9";
"${modifier}+x" = "exec ${swapOutputWorkspaces}";
"${modifier}+Ctrl+l" = "exec ${lockCmd}";
"--locked XF86AudioPlay" = "exec ${pkgs.playerctl}/bin/playerctl play-pause";
"XF86AudioPrev" = "exec ${pkgs.playerctl}/bin/playerctl previous";
"XF86AudioNext" = "exec ${pkgs.playerctl}/bin/playerctl next";
"XF86AudioRaiseVolume" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --change-volume +5";
"XF86AudioLowerVolume" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --change-volume -5";
"--locked XF86AudioMute" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --toggle-mute";
"Print" = "exec ${pkgs.shotman}/bin/shotman --capture region";
# alternatively run this command
# swaymsg input "1386:914:Wacom_Intuos_Pro_S_Pen" tool_mode "* relative"
# and then switch to a different VT (alt+ctrl+f2) and back
"1386:914:Wacom_Intuos_Pro_S_Pen" = {
tool_mode = "* relative";
};
terminal = "alacritty";
startup =
[
{
command = builtins.toString (
pkgs.writeShellScript "ensure-graphical-session" ''
(
${pkgs.coreutils}/bin/sleep 0.2
${pkgs.systemd}/bin/systemctl --user restart graphical-session.target
) &
''
);
}
]
++ lib.optionals config.services.swayidle.enable [
{
command = builtins.toString (
pkgs.writeShellScript "ensure-graphical-session" ''
(
${pkgs.coreutils}/bin/sleep 0.2
${pkgs.systemd}/bin/systemctl --user restart swayidle
) &
''
);
}
];
colors.focused = lib.mkOptionDefault { childBorder = lib.mkForce "#ffa500"; };
window.titlebar = false;
window.border = 4;
# this maps to focus_on_window_activation
focus.newWindow = "urgent";
};
keybindings = lib.mkOptionDefault {
# as of 2023-05-21 the `!!` arg parsing mode was broken for me on yofi
# "${modifier}+d" = "exec ${packages'.yofi}/bin/yofi binapps";
"${modifier}+d" = "exec ${pkgs.fuzzel}/bin/fuzzel --show-actions";
# only 1-9 exist on the default config
"${modifier}+0" = "workspace number 0";
"${modifier}+Shift+0" = "move container to workspace number 0";
# disable splitting for now as i sometimes trigger it accidentally and then get stuck with it
"${modifier}+b" = "nop";
"${modifier}+v" = "nop";
# move workspace to output
"${modifier}+Control+Shift+${left}" = "move workspace to output left";
"${modifier}+Control+Shift+${right}" = "move workspace to output right";
"${modifier}+Control+Shift+${up}" = "move workspace to output up";
"${modifier}+Control+Shift+${down}" = "move workspace to output down";
# move workspace to output with arrow keys
"${modifier}+Control+Shift+Left" = "move workspace to output left";
"${modifier}+Control+Shift+Right" = "move workspace to output right";
"${modifier}+Control+Shift+Up" = "move workspace to output up";
"${modifier}+Control+Shift+Down" = "move workspace to output down";
"${modifier}+Shift+e" = "exec ${pkgs.sway}/bin/swaymsg exit";
"${modifier}+q" = "kill";
"${modifier}+Shift+q" = "exec ${pkgs.sway}/bin/swaymsg -t get_tree | ${pkgs.jq}/bin/jq 'recurse(.nodes[], .floating_nodes[]) | select(.focused).pid' | ${pkgs.findutils}/bin/xargs -L1 kill -9";
"${modifier}+x" = "exec ${swapOutputWorkspaces}";
"${modifier}+Ctrl+l" = "exec ${lockCmd}";
"--locked XF86AudioPlay" = "exec ${pkgs.playerctl}/bin/playerctl play-pause";
"XF86AudioPrev" = "exec ${pkgs.playerctl}/bin/playerctl previous";
"XF86AudioNext" = "exec ${pkgs.playerctl}/bin/playerctl next";
"XF86AudioRaiseVolume" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --change-volume +5";
"XF86AudioLowerVolume" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --change-volume -5";
"--locked XF86AudioMute" = "exec ${pkgs.pulsemixer}/bin/pulsemixer --toggle-mute";
"Print" = "exec ${pkgs.shotman}/bin/shotman --capture region";
};
terminal = "alacritty";
startup =
[
{
command = builtins.toString (pkgs.writeShellScript "ensure-graphical-session" ''
(
${pkgs.coreutils}/bin/sleep 0.2
${pkgs.systemd}/bin/systemctl --user restart graphical-session.target
) &
'');
}
]
++ lib.optionals config.services.swayidle.enable [
{
command = builtins.toString (pkgs.writeShellScript "ensure-graphical-session" ''
(
${pkgs.coreutils}/bin/sleep 0.2
${pkgs.systemd}/bin/systemctl --user restart swayidle
) &
'');
}
];
colors.focused = lib.mkOptionDefault {
childBorder = lib.mkForce "#ffa500";
};
window.titlebar = false;
window.border = 4;
# this maps to focus_on_window_activation
focus.newWindow = "urgent";
};
};
services.swayidle = {

View file

@ -1,14 +1,16 @@
{
pkgs,
config,
lib,
repoFlake,
nodeFlake,
...
}:
let
}: let
inherit (import ../lib.nix {}) mkSimpleTrayService;
nixpkgs-wayland' = repoFlake.inputs.nixpkgs-wayland.packages.${pkgs.system};
in
{
wayprompt = nixpkgs-wayland'.wayprompt;
in {
fonts.fontconfig.enable = true;
# services.gpg-agent.pinentryFlavor = lib.mkForce null;
@ -24,15 +26,14 @@ in
systemd.user.targets.tray = {
Unit = {
Description = "Home Manager System Tray";
Requires = [ "graphical-session-pre.target" ];
Requires = ["graphical-session-pre.target"];
};
};
home.packages =
with pkgs;
home.packages = with pkgs;
[
# required by network-manager-applet
networkmanagerapplet
pkgs.networkmanagerapplet
wlr-randr
wayout
@ -47,34 +48,29 @@ in
# TODO: whwat's this for?
# wltype
pavucontrol
playerctl
pasystray
qt5.qtwayland
qt6.qtwayland
# libsForQt5.qt5.qtwayland
# libsForQt6.qt6.qtwayland
# audio
playerctl
helvum
pasystray
sonusmix
pwvucontrol
# probably required by flameshot
# xdg-desktop-portal xdg-desktop-portal-wlr
# grim
waypipe
]
++ (lib.lists.optionals (!pkgs.stdenv.isAarch64)
++ (
lib.lists.optionals (!pkgs.stdenv.isAarch64)
# TODO: broken on aarch64
[ ]
[
]
);
home.sessionVariables = {
XDG_SESSION_TYPE = "wayland";
NIXOS_OZONE_WL = "1";
MOZ_ENABLE_WAYLAND = "1";
WLR_NO_HARDWARE_CURSORS = "1";
};
home.pointerCursor = {

View file

@ -3,15 +3,14 @@
lib,
pkgs,
...
}:
let
}: let
extensions =
[
#undetectable adblocker
{ id = "gcfcpohokifjldeandkfjoboemihipmb"; }
{id = "gcfcpohokifjldeandkfjoboemihipmb";}
# ublock origin
{ id = "cjpalhdlnbpafiamejdnhcphjbkeiagm"; }
{id = "cjpalhdlnbpafiamejdnhcphjbkeiagm";}
# # YT ad block
# {id = "cmedhionkhpnakcndndgjdbohmhepckk";}
@ -20,15 +19,15 @@ let
# {id = "cfhdojbkjhnklbpkdaibdccddilifddb";}
# Cookie Notice Blocker
{ id = "odhmfmnoejhihkmfebnolljiibpnednn"; }
{id = "odhmfmnoejhihkmfebnolljiibpnednn";}
# i don't care about cookies
{ id = "fihnjjcciajhdojfnbdddfaoknhalnja"; }
{id = "fihnjjcciajhdojfnbdddfaoknhalnja";}
# NopeCHA
{ id = "dknlfmjaanfblgfdfebhijalfmhmjjjo"; }
{id = "dknlfmjaanfblgfdfebhijalfmhmjjjo";}
# h264ify
{ id = "aleakchihdccplidncghkekgioiakgal"; }
{id = "aleakchihdccplidncghkekgioiakgal";}
# clippy
# {id = "honbeilkanbghjimjoniipnnehlmhggk"}
@ -39,43 +38,31 @@ let
}
# cookie autodelete
{ id = "fhcgjolkccmbidfldomjliifgaodjagh"; }
{id = "fhcgjolkccmbidfldomjliifgaodjagh";}
# unhook
{ id = "khncfooichmfjbepaaaebmommgaepoid"; }
{id = "khncfooichmfjbepaaaebmommgaepoid";}
]
++ (lib.lists.optionals ((builtins.match "^steveej.*" name) != null) [
# polkadotjs
{ id = "mopnmbcafieddcagagdcbnhejhlodfdd"; }
# rabby wallet
{ id = "acmacodkjbdgmoleebolmdjonilkdbch"; }
# phantom wallet
{ id = "bfnaelmomeimhlpmgjnjophhpkkoljpa"; }
# Vimium C
{ id = "hfjbmagddngcpeloejdejnfgbamkjaeg"; }
{id = "hfjbmagddngcpeloejdejnfgbamkjaeg";}
# TODO: this causes scrolling the tab bar all the way to the end. look for a different one or report
# always right
{ id = "npjpaghfnndnnmjiliibnkmdfgbojokj"; }
# shazam music
{ id = "mmioliijnhnoblpgimnlajmefafdfilb"; }
{id = "npjpaghfnndnnmjiliibnkmdfgbojokj";}
]);
in
{
in {
programs.chromium = {
enable = true;
inherit extensions;
# TODO: extensions currently don't work with ungoogled-chromium
package = pkgs.chromium;
};
programs.brave = {
# TODO: enable this on aarch64-linux
enable = true && !pkgs.stdenv.targetPlatform.isAarch64;
enable =
true
&& !pkgs.stdenv.targetPlatform.isAarch64;
inherit extensions;
};
programs.browserpass = {browsers = ["chromium" "brave"];};
}

View file

@ -1,5 +1,8 @@
{ pkgs, ... }:
{
pkgs,
repoFlake,
...
}: {
services.espanso = {
package = pkgs.espanso-wayland;
# package = pkgs.espanso-wayland.overrideAttrs (_: {
@ -21,62 +24,64 @@
# backend = "Clipboard";
};
};
matches =
let
playerctl = ''${pkgs.coreutils}/bin/env DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/$(${pkgs.coreutils}/bin/id -u)/bus" ${pkgs.playerctl}/bin/playerctl'';
in
{
default = {
matches = [
{
trigger = ":vpos";
replace = "{{output}}";
vars = [
{
name = "output";
type = "script";
params = {
args = [
(pkgs.writeScript "espanso" ''
#! ${pkgs.python3}/bin/python
import subprocess, os, math, datetime
matches = let
playerctl = ''
${pkgs.coreutils}/bin/env DBUS_SESSION_BUS_ADDRESS="unix:path=/run/user/$(${pkgs.coreutils}/bin/id -u)/bus" ${pkgs.playerctl}/bin/playerctl'';
in {
default = {
matches = [
{
trigger = ":vpos";
replace = "{{output}}";
vars = [
{
name = "output";
type = "script";
params = {
args = [
(pkgs.writeScript "espanso" ''
#! ${pkgs.python3}/bin/python
import subprocess, os, math, datetime
id=str(os.getuid())
result=subprocess.run(args=["${pkgs.playerctl}/bin/playerctl", "position"], env={"DBUS_SESSION_BUS_ADDRESS": "unix:path=/run/user/"+id+"/bus"},capture_output=True)
result.check_returncode()
id=str(os.getuid())
result=subprocess.run(args=["${pkgs.playerctl}/bin/playerctl", "position"], env={"DBUS_SESSION_BUS_ADDRESS": "unix:path=/run/user/"+id+"/bus"},capture_output=True)
result.check_returncode()
position_secs = math.trunc(float(result.stdout))
position_human = datetime.timedelta(seconds=position_secs)
print("%s - %s" % (position_human, position_secs))
'')
];
};
}
];
}
{
trigger = ":vtit";
replace = "{{output}}";
vars = [
{
name = "output";
type = "script";
params = {
args = [ (pkgs.writeShellScript "espanso" "${playerctl} metadata title") ];
};
}
];
}
{
trigger = ":dunno";
replace = "¯\\_()_/¯";
}
{
trigger = ":shrug";
replace = "¯\\_()_/¯";
}
];
};
position_secs = math.trunc(float(result.stdout))
position_human = datetime.timedelta(seconds=position_secs)
print("%s - %s" % (position_human, position_secs))
'')
];
};
}
];
}
{
trigger = ":vtit";
replace = "{{output}}";
vars = [
{
name = "output";
type = "script";
params = {
args = [
(pkgs.writeShellScript "espanso"
"${playerctl} metadata title")
];
};
}
];
}
{
trigger = ":dunno";
replace = "¯\\_()_/¯";
}
{
trigger = ":shrug";
replace = "¯\\_()_/¯";
}
];
};
};
};
}

View file

@ -1,417 +1,6 @@
{
repoFlake,
pkgs,
config,
lib,
...
}:
let
# Search extension names with below command:
# nix flake show --json "gitlab:rycee/nur-expressions?dir=pkgs/firefox-addons" --all-systems | jq -r '.packages."x86_64-linux" | keys[]' | rg QUERY
ryceeAddons = with pkgs.nur.repos.rycee.firefox-addons; [
ublock-origin
{pkgs, ...}: {
programs.librewolf = {enable = true;};
programs.firefox = {enable = true;};
# bypass-paywalls-clean (can't use, was creating popups)
consent-o-matic
terms-of-service-didnt-read
auto-tab-discard
# redirector # For nixos wiki
# darkreader
facebook-container
control-panel-for-twitter
# containerise
facebook-tracking-removal
vimium
cookie-autodelete
auto-tab-discard
istilldontcareaboutcookies
youtube-recommended-videos
display-_anchors
];
customAddons = [
];
search = {
force = true;
default = "DuckDuckGo";
privateDefault = "DuckDuckGo";
};
mkProfile =
override:
lib.recursiveUpdate {
extensions = ryceeAddons ++ customAddons;
inherit search;
settings = {
# automatically enable extensions
"extensions.autoDisableScopes" = 0;
"middlemouse.paste" = false;
"browser.download.useDownloadDir" = false;
"browser.tabs.insertAfterCurrent" = true;
"browser.tabs.warnOnClose" = true;
"browser.toolbars.bookmarks.visibility" = "never";
"browser.quitShortcut.disabled" = false;
# restore the previous session automatically
"browser.startup.page" = 3;
"browser.sessionstore.resume_from_crash" = true;
"browser.sessionstore.restore_pinned_tabs_on_demand" = true;
"browser.sessionstore.restore_on_demand" = true;
"browser.urlbar.suggest.bookmark" = true;
"browser.urlbar.suggest.engines" = true;
"browser.urlbar.suggest.history" = true;
"browser.urlbar.suggest.openpage" = true;
"browser.urlbar.suggest.topsites" = false;
"browser.urlbar.trimHttps" = true;
"sidebar.position_start" = false;
"findbar.highlightAll" = true;
"browser.tabs.hoverPreview.enabled" = true;
# Disable fx accounts
"identity.fxaccounts.enabled" = false;
# Disable "save password" prompt
"signon.rememberSignons" = false;
# Harden
"privacy.trackingprotection.enabled" = true;
"dom.security.https_only_mode" = true;
# Disable irritating first-run stuff
"browser.disableResetPrompt" = true;
"browser.download.panel.shown" = true;
"browser.feeds.showFirstRunUI" = false;
"browser.messaging-system.whatsNewPanel.enabled" = false;
"browser.rights.3.shown" = true;
"browser.shell.checkDefaultBrowser" = false;
"browser.shell.defaultBrowserCheckCount" = 1;
"browser.startup.homepage_override.mstone" = "ignore";
"browser.uitour.enabled" = false;
"startup.homepage_override_url" = "";
"trailhead.firstrun.didSeeAboutWelcome" = true;
"browser.bookmarks.restore_default_bookmarks" = false;
"browser.bookmarks.addedImportButton" = true;
# Disable "Save to Pocket" or Pocket entirely
"extensions.pocket.enabled" = false;
# Disable telemetry
"toolkit.telemetry.enabled" = false;
"toolkit.telemetry.unified" = false;
"toolkit.telemetry.archive.enabled" = false;
"datareporting.healthreport.uploadEnabled" = false;
"app.shield.optoutstudies.enabled" = false;
"browser.discovery.enabled" = false;
"browser.newtabpage.activity-stream.feeds.telemetry" = false;
"browser.newtabpage.activity-stream.telemetry" = false;
"browser.ping-centre.telemetry" = false;
"datareporting.healthreport.service.enabled" = false;
"datareporting.policy.dataSubmissionEnabled" = false;
"datareporting.sessions.current.clean" = true;
"devtools.onboarding.telemetry.logged" = false;
"toolkit.telemetry.bhrPing.enabled" = false;
"toolkit.telemetry.firstShutdownPing.enabled" = false;
"toolkit.telemetry.hybridContent.enabled" = false;
"toolkit.telemetry.newProfilePing.enabled" = false;
"toolkit.telemetry.prompted" = 2;
"toolkit.telemetry.rejected" = true;
"toolkit.telemetry.reportingpolicy.firstRun" = false;
"toolkit.telemetry.server" = "";
"toolkit.telemetry.shutdownPingSender.enabled" = false;
"toolkit.telemetry.unifiedIsOptIn" = false;
"toolkit.telemetry.updatePing.enabled" = false;
# Disable any feeds on the new tab page
"browser.newtabpage.activity-stream.showTopSites" = false;
"browser.newtabpage.activity-stream.default.sites" = lib.mkForce [ ];
"browser.newtabpage.activity-stream.discoverystream.enabled" = false;
"browser.newtabpage.activity-stream.feeds.topsites" = false;
"browser.newtabpage.activity-stream.showSponsoredTopSites" = false;
"browser.newtabpage.activity-stream.improvesearch.topSiteSearchShortcuts" = false;
"browser.newtabpage.blocked" = lib.genAttrs [
# Youtube
"26UbzFJ7qT9/4DhodHKA1Q=="
# Facebook
"4gPpjkxgZzXPVtuEoAL9Ig=="
# Wikipedia
"eV8/WsSLxHadrTL1gAxhug=="
# Reddit
"gLv0ja2RYVgxKdp0I5qwvA=="
# Amazon
"K00ILysCaEq8+bEqV/3nuw=="
# Twitter
"T9nJot5PurhJSy8n038xGA=="
] (_: 1);
"browser.topsites.blockedSponsors" = [
"adidas"
"temuaffiliateprogram.pxf"
"s.click.aliexpress"
];
# enable userChrome
"toolkit.legacyUserProfileCustomizations.stylesheets" = true;
"devtools.chrome.enabled" = true;
"devtools.debugger.remote-enabled" = true;
# disable translations for some languages
"browser.translations.neverTranslateLanguages" = [
"en"
"de"
];
"browser.translations.automaticallyPopup" = false;
# enable pipewire (and libcamera) sources
"media.webrtc.camera.allow-pipewire" = true;
};
userChrome =
let
name = override.color or colors.grey;
value = colorValues."${name}".normal;
valueBright = colorValues."${name}".highlight;
valueDark = colorValues."${name}".inactive;
in
''
@namespace url("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"); /* only needed once */
#nav-bar {
background-color: ${value} !important;
color: black !important;
}
/* don't show close button on background tabs */
#tabbrowser-tabs[closebuttons="activetab"] .tabbrowser-tab:not([selected]):not([pinned]):not([hover]) .tab-close-button {
display: none !important;
}
/* show close button on hover */
#tabbrowser-tabs[closebuttons="activetab"] .tabbrowser-tab:not([selected]):not([pinned]):hover .tab-close-button {
display: -moz-inline-box !important;
}
/* default */
#TabsToolbar {
background: ${valueDark} !important;
}
/* default tab */
#TabsToolbar #tabbrowser-tabs .tabbrowser-tab .tab-content {
background: ${value} !important;
opacity: 0.8
}
/* selected tab */
#TabsToolbar #tabbrowser-tabs .tabbrowser-tab[selected] .tab-content {
background: ${valueBright} !important;
box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2), 0 6px 20px 0 rgba(0,0,0,0.19);
}
/* hovered tab */
#TabsToolbar #tabbrowser-tabs .tabbrowser-tab:hover:not([selected]) .tab-content {
background: ${valueBright} !important;
}
/* unloaded/pending tab */
#TabsToolbar #tabbrowser-tabs .tabbrowser-tab[pending] .tab-content {
background: ${valueDark} !important;
}
'';
# /* new tab */
# #TabsToolbar #tabbrowser-tabs #tabs-newtab-button .toolbarbutton-icon {
# background: unset !important;
# }
# #TabsToolbar #tabbrowser-tabs #tabs-newtab-button {
# /* background: var(--default_tabs_bg_newtab) !important;
# }
# /* hovered new tab */
# #TabsToolbar #tabbrowser-tabs #tabs-newtab-button:hover {
# background: var(--default_tabs_bg_newtab_hovered) !important;
# }
} (builtins.removeAttrs override [ "color" ]);
# TODO: insert the id automatically
mkProfiles = attrs: builtins.mapAttrs (_k: v: v) attrs;
colors = builtins.mapAttrs (name: _: name) colorValues;
colorValues = {
blue = {
normal = "#49b1fc";
highlight = "#05a9fc"; # Brighter blue
inactive = "#1f81c6"; # Darker blue
};
green = {
normal = "#51cd00";
highlight = "#5ae200"; # Brighter green
inactive = "#45ad00"; # Darker green
};
orange = {
normal = "#ff9800";
highlight = "#ffb74d"; # Brighter orange
inactive = "#c76a00"; # Darker orange
};
red = {
normal = "#f6685e";
highlight = "#ff4336"; # Brighter red
inactive = "#aa463f"; # Darker red
};
yellow = {
normal = "#fced4b";
highlight = "#fce705"; # Brighter yellow
inactive = "#dbbe00"; # Darker yellow
};
purple = {
normal = "#9c27b0";
highlight = "#ab47bc"; # Brighter purple
inactive = "#7b1fa2"; # Darker purple
};
pink = {
normal = "#e91e63";
highlight = "#ff6090"; # Brighter pink
inactive = "#c2185b"; # Darker pink
};
brown = {
normal = "#795548";
highlight = "#a88b6f"; # Brighter brown
inactive = "#4e3b30"; # Darker brown
};
grey = {
normal = "#9e9e9e";
highlight = "#bdbdbd"; # Brighter grey
inactive = "#757575"; # Darker grey
};
teal = {
normal = "#009688";
highlight = "#26c6da"; # Brighter teal
inactive = "#00796b"; # Darker teal
};
};
in
{
nixpkgs.overlays = [
repoFlake.inputs.nur.overlays.default
];
nixpkgs.config.allowUnfreePredicate =
pkg:
builtins.elem (lib.getName pkg) [
"youtube-recommended-videos"
];
programs.librewolf = {
enable = false;
};
programs.firefox = {
enable = true;
package = pkgs.firefox-esr;
profiles = mkProfiles {
"personal" = mkProfile {
id = 0;
isDefault = true;
color = colors.blue;
};
"comms" = mkProfile {
id = 1;
color = colors.blue;
};
"admin" = mkProfile {
id = 2;
color = colors.blue;
};
"infra" = mkProfile {
id = 3;
color = colors.blue;
};
"finance" = mkProfile {
id = 4;
color = colors.yellow;
};
"business-admin" = mkProfile {
id = 5;
color = colors.teal;
};
"business-comms" = mkProfile {
id = 6;
color = colors.teal;
};
"business-dev" = mkProfile {
id = 7;
color = colors.teal;
};
"holo-dev" = mkProfile {
id = 8;
color = colors.green;
};
"holo-infra" = mkProfile {
id = 9;
color = colors.green;
};
"holo-comms" = mkProfile {
id = 10;
color = colors.green;
};
"justyna" = mkProfile {
id = 11;
color = colors.pink;
};
"justyna-office" = mkProfile {
id = 12;
color = colors.pink;
};
};
};
# create one desktop entry for each profile
xdg.desktopEntries = lib.mapAttrs' (
k: _v:
lib.nameValuePair "firefox-profile-${k}" {
categories = [
"Network"
"WebBrowser"
];
exec = "${lib.getExe config.programs.firefox.package} -P ${k}";
genericName = "Web Browser";
icon =
builtins.replaceStrings [ ".desktop" ] [ "" ]
config.programs.firefox.package.desktopItem.name;
mimeType = [
"text/html"
"text/xml"
"application/xhtml+xml"
"application/vnd.mozilla.xul+xml"
"x-scheme-handler/http"
"x-scheme-handler/https"
];
name = "Firefox: ${k}";
startupNotify = true;
settings.StartupWMClass =
# To group windows of different profiles.
# Set WM_CLASS on Xorg using --class, set app-id on Wayland using --name.
#if profile.name == "default"
#then "firefox"
#else "firefox-${profile.name}";
"firefox";
terminal = false;
type = "Application";
}
) config.programs.firefox.profiles;
# home.file.".mozilla/native-messaging-hosts/passff.json".source = "${pkgs.passff-host}/share/passff-host/passff.json";
}

View file

@ -1,14 +1,28 @@
{ lib, pkgs, osConfig, ... }:
{
home.packages = [ pkgs.gcr ];
lib,
pkgs,
config,
...
}: {
home.packages =
[
pkgs.gcr
]
++ (
if config.services.gpg-agent.pinentryFlavor == "gtk2"
then [pkgs.pinentry-gtk2]
else if config.services.gpg-agent.pinentryFlavor == "gnome3"
then [pkgs.pinentry-gnome]
else []
);
programs.gpg.enable = true;
services.gpg-agent = {
enable = true;
enableScDaemon = !osConfig.services.pcscd.enable;
enableScDaemon = true;
enableSshSupport = true;
grabKeyboardAndMouse = true;
pinentryPackage = lib.mkDefault pkgs.pinentry-gtk2;
pinentryFlavor = lib.mkDefault "gtk2";
extraConfig = ''
no-allow-external-cache
'';

View file

@ -1,25 +1,32 @@
{ pkgs, config, ... }:
{
pkgs,
config,
...
}: let
# TODO: clean up the impurity in here
in {
home.sessionVariables.HOMESHICK_DIR = "${pkgs.homeshick}";
home.activation.bootstrapRepos = config.lib.dag.entryAfter [ "writeBoundary" ] ''
$DRY_RUN_CMD ${pkgs.writeScript "activation-script" ''
set -e
echo home-manager path is ${config.home.path}
echo home is $HOME
home.activation.bootstrapRepos = config.lib.dag.entryAfter ["writeBoundary"] ''
$DRY_RUN_CMD ${
pkgs.writeScript "activation-script" ''
set -e
echo home-manager path is ${config.home.path}
echo home is $HOME
source ${pkgs.homeshick}/homeshick.sh
type homeshick
source ${pkgs.homeshick}/homeshick.sh
type homeshick
# echo Updating homeshick
# ln -sfT ${pkgs.homeshick} "$HOMESICK_REPOS"/.homeshick
# mv -Tf "$HOMESICK_REPOS"/{.,}homeshick
''};
# echo Updating homeshick
# ln -sfT ${pkgs.homeshick} "$HOMESICK_REPOS"/.homeshick
# mv -Tf "$HOMESICK_REPOS"/{.,}homeshick
''
};
'';
nixpkgs.config = {
packageOverrides =
pkgs: with pkgs; {
packageOverrides = pkgs:
with pkgs; {
homeshick = builtins.fetchGit {
url = "https://github.com/andsens/homeshick.git";
ref = "master";

View file

@ -1,8 +1,3 @@
{ pkgs, nodeFlake, ... }:
let
pkgsStable = nodeFlake.inputs.nixpkgs-stable.legacyPackages.${pkgs.system};
in
{
home.packages = [ pkgsStable.libreoffice ];
{pkgs, ...}: {
home.packages = with pkgs; [libreoffice-fresh];
}

View file

@ -1,161 +1,131 @@
{ repoFlake, pkgs, ... }:
{
imports = [ repoFlake.inputs.nixvim.homeManagerModules.nixvim ];
pkgs,
lib,
...
}: let
in {
# FIXME: this doesn't work
home.sessionVariables.EDITOR = "nvim";
programs.nixvim = {
programs.neovim = {
enable = true;
defaultEditor = true;
vimdiffAlias = true;
vimAlias = true;
extraPython3Packages = ps: with ps; [ ];
extraPython3Packages = ps: with ps; [];
# extraConfigVim = builtins.readFile ./neovim/vimrc;
extraConfig = builtins.readFile ./neovim/vimrc;
clipboard = {
register = "unnamedplus";
providers.wl-copy.enable = true;
};
plugins = with pkgs;
[
# yaml-folds
{
plugin = vimUtils.buildVimPlugin {
name = "vim-yaml-folds";
src = fetchFromGitHub {
owner = "pedrohdz";
repo = "vim-yaml-folds";
rev = "890ccd8e5370808d569e96dbb06cbeca2cf5993a";
sha256 = "018z6xcwrq58q6lj6gwhrifjaxkmrlkkg0n86s6mjjlwkbs2qa4m";
};
buildInputs = [zip vim];
};
}
plugins = {
airline = {
enable = true;
settings = {
powerline_fonts = 1;
skip_empty_sections = 1;
theme = "papercolor";
};
};
fugitive.enable = true;
gitblame.enable = true;
lsp = {
enable = true;
};
{
plugin = vimUtils.buildVimPlugin {
name = "vim-yaml";
src = fetchFromGitHub {
owner = "stephpy";
repo = "vim-yaml";
rev = "e97e063b16eba4e593d620676a0a15fa98613979";
sha256 = "0vqahbrnr43lxanpziyrmzaqqb3cmyny8ry1xvmy2xyd1larzfrk";
};
};
}
nix.enable = true;
# broken 2021-06-08
# {
# plugin = vimUtils.buildVimPlugin {
# name = "vim-markdown-toc";
# src = fetchFromGitHub {
# owner = "mzlogin";
# repo = "vim-markdown-toc";
# rev = "b7bb6c37033d3a6c93906af48dc0e689bd948638";
# sha256 = "026xf2gid4qivwawh7if3nfk7zja9di0flhdzdx82lvil9x48lyz";
# };
# };
# }
# TODO: enable in next release
# numbertoggle.enable = true;
# broken 2021-06-08
# {
# plugin = vimUtils.buildVimPlugin {
# name = "vim-perl";
# src = fetchFromGitHub {
# owner = "vim-perl";
# repo = "vim-perl";
# rev = "f330b5d474c44e6cfae22ba50868093dea3e9adb";
# sha256 = "1dy40ixgixj0536c5ggra51b4yd1lbw4j6l0j5zc3diasb7m2gvr";
# };
# };
# }
# successfor to ctrlp and fzf
telescope.enable = true;
{
plugin = vimUtils.buildVimPlugin {
name = "git-blame";
src = fetchFromGitHub {
"owner" = "zivyangll";
"repo" = "git-blame.vim";
"rev" = "9d144b7bed5d8f1c9259551768b7f3b3d1294917";
"sha256" = "06zb5xcc59k25rpwl46j82fcqckiznmj97v6i0mwlb8jhqqrhy9j";
};
};
}
]
++ (with pkgs.vimPlugins; [
delimitMate
vim-airline
vim-airline-themes
ctrlp
vim-css-color
rainbow_parentheses
vim-colorschemes
vim-colorstepper
vim-signify
fugitive
vim-indent-guides
UltiSnips
fzfWrapper
todo-comments.enable = true;
ncm2
ncm2-bufword
ncm2-path
ncm2-tmux
ncm2-ultisnips
nvim-yarp
toggleterm.enable = true;
LanguageClient-neovim
treesitter = {
enable = true;
Improved-AnsiEsc
tabular
grammarPackages = with pkgs.vimPlugins.nvim-treesitter.builtGrammars; [
bash
json
lua
make
markdown
nix
regex
toml
vim
vimdoc
xml
yaml
];
};
# Nix
vim-addon-nix
tlib
vim-addon-vim2nix
treesitter-context.enable = true;
treesitter-refactor.enable = true;
# LaTeX
vim-latex-live-preview
vimtex
# This plugin trims trailing whitespace and lines.
trim.enable = true;
};
# YAML
vim-yaml
# plugins = with pkgs;
# [
# # yaml-folds
# {
# plugin = vimUtils.buildVimPlugin {
# name = "vim-yaml-folds";
# src = fetchFromGitHub {
# owner = "pedrohdz";
# repo = "vim-yaml-folds";
# rev = "890ccd8e5370808d569e96dbb06cbeca2cf5993a";
# sha256 = "018z6xcwrq58q6lj6gwhrifjaxkmrlkkg0n86s6mjjlwkbs2qa4m";
# };
# buildInputs = [zip vim];
# };
# }
# markdown
vim-markdown
vim-markdown-toc
# {
# plugin = vimUtils.buildVimPlugin {
# name = "vim-yaml";
# src = fetchFromGitHub {
# owner = "stephpy";
# repo = "vim-yaml";
# rev = "e97e063b16eba4e593d620676a0a15fa98613979";
# sha256 = "0vqahbrnr43lxanpziyrmzaqqb3cmyny8ry1xvmy2xyd1larzfrk";
# };
# };
# }
# {
# plugin = vimUtils.buildVimPlugin {
# name = "git-blame";
# src = fetchFromGitHub {
# "owner" = "zivyangll";
# "repo" = "git-blame.vim";
# "rev" = "9d144b7bed5d8f1c9259551768b7f3b3d1294917";
# "sha256" = "06zb5xcc59k25rpwl46j82fcqckiznmj97v6i0mwlb8jhqqrhy9j";
# };
# };
# }
# ]
# ++ (with pkgs.vimPlugins; [
# delimitMate
# vim-airline
# vim-airline-themes
# ctrlp
# vim-css-color
# rainbow_parentheses
# vim-colorschemes
# vim-colorstepper
# vim-signify
# fugitive
# vim-indent-guides
# UltiSnips
# fzfWrapper
# ncm2
# ncm2-bufword
# ncm2-path
# ncm2-tmux
# ncm2-ultisnips
# nvim-yarp
# LanguageClient-neovim
# Improved-AnsiEsc
# tabular
# # Nix
# vim-addon-nix
# tlib
# vim-addon-vim2nix
# # LaTeX
# vim-latex-live-preview
# vimtex
# # YAML
# vim-yaml
# # markdown
# vim-markdown
# vim-markdown-toc
# # misc syntax support
# vim-bazel
# maktaba
# ]);
# misc syntax support
vim-bazel
maktaba
]);
};
}

View file

@ -49,8 +49,8 @@ let g:ctrlp_custom_ignore = {
\ 'dir': '\v[\/]\.(git|hg|svn)$$',
\ 'file': '\v\.(exe|so|dll)$$',
\ }
"let g:ctrlp_max_files=0
"let g:ctrlp_max_depth=1000
let g:ctrlp_max_files=0
let g:ctrlp_max_depth=1000
"let g:ctrlp_match_func = { 'match': 'pymatcher#PyMatch' }
"let g:pydiction_location = '~/.vim/bundle/pydiction/complete-dict'

View file

@ -1,25 +1,21 @@
{ pkgs, lib, ... }:
{
pkgs,
lib,
...
}: {
programs.obs-studio = {
enable = true;
plugins =
builtins.map
(
plugin:
(plugin.overrideAttrs (attrs: {
meta = lib.mkMerge [
{ inherit (attrs) meta; }
{ meta.platforms = [ pkgs.stdenv.system ]; }
];
}))
)
(
with pkgs.obs-studio-plugins;
[
# wlrobs
obs-backgroundremoval
obs-pipewire-audio-capture
]
);
builtins.map (plugin: (plugin.overrideAttrs (attrs: {
meta = lib.mkMerge [
{inherit (attrs) meta;}
{meta.platforms = ["aarch64-linux"];}
];
})))
(with pkgs.obs-studio-plugins; [
# wlrobs
obs-backgroundremoval
obs-pipewire-audio-capture
]);
};
}

View file

@ -1,37 +0,0 @@
{ pkgs, repoFlake, ... }:
let
pkgsVscodium = import repoFlake.inputs.nixpkgs-vscodium { inherit (pkgs) system config; };
in
{
home.packages = [
pkgs.nil
pkgs.nixd
pkgs.nixfmt-rfc-style
# TODO: automate linking this
# 1. get the commit with: `codium --version`
# 2. create the binary directory: `mkdir -p /home/steveej/.vscodium-server/bin/c8ce3ba4bc6b30b3b10edc61481cb85b1d2396bc/bin/`
# 3. link the binary. this relies on the client-side setting `"remote.SSH.experimental.serverBinaryName": "openvscode-server"` : ln -s $(which openvscode-server) /home/steveej/.vscodium-server/bin/c8ce3ba4bc6b30b3b10edc61481cb85b1d2396bc/bin/
/*
e.g.:
```
(
set -e
export COMMIT=$(codium --version | rg '^[0-9a-f]{40}$')
ssh bm-hostkey0 "pkill -9 openvscode; rm -rf /home/steveej/.vscodium-server/bin/$COMMIT; mkdir -p /home/steveej/.vscodium-server/bin/$COMMIT/bin/; ln -s \$(which openvscode-server) /home/steveej/.vscodium-server/bin/$COMMIT/bin/"
)
```
*/
(pkgsVscodium.openvscode-server.overrideAttrs (attrs: {
src = repoFlake.inputs.openvscode-server;
version = "1.94.2";
yarnCache = attrs.yarnCache.overrideAttrs (_: {
outputHash = "sha256-89c6GYLT2RzHqwxBKegYqB6g5rEJ6/nH53cnfV7b0Tt=";
});
}))
pkgs.waypipe
];
}

View file

@ -1,5 +1,8 @@
{ repoFlake, pkgs, ... }:
{
repoFlake,
pkgs,
...
}: {
# required by pass-otp
# home.sessionVariables.PASSWORD_STORE_EXTENSIONS_DIR = "$HOME/.nix-profile/lib/password-store/extensions";
# home.sessionVariables.PASSWORD_STORE_ENABLE_EXTENSIONS = "true";
@ -7,6 +10,7 @@
home.packages = with pkgs; [
gnupg
pass
# broken on wayland
# rofi-pass

View file

@ -4,8 +4,7 @@
pkgs,
osConfig,
...
}:
let
}: let
libdecsync = pkgs.python3Packages.buildPythonPackage rec {
pname = "libdecsync";
version = "2.2.1";
@ -39,51 +38,50 @@ let
# pkgs.libxcrypt
];
propagatedBuildInputs = [
libdecsync
pkgs.python3Packages.setuptools
];
propagatedBuildInputs = [libdecsync pkgs.python3Packages.setuptools];
};
radicale-decsync = pkgs.radicale.overrideAttrs (old: {
propagatedBuildInputs = old.propagatedBuildInputs ++ [ radicale-storage-decsync ];
propagatedBuildInputs =
old.propagatedBuildInputs
++ [radicale-storage-decsync];
});
mkRadicaleService =
{ suffix, port }:
let
radicale-config = pkgs.writeText "radicale-config-${suffix}" ''
[server]
hosts = localhost:${builtins.toString port}
mkRadicaleService = {
suffix,
port,
}: let
radicale-config = pkgs.writeText "radicale-config-${suffix}" ''
[server]
hosts = localhost:${builtins.toString port}
[auth]
type = htpasswd
htpasswd_filename = ${osConfig.sops.secrets.radicale_htpasswd.path}
htpasswd_encryption = bcrypt
[auth]
type = htpasswd
htpasswd_filename = ${osConfig.sops.secrets.radicale_htpasswd.path}
htpasswd_encryption = bcrypt
[storage]
type = radicale_storage_decsync
filesystem_folder = ${config.xdg.dataHome}/radicale/radicale-${suffix}
decsync_dir = ${config.xdg.dataHome}/decsync/decsync-${suffix}
'';
in
{
systemd.user.services."radicale-${suffix}" = {
Unit.Description = "Radicale with DecSync (${suffix})";
Service = {
ExecStart = "${radicale-decsync}/bin/radicale -C ${radicale-config}";
Restart = "on-failure";
};
Install.WantedBy = [ "default.target" ];
[storage]
type = radicale_storage_decsync
filesystem_folder = ${config.xdg.dataHome}/radicale/radicale-${suffix}
decsync_dir = ${config.xdg.dataHome}/decsync/decsync-${suffix}
'';
in {
systemd.user.services."radicale-${suffix}" = {
Unit.Description = "Radicale with DecSync (${suffix})";
Service = {
ExecStart = "${radicale-decsync}/bin/radicale -C ${radicale-config}";
Restart = "on-failure";
};
Install.WantedBy = ["default.target"];
};
};
in
builtins.foldl' (sum: cur: lib.recursiveUpdate sum (mkRadicaleService cur)) { } [
{
suffix = "personal";
port = 5232;
}
{
suffix = "family";
port = 5233;
}
]
builtins.foldl' (sum: cur: lib.recursiveUpdate sum (mkRadicaleService cur)) {} [
{
suffix = "personal";
port = 5232;
}
{
suffix = "family";
port = 5233;
}
]

View file

@ -1,26 +1,21 @@
_:
let
passwords = import ../../variables/passwords.crypt.nix;
in
{
pkgs,
config,
...
}: let
passwords = import ../../variables/passwords.crypt.nix;
in {
services.gammastep = {
enable = true;
provider = "manual";
enableVerboseLogging = true;
inherit (passwords.location.stefan) longitude latitude;
temperature = {
# day = 6700;
day = 3000;
day = 6700;
night = 3000;
};
tray = true;
settings = {
general = {
adjustment-method = "wayland";
};
gammastep = {
# brightness-day = 1.0;
brightness-day = 0.5;
brightness-day = 1.0;
brightness-night = 0.5;
};
};

View file

@ -1,11 +1,18 @@
{ pkgs, packages', ... }:
{
pkgs,
config,
lib,
packages',
...
}:
# useful testing command:
# for i in `seq 0 10`; do nix shell nixpkgs#libnotify --command notify-send notifiiiiiii "$i"; sleep 1; done
let
inherit (import ../lib.nix { }) mkSimpleTrayService;
in
{
home.packages = [ packages'.salut ];
inherit (import ../lib.nix {}) mkSimpleTrayService;
in {
home.packages = [
packages'.salut
];
xdg.configFile."salut/config.ini" = {
enable = true;
@ -27,5 +34,7 @@ in
onChange = "${pkgs.systemd}/bin/systemctl --user restart salut";
};
systemd.user.services.salut = mkSimpleTrayService { execStart = "${packages'.salut}/bin/salut"; };
systemd.user.services.salut = mkSimpleTrayService {
execStart = "${packages'.salut}/bin/salut";
};
}

View file

@ -1,32 +1,34 @@
{
config,
pkgs,
nodeFlake,
repoFlake,
lib,
...
}:
let
pkgsVscodium = import repoFlake.inputs.nixpkgs-vscodium { inherit (pkgs) system config; };
in
{
}: let
pkgsVscodium = import repoFlake.inputs.nixpkgs-vscodium {inherit (pkgs) system config;};
in {
programs.vscode = {
enable = true;
package = pkgsVscodium.vscodium;
extensions =
with pkgsVscodium.vscode-extensions;
[
# TODO: how can i install (this) vsix(s) directly?
# (builtins.fetchurl {
# # https://open-vsx.org/extension/jeanp413/open-remote-ssh
# url = "https://open-vsx.org/api/jeanp413/open-remote-ssh/0.0.45/file/jeanp413.open-remote-ssh-0.0.45.vsix";
# sha256 = "1qc1qsahfx1nvznq4adplx63w5d94xhafngv76vnqjjbzhv991v2";
# })
]
++ (with pkgsVscodium.vscode-extensions; [
bbenoist.nix
eamodio.gitlens
mkhl.direnv
jnoortheen.nix-ide
tomoki1207.pdf
vscodevim.vim
# bbenoist.nix
jnoortheen.nix-ide
ms-vscode.theme-tomorrowkit
nonylene.dark-molokai-theme
ms-python.vscode-pylance
kamadorueda.alejandra
# TODO: these are not in nixpkgs
@ -37,95 +39,25 @@ in
# TODO: not compatible with vscodium
# ms-vscode-remote.remote-ssh
]
++ (
let
] ++ (let
extensions = repoFlake.inputs.nix-vscode-extensions.extensions.${pkgs.system};
in
with extensions.vscode-marketplace;
with extensions.vscode-marketplace-release;
[
in (with extensions.vscode-marketplace; [
tamasfe.even-better-toml
serayuzgur.crates
rust-lang.rust-analyzer
swellaby.vscode-rust-test-adapter
serayuzgur.crates
rust-lang.rust-analyzer
swellaby.vscode-rust-test-adapter
tamasfe.even-better-toml
golang.go
jeff-hykin.better-go-syntax
blueglassblock.better-json5
nefrob.vscode-just-syntax
# fabianlauer.vs-code-xml-format
bierner.emojisense
]
)
++ (
let
nix4vscodeToml = pkgs.writeText "nix4vscode.toml" ''
vscode_version = "${config.programs.vscode.package.version}"
[[extensions]]
publisher_name = "FelixZeller"
extension_name = "markdown-oxide"
[[extensions]]
publisher_name = "ibecker"
extension_name = "treefmt-vscode"
[[extensions]]
publisher_name = "AntiAntiSepticeye"
extension_name = "vscode-color-picker"
# [[extensions]]
# publisher_name = "nefrob"
# extension_name = "vscode-just-syntax"
[[extensions]]
publisher_name = "fabianlauer"
extension_name = "vs-code-xml-format"
'';
nix4vscodeNix =
pkgs.runCommand "nix4vscode.nix"
{
# nix4vscode needs internet access
__noChroot = true;
requiredSystemFeatures = [ "recursive-nix" ];
buildInputs = [
pkgs.nix
pkgs.cacert
(pkgs.callPackage "${repoFlake.inputs.nix4vscode.outPath}/nix/package.nix" { })
# pkgs.strace
];
# outputHashAlgo = "sha256";
# outputHashMode = "recursive";
# outputHash = lib.fakeSha256;
}
''
# set -x
# export RUST_BACKTRACE=full
# export RUST_LOG=trace
export HOME=$(mktemp -d)
# strace -ffZyyY
nix4vscode ${nix4vscodeToml} > $out
'';
nix4vscodeExtensions = builtins.removeAttrs (pkgs.callPackage nix4vscodeNix { }) [
"override"
"overrideDerivation"
];
nix4vscodeExtensions' = lib.attrsets.mapAttrsToList (
_: v: builtins.head (builtins.attrValues v)
) nix4vscodeExtensions;
in
nix4vscodeExtensions'
);
golang.go
jeff-hykin.better-go-syntax
])));
mutableExtensionsDir = true;
};
home.packages = [
pkgs.nixpkgs-fmt
pkgs.alejandra
pkgs.nil
pkgs.nixfmt-rfc-style
];
}
# TODO: automate
@ -202,3 +134,4 @@ in
# xyz.plsql-language
# yzane.markdown-pdf
# zxh404.vscode-proto3

View file

@ -1,5 +1,6 @@
#custom-cputemp {
padding: 0 10px;
background-color: #f0932b;
color: #ffffff;
padding: 0 10px;
background-color: #f0932b;
color: #ffffff;
}

View file

@ -1,5 +1,9 @@
{ pkgs, repoFlake, ... }:
{
pkgs,
config,
repoFlake,
...
}: {
home.packages = [
# required by any bar that has a tray plugin
pkgs.libappindicator-gtk3
@ -8,18 +12,17 @@
programs.waybar = {
enable = true;
package =
repoFlake.inputs.nixpkgs-wayland.outputs.packages.${pkgs.stdenv.hostPlatform.system}.waybar;
style = pkgs.lib.readFile "${pkgs.waybar.src}/resources/style.css" + pkgs.lib.readFile ./waybar.css;
package = repoFlake.inputs.nixpkgs-wayland.outputs.packages.${pkgs.stdenv.hostPlatform.system}.waybar;
style =
pkgs.lib.readFile "${pkgs.waybar.src}/resources/style.css"
+ pkgs.lib.readFile ./waybar.css;
systemd.enable = true;
settings = {
mainBar = {
layer = "top";
position = "bottom";
height = 30;
output =
# hide the bar on HEADDLESS displays as i use them only for screensharing
(builtins.genList (i: "!HEADLESS-${builtins.toString i}") 99) ++ [ "*" ];
output = ["*"];
# output = [
# "eDP-1"
# "DP-*"

View file

@ -3,29 +3,27 @@
lib,
pkgs,
...
}:
let
just-plugin =
let
plugin_file = pkgs.writeText "_just" ''
#compdef just
#autload
}: let
just-plugin = let
plugin_file = pkgs.writeText "_just" ''
#compdef just
#autload
alias justl="\just --list"
alias juste="\just --evaluate"
alias justl="\just --list"
alias juste="\just --evaluate"
local subcmds=()
local subcmds=()
while read -r line ; do
if [[ ! $line == Available* ]] ;
then
subcmds+=(''${line/[[:space:]]*\#/:})
fi
done < <(just --list)
while read -r line ; do
if [[ ! $line == Available* ]] ;
then
subcmds+=(''${line/[[:space:]]*\#/:})
fi
done < <(just --list)
_describe 'command' subcmds
'';
in
_describe 'command' subcmds
'';
in
pkgs.stdenv.mkDerivation {
name = "just-completions";
version = "0.1.0";
@ -37,8 +35,7 @@ let
chmod --recursive a-w $out
'';
};
in
{
in {
programs.zsh = {
enable = true;
@ -49,59 +46,56 @@ in
# will be called again by oh-my-zsh
enableCompletion = false;
enableAutosuggestions = true;
initExtra =
let
inNixShell = ''$([[ -n "$IN_NIX_SHELL" ]] && printf " 🐚")'';
in
''
if test ! -n "$TMPDIR" -a -z "$TMPDIR"; then
unset TMPDIR
fi
initExtra = let
inNixShell = ''$([[ -n "$IN_NIX_SHELL" ]] && printf " 🐚")'';
in ''
if test ! -n "$TMPDIR" -a -z "$TMPDIR"; then
unset TMPDIR
fi
if test ! -n "$TMP" -a -z "$TMP"; then
unset TMP
fi
if test ! -n "$TMP" -a -z "$TMP"; then
unset TMP
fi
PROMPT='%F{%(!.red.green)}%n%f@%m %(?.%F{green}%f.%F{red} ($?%))%f %F{blue}%~%f${inNixShell}%F{magenta}$(git_prompt_info)%f$prompt_newline%_%F{%(!.red.green)}$(prompt_char)%f '
RPROMPT=""
PROMPT='%F{%(!.red.green)}%n%f@%m %(?.%F{green}%f.%F{red} ($?%))%f %F{blue}%~%f${inNixShell}%F{magenta}$(git_prompt_info)%f$prompt_newline%_%F{%(!.red.green)}$(prompt_char)%f '
RPROMPT=""
# Automatic rehash
zstyle ':completion:*' rehash true
# Automatic rehash
zstyle ':completion:*' rehash true
if [ -f $HOME/.shrc.d/sh_aliases ]; then
. $HOME/.shrc.d/sh_aliases
fi
if [ -f $HOME/.shrc.d/sh_aliases ]; then
. $HOME/.shrc.d/sh_aliases
fi
${
if builtins.hasAttr "homeshick" pkgs then
''
source ${pkgs.homeshick}/homeshick.sh
fpath=(${pkgs.homeshick}/completions $fpath)
''
else
""
}
${
if builtins.hasAttr "homeshick" pkgs
then ''
source ${pkgs.homeshick}/homeshick.sh
fpath=(${pkgs.homeshick}/completions $fpath)
''
else ""
}
# Disable intercepting of ctrl-s and ctrl-q as flow control.
stty stop ''' -ixoff -ixon
# Disable intercepting of ctrl-s and ctrl-q as flow control.
stty stop ''' -ixoff -ixon
# don't cd into directories when executed
unsetopt AUTO_CD
# don't cd into directories when executed
unsetopt AUTO_CD
# print lines without termination
setopt PROMPT_CR
setopt PROMPT_SP
export PROMPT_EOL_MARK=""
# print lines without termination
setopt PROMPT_CR
setopt PROMPT_SP
export PROMPT_EOL_MARK=""
${lib.optionalString config.services.gpg-agent.enable ''
export SSH_AUTH_SOCK="$XDG_RUNTIME_DIR/gnupg/S.gpg-agent.ssh"
''}
${lib.optionalString config.services.gpg-agent.enable ''
export SSH_AUTH_SOCK="$XDG_RUNTIME_DIR/gnupg/S.gpg-agent.ssh"
''}
${lib.optionalString config.programs.neovim.enable ''
export EDITOR="nvim"
''}
'';
${lib.optionalString config.programs.neovim.enable ''
export EDITOR="nvim"
''}
'';
plugins = [
{
@ -134,10 +128,7 @@ in
oh-my-zsh = {
enable = true;
theme = "tjkirch";
plugins = [
"git"
"sudo"
];
plugins = ["git" "sudo"];
};
};
}

View file

@ -1,8 +1,7 @@
{ lib, ... }:
{
{lib, ...}: {
options.flake.colmena = lib.mkOption {
# type = lib.types.attrsOf lib.types.unspecified;
type = lib.types.raw;
default = { };
default = {};
};
}

View file

@ -1,37 +1,38 @@
{ pkgs, ... }:
{
inputs',
system,
config,
lib,
pkgs,
...
}: {
packages = {
myPython = pkgs.python310.withPackages (
ps:
myPython = pkgs.python310.withPackages (ps:
with ps;
[
pep8
yapf
flake8
# autopep8 (broken)
# pylint (broken)
ipython
llfuse
dugong
defusedxml
wheel
pip
virtualenv
cffi
# pyopenssl
urllib3
# mistune (insecure)
sympy
[
pep8
yapf
flake8
# autopep8 (broken)
# pylint (broken)
ipython
llfuse
dugong
defusedxml
wheel
pip
virtualenv
cffi
# pyopenssl
urllib3
# mistune (insecure)
sympy
flask
flask
pyaml
requests
]
++ [
pkgs.pypi2nix
pkgs.libffi
]
);
pyaml
requests
]
++ [pkgs.pypi2nix pkgs.libffi]);
};
}

View file

@ -1,12 +1,14 @@
# WARN: this file will get overwritten by $ cachix use <name>
{ lib, ... }:
let
{
pkgs,
lib,
...
}: let
folder = ./cachix;
toImport = name: _value: folder + ("/" + name);
toImport = name: value: folder + ("/" + name);
filterCaches = key: value: value == "regular" && lib.hasSuffix ".nix" key;
imports = lib.mapAttrsToList toImport (lib.filterAttrs filterCaches (builtins.readDir folder));
in
{
in {
inherit imports;
nix.settings.substituters = [ "https://cache.nixos.org/" ];
nix.settings.substituters = ["https://cache.nixos.org/"];
}

View file

@ -1,6 +1,8 @@
{
nix = {
settings.substituters = [ "https://nixpkgs-wayland.cachix.org" ];
settings.substituters = [
"https://nixpkgs-wayland.cachix.org"
];
settings.trusted-public-keys = [
"nixpkgs-wayland.cachix.org-1:3lwxaILxMRkVhehr5StQprHdEo4IrE8sRho9R9HOLYA="
];

View file

@ -0,0 +1,87 @@
{
hostAddress,
localAddress,
containerBackupCfg,
sshPort ? containerBackupCfg.portInt,
autoStart ? false,
}: {
config = {
config,
pkgs,
lib,
...
}: {
system.stateVersion = "22.05"; # Did you read the comment?
imports = [../profiles/containers/configuration.nix];
networking.firewall.enable = false;
# services.ddclientovh = {
# enable = true;
# domain = containerBackupCfg.addr;
# };
services.openssh.enable = true;
users.extraUsers."${containerBackupCfg.user}" = {
uid = 2000;
group = containerBackupCfg.group;
shell = pkgs.bashInteractive;
home = "/${containerBackupCfg.targetPath}";
openssh.authorizedKeys.keys = [
"ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQDNI3H0BRSYOZ/MbTs9J80doJwSd1HymFOP5quNt0J48vxZ5FPVrT2FHpQiNrCcYbCKRsU4X8AiGUHiXC0PapQQ3JDkqp6WZoqBNDx6BI7RadyH1TqVQPlou3pQmCAogzfBInruR53YTDmQqXiPwfM0okPOXgiBNjDfZXOX4+CyUfkmZZwASoicTInqWGkn1sFnh4tyXIkgWflg0njlVmfkVvH71+evvKLYHtoNpVXazkQ0SXbyuW5f3mSta7TNkpC3HbBm+4n+WxYGySrlRLWQhTo+aoWUKk9h5zvECDNpwRtbqzt+bA9nKrdg180ceu8hruwvWNiC6PPA2GW9Z1+VKROviGu1C3dliE/pPCBtK+ZoRVv2CGE+pmAuQsB9Nif9tk5tY6HJhuLNxKYiMfQkiLsDYv6KdZXUIVK/4BIDkZuQNnjhdOQBLnea0ANOhutA9gnjxnsd3UT6ovfazg5gud7n3u4yBtzjTkRrqWZ63eM1NmUVOgMWHQ715pV+hJfOFGqzRBEe3g/p3bWNgpROBYJbG1H8l9DN7emG4FGWsb1HeNFwQ5lS0Zsezb7qzahr4vSmHNugVw7w8ONt5dPbPI9wQnWvkkuHH76P/NYy6OC6lHrN1rXyA1okqdPr06YAZnCot+Pqdgn/ijxgp06J3dtkhin+Q7PoQbGff3ERIw== bkp"
];
packages = with pkgs; [btrfs-progs];
isSystemUser = true;
};
security.sudo = {
enable = true;
extraRules = [
{
users = ["bkp"];
commands = [
{
command = "/etc/profiles/per-user/bkp/bin/btrfs";
options = ["NOPASSWD"];
}
{
command = "/run/current-system/sw/bin/readlink";
options = ["NOPASSWD"];
}
{
command = "/run/current-system/sw/bin/test";
options = ["NOPASSWD"];
}
];
}
];
};
};
inherit autoStart;
bindMounts = {
"/${containerBackupCfg.targetPath}" = {
hostPath = "/var/lib/container-volumes/backup-target";
isReadOnly = false;
};
};
extraFlags = ["--resolv-conf=bind-host"];
privateNetwork = true;
forwardPorts = [
{
# ssh
containerPort = 22;
hostPort = sshPort;
protocol = "tcp";
}
];
inherit hostAddress localAddress;
}

View file

@ -5,107 +5,88 @@
subvolumes,
targetPathSuffix ? "",
autoStart ? false,
}:
let
}: let
passwords = import ../../variables/passwords.crypt.nix;
subvolumeParentDir = "/var/lib/container-volumes";
in
{
config =
{ pkgs, ... }:
{
system.stateVersion = "20.03"; # Did you read the comment?
in {
config = {pkgs, ...}: {
system.stateVersion = "20.03"; # Did you read the comment?
imports = [ ../profiles/containers/configuration.nix ];
imports = [../profiles/containers/configuration.nix];
environment.systemPackages = with pkgs; [
btrfs-progs
btrbk
];
environment.systemPackages = with pkgs; [btrfs-progs btrbk];
networking.firewall.enable = true;
networking.firewall.enable = true;
systemd.services."bkp-sync" = {
enable = true;
description = "bkp-sync service";
systemd.services."bkp-sync" = {
enable = true;
description = "bkp-sync service";
serviceConfig = {
Type = "oneshot";
};
serviceConfig = {Type = "oneshot";};
after = [ "bkp-run.service" ];
after = ["bkp-run.service"];
requires = [ "bkp-run.service" ];
requires = ["bkp-run.service"];
path = with pkgs; [ utillinux ];
script = ''
set -x
true
path = with pkgs; [utillinux];
script = ''
set -x
true
'';
};
systemd.services."bkp-run" = {
enable = true;
description = "bkp-run";
serviceConfig = {Type = "oneshot";};
partOf = ["bkp-sync.service"];
path = with pkgs; [btrfs-progs btrbk coreutils];
script = let
btrbkConf = pkgs.writeText "cfg" ''
timestamp_format long
ssh_identity ${passwords.storage.backupTarget.keyPath}
ssh_user ${passwords.storage.backupTarget.user}
ssh_compression no
backend_remote btrfs-progs-sudo
compat_remote busybox
btrfs_commit_delete each
snapshot_create onchange
snapshot_preserve_min latest
snapshot_preserve 7d 4w
target_preserve_min latest
target_preserve 7d 4w 12m *y
volume ${subvolumeParentDir}
target ${passwords.storage.backupTarget.target}/container-volumes/${targetPathSuffix}
${builtins.foldl' (sum: elem: sum + " subvolume " + elem + "\n") ""
subvolumes}
'';
};
in ''
#! ${pkgs.bash}/bin/bash
set -Eeuxo pipefail
systemd.services."bkp-run" = {
enable = true;
description = "bkp-run";
btrbk -c ${btrbkConf} --progress ''${@:-run}
'';
};
serviceConfig = {
Type = "oneshot";
};
partOf = [ "bkp-sync.service" ];
path = with pkgs; [
btrfs-progs
btrbk
coreutils
];
script =
let
btrbkConf = pkgs.writeText "cfg" ''
timestamp_format long
ssh_identity ${passwords.storage.backupTarget.keyPath}
ssh_user ${passwords.storage.backupTarget.user}
ssh_compression no
backend_remote btrfs-progs-sudo
compat_remote busybox
btrfs_commit_delete each
snapshot_create onchange
snapshot_preserve_min latest
snapshot_preserve 7d 4w
target_preserve_min latest
target_preserve 7d 4w 12m *y
volume ${subvolumeParentDir}
target ${passwords.storage.backupTarget.target}/container-volumes/${targetPathSuffix}
${builtins.foldl' (sum: elem: sum + " subvolume " + elem + "\n") "" subvolumes}
'';
in
''
#! ${pkgs.bash}/bin/bash
set -Eeuxo pipefail
btrbk -c ${btrbkConf} --progress ''${@:-run}
'';
};
systemd.timers."bkp" = {
description = "Timer to trigger bkp periodically";
enable = true;
wantedBy = [
"timer.target"
"multi-user.target"
];
timerConfig = {
# Obtained using `systemd-analyze calendar "Wed 23:00"`
# OnCalendar = "Wed *-*-* 23:00:00";
OnStartupSec = "1m";
Unit = "bkp-sync.service";
OnUnitInactiveSec = "2h";
Persistent = "true";
};
systemd.timers."bkp" = {
description = "Timer to trigger bkp periodically";
enable = true;
wantedBy = ["timer.target" "multi-user.target"];
timerConfig = {
# Obtained using `systemd-analyze calendar "Wed 23:00"`
# OnCalendar = "Wed *-*-* 23:00:00";
OnStartupSec = "1m";
Unit = "bkp-sync.service";
OnUnitInactiveSec = "2h";
Persistent = "true";
};
};
};
inherit autoStart;
@ -133,10 +114,10 @@ in
}
];
extraFlags = [ "--resolv-conf=bind-host" ];
extraFlags = ["--resolv-conf=bind-host"];
privateNetwork = true;
forwardPorts = [ ];
forwardPorts = [];
inherit hostAddress localAddress;
}

View file

@ -1,210 +1,194 @@
{
specialArgs,
hostBridge,
repoFlake,
hostAddress,
localAddress,
imapsPort ? 993,
sievePort ? 4190,
autoStart ? false,
}:
{
inherit specialArgs;
config =
{
pkgs,
config,
repoFlake,
...
}:
{
system.stateVersion = "22.05"; # Did you read the comment?
}: {
config = {
pkgs,
config,
lib,
...
}: {
system.stateVersion = "21.11"; # Did you read the comment?
imports = [
../profiles/containers/configuration.nix
imports = [
../profiles/containers/configuration.nix
repoFlake.inputs.sops-nix.nixosModules.sops
../profiles/common/user.nix
];
repoFlake.inputs.sops-nix.nixosModules.sops
../profiles/common/user.nix
];
networking.firewall.allowedTCPPorts = [
imapsPort
sievePort
];
# FIXME: find out how to use the `defaultSopsFile` so i don't have to specify each secret separately
# sops.defaultSopsFile = ./mailserver_secrets.yaml;
# FIXME: find out how to use the `defaultSopsFile` so i don't have to specify each secret separately
# sops.defaultSopsFile = ./mailserver_secrets.yaml;
sops.age.sshKeyPaths = [ "/etc/ssh/ssh_host_ed25519_key" ];
sops.secrets.email_mailStefanjunkerDe = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_mailStefanjunkerDeHetzner = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_schtifATwebDe = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_dovecot_steveej = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
# TODO: switch to something other than ddclient as it's no longer maintained
# TODO: switch to a let's encrypt certificate
sops.secrets.dovecotSslServerCert = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
sops.secrets.dovecotSslServerKey = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
services.dovecot2 = {
enable = true;
modules = [ pkgs.dovecot_pigeonhole ];
protocols = [ "sieve" ];
enableImap = true;
enableLmtp = true;
enablePAM = true;
showPAMFailure = true;
mailLocation = "maildir:~/.maildir";
sslServerCert = config.sops.secrets.dovecotSslServerCert.path;
sslServerKey = config.sops.secrets.dovecotSslServerKey.path;
#configFile = "/etc/dovecot/dovecot2_manual.conf";
extraConfig = ''
auth_mechanisms = cram-md5 digest-md5
auth_verbose = yes
passdb {
driver = passwd-file
args = scheme=CRYPT username_format=%u /etc/dovecot/users
}
protocol lda {
postmaster_address = "mail@stefanjunker.de"
mail_plugins = $mail_plugins sieve
}
protocol imap {
mail_max_userip_connections = 64
}
'';
};
environment.etc."dovecot/users".source = config.sops.secrets.email_dovecot_steveej.path;
systemd.services.steveej-getmail-stefanjunker = {
enable = true;
wantedBy = [ "multi-user.target" ];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
serviceConfig.RestartSec = 600;
serviceConfig.Restart = "always";
description = "Getmail service";
path = [ pkgs.getmail6 ];
script =
let
rc = pkgs.writeText "mailATstefanjunker.de.getmail.rc" ''
[options]
verbose = 1
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = ssl0.ovh.net
port = 993
username = mail@stefanjunker.de
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_mailStefanjunkerDe.path}")
mailboxes = ('INBOX',)
[destination]
type = MDA_external
path = ${pkgs.dovecot}/libexec/dovecot/dovecot-lda
'';
in
''
getmail --idle=INBOX --rcfile=${rc}
'';
};
systemd.services.steveej-getmail-stefanjunker-hetzner = {
enable = true;
wantedBy = [ "multi-user.target" ];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
serviceConfig.RestartSec = 60;
serviceConfig.Restart = "always";
description = "Getmail service";
path = [ pkgs.getmail6 ];
script =
let
rc = pkgs.writeText "mailATstefanjunker.de.getmail.rc" ''
[options]
verbose = 2
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = mail.your-server.de
port = 993
username = mail@stefanjunker.de
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_mailStefanjunkerDeHetzner.path}")
mailboxes = ('INBOX',)
[destination]
type = MDA_external
path = ${pkgs.dovecot}/libexec/dovecot/dovecot-lda
'';
in
''
getmail --rcfile=${rc} --idle=INBOX
'';
};
systemd.services.steveej-getmail-webde = {
enable = true;
wantedBy = [ "multi-user.target" ];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
description = "Getmail service";
path = [ pkgs.getmail6 ];
serviceConfig.RestartSec = 1000;
serviceConfig.Restart = "always";
script =
let
rc = pkgs.writeText "schtifATweb.de.getmail.rc" ''
[options]
verbose = 1
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = imap.web.de
port = 993
username = schtif
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_schtifATwebDe.path}")
mailboxes = ('INBOX',)
[destination]
type = Maildir
path = ~/.maildir/
'';
in
''
getmail --rcfile=${rc} --idle=INBOX
'';
};
sops.age.sshKeyPaths = ["/etc/ssh/ssh_host_ed25519_key"];
sops.secrets.email_mailStefanjunkerDe = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_mailStefanjunkerDeHetzner = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_schtifATwebDe = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.steveej.name;
};
sops.secrets.email_dovecot_steveej = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
# TODO: switch to something other than ddclient as it's no longer maintained
# TODO: switch to a let's encrypt certificate
sops.secrets.dovecotSslServerCert = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
sops.secrets.dovecotSslServerKey = {
sopsFile = ./mailserver_secrets.yaml;
owner = config.users.users.dovecot2.name;
};
services.dovecot2 = {
enable = true;
modules = [pkgs.dovecot_pigeonhole];
protocols = ["sieve"];
enableImap = true;
enableLmtp = true;
enablePAM = true;
showPAMFailure = true;
mailLocation = "maildir:~/.maildir";
sslServerCert = config.sops.secrets.dovecotSslServerCert.path;
sslServerKey = config.sops.secrets.dovecotSslServerKey.path;
#configFile = "/etc/dovecot/dovecot2_manual.conf";
extraConfig = ''
auth_mechanisms = cram-md5 digest-md5
auth_verbose = yes
passdb {
driver = passwd-file
args = scheme=CRYPT username_format=%u /etc/dovecot/users
}
protocol lda {
postmaster_address = "mail@stefanjunker.de"
mail_plugins = $mail_plugins sieve
}
protocol imap {
mail_max_userip_connections = 64
}
'';
};
environment.etc."dovecot/users".source = config.sops.secrets.email_dovecot_steveej.path;
systemd.services.steveej-getmail-stefanjunker = {
enable = true;
wantedBy = ["multi-user.target"];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
serviceConfig.RestartSec = 600;
serviceConfig.Restart = "always";
description = "Getmail service";
path = [pkgs.getmail6];
script = let
rc = pkgs.writeText "mailATstefanjunker.de.getmail.rc" ''
[options]
verbose = 1
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = ssl0.ovh.net
port = 993
username = mail@stefanjunker.de
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_mailStefanjunkerDe.path}")
mailboxes = ('INBOX',)
[destination]
type = MDA_external
path = ${pkgs.dovecot}/libexec/dovecot/dovecot-lda
'';
in ''
getmail --idle=INBOX --rcfile=${rc}
'';
};
systemd.services.steveej-getmail-stefanjunker-hetzner = {
enable = true;
wantedBy = ["multi-user.target"];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
serviceConfig.RestartSec = 60;
serviceConfig.Restart = "always";
description = "Getmail service";
path = [pkgs.getmail6];
script = let
rc = pkgs.writeText "mailATstefanjunker.de.getmail.rc" ''
[options]
verbose = 2
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = mail.your-server.de
port = 993
username = mail@stefanjunker.de
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_mailStefanjunkerDeHetzner.path}")
mailboxes = ('INBOX',)
[destination]
type = MDA_external
path = ${pkgs.dovecot}/libexec/dovecot/dovecot-lda
'';
in ''
getmail --rcfile=${rc} --idle=INBOX
'';
};
systemd.services.steveej-getmail-webde = {
enable = true;
wantedBy = ["multi-user.target"];
serviceConfig.User = "steveej";
serviceConfig.Group = "dovecot2";
description = "Getmail service";
path = [pkgs.getmail6];
serviceConfig.RestartSec = 1000;
serviceConfig.Restart = "always";
script = let
rc = pkgs.writeText "schtifATweb.de.getmail.rc" ''
[options]
verbose = 1
read_all = 0
delete_after = 30
[retriever]
type = SimpleIMAPSSLRetriever
server = imap.web.de
port = 993
username = schtif
password_command = ("${pkgs.coreutils}/bin/cat", "${config.sops.secrets.email_schtifATwebDe.path}")
mailboxes = ('INBOX',)
[destination]
type = Maildir
path = ~/.maildir/
'';
in ''
getmail --rcfile=${rc} --idle=INBOX
'';
};
};
inherit autoStart;
@ -219,6 +203,8 @@
};
};
# extraFlags = ["--resolv-conf=bind-host"];
privateNetwork = true;
forwardPorts = [
{
@ -236,5 +222,5 @@
}
];
inherit hostBridge hostAddress localAddress;
inherit hostAddress localAddress;
}

View file

@ -7,37 +7,37 @@ dovecotSslServerCert: ENC[AES256_GCM,data:ylK0IIj2vdY0mXOqSgA5zYmFYGote/uMtDWy2r
dovecotSslServerKey: ENC[AES256_GCM,data:KYpQZbioLGrp/6R6j/c4uJhBpoDT2aj7UffQQug8Otzr/0rk51tavsjg4YRQGIv+ZpFYpWAuHbhW4O8AsRgpi0AX3hKsZICEdNubfK5zfd+SInXveaVFbHHjOuzcqftraUrqx9APu+omk4LlpxpWTbj/bAcRnRBn0C093AeJNi1giaCZd4NxmmkYqwYzrjUc6LYHvICEnjA87ZVpeOKE/6B2Ng5QWDKhZNmjy7YDXAk4DS+P2grLmoGvnz6ubtaypSzaKXYTFz/uxEvtCCPlIaJHm3Nz0i0j1rjX3S/w3c26zuIFtwCmAQzGnHyQwbx7ILwCXfnyQnpM7+R5+fxcYvcK2GEJyTGzg/JFa++TI1YO+wpknjzxK3Sa8aX0pUbx/TEjnY3+tRnx7YNuih2ZNZrPHy8uJJtO9Aef84Sq5vLQG5n1/ya0pVhjCbs1pgpeK/qT3ikLbkcJg6NxAq3hqqQdR4TTkZBwKLVfzcMXLDZB0GphhVvtO0W7afRCE+nA/FPDT2NN6WLD15cN5F8w6USi0iQlwFb+TE8nt1ghhoGmwCMx+lX1Bk/jdIlYtJ62T8+T3nRVJ6ZRlUa1rkbAADaWZVvLR2/ylaEkeYFo/CC6lUg4DWPCVoGFxaWaU+ZaIDjbiYcqGQFBwq8JZ44hAOyJQpb7N1zgDVyPh/xr+ukmjutFuu97FY55VTn+8eipRiR4TZpPRH+KvB/FmlLNaim76YZCRH9Dv2ENbz9fXpWv7P+yh06+ci9HKvjNAzR6NRr368tK2srEEhWzFv+nAsRetzc2VcfwNMcg5/mvlWHVZSmONXC5adEo/W5XgJgUnH/fkz5IRPY/1iteq8PTCPUkubzF+qT2+suzEDnvgXlaKsqHkrk+n8YySl+GRABnasmnBYdb8vboDM41ptw3PXDoL+l07o6KxTwPOWWl9BVNMT8VzL7gAl+dlxjkEUSqn53OrsYDluxefBa3c0rfvk8CCvOMjgLkagK9O+VavqJEo00zd3f0ZzMcIoRebuDzYILw3DTrG/qyLXGsRoybBr+qcuSVBzM5RnjcToFJO4W/0EIdH1drZmqHdNgSNwPPRSNCivrhV25syUCrTee/xkDVUr47z67pK/5Mh0ewlwq0hcl/dBoA0YP/PptntK0CHfistD8chNtdMk3PyzqSiFaDPQ3T4wdc3zTNUjXeQ5643k5weJXFPg4tUuCCa8HxUJHd5sLnNY0OaRBwh2SLkQlcXYFQDzVHSoVscR3tf+57L7aF2hVQT2QtJKdZQjOyMg5YK0UlVc3tkyPZzyjOVaP7eTCRKwXI1NminHmmy1ZzZ+w+8+oX8cfvE9HdbqDoDp0MnkicS0+5S0lZwkRWrjUx/gS4aMWLbCHUQHY8wm+fmyDLJ/oI4ukdUI5YLOutlCsIY+aotnVMoORgdd/EPeZVYJmci/pvMjPF9Eard0aD4rLA7z/HwGgc3VEGmNluE+20BXO3bFIqwa9tzMqzOJB0qglP35MjVGiUe6Svq13DAmSOnzN+WqcVbTMJG8J1bwKqvmaN8AEpO0zU94ZhHspUtGyQQ0D6sMsw9jqJ1WyLE7aXeFR6OHrpw3DC2mCpr/qX8QFsveeyB83Za2+CuVVi2sqGAKYzkwlUPkeuaxfBak0apwJsF2trT1uMvPOuIda8k4XhtYLxah2BDJZIoMqUVz2xcN4OuW8bdSX/lepsyZZO34VEQDLBa2dxCCHJmCKf6io/0YlswNKGDQh+DI935KTdqBnHSJ9IjvADQuu+K37aS0L9V0ZLXiM5SBQtbB7kQpHjvivq97ru7QpFqJf8HCl1vDs4gJ/NV+J0+CX6dQTQOtHvwxD2CPGiiSv40ycoJAcwiqTh5T+hRPtca6bSes/jGN5iQjfLCRbwvL/ItLLAK3F2cEIdKZnfhJkdEAIwWFLvR4R5I7ZcCK5GgKz5dPROup8BAONA8XxcJWXaXV0YkfEmCDbZYMFC7pcx4NAnGp881RyAaG/HlstBHHVagpP2fwZ8K0J/2KPillOq/Die+vNc2++hx4EuftvNkZhSd+7zIYNKHQd0M4Ea74flgmmW5lG73bE1BkhVd2DsgEDihH19/vJjFH4PxKINKp0ij4jMyq9w+WsGiUqSDaQz/MZJ8wjzaSjvmSj4qlOAitr/s3f041e77rMb0W2ieCtYEy7IsebIqIWgKn/crm5FhyUtBCPEqFZgAKS313bXUio8LktqXCrZjZ0ZG8DmQG6hnK4PstKlIUQoNuFnb8Bp1zDgY4i2hb6Zmu7NnqnOaJJTjSGwaZOav0oMousn67BuFtwoMaGp+OjCopZ3HPfg19usnjvWpOgccXWYlQc0HOlGXUq+otKlXtQwAjUvz50GmV+lY3t4rpCgqk+pj9iH62xuzDQ01FOXl+v3Ehnw97mNJk9YarueG0Hl/1f6dhwXnjeEv35LLyWUjQolOoYgycEkgQ/cCCOSm7zgK1VT0oTLFISai8IG0qDP9HCszteHZhp+y4bsXQfAJTY11QLr7hx9/nQmVlHksDN5Wsno4wbkT+D2xb5EaDU2RBqZfTVcbRBWRtAhQcRPxdaUXyI7oKEaFg8fvQZ8wK/Ae+L18ub+Latb5W69dUVT6I13tPleXDl1oen9BXzaX7sygSpY4lJoXlu+SCKyNTMrC36PrB39QUWosw03ZsiKT5xjgN5+1m32yv4cg8lAwNCR4xxShrnhSbZ328yifaAuTnSawZmUGBVxPx4glVcvNUOXW2UvVtmeKU0SG1E+UGBAq7/UfaadMM7BsjyaaKpBa/tXZTm0rn8UiFqujvgNjQ3F/3ybRdlO5d6eMI9Na+1gqg6qxYSGR0H0wAdPhtyGRxpumehAQGeMKd49Sg6jspaf3NAjjuZ0Yp+eJV9652WqVZ7xtCNqRURV353h+XPGR+ZZ9siHRDQ+NcbxPkfbHw0/RTvZvEIdaDi5+DLh6tgIxMEtOpwTlfFrOUDaIcmWvzk92VtBFuafvoGzTipryTnMszjCsUTvyEPN8jPd6r8UmOFGXF2aVNksmn/bI97i4s1kYLgY8XsEOyx+Q9pUTkTEMn2JWgnEcSOAtaX1ZskHnfueKzUPb+/YWb+z8SNCgnUqHqa42qBqwlhdshzYhhfKhEisUptirzzp1kcbyHrug5PzHxh8Qri2pjHxSHYQ5sjig6K6B1YEuHP6uo19fL6BdgGlhKroiOF/6TMAcE9V3+yqvDdsW/IC0QXLHIBKC7wlDgLc25ltGogD/76P6tViDAb6+HNSSXJO056Ovq0z2BrXhnq1AmWa99mVnOLJwafRWPZC,iv:XxnAsh6yx9gICi3N6oTttpGXvguGZImWNIMp9srDJLM=,tag:M9gFSD5PNIfoCLet6Vy6QA==,type:str]
hetznerDnsApiToken: ENC[AES256_GCM,data:JfL4Xg9TZu4Og35g0SwfrI1uxiqgdFa7p5AQcfiPwLY=,iv:yOak3uXX7CNglu8O2UW/1sOI7BGZxpRQAFJCvRbzU0Y=,tag:6orkQIy7BxACziLWpYoS5Q==,type:str]
sops:
kms: []
gcp_kms: []
azure_kv: []
hc_vault: []
age:
- recipient: age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBWaE9nNytUbXhWeWZYWndn
R3pMV3N1NjJPK2gzUDl2YitxWEU4NUFPRUJ3Cm1tMGhGcU56bSs5SUIzRmhqVHN2
dXIzYlkvS1JnWnladGdXTnRKMXNOWncKLS0tIGhyRFhFV1VRVXVYN1pJWjNFd1Rj
bENCWmVNUEJyZFBpRmYwbWVndFJGcUEKzvkGz3WycSrU4qPcBhs4cSCn/9TQ62sl
T6TuDra97qJJ1Pg9VZGHT/OoSleLA4s0qpNlAxnAnNaO0conTsREZQ==
-----END AGE ENCRYPTED FILE-----
lastmodified: "2023-07-17T12:01:21Z"
mac: ENC[AES256_GCM,data:003nzaNWdXLscJy9XZcwAb93M9Eo3Bdg9s5MHHiv4/TitaaZE7VghWHKv5DrcoA0GGdN9SnIVqHd+o6OPVER91XLVxoiX7ixtlu1RIRfqdama3RRPtSki5wP5wPz6qF4vRBIKfrTpZK7thXLYs2NhCB9HJYljNhcgLtzEG5bWgY=,iv:tEP530Pij3bt3hc5PCYGjFFyPiKgo34dHm23Xtmrxt8=,tag:macr/U8R5+wktTBJ9OqI/w==,type:str]
pgp:
- created_at: "2023-07-02T20:30:30Z"
enc: |-
-----BEGIN PGP MESSAGE-----
kms: []
gcp_kms: []
azure_kv: []
hc_vault: []
age:
- recipient: age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSBWaE9nNytUbXhWeWZYWndn
R3pMV3N1NjJPK2gzUDl2YitxWEU4NUFPRUJ3Cm1tMGhGcU56bSs5SUIzRmhqVHN2
dXIzYlkvS1JnWnladGdXTnRKMXNOWncKLS0tIGhyRFhFV1VRVXVYN1pJWjNFd1Rj
bENCWmVNUEJyZFBpRmYwbWVndFJGcUEKzvkGz3WycSrU4qPcBhs4cSCn/9TQ62sl
T6TuDra97qJJ1Pg9VZGHT/OoSleLA4s0qpNlAxnAnNaO0conTsREZQ==
-----END AGE ENCRYPTED FILE-----
lastmodified: "2023-07-17T12:01:21Z"
mac: ENC[AES256_GCM,data:003nzaNWdXLscJy9XZcwAb93M9Eo3Bdg9s5MHHiv4/TitaaZE7VghWHKv5DrcoA0GGdN9SnIVqHd+o6OPVER91XLVxoiX7ixtlu1RIRfqdama3RRPtSki5wP5wPz6qF4vRBIKfrTpZK7thXLYs2NhCB9HJYljNhcgLtzEG5bWgY=,iv:tEP530Pij3bt3hc5PCYGjFFyPiKgo34dHm23Xtmrxt8=,tag:macr/U8R5+wktTBJ9OqI/w==,type:str]
pgp:
- created_at: "2023-07-02T20:30:30Z"
enc: |-
-----BEGIN PGP MESSAGE-----
wcBMA0SHG/zF3227AQgAli6PQTNwh9N5Oo1LJvHysQNdxdZAq4QbfcwcIfpJIDds
0TQs28EeSttv47P2ga4Nb1O5dVUnlvwbP+uV9RbioYF4LfZ2/uNlS1lSGwsLbPcf
SsY+U2WvpJgyo3EWQRusR/OXLFg0EdqDPDseH1w1u8tGALDrewre5oBjrMa0GRbb
5F8lK/FVxSJxz70UkHgE7c6pSqPpznlgVduUwoOWnlhTw4aet7lLik+/C9K7LBDc
Q04sW1W2yqYr2882xPAUwfBhgfZQ1Uld5aDwqwPH+1Ttx26e7JrGSFaIX8GTVVpc
RJqN6uman5at3lOaEKXS1qf7T9ZI003CvdFwHS1G89JRAemdeK4bur5wS3VXBhDx
44fHgmDcOohHilTahwmyXCT70KjjHbd9665vAhsl0N9aOrOBdOgq0HmLjNzAQkz5
uGcEfsNiUXPngkNrh/Nvhh9w
=yHDZ
-----END PGP MESSAGE-----
fp: 6F7069FE6B96E894E60EC45C6EEFA706CB17E89B
unencrypted_suffix: _unencrypted
version: 3.7.3
wcBMA0SHG/zF3227AQgAli6PQTNwh9N5Oo1LJvHysQNdxdZAq4QbfcwcIfpJIDds
0TQs28EeSttv47P2ga4Nb1O5dVUnlvwbP+uV9RbioYF4LfZ2/uNlS1lSGwsLbPcf
SsY+U2WvpJgyo3EWQRusR/OXLFg0EdqDPDseH1w1u8tGALDrewre5oBjrMa0GRbb
5F8lK/FVxSJxz70UkHgE7c6pSqPpznlgVduUwoOWnlhTw4aet7lLik+/C9K7LBDc
Q04sW1W2yqYr2882xPAUwfBhgfZQ1Uld5aDwqwPH+1Ttx26e7JrGSFaIX8GTVVpc
RJqN6uman5at3lOaEKXS1qf7T9ZI003CvdFwHS1G89JRAemdeK4bur5wS3VXBhDx
44fHgmDcOohHilTahwmyXCT70KjjHbd9665vAhsl0N9aOrOBdOgq0HmLjNzAQkz5
uGcEfsNiUXPngkNrh/Nvhh9w
=yHDZ
-----END PGP MESSAGE-----
fp: 6F7069FE6B96E894E60EC45C6EEFA706CB17E89B
unencrypted_suffix: _unencrypted
version: 3.7.3

View file

@ -1,124 +0,0 @@
{
"nodes": {
"flake-compat": {
"flake": false,
"locked": {
"lastModified": 1696426674,
"narHash": "sha256-kvjfFW7WAETZlt09AgDn1MrtKzP7t90Vf7vypd3OL1U=",
"owner": "edolstra",
"repo": "flake-compat",
"rev": "0f9255e01c2351cc7d116c072cb317785dd33b33",
"type": "github"
},
"original": {
"owner": "edolstra",
"repo": "flake-compat",
"type": "github"
}
},
"flake-parts": {
"inputs": {
"nixpkgs-lib": [
"nix-snapshotter",
"nixpkgs"
]
},
"locked": {
"lastModified": 1704152458,
"narHash": "sha256-DS+dGw7SKygIWf9w4eNBUZsK+4Ug27NwEWmn2tnbycg=",
"owner": "hercules-ci",
"repo": "flake-parts",
"rev": "88a2cd8166694ba0b6cb374700799cec53aef527",
"type": "github"
},
"original": {
"owner": "hercules-ci",
"repo": "flake-parts",
"type": "github"
}
},
"nix-snapshotter": {
"inputs": {
"flake-compat": "flake-compat",
"flake-parts": "flake-parts",
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1723875769,
"narHash": "sha256-66GofByLJ+S4ZZphIC+vJKeL9VJ2bzH2VbcJ3OqteMM=",
"owner": "pdtpartners",
"repo": "nix-snapshotter",
"rev": "6eaadfd8f89e5e7d79b2013626bbd36e388159da",
"type": "github"
},
"original": {
"owner": "pdtpartners",
"repo": "nix-snapshotter",
"type": "github"
}
},
"nixlib": {
"locked": {
"lastModified": 1728781282,
"narHash": "sha256-hUP9oxmnOmNnKcDOf5Y55HQ+NnoT0+bLWHLQWLLw9Ks=",
"owner": "nix-community",
"repo": "nixpkgs.lib",
"rev": "16340f605f4e8e5cf07fd74dcbe692eee2d4f51b",
"type": "github"
},
"original": {
"owner": "nix-community",
"repo": "nixpkgs.lib",
"type": "github"
}
},
"nixos-generators": {
"inputs": {
"nixlib": "nixlib",
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1728867876,
"narHash": "sha256-NCyOA8WZNoojmXH+kBDrQj3LwvakYNzSc0h+LTXkmPE=",
"owner": "nix-community",
"repo": "nixos-generators",
"rev": "fdf142111597f6c6283cf5ffe092b6293a3911d0",
"type": "github"
},
"original": {
"owner": "nix-community",
"repo": "nixos-generators",
"type": "github"
}
},
"nixpkgs": {
"locked": {
"lastModified": 1728897630,
"narHash": "sha256-0utJPs4o2Mody8GDwo4hnGuxc8dJqju4u9lLJY4d/Lw=",
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "c9f0b4a395289ce18727e2a8e43cae6796693ccc",
"type": "github"
},
"original": {
"owner": "NixOS",
"ref": "nixos-unstable-small",
"repo": "nixpkgs",
"type": "github"
}
},
"root": {
"inputs": {
"nix-snapshotter": "nix-snapshotter",
"nixos-generators": "nixos-generators",
"nixpkgs": "nixpkgs"
}
}
},
"root": "root",
"version": 7
}

View file

@ -1,371 +0,0 @@
{
inputs = {
nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable-small";
# nixpkgs-systemd256.url = "github:NixOS/nixpkgs/962cf03fb8c782c5e00f465397e03dc84284acc9";
nixos-generators = {
url = "github:nix-community/nixos-generators";
inputs.nixpkgs.follows = "nixpkgs";
};
nix-snapshotter = {
url = "github:pdtpartners/nix-snapshotter";
inputs.nixpkgs.follows = "nixpkgs";
};
};
outputs =
{ self, nixpkgs, ... }:
let
systems = [
"aarch64-linux"
"x86_64-linux"
];
forAllSystems = nixpkgs.lib.genAttrs systems;
in
{
nixosConfigurations.default = nixpkgs.lib.nixosSystem {
system = "aarch64-linux";
specialArgs = { };
modules = [
(
{
config,
modulesPath,
pkgs,
lib,
...
}:
{
nixpkgs.overlays = [
(_final: _previous: {
# inherit (self.inputs.nixpkgs-systemd256.legacyPackages.${pkgs.system}) systemd systemdMinimal;
# systemd =
# self.inputs.nixpkgs-systemd256.legacyPackages.${pkgs.system}.systemd.overrideAttrs (prevAttrs: {
# src = /home/steveej/src/others/systemd;
# withAppArmor = false;
# withRepart = false;
# withHomed = false;
# withAcl = false;
# withEfi = false;
# withBootloader = false;
# withCryptsetup = false;
# withLibBPF = false;
# withOomd = false;
# withFido2 = false;
# withApparmor = false;
# withDocumentation = false;
# withUtmp = false;
# withQrencode = false;
# withVmspawn = false;
# withMachined = false;
# withLogTrace = true;
# withArchive = false;
# # don't need these but cause errors for exampel files not found
# # withLogind = false;
# })
# pkgs.systemdMinimal.override {
# # getting errors with these disabled
# withCoredump = true;
# withCompression = true;
# withLogind = true;
# withSysusers = true;
# withUserDb = true;
# }
# pkgs.systemdMinimal
# pkgs.systemd.override {
# withRepart = false;
# withHomed = false;
# withAcl = false;
# withEfi = false;
# withBootloader = false;
# withCryptsetup = false;
# withLibBPF = false;
# withOomd = false;
# withFido2 = false;
# withApparmor = false;
# withDocumentation = false;
# withUtmp = false;
# withQrencode = false;
# withVmspawn = false;
# withMachined = false;
# withLogTrace = true;
# # don't need these but cause errors for exampel files not found
# # withLogind = false;
# }
# ;
})
];
imports = [ (modulesPath + "/profiles/minimal.nix") ];
system.stateVersion = "24.11";
# https://github.com/hercules-ci/arion/blob/c24c185e67f093298a081900b49ca18716077dec/src/nix/modules/nixos/container-systemd.nix
boot.isContainer = true;
# boot.tmp.useTmpfs = true;
boot.loader.grub.enable = lib.mkForce false;
boot.loader.systemd-boot.enable = lib.mkForce false;
services.journald.console = "/dev/console";
services.journald.storage = "none";
# boot.specialFileSystems = lib.mkForce {};
services.nscd.enable = false;
system.nssModules = lib.mkForce [ ];
systemd.services.systemd-logind.enable = false;
systemd.services.console-getty.enable = false;
systemd.sockets.nix-daemon.enable = false;
systemd.services.nix-daemon.enable = false;
systemd.oomd.enable = false;
networking.useDHCP = false;
networking.firewall.enable = false;
# system.build.earlyMountScript =
# lib.mkForce ''
# '';
# system.activationScripts.specialfs =
# lib.mkForce ''
# '';
boot.postBootCommands = ''
ls -lha /run
mkdir -p /run/wrappers
'';
boot.kernelParams = [ "systemd.log_level=debug" ];
# services.udev.enable = false;
# TODO: this is only needed because `/run/current-system` is missing
# environment.variables.PATH = "${lib.makeBinPath config.environment.systemPackages}:$PATH";
systemd.mounts = lib.mkForce [ ];
fileSystems = lib.mkForce { };
services.mycelium.enable = false;
services.mycelium.keyFile = "/var/lib/secrets/mycelium-keyfile";
systemd.services.mycelium.serviceConfig.DynamicUser = lib.mkForce false;
systemd.services.mycelium.serviceConfig.User = lib.mkForce "root";
systemd.services.mycelium.serviceConfig.ExecStart = lib.mkForce (
pkgs.writeShellScript "mycelium" ''
while true; do
ls -lha $CREDENTIALS_DIRECTORY
sleep 5
done
''
);
systemd.services.testing-credentials = {
wantedBy = [ "multi-user.target" ];
path = [ pkgs.coreutils ];
serviceConfig = {
# SyslogIdentifier = "testing-credentials";
# StateDirectory = "testing-credentials";
# DynamicUser = true;
# User = "tc";
# ProtectHome = true;
# ProtectSystem = true;
# LoadCredential = [
# "mycelium-keyfile:${self.nixosConfigurations.default.config.services.mycelium.keyFile}"
# "hosts:/etc/hosts"
# ];
SetCredential = "mycelium-keyfile:not secret string";
ExecStart = lib.mkForce (
pkgs.writeShellScript "mycelium" ''
cd $STATE_DIRECTORY
pwd
env
while true; do
ls -lha $CREDENTIALS_DIRECTORY
sleep 5
done
''
);
};
};
services.caddy = {
enable = true;
globalConfig = ''
auto_https off
'';
virtualHosts.":80" = {
extraConfig = ''
respond "hello from ${config.networking.hostName}"
'';
};
};
}
)
];
};
packages = forAllSystems (
system:
let
name = "mycelium";
inherit (self.inputs) nix-snapshotter;
config = {
entrypoint = "${self.nixosConfigurations.default.config.system.build.toplevel}/init";
# port = 2379;
args = [ ];
# nodePort = 30001;
};
myceliumPorts = {
tcp = [ 9651 ];
udp = [
9650
9651
];
};
inherit (config)
entrypoint
# port
args
# nodePort
;
pkgs = import nixpkgs { overlays = [ nix-snapshotter.overlays.default ]; };
image = pkgs.nix-snapshotter.buildImage {
inherit name;
resolvedByNix = true;
config = {
entrypoint = [ entrypoint ];
env = [
# this is read by the `/init` script and prevents various incompatible commands like mount, etc.
# the value of this doesn't seem to matter as long as it's not an empty string.
"container=nerd"
"SYSTEMD_LOG_LEVEL=debug"
];
volumes = {
# "/var/lib/private/mycelium/key.bin" = {};
# "/run" = {};
# "/tmp" = {};
# "/etc" = {};
};
copyToRoot = [
# self.nixosConfigurations.default.config.system.build.toplevel
];
};
};
in
{
k8s =
let
pod = pkgs.writeText "${name}-pod.json" (
builtins.toJSON {
apiVersion = "v1";
kind = "Pod";
metadata = {
inherit name;
labels = {
inherit name;
};
};
spec.containers = [
{
inherit name args;
image = "nix:0${image}";
ports = [
{
name = "mycelium-tcp-0";
containerPort = builtins.elemAt myceliumPorts.tcp 0;
}
{
name = "mycelium-udp-0";
protocol = "UDP";
containerPort = builtins.elemAt myceliumPorts.udp 0;
}
{
name = "mycelium-udp-1";
protocol = "UDP";
containerPort = builtins.elemAt myceliumPorts.udp 1;
}
];
}
];
}
);
service = pkgs.writeText "${name}-service.json" (
builtins.toJSON {
apiVersion = "v1";
kind = "Service";
metadata.name = "${name}-service";
spec = {
type = "NodePort";
selector = {
inherit name;
};
ports = [
{
name = "mycelium-tcp-0";
port = builtins.elemAt myceliumPorts.tcp 0 + 50000;
targetPort = "mycelium-tcp-0";
}
{
name = "mycelium-udp-0";
protocol = "UDP";
port = builtins.elemAt myceliumPorts.udp 0 + 50000;
targetPort = "mycelium-udp-0";
}
{
name = "mycelium-udp-1";
protocol = "UDP";
port = builtins.elemAt myceliumPorts.udp 1 + 50000;
targetPort = "mycelium-udp-1";
}
];
};
}
);
in
pkgs.runCommand "declarative-k8s" { } ''
mkdir -p $out/share/k8s
cp ${pod} $out/share/k8s/
cp ${service} $out/share/k8s/
'';
inherit image;
start = pkgs.writeShellApplication {
name = "start";
text = ''
set -x
rm -rf ./result
nix build --impure .#image
sudo nix2container load ./result
sudo -E nerdctl run --name ${name} --privileged -dt \
--cgroup-manager cgroupfs \
--volume "$PWD/key.bin.crypt:${self.nixosConfigurations.default.config.services.mycelium.keyFile}:ro" \
"nix:0$(readlink result):latest"
'';
};
stop = pkgs.writeShellApplication {
name = "stop";
text = ''
set +e
sudo -E nerdctl stop -t 60 ${name}
sudo -E nerdctl rm --force ${name}
sudo -E nerdctl system prune --all --force
sudo systemctl stop nix-snapshotter
sudo systemctl stop containerd
mount | rg -No '(/var/lib/container|/tmp/initial)[^ ]+' | tac | xargs sudo umount -l
sudo systemctl start containerd
sudo systemctl start nix-snapshotter
'';
# tmpfs on /run/credentials/mycelium.service type tmpfs (ro,nosuid,nodev,noexec,relatime,nosymfollow,size=1024k,nr_inodes=1024,mode=700,noswap)
# mount -t tmpfs tmpfs /run/credentials/mycelium.service -o ro,nosuid,nodev,noexec,relatime,nosymfollow,size=1024k,nr_inodes=1024,mode=700,noswap
};
}
);
};
}

View file

@ -1,81 +1,31 @@
{
specialArgs,
hostBridge,
hostAddress,
localAddress,
syncthingPort ? 22000,
syncthingLocalAnnouncePort ? 21027,
smbTcpPort ? 445,
autoStart ? false,
}:
{
inherit specialArgs;
config =
{ ... }:
{
system.stateVersion = "20.05"; # Did you read the comment?
}: {
config = {
config,
pkgs,
...
}: {
system.stateVersion = "20.05"; # Did you read the comment?
imports = [ ../profiles/containers/configuration.nix ];
imports = [../profiles/containers/configuration.nix];
networking.firewall.allowedTCPPorts = [
# syncthing gui
8384
];
networking.firewall.enable = true;
networking.firewall.allowedTCPPorts = [
# syncthing gui
8384
];
services.syncthing = {
enable = true;
openDefaultPorts = true;
guiAddress = "0.0.0.0:8384";
};
services.samba = {
enable = true;
securityType = "user";
openFirewall = true;
settings = {
global = {
"workgroup" = "DMZ";
"server string" = "syncthing";
"netbios name" = "syncthing";
"security" = "user";
#"use sendfile" = "yes";
#"max protocol" = "smb2";
# note: localhost is the ipv6 localhost ::1
"hosts allow" = "192.168.23. 127.0.0.1 localhost";
"hosts deny" = "0.0.0.0/0";
"guest account" = "nobody";
"map to guest" = "bad user";
};
"scan-stefan" = {
"path" = "/var/lib/syncthing/Sync/Home::Scan::Stefan";
"browseable" = "yes";
"read only" = "no";
"guest ok" = "no";
"create mask" = "0644";
"directory mask" = "0755";
"force user" = "syncthing";
"force group" = "syncthing";
};
"scan-justyna" = {
"path" = "/var/lib/syncthing/Sync/Home::Scan::Justyna";
"browseable" = "yes";
"read only" = "no";
"guest ok" = "no";
"create mask" = "0644";
"directory mask" = "0755";
"force user" = "syncthing";
"force group" = "syncthing";
};
};
};
# TODO: find out if smbpasswd file is still used and set it here. or find an alternative
# sops.secrets.smbpasswd = {
# };
# environment.etc."samba/smbpasswd".source = config.sops.secrets.smbpasswd.text;
services.syncthing = {
enable = true;
openDefaultPorts = true;
guiAddress = "0.0.0.0:8384";
};
};
inherit autoStart;
@ -86,6 +36,8 @@
};
};
extraFlags = ["--resolv-conf=bind-host"];
privateNetwork = true;
forwardPorts = [
{
@ -103,12 +55,7 @@
hostPort = syncthingLocalAnnouncePort;
protocol = "udp";
}
{
containerPort = 445;
hostPort = smbTcpPort;
protocol = "tcp";
}
];
inherit hostBridge hostAddress localAddress;
inherit hostAddress localAddress;
}

View file

@ -1,427 +1,227 @@
{
specialArgs,
hostBridge,
repoFlake,
hostAddress,
localAddress,
httpPort,
httpsPort,
forgejoSshPort,
httpPort ? 80,
httpsPort ? 443,
autoStart ? false,
}:
let
}: let
domain = "www.stefanjunker.de";
in
{
inherit specialArgs;
config =
{
config,
pkgs,
lib,
repoFlake,
nodeFlake,
system,
...
}:
let
nixpkgs-kanidm = nodeFlake.inputs.nixpkgs-unstable;
in
{
system.stateVersion = "22.05"; # Did you read the comment?
disabledModules = [
"services/misc/forgejo.nix"
"services/security/kanidm.nix"
];
imports = [
"${nodeFlake.inputs.nixpkgs-unstable}/nixos/modules/services/misc/forgejo.nix"
"${nixpkgs-kanidm}/nixos/modules/services/security/kanidm.nix"
../profiles/containers/configuration.nix
repoFlake.inputs.sops-nix.nixosModules.sops
];
sops.defaultSopsFile = ./webserver_secrets.yaml;
networking.firewall.allowedTCPPorts = [
httpPort
httpsPort
forgejoSshPort
];
sops.age.sshKeyPaths = [ "/etc/ssh/ssh_host_ed25519_key" ];
sops.secrets.hedgedoc_environment_file = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.hedgedoc.name;
};
services.caddy = {
enable = true;
logFormat = ''
level ERROR
'';
virtualHosts."${domain}" = {
extraConfig = ''
redir /hedgedoc* https://hedgedoc.${domain}
file_server /*/* {
browse
root /var/www/stefanjunker.de/htdocs/caddy
pass_thru
}
# respond "Hi"
# respond (not /*/*) "Hi"
'';
};
virtualHosts."hedgedoc.${domain}" = {
extraConfig = ''
reverse_proxy http://[::1]:3000
'';
};
virtualHosts."authelia.${domain}" = {
extraConfig = ''
reverse_proxy http://127.0.0.1:${builtins.toString config.services.authelia.instances.default.settings.server.port}
'';
};
virtualHosts."lldap.${domain}" = {
extraConfig = ''
reverse_proxy http://127.0.0.1:${builtins.toString config.services.lldap.settings.http_port}
'';
};
virtualHosts."forgejo.${domain}" = {
extraConfig = ''
reverse_proxy http://127.0.0.1:${builtins.toString config.services.forgejo.settings.server.HTTP_PORT}
'';
};
virtualHosts."kanidm.${domain}" = {
extraConfig = ''
reverse_proxy https://${builtins.toString config.services.kanidm.serverSettings.bindaddress} {
transport http {
tls_server_name ${config.services.kanidm.serverSettings.domain}
}
}
'';
};
};
services.hedgedoc = {
enable = true;
settings = {
domain = "hedgedoc.${domain}";
urlPath = "";
protocolUseSSL = true;
db = {
dialect = "sqlite";
storage = "/var/lib/hedgedoc/db.hedgedoc.sqlite";
};
allowAnonymous = false;
allowAnonymousEdits = false;
allowGravatar = false;
allowFreeURL = false;
defaultPermission = "private";
allowEmailRegister = false;
email = false;
ldap = {
url = "ldap://127.0.0.1:${builtins.toString config.services.lldap.settings.ldap_port}";
bindDn = "uid=admin,ou=people,dc=stefanjunker,dc=de";
# these are set via the `environmentFile`
# bindCredentials = "$LDAP_ADMIN_PASSWORD";
searchBase = "ou=people,dc=stefanjunker,dc=de";
searchFilter = "(&(memberOf=cn=hedgedoc,ou=groups,dc=stefanjunker,dc=de)(uid={{username}}))";
useridField = "uid";
};
oauth2 =
let
originURL = config.services.kanidm.serverSettings.origin;
in
{
providerName = "kanidm (${originURL})";
authorizationURL = "${originURL}/ui/oauth2";
tokenURL = "${originURL}/oauth2/token";
userProfileURL = "${originURL}/oauth2/openid/hedgedoc/userinfo";
scope = "openid email profile";
# rolesClaim = "roles";
# accessRole = "role/hedgedoc";
userProfileUsernameAttr = "name";
userProfileDisplayNameAttr = "displayname";
userProfileEmailAttr = "email";
clientID = "hedgedoc";
# set via the `environmentFile`
# clientSecret = "$CMD_OAUTH2_CLIENT_SECRET";
};
uploadsPath = "/var/lib/hedgedoc/uploads";
};
environmentFile = config.sops.secrets.hedgedoc_environment_file.path;
};
services.jitsi-meet = {
enable = false;
hostName = "meet.${domain}";
config = {
prejoinPageEnabled = true;
};
caddy.enable = true;
nginx.enable = false;
};
sops.secrets.authelia_storageEncryptionKey = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.authelia-default.name;
};
sops.secrets.authelia_jwtSecret = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.authelia-default.name;
};
services.authelia.instances.default =
let
baseDir = "/var/lib/authelia-default";
in
{
enable = true;
secrets.storageEncryptionKeyFile = config.sops.secrets.authelia_storageEncryptionKey.path;
secrets.jwtSecretFile = config.sops.secrets.authelia_jwtSecret.path;
settings = {
theme = "auto";
default_2fa_method = "totp";
log.level = "debug";
server = {
disable_healthcheck = true;
host = "127.0.0.1";
port = 9091;
# path = "authelia";
};
storage = {
local.path = "${baseDir}/authelia.sqlite";
};
authentication_backend = {
file.path = "${baseDir}/first_factor.yaml";
file.search.email = true;
file.search.case_insensitive = false;
};
access_control = {
default_policy = "one_factor";
};
session.domain = "stefanjunker.de";
notifier = {
disable_startup_check = true;
filesystem.filename = "${baseDir}/notification.txt";
};
};
};
users.groups.lldap = { };
users.users.lldap = {
isSystemUser = true;
group = "lldap";
};
sops.secrets.lldap_jwtSecret = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
sops.secrets.lldap_adminPassword = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
sops.secrets.lldap_environmentFile = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
services.lldap = {
enable = true;
environment = {
LLDAP_JWT_SECRET_FILE = config.sops.secrets.lldap_jwtSecret.path;
LLDAP_LDAP_USER_PASS_FILE = config.sops.secrets.lldap_adminPassword.path;
};
environmentFile = config.sops.secrets.lldap_environmentFile.path;
settings = {
verbose = true;
ldap_base_dn = "dc=stefanjunker,dc=de";
http_url = "https://lldap.${domain}";
## Options to configure SMTP parameters, to send password reset emails.
## To set these options from environment variables, use the following format
## (example with "password"): LLDAP_SMTP_OPTIONS__PASSWORD
smtp_options = {
## Whether to enabled password reset via email, from LLDAP.
enable_password_reset = true;
# port = 465;
## How the connection is encrypted, either "NONE" (no encryption), "TLS" or "STARTTLS".
# smtp_encryption = "TLS";
};
# database_url = "sqlite:///var/lib/lldap/users.db?mode=rwc";
};
};
sops.secrets.FORGEJO_JWT_SECRET = { };
sops.secrets.FORGEJO_INTERNAL_TOKEN = { };
sops.secrets.FORGEJO_SECRET_KEY = { };
services.forgejo = {
enable = true;
package = nodeFlake.inputs.nixpkgs-unstable.legacyPackages.${pkgs.system}.forgejo;
settings = {
service.DISABLE_REGISTRATION = true;
server.HTTP_ADDR = "127.0.0.1";
server.START_SSH_SERVER = true;
server.SSH_PORT = forgejoSshPort;
server.ROOT_URL = "https://forgejo.${domain}";
server.HTTP_PORT = 3001;
# TODO: how do i get a 3072 length SSH key with the yubikey?
"ssh.minimum_key_sizes".RSA = 2048;
};
secrets = {
oauth2.JWT_SECRET = lib.mkForce config.sops.secrets.FORGEJO_JWT_SECRET.path;
security.INTERNAL_TOKEN = lib.mkForce config.sops.secrets.FORGEJO_INTERNAL_TOKEN.path;
security.SECRET_KEY = lib.mkForce config.sops.secrets.FORGEJO_SECRET_KEY.path;
};
};
systemd.services.lldap.serviceConfig.User = config.users.users.lldap.name;
systemd.services.lldap.serviceConfig.Group = config.users.groups.lldap.name;
systemd.services.lldap.serviceConfig.DynamicUser = lib.mkForce false;
# combine a path watcher with a service that transfers the certs by caddy to kanidm
# TODO: had an issue where the certificate in kanidm was expired, despite caddy having a refreshed certificate
systemd.paths.kanidm-tls-watch = {
enable = true;
requiredBy = [ "kanidm.service" ];
pathConfig = {
PathChanged = [
"${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.key"
"${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.crt"
];
Unit = "kanidm-tls-update.service";
};
};
systemd.services.kanidm-tls-update =
let
dbDir = builtins.dirOf config.services.kanidm.serverSettings.db_path;
in
{
enable = true;
requiredBy = [ "kanidm.service" ];
unitConfig = {
# ConditionPathExists = [
# "${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.key"
# "${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.crt"
# ];
};
serviceConfig.Type = "oneshot";
script =
let
tlsDir = builtins.dirOf config.services.kanidm.serverSettings.tls_key;
in
''
set -xe
cat "${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.key" > tls.key
cat "${config.services.caddy.dataDir}/.local/share/caddy/certificates/acme-v02.api.letsencrypt.org-directory/${config.services.kanidm.serverSettings.domain}/${config.services.kanidm.serverSettings.domain}.crt" > tls.chain
chown ${config.systemd.services.kanidm.serviceConfig.User}:${config.systemd.services.kanidm.serviceConfig.Group} tls.{key,chain}
chmod 400 tls.{key,chain}
# create the kanidm directory in case it's missing
if [[ ! -d ${tlsDir} ]]; then
mkdir -p ${tlsDir}
chown -R ${config.systemd.services.kanidm.serviceConfig.User}:${config.systemd.services.kanidm.serviceConfig.Group} ${tlsDir}
chmod 700 ${tlsDir}
fi
mv tls.key ${config.services.kanidm.serverSettings.tls_key}
mv tls.chain ${config.services.kanidm.serverSettings.tls_chain}
if [[ ! -d ${dbDir} ]]; then
mkdir -p ${dbDir}
chown -R ${config.systemd.services.kanidm.serviceConfig.User}:${config.systemd.services.kanidm.serviceConfig.Group} ${dbDir}
chmod 700 ${dbDir}
fi
'';
};
systemd.services.kanidm.serviceConfig =
let
dbDir = builtins.dirOf config.services.kanidm.serverSettings.db_path;
in
# stateDir = "/var/lib/${config.systemd.services.kanidm.serviceConfig.StateDirectory}";
{
# ExecStartPre = ''
# mkdir -p ${dbDir}
# '';
BindPaths = [
dbDir
# stateDir
];
};
services.kanidm =
let
dataDir = "/var/lib/kanidm";
in
{
package = nixpkgs-kanidm.legacyPackages.${pkgs.system}.kanidm;
enablePam = false;
enableClient = false;
enableServer = true;
serverSettings = {
role = "WriteReplica";
log_level = "debug";
domain = "kanidm.${domain}";
origin = "https://kanidm.${domain}";
bindaddress = "127.0.0.1:8444";
# don't expose ldap
# ldapbindaddress = "[::1]:6636";
tls_key = "${dataDir}/tls/tls.key";
tls_chain = "${dataDir}/tls/tls.chain";
online_backup = {
schedule = "00 06 * * *";
};
};
};
in {
config = {
config,
pkgs,
lib,
...
}: {
system.stateVersion = "22.05"; # Did you read the comment?
imports = [
../profiles/containers/configuration.nix
repoFlake.inputs.sops-nix.nixosModules.sops
];
networking.firewall.enable = false;
sops.age.sshKeyPaths = ["/etc/ssh/ssh_host_ed25519_key"];
sops.secrets.hedgedoc_environment_file = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.hedgedoc.name;
};
services.caddy = {
enable = true;
virtualHosts."${domain}" = {
extraConfig = let
port = "${builtins.toString config.services.authelia.instances.default.settings.server.port}";
path = "${config.services.authelia.instances.default.settings.server.path}";
in ''
redir /hedgedoc* https://hedgedoc.${domain}
file_server /*/* {
browse
root /var/www/stefanjunker.de/htdocs/caddy
pass_thru
}
# respond "Hi"
# respond (not /*/*) "Hi"
'';
};
virtualHosts."hedgedoc.${domain}" = {
extraConfig = ''
reverse_proxy http://[::1]:3000
'';
};
virtualHosts."authelia.${domain}" = {
extraConfig = ''
reverse_proxy http://127.0.0.1:${builtins.toString config.services.authelia.instances.default.settings.server.port}
'';
};
virtualHosts."lldap.${domain}" = {
extraConfig = ''
reverse_proxy http://127.0.0.1:${builtins.toString config.services.lldap.settings.http_port}
'';
};
};
services.hedgedoc = {
enable = true;
settings = {
domain = "hedgedoc.${domain}";
urlPath = "";
protocolUseSSL = true;
db = {
dialect = "sqlite";
storage = "/var/lib/hedgedoc/db.hedgedoc.sqlite";
};
allowAnonymous = false;
allowAnonymousEdits = false;
allowGravatar = false;
allowFreeURL = false;
defaultPermission = "private";
allowEmailRegister = false;
email = false;
ldap = {
url = "ldap://127.0.0.1:${builtins.toString config.services.lldap.settings.ldap_port}";
bindDn = "uid=admin,ou=people,dc=stefanjunker,dc=de";
# these are set via the `environmentFile`
bindCredentials = "$LDAP_ADMIN_PASSWORD";
searchBase = "ou=people,dc=stefanjunker,dc=de";
searchFilter = "(&(memberOf=cn=hedgedoc,ou=groups,dc=stefanjunker,dc=de)(uid={{username}}))";
useridField = "uid";
};
uploadsPath = "/var/lib/hedgedoc/uploads";
};
environmentFile = config.sops.secrets.hedgedoc_environment_file.path;
};
services.jitsi-meet = {
enable = false;
hostName = "meet.${domain}";
config = {
prejoinPageEnabled = true;
};
caddy.enable = true;
nginx.enable = false;
};
sops.secrets.authelia_storageEncryptionKey = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.authelia-default.name;
};
sops.secrets.authelia_jwtSecret = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.authelia-default.name;
};
services.authelia.instances.default = let
baseDir = "/var/lib/authelia-default";
in {
enable = true;
secrets.storageEncryptionKeyFile = config.sops.secrets.authelia_storageEncryptionKey.path;
secrets.jwtSecretFile = config.sops.secrets.authelia_jwtSecret.path;
settings = {
theme = "auto";
default_2fa_method = "totp";
log.level = "debug";
server = {
disable_healthcheck = true;
host = "127.0.0.1";
port = 9091;
# path = "authelia";
};
storage = {
local.path = "${baseDir}/authelia.sqlite";
};
authentication_backend = {
file.path = "${baseDir}/first_factor.yaml";
file.search.email = true;
file.search.case_insensitive = false;
};
access_control = {
default_policy = "one_factor";
};
session.domain = "stefanjunker.de";
notifier = {
disable_startup_check = true;
filesystem.filename = "${baseDir}/notification.txt";
};
};
};
users.groups.lldap = {};
users.users.lldap = {
isSystemUser = true;
group = "lldap";
};
sops.secrets.lldap_jwtSecret = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
sops.secrets.lldap_adminPassword = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
sops.secrets.lldap_environmentFile = {
sopsFile = ./webserver_secrets.yaml;
owner = config.users.users.lldap.name;
};
services.lldap = {
enable = true;
environment = {
LLDAP_JWT_SECRET_FILE = config.sops.secrets.lldap_jwtSecret.path;
LLDAP_LDAP_USER_PASS_FILE = config.sops.secrets.lldap_adminPassword.path;
};
environmentFile = config.sops.secrets.lldap_environmentFile.path;
settings = {
verbose = true;
ldap_base_dn = "dc=stefanjunker,dc=de";
http_url = "https://lldap.${domain}";
## Options to configure SMTP parameters, to send password reset emails.
## To set these options from environment variables, use the following format
## (example with "password"): LLDAP_SMTP_OPTIONS__PASSWORD
smtp_options = {
## Whether to enabled password reset via email, from LLDAP.
enable_password_reset = true;
# port = 465;
## How the connection is encrypted, either "NONE" (no encryption), "TLS" or "STARTTLS".
# smtp_encryption = "TLS";
};
# database_url = "sqlite:///var/lib/lldap/users.db?mode=rwc";
};
};
systemd.services.lldap.serviceConfig.User = config.users.users.lldap.name;
systemd.services.lldap.serviceConfig.Group = config.users.groups.lldap.name;
systemd.services.lldap.serviceConfig.DynamicUser = lib.mkForce false;
};
inherit autoStart;
bindMounts = {
@ -453,18 +253,11 @@ in
hostPath = "/var/lib/container-volumes/webserver/var-lib-lldap";
isReadOnly = false;
};
"/var/lib/forgejo" = {
hostPath = "/var/lib/container-volumes/webserver/var-lib-forgejo";
isReadOnly = false;
};
"/var/lib/kanidm" = {
hostPath = "/var/lib/container-volumes/webserver/var-lib-kanidm";
isReadOnly = false;
};
};
# extraFlags = ["--resolv-conf=bind-host"];
# networking.useHostResolvConf = true;
privateNetwork = true;
forwardPorts = [
{
@ -479,14 +272,7 @@ in
hostPort = httpsPort;
protocol = "tcp";
}
{
# forgejo ssh
containerPort = forgejoSshPort;
hostPort = forgejoSshPort;
protocol = "tcp";
}
];
inherit hostBridge hostAddress localAddress;
inherit hostAddress localAddress;
}

View file

@ -1,45 +1,41 @@
hedgedoc_environment_file: ENC[AES256_GCM,data:gPTokPMGBAN/lGGeUs95vg45yVrrSmFCKWTjlMV4V+YnflcqiaZvifX9+0fe3DELwNL4kY4st4N0MadhLkTiSieyp46fP8Dujk4Prhi7JWweBDsN4WtxcwJfAdowgh5LTzqM3zggC/J9NGR/zgJGLYraOqsFueXycxDxntE+8MlepYFGsND4WbFHNRvsVd7xUWerZZD+JFhws2sjwC9DqoJ+mBX4u9J2faSrL3okBGwRpEZlJhe6/8pT0l1aVxI0b/9UsLUL/him/vVqY8ygMP8O95gzuDEaCtwSXw08ylhb3g3YHdMh9ZOe9dPNVocVFrB15HfxeY4KzRCVfvgmBsSiUrgUAZQ8aav2ZWHPKQ==,iv:AVtx/43MK5KVxP59olEmbkUzLhd0cBjPpVeiAJGELfM=,tag:Hd3edeUzLgHnwAwPiMGp4A==,type:str]
hedgedoc_environment_file: ENC[AES256_GCM,data:uBaATOTIkCkboAfaB7d6G2G4AfKszipQe+mc0XPJHik30wLppCKpEc61ELLbiZ1xGaOEWKUSMHc0GyBapykrgEe0UUYJ0Ukpq9bj9/J2VC7BLu1ABbr+pWpJR68+IOKY2GWlioSDIL6JwaGIjLV5sLrUjJgtwzAYrqAU13VS5RVHtGtz+7TgwHIJADoec+jSRhkh82g198eaAUbKyAFB9yhXFWgq6ozh8RgtkYKAP7LXIuyJt9BYJoNQ,iv:MCMJph0W1PC0n9h7xhPMxtJINQP+QRBf2anzXEzydwc=,tag:zj2o+/JpBRTYgYpSMJedPw==,type:str]
authelia_storageEncryptionKey: ENC[AES256_GCM,data:BLj2+w0jUOiiqljd4WcYt90I1Y/tm6vYRn9IPvv7k+ykjeWeafDcb9LpAbYZ82iAbCDZ6cDnTIJSH50TYFM1Bw==,iv:DfrFuTMS6rzWS1F7hIloD7Eb9N6LV6MDsPGEidTCIkM=,tag:4TxiUuWj8LLCAe+3SQWthA==,type:str]
authelia_jwtSecret: ENC[AES256_GCM,data:CtvhPJDlM8kZDh3MWI6jBEIK5P/Rc0ZY3JfQ/1qn2FyZ0kOE9CMznRQdzi125Mlh+LgfhS00aeY/esuSJ1YKnw==,iv:o29+Ja4E4USpxD5Bgg4nGpj1WdK+uJJeuyqa3c92Pys=,tag:Ko/6PqIM7FyvqMJAepTNKw==,type:str]
lldap_jwtSecret: ENC[AES256_GCM,data:Jd05K5zZZcdFY9P+PM1ycpl4eKr7THXzlEC2gxhfq0kZ0c7NrmqpnxLFyMOoq0oZwFXQ3aE29N+dYYCbWgEs0g==,iv:k9Y4XZcFSUaaOvooMzH1AlHaI/RiZZ0cpSqTU6jzsUU=,tag:EHwIMQ00Z+IrXAKgugMbmQ==,type:str]
lldap_adminPassword: ENC[AES256_GCM,data:qZviC+/V25iHWS2d5KKrMfCLmmWKAkXoiLW3NJyZWIvMRbFPtfJGv/5e++idcKNLdPHRgvGpdeTpOdZNK7ETSQ==,iv:jX8bzgYVXZfMQ8Qxa7WaUiQFE/mBmQWZ3o000njeEC8=,tag:4Rd3WVGIw1rBLKND4xPbMg==,type:str]
lldap_environmentFile: ENC[AES256_GCM,data:TpdO1N2MgHWI4TipvlwfVjnKppzpluI9WA3ejbgT8jrRXXTCA94PS734wDHLtEAIwKdIQd/JGDS+1kbdvgDL3F3HIOX5HLz9h7CtkDBYT6qOy0Zb0tNHjmJco6dL/iMwuzglXxu2460nadO+lHoTs3DA3lesghzpJzm41hgElzcxXS2sa/hsV+kjmbyfu6Xi94kbqcHBLA/mppWmLSgJN6wu/bO07XfaSB1ghHnAR7BL9XZDjoNDzljZAXDpDBw3WD6mwoZeIjGbkEuL4nUnkS6CkA+y7IORA24XGGAczRxZp4vLfUOnnlFCPGIHBsRTbrTB4bcEDBK4+5gHfNhXxvD5VlNMb4TPqYdcEIxkgMxZNLV5U2LTlzn18HNOCvsPb9XOOtY21j6qHMMQDXZREmn5NsW0HXM4gNZ0fC9UEe1MYBhyE3gGEGDzzDUrrQCGLm7/1OC7NRlzuI7M/5DlgcREwK1PkjPDmfRCAq86l0N5lMP/A7MMq2SJWcZvf+ot3fInugq485773vgWWl2Rodl08SZ8YHnzj0L6anPu856v2BsIotE0iRJSCpzA2ZgOJ9RViBfoq6F3beJKLnGN7oGb8XBviRTnXrTN6BTuFyv3dIZ7qcuTGTY+ucjRXfGJ1TVlVQBbiqhQDz5c9D5e0RVnRe3AkMXeDMOd4GlWW5gsJSuZtlYq1aMEf/Bx+4WMyY/Wh+Jk1xxf30bth5L1dW82p6fNFhEuKabtkBALOg/CQzYczMeGP9ai6BWgZL8QPlQoEUpHh59Vz91V6unQSOJ2PNr5wzC6j75IKInVjcp4d1S9K2UAxg+HETn5p9T1sBRdAAVz0YgO5902FwDTsA+2x6Q=,iv:U94CNFxQ8kyIYdH0EyqQIJ3s7QKaLlMa+5coO0dQnto=,tag:KZEizL99W5BtcaXSnYXFhg==,type:str]
#ENC[AES256_GCM,data:uNqahO8WF6QFNkbPnQq2UDKn/gFt0H56keUb,iv:CDVKC3ER5rsKoMmBi2g5g+F3ZfKc3+Rs8bjxFhgSPZ4=,tag:oGPl6TB/nghGwWvVBLFlGQ==,type:comment]
FORGEJO_JWT_SECRET: ENC[AES256_GCM,data:nVz9x7+K+rBIZxuQP7o0WNFHUz89eR9cwBjfSAx9/WH5PF+/aWazZOJpVg==,iv:4qpHo143fe/sVhKfYDwxr+YiBZ2q/WWViYSwoxz0i/k=,tag:smSsJsqa6uZKarcoOMUjwQ==,type:str]
FORGEJO_INTERNAL_TOKEN: ENC[AES256_GCM,data:EIono9HSyvp1nQM0ij3ln3IUXO4moFbRgVddeV0BZBXmZG05jdjZ1SIXo/BxoSmRKnjllR7P00CpajNM5zORldlsBId5oAYL5GZtY3/nmxeXucJidknuow22G7Z8wRJJGBdishbgQhmc,iv:1D93gTUF1+DUR8qLJgML+oUhvSslhxEjGnbBC/PWHXw=,tag:NZB+mwba4TzLcUANZLDRTw==,type:str]
FORGEJO_SECRET_KEY: ENC[AES256_GCM,data:CewYFZtcXKUD5/oSM0Q32rhw+urdA0eQhdYp8EFHUXxEtL6f5NWK6IOwIlMuEv1/FjtTWlqxWekOZpmxBRzwnw==,iv:qLyVB7Nc+rDbBoO5g82/vPdykwOATHCSDLhvS+fK9PM=,tag:4NMhUvKmrRd6qrcQq3R8wA==,type:str]
sops:
kms: []
gcp_kms: []
azure_kv: []
hc_vault: []
age:
- recipient: age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA0SkxFSkJQb29UeVRnZnFh
U3BJeGZ1NUVzMk0ycXBvWExyZDcveXZrd2pJCmpCeS80VE5McWVHQnZpaHFERmNh
YWZIMHRtQkd5Vm54MWR3bkhUUDRvejQKLS0tIG9NSkpCSkEyZFRyOXorWE1KLytP
eWdXVHg5MTlQQU9GeElPeUZXUlBlaTgKceDu3tLbQM/DxY0tJYJTPy2Dl/SBYaoc
KfMZOkc322/NvgWu/3Ke0hV1/eMk8EICwXbSwHhXr5a0+cwPZ9xV4A==
-----END AGE ENCRYPTED FILE-----
lastmodified: "2024-10-16T12:28:51Z"
mac: ENC[AES256_GCM,data:nrd2czzJlBcFfwn6lzh4qqco+/XsU2J6BqvQqMtskh3mL4Xx25IAzxiCno0KlNGr6o4YsuZP5anOX9RvrDq76Us3JQ7pDi3iQGPhmg+SE9u3Rwqn1/3YConvdfPV2DNB+tuyG3UVoRqpA4d+HdcYjN9n1UKk54R6UdSm9UrA+zc=,iv:Juupyet09zUAMu7bmVxq+/Q0bXJAzR0wAyt6vKNns3w=,tag:owdUWuXrQcDdiWi+1geY9A==,type:str]
pgp:
- created_at: "2023-07-09T17:51:27Z"
enc: |-
-----BEGIN PGP MESSAGE-----
kms: []
gcp_kms: []
azure_kv: []
hc_vault: []
age:
- recipient: age18dmqd7r7fanrfmdxsvwgv9psvhs3hw5ydpvw0na0dv3dlrg4rs3q2wpvgv
enc: |
-----BEGIN AGE ENCRYPTED FILE-----
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSA0SkxFSkJQb29UeVRnZnFh
U3BJeGZ1NUVzMk0ycXBvWExyZDcveXZrd2pJCmpCeS80VE5McWVHQnZpaHFERmNh
YWZIMHRtQkd5Vm54MWR3bkhUUDRvejQKLS0tIG9NSkpCSkEyZFRyOXorWE1KLytP
eWdXVHg5MTlQQU9GeElPeUZXUlBlaTgKceDu3tLbQM/DxY0tJYJTPy2Dl/SBYaoc
KfMZOkc322/NvgWu/3Ke0hV1/eMk8EICwXbSwHhXr5a0+cwPZ9xV4A==
-----END AGE ENCRYPTED FILE-----
lastmodified: "2023-07-17T11:48:04Z"
mac: ENC[AES256_GCM,data:Bgmm5+IrFdnTG907cZe0cnSmbWLyNDVYyABFj5eRuGsYCthclRM9WEKktvJg2RVYcND39IEH/FiFR/Hxf5YgrUcU7HKEXKzn7U4AGcREh2tb5EVTELjAJ4e00omNoD1gmFOklRS9AWce1g03AGzfbzM68enpDUkxWWTU2FOPei8=,iv:A9V4EsMAIoEs7j/eWy06Y9RExz+N/PT70TBNSViswKc=,tag:287n8ygaEj/40vh1x2IQig==,type:str]
pgp:
- created_at: "2023-07-09T17:51:27Z"
enc: |-
-----BEGIN PGP MESSAGE-----
wcBMA0SHG/zF3227AQgAs92CvegZAcuyNllIp9zHUp7jFqfXhuoAOKKmOZvN4TBD
gQM7jKAXXwbMy90gGWF9EkdMzeBqG4S9ZM8gPAYcZkt98F0PGu6wBSvvYnUdDOcO
8tvhEhBSE19xCIR7BeG9bhooEJ1V3LSZzrwyikeHUHAqDQLrwM7jrPOef22PIzH+
XPtwWMVwVzwRJTZ/uV11vIV60b0zfnB8ZJzv7RbXsob8octy4LRe6Vb0BUd5ON3w
YULnyMlFFGekiqAPBk0K5Xib35qBu6mtnmxWzVUqT4pgiShoZsRQs3At1Onm7Cku
bqIDMoCYTvSzwDCOYp2+ni/ZOIuDvBiRCPoNuLjkD9JRAcCbjuxA6w0eaJKFTzoI
F1olIecBtQOQQn+iXya/rx69wDtR9965gecWRMbRg6tYncumpdQB//MWALhVmr6i
g+ZF+9NNqOTKsBzEnuGsZRnI
=iXfo
-----END PGP MESSAGE-----
fp: 6F7069FE6B96E894E60EC45C6EEFA706CB17E89B
unencrypted_suffix: _unencrypted
version: 3.8.1
wcBMA0SHG/zF3227AQgAs92CvegZAcuyNllIp9zHUp7jFqfXhuoAOKKmOZvN4TBD
gQM7jKAXXwbMy90gGWF9EkdMzeBqG4S9ZM8gPAYcZkt98F0PGu6wBSvvYnUdDOcO
8tvhEhBSE19xCIR7BeG9bhooEJ1V3LSZzrwyikeHUHAqDQLrwM7jrPOef22PIzH+
XPtwWMVwVzwRJTZ/uV11vIV60b0zfnB8ZJzv7RbXsob8octy4LRe6Vb0BUd5ON3w
YULnyMlFFGekiqAPBk0K5Xib35qBu6mtnmxWzVUqT4pgiShoZsRQs3At1Onm7Cku
bqIDMoCYTvSzwDCOYp2+ni/ZOIuDvBiRCPoNuLjkD9JRAcCbjuxA6w0eaJKFTzoI
F1olIecBtQOQQn+iXya/rx69wDtR9965gecWRMbRg6tYncumpdQB//MWALhVmr6i
g+ZF+9NNqOTKsBzEnuGsZRnI
=iXfo
-----END PGP MESSAGE-----
fp: 6F7069FE6B96E894E60EC45C6EEFA706CB17E89B
unencrypted_suffix: _unencrypted
version: 3.7.3

View file

@ -1,25 +1,20 @@
{
dir,
pkgs ? import <channels-nixos-stable> { },
ownLib ? import ../lib/default.nix { inherit (pkgs) lib; },
pkgs ? import <channels-nixos-stable> {},
ownLib ? import ../lib/default.nix {inherit (pkgs) lib;},
gitRoot ? "$(git rev-parse --show-toplevel)",
# FIXME: why do these need explicit mentioning?
moreargs ? "",
rebuildarg ? "",
...
}@args:
let
rebuildargsSudo = [
"switch"
"boot"
];
rebuild =
{
gitRoot,
rebuildarg ? "dry-activate",
moreargs ? "",
...
}:
} @ args: let
rebuildargsSudo = ["switch" "boot"];
rebuild = {
gitRoot,
rebuildarg ? "dry-activate",
moreargs ? "",
...
}:
pkgs.writeScript "script" ''
#!/usr/bin/env bash
set -xe
@ -35,24 +30,25 @@ let
${
if
(builtins.elem rebuildarg rebuildargsSudo) && (builtins.match ".*--target-host.*" moreargs) == null
then
"sudo -E \\"
else
""
(builtins.elem rebuildarg rebuildargsSudo)
&& (builtins.match ".*--target-host.*" moreargs) == null
then "sudo -E \\"
else ""
}
nixos-rebuild --show-trace -I nixos-config=''${NIXOS_CONFIG} ${rebuildarg} ${moreargs}
'';
in
{
recipes = {
rebuild = rebuild {
inherit gitRoot;
inherit moreargs;
inherit rebuildarg;
in {
recipes =
{
rebuild =
rebuild {
inherit gitRoot;
inherit moreargs;
inherit rebuildarg;
}
# // pkgs.lib.attrsets.optionalAttrs (moreargs != "") { inherit moreargs; }
# // pkgs.lib.attrsets.optionalAttrs (rebuildarg != "") { inherit rebuildarg; }
;
}
# // pkgs.lib.attrsets.optionalAttrs (moreargs != "") { inherit moreargs; }
# // pkgs.lib.attrsets.optionalAttrs (rebuildarg != "") { inherit rebuildarg; }
;
} // (import ./disk.nix (args // { inherit pkgs ownLib gitRoot; }));
// (import ./disk.nix (args // {inherit pkgs ownLib gitRoot;}));
}

View file

@ -3,29 +3,40 @@
ownLib,
dir,
gitRoot,
diskId ? (import ((builtins.getEnv "PWD") + "/${dir}/hw.nix") { }).hardware.opinionatedDisk.diskId,
diskId ?
(import ((builtins.getEnv "PWD") + "/${dir}/hw.nix")
{})
.hardware
.opinionatedDisk
.diskId,
encrypted ?
(import ((builtins.getEnv "PWD") + "/${dir}/hw.nix") { }).hardware.opinionatedDisk.encrypted,
(import ((builtins.getEnv "PWD") + "/${dir}/hw.nix")
{})
.hardware
.opinionatedDisk
.encrypted,
previousDiskId ? "",
...
}:
let
}: let
mntRootVol = "/mnt/${diskId}-root";
in
rec {
in rec {
diskMount = pkgs.writeScript "script" ''
#!/usr/bin/env bash
set -xe
echo Mounting ${diskId}
${pkgs.lib.strings.optionalString encrypted ''
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${ownLib.disk.luksName diskId}
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${
ownLib.disk.luksName diskId
}
''}
sleep 1
sudo vgchange -ay ${ownLib.disk.volumeGroup diskId}
sudo mkdir -p /mnt
sudo mkdir ${mntRootVol}
sudo mount ${ownLib.disk.rootFsDevice diskId} ${mntRootVol}
sudo mount ${ownLib.disk.rootFsDevice diskId} ${mntRootVol}/nixos/home -o subvol=home
sudo mount ${
ownLib.disk.rootFsDevice diskId
} ${mntRootVol}/nixos/home -o subvol=home
sudo mount ${ownLib.disk.bootFsDevice diskId} ${mntRootVol}/nixos/boot
'';
@ -62,7 +73,9 @@ rec {
#!/usr/bin/env bash
set -xe
read -p "Continue to format ${ownLib.disk.bootGrubDevice diskId} (YES/n)? " choice
read -p "Continue to format ${
ownLib.disk.bootGrubDevice diskId
} (YES/n)? " choice
case "$choice" in
YES ) echo "Continuing in 3 seconds..."; sleep 3;;
n|N ) echo "Exiting..."; exit 0;;
@ -109,11 +122,15 @@ rec {
${pkgs.lib.strings.optionalString encrypted ''
# Encrypt
sudo cryptsetup luksFormat ${ownLib.disk.bootLuksDevice diskId} -
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${ownLib.disk.luksName diskId}
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${
ownLib.disk.luksName diskId
}
''}
# LVM
sudo vgcreate ${ownLib.disk.volumeGroup diskId} ${ownLib.disk.lvmPv diskId encrypted}
sudo vgcreate ${ownLib.disk.volumeGroup diskId} ${
ownLib.disk.lvmPv diskId encrypted
}
sudo lvcreate ${ownLib.disk.volumeGroup diskId} -L 2G -n swap
sudo lvcreate ${ownLib.disk.volumeGroup diskId} -l 100%FREE -n root
@ -137,7 +154,9 @@ rec {
#!/usr/bin/env bash
set -xe
read -p "Continue to relabel ${ownLib.disk.bootGrubDevice diskId} (YES/n)?" choice
read -p "Continue to relabel ${
ownLib.disk.bootGrubDevice diskId
} (YES/n)?" choice
case "$choice" in
YES ) echo "Continuing in 3 seconds..."; sleep 3;;
n|N ) echo "Exiting..."; exit 0;;
@ -168,9 +187,13 @@ rec {
if test "${previousDiskId}"; then
${pkgs.lib.strings.optionalString encrypted ''
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${ownLib.disk.luksName diskId}
''}
${
pkgs.lib.strings.optionalString encrypted ''
sudo cryptsetup luksOpen ${ownLib.disk.bootLuksDevice diskId} ${
ownLib.disk.luksName diskId
}
''
}
sync
sleep 1
if sudo vgs ${previousDiskId}; then

View file

@ -1,5 +1,4 @@
{ lib, ... }:
{
{lib, ...}: {
boot.loader.grub.efiSupport = lib.mkForce false;
boot.loader.efi.canTouchEfiVariables = lib.mkForce false;
}

View file

@ -1,5 +1,4 @@
{ ... }:
{
{...}: {
imports = [
../../profiles/common/configuration.nix
../../profiles/graphical/configuration.nix

View file

@ -3,17 +3,17 @@
repoFlake,
nodeFlake,
...
}:
let
}: let
system = "x86_64-linux";
in
{
in {
meta.nodeSpecialArgs.${nodeName} = {
inherit repoFlake nodeName nodeFlake;
packages' = repoFlake.packages.${system};
};
meta.nodeNixpkgs.${nodeName} = import nodeFlake.inputs.nixpkgs.outPath { inherit system; };
meta.nodeNixpkgs.${nodeName} = import nodeFlake.inputs.nixpkgs.outPath {
inherit system;
};
${nodeName} = {
deployment.targetHost = "elias-e525.lan";

View file

@ -6,5 +6,5 @@
inputs.nixpkgs.follows = "nixpkgs";
};
outputs = _: { };
outputs = _: {};
}

View file

@ -1,4 +1,4 @@
_: {
{...}: {
# TASK: new device
hardware.opinionatedDisk = {
enable = true;

View file

@ -1,5 +1,8 @@
{ pkgs, lib, ... }:
let
{
pkgs,
lib,
...
}: let
homeEnv = keyboard: {
imports = [
../../../home-manager/profiles/common.nix
@ -19,27 +22,26 @@ let
rustdesk
];
};
in
{
services.gnome = builtins.mapAttrs (_attr: value: lib.mkForce value) {
in {
services.gnome = builtins.mapAttrs (attr: value: lib.mkForce value) {
gnome-remote-desktop.enable = true;
};
home-manager.users.steveej = homeEnv {
layout = "en";
options = [ "nodeadkey" ];
options = ["nodeadkey"];
variant = "altgr-intl";
};
home-manager.users.elias = homeEnv {
layout = "de";
options = [ ];
options = [];
variant = "";
};
home-manager.users.justyna = homeEnv {
layout = "de";
options = [ ];
options = [];
variant = "";
};

View file

@ -1,5 +1,10 @@
{ pkgs, lib, ... }:
{
pkgs,
lib,
config,
...
}: let
in {
# TASK: new device
networking.hostName = "elias-e525"; # Define your hostname.
@ -33,13 +38,11 @@
# udev.packages = [ pkgs.gnome3.gnome-settings-daemon ];
};
security.pki.certificateFiles = [ "${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt" ];
security.pki.certificateFiles = ["${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt"];
services.xserver.videoDrivers = [ "modesetting" ];
services.xserver.videoDrivers = ["modesetting"];
boot.kernelPackages = lib.mkForce pkgs.linuxPackages_latest;
nix.gc = {
automatic = true;
};
nix.gc = {automatic = true;};
}

View file

@ -1,9 +1,12 @@
{ config, pkgs, ... }:
let
keys = import ../../../variables/keys.nix;
inherit (pkgs.callPackage ../../lib/default.nix { }) mkUser;
in
{
config,
pkgs,
lib,
...
}: let
keys = import ../../../variables/keys.nix;
inherit (pkgs.callPackage ../../lib/default.nix {}) mkUser;
in {
sops.secrets.sharedUsers-elias = {
sopsFile = ../../../../secrets/shared-users.yaml;
neededForUsers = true;

View file

@ -1,5 +1,4 @@
{ lib, ... }:
{
{lib, ...}: {
boot.loader.grub.efiInstallAsRemovable = lib.mkForce true;
boot.loader.efi.canTouchEfiVariables = lib.mkForce false;
}

View file

@ -1,5 +1,4 @@
{ ... }:
{
{...}: {
imports = [
../../profiles/common/configuration.nix
../../modules/opinionatedDisk.nix

View file

@ -1,4 +1,5 @@
_: {
{...}: let
in {
# TASK: new device
hardware.opinionatedDisk = {
enable = true;

View file

@ -1,17 +1,17 @@
{ pkgs, ... }:
{
nixpkgs.config.packageOverrides =
pkgs: with pkgs; {
inherit ((import ../../../default.nix { versionsPath = ./versions.nix; })) nixPath;
{pkgs, ...}: {
nixpkgs.config.packageOverrides = pkgs:
with pkgs; {
nixPath =
(import ../../../default.nix {
versionsPath = ./versions.nix;
})
.nixPath;
};
home-manager.users.steveej = import ../../../home-manager/configuration/text-minimal.nix {
inherit pkgs;
};
environment.systemPackages = with pkgs; [
iw
wirelesstools
];
environment.systemPackages = with pkgs; [iw wirelesstools];
system.stateVersion = "21.11";
}

View file

@ -1,8 +1,12 @@
{ pkgs, lib, ... }:
let
passwords = import ../../../variables/passwords.crypt.nix;
in
{
pkgs,
lib,
config,
...
}: let
keys = import ../../../variables/keys.nix;
passwords = import ../../../variables/passwords.crypt.nix;
in {
# TASK: new device
networking.hostName = "fwhost1"; # Define your hostname.
@ -17,14 +21,11 @@ in
networking.firewall.logRefusedConnections = false;
networking.usePredictableInterfaceNames = false;
networking.bridges.breth.interfaces = [
"eth0"
"eth1"
];
networking.bridges.breth.interfaces = ["eth0" "eth1"];
networking.bridges.breth.rstp = true;
networking.defaultGateway.address = "172.172.171.10";
networking.nameservers = [ "172.172.171.10" ];
networking.nameservers = ["172.172.171.10"];
# WAN interfaces, currently unused because the OPNsense guest acts as a router.
networking.vlans.wan1.id = 3;

View file

@ -1 +1,9 @@
_: { }
{
config,
pkgs,
...
}: let
passwords = import ../../../variables/passwords.crypt.nix;
keys = import ../../../variables/keys.nix;
inherit (import ../../lib/default.nix {}) mkUser;
in {}

View file

@ -4,12 +4,9 @@ let
ref = "nixos-21.11";
rev = "386234e2a61e1e8acf94dfa3a3d3ca19a6776efb";
};
in
{
in {
inherit nixpkgs;
nixos = nixpkgs // {
suffix = "/nixos";
};
nixos = nixpkgs // {suffix = "/nixos";};
"channels-nixos-stable" = nixpkgs;
"channels-nixos-unstable" = {

View file

@ -6,12 +6,9 @@ let
<% git ls-remote https://github.com/nixos/nixpkgs nixos-21.11 | awk '{ print $1 }' | tr -d '
' -%>'';
};
in
{
in {
inherit nixpkgs;
nixos = nixpkgs // {
suffix = "/nixos";
};
nixos = nixpkgs // {suffix = "/nixos";};
"channels-nixos-stable" = nixpkgs;
"channels-nixos-unstable" = {

View file

@ -1,5 +1,4 @@
{ lib, ... }:
{
{lib, ...}: {
boot.loader.grub.efiInstallAsRemovable = lib.mkForce true;
boot.loader.efi.canTouchEfiVariables = lib.mkForce false;
}

View file

@ -1,5 +1,4 @@
{ ... }:
{
{...}: {
imports = [
../../profiles/common/configuration.nix
../../modules/opinionatedDisk.nix

View file

@ -1,4 +1,5 @@
_: {
{...}: let
in {
# TASK: new device
hardware.opinionatedDisk = {
enable = true;

View file

@ -1,17 +1,17 @@
{ pkgs, ... }:
{
nixpkgs.config.packageOverrides =
pkgs: with pkgs; {
inherit ((import ../../../default.nix { versionsPath = ./versions.nix; })) nixPath;
{pkgs, ...}: {
nixpkgs.config.packageOverrides = pkgs:
with pkgs; {
nixPath =
(import ../../../default.nix {
versionsPath = ./versions.nix;
})
.nixPath;
};
home-manager.users.steveej = import ../../../home-manager/configuration/text-minimal.nix {
inherit pkgs;
};
environment.systemPackages = with pkgs; [
iw
wirelesstools
];
environment.systemPackages = with pkgs; [iw wirelesstools];
system.stateVersion = "21.11";
}

View file

@ -1,8 +1,13 @@
{ pkgs, lib, ... }:
let
passwords = import ../../../variables/passwords.crypt.nix;
in
{
pkgs,
lib,
config,
utils,
...
}: let
keys = import ../../../variables/keys.nix;
passwords = import ../../../variables/passwords.crypt.nix;
in {
# TASK: new device
networking.hostName = "fwhost2"; # Define your hostname.
@ -17,14 +22,11 @@ in
networking.firewall.logRefusedConnections = false;
networking.usePredictableInterfaceNames = false;
networking.bridges.breth.interfaces = [
"eth0"
"eth1"
];
networking.bridges.breth.interfaces = ["eth0" "eth1"];
networking.bridges.breth.rstp = true;
networking.defaultGateway.address = "172.172.171.10";
networking.nameservers = [ "172.172.171.10" ];
networking.nameservers = ["172.172.171.10"];
# WAN interfaces, currently unused because the OPNsense guest acts as a router.
networking.vlans.wan1.id = 3;

View file

@ -1,4 +1,12 @@
_: {
{
config,
pkgs,
...
}: let
passwords = import ../../../variables/passwords.crypt.nix;
keys = import ../../../variables/keys.nix;
inherit (import ../../lib/default.nix {inherit (pkgs) lib;}) mkUser;
in {
# users.extraUsers.steveej2 = mkUser {
# uid = 1001;
# openssh.authorizedKeys.keys = keys.users.steveej.openssh;

View file

@ -4,12 +4,9 @@ let
ref = "nixos-21.11";
rev = "386234e2a61e1e8acf94dfa3a3d3ca19a6776efb";
};
in
{
in {
inherit nixpkgs;
nixos = nixpkgs // {
suffix = "/nixos";
};
nixos = nixpkgs // {suffix = "/nixos";};
"channels-nixos-stable" = nixpkgs;
"channels-nixos-unstable" = {

View file

@ -6,12 +6,9 @@ let
<% git ls-remote https://github.com/nixos/nixpkgs nixos-21.11 | awk '{ print $1 }' | tr -d '
' -%>'';
};
in
{
in {
inherit nixpkgs;
nixos = nixpkgs // {
suffix = "/nixos";
};
nixos = nixpkgs // {suffix = "/nixos";};
"channels-nixos-stable" = nixpkgs;
"channels-nixos-unstable" = {

View file

@ -1,146 +0,0 @@
{
repoFlake,
pkgs,
lib,
nodeFlake,
nodeName,
system,
...
}:
{
disabledModules = [ ];
imports = [
nodeFlake.inputs.disko.nixosModules.disko
repoFlake.inputs.sops-nix.nixosModules.sops
nodeFlake.inputs.srvos.nixosModules.roles-nix-remote-builder
{
roles.nix-remote-builder.schedulerPublicKeys = [
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINQ22z5rDdCLYH+MEoEt+tXJXTJqoeZNqvJl2n4aB+Kn steveej@steveej-x13s"
# TODO: make this a reference to the private key's secret
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIC8FHuK0k86iBWq41+NAhVwJqH1ZpGJe+q01m7iLviz6 root@steveej-t14"
];
}
../../snippets/nix-settings.nix
{ nix.settings.sandbox = lib.mkForce "relaxed"; }
../../snippets/mycelium.nix
# user config
../../profiles/common/user.nix
{
users.commonUsers = {
enable = true;
enableNonRoot = true;
};
}
../../snippets/home-manager-with-zsh.nix
# {
# home-manager.users.steveej = {pkgs, ...}: {
# imports = [
# ../../../home-manager/programs/pass.nix
# ../../../home-manager/programs/openvscode-server.nix
# ];
# };
# }
];
services.openssh = {
enable = true;
openFirewall = true;
settings.PermitRootLogin = "yes";
extraConfig = ''
StreamLocalBindUnlink yes
'';
};
boot = {
kernel = {
sysctl = {
"net.ipv4.conf.all.forwarding" = true;
"net.ipv6.conf.all.forwarding" = true;
};
};
};
networking = {
hostName = nodeName;
useNetworkd = true;
useDHCP = true;
nat.enable = true;
firewall.enable = true;
firewall.allowedTCPPorts = [ 5201 ];
firewall.allowedUDPPorts = [ 5201 ];
};
disko.devices =
let
disk = id: {
type = "disk";
device = "/dev/${id}";
content = {
type = "gpt";
partitions = {
boot = {
size = "1M";
type = "EF02"; # for grub MBR
};
mdadm = {
size = "100%";
content = {
type = "mdraid";
name = "raid0";
};
};
};
};
};
in
{
disk = {
sda = disk "sda";
sdb = disk "sdb";
};
mdadm = {
raid0 = {
type = "mdadm";
level = 0;
content = {
type = "gpt";
partitions = {
primary = {
size = "100%";
content = {
type = "filesystem";
format = "btrfs";
mountpoint = "/";
};
};
};
};
};
};
};
system.stateVersion = "24.05";
boot.kernelPackages = pkgs.linuxPackages_latest;
boot.initrd.includeDefaultModules = true;
boot.initrd.kernelModules = [
"dm-raid"
"dm-integrity"
"xhci_pci_renesas"
];
hardware.enableRedistributableFirmware = true;
virtualisation.libvirtd.enable = true;
boot.binfmt.emulatedSystems = [ "aarch64-linux" ];
}

View file

@ -1,124 +0,0 @@
{
"nodes": {
"disko": {
"inputs": {
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1719401812,
"narHash": "sha256-QONBQ/arBsKZNJuSd3sMIkSYFlBoRJpvf1jGlMfcOuI=",
"owner": "nix-community",
"repo": "disko",
"rev": "b6a1262796b2990ec3cc60bb2ec23583f35b2f43",
"type": "github"
},
"original": {
"owner": "nix-community",
"repo": "disko",
"type": "github"
}
},
"get-flake": {
"locked": {
"lastModified": 1714237590,
"narHash": "sha256-9gtHdGbzFHaR20xORN8IYd67ROWS+1nqQ5CsPf9MD8I=",
"owner": "ursi",
"repo": "get-flake",
"rev": "a6c57417d1b857b8be53aba4095869a0f438c502",
"type": "github"
},
"original": {
"owner": "ursi",
"repo": "get-flake",
"type": "github"
}
},
"home-manager": {
"inputs": {
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1718530513,
"narHash": "sha256-BmO8d0r+BVlwWtMLQEYnwmngqdXIuyFzMwvmTcLMee8=",
"owner": "nix-community",
"repo": "home-manager",
"rev": "a1fddf0967c33754271761d91a3d921772b30d0e",
"type": "github"
},
"original": {
"owner": "nix-community",
"ref": "release-24.05",
"repo": "home-manager",
"type": "github"
}
},
"nixpkgs": {
"locked": {
"lastModified": 1719253556,
"narHash": "sha256-A/76RFUVxZ/7Y8+OMVL1Lc8LRhBxZ8ZE2bpMnvZ1VpY=",
"owner": "nixos",
"repo": "nixpkgs",
"rev": "fc07dc3bdf2956ddd64f24612ea7fc894933eb2e",
"type": "github"
},
"original": {
"owner": "nixos",
"ref": "nixos-24.05",
"repo": "nixpkgs",
"type": "github"
}
},
"nixpkgs-unstable": {
"locked": {
"lastModified": 1719254875,
"narHash": "sha256-ECni+IkwXjusHsm9Sexdtq8weAq/yUyt1TWIemXt3Ko=",
"owner": "nixos",
"repo": "nixpkgs",
"rev": "2893f56de08021cffd9b6b6dfc70fd9ccd51eb60",
"type": "github"
},
"original": {
"owner": "nixos",
"ref": "nixos-unstable",
"repo": "nixpkgs",
"type": "github"
}
},
"root": {
"inputs": {
"disko": "disko",
"get-flake": "get-flake",
"home-manager": "home-manager",
"nixpkgs": "nixpkgs",
"nixpkgs-unstable": "nixpkgs-unstable",
"srvos": "srvos"
}
},
"srvos": {
"inputs": {
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1719189969,
"narHash": "sha256-6MSZrWvXSvUKIr0iC9eSbQ09NSm+j1Oh4o9Gentu1CU=",
"owner": "numtide",
"repo": "srvos",
"rev": "4f314be1307c8d5f1fb3d882a67e09dbdf285850",
"type": "github"
},
"original": {
"owner": "numtide",
"repo": "srvos",
"type": "github"
}
}
},
"root": "root",
"version": 7
}

View file

@ -1,52 +0,0 @@
{
inputs = {
nixpkgs.url = "github:nixos/nixpkgs/nixos-24.05";
nixpkgs-unstable.url = "github:nixos/nixpkgs/nixos-unstable";
get-flake.url = "github:ursi/get-flake";
home-manager.url = "github:nix-community/home-manager/release-24.05";
home-manager.inputs.nixpkgs.follows = "nixpkgs";
disko.url = "github:nix-community/disko";
disko.inputs.nixpkgs.follows = "nixpkgs";
srvos.url = "github:numtide/srvos";
srvos.inputs.nixpkgs.follows = "nixpkgs";
};
# outputs = _: {};
outputs =
{
self,
get-flake,
nixpkgs,
...
}:
let
system = "x86_64-linux";
nodeName = "hostkey-0";
mkNixosConfiguration =
{
extraModules ? [ ],
...
}@attrs:
nixpkgs.lib.nixosSystem (
nixpkgs.lib.attrsets.recursiveUpdate attrs {
specialArgs = {
nodeFlake = self;
repoFlake = get-flake ../../../..;
inherit nodeName;
};
modules = [ ./configuration.nix ] ++ extraModules;
}
);
in
{
nixosConfigurations = {
native = mkNixosConfiguration { inherit system; };
};
};
}

View file

@ -1,24 +1,16 @@
{
"enabled": 1,
"hidden": false,
"description": "Jobsets",
"nixexprinput": "src",
"nixexprpath": "default.nix",
"checkinterval": 300,
"schedulingshares": 100,
"enableemail": false,
"emailoverride": "",
"keepnr": 3,
"inputs": {
"src": {
"type": "git",
"value": "git://github.com/shlevy/declarative-hydra-example.git",
"emailresponsible": false
},
"nixpkgs": {
"type": "git",
"value": "git://github.com/NixOS/nixpkgs.git release-16.03",
"emailresponsible": false
"enabled": 1,
"hidden": false,
"description": "Jobsets",
"nixexprinput": "src",
"nixexprpath": "default.nix",
"checkinterval": 300,
"schedulingshares": 100,
"enableemail": false,
"emailoverride": "",
"keepnr": 3,
"inputs": {
"src": { "type": "git", "value": "git://github.com/shlevy/declarative-hydra-example.git", "emailresponsible": false },
"nixpkgs": { "type": "git", "value": "git://github.com/NixOS/nixpkgs.git release-16.03", "emailresponsible": false }
}
}
}

View file

@ -1,5 +1,4 @@
{ lib, ... }:
{
{lib, ...}: {
boot.loader.grub.efiInstallAsRemovable = lib.mkForce false;
boot.loader.efi.canTouchEfiVariables = lib.mkForce false;
boot.loader.grub.efiSupport = lib.mkForce false;

View file

@ -1,5 +1,4 @@
{ ... }:
{
{...}: {
imports = [
../../profiles/common/configuration.nix
../../profiles/graphical/configuration.nix

View file

@ -3,17 +3,17 @@
repoFlake,
nodeFlake,
...
}:
let
}: let
system = "x86_64-linux";
in
{
in {
meta.nodeSpecialArgs.${nodeName} = {
inherit repoFlake nodeName nodeFlake;
packages' = repoFlake.packages.${system};
};
meta.nodeNixpkgs.${nodeName} = import nodeFlake.inputs.nixpkgs.outPath { inherit system; };
meta.nodeNixpkgs.${nodeName} = import nodeFlake.inputs.nixpkgs.outPath {
inherit system;
};
${nodeName} = {
deployment.targetHost = nodeName;

View file

@ -6,8 +6,8 @@
inputs.nixpkgs.follows = "nixpkgs";
};
inputs.disko.url = "github:nix-community/disko";
inputs.disko.url = github:nix-community/disko;
inputs.disko.inputs.nixpkgs.follows = "nixpkgs";
outputs = _: { };
outputs = _: {};
}

View file

@ -1,6 +1,12 @@
{ nodeFlake, ... }:
{
imports = [ nodeFlake.inputs.disko.nixosModules.disko ];
repoFlake,
nodeFlake,
lib,
...
}: {
imports = [
nodeFlake.inputs.disko.nixosModules.disko
];
disko.devices.disk.sda = {
device = "/dev/sda";
@ -14,7 +20,7 @@
start = "0";
end = "1M";
part-type = "primary";
flags = [ "bios_grub" ];
flags = ["bios_grub"];
}
{
name = "root";
@ -24,14 +30,14 @@
bootable = true;
content = {
type = "btrfs";
extraArgs = [ "-f" ]; # Override existing partition
extraArgs = ["-f"]; # Override existing partition
subvolumes = {
# Subvolume name is different from mountpoint
"/rootfs" = {
mountpoint = "/";
};
"/nix" = {
mountOptions = [ "noatime" ];
mountOptions = ["noatime"];
};
};
};

View file

@ -3,8 +3,7 @@
lib,
packages',
...
}:
let
}: let
homeEnv = keyboard: {
imports = [
../../../home-manager/profiles/common.nix
@ -24,19 +23,15 @@ let
rustdesk
];
};
in
{
services.gnome = builtins.mapAttrs (_attr: value: lib.mkForce value) {
in {
services.gnome = builtins.mapAttrs (attr: value: lib.mkForce value) {
gnome-remote-desktop.enable = true;
};
services.printing.drivers = lib.mkForce (
with packages';
[
dcpj4110dwDriver
dcpj4110dwCupswrapper
]
);
services.printing.drivers = lib.mkForce (with packages'; [
dcpj4110dwDriver
dcpj4110dwCupswrapper
]);
services.printing.extraConf = ''
LogLevel debug
@ -44,29 +39,31 @@ in
home-manager.users.steveej = homeEnv {
layout = "en";
options = [ "nodeadkey" ];
options = ["nodeadkey"];
variant = "altgr-intl";
};
home-manager.users.elias = homeEnv {
layout = "de";
options = [ ];
options = [];
variant = "";
};
home-manager.users.justyna =
lib.attrsets.recursiveUpdate
(homeEnv {
layout = "de";
options = [ ];
variant = "";
})
{
services.syncthing.enable = true;
services.syncthing.tray = true;
(homeEnv {
layout = "de";
options = [];
variant = "";
})
{
services.syncthing.enable = true;
services.syncthing.tray = true;
home.packages = with pkgs; [ session-desktop ];
};
home.packages = with pkgs; [
session-desktop
];
};
system.stateVersion = "21.11";
}

View file

@ -1,8 +1,11 @@
{ pkgs, lib, ... }:
let
passwords = import ../../../variables/passwords.crypt.nix;
in
{
pkgs,
lib,
config,
...
}: let
passwords = import ../../../variables/passwords.crypt.nix;
in {
networking.firewall.enable = true;
networking.firewall.allowedTCPPorts = [
# iperf3
@ -36,13 +39,11 @@ in
# udev.packages = [ pkgs.gnome3.gnome-settings-daemon ];
};
security.pki.certificateFiles = [ "${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt" ];
security.pki.certificateFiles = ["${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt"];
services.xserver.videoDrivers = [ "modesetting" ];
services.xserver.videoDrivers = ["modesetting"];
boot.kernelPackages = lib.mkForce pkgs.linuxPackages_latest;
nix.gc = {
automatic = true;
};
nix.gc = {automatic = true;};
}

View file

@ -1,9 +1,11 @@
{ config, pkgs, ... }:
let
keys = import ../../../variables/keys.nix;
inherit (pkgs.callPackage ../../lib/default.nix { }) mkUser;
in
{
config,
pkgs,
...
}: let
keys = import ../../../variables/keys.nix;
inherit (pkgs.callPackage ../../lib/default.nix {}) mkUser;
in {
sops.secrets.sharedUsers-elias = {
sopsFile = ../../../../secrets/shared-users.yaml;
neededForUsers = true;

File diff suppressed because it is too large Load diff

View file

@ -5,24 +5,25 @@
nodeFlake,
localDomainName ? "internal",
...
}:
{
}: {
meta.nodeSpecialArgs.${nodeName} = {
inherit
repoFlake
nodeName
nodeFlake
system
;
inherit repoFlake nodeName nodeFlake system;
packages' = repoFlake.packages.${system};
nodePackages' = nodeFlake.packages.${system};
inherit (nodeFlake.inputs.bpir3.packages.${system}) armTrustedFirmwareMT7986;
inherit
(nodeFlake.inputs.bpir3.packages.${system})
armTrustedFirmwareMT7986
;
inherit localDomainName;
};
meta.nodeNixpkgs.${nodeName} = import nodeFlake.inputs.nixpkgs.outPath { inherit system; };
meta.nodeNixpkgs.${nodeName} =
import nodeFlake.inputs.nixpkgs.outPath
{
inherit system;
};
${nodeName} = {
deployment.targetHost = "${nodeName}.${localDomainName}";

Some files were not shown because too many files have changed in this diff Show more