bash のみのスクリプトを使用して、bash の進行状況インジケーターをどのように提供できますか?
たとえば、bash からコマンドを実行すると、そのコマンドの実行中に、まだ何かが起こっていることをユーザーに知らせます。
SCP を使用したこの例では、プロセス ID (pid) を取得し、そのプロセスの実行中に何かを実行する方法を示しています。
これにより、単純な回転アイコンが表示されます。
/usr/bin/scp me@website.com:file somewhere 2>/dev/null &
pid=$! # Process Id of the previous running command
spin[0]="-"
spin[1]="\\"
spin[2]="|"
spin[3]="/"
echo -n "[copying] ${spin[0]}"
while [ kill -0 $pid ]
do
for i in "${spin[@]}"
do
echo -ne "\b$i"
sleep 0.1
done
done
ウィリアム・パーセルのソリューション
/usr/bin/scp me@website.com:file somewhere 2>/dev/null &
pid=$! # Process Id of the previous running command
spin='-\|/'
i=0
while kill -0 $pid 2>/dev/null
do
i=$(( (i+1) %4 ))
printf "\r${spin:$i:1}"
sleep .1
done
現在処理されているファイル数や合計数など、完了したパーセンテージを推定する方法がある場合は、簡単な計算と画面幅に関する仮定を使用して、単純な線形進行状況メーターを作成できます。
count=0
total=34
pstr="[=======================================================================]"
while [ $count -lt $total ]; do
sleep 0.5 # this is work
count=$(( $count + 1 ))
pd=$(( $count * 73 / $total ))
printf "\r%3d.%1d%% %.${pd}s" $(( $count * 100 / $total )) $(( ($count * 1000 / $total) % 10 )) $pstr
done
または、リニア メーターの代わりに、残り時間を推定することもできます。他の同様のものと同じくらい正確です。
count=0
total=34
start=`date +%s`
while [ $count -lt $total ]; do
sleep 0.5 # this is work
cur=`date +%s`
count=$(( $count + 1 ))
pd=$(( $count * 73 / $total ))
runtime=$(( $cur-$start ))
estremain=$(( ($runtime * $total / $count)-$runtime ))
printf "\r%d.%d%% complete ($count of $total) - est %d:%0.2d remaining\e[K" $(( $count*100/$total )) $(( ($count*1000/$total)%10)) $(( $estremain/60 )) $(( $estremain%60 ))
done
printf "\ndone\n"
ここで、私が使用する簡単なワンライナーを示します。
while true; do for X in '-' '/' '|' '\'; do echo -en "\b$X"; sleep 0.1; done; done
これが私の試みです。私はスクリプトをbashするのが初めてなので、このコードのいくつかはひどいかもしれません:)
出力例:
コード:
progressBarWidth=20
# Function to draw progress bar
progressBar () {
# Calculate number of fill/empty slots in the bar
progress=$(echo "$progressBarWidth/$taskCount*$tasksDone" | bc -l)
fill=$(printf "%.0f\n" $progress)
if [ $fill -gt $progressBarWidth ]; then
fill=$progressBarWidth
fi
empty=$(($fill-$progressBarWidth))
# Percentage Calculation
percent=$(echo "100/$taskCount*$tasksDone" | bc -l)
percent=$(printf "%0.2f\n" $percent)
if [ $(echo "$percent>100" | bc) -gt 0 ]; then
percent="100.00"
fi
# Output to screen
printf "\r["
printf "%${fill}s" '' | tr ' ' ▉
printf "%${empty}s" '' | tr ' ' ░
printf "] $percent%% - $text "
}
## Collect task count
taskCount=33
tasksDone=0
while [ $tasksDone -le $taskCount ]; do
# Do your task
(( tasksDone += 1 ))
# Add some friendly output
text=$(echo "somefile-$tasksDone.dat")
# Draw the progress bar
progressBar $taskCount $taskDone $text
sleep 0.01
done
echo
ここでソースを見ることができます: https://gist.github.com/F1LT3R/fa7f102b08a514f2c535
bash スクリプト用のサイケデリック プログレス バー。コマンド ラインで './progressbar x y' として呼び出します。ここで、'x' は秒単位の時間、'y' は表示するメッセージです。内部関数の progressbar() はスタンドアロンでも機能し、'x' をパーセンテージとして、'y' をメッセージとして受け取ります。
#!/bin/bash
if [ "$#" -eq 0 ]; then echo "x is \"time in seconds\" and z is \"message\""; echo "Usage: progressbar x z"; exit; fi
progressbar() {
local loca=$1; local loca2=$2;
declare -a bgcolors; declare -a fgcolors;
for i in {40..46} {100..106}; do
bgcolors+=("$i")
done
for i in {30..36} {90..96}; do
fgcolors+=("$i")
done
local u=$(( 50 - loca ));
local y; local t;
local z; z=$(printf '%*s' "$u");
local w=$(( loca * 2 ));
local bouncer=".oO°Oo.";
for ((i=0;i<loca;i++)); do
t="${bouncer:((i%${#bouncer})):1}"
bgcolor="\\E[${bgcolors[RANDOM % 14]}m \\033[m"
y+="$bgcolor";
done
fgcolor="\\E[${fgcolors[RANDOM % 14]}m"
echo -ne " $fgcolor$t$y$z$fgcolor$t \\E[96m(\\E[36m$w%\\E[96m)\\E[92m $fgcolor$loca2\\033[m\r"
};
timeprogress() {
local loca="$1"; local loca2="$2";
loca=$(bc -l <<< scale=2\;"$loca/50")
for i in {1..50}; do
progressbar "$i" "$loca2";
sleep "$loca";
done
echo -e "\n"
};
timeprogress "$1" "$2"