ユーザー入力を受けてエラーが発生した場合は、プロンプトを繰り返すためにwhileループを作成しました。
while true; do
read -p "Enter hostname : " fqdn
pattern="(^[^\.]*\.[^\.]*\.[^\.]*$)"
if [[ -z "$fqdn" ]]; then #if fqdn input is empty
echo "Error! Hostname cannot be empty"
continue
elif [[ ! "${fqdn}" =~ ${pattern} ]]; then
echo "Error! Format incorrect"
continue
else
echo "hostname is $fqdn"
break
fi
done
私の目標:
- の場合もし/エリーフプロンプトを2回だけ表示してから終了する方法を示します。
- 上記のwhileループを改善する方法はありますか?例えば ケーススイッチ。ケースの切り替えを理解するのは難しいですか?
オペレーティングシステム:Ubuntu 20.04(ヘッドレス)
ベストアンサー1
次のbash
スクリプトはユーザーから文字列を読み取り、その文字列が適用するホスト名の条件を満たしているかどうかをテストします。
ステートメントで使用されている2つのパターンの最初のものは、間にcase
文字がない2つの点の病理学的ケースをテストします(これは私たちが行動しないパターンです)。 2番目のパターンに複数の点があり、両端に点のない文字列が含まれていることをテストします。fdqn
2番目のパターンが文字列と一致する場合にのみ、ホスト名変数はその文字列に設定されます。この文字列はfoo..bar
2 番目のパターンと一致するため、2 つのドットの部分文字列を 1 番目のパターンと前提に一致させます。
#!/bin/bash
unset -v count fdqn
while true; do
read -p 'Enter hostname: ' -r
case $REPLY in (*..*) ;; ([!.]*.*.*[!.]) fdqn=$REPLY; break; esac
echo 'Invalid format' >&2
count=$(( count + 1 ))
[ "$count" -eq 2 ] && break
done
if [ -z "$fdqn" ]; then
echo 'No valid hostname entered' >&2
exit 1
fi
printf 'The hostname is "%s"\n' "$fdqn"
このcount
変数は、ユーザーが文字列を入力しようとした回数を追跡します。この変数の値が2に達すると、ループを終了します。
case
移植可能なスクリプトにしたくない限り(この場合は文を別々に実行する必要がありますsh
)、ここで実際に文を使用する必要はありません。read
globbing演算子を使用する==
場合、ステートメントbash
はcase
次のようになります。
if [[ $REPLY == *..* ]]; then
:
elif [[ $REPLY == [!.]*.*.*[!.] ]]; then
fdqn=$REPLY
break
fi
&&
これら2つのテストは、最初のテストが音声の場合に接続するためにも使用できます。
if [[ $REPLY != *..* ]] && [[ $REPLY == [!.]*.*.*[!.] ]]; then
fdqn=$REPLY
break
fi
3つのドットを含むホスト名を取得したくない場合は、一致しないように$REPLY
一致しないことを確認してください。*.*.*.*
*..*