#; common fixtures function load_fixtures() { export DEFAULT_YADM_DIR="$HOME/.yadm" export DEFAULT_REPO="repo.git" export DEFAULT_CONFIG="config" export DEFAULT_ENCRYPT="encrypt" export DEFAULT_ARCHIVE="files.gpg" export DEFAULT_BOOTSTRAP="bootstrap" export T_YADM="$PWD/yadm" export T_TMP="$BATS_TMPDIR/ytmp" export T_DIR_YADM="$T_TMP/.yadm" export T_DIR_WORK="$T_TMP/yadm-work" export T_DIR_REPO="$T_DIR_YADM/repo.git" export T_YADM_CONFIG="$T_DIR_YADM/config" export T_YADM_ENCRYPT="$T_DIR_YADM/encrypt" export T_YADM_ARCHIVE="$T_DIR_YADM/files.gpg" export T_YADM_BOOTSTRAP="$T_DIR_YADM/bootstrap" export T_YADM_Y T_YADM_Y=( "$T_YADM" -Y "$T_DIR_YADM" ) export T_SYS T_SYS=$(uname -s) export T_HOST T_HOST=$(hostname -s) export T_USER T_USER=$(id -u -n) } function configure_git() { (git config user.name || git config --global user.name 'test') >/dev/null (git config user.email || git config --global user.email 'test@test.test') > /dev/null } function make_parents() { local parent_dir parent_dir=$(dirname "$@") mkdir -p "$parent_dir" } function test_perms() { local test_path="$1" local regex="$2" local ls ls=$(ls -ld "$test_path") local perms="${ls:0:10}" if [[ ! $perms =~ $regex ]]; then echo "ERROR: Found permissions $perms for $test_path" return 1 fi return 0 } function test_repo_attribute() { local repo_dir="$1" local attribute="$2" local expected="$3" local actual actual=$(GIT_DIR="$repo_dir" git config --local "$attribute") if [ "$actual" != "$expected" ]; then echo "ERROR: repo attribute $attribute set to $actual" return 1 fi return 0 } #; create worktree at path function create_worktree() { local DIR_WORKTREE="$1" if [ -z "$DIR_WORKTREE" ]; then echo "ERROR: create_worktree() called without a path" return 1 fi if [[ ! "$DIR_WORKTREE" =~ ^$T_TMP ]]; then echo "ERROR: create_worktree() called with a path outside of $T_TMP" return 1 fi #; remove any existing data rm -rf "$DIR_WORKTREE" #; create some standard files if [ ! -z "$TEST_TREE_WITH_ALT" ] ; then for f in \ "alt-none##S" \ "alt-none##S.H" \ "alt-none##S.H.U" \ "alt-base##" \ "alt-base##S" \ "alt-base##S.H" \ "alt-base##S.H.U" \ "alt-system##" \ "alt-system##S" \ "alt-system##S.H" \ "alt-system##S.H.U" \ "alt-system##$T_SYS" \ "alt-host##" \ "alt-host##S" \ "alt-host##S.H" \ "alt-host##S.H.U" \ "alt-host##$T_SYS.$T_HOST" \ "alt-host##${T_SYS}_${T_HOST}" \ "alt-user##" \ "alt-user##S" \ "alt-user##S.H" \ "alt-user##S.H.U" \ "alt-user##$T_SYS.$T_HOST.$T_USER" \ "alt-user##${T_SYS}_${T_HOST}_${T_USER}" \ "alt-override-system##" \ "alt-override-system##$T_SYS" \ "alt-override-system##custom_system" \ "alt-override-host##" \ "alt-override-host##$T_SYS.$T_HOST" \ "alt-override-host##$T_SYS.custom_host" \ "alt-override-user##" \ "alt-override-user##S.H.U" \ "alt-override-user##$T_SYS.$T_HOST.custom_user" \ "dir one/alt-none##S/file1" \ "dir one/alt-none##S/file2" \ "dir one/alt-none##S.H/file1" \ "dir one/alt-none##S.H/file2" \ "dir one/alt-none##S.H.U/file1" \ "dir one/alt-none##S.H.U/file2" \ "dir one/alt-base##/file1" \ "dir one/alt-base##/file2" \ "dir one/alt-base##S/file1" \ "dir one/alt-base##S/file2" \ "dir one/alt-base##S.H/file1" \ "dir one/alt-base##S.H/file2" \ "dir one/alt-base##S.H.U/file1" \ "dir one/alt-base##S.H.U/file2" \ "dir one/alt-system##/file1" \ "dir one/alt-system##/file2" \ "dir one/alt-system##S/file1" \ "dir one/alt-system##S/file2" \ "dir one/alt-system##S.H/file1" \ "dir one/alt-system##S.H/file2" \ "dir one/alt-system##S.H.U/file1" \ "dir one/alt-system##S.H.U/file2" \ "dir one/alt-system##$T_SYS/file1" \ "dir one/alt-system##$T_SYS/file2" \ "dir one/alt-host##/file1" \ "dir one/alt-host##/file2" \ "dir one/alt-host##S/file1" \ "dir one/alt-host##S/file2" \ "dir one/alt-host##S.H/file1" \ "dir one/alt-host##S.H/file2" \ "dir one/alt-host##S.H.U/file1" \ "dir one/alt-host##S.H.U/file2" \ "dir one/alt-host##$T_SYS.$T_HOST/file1" \ "dir one/alt-host##$T_SYS.$T_HOST/file2" \ "dir one/alt-host##${T_SYS}_${T_HOST}/file1" \ "dir one/alt-host##${T_SYS}_${T_HOST}/file2" \ "dir one/alt-user##/file1" \ "dir one/alt-user##/file2" \ "dir one/alt-user##S/file1" \ "dir one/alt-user##S/file2" \ "dir one/alt-user##S.H/file1" \ "dir one/alt-user##S.H/file2" \ "dir one/alt-user##S.H.U/file1" \ "dir one/alt-user##S.H.U/file2" \ "dir one/alt-user##$T_SYS.$T_HOST.$T_USER/file1" \ "dir one/alt-user##$T_SYS.$T_HOST.$T_USER/file2" \ "dir one/alt-user##${T_SYS}_${T_HOST}_${T_USER}/file1" \ "dir one/alt-user##${T_SYS}_${T_HOST}_${T_USER}/file2" \ "dir one/alt-override-system##/file1" \ "dir one/alt-override-system##/file2" \ "dir one/alt-override-system##$T_SYS/file1" \ "dir one/alt-override-system##$T_SYS/file2" \ "dir one/alt-override-system##custom_system/file1" \ "dir one/alt-override-system##custom_system/file2" \ "dir one/alt-override-host##/file1" \ "dir one/alt-override-host##/file2" \ "dir one/alt-override-host##$T_SYS.$T_HOST/file1" \ "dir one/alt-override-host##$T_SYS.$T_HOST/file2" \ "dir one/alt-override-host##$T_SYS.custom_host/file1" \ "dir one/alt-override-host##$T_SYS.custom_host/file2" \ "dir one/alt-override-user##/file1" \ "dir one/alt-override-user##/file2" \ "dir one/alt-override-user##S.H.U/file1" \ "dir one/alt-override-user##S.H.U/file2" \ "dir one/alt-override-user##$T_SYS.$T_HOST.custom_user/file1" \ "dir one/alt-override-user##$T_SYS.$T_HOST.custom_user/file2" \ "dir2/file2" \ ; do make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done fi if [ ! -z "$TEST_TREE_WITH_WILD" ] ; then #; wildcard test data - yes this is a big mess :( #; none for f in "wild-none##"; do make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done #; system for WILD_S in 'local' 'wild' 'other'; do local s_base="wild-system-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac local f="${s_base}##${WILD_S}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done #; system.host for WILD_S in 'local' 'wild' 'other'; do local s_base="wild-host-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac for WILD_H in 'local' 'wild' 'other'; do local h_base="${s_base}-$WILD_H" case $WILD_H in local) WILD_H="$T_HOST";; wild) WILD_H="%";; esac local f="${h_base}##${WILD_S}.${WILD_H}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done done #; system.host.user for WILD_S in 'local' 'wild' 'other'; do local s_base="wild-user-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac for WILD_H in 'local' 'wild' 'other'; do local h_base="${s_base}-$WILD_H" case $WILD_H in local) WILD_H="$T_HOST";; wild) WILD_H="%";; esac for WILD_U in 'local' 'wild' 'other'; do local u_base="${h_base}-$WILD_U" case $WILD_U in local) WILD_U="$T_USER";; wild) WILD_U="%";; esac local f="${u_base}##${WILD_S}.${WILD_H}.${WILD_U}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done done done #; class for WILD_C in 'local' 'wild' 'other'; do local c_base="wild-class-$WILD_C" case $WILD_C in local) WILD_C="set_class";; wild) WILD_C="%";; esac local f="${c_base}##${WILD_C}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done #; class.system for WILD_C in 'local' 'wild' 'other'; do local c_base="wild-class-system-$WILD_C" case $WILD_C in local) WILD_C="set_class";; wild) WILD_C="%";; esac for WILD_S in 'local' 'wild' 'other'; do local s_base="${c_base}-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac local f="${s_base}##${WILD_C}.${WILD_S}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done done #; class.system.host for WILD_C in 'local' 'wild' 'other'; do local c_base="wild-class-system-host-$WILD_C" case $WILD_C in local) WILD_C="set_class";; wild) WILD_C="%";; esac for WILD_S in 'local' 'wild' 'other'; do local s_base="${c_base}-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac for WILD_H in 'local' 'wild' 'other'; do local h_base="${s_base}-$WILD_H" case $WILD_H in local) WILD_H="$T_HOST";; wild) WILD_H="%";; esac local f="${h_base}##${WILD_C}.${WILD_S}.${WILD_H}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done done done #; class.system.host.user for WILD_C in 'local' 'wild' 'other'; do local c_base="wild-class-system-host-user-$WILD_C" case $WILD_C in local) WILD_C="set_class";; wild) WILD_C="%";; esac for WILD_S in 'local' 'wild' 'other'; do local s_base="${c_base}-$WILD_S" case $WILD_S in local) WILD_S="$T_SYS";; wild) WILD_S="%";; esac for WILD_H in 'local' 'wild' 'other'; do local h_base="${s_base}-$WILD_H" case $WILD_H in local) WILD_H="$T_HOST";; wild) WILD_H="%";; esac for WILD_U in 'local' 'wild' 'other'; do local u_base="${h_base}-$WILD_U" case $WILD_U in local) WILD_U="$T_USER";; wild) WILD_U="%";; esac local f="${u_base}##${WILD_C}.${WILD_S}.${WILD_H}.${WILD_U}" make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done done done done fi for f in \ .bash_profile \ .gnupg/gpg.conf \ .gnupg/pubring.gpg \ .gnupg/secring.gpg \ .hammerspoon/init.lua \ .ssh/config \ .ssh/secret.key \ .ssh/secret.pub \ .tmux.conf \ .vimrc \ ; do make_parents "$DIR_WORKTREE/$f" echo "$f" > "$DIR_WORKTREE/$f" done #; change all perms (so permission updates can be observed) find "$DIR_WORKTREE" -exec chmod 0777 '{}' ';' } #; create a repo in T_DIR_REPO function build_repo() { local files_to_add=( "$@" ) #; create a worktree create_worktree "$T_DIR_WORK" #; remove the repo if it exists if [ -e "$T_DIR_REPO" ]; then rm -rf "$T_DIR_REPO" fi #; create the repo git init --shared=0600 --bare "$T_DIR_REPO" >/dev/null 2>&1 #; standard repo config GIT_DIR="$T_DIR_REPO" git config core.bare 'false' GIT_DIR="$T_DIR_REPO" git config core.worktree "$T_DIR_WORK" GIT_DIR="$T_DIR_REPO" git config status.showUntrackedFiles no GIT_DIR="$T_DIR_REPO" git config yadm.managed 'true' if [ ${#files_to_add[@]} -ne 0 ]; then for f in "${files_to_add[@]}"; do GIT_DIR="$T_DIR_REPO" git add "$T_DIR_WORK/$f" >/dev/null done GIT_DIR="$T_DIR_REPO" git commit -m 'Create repo template' >/dev/null fi } #; remove all tmp files function destroy_tmp() { load_fixtures rm -rf "$T_TMP" } configure_git