【Windows】バッチコマンドで繰り返し作業をサボろう！①【導入編】

# INDEX
- 1. 背景
- 2. 目的
- 3. やろうず！
- 4. あとがき

# 1. 背景
![34a92ba146c7578f492ceeb3d1bcb3af.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/92447/2218b150-d6ce-54f0-2048-e4d77a585661.jpeg)
…という事で、作ったアプリのテストで、iPhone/iPadのスクショを撮ったんですが、高解像度な上にデフォルトがフルカラーPNGなんだね。
後でテスト結果集計する為に大量のpngファイルを一括でjpgにしたり、画質を落としたりってのをやりたかったので古（いにしえ）のバッチコマンド仕立てにしたという話。自作なので客先PCに入れるにも理解が得やすいし。
それにしてもiPhoneって端末からそのままアップするとファイル名がハッシュだったり、画質最高のPNGだったり解像度お化けだったりで扱いにくね…。大切な事なので2回言いました。
それに何と言っても **GUIで1ファイル毎にやってられっかYO！面倒くせぇんだYO！！**（あ、関係ないですが[藤原書記](https://www.google.com/search?q=%E3%83%89%E3%83%BC%E3%83%B3%E3%81%A0YO&source=lmns&bih=934&biw=1561&hl=ja&sa=X&ved=2ahUKEwiqi6mxgvDtAhVvEqYKHaweDHsQ_AUoAHoECAEQAA)は大好きです）

今回は、導入編という事でバッチコマンドの基本部分を自分のPCに構築する。

# 2. 目的
コマンドプロンプトでお手製のバッチコマンドを使えるようにする。
完成系はこんな感じ。

```winbatch
> test
バッチコマンドのテンプレートです。これを参考にコマンドを実装して下さい。
usage)
  test

>
```

# 3. やろうず！
- この記事でやる作業の流れはこんな感じ
    - 1. バッチコマンド置き場をWindowsのパスに通す
    - 2. バッチコマンドを作る
    - 3. 動作確認する

## 3.1. バッチコマンド置き場をWindowsのパスに通す
- 置き場所を決める！
    - 好きに決めていい。自分は `d:\usr\bin` にした。
        ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/92447/74ee66d0-953f-ec9a-779c-473f94ff5f66.png)
- 環境変数の編集ウィンドウを開き、バッチコマンド置き場を定義した環境変数を環境変数`PATH`に追加する
    - 環境変数ウィンドウを開く（スタートメニュー脇の検索ツールで【環境変数】とか入れると出てくる）
        ![68747470733a2f2f71696974612d696d6167652d73746f72652e73332e61702d6e6f727468656173742d312e616d617a6f6e6177732e636f6d2f302f39323434372f37373231613839612d383935652d626266332d386135312d6538646361363632613863332e706e67.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/92447/e21d2eab-f05c-6b89-4cdf-dce59e323457.png)

    - 上のスクショのようにバッチコマンドを置く位置の環境変数を定義して、そこにディレクトリを指定する
        - 自分は `USER_BIN_HOME` にした
    - 上で追加した環境変数を `PATH`の末尾に追加する（分かってる人ならどこでもいい）
        ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/92447/ffb2ea70-3840-c895-fe93-d2902032e628.png)
        - ちなみに自分だけで使うはずなので **ユーザ環境変数に設定した方が良い** 。システム環境変数は全ユーザに影響するし**管理者権限も必要になる**し。


## 3.2. バッチコマンドを作る
今回はテンプレなんで、これをコピペして、文字コードを`Shift-JIS`でテキストファイル化しておく。名前は`test.bat`とでもしておいてくれ。なので自分は `d:\usr\bin\test.bat` にファイルを置いた。

```winbatch
@echo off

rem 引数チェック
if "%1"=="" (
  call :HELP_MSG
  exit /b 0
) else (
  rem 引数のバリデとか事前処理
  if /i not "%1"=="start" (
    echo Opps! unknown arguments.
    exit /b 1
  )
)

rem メイン処理
echo hello!

exit /b 0

rem ------------------------------
rem ヘルプ用メッセージ
rem ------------------------------
:HELP_MSG
  echo バッチコマンドのテンプレートです。これを参考にコマンドを実装して下さい。
  echo usage)
  echo  test start
  echo.
exit /b
```

## 3.3. 動作確認する
コマンドプロンプトを起動しなおして、次のように操作する。
同じような応答が返ってきたら今回の作業は成功だ！おめでとう！！

### whereコマンドでパスが通っている事を確認する
```console
> where test
D:\usr\bin\test.bat
```
- 返ってきたな。ぐっぼーぃ！
- **コマンドがないぞ** と怒られる場合は、コマンドプロンプト再起動、環境変数の不備を確認してみてくれ

### そのまま実行してヘルプメッセージが出る事を確認する
```console
> test
バッチコマンドのテンプレートです。これを参考にコマンドを実装して下さい。
usage)
 test start
```
- よしよし、これもいいな。
- ヘルプメッセージが出ない場合は、バッチコマンドの文字コードが`Shift-JIS`になっている事や、コピペミスを確認してみてくれ。ローカルチェックはしているので出ないはずなんだ。

### おまけで付けた引数分岐も確認してみる
```console
> test start
hello!

>
```
- ここまでできればテンプレとして十分だと思う！

## 3.4. ちょっとだけソース解説
先述のスクリプトはこんな感じでラベルを使って疑似的なサブルーチンを実現している。
`任意の処理` を `:ラベル名` と `exit /b` で括るイメージだ。
ラベルに飛ぶだけだったら`goto`で良いんだけど、`exit`をした時に戻ってきて欲しいので`call`を使うのが肝。また、ラベルは別にサブルーチンではないので、メイン処理用の`exit /b`が無いと疑似サブルーチンの処理も順次実行してしまう。

```winbatch
@echo off

rem 疑似サブルーチンの呼出元
echo hello! how are you?
call :FINE_THX
echo me too.

exit /b

rem 疑似サブルーチンの呼出先
:FINE_THX
  echo fine, thanks.
exit /b
```

上記を実行するとこんな感じになるので、サブルーチンを呼んだ感じの順番になっている事が分かる。

```console
> test
hello! how are you?
fine, thanks.
me too.

>
```

せっかくなんで、`call`の代わりに`goto`を使うとこうなる。`me too.`が出てこないね。

```console
> test
hello! how are you?
fine, thanks.

>
```

メイン処理の `exit /b` を忘れた場合。`me too.`の後にまた`file, thanks.`が出てしまっている。
つまり疑似サブルーチンをまた実行してしまったという事。他言語だと`which case`に`break`を入れ忘れたと言えば通じるだろうか。

```console
> test
hello! how are you?
fine, thanks.
me too.
fine, thanks.

>
```


# 4. あとがき
今回作成したバッチコマンドはいわゆる「hello, world」なので **このままでは** クソの役にも立たない。
連続物の記事として以下のようなバッチコマンドは実際に作って記事にしてみようと思っている。

- 特定URL+連番ファイルのダウンロードする
- 高画質PNGをそこそこの品質・解像度のJPGに変換する

…というかバッチコマンドはもう作ったので、記事作成は年末年始のお題にしておこうかなと思ってる。
もしこの記事が「役に立った！次も見たい！」という方は高評価ボタンとチャンネル登録をしｔ（ｒｙ

あー、サブルーチン周りももう少し書きたい気分。これは別記事かな。

以上！