nc (netcat) 入門 - ポート疎通とデバッグの万能ツール
この記事で解決できること
nc -zvでポートが開いているか 1 コマンドで確認 できる-lフラグで 簡易サーバを即座に起動 し、通信テストができる- ファイル転送・バナー取得・UDP 疎通確認など nc の主要な活用パターン が身につく
nc.openbsd/ncatの違いと、-zが使えない場合の対処法がわかる
結論(実務の型)
- ポート疎通確認 →
nc -zv host port - 簡易サーバ →
nc -l 8080(受信側) - ファイル転送 → 受信側
nc -l 9999 > out.txt、送信側nc host 9999 < in.txt - タイムアウトは
-w 秒数で指定する
nc とは?
nc(netcat)は TCP / UDP のソケットに対して直接 read/write するコマンドライン汎用ツールで「ネットワークの Swiss Army knife」とも呼ばれる。curl は HTTP、ping は ICMP と用途が固定されているのに対し、nc は任意のポートと任意のプロトコルで通信できる点が最大の特長。サービスが起動していない状態でも nc だけで受信側を立ててテストできるため、ネットワーク疎通・アプリ起動前の検証・CI 環境の接続テストに幅広く使われる。
ポートが開いているか確認するには?
-z(zero-I/O モード:データを送らず接続のみ確認)と -v(詳細表示)を組み合わせて使う。
$ nc -zv example.com 80 Connection to example.com 80 port [tcp/http] succeeded! $ nc -zv example.com 22 Connection to example.com 22 port [tcp/ssh] succeeded!
ポートが閉じている・到達不可の場合:
$ nc -zv example.com 25 nc: connectx to example.com port 25 (tcp) failed: Connection refused
ポート範囲をまとめてスキャンする:
$ nc -zv example.com 20-25
-w でタイムアウト(秒)を設定するとハングを防げる。
$ nc -zv -w 3 192.168.1.10 443
簡易サーバ(listen モード)を起動するには?
-l フラグで指定ポートを待ち受ける。接続が来ると標準入出力をソケットに接続する。
# 受信側(先に起動) $ nc -l 8080 # 送信側(別ターミナル) $ nc localhost 8080 Hello from client!
送信側で入力した内容がリアルタイムに受信側へ流れる。双方向通信になるため、簡易チャットとして使うことも可能。
nc はデータを平文で送受信する。認証・暗号化はない。本番環境での永続サーバとして使うことは想定されていない。
ファイル転送はできるか?
リダイレクトを使って受信側 → 送信側の順で起動するだけで転送できる。SCP / rsync が使えない環境での一時的なデータ渡しに有効。
# 受信側(先に起動) $ nc -l 9999 > received.tar.gz # 送信側 $ nc receiver-host 9999 < archive.tar.gz
転送が終わったら送信側の nc が EOF を送り終了する。受信側が終了しない場合は Ctrl+C で止める。
OpenBSD 版は -q 0(EOF 受信後すぐに終了)オプションで受信側も自動終了させられる。
$ nc -l 9999 -q 0 > received.tar.gz
HTTP / SMTP バナーを確認するには?
nc でサービスへ接続し、プロトコル仕様に沿ったリクエストを手動送信することで、サービスの応答(バナー)を確認できる。
HTTP ヘッダーを確認する
$ printf "HEAD / HTTP/1.0\r\n\r\n" | nc example.com 80 HTTP/1.1 200 OK Server: nginx/1.24.0 ...
SMTP バナーを確認する
$ nc mail.example.com 25 220 mail.example.com ESMTP Postfix (Ubuntu)
バナーに含まれるバージョン情報やサーバ種別を確認することで、ミドルウェアのデプロイ確認やセキュリティ評価ができる。
UDP モードを使うには?
-u フラグを付けると UDP ソケットを使う。DNS(53)・NTP(123)・syslog(514)など UDP サービスの疎通確認に使う。
# UDP ポート疎通確認 $ nc -u -zv 8.8.8.8 53 Connection to 8.8.8.8 53 port [udp/domain] succeeded! # UDP 簡易リッスン $ nc -u -l 5005
UDP はコネクションレスのため -z での疎通確認が不正確になる場合がある。相手がパケットを受け取っても応答しなければ失敗と判定される。UDP 疎通の正確な確認は専用ツール(nmap -sU 等)を検討する。
nc のバリアントはどう違う?
Linux の nc コマンドには複数の実装が存在し、オプションの互換性が異なる。
| コマンド | パッケージ | 特徴 |
|---|---|---|
nc (OpenBSD 版) |
netcat-openbsd |
Ubuntu/Debian 標準。-z -w -q など豊富 |
nc (Traditional 版) |
netcat-traditional |
旧実装。-z 非対応、-e でシェル実行可 |
ncat |
ncat(nmap 同梱) |
SSL/TLS 対応、ブローカーモードあり |
現在のバリアントを確認する:
$ nc -h 2>&1 | head -1 OpenBSD netcat (Debian patchlevel 1.226-1)
OpenBSD 版に切り替える(Ubuntu):
$ sudo apt install netcat-openbsd $ sudo update-alternatives --config nc
よくある事故パターン
1. nc: invalid option -- 'z'
netcat-traditional が入っている場合は -z が使えない。netcat-openbsd をインストールして切り替える(前述の「バリアント」参照)。
2. ポートが開いているのに「Connection refused」
アプリが LISTEN していないか、ファイアウォールでブロックされている。
# LISTEN 状態を確認 $ ss -tlnp | grep ':8080' # UFW 状態確認 $ sudo ufw status
3. ファイル転送が終了しない
受信側の nc が EOF を認識せずハングする場合は Ctrl+C で止め、送信側が先に終了していることを確認する。OpenBSD 版では -q 0 を付けると EOF で自動終了する。
4. -l で再利用できない(Address already in use)
ポートが TIME_WAIT 状態にある可能性がある。
# ポート使用状況を確認 $ ss -tlnp | grep ':8080'
別ポートを使うか、少し待ってから再試行する。