250
216

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

知ると便利なヒアドキュメント

Posted at

#知ると便利なヒアドキュメント
よく、コマンドを実行する時に引数としてファイルを指定して、その中に書かれた物を使うといった物がある。例えばsftpのコマンド。更にはsshのキーファイルやpgpass、rsyncのエクスクルードなどなど。そういうコマンドをシェルから呼ぶ時にヒアドキュメントを使うと綺麗にかけたりすることがあります。
複数行に渡るファイルをシェルから作るときもechoを連発する必要もなくなります。

##ヒアドキュメントとは

echo line1
echo line2
echo line3

上記のような事を下記に置き換える事ができます。

cat <<EOF
line1
line2
line3
EOF

シンプルですね。
ファイルを作りたいときはリダイレクトするだけです。

cat <<EOF > test
line1
line2
line3
EOF

これだけで複数行に渡ったファイルを作れます。
シェルスクリプトの中でちょっとしたファイルや接続ファイル、エクスクルードファイルなどが必要な時、シェルスクリプトに含める事ができます。

ヒアドキュメントは標準入力として扱われます。文字列リテラルではありません。
従ってファイルを作る時もechoに渡すのではなく、catを使用しています。

##文法

cat <<EOF > test
line1
line2
line3
EOF

コマンドに<< EOSが渡されると次の行からEOSが単独で現れる行までの間が
ヒアドキュメントの内容になります。
EOSの部分は任意の文字を使うことができます。
また「EOSが単独で現れる行」というのは空白やタブも含んではいけません。

###行頭のタブを取り除く
ヒアドキュメントは便利ですが、インデントできないのが難点です。
EOSをインデントしてしまうとヒアドキュメントの終わりとして認識してくれませんし、
ヒアドキュメントの内容にインデントがそのまま反映されてしまいます。
この問題を解決するための機能が用意されていて、<<を<<-に書き換えるだけで
使用できます。<<-でヒアドキュメントを書くと、行頭のタブを無視してくれます。
ただ、やはり空白だけは無視してくれません。

cat <<-EOF > test
\t\tline1
\tline2
\t\tline3
\tEOF
testファイル
        line1
    line2
        line3

###変数展開をやめさせる
EOFをクォートします。

HOGE=hogehoge
cat <<'EOF' > test
line1
lne2
line3
$HOGE
EOF

としておけば下記のように$HOGEは文字列として扱われます。

testファイル
line1
line2
line3
$HOGE

##応用
ファイルを作るだけなく色々な所で役に立ちます。

sftp -oPort=2222 -oIdentityFile=hoge hoge@hogehoge.hogehoge.hoge << EOF
cd /tmp
put hoge1
cd /home
put hoge2
put hoge3
quit
EOF

##注意
便利ですが、パスワードファイルやキーファイルをシェルで作成する時は
シェルファイル自体のパーミッション、オーナーに十分注意しましょう。

250
216
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
250
216

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?