@sunatomo さま
お疲れ様です。
早速、新リリース試してみましたが、Album Viewから+サインをクリックし、アルバムをキューに追加しようとすると"No Such Directory"のエラーが出るようになりました。因みにNASから直接追加する分には問題ありません。
よろしくお願いします。
webui-plus開発/サポート(webui-plus development/support)
@sunatomo さま
お疲れ様です。
早速、新リリース試してみましたが、Album Viewから+サインをクリックし、アルバムをキューに追加しようとすると"No Such Directory"のエラーが出るようになりました。因みにNASから直接追加する分には問題ありません。
よろしくお願いします。
@Ashra さま
早速、新リリース試してみましたが、Album Viewから+サインをクリックし、アルバムをキューに追加しようとすると"No Such Directory"のエラーが出るようになりました。
失礼いたしました。AlbumViewのリンク周りでアルバム名の認識を拡張した際にパスのエンコード・デコードに使用する関数が混在していたためでした。
という訳で、差替パッケージをアップしましたので、12/18版をお試しの方はアップデート頂ますようお願いします。
ちょっとおまけ:JavaScriptでのURLエンコード・デコードについて
JavaScriptでは過去の経緯は不明ですが、URLエンコード・デコードでそれぞれ2種類の関数があります。
エンコード側のみ関数名を書くと、encodeURI と encodeURIComponet になります。
後者の方はこちらの通り 通常URLとして使用する全ての文字列をエンコードしてくれるというものです。
実はmpdで各楽曲ファイルやディレクトリのパスとして今まで使用していたURLでは前者の関数を使用していました。
(それで問題が出なかった理由としては「NASによるファイル共有のパスで使用されているディレクトリ名」は必ずしも「アルバム名」と一致するとは限らないためです。)
今回AlbumViewではアルバムの特定のためURLにアルバム名文字列を直接入力する必要が生じましたが、このときに様々な文字を正確に伝送するため後者の関数を使用する必要がありました。
↑
この修正を行った結果、「+」ボタンでのアルバム追加でデコードが正常に出来ないケースがバグとして発生したわけです。
長らくご無沙汰しております。
さて、リハビリを兼ねて個人的な興味のあるところからとなりますが、
「httpsのサポートがなんとかなりそう」というところまで判明しましたので、
もう少しだけ情報を集めてやり方を記載していきます。
目処は今週末を予定します。
ただし、httpsを有効化した場合、WebUIから "smpd.local" 以外のアクセスもすべてhttpsを使わないとブラウザの設定上エラーとなる事例があるため、プログラムの修正版リリースも必要な模様です。
今回の説明は以下の3部立てでレスを分けます。
1.サポートを行う前提(建前)について
2.自分でCA証明書と サーバ鍵などのセットを作成する方法について
3.ympd(webui)で https を有効化する方法+当方作成のCA証明書+サーバ鍵の配布
・webuiにてhttps サポートを行う理由
現状の近代的ブラウザではhttp に代わり https が標準となりつつあります。
(理由としてはサーバとブラウザ間の通信を暗号化してその内容を保証するため)
すでに一部ブラウザでは smpd ターゲットである LAN 環境下でも https を使わないと NG (もしくは設定変更により http でのアクセスを有効化する必要がある)な事例が発生しているため、
今回サポートの記述を追加しています。
また、今後”もしかしたら”サポートする可能性があるPWA(プログレッシブWebアプリ)では https アクセスが前提となるため、
これを先取りしてサポートする必要があります。
注意:https 化した場合、以下の制限があります。
・smpd で webui にアクセスする場合、「全ての端末で https でアクセスする必要」があります(例えばPCだけは https、ipad は http などの使い分けは 「NG」)
・エラーメッセージを表示させない「正しい https での通信を確立する」ためには、各端末のブラウザでCA証明書をインストールする必要があります。
なお、サーバ証明書を公の証明機関に送ることで端末に既にインストール済みのCA証明書で認証させることは可能ですが、
そのために当方として使用料金を支払う予定はありません(個人的に行いたい方はご自分でどうぞ)。
以下、個人的にはこちらの記述が非常に分かりやすく、結果としてこの記述に助けられたので、参照しながら記載します。
作成についてはsmpdのインストールされたRaspberryPi上で実施します。
root ユーザでも良いので ssh ログイン後、ホームディクトリ内に ”cert” でも何でも良いのでディレクトリを作成してその中でコマンドをを入れてください。
・CA証明書を作成する
(1)CA証明書で使用する秘密鍵を生成
openssl genrsa -aes256 -out localCA.key 2048
パラメータ + オプションを解説すると、
genrsa: RSAによる秘密鍵生成
-aes256: 秘密鍵をaes256ビットでの暗号化(パスワード付き)
-out ファイル名: 指定ファイル名で出力
数字: キーのビット数(2048ビット)
このときの秘密鍵は暗号化されているため、この後で使用するたびにopensslのアプリから問い合わせを受けます。
(2)生成した秘密鍵と識別情報を指定してCSR (certificate signing request 証明書署名要求) を生成
openssl req -out localCA.csr -key localCA.key -new
識別情報は以下の通りでOKでしょう。
Country Name:jp
State or Province Name:Tokyo
Locality Name: 空欄でOK
Organization Name: Papalius
(ここはsmpd作者のパパリウス様に敬意を込めてこのようにしましたが、実際にはサイト例の通り John Doe のような匿名でも良いです)
Organizational Unit Name:空欄でOK
Common Name:Papalius
(ここはサイト例の通り Organization Name と合わせています)
Email Address:symphonic.mpd@gmail.com
(smpd のサポートサイトにしましたが、ここも実際には適当に入れてもOKです)
A challenge password:空欄でOK
An optional company name:空欄でOK
パラメータ・オプションの解説は以下の通り
req: CSRの作成要求
-key: 使用する秘密鍵の指定
-new: 新規作成
作成したCSRの中身を確認する際、以下の通りコマンドを入れてください(サイトの例のように表示されればOK)。
openssl req -text -noout in localCA.csr
(3)CA証明書を作成(CSRを秘密鍵で自己署名)
ここでのポイントは -days オプションの数字です。
LAN上でsmpdでしか使わない CA証明書ですから、なるべく長めというわけで、5110日に指定しました(2036年まで有効化)。
セキュリティ的に怖い場合は、短くしても良いでしょう(ただし 証明書の有効年度がすぎると再度インストールが必要)。
openssl x509 -req -days 5110 -signkey localCA.key -in localCA.csr -out localCA.crt -extfile rootca_v3.ext
パラメータ・オプションの解説は以下の通り
x509: x509形式でCA証明書作成
-signkey: サインキーを指定する
-in: CSRファイルを指定
-out: 出力ファイルを指定
-extfile: openssl に渡すパラメータファイルを指定
smpdの標準イメージの場合、openssl のパラメータファイルは /etc/ssl/openssl.cnf を使用しますが、実際には以下の記述でCA証明書専用パラメータファイルを作っておいたほうが私は良いと思います。
subjectKeyIdentifier=hash
authorityKeyIdentifier=keyid,issuer
basicConstraints=critical,CA:true
keyUsage = cRLSign, keyCertSign
nsCertType = sslCA, emailCA
簡単に言うと、ルート証明書での設定のポイントは basicConstraints と keyUsare で、
正確にはこのように記載がないとNGとなります。
作成後の証明書の中身を確認する場合は、以下のコマンドになります。(2項のコマンドに似ているが、頭のパラメータにx509と付いている。これは、証明書の初期がx509であるためになります。)
openssl x509 -text -noout -in localCA.crt
これで localCA.crt という名称でCA証明書が生成されました。
(4)Android向けのバイナリ証明書を生成する。
Androidの場合、バイナリ証明書を生成しないとインストールできません。
これは作成済みのlocalCA.crtをder形式に変換しlocalCA.der.crtファイルに出力するというコマンドになります。
openssl x509 -in localCA.crt -out localCA.der.crt -outform der
・サーバ証明書を作成する
次は実際にサーバで使用する証明書を作成していきます。
(1)サーバ用の秘密鍵を生成
CA証明書の秘密鍵とほぼ同じなので、説明は省略
openssl genrsa -out smpd.local.key 2048
ここで仮に -aes256 を指定した場合、以下のコマンドで復号したものを使用しないと
サーバ証明書として ympd に読み込ませた場合に ympd 側でエラーが発生します。
(パスフレーズが指定されていないため使えない)
一応消し込みのコマンドは以下の通り
mv smpd.local.key smpd.local.encrypted.key
openssl rsa -n smpd.local.encrypted.key -out smpd.local.key
(2)サーバ用の秘密鍵と識別情報からCSRを生成
openssl req -out smpd.local.csr -key smpd.local.key -new
識別情報はCA証明書と少し異なります(具体的にはCommon Name に ”smpd.local” が入る)。
Country Name: jp
State or Province Name: Tokyo
Locality Name:空欄でOK
Organization Name:Papalius
Organizational Unit Name:空欄でOK
Common Name: smpd.local
Email Address:Address:symphonic.mpd@gmail.com
A challenge password:空欄でOK
An optional company name:空欄でOK
(3)サーバ証明書作成のためのパラメータファイルを作成
以下の記述でsmpd.local.csxファイルを作成します。
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
subjectAltName = DNS:smpd.local, IP:192.168.11.162, DNS:app, DNS:app.local
extendedKeyUsage = serverAuth
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid, issuer
subjectAltName は俗にSANと言われるもので、サーバ証明書でDNSやIP指定した場合にどのURLで参照されたかを指定するものです。つまり、固定IP運用の場合はIP:以降に自分のsmpdのIPアドレスを入力する必要があります。
(4)CSR+SAN+CA秘密鍵+CA証明書でサーバ証明書を作成
openssl x509 -req -days 395 -CA localCA.crt -CAkey localCA.key -CAcreateserial -in smpd.local.csr -extfile smpd.local.csx -out smpd.local.crt
生成するのはCA証明書と同じくx509形式のため、内容確認コマンドも同一のため省略します。
ここでの注意は現在の最新環境だとサーバ証明書の有効期限が13ヶ月以内でないと正常に動かない環境があるということです(具体的にはipadがそうでした)。
(5)ympd 向けにサーバ秘密鍵とサーバ証明書を1ファイル化
cat smpd.local.key smpd.local.crt > smpd.local.pem
2つのファイルを標準出力に流し、それをファイルにリダイレクト化してテキスト保存するということです。
それでは最終章になりますが、実際に ympd での https 有効化方法などについて以下で説明します。
(1)必要なファイルを複写
ympdのルートディレクトリである /var/lib/mpd/music にCA証明書+「サーバ秘密鍵とサーバ証明書セット」を複写します。
cp localCA.crt /var/lib/mpd/music/
cp localCA.der.crt /var/lib/mpd/music/
cp smpd.local.pem /var/lib/mpd/music/ssl.pem
(2)先に各端末にてCA証明書をダウンロードしておく
http://smpd.local/localCA.crt などのURLでブラウザにアクセスし、CA証明書をダウンロードして保存しておきます。
もしこの方法がNGの場合は Filezilla などでFTP経由でダウンロードするか、USBメモリなどに転送したものを端末に複写して下さい。
Androidの端末の場合、ダウンロードするファイルはlocalCA.der.crtになります。
ipadなどのApple製品の場合、電子メールの添付ファイルかSafari経由でしか証明書のダウンロードは出来ません。
(Safariの場合、場所でCA証明書のリンクを指定するとプロファイルとしてインストール直前まで処理を進めることが出来ます)。
(3)各ブラウザの設定を見て、CA証明書をインストールする。
以下、ブラウザごとに解説をします。
a.Chrome系のブラウザ(PC上での)
場所でchrome://settings と入力して設定画面を表示し、その中の「プライバシーとセキュリティ」を選択します。
次に「セキュリテイ」項目から「証明書の管理」がありますのでこれを選択します。
Windowsの場合はOSの証明書管理が開きますので、認証局で「インポート」を選んでダウンロード済みのCA証明書をインポートします。
Linux版でも基本的には同じです。ただし、ブラウザ毎に実施する必要があります。
b.Firefox(PC上での)
基本的にChromeと同様ですが、Firefoxの場合Windows・Linux版問わず独自の証明書ストレージを持つためこれを有効にする必要があります。
c.Android端末上のChrome・Firefox
私の手元にあるAndroid v13のOnePlus8を基準に説明しますが、「設定」の「パスワードとセキュリティ」画面から「システムセキュリティ」を選択し、
「認証情報ストレージ」から「ストレージから証明書をインストール」を選択してストレージに保存したder形式の証明書をインストールします。
Chromeの場合はこれでインストール完了ですが、Firefoxの場合はOSのユーザが追加したCA証明書を認識するようもうひと手間必要になります。
Firefoxを起動し、「設定」から「Firefox」についてをクリックしてFirefox Browserのアイコンを5回タップすると「設定」内に「Secret Settings」の項目が追加されます。
「Secret Settings」の「Use third party CA certificates」をOnにするとこのCA証明書が有効になります。
e.ipadの場合(恐らくiPhoneも同じ)
「設定」→「一般」→「VPNとデバイス管理」を表示させます。
構成プロファイルにインストール済みのCA証明書が表示されますので、これをクリックして「インストール」を押します。
次に、「設定」→「一般」→「情報」→「証明書信頼設定」画面でインストールしたルート証明書をOnにして下さい。
(4)systemd の ympd 関連記述を修正する。
2箇所修正が必要です。
/lib/systemd/system/ympd.socket
ListenStream=80 の数値を443にしてください。
一応同じ行を複写しておいて 80の先頭に#を入れておくとコメント化出来て復活が楽になります。
/lib/systemd/system/ympd.service
ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport 80 -i 200 --documentroot /var/lib/mpd/music
を
ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport "ssl://443:/var/lib/mpd/music/ssl.pem" -i 200 --documentroot /var/lib
に変更してください。
これも ympd.socket と同じく元の80ポートの設定を複写してSSLに対応させ、元の行の先頭に#をつけてコメント化しておくことを推奨します。
両方のファイル修正後
systemctl daemon-reload
が必要です。
(5)念の為smpdを再起動してからブラウザでアクセス。
ブラウザの場所で「https://smpd.local」と入力し HTTPS でのアクセスを明示化しないと NG かもしれません。
・私の作ったCA証明書+サーバ証明書をそのまま使いたい場合
cert.zip
固定IPアドレスでの https で正常動作させるには、本ZIPファイルを解凍したsrcディレクトリ内部にサーバ証明書向けのファイル1式があるので、
前の投稿で記載の csx ファイルを各自編集してサーバ証明書を作り直してみてください。
・https 有効化による弊害対応
取り急ぎ 「add-stream プラグインによる radio-browser.org へのアクセスが出来ない」対策を実施したものを以下のファイルで配布します。
/opt/plugins/13-add_stream/form.html を書き換えしてください。
(具体的には https サポートを有効化した場合、webui からの全てのアクセスを https で行わないとエラーになってしまう。)
form.html.zip
前にここに書いた記述は不要になりましたので削除します。
なお、CA証明書・サーバ証明書と生成+インストール用のシェルスクリプトはセットにして提供し直ししたいと思います。
SSLサポートなのですが、自分で色々書いておいて各端末・ブラウザでの一通りの検証が足りないことに気づきました。
(具体的に言うと、Chromeは結構設定がザル・Firefoxなどそれ以外のブラウザはルート証明書が正しくないと接続させてくれない)
というわけで「手持ちの全デバイスでこれでイケる」という設定が確認できるまで少々時間をください。
(もし有識者で「openssl の使い方、誤っているよ」というアドバイスは大歓迎です。)
確認予定の環境は以下の通りとします。
Windows:Chrome・Firefox・Edge・ie11(ie11はそもそも動きませんでした...)
ちなみにWindows10・11の場合、https://smpd.localの動き(mDNSによる名前解決)がLinux/Macに比べて異常に重いため固定IP推奨ですね...
これはこれで、非常に問題あり。
Linux:Chrome・Firefox
Android:Chrome・Lightning・DuckDuckGo
(LightiningとDuckDuckGoは動作せず。代わりと言っては難ですが、Firefoxの動作を確認したので勘弁していただきたく)
ipad:Chrome・Safari
ちなみに参考情報ですが、PWAは手元では動きました。
さて、MacOS だけは手元になく動作確認出来ませんでしたが、それ以外の環境でほぼ https での動作確認が出来ましたので、
改めて本スレッドに纏めます。
1.CA証明書とサーバ証明書のympdルートディレクトリに複写
cert.zip にCA証明書、サーバ証明書の必要ファイルを全て纏めました。
当該ファイルを smpd のSDカードに解答し、そのまま同梱の証明書を使用する場合は以下の通りsshでコマンドを入力して下さい。
cp smpd.local.pem /var/lib/mpd/music/ssl.pem
cp localCA/localCA.crt /var/lib/mpd/music/
cp localCA/localCA.der.crt /var/lib/mpd/music
2.CA証明書・サーバ証明書を自分で作成したい場合
cert.zipの解凍先で、CA証明書の場合は localCA/genRootCA.sh を、サーバ証明書の場合は genSVcert.sh を実行して下さい。
(smpd を固定IPアドレス運用している場合、openssl の subjectAltName に当該アドレスを自動追加します)。
3.CA証明書をお使いの端末にインストール
httpsでのセキュアな通信を行うためには、
サーバ側にサーバ証明書と秘密鍵を、
端末側にサーバ証明書を署名するために使用したCA証明書をインストールする必要があります。
CA証明書のファイルをサーバから転送する方法は以下の3種類あります。
・http://smpd.local/localCA.crt へブラウザでアクセスし、ファイルダウンロード
(この方法はipad・iosではSafariで必ず行う必要あり。
またAndroidの場合はlocalCA.der.crtをダウンロードする必要あり)
・cert.zipを解凍しlocalCA.crt・localCA.der.crtを端末のストレージに複写(そのまま使用する場合)
・Filezilla経由でFTPによるダウンロード
以下、各OSとブラウザ毎にインストール方法を解説します
OS | ブラウザ | インストール方法 |
---|---|---|
Windows | Chrome | ブラウザの場所でchrome://settings と入力してブラウザの設定画面を表示し、「プライバシーとセキュリティ」を選択。 次に「セキュリテイ」項目内に「証明書の管理」がありますのでこれを選択。 OSの証明書管理が開きますので、認証局で「インポート」を選んでダウンロード済みのCA証明書をファイル選択してインポート。 |
Windows | Edge | 上に同じ |
Windows | Firefox | 設定画面の構成はChromeなどと同じですが、Firefoxの場合はCA証明書の格納場所が独立(OSとは別)のため、個別にインストール処理が必要 (操作方法はOSの証明書管理とほぼ同等)。 |
Linux | Chrome | Windows と画面構成はほぼ同じですが、Windows 版のFirefox と同様、CA証明書の格納場所は各ブラウザで独立しているため、 smpdでhttps接続したいブラウザ全てでインストールが必要。 |
Linux | Firefox | Chromeと同様 |
Android | Chrome | 以下、私の手元にあるAndroid v13のOnePlus8を例に説明。 「設定」の「パスワードとセキュリティ」画面から「システムセキュリティ」を選択し、「認証情報ストレージ」から「ストレージから証明書をインストール」を選択してストレージに保存したder形式の証明書をインストール。 |
Android | Firefox | CA証明書のインストールはChromeのやり方でOKですが、さらにOSのユーザ追加したCA証明書を認識するようもうひと手間必要。 Firefoxを起動し、「設定」から「Firefoxについて」を選択し「Firefox Browser」の画像を領域を5回タップすると「設定」内に「Secret Settings」の項目が追加される。「Secret Settings」の「Use third party CA certificates」をOnにするとこのCA証明書が有効になる。 |
ipad | Safari | まず、Safari で http://smpd.local/localCA.crt にアクセスし、証明書をプロファイルとしてダウンロード。 次に「設定」→「一般」→「VPNとデバイス管理」を表示させ、「構成プロファイル」に今回ダウンロードしたCA証明書が表示されるので、これをクリックして「インストール」を押す。 次に、「設定」→「一般」→「情報」→「証明書信頼設定」画面でインストールしたルート証明書をOnにする。 |
4.systemdのsocket・serviceでhttpsを有効化
/lib/systemd/system/ympd.socket
従来のhttpでの80番ポート待受を443番ポート待受に変更します
#ListenStream=80
ListenStream=443
/lib/systemd/system/ympd.service
#ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport 80 -i 200 --documentroot /var/lib/mpd/music
ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport "ssl://443:/var/lib/mpd/music/ssl.pem" -i 200 --documentroot /var/lib
どちらも従来の記述の先頭に”#"をつけてコメント化し、httpsを有効化しています。
ファイル修正後 systemctl daemon-reload
とコマンドを入れて、smpdを再起動して下さい。
5.各端末のブラウザでの初期動作について
既にhttpでアクセスしていた場合、"https://smpd.local" と場所に明示しないと正常動作しない場合があります。
また、ブラウザによってはキャッシュが残っていて接続に失敗する場合があります。
6.サーバ証明書の有効期限について
ipadOSの機能制限により、サーバ証明書の有効期限は「作成後13ヶ月以内」となっています(恐らくiphone・MacOSも同じ成約あり)。
このため、httpsを継続して使用する場合、1年後に再度サーバ証明書を作り直しをしてインストールし直す必要があります。
(CA証明書は2036年まで有効にしてありますので、本システムのライフスパン中は再作成は不要だと思います。)
7.CA証明書について
強制はしませんが、自宅以外にも様々な環境で複数のsmpdでhttpsを有効化する場合、
いちいち個別のCA証明書を各サーバで作るのではなく、単一の証明書で済ませたほうが便利です(基本、そのためのCA証明書ですから)。
というわけで、公式配布するCA証明書を使用することをおすすめします。
(今回はパッケージ作成が間に合いませんでしたが、今後パッケージ作成後はcert.zipの機能を同梱します。)
8.現時点で動作非サポート環境
AndroidでのLightningとDuckDuckGo
(恐らくAndroid OSのユーザCA証明書ストレージを使用していないため、
サーバ証明書の証明が出来ずに https でのセキュアな接続が不可)
新パッケージ提供の予告
久しぶりにパッケージ化を行うため、作業手順を思い出しながらになるので少々時間はかかりますが、
以下の更新を実装した新パッケージをリリースします。
1)httpsサポート関連ファイルの追加
2)Firefoxでのスタイルシートズレ対応
(PC版・Android版共に発生しているリスト表示領域の右側がはみ出ている件、
Android版でハンバーガーメニュー表示時にボリウム調整のスライダーが消える件に対応します)
あと、先日のhttpsサポート関連で Windows のブラウザを触っていて気づいたのですが、
ブラウザの場所で smpd.local を指定した場合、通常は mDNS (Bonjour・avahi)でIPアドレスに解決してアクセスするのですが、
Windows の場合は名前解決が遅い(もしくは失敗する)挙動が見られるため、
技術的に押さえておきたいと思っています。
(残念ながらAndroid は OS レベルで mDNS 未サポートのため、ブラウザでのIPアドレス解決は不可能です。
ただし後述しますが、Playストアで mDNS をサポートするアプリをインストールした場合、
ローカルネットワーク上でどのような端末がどのサービスを提供しているか確認可能です。)
現在の知見で言うと、以下の通り。
Apple系の(当方手元ではiPad):Bonjour の開発元なので当然のように名前解決可能
Linux :avahi が動作する環境ならば当然のように名前解決可能
Windows:Windows10/11 問わず、待たされることが大。場合によってはタイムアウトも発生。
参考:Android のmDNS情報閲覧用のアプリ(Service Browser・mDNS Discovery)で当方宅内の情報を確認したところ、
smpdは"_raop._tcp"のサービス名しか返していないことが判明しました。
(本当ならば"_http._tcp"も返してほしいところ)
smpdではShairport-Sync(AirPlay用のアプリケーション)がmDNSのサーバとしても動作し"_raop._tcp"のサービス名を返しているため、
これの改造もしくは_http._tcpを返す他のデーモンが必要かもしれません。
なお、Linux で mDNS のサービスとホスト名を確認する際は avahi-browse -alr
とコマンドを入れてみて下さい。
mDNS周りの規格について
もう少し補足を記載します。
1.mDNSの基本プロトコル
RFC 6762という規格で日本語訳参考資料はこちら、
従来のDNSを補完する目的で同一ネットワーク内にマルチキャストで問い合わせを送信することで、
ホスト名からIPアドレスを解決することが可能な仕組みになっています。
symphonic-mpd ではインストールイメージはsmpd.localという名前が最初から付けられていますので、
この機能が正常に動作すれば「例え DHCP により当該RaspberryPiに動的に IP アドレスが付与された場合でも」これを特定することが可能になるというわけです。
mDNS の実装はソフトウェア開発者により名称が異なり、Appleの場合はBonjour、Linux 等では Avahi というふうに名乗っています。
mDNSによるホスト名からIPアドレスを特定するだけの通信についてはワンショット(1回のみ)となっています。
この時、リクエストを送る側は 224.0.0.251:5353 (IPアドレス 224.0.0.251 ポート5353)に対して送信します。
mDNSサーバでこのリクエストが受信されそれが自分のホスト名と一致すると、自分のIPアドレスを返すので、IPアドレスの特定がされるという訳です。
2.サービス問い合わせ
RFC6762 に追加し、RFC6763 では5353ポートでのマルチキャストの継続的な通信を行った場合は実際に動作しているサービスの問い合わせが可能になります。
先の投稿で _raop._tcp と記載していたものは、Shairport-Sync が RFC6763 に基づきクライアントに返していた自分の動作サービス(AirPlay)についての情報になります。
本来ならばsmpd.localでは httpd のサービスも存在するため、_http._tcp も合わせて返してほしいところです。
3.他の同様パッケージでの対応方法
Volumio についてちょっとググってみました。
Linux 系の Avahi を内部でインストール済みであるため、これで mDNS は賄っているとのことです。
Avahi では設定ディレクトリ内に存在するサービスの設定ファイルを配置することにより、 RFC6763 で実現しているサービスを全部返すことができるようです。
4.Windows での mDNS サポート状況について
Window10以降でOS標準でサポートされたとのことですが、どうやらトラブル事例はそれなりにあるようです(うまく解決しないとのこと)。
解決方法としては3つほどありそうです。
(1)OS標準のmDNSを停止し、Apple の Bonjour をインストール
OSのmDNS停止にはレジストリ操作が必要。更に普通はインストール不要のBonjourインストールが必須
(2)mDNS以外の名前解決方法を使用する。
実はWindowsではLLMNRというIPv6対応の名前解決方法があり、smpdではsystemd-resolvedのデーモンでこれ用のポート(5355)が既に開いていました。
うまく使えれば、アドレスを返してくれるかもしれません。
(3)IPv6アドレスを付与しておく
こちらの情報によると、WindowsでのmDNS実装ではIPアドレスの問い合わせ時にIPv6パケットも要求しており、IPv6 アドレスがないと1秒待たさせるとのこと。←これが原因?!
※symphonic-mpdの v1 系では ipv6 サポートがカーネルレベルで無効化されているため、
(2)・(3)の方法ではどうしようもないことが明らかとなりました。
やはり Windows の場合は「(1)の通りOS標準のmDNSからBonjourに変更」もしくは「固定IP前提運用」しかないですね。
という訳で後ほど、「(1)の具体的なやり方」と
「LLMNRのポートを閉じる」設定方法を記載します。
今まで2回程度記述してきましたが、やっと現象が把握出来ましたので以下に纏めます。
本件は後程FAQにも纏めておきます。
(今まで記述してきた内容は課題解決のためのプロセスに関する「読み物」だと思って下さい。)
Windows10・11機にてブラウザの場所に http://smpd.local もしくは https://smpd.local でsmpd機に問い合わせした際、
名前解決に失敗して表示されない(もしくは成功しても正常に接続出来ない)。
Windowsのブラウザで場所を入力後、ホスト名→IPアドレス変換するために mDNS(UDPマルチキャストを用いたホスト名→IPアドレス変換)のパケットが端末から伝送されるが、
WiFi環境下では smpd サーバからの応答のUDPマルチキャストによるレスポンスが消えることがあるため。
以下のどれかを試してみて下さい。
1)Windows 機では有線接続とする (smpd.local継続使用時)
2)smpd.local での運用を止め、固定IPアドレス下で直接IPアドレスを入力する。
3)WiFiルータ・アクセスポイントの設定見直し・機種変更を検討する。
mDNSのsmpdサーバでの挙動を調査していたところ、現状使用できないLLMNRによる名前解決向けポートの5355がTCP・UDP共に開いた状態であることが判明しました。
当該ポートを閉じるためには /etc/systemd/resolvd.conf をエディタで開き、LLMNR=no
という記述を追加して下さい。
入力する場所としては MulticastDNS=no
の一つ前が分かりやすくて良いと思います。
(smpd v1ではipv6が無効化されているため仮に外部からパケットを受信しても無害ではあると思いますが、
不要ポートを閉じていたほうが良いと思われるので、設定を推奨します。)
設定変更後、再起動するか systemctl restart systemd-resolvd.service
でsystemd-resolvd を再立ち上げして下さい。
また、ss コマンドで以下の通り、開いているポートは53(DNS), 5353(mDNS), 22(SSH),80(HTTP)もしくは443(HTTPS), 5000(AirPlay)以外のポートが閉じられていることを確認して下さい。
(spotifydを使用している場合、ほかも開いているかも)
root [ ~ ]# ss -nltup
Netid State Recv-Q Send-Q Local Address:Port Peer Address:Port Process
udp UNCONN 0 0 127.0.0.53:53 0.0.0.0:* users:(("systemd-resolve",pid=164,fd=12))
udp UNCONN 0 0 0.0.0.0:5353 0.0.0.0:* users:(("shairport-sync",pid=689,fd=6))
tcp LISTEN 0 0 127.0.0.53:53 0.0.0.0:* users:(("systemd-resolve",pid=164,fd=13))
tcp LISTEN 0 0 0.0.0.0:22 0.0.0.0:* users:(("sshd",pid=170,fd=3))
tcp LISTEN 0 0 0.0.0.0:443 0.0.0.0:* users:(("ympd",pid=956,fd=3),("systemd",pid=1,fd=56))
tcp LISTEN 0 0 0.0.0.0:5000 0.0.0.0:* users:(("shairport-sync",pid=689,fd=3))
最後にWiresharkでパケットを取り直してみたところ、
LLMNR・DNS・mDNSによるブラウザからsmpd.localの名前解決請求は確認したが、そのレスポンスがないことに気づきました。
Shairport-Sync のログモードをデバッグにすると正常にmDNSの要求は受信されてそのレスポンスは返している模様でした。
ここで我が家のPCやAndroidスマホはWiFi経由であったことを思い出し、
PCをsmpdサーバと同じL2-SWに有線LANで接続してパケットキャプチャーを行ったところ、mDNSの応答がsmpdから返って正常にブラウザの表示がされたことから、
WiFiに環境下による応答パケットロスであると断定出来たという訳です。
しばらくご無沙汰していたら、閑古鳥が鳴いているようでなかなかレスが付きませんが、一つお聞きしたい事項があります。
実はインターネット経由でカバーアートを取得する際、「先方のサイトで想定しているアルバム名と実際にライブラリに収録されているライブラリ名が完全一致しないため」にカバーアートがヒットしない場合があります。
(例えば末尾に[Deluxe Edition]がついている場合など)
ヒット率を向上するため、以下のどちらかの機能を追加してみようと思いますがどちらがお望みですか?
辞書式で問い合わせ前にアルバム名末尾の余計な文字列を削除して問い合わせ
人間系で修正して再問い合わせ可能なダイアログを提供
@sunatomo さま
シマネコと申します。
投稿いただき有難うございます。
ずっとSMPDを使わせていただいております。
"smpd.local" に反応しないことが多く、ずっと前からなんでだろう?と思っておりました。
Windows-PCやAndoroid,i-OSで反応が違うのでいろいろ試して接続しておりました。
(Network Scanner等でipアドレスのあたりをつけて、http:// ipアドレスの入力でつないでいます。)
今回説明いただいたことは、能力不足で理解できていないのですが、さっそく試してみたいと思います。
技術知識がなくて、なかなか反応することができないのですが、ほとんど毎日 "Symphonic-mpd"の投稿は見ておりますので、これからもよろしくお願いいたします。
ありがとうございました。
@sunatomo
I think option "2 - Provides human-modifiable ..." would be best as it would provide flexibility.
1年ぶりになりますが、ある程度の成果が見込まれましたのでアップデートを提供します。
ログは以下の通り。
https のサポートについて
標準ではOFFにしておりますが、httpsを今回からサポートすることにしました。
有効化したい方は次の投稿で詳細を記載しますので、そちらの手順に基づき実行して下さい。
インターネット経由のカバーアート再取得サポートについて
Castle 様の提案通り、まずは手動でカバーアートに必要な文字列を変更可能なダイアログを提供します(試作段階のため、今後UIが変更の恐れあり)。
カバーモードのカバーアート表示域をクリックすると、上のダイアログが表示されます。各コンポーネントの説明は下記のとおりです。
名前 | 詳細 |
---|---|
Current URL | 当該カバーアート領域で現在先頭に指定されているURLを表示(編集不可) |
Album Name | 楽曲から取得したアルバム名を表示 |
Album Artist | 楽曲から取得したアルバムアーティスト名を表示 |
Song Name | 楽曲から取得した楽曲名を表示 |
Song Artist | 楽曲から取得したアーティスト名を表示 |
Spin ボタン | カバーアート表示領域で指定されたカバーアートのURL候補の順番を変更 (これにより、希望のカバーアートを優先表示可) |
recover ボタン | Album Name 〜 Song Artist の文字列を楽曲から取得したものに復元 |
ReGet ボタン | Album Name 〜 Song Artist に記載の文字列で再度インターネットからのカバーアート再検索を実施 |
各サービスにより必要なパラメータが異なるのですが、最小公倍数で以上4つの項目が必要になります。
Album Name, Album Artist は同一アルバム再生中は変更しないように実装しましたが、もしかしたら想定外の動作がある可能性があること、
現状の仕様では Current URL が見えにくい、
また、スマホ向けには本機能はOFFになっていることから
もう少しブラッシュアップが必要と考えています。
a) 動作させる端末にルート証明書を予めインストールしておく
http://smpd.local/ 直下においたルート証明書をダウンロードして各ブラウザの証明書保管場所に保存して下さい。
OS | ブラウザ | ファイル名 | 備考 |
---|---|---|---|
Windows | edge chrome |
localCA.crt | OSの証明書ストレージ |
WIndows | FireFox | localCA.crt | FireFox独自の証明書ストレージ |
Linux FreeBSD等 |
chrome FireFox |
localCA.crt | 各ブラウザの証明書ストレージ |
Android | chrome FireFox |
localCA.der.crt | OSの証明書ストレージ内※1 |
iphone ipad |
chrome safari |
localCA.crt | OSの証明書ストレージ※2 |
※1 Android の場合、「設定 > パスワードとセキュリティ > システムセキュリティ > 認証情報ストレージ > ストレージから証明書をインストール」(手元のOneplus8 Android V13の場合)、
「設定 > セキュリティ > 暗号化と認証情報 > SDカードからインストール」(手元のXperia XZ2 Android V11の場合)
等の操作でサーバ証明書をインストールできます。
※2 Apple 社製品の場合、ルート証明書は 「Safari からのダウンロード」か「メールでの添付ファイルによる送付」以外はインストールできません。
また、ダウンロード後 「設定 > 一般 > VPNとデバイス管理 >ダウンロード済みプロファイルのインストール作業」と「設定 > 情報 > 証明書信頼設定」の2つの設定が必要になります。
ちなみにChrome・FireFoxともに証明書の設定画面は「設定>プライバシーとセキュリティ」からアクセス可能です。
b) /opt/cert ディレクトリの systemd 関連ファイルを複写
remakeCert.service, remakeCert.timer を /etc/systemd/system に複写します。
最近のセキュリティ強化により smpd サーバで使用するサーバ証明書は有効期限が13ヶ月以下にしないとブラウザ側で弾かれる現象が発生しています。
このため、smpd で使用するサーバ証明書も有効期限が13ヶ月以内となっていますが、証明書の再発行+ympdの再起動をsystemdのタイマーで処理させるための設定ファイルを複写するという訳です。
ちなみにremakeCert.timerのタイマー設定は毎年1月1日の4:00となっているため、変更したい方は当該ファイルを編集して下さい。
c) systemd のタイマー設定を有効化
まず systemctl daemon-reload
で設定ファイルをsystemdに反映させます。
次に systemctl enable remakeCert.timer
で remakeCert.timer を有効化します。
さらに systemctl start remakeCert.timer
で remakeCert.timer を開始させればOKです。
一応動作を確認する際は systemctl list-timers
と入力し、以下の状況であることを確認して下さい。
NEXT LEFT LAST PASSED UNIT ACTIVATES
Mon 2023-01-02 10:23:30 JST 14min left Sun 2023-01-01 10:23:30 JST 23h ago systemd-tmpfiles-clean.timer systemd-tmpfiles-clean.service
Mon 2024-01-01 04:00:00 JST 11 months 28 days left Sun 2023-01-01 04:00:04 JST 1 day 6h ago remakeCert.timer remakeCert.service
2 timers listed.
Pass --all to see loaded but inactive timers, too.
d) ympdのhttps 関連設定を有効化
まず、ympd.socketを書き換えます。
[Socket]
#ListenStream=80
ListenStream=443
KeepAlive=true
PassCredentials=true
[Install]
WantedBy=sockets.target
もともとは ListenStream=443 の行は記載なしだったと思いますが、本行を ListenStream=80 の真下に追加し、ListenStream=80 の先頭に#を付けてコメントアウト化して下さい。
次に今回添付のympd.serviceを書き換えします。
[Unit]
Description=ympd server daemon
Requires=network.target local-fs.target
After=mpd.service
[Service]
EnvironmentFile=/etc/environment
Type=simple
ExecStartPre=/usr/bin/ympd-plus.sh
ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport 80 -i 200 --documentroot /var/lib/mpd/music
#ExecStart=/usr/bin/ympd -h /run/mpd/socket --webport "ssl://443:/var/lib/mpd/music/ssl.pem" -i 200 --documentroot /var/lib/mpd/music
User=root
CPUSchedulingPolicy=other
CPUAffinity=3
[Install]
WantedBy=multi-user.target
ExecStart の --webport 80 と書かれている行をコメントアウトし、その下の行を有効化して下さい。
両方のファイル編集後、以下のコマンドでympdをhttpsで起動させます。
systemctl daemon-reload
systemctl stop ympd.service
systemctl stop ympd.socket
systemctl start ympd.socket
systemctl start ympd.service
cp /opt/cert/smpd.loca.pem /var/lib/mpd/music/ssl.pem
ルート証明書も/var/lib/mpd/musicに複写し直し、前項の通り使用する端末に配布して下さい。
昨日アップしたばかりですが、カバーアート再取得関係での課題を解決した目処が付きましたので、今週末に再リリースします。
・携帯電話向けの設定画面
レイアウトを調整の上、対応できましたのでデスクトップ版と同じく機能を提供します。
・埋め込みカバーアートの対応改善
従来は埋め込みカバーアートの取得設定が有効な場合はその有無を確認せずにURLを生成していたのですが、
埋め込みカバーアートの抽出に失敗した場合はURL生成しないように設定を変更しました。
・インターネットからのカバーアートの取得方法改善
従来はインターネットへのカバーアート取得がOnの場合は、楽曲変更時に毎回問い合わせを行っていましたが、
今回から「同一アルバムでの再生が継続していた場合」は最初の1回だけ取得しその後は取得しない処理に変更しました。
↑
これについてはアルバム名を修正後にインターネットへ問い合わせた場合も適用させます。
特に3番目の拡張に関する動作の検証のため、少し時間を頂きたくよろしくおねがいします。