本文へスキップ
BecomeCoder

シェルスクリプトコース · 第4章 条件分岐 · レッスン19

case ― 値によって振り分ける

ブラウザで完結

導入

ifelifelif… と3段4段に伸びてきたら、case の出番です。「この値だったらこれ」という分岐は、case のほうが圧倒的に読みやすく、パターン(*.txt のような書き方)も使えます。

説明

case は、1つの値をいくつものパターンと照合します。

#!/bin/bash

action=$1

case "$action" in
  start)
    echo "サービスを起動します"
    ;;
  stop)
    echo "サービスを停止します"
    ;;
  restart|reload)
    echo "サービスを再起動します"
    ;;
  *)
    echo "使い方: sh script.sh {start|stop|restart}"
    ;;
esac

読み方はこうです。

  • パターン) … このパターンに一致したら、次の ;; までを実行する
  • ;; … その枝の終わり(忘れやすい
  • restart|reload| で複数のパターンをまとめられる
  • *) … どれにも当てはまらないとき(他の言語の default)
  • esac … 終わり(case の逆さま)

パターンにはワイルドカードが使えます。ここが if との大きな違いです。

case "$file" in
  *.txt) echo "テキストファイル" ;;
  *.log) echo "ログファイル" ;;
  *.tar.gz) echo "圧縮ファイル" ;;
  *) echo "不明な種類" ;;
esac
flowchart TD
    A["case \"$action\" in"] --> B{"start ?"}
    B -->|"一致"| C["起動処理 → ;;"]
    B -->|"不一致"| D{"stop ?"}
    D -->|"一致"| E["停止処理 → ;;"]
    D -->|"不一致"| F{"restart / reload ?"}
    F -->|"一致"| G["再起動処理 → ;;"]
    F -->|"不一致"| H["*) 使い方を表示"]

systemctl start nginx のような「サブコマンドを取るツール」は、中身がまさにこの形をしています。自分のスクリプトにも start / stop / status を持たせると、一気に道具らしくなります。

やってみよう

端末で sh script.sh startsh script.sh stopsh script.sh reload、そして引数なしの sh script.sh を順に実行してください。それぞれ別の枝に落ちること、引数なしでは *) の使い方表示になることを確かめましょう。

演習

sh script.sh restart を実行して、サービスを再起動します と表示させてください。

ヒント1を見る

restart|reload) の枝に入る引数を渡します。

ヒント2を見る

下の端末で sh script.sh restart

実際に動かしてみよう

本文のサンプルや演習のコードは、コードブロック右上の「コピー」ボタンでコピーして、下のエディタに貼り付ければそのまま実行できます。

シェルスクリプト(シミュレート)

スクリプトを書くエディタと、それを動かす仮想シェルを読み込みます(本物のbashではなく、動きを再現した学習用の環境です)。
スクロールして表示された時点でも自動で読み込まれます。