AirPlayでUbuntuから音声・動画を転送してAppleTVで再生するために使えるRubyGemsに関する考察

考察の背景

iPhoneMacなどからAppleTVに対してAirPlayと呼ばれる機能を用いてストリーミング再生することが可能である。AppleTVをテレビやアンプと接続しておくことで、動画コンテンツを大画面テレビで音声コンテンツを音楽アンプで容易に転送できるため、コンテンツに適した形態で消費することができる。また、iPhoneMacなど転送元から一時停止やシーク・音量などの操作が行えるため、それぞれのリモコンで操作する手間がなく良い。

しかしながら、iOSMacWindows上のiTunes以外では、AirPlayを利用することが容易ではない。サードパーティがAirPlayによる転送のためのアプリを販売している様子が見受けられる。その転送は画面転送であり動画・音声転送ではない(これについて調べたのは過去なので今は様子が変わっているかもし知れない)。

画面転送では問題が出る場合がある。

AirPlayではリソースのURL、例えばYoutubeの動画URLをAppleTVに渡し、AppleTVは直接Youtubeの動画URLを叩くことでダウンロードを行いながら再生する。この場合は、AppleTVがYoutubeの動画をダウンロードするだけの回線帯域の消費である。

それに対して画面転送では、例えばWindows PCにYoutubeから一旦ダウンロードを行い、再度AppleTVに転送するという経路を通るため、前述の手法の2倍の帯域が必要であり、かつオリジナルの動画ファイルではなく転送用に再エンコードし直したものを送ることになる。2倍の帯域が必要という点で手元のPCが、無線LAN、特に802.11gなどを使っている場合は状況によって足りなくなるときがある。そのようなときに、コンテンツを格納するサーバとAppleTVが有線経路によって直で通信してくれると助かる。

この理由から、Windows上のサードパーティのAirPlay転送では不満足であり、AirPlayのURLによる再生を行う方法がコンテンツ消費としては望ましい。特にUbuntuの入ったサーバ上で実行して転送できると、なお良い。

airplayとそれを使ったCUIアプリ

AirPlayによるURLの再生を行う方法は、RubyGemsの中の1つairplayによって開拓され、airplayを用いたアプリケーションがいくつか登場している。これらのアプリはGoogle検索ではランクが高くなく、見つかりにくいので、ここに記しておく。アプリはUbuntu上でのみ検証し、全て動作を確認した。

AirPlayを活用するgemアプリケーションが用いる基本ライブラリはairplayである。

airplayライブラリを使った再生支援のgemは今のところ3つ知っている。

gem installしたりapt-get installしたりする必要がある。詳しい方法については、githubの各レポジトリを参照されたし。

airplayアプリの注意すべき点

これらの3つのアプリを使う上でいくつか注意点があるので書いておく。

  • airplay-cliおよびairplayerはavahiがちゃんと動いていないと動作しない
    • エラーは下の通り

DNSSD operation failed with unrecognized error code: -65537 (DNSSD::UnknownError)

      • このエラーが出た場合、avahiが起動しているか確認する
      • Ubuntuの場合、起動していないときがある。/etc/default/avahi-daemon ファイル内の AVAHI_DAEMON_DETECT_LOCAL=1 を AVAHI_DAEMON_DETECT_LOCAL=0 にして sudo start avahi-daemon すると起動する。この問題、すげー悩んだ。
    • airplay-cliを試してみて駄目だったらairplayerのREADME参考にapt-getした方が良い(と思う、多分、これについて確認していない)
  • airplay-cliやairplayerではローカルの動画ファイルを再生できない
    • airplayではローカルに存在する動画の転送は、ローカルにHTTPサーバを立ててAppleTVにそこにアクセスさせてダウンロードさせる方法を採用している
    • airplay-cliやairplayerでは、ローカルのサーバはairplayライブラリ経由でreel https://github.com/celluloid/reelを使う
    • なぜかRackサーバがreelだと起動しないのでwebrickに変更すると起動する

airplay-1.0.3/lib/airplay/server.rb:

module Airplay
  class Server
    include Celluloid

    attr_reader :port

    def initialize
      @port = Airplay.configuration.port || find_free_port
      @logger = Airplay::Logger.new("airplay::server")
      @server = Rack::Server.new(
        server: :reel,
        Host: private_ip,

module Airplay
  class Server
    include Celluloid

    attr_reader :port

    def initialize
      @port = Airplay.configuration.port || find_free_port
      @logger = Airplay::Logger.new("airplay::server")
      @server = Rack::Server.new(
        server: :webrick,
        Host: private_ip,

にする。何故、reelだと動かないのかについては調べていない。バージョン依存の問題かもしれない。
reel (0.5.0), ruby (1.9.3-p194), airplay (1.0.3)だが。

airplayアプリを改造する

機能的にはairstreamのシークとairplayerのyoutube直再生がいい感じなので、どちらか好きな方を改造して使うと消費が捗る。

自分でairplayアプリを書く

airplayライブラリを使ったCUIを自分で書く場合も簡単で、

#!/usr/bin/env ruby
require 'airplay'
player = Airplay.devices.first.play "./video.mp4"
sleep 120

とかやれば、動く。

さいごに

airplayライブラリ書いた人の苦労、凄いと思うのでHUGしてあげて欲しい。

こちらからは以上です。