それマグで!

知識はカップより、マグでゆっくり頂きます。 takuya_1stのブログ

習慣に早くから配慮した者は、 おそらく人生の実りも大きい。

OpenWrtの各機能をcurl/JSON/APIで叩いて状態を取得する。

openwrt の各機能へcurlでアクセスする

ネットの検索結果を眺めていると、面白いものを見つけた。

https://floatingoctothorpe.uk/2017/managing-openwrt-remotely-with-curl.html

ただし任意のコマンドが実行できてしまうので、「定期的に状態を取得したい」のであれば、SSHを使うべきある(後述)

導入

luci へrpc 機能を追加するパッケージを使う。

opkg install luci-mod-rpc
/etc/init.d/uhttpd restart

ログイン。

最初にログインして、キーを発行する。

curl -X POST http://192.168.1.1/cgi-bin/luci/rpc/auth --data '
{
  "id": 1,
  "method": "login",
  "params": ["root", "Passwooooord"]
}' | jq .

JSONでレスポンスが返ってくる。

{
  "id": 1,
  "result": "0240189644e2d261dd5fxxxxxxxxxxxx",
  "error": null
}

出てきた、キーは、後で使いやすいように変数に放り込んでおく

APIKEY=1629306752494e0xxxxxxxxxxxx

キーの有効期限を確認。

最初にリクエストの練習として、キーの有効期限を取得する。

APIKEY=1629306752494e0xxxxxxxxxxxx
curl -X POST http://192.168.2.1/cgi-bin/luci/rpc/uci?auth=$APIKEY --data '
{
  "id": "1",
  "method": "get",
  "params": ["luci", "sauth", "sessiontime"]
}'

最大1時間の有効期限が得られる。

{
  "id": "1",
  "result": "3600",
  "error": null
}

Luciのトップページに表示される情報を取得する。

curl -X POST http://192.168.1.1/cgi-bin/luci/rpc/sys?auth=$APIKEY --data '
{
  "id": "1",
  "method": "exec",
  "params": ["ubus call system info"]
}'  | jq .result -r   |  jq .
curl -X POST http://192.168.1.1/cgi-bin/luci/rpc/sys?auth=$APIKEY --data '
{
  "id": "1",
  "method": "exec",
  "params": ["ubus call system board"]
}'  | jq .result -r   |  jq .

これで、luci で使われている画面に出ているJSONを好きな部分をAPI経由で取れるようになった。

コマンドの調べ方。

LUCI の画面を表示した状態で、http リクエストを眺めていると、コマンドが何となく分かる。

f:id:takuya_1st:20220203020356p:plain

ubus コマンド

ubus コマンドで情報取得が出来る。

ubus list 
ubus call system info
ubus call luci.ddns get_services_status

細かい部分は、openwrtのマニュアルにある。

他に取れるもの

  • ファイルを表示
  • uci で設定
  • パッケージ関連

等がある。それぞれEndpointが異なる。

/cgi-bin/luci/rpc/uci
/cgi-bin/luci/rpc/fs
/cgi-bin/luci/rpc/sys
/cgi-bin/luci/rpc/ipkg

ファイルを取得はログの閲覧などにできます。

コマンドインジェクションだから利用には注意。

これ、コマンドインジェクションで実現されているので、実行には十分に注意する必要がある。

代替手段にする → SSHの公開鍵オプションを使う

RPCを有効にしてしまうと、任意のコマンドが実行できてしまう、またHTTPでアクセスするので、パスワードは丸見えである。しかもプログラムから自動実行するとパスワードが定期的に流れるのである。恐ろしい。

ssh の公開鍵には、コマンドの実行を制限する機能がある。これを使って、指定のコマンドしか使えない「RSA鍵ペア」を用いて、状態を取得するほうがいい。

no-pty,no-port-forwarding,no-agent-forwarding,command="/bin/ubus call luci.ddns get_services_status" ssh-rsa AAAAB3NXXXXXXXXXX name@host

openwrt の dropbear でもちゃんとOptionが使える。

オプションを認識しているので、指定のコマンド専用の鍵を作ることが出来る。

f:id:takuya_1st:20220210041206p:plain

このほうがかなり安心であり、セキュリティも十分である。