bash getopts、短いオプションのみ、すべて値が必要です。

bash getopts、短いオプションのみ、すべて値が必要です。

さまざまなオプションを受け入れるシェルスクリプトを作成しようとしていますが、オプションと引数の可変getopts順序を処理できるため、良い解決策のようです。

次のように、各オプションに対応する値を必要とする短いオプションのみを使用します。./command.sh -a arga -g argg -b argbしかし、オプションを非特定の順序で入力できるようにしたいと思います。これは、ほとんどの人がシェルコマンドを使用するのに慣れています。

caseもう一つのことは、オプションパラメータ値を直接、できるだけ明細書で確認したいという点だ。その理由は、ステートメント:)に対する私のテストが一貫性のない結果をもたらしたからです(おそらく私の理解の欠如によるものです)。たとえば、case

#!/bin/bash
OPTIND=1 # Reset if getopts used previously
if (($# == 0)); then
        echo "Usage"
        exit 2
fi
while getopts ":h:u:p:d:" opt; do
        case "$opt" in

                h)
                        MYSQL_HOST=$OPTARG
                        ;;
                u)
                        MYSQL_USER=$OPTARG
                        ;;
                p)
                        MYSQL_PASS=$OPTARG
                        ;;
                d)
                        BACKUP_DIR=$OPTARG
                        ;;
                \?)
                        echo "Invalid option: -$OPTARG" >&2
                        exit 2;;
                :)
                       echo "Option -$OPTARG requires an argument" >&2
                       exit 2;;
        esac
done
shift $((OPTIND-1))
echo "MYSQL_HOST='$MYSQL_HOST'  MYSQL_USER='$MYSQL_USER'  MYSQL_PASS='$MYSQL_PASS'  BACKUP_DIR='$BACKUP_DIR' Additionals: $@"

何が起こるかはこれが失敗するということです... -dに引数が必要ですが、私が取得する値が私が必要な値ではないという./command.sh -d -h
フラグを指定したいときです。-d=-h

だから、各オプションが設定され、一度だけ設定されていることを確認するために、Caseステートメントで独自の検証を実行する方が簡単になると思いました。

以下を実行しようとしていますが、私のif [ ! "$MYSQL_HOST" ]; thenブロックは実行されません。

OPTIND=1 # Reset if getopts used previously

if (($# == 0)); then
        echo "Usage"
        exit 2
fi

while getopts ":h:u:p:d:" opt; do
        case "$opt" in

                h)
                        MYSQL_HOST=$OPTARG
                        if [ ! "$MYSQL_HOST" ]; then
                                echo "host not set"
                                exit 2
                        fi
                        ;;
                u)
                        MYSQL_USER=$OPTARG
                        if [ ! "$MYSQL_USER" ]; then
                                echo "username not set"
                                exit 2
                        fi
                        ;;
                p)
                        MYSQL_PASS=$OPTARG
                        if [ ! "$MYSQL_PASS" ]; then
                                echo "password not set"
                                exit 2
                        fi
                        ;;
                d)
                        BACKUP_DIR=$OPTARG
                        if [ ! "$BACKUP_DIR" ]; then
                                echo "backup dir not set"
                                exit 2
                        fi
                        ;;
                \?)
                        echo "Invalid option: -$OPTARG" >&2
                        exit 2;;
                #:)
                #       echo "Option -$opt requires an argument" >&2
                #       exit 2;;
        esac
done
shift $((OPTIND-1))

echo "MYSQL_HOST='$MYSQL_HOST'  MYSQL_USER='$MYSQL_USER'  MYSQL_PASS='$MYSQL_PASS'  BACKUP_DIR='$BACKUP_DIR' Additionals: $@"

OPTARGan内の長さが0であることを確認する方法はありませんかgetopts ... while ... case

外部でパラメータ検証を実行することに頼りたくありません。これにより、etcgetoptsのパラメータ値を取得し、欠落しているオプションをキャプチャできない可能性があります。:)while ... case ... esac
-d

ベストアンサー1

getoptit次のように2番目のスクリプト(私が保存したもの)を呼び出すとき:

getoptit -d -h

これにより、次のものが印刷されます。

MYSQL_HOST=''  MYSQL_USER=''  MYSQL_PASS=''  BACKUP_DIR='-h' Additionals: 

if [ ! "$BACKUP_DIR" ]; thenこのようにBACKUP_DIRが設定されていない場合は、テストしてみてください。すると、内部のコードが実行されないのが正常です。

各オプションが一度設定されたかどうかをテストするには、$ OPTAGRG値に基づいて割り当てる前にこれを行う必要があります。また、割り当てる前に $OPTARG が a で始まっていることを確認する必要があります'-'(-d -hエラーの場合)。

...
            d)
                    if [ ! -z "$BACKUP_DIR" ]; then
                            echo "backup dir already set"
                            exit 2
                    fi
                    if [ z"${OPTARG:0:1}" == "z-" ]; then
                            echo "backup dir starts with option string"
                            exit 2
                    fi
                    BACKUP_DIR=$OPTARG
                    ;;
...

おすすめ記事