暗号化してセキュアに画面共有する - エンドーツーエンド暗号化/Piping Server経由
#Piping_Screen_Share #画面共有 #screen_sharing #Piping_Server #セキュリティ #エンドツーエンド暗号化 #Vue #TypeScript #制作物
デモ動画
https://youtu.be/BPjEtkVSa0E
アプリケーション
Piping Screen Share:
GitHubリポジトリ
https://gh-card.dev/repos/nwtgck/piping-screen-share-web.svg https://github.com/nwtgck/piping-screen-share-web
なんのために作ったか
セキュアに手軽に画面共有をしたいから。
(+ Piping Serverを使った実用例の提示の一環)
目指したことの詳細
以下のようなこと目指して開発した。
エンドツーエンドで暗号化され、サーバーも画面を知ることはできないにする
アカウントレスですぐ共有できる
Webブラウザで動き、多くのデバイスで利用できる
実装が公開され、利用者が安心できる状況
経由するPiping Serverを手軽に変更できる
経由するサーバーが変更できるメリットは、
自分が立てているPiping Serverを使ったり
プライベートネットワークにデプロイされたPiping Serverを使ってよりセキュアにする
(エンドツーエンド暗号化していても、強力はマシンで解読されたり、暗号化アルゴリズムの危殆化、IPアドレスなどの必然的に渡る情報を避けたり、色々よりセキュアにする保険になると思う。)
技術的なこと
Vue + TypeScript
Progressive Web App (PWA)
Web CryptoのAES GCMによるエンドツーエンド暗号化
パスフレーズをSHA256したものから鍵を作り暗号化する
サーバーは鍵がわからないため、サーバーもどんなデータが転送されているは知れない
MediaStreamRecorderを使って画面キャプチャをストリームさせている
500msごとので動画blobが得られる
コードを少し変更すれば任意のMediaStreamをストリームできるため、インカメラなど使ってテレビ電話・テレビ会議的なことにもできるはず
そのときは、音は別で送ることになりそう。<video muted>しないとJS側でplay()できないと思う
動画再生はダブルバッファのようなことを行なっている
常に2つのBlob URLが<video src="...">にロードされていて、切り替えている
ちらつきを起こさないようにするため
Piping Serverを経由
WebRTCなどは使っていない
HTTPのリクエストだけで通信される。(fetch()で通信される)
上記の動画blobを暗号化後チャンクのようにして転送している
静的ホストできる(Amanzon S3、GitHub Pages、Netlifyとかにホストできる)
誕生経緯
Piping Screen Share誕生経緯
Piping Chunkの転送手法をベースにしない理由
Piping Screen ShareをPiping Chunkの転送手法の上に構築しなかった理由
1台のPCで画面共有の動作確認したい人向けの注意点
ブラウザの一つを普通に開いて、もうひとつはシークレットブラウズなどにすると良い。
Piping ServerがHTTP/1を使っている場合、ブラウザのリクエスト上限の6つに引っかかる。
エラーするわけではなく、後発のHTTPリクエストが先発のリクエストの終了を待ちます。
違うタブでのリクエストも待つ対象になってしまうので、シークレットブラウズなどを使うのが良い。
Piping ServerがHTTP/2を話すときは、こういうことは考えなくてOK。
ブラウザの対応状況
Chrome推奨。新しいEdgeもいけるかも。
ブラウザでの画面共有はたぶん新しめのWebの技術。
Google Chromeで動作確認している。
現在のSafariはnavigator.mediaDevices.getDisplayMedia()に対応していないため、画面共有はできない。