Raspberry Pi 2で遊ぶ(Ver.2.0):miniupnpcでルータのポート開け

このページは「Raspberry Pi記事まとめ 」に集約しています。

サーバとして外部公開するとき、通常だとルータのポートマッピングとポートフォワードの設定をする必要がありました。 設定する度にルータが再起動しないといけないので、QNAPを触っていたときに見つけたUPnPをLinuxで使えるか調べたところ、どうやらいけそうなことがわかりました。

UPnP(Universal Plug and Play)は、開けたいポートをルータに通知し、そのデバイスに対してのみポートを開けてくれる機能です。 QNAPのNASでルータ設定なしでWeb管理画面の外部アクセスをするときや、Skypeなどでも使用されています。

参考サイト

便利なのに意外と情報少ないんですよね・・・不思議。

■ 基本情報
Raspberry Pi 2 Model B + Class10 16GB microSDXC + WLI-UTX-AG300
IPアドレス体系は192.168.24.0、DHCP運用
ホスト名はgusion、Avahiではgusion.local
ユーザ名はpiからakitakaに置き換え

miniupnpcのインストール

Linux用のUPnPには、miniupnpcというパッケージがあります。

$ sudo apt-get install miniupnpc

UPnPを使って空いているポート一覧を見る

とにかくポートが空いている一覧ではなく、UPnPを用いて空いているポート一覧が表示されます。

$ sudo upnpc -l

ufw(ファイアウォール)が有効になっていると以下のメッセージが出ることがあります。

No IGD UPnP Device found on the network !

ので、ufwは切って再度実行しましょう。

$ sudo ufw disable

ポート空け(ポートマッピング)の追加

8080ポートを開けるには以下のようなコマンドを使います。

$ sudo upnpc -a 192.168.24.199 8080 8080 tcp

競合しているポートがあるとちゃんと警告してくれます。

AddPortMapping(8080, 8080, 192.168.24.199) failed with code 718 (ConflictInMappingEntry)
InternalIP:Port = 使用しているPCのIPアドレス:8080

これでいちいちルータの設定をいじる必要なくポート空けができるようになりました。
が、そのポートを使うサービスが動いてないと意味がありません。mjpg-streamerやmotioneyeなどを動かしておく必要があります。

準備ができたら、ufwも有効にして、ポートチェック【外部からポート開放確認】やスマホから外部アクセスできるか試してみましょう。

ポートマッピングの削除

空けた8080を閉じるには以下のコマンドを使います。

$ sudo upnpc -d 8080 tcp

固定IPを使用せずにminiupnpcを使う

サーバの基本は固定IPですが、DHCPのまま使う方法のヒントが「raspiでramdisk – Qiita」にありました。

自宅と実家のIPを固定してないので、UFWで許可するIPを動的に変えられる様にCRONで定期的に設定を更新している。

つまり、miniupnpcで明示しないといけないIPアドレスをCRONで自動取得するようにすれば、固定IPにすることなくUPnPを使用することができます。

IPアドレスのみを取得する方法

ipコマンドやifconfigコマンドではIP以外の情報がぞろぞろと付いてきます。
IPアドレスだけ取得する方法は「linuxで自分のIPアドレス文字列を抽出するための13のコマンド | mooapp」にありました。

$ hostname -I | cut -f1 -d' '

他にもありますが、今回はこのコマンドでアドレス取得します。

miniupnpcに使う場合

専用のスクリプトを作っても良いのですが、コマンド内でコマンドを実行する方法があります。
「`」で囲んだコマンドの実行結果を親コマンドに反映させる事ができます。
自分のIPアドレスを取得してpingする場合は以下のようになります。

$ ping `hostname -I | cut -f1 -d' '`

miniupnpcに使う場合は以下のようになります。

$ sudo upnpc -a `hostname -I | cut -f1 -d' '` 8080 8080 tcp

これが一番短くていいんじゃないでしょうか。

起動時にminiupnpcを有効にする

miniupnpcはサービスではないので起動時に実行されません。
cronで実行するだけなら上のコマンドでいけますが、いくつか条件を入れたいのでスクリプトを作ります。

$ vi miniupnpc.sh
【新規ファイル】
#!/bin/sh

upnpc -a `hostname -I | cut -f1 -d' '` 9000 9000 tcp

実行権限を付与

$ chmod 755 miniupnpc.sh

実行

$ sudo ./miniupnpc.sh

できたスクリプトをcronで回すか、init.d起動スクリプトにおけばいいかと思ったのですが・・・ufwが弾くことがあります。
1900ポート以外に変動するポートを使ってるようで。かと思えばうまく行ったり。よくわかりません。

コメントを残す

以下に詳細を記入するか、アイコンをクリックしてログインしてください。

WordPress.com ロゴ

WordPress.com アカウントを使ってコメントしています。 ログアウト / 変更 )

Twitter 画像

Twitter アカウントを使ってコメントしています。 ログアウト / 変更 )

Facebook の写真

Facebook アカウントを使ってコメントしています。 ログアウト / 変更 )

Google+ フォト

Google+ アカウントを使ってコメントしています。 ログアウト / 変更 )

%s と連携中