add argument to limit number of parallel background jobs
This commit is contained in:
parent
fa62b8a094
commit
e03f7c33d9
2 changed files with 80 additions and 18 deletions
|
|
@ -13,8 +13,12 @@ It was inspired by [[https://wiki.ros.org/wstool][wstool]], [[https://github.com
|
||||||
Usage: gis [OPTIONS] [COMMAND]
|
Usage: gis [OPTIONS] [COMMAND]
|
||||||
|
|
||||||
Show a status summary of all Git repositories which are found recursively in
|
Show a status summary of all Git repositories which are found recursively in
|
||||||
current work directory. If the colon-separated environment variable $GIS_PATH
|
current work directory. The colon colon-separated environment variable
|
||||||
is set, the declared directories will be used instead.
|
$GIS_PATH or the '-p' argument can be used to modify the search path.
|
||||||
|
|
||||||
|
All 'fetch' and 'pull' operations are executed in parallel. The number of
|
||||||
|
background jobs can be limited with the environment variable $GIS_JOBS or the
|
||||||
|
'-j' argument.
|
||||||
|
|
||||||
COMMANDS
|
COMMANDS
|
||||||
fetch Execute 'git fetch --prune --all' for all found repositories
|
fetch Execute 'git fetch --prune --all' for all found repositories
|
||||||
|
|
@ -22,6 +26,7 @@ It was inspired by [[https://wiki.ros.org/wstool][wstool]], [[https://github.com
|
||||||
which are behind upstream, includes 'gis fetch'
|
which are behind upstream, includes 'gis fetch'
|
||||||
|
|
||||||
OPTIONS
|
OPTIONS
|
||||||
|
-j, --jobs N Limit 'fetch' and 'pull' commands to N parallel jobs
|
||||||
-p, --path PATH Use PATH for searching Git repositories
|
-p, --path PATH Use PATH for searching Git repositories
|
||||||
-h, --help Show this help message and exit
|
-h, --help Show this help message and exit
|
||||||
#+end_example
|
#+end_example
|
||||||
|
|
|
||||||
89
gis
89
gis
|
|
@ -14,8 +14,12 @@ function print_usage {
|
||||||
Usage: gis [OPTIONS] [COMMAND]
|
Usage: gis [OPTIONS] [COMMAND]
|
||||||
|
|
||||||
Show a status summary of all Git repositories which are found recursively in
|
Show a status summary of all Git repositories which are found recursively in
|
||||||
current work directory. If the colon-separated environment variable \$GIS_PATH
|
current work directory. The colon colon-separated environment variable
|
||||||
is set, the declared directories will be used instead.
|
\$GIS_PATH or the '-p' argument can be used to modify the search path.
|
||||||
|
|
||||||
|
All 'fetch' and 'pull' operations are executed in parallel. The number of
|
||||||
|
background jobs can be limited with the environment variable \$GIS_JOBS or the
|
||||||
|
'-j' argument.
|
||||||
|
|
||||||
COMMANDS
|
COMMANDS
|
||||||
fetch Execute 'git fetch --prune --all' for all found repositories
|
fetch Execute 'git fetch --prune --all' for all found repositories
|
||||||
|
|
@ -23,6 +27,7 @@ COMMANDS
|
||||||
which are behind upstream, includes 'gis fetch'
|
which are behind upstream, includes 'gis fetch'
|
||||||
|
|
||||||
OPTIONS
|
OPTIONS
|
||||||
|
-j, --jobs N Limit 'fetch' and 'pull' commands to N parallel jobs
|
||||||
-p, --path PATH Use PATH for searching Git repositories
|
-p, --path PATH Use PATH for searching Git repositories
|
||||||
-h, --help Show this help message and exit
|
-h, --help Show this help message and exit
|
||||||
EOF
|
EOF
|
||||||
|
|
@ -34,11 +39,37 @@ function error {
|
||||||
exit 1
|
exit 1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function execute_git_command_on_list {
|
||||||
|
IFS=";" read -r -a git_dirs <<< "$2"
|
||||||
|
for dir in "${git_dirs[@]}"; do
|
||||||
|
cd "$dir" || echo "Failed to cd into ${text_bold}${text_red}${dir}${text_reset}"
|
||||||
|
|
||||||
|
# Get repository name
|
||||||
|
repository_name=$(basename "$dir")
|
||||||
|
|
||||||
|
# Execute 'fetch' or 'pull'
|
||||||
|
if [ "$1" == "fetch" ]; then
|
||||||
|
git fetch --prune --all 1> /dev/null 2> >(trap 'kill $! 2> /dev/null' INT TERM; sed "s/^/${text_bold}${text_blue}${repository_name}${text_reset} /")
|
||||||
|
elif [ "$1" == "pull" ]; then
|
||||||
|
git pull --recurse-submodules > >(sed "s/^/${text_bold}${text_magenta}${repository_name}${text_reset} /")
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
# Parse arguments
|
# Parse arguments
|
||||||
|
jobs=0
|
||||||
fetch=false
|
fetch=false
|
||||||
pull=false
|
pull=false
|
||||||
while (( "$#" )); do
|
while (( "$#" )); do
|
||||||
case "$1" in
|
case "$1" in
|
||||||
|
-j|--jobs)
|
||||||
|
if [ -n "$2" ] && [ "${2:0:1}" != "-" ]; then
|
||||||
|
jobs="$2"
|
||||||
|
shift 2
|
||||||
|
else
|
||||||
|
error "Argument for ${text_bold}$1${text_reset} is missing"
|
||||||
|
fi
|
||||||
|
;;
|
||||||
-p|--path)
|
-p|--path)
|
||||||
if [ -n "$2" ] && [ "${2:0:1}" != "-" ]; then
|
if [ -n "$2" ] && [ "${2:0:1}" != "-" ]; then
|
||||||
paths+=("$(realpath "$2")")
|
paths+=("$(realpath "$2")")
|
||||||
|
|
@ -107,6 +138,18 @@ for path in "${paths[@]}"; do
|
||||||
git_dirs+=("${found_git_dirs[@]}")
|
git_dirs+=("${found_git_dirs[@]}")
|
||||||
done
|
done
|
||||||
|
|
||||||
|
# Set default number of jobs if argument or $GIS_JOBS wasn't set
|
||||||
|
if [ "$jobs" == 0 ]; then
|
||||||
|
if [ "$GIS_JOBS" ]; then
|
||||||
|
jobs="$GIS_JOBS"
|
||||||
|
else
|
||||||
|
jobs="${#git_dirs[@]}"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
if ! [[ "$jobs" =~ ^[0-9]+$ ]]; then
|
||||||
|
error "Number of parallel jobs must be a positive number"
|
||||||
|
fi
|
||||||
|
|
||||||
# Fetch Git repositories
|
# Fetch Git repositories
|
||||||
if [ "$fetch" == true ]; then
|
if [ "$fetch" == true ]; then
|
||||||
|
|
||||||
|
|
@ -117,17 +160,24 @@ if [ "$fetch" == true ]; then
|
||||||
fi
|
fi
|
||||||
echo "${text_bold}${text_blue}Fetching${text_reset} ${#git_dirs[@]} repositor${suffix}"
|
echo "${text_bold}${text_blue}Fetching${text_reset} ${#git_dirs[@]} repositor${suffix}"
|
||||||
|
|
||||||
for dir in "${git_dirs[@]}"; do
|
# Create n lists of repositories where n is the number of parallel jobs
|
||||||
cd "$dir" || echo "Failed to cd into ${text_bold}${text_red}${dir}${text_reset}"
|
declare -a fetch_lists
|
||||||
|
for i in "${!git_dirs[@]}"; do
|
||||||
|
list_index=$((i % jobs))
|
||||||
|
if [ "${fetch_lists[$list_index]}" == "" ]; then
|
||||||
|
fetch_lists[list_index]="${git_dirs[$i]}"
|
||||||
|
else
|
||||||
|
fetch_lists[list_index]="${fetch_lists[$list_index]};${git_dirs[$i]}"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
# Get repository name
|
# Fetch all lists in background
|
||||||
repository_name=$(basename "$dir")
|
for fetch_list in "${fetch_lists[@]}"; do
|
||||||
|
execute_git_command_on_list "fetch" "${fetch_list}" &
|
||||||
# Fetch all Git repositories in background
|
|
||||||
git fetch --prune --all 1> /dev/null 2> >(trap 'kill $! 2> /dev/null' INT TERM; sed "s/^/${text_bold}${text_blue}${repository_name}${text_reset} /") &
|
|
||||||
fetch_pids+=("$!")
|
fetch_pids+=("$!")
|
||||||
done
|
done
|
||||||
|
|
||||||
|
# Wait for fetching of all lists
|
||||||
for pid in "${fetch_pids[@]}"; do
|
for pid in "${fetch_pids[@]}"; do
|
||||||
wait "$pid"
|
wait "$pid"
|
||||||
done
|
done
|
||||||
|
|
@ -154,17 +204,24 @@ if [ "$pull" == true ]; then
|
||||||
fi
|
fi
|
||||||
echo "${text_bold}${text_magenta}Pulling${text_reset} ${#pull_dirs[@]} repositor${suffix}"
|
echo "${text_bold}${text_magenta}Pulling${text_reset} ${#pull_dirs[@]} repositor${suffix}"
|
||||||
|
|
||||||
# Pull all Git repositories which are behind upstream in background
|
# Create n lists of repositories where n is the number of parallel jobs
|
||||||
for dir in "${pull_dirs[@]}"; do
|
declare -a pull_lists
|
||||||
cd "$dir" || echo "Failed to cd into ${text_bold}${text_red}${dir}${text_reset}"
|
for i in "${!pull_dirs[@]}"; do
|
||||||
|
list_index=$((i % jobs))
|
||||||
|
if [ "${pull_lists[$list_index]}" == "" ]; then
|
||||||
|
pull_lists[list_index]="${pull_dirs[$i]}"
|
||||||
|
else
|
||||||
|
pull_lists[list_index]="${pull_lists[$list_index]};${pull_dirs[$i]}"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
# Get repository name
|
# Pull all lists in background
|
||||||
repository_name=$(basename "$dir")
|
for pull_list in "${pull_lists[@]}"; do
|
||||||
|
execute_git_command_on_list "pull" "${pull_list}" &
|
||||||
git pull --recurse-submodules > >(trap 'kill $! 2> /dev/null' INT TERM; sed "s/^/${text_bold}${text_magenta}${repository_name}${text_reset} /") &
|
|
||||||
pull_pids+=("$!")
|
pull_pids+=("$!")
|
||||||
done
|
done
|
||||||
|
|
||||||
|
# Wait for pulling of all lists
|
||||||
for pid in "${pull_pids[@]}"; do
|
for pid in "${pull_pids[@]}"; do
|
||||||
wait "$pid"
|
wait "$pid"
|
||||||
done
|
done
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue