UPnPによるDLNAサーバの探索
DLNAサーバ(おうちクラウドDIGA)にある音楽ファイルを、スマホで操作してGoogle Homeで再生したい。
スマホにDLNAクライアントアプリを入れて、スマホをGoogle Homeにキャストしてみたところ、再生はできるものの、アプリのせいなのかわからないが途中で止まる。
またスマホで別の操作をしていると(ゲームとか)、その音がGoogle Homeから流れ出てしまう。
これはよろしくない。
ということで、次のような構成で音楽を再生できるようにすることを目標として、いろいろ調べてみることにした。
まずは、音楽データがあるDLNAサーバ(DMS)と通信できる必要がある。
ここの記事を参考にさせてもらい、Python 3.7でローカルネットワーク上のDLNAサーバを探すスクリプトを作って実行してみた。
DLNAってなんじゃらほい? - SSDPを喋ってみる - - 初老のボケ防止日記
import socket timeout = 10 msearch_request_lines = ( 'M-SEARCH * HTTP/1.1', 'HOST: 239.255.255.250:1900', 'MAN: "ssdp:discover"', f'MX: {timeout}', 'ST:ssdp:all', '', '' ) sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) sock.settimeout(timeout) msearch_request_body = '\r\n'.join(msearch_request_lines) sock.sendto(msearch_request_body.encode('utf-8'), ('239.255.255.250', 1900)) while True: try: res, device = sock.recvfrom(4096) print(f'>>>>>>>>>> from {device} <<<<<<<<<<') print(res.decode('utf-8')) except socket.timeout: break sock.close()
すると、やたらいっぱい応答が返ってきた。
その一部を載せておく。
>>>>>>>>>> from ('xxx.xxx.xxx.1', 1900) <<<<<<<<<< HTTP/1.1 200 OK CACHE-CONTROL: max-age=120 ST: upnp:rootdevice USN: uuid:bc329e00-1dd8-11b2-8601-84afec3998c1::upnp:rootdevice EXT: SERVER: SDK 4.3.0.0 UPnP/1.0 MiniUPnPd/1.6 LOCATION: http://xxx.xxx.xxx.1:57323/WFADeviceDesc.xml >>>>>>>>>> from ('xxx.xxx.xxx.1', 1900) <<<<<<<<<< HTTP/1.1 200 OK CACHE-CONTROL: max-age=120 ST: urn:schemas-wifialliance-org:device:WFADevice:1 USN: uuid:bc329e00-1dd8-11b2-8601-84afec3998c1::urn:schemas-wifialliance-org:device:WFADevice:1 EXT: SERVER: SDK 4.3.0.0 UPnP/1.0 MiniUPnPd/1.6 LOCATION: http://xxx.xxx.xxx.1:57323/WFADeviceDesc.xml >>>>>>>>>> from ('xxx.xxx.xxx.25', 1900) <<<<<<<<<< HTTP/1.1 200 OK CACHE-CONTROL: max-age=1800 DATE: Tue, 29 Jan 2019 15:04:54 GMT EXT: LOCATION: http://xxx.xxx.xxx.25:60607/D8AFF1C0AF18/Server1/ddd SERVER: Linux/4.0 UPnP/1.0 Panasonic-UPnP-MW/1.0 ST: urn:schemas-upnp-org:service:RenderingControl:1 USN: uuid:4D454930-0300-1000-8000-D8AFF1C0AF18::urn:schemas-upnp-org:service:RenderingControl:1 >>>>>>>>>> from ('xxx.xxx.xxx.25', 1900) <<<<<<<<<< HTTP/1.1 200 OK CACHE-CONTROL: max-age=1800 DATE: Tue, 29 Jan 2019 15:04:54 GMT EXT: LOCATION: http://xxx.xxx.xxx.25:60607/D8AFF1C0AF18/Server1/ddd SERVER: Linux/4.0 UPnP/1.0 Panasonic-UPnP-MW/1.0 ST: urn:schemas-upnp-org:service:ConnectionManager:1 USN: uuid:4D454930-0300-1000-8000-D8AFF1C0AF18::urn:schemas-upnp-org:service:ConnectionManager:1 >>>>>>>>>> from ('xxx.xxx.xxx.25', 1900) <<<<<<<<<< HTTP/1.1 200 OK CACHE-CONTROL: max-age=1800 DATE: Tue, 29 Jan 2019 15:04:52 GMT EXT: LOCATION: http://xxx.xxx.xxx:60606/D8AFF1C0AF18/Server0/ddd SERVER: Linux/4.0 UPnP/1.0 Panasonic-UPnP-MW/1.0 ST: urn:schemas-upnp-org:service:ContentDirectory:2 USN: uuid:4D454930-0100-1000-8000-D8AFF1C0AF18::urn:schemas-upnp-org:service:ContentDirectory:2 ・・・
xxx.xxx.xxx.1というのは無線ルータ。UPnPで応答するものはすべて何かしら返してくる様子。
音楽データがあるDLNAサーバはxxx.xxx.xxx.25。これからも複数の応答が返ってきている。役割毎に応答を返している様子。
今回はDLNAサーバにある音楽データを取得したいので、応答のUSNにContentDirectoryを含むものが対象。
上記の応答結果だと一番下に記載しているものが該当する。
とりあえずDLNAサーバの検知はできた。
次は、応答のLOCATIONに書かれているURIを辿って、実際の音楽データのURIを取得してみる予定。 →コンテンツの中身の探索