次のようなものを使いたい
if [[ ! -z "$ENV" && $ENV == 'production' ]]; then echo "production"; else echo "dev"; fi
しかし、BusyBoxでは動作しません:(
sh: 1: [[: not found
ビジボックスに入るIFステートメントでは、ANDまたはORの組み合わせが機能しないようです。
答え1
[[...]]
bash
でもサポートされているKornシェル構成ですが、zsh
標準構成ではありませんsh
(そして他のシェルではサポートされていません)。
busybox
sh
ash
これはPOSIX仕様のサブセット(POSIXロケール内でほとんど互換性があります)を実装し、sh
特にこの拡張ではない拡張はほとんどありません。
2019年編集。使用して構築するときbusybox ashは今[[...]]
kshだけでなく 。ASH_TEST
ASH_BASH_COMPAT
yash
それにもかかわらず、スクリプトを書くときはsh
POSIX仕様に従う必要があります。sh
使用されるスクリプトは[[...]]
呼び出されるか、ksh
明示的bash
にzsh
呼び出される必要があります。bash
また、POSIX shと主に互換性がありますが、より多くの拡張機能(この拡張機能を含む)を備えたシェルです。
テストX空でなければproduction
意味がありません。もしX==production
もしそうなら、明らかに空ではありません。
文字列比較のためにPOSIXシェルとユーティリティを使用すると、いくつかのオプションがあります。この場合、最も明確なオプションは次のとおりです。
この
[
ユーティリティはとも呼ばれ、test
通常シェルに組み込まれています。if [ "$var" = production ]; then echo PROD fi
構造
case
:case $var in production) echo PROD;; "") echo EMPTY;; *) echo non-PROD;; esac
これで、変数が次のようになっていることを確認したい場合があります。置く(null以外の場合と逆)、逆参照する前にオプションが有効になっている場合nounset
(set -u
またはshe-bang行で使用)、そうでない場合はaが設定されていない場合はシェルが終了します。これを行うには、次の操作を行う必要があります。set -o nounset
#! /bin/sh -u
[ "$ENV" = production ]
$ENV
if [ "${var+set}" = set ] && [ "$var" = production ]; then
echo PROD
fi
-a
[
(AND演算子は廃止され、信頼できないため使用しないでください。)
より良い、正式な方法は次のとおりです。
if [ "${var-}" = production ]; then
echo PROD
fi
nounset
${var+string}
トリガーまたは拡張されません${var-string}
。変数が設定されている場合は${var-}
コンテンツに展開され、それ以外の場合は空の文字列に展開されます。$var
その他の注意事項:
$ENV
特殊変数ですsh
。インタラクティブに実行されると、初期化を読み取ったファイルのパスとして扱われます(~/.bashrc
forと同じbash
)。他の目的に使用しないでください。
文字列比較の使用[ "x$var" = xproduction ]
または実行を提案する古いUnixシェルスクリプト文書を見つけることができます。これは、akaユーティリティのいくつかの以前のバージョンで、またはなどの特定の値によって混乱するバグを[ production = "$var" ]
克服するためのものです。最新のシステムではこれを必要としませんが、非常に古いシステムでは心に留めておくべきことです。とにかく、この構成にはそのような問題はありません。[
test
$var
!
(
-n
case
文字列比較を実行できる他のPOSIXユーティリティには、およびがexpr
ありますawk
。
awk_equal() { awk 'BEGIN{exit(!(""ARGV[1] == ""ARGV[2]))}' "$1" "$2"; }
expr_equal() { expr "x $1" = "x $2" > /dev/null; }
if awk_equal "$var" production; then
echo PROD
fi
if expr_equal "$var" production; then
echo PROD
fi
文字列比較(それ以外の場合はorと同じように処理されます)を取得し、同じ理由で演算子としての値に問題が発生しないようにするには、""
値の前にwithが必要です。awk
1
01
1e0
x
expr
expr
awk
and expr
(少なくともPOSIXly)の場合、実際にはそうではありません。平等演算子は、代わりに両方のオペランドが同じソート順序を持つかどうかをテストします。これは必ずしも同じではありません。たとえば、私のシステムでは、expr_equal ② ③
②と③の両方に定義されたソート順序がないため、trueが返されます。いくつかのawk
実装(たとえばgawk
、mawk
busybox)はawk
POSIX要件を無視し、代わりに単純なバイト間比較を実行します。
[
とにかく、私はあなたがここよりもこれを好むどんな妥当な理由も考えることができませんcase
。
答え2
古い[
構文を使用できます
if [ -n "$ENV" -a "$ENV" = 'production' ]
-n
(読みやすくなるので代わりに使っていますが、! -z
同じです。)
または、文字列に値を指定して前の構文に単純化することもできます。
if [ "x$ENV" = 'xproduction' ]
最後に、-n
テストは実際には必要ないかもしれません。
if [ "$ENV" = 'production' ]