fix(package): migrator: index_of subshell issue
This commit is contained in:
@@ -14,16 +14,12 @@
|
|||||||
|
|
||||||
set -eu
|
set -eu
|
||||||
|
|
||||||
if ! command -v psql >/dev/null; then
|
|
||||||
log error "Required tool (psql) are not installed."
|
|
||||||
exit 127
|
|
||||||
fi
|
|
||||||
|
|
||||||
VERSION='0.0.1'
|
VERSION='0.0.1'
|
||||||
MIGRATION_DIR="${MIGRATION_DIR:-migration}"
|
MIGRATION_DIR="${MIGRATION_DIR:-migration}"
|
||||||
quote() { printf "'%s'" "$(printf %s "$1" | sed "s/'/'\\\\''/g")"; }
|
|
||||||
REMAINING_ARS=
|
REMAINING_ARS=
|
||||||
|
|
||||||
|
quote() { printf "'%s'" "$(printf %s "$1" | sed "s/'/'\\\\''/g")"; }
|
||||||
|
|
||||||
# cat filename | sha256sum()
|
# cat filename | sha256sum()
|
||||||
# sha256sum(filename)
|
# sha256sum(filename)
|
||||||
sha256sum() {
|
sha256sum() {
|
||||||
@@ -32,32 +28,6 @@ sha256sum() {
|
|||||||
cksum --algorithm=sha256 --untagged "$file" | awk '{printf $1}'
|
cksum --algorithm=sha256 --untagged "$file" | awk '{printf $1}'
|
||||||
}
|
}
|
||||||
|
|
||||||
while [ $# -gt 0 ]; do
|
|
||||||
log debug "arg: $1"
|
|
||||||
case $1 in
|
|
||||||
migrate|create|fetch|list|init)
|
|
||||||
[ "${SUBCOMMAND+x}" ] && {
|
|
||||||
log error "ambiguous subcommand, decide ${WHITE}$SUBCOMMAND ${NC}or ${WHITE}$1";
|
|
||||||
exit 2;
|
|
||||||
}
|
|
||||||
SUBCOMMAND=$1
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--migration-dir|-d)
|
|
||||||
MIGRATION_DIR=$2
|
|
||||||
shift 2
|
|
||||||
;;
|
|
||||||
--inherits)
|
|
||||||
INHERITS_LIST="${INHERITS_LIST+$INHERITS_LIST\"}$2"
|
|
||||||
shift 2
|
|
||||||
;;
|
|
||||||
--*|-*) REMAINING_ARS="$REMAINING_ARS $(quote "$1")"; shift ;; # unknown global -> pass through
|
|
||||||
*) REMAINING_ARS="$REMAINING_ARS $(quote "$1")"; shift ;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
|
|
||||||
[ ${INHERITS_LIST+x} ] && INHERITS_LIST="$(printf '%s' "$INHERITS_LIST" | sed -E 's/"/,/g; s/([^,]+)/"\1"/g')"
|
|
||||||
|
|
||||||
# shellcheck disable=SC2120
|
# shellcheck disable=SC2120
|
||||||
init() {
|
init() {
|
||||||
while [ $# -gt 0 ]; do
|
while [ $# -gt 0 ]; do
|
||||||
@@ -192,8 +162,6 @@ EOF
|
|||||||
printf '%s' "$sql"
|
printf '%s' "$sql"
|
||||||
}
|
}
|
||||||
|
|
||||||
[ "${SUBCOMMAND+x}" ] || { log error "no subcomand specified"; exit 1; }
|
|
||||||
|
|
||||||
help() {
|
help() {
|
||||||
# inherits: List one or more tables the migration table must inherit from
|
# inherits: List one or more tables the migration table must inherit from
|
||||||
echo help
|
echo help
|
||||||
@@ -269,6 +237,24 @@ migration_list() {
|
|||||||
find "$MIGRATION_DIR" -maxdepth 1 -type d -regextype posix-extended -regex '^.*/[0-9]{14}-.*$' -printf '%f\n' | sort
|
find "$MIGRATION_DIR" -maxdepth 1 -type d -regextype posix-extended -regex '^.*/[0-9]{14}-.*$' -printf '%f\n' | sort
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# index_of(array, name)
|
||||||
|
index_of() {
|
||||||
|
local list name m i=1
|
||||||
|
list=$1
|
||||||
|
name=$2
|
||||||
|
[ -z "$name" ] && return 1
|
||||||
|
|
||||||
|
# no subshell, no pipeline
|
||||||
|
while IFS= read -r m; do
|
||||||
|
[ "$m" = "$name" ] && { printf '%s\n' "$i"; return 0; }
|
||||||
|
i=$((i+1))
|
||||||
|
done <<EOF
|
||||||
|
$list
|
||||||
|
EOF
|
||||||
|
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
migrate() {
|
migrate() {
|
||||||
local fs_migrations db_migrations db_migration fs_migration psql_args var #target_migration
|
local fs_migrations db_migrations db_migration fs_migration psql_args var #target_migration
|
||||||
MIGRATOR_REMAINING_ARS=
|
MIGRATOR_REMAINING_ARS=
|
||||||
@@ -342,21 +328,20 @@ migrate() {
|
|||||||
eval "set -- $MIGRATOR_REMAINING_ARS"
|
eval "set -- $MIGRATOR_REMAINING_ARS"
|
||||||
target_migration="$("migrate_$MIGRATE_SUBCOMMAND" "$@")"
|
target_migration="$("migrate_$MIGRATE_SUBCOMMAND" "$@")"
|
||||||
|
|
||||||
log debug "target_migration: ${target_migration}"
|
if [ -z "$db_migrations" ]; then
|
||||||
|
log info "it'll firs migration"
|
||||||
|
current_idx=0
|
||||||
|
else
|
||||||
|
current_migration=$(printf '%s\n' "$db_migrations" | tail -n1)
|
||||||
|
current_idx=$(index_of "$fs_migrations" "$current_migration")
|
||||||
|
fi
|
||||||
|
|
||||||
index_of
|
log debug "[$WHITE$fs_migrations$NC]"
|
||||||
|
log debug "$target_migration"
|
||||||
|
|
||||||
}
|
target_idx=$(index_of "$fs_migrations" "$target_migration")
|
||||||
|
|
||||||
idx_of() {
|
log debug "indexes $WHITE$current_idx$NC $WHITE${target_idx}"
|
||||||
name=$1
|
|
||||||
[ -z "$name" ] && { echo 0; return; }
|
|
||||||
i=1
|
|
||||||
printf '%s\n' "$fs_migrations" | while IFS= read -r m; do
|
|
||||||
[ "$m" = "$name" ] && { echo "$i"; return; }
|
|
||||||
i=$((i+1))
|
|
||||||
done
|
|
||||||
echo 0
|
|
||||||
}
|
}
|
||||||
|
|
||||||
form_psql_args() {
|
form_psql_args() {
|
||||||
@@ -493,8 +478,43 @@ generate_word() {
|
|||||||
printf '%s' "$w"
|
printf '%s' "$w"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ! command -v psql >/dev/null; then
|
||||||
|
log error "Required tool (psql) are not installed."
|
||||||
|
exit 127
|
||||||
|
fi
|
||||||
|
|
||||||
|
if ! [ "${AS_LIBRARY+x}" ]; then
|
||||||
|
while [ $# -gt 0 ]; do
|
||||||
|
log debug "arg: $1"
|
||||||
|
case $1 in
|
||||||
|
migrate|create|fetch|list|init)
|
||||||
|
[ "${SUBCOMMAND+x}" ] && {
|
||||||
|
log error "ambiguous subcommand, decide ${WHITE}$SUBCOMMAND ${NC}or ${WHITE}$1";
|
||||||
|
exit 2;
|
||||||
|
}
|
||||||
|
SUBCOMMAND=$1
|
||||||
|
shift
|
||||||
|
;;
|
||||||
|
--migration-dir|-d)
|
||||||
|
MIGRATION_DIR=$2
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--inherits)
|
||||||
|
INHERITS_LIST="${INHERITS_LIST+$INHERITS_LIST\"}$2"
|
||||||
|
shift 2
|
||||||
|
;;
|
||||||
|
--*|-*) REMAINING_ARS="$REMAINING_ARS $(quote "$1")"; shift ;; # unknown global -> pass through
|
||||||
|
*) REMAINING_ARS="$REMAINING_ARS $(quote "$1")"; shift ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
[ ${INHERITS_LIST+x} ] && INHERITS_LIST="$(printf '%s' "$INHERITS_LIST" | sed -E 's/"/,/g; s/([^,]+)/"\1"/g')"
|
||||||
|
[ "${SUBCOMMAND+x}" ] || { log error "no subcomand specified"; exit 1; }
|
||||||
|
|
||||||
|
|
||||||
log debug "subcommand: $WHITE$SUBCOMMAND"
|
log debug "subcommand: $WHITE$SUBCOMMAND"
|
||||||
log debug "subcommand args: $WHITE$REMAINING_ARS"
|
log debug "subcommand args: $WHITE$REMAINING_ARS"
|
||||||
|
|
||||||
eval "set -- $REMAINING_ARS"
|
eval "set -- $REMAINING_ARS"
|
||||||
"$SUBCOMMAND" "$@"
|
"$SUBCOMMAND" "$@"
|
||||||
|
fi
|
||||||
|
|||||||
@@ -35,7 +35,7 @@
|
|||||||
mkPgTest = testName: testDrv: pkgs.runCommand "migrator-test-${testName}"
|
mkPgTest = testName: testDrv: pkgs.runCommand "migrator-test-${testName}"
|
||||||
{
|
{
|
||||||
nativeBuildInputs = [ pkgs.coreutils pkgs.gnugrep pkgs.gnused ];
|
nativeBuildInputs = [ pkgs.coreutils pkgs.gnugrep pkgs.gnused ];
|
||||||
buildInputs = [ migrator pkgs.postgresql ];
|
buildInputs = [ pkgs.which migrator pkgs.postgresql ];
|
||||||
} ''
|
} ''
|
||||||
${builtins.readFile self.legacyPackages.${system}.helpers.posix-shell.log}
|
${builtins.readFile self.legacyPackages.${system}.helpers.posix-shell.log}
|
||||||
test=${testDrv}
|
test=${testDrv}
|
||||||
|
|||||||
17
test/package/migrator/test/function-generate-word.sh
Normal file
17
test/package/migrator/test/function-generate-word.sh
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
# shellcheck disable=SC2034
|
||||||
|
AS_LIBRARY=
|
||||||
|
# shellcheck disable=SC1090
|
||||||
|
. "$(which migrator)"
|
||||||
|
|
||||||
|
log notice "test case: ${WHITE}generate word"
|
||||||
|
if ! answer=$(generate_word); then
|
||||||
|
log error "test failed: ${WHITE}error during generate_word call"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$(printf '%s' "$answer" | wc -c)" -ne 6 ]; then
|
||||||
|
log error "test failed: ${WHITE}word length must be 6 chars"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
log notice "test passed"
|
||||||
47
test/package/migrator/test/function-index-of.sh
Normal file
47
test/package/migrator/test/function-index-of.sh
Normal file
@@ -0,0 +1,47 @@
|
|||||||
|
# shellcheck disable=SC2034
|
||||||
|
AS_LIBRARY=
|
||||||
|
# shellcheck disable=SC1090
|
||||||
|
. "$(which migrator)"
|
||||||
|
|
||||||
|
array='item1
|
||||||
|
item2
|
||||||
|
item3
|
||||||
|
item4
|
||||||
|
item5
|
||||||
|
item6
|
||||||
|
item7'
|
||||||
|
|
||||||
|
log notice "test case: ${WHITE}index of"
|
||||||
|
if ! answer=$(index_of "$array" 'item4'); then
|
||||||
|
log error "test failed: ${WHITE}error during index_of call"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
is_number "$answer" >/dev/null || { log error "test failed: ${WHITE}answer not a number"; exit 1; }
|
||||||
|
|
||||||
|
if [ "$answer" -ne 4 ]; then
|
||||||
|
log error "test failed: ${WHITE}wrong answer"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
log notice "test case: ${WHITE}error: item not found"
|
||||||
|
if answer=$(index_of "$array" 'item10'); then
|
||||||
|
log error "test failed: ${WHITE} must return an error"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
log notice "test case: ${WHITE}one element"
|
||||||
|
array='20251104192425-add-info-to-profile'
|
||||||
|
item='20251104192425-add-info-to-profile'
|
||||||
|
|
||||||
|
if ! answer=$(index_of "$array" "$item"); then
|
||||||
|
log error "test failed: ${WHITE}error during index_of call"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$answer" -ne 1 ]; then
|
||||||
|
log error "test failed: ${WHITE}wrong answer"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
log notice "test passed"
|
||||||
17
test/package/migrator/test/function-migration-list/run.sh
Normal file
17
test/package/migrator/test/function-migration-list/run.sh
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
# shellcheck disable=SC2034
|
||||||
|
AS_LIBRARY=
|
||||||
|
# shellcheck disable=SC1090
|
||||||
|
. "$(which migrator)"
|
||||||
|
|
||||||
|
log notice "test case: ${WHITE}migration list"
|
||||||
|
if ! answer=$(migration_list); then
|
||||||
|
log error "test failed: ${WHITE}error during migration_list call"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$answer" != "20251104192425-add-info-to-profile" ]; then
|
||||||
|
log error "test failed: ${WHITE}unexpected \`migration list\` answer"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
log notice "test passed"
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
ALTER TABLE profile ADD COLUMN info TEXT;
|
||||||
@@ -6,3 +6,15 @@ columns() {
|
|||||||
FROM information_schema.columns
|
FROM information_schema.columns
|
||||||
WHERE table_name = '"${1};"
|
WHERE table_name = '"${1};"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# is_number(var)
|
||||||
|
is_number() {
|
||||||
|
case "$1" in
|
||||||
|
*[!0-9]*)
|
||||||
|
return 1
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
return 0
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user