mirror of
https://gitlab.com/TECHNOFAB/soonix.git
synced 2026-02-02 15:25:05 +01:00
feat(cli): add check mode which exits 2 if hooks/files are outdated
This commit is contained in:
parent
374e31d852
commit
5caa66ec8d
2 changed files with 82 additions and 64 deletions
145
lib/module.nix
145
lib/module.nix
|
|
@ -154,57 +154,65 @@ in {
|
|||
config = let
|
||||
hooks = config.hooks;
|
||||
# allow excluding gitignore since stuff like renovate can't use/commit it anyways
|
||||
getHookNames = {includeGitignored ? true}:
|
||||
if includeGitignored
|
||||
then (builtins.attrNames hooks)
|
||||
else
|
||||
map
|
||||
(hook: hook.name)
|
||||
(builtins.filter (hook: !hook.hook.gitignore) (builtins.attrValues hooks));
|
||||
|
||||
runHooks = args:
|
||||
concatMapStringsSep "\n" (hookName: let
|
||||
hook = hooks.${hookName};
|
||||
modes = {
|
||||
link =
|
||||
# sh
|
||||
''
|
||||
if [[ ! -L "${hook.output}" ]] || [[ "$(readlink "${hook.output}")" != "${hook.generatedDerivation}" ]]; then
|
||||
_soonix_log "info" "${hookName}" "Creating symlink: ${hook.output} -> ${hook.generatedDerivation}"
|
||||
runHooks = concatMapStringsSep "\n" (hookName: let
|
||||
hook = hooks.${hookName};
|
||||
modes = {
|
||||
link =
|
||||
# sh
|
||||
''
|
||||
if [[ ! -L "${hook.output}" ]] || [[ "$(readlink "${hook.output}")" != "${hook.generatedDerivation}" ]]; then
|
||||
_soonix_log "info" "${hookName}" "Creating symlink: ${hook.output} -> ${hook.generatedDerivation}"
|
||||
if [[ "$CHECK_MODE" != "true" ]]; then
|
||||
mkdir -p "$(dirname "${hook.output}")"
|
||||
ln -sf "${hook.generatedDerivation}" "${hook.output}"
|
||||
_changed=true
|
||||
else
|
||||
_soonix_log "info" "${hookName}" "Symlink up to date: ${hook.output}"
|
||||
_soonix_log "info" "${hookName}" "Would create symlink: ${hook.output} -> ${hook.generatedDerivation}"
|
||||
fi
|
||||
'';
|
||||
copy =
|
||||
# sh
|
||||
''
|
||||
if [[ ! -f "${hook.output}" ]] || ! cmp -s "${hook.generatedDerivation}" "${hook.output}"; then
|
||||
_soonix_log "info" "${hookName}" "Copying file: ${hook.generatedDerivation} -> ${hook.output}"
|
||||
_changed=true
|
||||
else
|
||||
_soonix_log "info" "${hookName}" "Symlink up to date: ${hook.output}"
|
||||
fi
|
||||
'';
|
||||
copy =
|
||||
# sh
|
||||
''
|
||||
if [[ ! -f "${hook.output}" ]] || ! cmp -s "${hook.generatedDerivation}" "${hook.output}"; then
|
||||
_soonix_log "info" "${hookName}" "Copying file: ${hook.generatedDerivation} -> ${hook.output}"
|
||||
if [[ "$CHECK_MODE" != "true" ]]; then
|
||||
mkdir -p "$(dirname "${hook.output}")"
|
||||
# required since they're read only
|
||||
rm -f "${hook.output}"
|
||||
cp "${hook.generatedDerivation}" "${hook.output}"
|
||||
_changed=true
|
||||
else
|
||||
_soonix_log "info" "${hookName}" "File up to date: ${hook.output}"
|
||||
_soonix_log "info" "${hookName}" "Would copy file: ${hook.generatedDerivation} -> ${hook.output}"
|
||||
fi
|
||||
'';
|
||||
};
|
||||
_changed=true
|
||||
else
|
||||
_soonix_log "info" "${hookName}" "File up to date: ${hook.output}"
|
||||
fi
|
||||
'';
|
||||
};
|
||||
|
||||
optionalGitignore =
|
||||
if hook.hook.gitignore
|
||||
then ''
|
||||
_soonix_add_to_gitignore "${hook.output}"
|
||||
''
|
||||
else "";
|
||||
in
|
||||
builtins.addErrorContext "[soonix] while generating script for ${hookName}"
|
||||
# sh
|
||||
optionalGitignore =
|
||||
if hook.hook.gitignore
|
||||
then ''
|
||||
_soonix_add_to_gitignore "${hook.output}"
|
||||
''
|
||||
# Process hook: ${hookName}
|
||||
else "";
|
||||
|
||||
isGitignored =
|
||||
if hook.hook.gitignore
|
||||
then "true"
|
||||
else "false";
|
||||
in
|
||||
builtins.addErrorContext "[soonix] while generating script for ${hookName}"
|
||||
# sh
|
||||
''
|
||||
# Process hook: ${hookName}
|
||||
# Skip if SKIP_GITIGNORE is set and this hook is gitignored
|
||||
if [[ "$SKIP_GITIGNORE" == "true" && "${isGitignored}" == "true" ]]; then
|
||||
: # skip
|
||||
else
|
||||
while IFS= read -r line; do
|
||||
case "$line" in
|
||||
UPDATED) _soonix_updated+=("${hookName}") ;;
|
||||
|
|
@ -217,13 +225,15 @@ in {
|
|||
|
||||
${modes.${hook.hook.mode} or (throw "Mode ${hook.hook.mode} doesnt exist")}
|
||||
|
||||
# Add to gitignore if requested
|
||||
${optionalGitignore}
|
||||
if [[ "$CHECK_MODE" != "true" ]]; then
|
||||
# Add to gitignore if requested
|
||||
${optionalGitignore}
|
||||
|
||||
# Run extra commands if file changed
|
||||
if [[ "$_changed" == "true" && -n "${hook.hook.extra}" ]]; then
|
||||
_soonix_log "info" "${hookName}" "Running extra command: ${hook.hook.extra}"
|
||||
eval "${hook.hook.extra}"
|
||||
# Run extra commands if file changed
|
||||
if [[ "$_changed" == "true" && -n "${hook.hook.extra}" ]]; then
|
||||
_soonix_log "info" "${hookName}" "Running extra command: ${hook.hook.extra}"
|
||||
eval "${hook.hook.extra}"
|
||||
fi
|
||||
fi
|
||||
|
||||
if [[ "$_changed" == "true" ]]; then
|
||||
|
|
@ -235,10 +245,11 @@ in {
|
|||
_soonix_log "error" "${hookName}" "Failed to process hook"
|
||||
_soonix_failed+=("${hookName}")
|
||||
}
|
||||
'')
|
||||
(getHookNames args);
|
||||
fi
|
||||
'')
|
||||
(builtins.attrNames hooks);
|
||||
|
||||
generateShellHook = args:
|
||||
generateShellHook =
|
||||
builtins.addErrorContext "[soonix] while generating shell hook"
|
||||
# sh
|
||||
''
|
||||
|
|
@ -275,13 +286,16 @@ in {
|
|||
_soonix_failed=()
|
||||
_soonix_uptodate=()
|
||||
|
||||
${runHooks args}
|
||||
${runHooks}
|
||||
|
||||
local output=$'\E[msoonix:\E[38;5;8m'
|
||||
local status=0
|
||||
|
||||
if [[ ''${#_soonix_updated[@]} -gt 0 ]]; then
|
||||
output="$output [updated: ''${_soonix_updated[*]}]" >&2
|
||||
if [[ "$CHECK_MODE" == "true" ]]; then
|
||||
status=2
|
||||
fi
|
||||
fi
|
||||
if [[ ''${#_soonix_uptodate[@]} -gt 0 ]]; then
|
||||
output="$output [unchanged: ''${_soonix_uptodate[*]}]" >&2
|
||||
|
|
@ -293,8 +307,8 @@ in {
|
|||
|
||||
printf "%s\E[m\n" "$output" >&2
|
||||
|
||||
if [[ $status -eq 1 ]]; then
|
||||
exit 1
|
||||
if [[ $status -ne 0 ]]; then
|
||||
exit $status
|
||||
fi
|
||||
'';
|
||||
|
||||
|
|
@ -308,7 +322,7 @@ in {
|
|||
# nothing to do if no hooks exist
|
||||
shellHook =
|
||||
if (builtins.length (builtins.attrNames config.hooks) > 0)
|
||||
then generateShellHook {}
|
||||
then generateShellHook
|
||||
else "";
|
||||
shellHookFile = pkgs.writeShellScript "shellHook" shellHook;
|
||||
devshellModule = {
|
||||
|
|
@ -325,6 +339,7 @@ in {
|
|||
set -euo pipefail
|
||||
|
||||
SKIP_GITIGNORE=false
|
||||
CHECK_MODE=false
|
||||
COMMAND=""
|
||||
|
||||
show_help() {
|
||||
|
|
@ -336,6 +351,7 @@ in {
|
|||
|
||||
COMMANDS:
|
||||
update Update all managed files
|
||||
check Check if all files are up to date (dry-run)
|
||||
list List all managed file targets
|
||||
help Show this help message
|
||||
|
||||
|
|
@ -352,7 +368,7 @@ in {
|
|||
|
||||
while [[ $# -gt 0 ]]; do
|
||||
case "$1" in
|
||||
update|list|help)
|
||||
update|check|list|help)
|
||||
COMMAND="$1"
|
||||
shift
|
||||
;;
|
||||
|
|
@ -396,17 +412,18 @@ in {
|
|||
'') (builtins.attrNames hooks)}
|
||||
;;
|
||||
update)
|
||||
if [[ "$SKIP_GITIGNORE" == "true" ]]; then
|
||||
function _soonix() {
|
||||
${generateShellHook {includeGitignored = false;}}
|
||||
}
|
||||
_soonix
|
||||
else
|
||||
function _soonix() {
|
||||
${generateShellHook {}}
|
||||
}
|
||||
_soonix
|
||||
fi
|
||||
function _soonix() {
|
||||
${generateShellHook}
|
||||
}
|
||||
_soonix
|
||||
;;
|
||||
check)
|
||||
CHECK_MODE=true
|
||||
echo "Checking files..."
|
||||
function _soonix() {
|
||||
${generateShellHook}
|
||||
}
|
||||
_soonix
|
||||
;;
|
||||
esac
|
||||
'';
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue