(※2018/3/17 新しい記事書きました) Dottyによる変更点と使い方
新しい記事を書きました. 本記事を包含します.
Dottyで何ができるようになるのかとその使い方を簡単にまとめたいと思います. 理論的な部分は深掘りしません.
以下ちょっと長め. 調べきれてない点も多々あるので, 抜けや間違いがあったら教えてください.
続きを読む複数のコマンドの出力をまとめてリダイレクトする2つの方法
1. ()
, {}
の利用
()
, {}
で囲んでまとめてリダイレクト先を指定する. 丸括弧の場合はサブシェルで, 波括弧の場合はカレントシェルで実行される.
例
{ command1 command2 } >> log 2>&1
2. exec
の利用
exec
は現行プロセスを別コマンドのプロセスに置換するコマンドである. このとき, 引数を省略してリダイレクトのみ記述することで現行プロセス (shell) のリダイレクト先を上書きすることができる.
例
exec >> log 2>&1 command1 command2
ちなみに元に戻す方法が見当たらないけどどうやるのだろうか… (exec 1>&1 2>&2
とかで戻ってくれても良さそうだがうまくいかない)
まとめ
exec
を使うと副作用が怖いので {}
(or ()
) でまとめてリダイレクトの方が無難っぽい (?)
sh・bash・zsh等, shellの違いでハマりやすい部分とか
前提として
sh
の実体は環境によって POSIX互換bash (bash --posix)
であったり, dash
であったり, busybox
であったりと様々である (ls -l `which sh`
とすれば実体がわかる). 唯一の制約は POSIX互換であること だ (※どこぞの今はなきお行儀が悪いOSを除けば). そのためシバンで sh
を利用する場合は, 最低限のPOSIX互換shell上で動作するように書かれるべき で, 例えば bash
拡張を用いる時はシバンで bash
を指定するべきだ. しかしながら, シバンで sh
を指定しているにも関わらずPOSIXの範囲を超えた命令を利用しても動いてしまうケースもままあり, 意識しないと難しい.
ハマりやすい差異の一例
空白 (正確には区切り文字) が含まれた変数
変数の展開され方が異なる
# bash, bash --posix, dash, busybox : > 'a b' x='a b' mv $x c # error (`mv a b c` と解釈される) ls # -> 'a b'
# zsh : > 'a b' x='a b' mv $x c # (`mv 'a b' c` と解釈される) ls # -> c
文字列の比較
==
による文字列比較はPOSIX互換のものではない
# dash [ 'a' = 'a' ] && echo 'ok' || echo 'ng' # -> ok [ 'a' == 'a' ] && echo 'ok' || echo 'ng' # error -> ng
# zsh [ 'a' = 'a' ] && echo 'ok' || echo 'ng' # -> ok [ 'a' == 'a' ] && echo 'ok' || echo 'ng' # error
# bash, bash --posix, busybox [ 'a' = 'a' ] && echo 'ok' || echo 'ng' # -> ok [ 'a' == 'a' ] && echo 'ok' || echo 'ng' # -> ok
プロセスリダイレクト
これは bash
・zsh
固有の機能の一つ
# bash --posix, dash, busybox cat <(echo 'a') # error
# bash, zsh cat <(echo 'a') # -> a
結論
shellは方言や実装で微妙に違うところが多すぎて厳しい
Docker Composeでビルド時に任意のイメージ名を指定する方法
公式リファレンスを見ても分かりづらいのでメモ.
Docker Compose経由でビルドされたデフォルトイメージ名は {プロジェクト名}_{サービス名}
となる (デフォルトプロジェクト名はディレクトリ名だが, コマンドラインオプション -p
から指定可能). 例えば以下のような構成であれば, イメージ名が hoge_fuga
, コンテナ名が piyo
となる.
hoge ┣ Dockerfile ┣ docker-compose.yml ┗ ...
# docker-compose.yml version: '2' services: fuga: build: . container_name: piyo
しばしば長ったらしいイメージ名になってしまう. そこで以下のように image
を追加することでイメージ名を指定できる. image
と build
が同時に宣言されている場合は, ビルドが優先的に実行されて, image
はその構成に使われる (image
によるプルは発生しない).
結果としてイメージ名が nyan
, コンテナ名が piyo
となる. ちなみにタグの付与も image
からできる. これらは全て, Compose File v2からの機能である.
# docker-compose.yml version: '2' services: fuga: build: . image: nyan container_name: piyo