[Kinesis Video Streams] DockerイメージのプロデューサーライブラリでMacのカメラを使用してみました

2020.03.02

1 はじめに

CX事業本部の平内(SIN)です。

Amazon Kinesis Video Streamsへ映像を配信するためのプロデューサーライブラリは、JavaとC++のコードがAWSより提供されています。

これを使用して、各種の環境で、GStreamerのシンクとなるkvssinkを作成する手順は、ここDevelopers.IOでも紹介されていますが、この作業は、基本的にコンパイルを伴う為、少し手間取ってしまうこともあります。
Amazon Kinesis Video Streamsを使ってストリーム映像をAWS上に流してみる【MacBook Pro】– ClassmethodサーバーレスAdvent Calendar 2017 #serverless #adventcalendar #reinvent
Amazon Kinesis Video Streamsを使ってストリーム映像をAWS上に流してみる【Raspberry Pi】– ClassmethodサーバーレスAdvent Calendar 2017 #serverless #adventcalendar #reinvent
Amazon Kinesis Video Streamsを使ってストリーム映像をAWS上に流してみる【Windows(MSVC)】

そんな中、Dockerイメージで提供されているものを使用すると、トラブルは、まず起こらないため、要件が許せば、超お勧めです。
[Amazon Kinesis Video Streams] Dockerイメージのプロデューサーライブラリで動画配信(Raspberry Pi編)
[Amazon Kinesis Video Streams] DockerイメージのプロデューサーライブラリでRTSPサーバの動画を配信してみました。

しかし、MacでこのDockerを使用する場合、GStreamerがOSに接続されているビデオデバイスにアクセスできないため、Macに着いているカメラなどが、基本的に利用できません。


例: Kinesis ビデオストリーム プロデューサー SDK GStreamer プラグインより

今回は、上記の制約を回避し、Docker版で、Macのカメラを使用する方法を試してみました。

2 構成

カメラの映像は、ホスト側のMacで動作するGStreamerからローカルのTCPストリーム経由で、Docker内のGStreamerへ送ります。プロデューサーを使用してKinesis Video Streamsへの送信を行うのは、Docker内で動作しているGStreamerです。

3 Dockerによる環境構築

DockerでのKinesis Video Streams への送信の手順は、以下のドキュメントのmacOSの所をそのまま実行しています。
Docker コンテナで GStreamer エレメントを実行します。

(1) Amazon ECR で認証

下記の出力を、そのまま実行してログインする

$ aws ecr get-login --no-include-email --region us-west-2 --registry-ids 546150905175

(2) macOSのDockerイメージのダウンロード

$ sudo docker pull 546150905175.dkr.ecr.us-west-2.amazonaws.com/kinesis-video-producer-sdk-cpp-amazon-linux:latest
$ docker images
REPOSITORY                                                                                 TAG                 IMAGE ID            CREATED             SIZE
546150905175.dkr.ecr.us-west-2.amazonaws.com/kinesis-video-producer-sdk-cpp-amazon-linux   latest              20b83f570e01        7 months ago        2.73GB

(3) macOSでのDockerイメージの実行

実行すると、kinesis-video-native-buildをカレントディレクトリとして起動します。

$ sudo docker run -it --network="host" 546150905175.dkr.ecr.us-west-2.amazonaws.com/kinesis-video-producer-sdk-cpp-amazon-linux /bin/bash
Password:
bash-4.2# pwd
/opt/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-native-build

(4) 環境変数の設定

ライブラリ等へのパスを設定します。

bash-4.2# export LD_LIBRARY_PATH=/opt/awssdk/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-native-build/downloads/local/lib:$LD_LIBRARY_PATH
bash-4.2# export PATH=/opt/awssdk/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-native-build/downloads/local/bin:$PATH
bash-4.2# export GST_PLUGIN_PATH=/opt/awssdk/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-native-build/downloads/local/lib:$GST_PLUGIN_PATH

認証情報も、環境変数で設定します。

bash-4.2# export AWS_DEFAULT_REGION=ap-northeast-1
bash-4.2# export AWS_ACCESS_KEY_ID=xxxxxxxxxxxxx
bash-4.2# export AWS_SECRET_ACCESS_KEY=xxxxxxxxxxxxxxxxxxxxxxxxxx

(5) 動作確認

ドキュメント記載されている使用例(RSTPサーバを入力とする例)で動作を確認しておきます。

bash-4.2# ./kinesis_video_gstreamer_sample_app dockerStream rtsp://192.168.0.110/ 

こちら、gst-launch-1.0を直接使う場合は、以下のようになります。(rtspからの入力が追いつかなくてエラーとなるので、sync=falseを追加しました)

bash-4.2# gst-launch-1.0 rtspsrc location=rtsp://192.168.0.110 short-header=TRUE sync=false ! rtph264depay ! video/x-h264, format=avc,alignment=au ! h264parse ! kvssink stream-name=dockerStream

4 Kinesis Video Streamsへの送信

(1) Mac側

Macのカメラを使用するために、まずは、DockerのホストとなっているMac側で、GStreamerによる送信を行います。

autovideosrcでカメラの入力を取得し、vtenc_h264_hwでh.264にエンコードした後、tcpserversinkでlocalhostに送っています。(ポートは、指定していないので、デフォルトの4953になっています。)

Mac側

$ gst-launch-1.0 autovideosrc ! videoconvert ! video/x-raw,width=1280,height=720 ! vtenc_h264_hw allow-frame-reordering=FALSE realtime=TRUE max-keyframe-interval=45 bitrate=512 ! gdppay ! tcpserversink host=127.0.0.1

(2) Docker側

一方、Docker側では、localhostからのTCPストリームを入力とし、 kvssinkで、Kinesis Video Streamsに送信しています。

Docker側

gst-launch-1.0 -v tcpclientsrc host=host.docker.internal ! gdpdepay ! video/x-h264, format=avc,alignment=au ! h264parse ! kvssink stream-name=dockerStream

(3) host.docker.internal

少し注意が必要なのは、MacのDockerでは、ホストマシンにアクセスする場合、localhostではなく、host.docker.internalを使用することです。

tcpclientsrc host=host.docker.internal

インターネット上では、docker.for.mac.localhostとか、docker.for.mac.host.internalを使用した例が見つかりましが、localhostのサブドメインが禁止されてから、host.docker.internalを利用するようにとのことです。

利用中のバージョン

$ docker --version
Docker version 19.03.2, build 6a30dfc


参考:Docker Community Edition 18.03.0-ce-mac59 2018-03-26

5 最後に

今回は、Macに搭載されたカメラで試しましたが、ソースは、autovideosrcですので、MacにUSB接続されたWebカメラも利用できます。

Macの利用者で、手軽にKinesis Video Streamsへの送信を試したい場合は、もしかすると、今回の要領が、最も嵌りが少ないかも知れません。