シェル芸
シェルスクリプト

たまに見ると便利なシェル芸集

まだまだ初心者ですが、いろいろためてきたものを載せてます


シェル芸とは?

シェル芸とは、主にUNIX系オペレーティングシステムにおいて

「マウスも使わず、ソースコードも残さず、GUIツールを立ち上げる間もなく、

あらゆる調査・計算・テキスト処理を CLI端末へのコマンド入力一撃で終わらせること」

である

(USP友の会:会長・上田隆一)

以下は自分が詰まったところをまとめています。


Q.しまった改行がCRLFだ!しかもめっちゃある時

GUIでこちこちやらずにCRLFをLFにする方法

例えばこんな時

/bin/bash^M: bad interpreter: そのようなファイルやディレクトリはありません

/bin/bash^M: bad interpreter: No such file or directory

こんな時はこう書きましょう

$ find ./target/pass(ディレクトリ)/*.filetype(拡張子) -type f -exec sed -i -e 's/\r//g' {} +

※バイナリファイルがあるときは拡張子に注意して実行してください


Q.毎回デフォルトの時刻を設定し直すのがめんどくさい

そんな時はこいつをコピペ

CentOSの場合

$ cp /usr/share/zoneinfo/Japan /etc/localtime ; sudo sed -i 's/UTC/Asia\/Tokyo/g' /etc/sysconfig/clock

Ubuntuの場合

$ timedatectl set-timezone Asia/Tokyo


Q.このファイル改行コードは何かわからない。。。

そんな時はfileコマンドで見てみましょう

$ file sample.sh

sample.sh: Bourne-Again shell script, UTF-8 Unicode text executable, with CRLF line terminators

最後らへんに改行コードが何か表示してくれます。


Q.リモートホスト先でスクリプトを起動しRootのものを操作したい

hostsなどRoot権限でしか操作できないものへのリダイレクトは通常一般ユーザーでの操作とみなされるのでsh -cのおまじないをするとsudoの権限が引き継がれるので操作可能な場合があります。

$ sudo sh -c "echo "hogehoge" >> hosts"


Q.テキトーにランダムなパスワードを作りたい

POSIX原理主義者な人の場合は以下の呪文を唱えてください

(生成する長さや含める文字のバリエーションを自由に選べます)

$ cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 16 | head -n 1

てっとり早くとりあえずランダムなやつを作りたい場合(コマンドが無い場合もあります。)

$ mkpasswd


Q.多段sshする先のファイルを手元に持ってきたい

いちいちSCPしたくない人へ

やり方1

Catを使う(猫じゃないよฅ( =✧ω✧= )ฅニャニャーン✧)

$ ssh user@hoge "ssh user@server 'cat remote.txt'" > local.txt

やり方2

ddコマンドを使う

$ ssh user@fumidai ssh user@server 'dd if=remote.txt 2> /dev/null' > local.txt

ちなみにサーバーに送りたい場合はこれ以下の呪文を唱える

$ ssh user@fumidai ssh user@server 'dd of=remote.txt' < local.txt

多段でsshしている先からファイルを取って来るときとか便利です。


Q.ファイルのリストをfor文で回したい、どうしたらいいの?

そんなあなたにぴったりの呪文はこちら!

$ IFS=$'¥n';for i in $(cat {引数とするファイル});do {実行したいコマンド} $i ;done


Q.変数の一部分だけをとりだしたい

echo ${HOGEHOGE#*@}のように表記することで@以降のみ取得できます

#は前方一致部分の削除、%は後方一致分の削除。

*でワイルドカード、##%%とやると最長一致

HOGE=${HOGEHOGE#*@}


Q.自分のグローバルIPをコンソール上から確認するには?

curlとかでリクエストをかけるとグローバルIPを教えてくれるドメインがあります。

$ curl ifconfig.co

$ http -b ifconfig.co
$ wget -qO- ifconfig.co
$ fetch -qo- https://ifconfig.co
$ bat -print=b ifconfig.co/ip

※セキュリティレベルの高いサーバーでは実施しないでください。


Q.ディレクトリを階層的に表示したいときは?

treeコマンドを使用するのがいいですがapt-get installとかできない場合はこれで代用しましょう。

$ pwd;find . | sort | sed '1d;s/^\.//;s/\/\([^/]*\)$/|--\1/;s/\/[^/|]*/|  /g'


Q.Pythonの静的なエラーを自動で修正する

autopepって便利ですよね、修正していいコードか一旦確認してから実行してください。

$ pep8 . | cut -d: -f1 | sort | uniq | xargs autopep8 -i


Q.指定した範囲のファイルを全文検索したい

例えば余分な空白が入ってないかを再帰的に確認したい時に便利

$ find . or pass/to/directory -type f | grep [search files extention]$ | xargs grep -n "some phrase you want to search"


Q.複数行指定したコメントアウトしたい

ヒアドキュメントを使えばコメントアウト可能

$ << COMMENTOUT

コメントアウトしたいメッセージ
COMMENTOUT


Q.複数のファイル名を一括で変換したい

とりあえずRenameコマンドを使ってみましょう

$ rename s/Before/After/g ./BeforeFiles


おまけ

FizzBuzzワンライナー

以下のように呪文を唱える

$ vim -es +$'norm 33o\nFizz\n\e' +$'let @a="ABuzz\e5k"|norm 20@a' +'%s/^$/\=line(".")/|%p|q!'

結果はやってみてからのお楽しみ

素数を数えたくてたまらない人向けdcワンライナー

$ echo '2p3p[dl!d2+s!%0=@l!l^!<#]s#[s/0ds^]s@[p]s&[ddvs^3s!l#x0<&2+l.x]ds.x'|dc

やめる時はctr+Cでやめましょう。