地方エンジニアの学習日記

興味ある技術の雑なメモだったりを書いてくブログ。たまに日記とガジェット紹介。

nc コマンドで始めるワンライナーHTTPサーバ

httpサーバワンライナー

httpサーバを簡易的に生成する方法はたくさんあってpythonなりperlなりでphpなりでワンライナーで書けたりします。

今回はそれらのLL言語を使わずにコマンドラインからhttpサーバを起動してみる

必要パッケージはnetcatコマンドを使うのでnmap-ncat.x86_64を入れてあげる。

使い方はとても簡単でncコマンドの引数に-l listenしたいポート番号を入れてあげるだけ。

$ nc -l 8080

# 別コンソールからcurlをlocalhostに向けて実行するとncに下記のように出力される。
GET / HTTP/1.1
User-Agent: curl/7.29.0
Host: localhost:8080
Accept: */*

これで単純なhttp通信を行うことが可能。ただこれだけだとデータを送信しただけで何もしない。curlもncも止まってしまうといった挙動になる。

(curlは相手からのデータが何も送られてこない場合はデフォルトで300秒のタイムアウトまで時間を取ってるらしい。-m 1とかやるとすぐにtimeoutとなってコマンドは返ってくる)

curlに対して簡易的なhttprレスポンスを返す場合は以下のように実行することでhttpリクエスト->レスポンスの動きをみることが可能。

$ while true; do ( echo "HTTP/1.0 200 Ok"; echo; echo "Hello World" ) | nc -l 8080; [ $? != 0 ] && break; done

# 別コンソールからcurl
$ curl localhost:8080 -m 2
Hello World

こんな感じで簡易的なhttpサーバをワンライナーで立てることが可能。

Proxy

L4プロキシーも名前付きパイプを利用することで作成することが可能。

名前付きパイプとは独立なプロセス間の通信を許可する特別なファイルタイプである。プロセスAが書き込んだ内容をプロセスBが読み取るといった動き。

名前なしパイプがps aux | grep apacheでいうところの|を示している。

$ mkinfo fifo

$ nc -l 8080 0< fifo | nc localhost 80 1> fifo

上記の状態では8080ポートで外部とtcp通信を行い受け取ったデータを80番ポートで待ち受けているプロセスへ名前付きパイプを通してデータを通信している。

qiita.com

名前付きpipeの使い道としては他にも複数ファイルへの同時出力なんかを行う際に使ったりする。下の書き方だとコメントアウト行のあるなしで出力先のファイルを分けている。

$ mkfifo pipe
$ (grep -v \# < fifo > hoge.txt) &
$ ls -l | tee fifo | grep \# > fuga.txt