AWSのtxtファイルからjsonファイルを生成するためのbashスクリプトを作成しようとしています。以下のスクリプトはcase
最初のオプションで失敗します。$opt
包括変数があるためです。基本的に終了番号を入力すると終了するようにしたいと思います。他の有効な番号のファイルを生成します。その番号が無効な場合は、追加オプションの入力を求められます。
#!/bin/bash
clear
# define variables
NOW=$(date +%F-%a-%H.%M) # year-month-date-day-hour.minute format
# display region list menu
region=($(aws ec2 describe-regions | jq -r '.Regions[].RegionName'))
aws ec2 describe-security-groups --region $region | jq -r '.SecurityGroups[].GroupId' > $region.txt
PS3="Select Region number: "
select opt in "${region[@]}" "exit"
do
case $opt in
$opt)
aws ec2 describe-security-groups --region $region | jq -r '.SecurityGroups[].GroupId' > $region.txt
# read security groups file into array and create individual json files
mkdir -p "$region"
while read group; do
echo "Processing group: $group"
aws ec2 describe-security-groups --region $region --group-ids "$group" > "$region"/"$group-"$DATE".json"
done < $region.txt
break
;;
"exit")
echo "Exiting..."
exit
;;
*)
echo "Invalid option, try again..."
esac
done
# cleanup security group text file
rm $region.txt
予想される動作は、1〜14の間の数字を入力し、セキュリティグループjsonファイルがゾーン名を持つディレクトリに作成されることです。この部分はうまくいきます。しかし、終了するために15を入力すると、これが発生します。
Select Region number: 15
Processing group: sg-4fec0526
また、16のように誤った数字を入力すると、15でも同じ現象が発生します。
Select Region number: 16
Processing group: sg-4fec0526
数字 15 を終了する必要があり、1 から 15 以外の数字には Invalid... というメッセージが表示され、別の数字を入力するように求められます。
なぜメニューですか?今は細かい制御が欲しい
答え1
case
おっしゃるように問題は陳述です。定義に応じて、すべての変数は常に自分と一致するため、常にtrueです。
case $opt in
$opt)
. . .
したがって、どの値を指定しても常に同じcase
ブロックを実行します。何をしたいのか分かりませんが、私は考えるあなたの目標は次のとおりです。
#!/bin/bash
## Enable extended globbing for the +(...) pattern
shopt -s extglob
clear
# define variables
NOW=$(date +%F-%a-%H.%M) # year-month-date-day-hour.minute format
# display region list menu
region=($(aws ec2 describe-regions |
jq -r '.Regions[].RegionName'))
aws ec2 describe-security-groups --region "$region" | jq -r '.SecurityGroups[].GroupId' > "$region.txt"
PS3="Select Region number: "
## make a dummy array which includes the values
validOptions=${region[0]};
for ((i=1; i<${#region[@]}; i++)); do
validOptions="$validOptions|${region[i]}"
done
select opt in "${region[@]}" "exit"
do
case $opt in
## This uses bash's +(pat1|pat2) syntax which matches
## one or more of the |-separated strings.
+($validOptions))
echo "Valid!"
aws ec2 describe-security-groups --region "$region" |
jq -r '.SecurityGroups[].GroupId' > "$region.txt"
# read security groups file into array and create
# individual json files
mkdir -p "$region"
while read group; do
echo "Processing group: $group"
aws ec2 describe-security-groups --region "$region" --group-ids "$group" > "${region}/${group}-${DATE}.json"
done < "$region.txt"
break
;;
"exit")
echo "Exiting..."
exit
;;
*)
echo "Invalid option $opt, try again..."
esac
done