- 2010-05-05 (水) 15:58
- Ruby
NHKのラジオ講座は安価に語学を学ぶことができる。ラジオを持っていない人でもストリーミングで聴くことができる。ただしロシア語などいくつかの講座は提供されていない。
ストリーミングは電車の中でiPodに入れて聴きたいと思ったときには不便である。ここではストリーミングファイルを自動的にダウンロードしてmp3に変換する。
ツールを手に入れる
ストリーミングファイルをダウンロードするにはRTMPDumpを使う。ビルド版もあるし、portやyumなどでインストールしてもいい。
flvをmp3に変換するにはFFmpegを使う。これは多種のコーデックをサポートするツールだが、そのぶんビルドが面倒臭い。既にビルドされているものを使うか、やはりportやyumを使って入手するとよい。
準備
まず語学講座のURLを連想配列に入れる。また、flvの情報が記録されているXMLファイルlistdataflv.xmlやストリーミングファイル置き場のURLも定数に入れておく。
#!/usr/local/bin/ruby -Ku
require 'rubygems'
require 'mechanize'
require 'nokogiri'
require 'kconv'
require 'logger'
require "fileutils"
RTMPDUMP = "rtmpdump "
FFMPEG = "ffmpeg "
STREAMING_BASE = "rtmp://flv9.nhk.or.jp/flv9/_definst_/gogaku/streaming/flv/"
COURSE_XML = "listdataflv.xml"
COURSE = {
"基礎英語1" => "http://www.nhk.or.jp/gogaku/english/basic1/",
"基礎英語2" => "http://www.nhk.or.jp/gogaku/english/basic2/",
"基礎英語3" => "http://www.nhk.or.jp/gogaku/english/basic3/",
"英語5分間トレーニング" => "http://www.nhk.or.jp/gogaku/english/training/",
"ラジオ英会話" => "http://www.nhk.or.jp/gogaku/english/kaiwa/",
"入門ビジネス英語" => "http://www.nhk.or.jp/gogaku/english/business1/",
"実践ビジネス英語" => "http://www.nhk.or.jp/gogaku/english/business2/",
"まいにち中国語" => "http://www.nhk.or.jp/gogaku/chinese/kouza/",
"まいにちフランス語" => "http://www.nhk.or.jp/gogaku/french/kouza/",
"まいにちイタリア語" => "http://www.nhk.or.jp/gogaku/italian/kouza/",
"まいにちハングル講座" => "http://www.nhk.or.jp/gogaku/hangeul/kouza/",
"まいにちドイツ語" => "http://www.nhk.or.jp/gogaku/german/kouza/",
"まいにちスペイン語" => "http://www.nhk.or.jp/gogaku/spanish/kouza/"
}
ダウンロードメソッドを作る
まず連想配列の名前を与えてdownloadメソッドを呼ぶ。存在しない講座ならreturnしておく。
ファイルが乱雑に置かれると面倒なので講座ごとにフォルダを作る。まだフォルダがなければ作成しておく。
MechanizeでXMLファイルをgetして、NokogiriのXMLパーサで解析する。解析にはxpathを使う。ファイル名はfile属性にある。講座名や日付もあるので利用する。
まだファイルがないときには、RTMPDumpを用いてflvファイルをダウンロードする。mp3ファイルがまだないときは続けてFFmpegを使って変換する。
最後に連続してアクセスしないように待ちを入れる。
#---------------------------------------------------------------------------
# ラジオ講座のダウンロード
#---------------------------------------------------------------------------
def download(course)
if COURSE[course] == nil then
return
end
unless( FileTest.exist?(course) ) then
FileUtils.mkdir_p course
end
agent = Mechanize.new
url = COURSE[course] + COURSE_XML
agent.get(url)
parser = Nokogiri::XML.parse(agent.page.body, nil)
parser.xpath("musicdata/music").each do |element|
flvname = element.attr("file")
filename = course + "/" + element.attr("kouza") + "_" + element.attr("hdate")
unless( FileTest.exist?("#{filename}.flv") ) then
command = RTMPDUMP + "-o #{filename}.flv -r #{STREAMING_BASE+flvname}"
system(command)
end
unless( FileTest.exist?("#{filename}.mp3") ) then
command = FFMPEG + "-i #{filename}.flv #{filename}.mp3"
system(command)
end
end
sleep(1)
end
聴きたい講座をダウンロードする
#---------------------------------------------------------------------------
# エントリポイント
#---------------------------------------------------------------------------
download("基礎英語1")
聴きたい講座を指定してdownloadメソッドを呼ぶ。
実行結果
RTMPDump v2.2 (c) 2010 Andrej Stepanchuk, Howard Chu, The Flvstreamer Team; license: GPL Connecting ... Starting download at: 0.000 kB Metadata: duration 900.76 audiodatarate 64.00 audiodelay 0.04 audiocodecid 2.00 canSeekToEnd TRUE 7577.419 kB / 900.81 sec (100.0%) Download complete FFmpeg version 0.5.1, Copyright (c) 2000-2009 Fabrice Bellard, et al. configuration: --prefix=/opt/local --disable-vhook --enable-gpl --enable-postproc --enable-swscale --enable-avfilter --enable-avfilter-lavf --enable-libmp3lame --enable-libvorbis --enable-libtheora --enable-libdirac --enable-libschroedinger --enable-libfaac --enable-libfaad --enable-libxvid --enable-libx264 --enable-nonfree --mandir=/opt/local/share/man --enable-shared --enable-pthreads --cc=/usr/bin/gcc-4.2 --arch=x86_64 libavutil 49.15. 0 / 49.15. 0 libavcodec 52.20. 1 / 52.20. 1 libavformat 52.31. 0 / 52.31. 0 libavdevice 52. 1. 0 / 52. 1. 0 libavfilter 1. 4. 0 / 1. 4. 0 libswscale 1. 7. 1 / 1. 7. 1 libpostproc 51. 2. 0 / 51. 2. 0 built on Apr 11 2010 12:49:33, gcc: 4.2.1 (Apple Inc. build 5646) (dot 1) Input #0, flv, from '基礎英語1/基礎英語14月30日放送分.flv': Duration: 00:15:00.75, start: 0.000000, bitrate: 64 kb/s Stream #0.0: Audio: mp3, 44100 Hz, mono, s16, 64 kb/s Output #0, mp3, to '基礎英語1/基礎英語14月30日放送分.mp3': Stream #0.0: Audio: libmp3lame, 44100 Hz, mono, s16, 64 kb/s Stream mapping: Stream #0.0 -> #0.0 Press [q] to stop encoding [libmp3lame @ 0x101812800]lame: output buffer too small (buffer index: 9404, free bytes: 388) Audio encoding failed
FFmpegのバージョンによってはAudio encoding failedになる。解決策がここにある。
[libmp3lame @ 0x101812800]lame: output buffer too small (buffer index: 9404, free bytes: 388) Audio encoding failed
- Newer: RubyでSBIランキングの売り越し額を調べる
- Older: Rubyで2chの市況1板のニュースを集めTweetする
Comments:0
Trackback+Pingback:0
- TrackBack URL for this entry
- http://blog.neoneet.jp/2010/05/05/ruby%e3%81%a7nhk%e3%83%a9%e3%82%b8%e3%82%aa%e8%ac%9b%e5%ba%a7%e3%81%ae%e3%82%b9%e3%83%88%e3%83%aa%e3%83%bc%e3%83%9f%e3%83%b3%e3%82%b0%e3%82%92%e4%bf%9d%e5%ad%98%e3%81%99%e3%82%8b/trackback/
- Listed below are links to weblogs that reference
- RubyでNHKラジオ講座のストリーミングを保存する from 週刊(月刊?)プレカリアート














