dropcaster 0.0.4 → 0.0.5.rc1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,47 +1,28 @@
1
- require 'mp3info'
2
- require 'digest/sha1'
3
-
4
- module Dropcaster
5
- class Item < DelegateClass(Hash)
6
- include HashKeys
7
-
8
- def initialize(file_path, options = nil)
9
- super(Hash.new)
10
-
11
- Mp3Info.open(file_path){|mp3info|
12
- self[:file_name] = Pathname.new(File.expand_path(file_path)).relative_path_from(Pathname.new(Dir.pwd)).cleanpath.to_s
13
- self[:tag] = mp3info.tag
14
- self[:tag2] = mp3info.tag2
15
- self[:duration] = mp3info.length
16
- }
17
-
18
- self[:file_size] = File.new(self.file_name).stat.size
19
- self[:uuid] = Digest::SHA1.hexdigest(File.read(self.file_name))
20
-
21
- unless self.tag2.TDR.blank?
22
- self[:pub_date] = DateTime.parse(self.tag2.TDR)
23
- else
24
- Dropcaster.logger.info("#{file_path} has no pub date set, using the file's modification time")
25
- self[:pub_date] = DateTime.parse(File.new(self.file_name).mtime.to_s)
26
- end
27
-
28
- # Remove iTunes normalization crap (if configured)
29
- if options && options[:strip_itunes_private]
30
- Dropcaster.logger.info("Removing iTunes' private normalization information from comments")
31
- self.tag2.COM.delete_if{|comment|
32
- comment =~ /^( [0-9A-F]{8}){10}$/
33
- }
34
- end
35
-
36
- # Convert lyrics frame into a hash, keyed by the three-letter language code
37
- if tag2.ULT
38
- lyrics_parts = tag2.ULT.split(0.chr)
39
-
40
- if lyrics_parts && 3 == lyrics_parts.size
41
- self.lyrics = Hash.new
42
- self.lyrics[lyrics_parts[1]] = lyrics_parts[2]
43
- end
44
- end
45
- end
46
- end
47
- end
1
+ require 'mp3info'
2
+ require 'digest/sha1'
3
+
4
+ module Dropcaster
5
+ class Item
6
+ attr_reader :file_name, :tag, :tag2, :duration, :file_size, :uuid, :pub_date, :pub_date, :lyrics
7
+ attr_accessor :artist, :image_url, :url, :keywords
8
+
9
+ def initialize(file_path, options = nil)
10
+ Mp3Info.open(file_path){|mp3info|
11
+ @file_name = Pathname.new(File.expand_path(file_path)).relative_path_from(Pathname.new(Dir.pwd)).cleanpath.to_s
12
+ @tag = mp3info.tag
13
+ @tag2 = mp3info.tag2
14
+ @duration = mp3info.length
15
+ }
16
+
17
+ @file_size = File.new(@file_name).stat.size
18
+ @uuid = Digest::SHA1.hexdigest(File.read(file_name))
19
+
20
+ unless tag2.TDR.blank?
21
+ @pub_date = DateTime.parse(tag2.TDR)
22
+ else
23
+ Dropcaster.logger.info("#{file_path} has no pub date set, using the file's modification time")
24
+ @pub_date = DateTime.parse(File.new(file_name).mtime.to_s)
25
+ end
26
+ end
27
+ end
28
+ end
@@ -1,9 +1,9 @@
1
- require 'logger'
2
-
3
- module Dropcaster
4
- class LogFormatter < Logger::Formatter
5
- def call(severity, time, program_name, message)
6
- "#{severity}: #{message}\n"
7
- end
8
- end
9
- end
1
+ require 'logger'
2
+
3
+ module Dropcaster
4
+ class LogFormatter < Logger::Formatter
5
+ def call(severity, time, program_name, message)
6
+ "#{severity}: #{message}\n"
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,3 @@
1
+ module Dropcaster
2
+ VERSION = '0.0.5.rc1'
3
+ end
data/lib/dropcaster.rb CHANGED
@@ -1,30 +1,28 @@
1
- $:.unshift File.dirname(__FILE__)
2
-
3
- require 'bundler/setup'
4
- require 'delegate'
5
- require 'yaml'
6
- require 'active_support/core_ext/date_time/conversions'
7
- require 'active_support/core_ext/object/blank'
8
- require 'active_support/core_ext/module/attribute_accessors'
9
- require 'logger'
10
- require 'active_support/core_ext/logger'
11
-
12
- require 'dropcaster/errors'
13
- require 'dropcaster/log_formatter'
14
- require 'dropcaster/hashkeys'
15
- require 'dropcaster/channel'
16
- require 'dropcaster/item'
17
- require 'dropcaster/channel_file_locator'
18
-
19
- module Dropcaster
20
- VERSION = File.read(File.join(File.dirname(__FILE__), *%w[.. VERSION]))
21
- CHANNEL_YML = 'channel.yml'
22
-
23
- mattr_accessor :logger
24
-
25
- unless @@logger
26
- @@logger = Logger.new(STDERR)
27
- @@logger.level = Logger::WARN
28
- @@logger.formatter = LogFormatter.new
29
- end
30
- end
1
+ $:.unshift File.dirname(__FILE__)
2
+
3
+ require 'bundler/setup'
4
+ require 'yaml'
5
+ require 'active_support/core_ext/date_time/conversions'
6
+ require 'active_support/core_ext/object/blank'
7
+ require 'active_support/core_ext/module/attribute_accessors'
8
+
9
+ require 'logger'
10
+ require 'active_support/core_ext/logger'
11
+
12
+ require 'dropcaster/errors'
13
+ require 'dropcaster/log_formatter'
14
+ require 'dropcaster/channel'
15
+ require 'dropcaster/item'
16
+ require 'dropcaster/channel_file_locator'
17
+
18
+ module Dropcaster
19
+ CHANNEL_YML = 'channel.yml'
20
+
21
+ mattr_accessor :logger
22
+
23
+ unless @@logger
24
+ @@logger = Logger.new(STDERR)
25
+ @@logger.level = Logger::WARN
26
+ @@logger.formatter = LogFormatter.new
27
+ end
28
+ end
@@ -1,43 +1,45 @@
1
- <!DOCTYPE html>
2
- <html lang="<%= h(language) %>">
3
- <head>
4
- <meta charset="utf-8"/>
5
- <title><%= h(title) %></title>
6
- <meta name="generator" content="Dropcaster <%= Dropcaster::VERSION%>"/>
7
- <% unless copyright.blank? %>
8
- <meta name="copyright" content="<%= h(copyright) %>"/>
9
- <% end %>
10
- <link rel="canonical" href="<%= h(url) %>"/>
11
- </head>
12
-
13
- <body id="home">
14
- <h1><%= h(title) %></h1>
15
- <% unless subtitle.blank? %>
16
- <h2><%= h(subtitle) %></h2>
17
- <% end %>
18
-
19
- <% unless image_url.blank? %>
20
- <img src="<%= image_url %>"/>
21
- <% end %>
22
- <p><%= h(description) %></p>
23
-
24
- <h1>Episodes</h1>
25
- <% items.each{|item| %>
26
- <div class="item" id="<%= h(item.uuid) %>">
27
- <h1><%= item.tag.title || item.tag2.TIT2%></h1>
28
- <% unless item.tag2.SUBTITLE.blank? %>
29
- <h2><%= h(item.tag2.SUBTITLE) %></h2>
30
- <% end %>
31
- <% unless item.tag2.TT3.blank? %>
32
- <p><%= h(item.tag2.TT3) %></p>
33
- <% end %>
34
- <img src="<%= item.image_url %>"/>
35
- <p>Download: <a href="<%= item.url %>">MP3</a> (<%= humanize_time(item.duration.to_i) %>, <%= humanize_size(item.file_size) %>)</p>
36
- <p>Published <%= h(item.pub_date.to_formatted_s(:rfc822)) %></p>
37
- <% unless item.keywords.blank? %>
38
- <p><%= h(item.keywords) %></p>
39
- <% end %>
40
- </div>
41
- <% } %>
42
- </body>
43
- </html>
1
+ <!DOCTYPE html>
2
+ <html lang="<%= h(language) %>">
3
+ <head>
4
+ <meta charset="utf-8"/>
5
+ <title><%= h(title) %></title>
6
+ <meta name="generator" content="Dropcaster <%= Dropcaster::VERSION%>"/>
7
+ <meta name="keywords" content="<%= keywords.map{|k| h(k)}.join(', ') %>"/>
8
+ <% unless copyright.blank? %>
9
+ <meta name="copyright" content="<%= h(copyright) %>"/>
10
+ <% end %>
11
+ <link rel="canonical" href="<%= h(url) %>"/>
12
+ <link rel="alternate" type="application/rss+xml" title="<%= h(title) %> Podcast Feed" href="<%= h(url) %>">
13
+ </head>
14
+
15
+ <body id="home">
16
+ <h1><%= h(title) %></h1>
17
+ <% unless subtitle.blank? %>
18
+ <h2><%= h(subtitle) %></h2>
19
+ <% end %>
20
+
21
+ <% unless image_url.blank? %>
22
+ <img src="<%= image_url %>"/>
23
+ <% end %>
24
+ <p><%= h(description) %></p>
25
+
26
+ <h1>Episodes</h1>
27
+ <% items.each{|item| %>
28
+ <div class="item" id="<%= h(item.uuid) %>">
29
+ <h1><%= item.tag.title || item.tag2.TIT2%></h1>
30
+ <% unless item.tag2.SUBTITLE.blank? %>
31
+ <h2><%= h(item.tag2.SUBTITLE) %></h2>
32
+ <% end %>
33
+ <% unless item.tag2.TT3.blank? %>
34
+ <p><%= h(item.tag2.TT3) %></p>
35
+ <% end %>
36
+ <img src="<%= item.image_url %>"/>
37
+ <p>Download: <a href="<%= item.url %>">MP3</a> (<%= humanize_time(item.duration.to_i) %>, <%= humanize_size(item.file_size) %>)</p>
38
+ <p>Published <%= h(item.pub_date.to_formatted_s(:rfc822)) %></p>
39
+ <% unless item.keywords.blank? %>
40
+ <p><%= item.keywords.map{|k| h(k)}.join(',') %></p>
41
+ <% end %>
42
+ </div>
43
+ <% } %>
44
+ </body>
45
+ </html>
@@ -1,64 +1,65 @@
1
- <?xml version="1.0" encoding="UTF-8"?>
2
- <!-- This file generated by Dropcaster <%= Dropcaster::VERSION%> -->
3
- <rss xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd" version="2.0">
4
- <channel>
5
- <title><%= h(title) %></title>
6
- <link><%= h(url) %></link>
7
- <description><%= h(description) %></description>
8
- <itunes:summary><%= h(description) %></itunes:summary>
9
- <% unless language.blank? %>
10
- <language><%= h(language) %></language>
11
- <% end %>
12
- <% unless copyright.blank? %>
13
- <copyright><%= h(copyright) %></copyright>
14
- <% end %>
15
- <% unless subtitle.blank? %>
16
- <itunes:subtitle><%= h(subtitle) %></itunes:subtitle>
17
- <% end %>
18
- <% unless author.blank? %>
19
- <itunes:author><%= h(author) %></itunes:author>
20
- <% end %>
21
- <% unless owner.nil? %>
22
- <itunes:owner>
23
- <itunes:name><%= h(owner[:name]) %></itunes:name>
24
- <itunes:email><%= h(owner[:email]) %></itunes:email>
25
- </itunes:owner>
26
- <% end %>
27
- <% unless image_url.blank? %>
28
- <itunes:image href="<%= image_url %>"/>
29
- <% end %>
30
- <% categories.each{|category| %>
31
- <% if category.respond_to?(:each_line) %>
32
- <itunes:category text="<%= h(category) %>"/>
33
- <% else %>
34
- <itunes:category text="<%= h(category.first) %>">
35
- <itunes:category text="<%= h(category.last) %>"/>
36
- </itunes:category>
37
- <% end %>
38
- <% } unless categories.blank? %>
39
- <% unless explicit.blank? %>
40
- <itunes:explicit><%= h(explicit) %></itunes:explicit>
41
- <% end %>
42
- <generator>Dropcaster <%= Dropcaster::VERSION%></generator>
43
- <% items.each{|item| %>
44
- <item>
45
- <title><%= item.tag.title || item.tag2.TIT2%></title>
46
- <itunes:author><%= h(item.tag2.TP1 || item.tag2.TPE1) %></itunes:author>
47
- <% unless item.tag2.SUBTITLE.blank? %>
48
- <itunes:subtitle><%= h(item.tag2.SUBTITLE) %></itunes:subtitle>
49
- <% end %>
50
- <% unless item.tag2.TT3.blank? %>
51
- <itunes:summary><%= h(item.tag2.TT3) %></itunes:summary>
52
- <% end %>
53
- <itunes:image href="<%= item.image_url %>"/>
54
- <enclosure url="<%= item.url %>" length="<%= item.file_size %>" type="audio/mp3"/>
55
- <guid isPermaLink="false"><%= h(item.uuid) %></guid>
56
- <pubDate><%= h(item.pub_date.to_formatted_s(:rfc822)) %></pubDate>
57
- <itunes:duration><%= item.duration.to_i %></itunes:duration>
58
- <% unless item.keywords.blank? %>
59
- <itunes:keywords><%= h(item.keywords) %></itunes:keywords>
60
- <% end %>
61
- </item>
62
- <% } %>
63
- </channel>
64
- </rss>
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <!-- This file generated by Dropcaster <%= Dropcaster::VERSION %> -->
3
+ <rss xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd" version="2.0">
4
+ <channel>
5
+ <title><%= h(title) %></title>
6
+ <link><%= h(url) %></link>
7
+ <description><%= h(description) %></description>
8
+ <itunes:summary><%= h(description) %></itunes:summary>
9
+ <% unless language.blank? %>
10
+ <language><%= h(language) %></language>
11
+ <% end %>
12
+ <% unless copyright.blank? %>
13
+ <copyright><%= h(copyright) %></copyright>
14
+ <% end %>
15
+ <% unless subtitle.blank? %>
16
+ <itunes:subtitle><%= h(subtitle) %></itunes:subtitle>
17
+ <% end %>
18
+ <% unless author.blank? %>
19
+ <itunes:author><%= h(author) %></itunes:author>
20
+ <% end %>
21
+ <% unless owner.nil? %>
22
+ <itunes:owner>
23
+ <itunes:name><%= h(owner[:name]) %></itunes:name>
24
+ <itunes:email><%= h(owner[:email]) %></itunes:email>
25
+ </itunes:owner>
26
+ <% end %>
27
+ <% unless image_url.blank? %>
28
+ <itunes:image href="<%= image_url %>"/>
29
+ <% end %>
30
+ <% categories.each{|category| %>
31
+ <% if category.respond_to?(:each_line) %>
32
+ <itunes:category text="<%= h(category) %>"/>
33
+ <% else %>
34
+ <itunes:category text="<%= h(category.first) %>">
35
+ <itunes:category text="<%= h(category.last) %>"/>
36
+ </itunes:category>
37
+ <% end %>
38
+ <% } unless categories.blank? %>
39
+ <% unless explicit.blank? %>
40
+ <itunes:explicit><%= h(explicit) %></itunes:explicit>
41
+ <% end %>
42
+ <generator>Dropcaster <%= Dropcaster::VERSION%></generator>
43
+ <% unless keywords.blank? %>
44
+ <itunes:keywords><%= keywords.map{|k| h(k)}.join(',') %></itunes:keywords>
45
+ <% end %>
46
+ <% items.each{|item| %>
47
+ <item>
48
+ <title><%= item.tag.title || item.tag2.TIT2%></title>
49
+ <itunes:author><%= h(item.tag2.TP1 || item.tag2.TPE1) %></itunes:author>
50
+ <% unless item.tag2.TT3.blank? %>
51
+ <itunes:subtitle><%= h(truncate(item.tag2.TT3, 50)) %></itunes:subtitle>
52
+ <itunes:summary><%= h(item.tag2.TT3) %></itunes:summary>
53
+ <% end %>
54
+ <itunes:image href="<%= item.image_url %>"/>
55
+ <enclosure url="<%= item.url %>" length="<%= item.file_size %>" type="audio/mp3"/>
56
+ <guid isPermaLink="false"><%= h(item.uuid) %></guid>
57
+ <pubDate><%= h(item.pub_date.to_formatted_s(:rfc822)) %></pubDate>
58
+ <itunes:duration><%= item.duration.to_i %></itunes:duration>
59
+ <% unless item.keywords.blank? %>
60
+ <itunes:keywords><%= item.keywords.map{|k| h(k)}.join(',') %></itunes:keywords>
61
+ <% end %>
62
+ </item>
63
+ <% } %>
64
+ </channel>
65
+ </rss>
@@ -1,12 +1,12 @@
1
- # Returns true if we run on a windows platform
2
- #
3
- # Sample:
4
- #
5
- # puts "Windows" if Kernel.is_windows?
6
- #
7
- # http://snippets.dzone.com/posts/show/2112
8
- #
9
- def Kernel.is_windows?
10
- processor, platform, *rest = RUBY_PLATFORM.split("-")
11
- platform == 'mingw32'
12
- end
1
+ # Returns true if we run on a windows platform
2
+ #
3
+ # Sample:
4
+ #
5
+ # puts "Windows" if Kernel.is_windows?
6
+ #
7
+ # http://snippets.dzone.com/posts/show/2112
8
+ #
9
+ def Kernel.is_windows?
10
+ processor, platform, *rest = RUBY_PLATFORM.split("-")
11
+ platform == 'mingw32'
12
+ end
@@ -1,15 +1,16 @@
1
- :title: All About Everything
2
- :subtitle: A show about everything
3
- :url: http://www.example.com/podcasts/everything/
4
- :language: en-us
5
- :copyright: © 2011 John Doe and Family
6
- :author: John Doe
7
- :description: All About Everything is a show about everything. Each week we dive into any subject known to man and talk about it as much as we can. Look for our Podcast in the iTunes Store!
8
- :owner:
9
- :name: John Doe
10
- :email: john.doe@example.com
11
- :image_url: AllAboutEverything.jpg
12
- :categories:
13
- - [Technology, Gadgets]
14
- - TV & Film
15
- :explicit: No
1
+ :title: All About Everything
2
+ :subtitle: A show about everything
3
+ :url: http://www.example.com/podcasts/everything/
4
+ :language: en-us
5
+ :copyright: © 2011 John Doe and Family
6
+ :author: John Doe
7
+ :description: All About Everything is a show about everything. Each week we dive into any subject known to man and talk about it as much as we can. Look for our Podcast in the iTunes Store!
8
+ :owner:
9
+ :name: John Doe
10
+ :email: john.doe@example.com
11
+ :image_url: AllAboutEverything.jpg
12
+ :keywords: [bumm, zack, return]
13
+ :categories:
14
+ - [Technology, Gadgets]
15
+ - TV & Film
16
+ :explicit: No
@@ -1,40 +1,40 @@
1
- {
2
- "generator" : {
3
- "name" : "Dropcaster",
4
- "version" : "<%= Dropcaster::VERSION%>"
5
- },
6
- "channel" : {
7
- "title" : "<%= title %>",
8
- "link" : "<%= url %>",
9
- "description" : "<%= description %>",
10
- "language" : "<%= language %>",
11
- "copyright" : "<%= copyright %>",
12
- "subtitle" : "<%= subtitle %>",
13
- "author" : "<%= author %>",
14
- "owner" : {
15
- "name" : "<%= owner[:name] %>",
16
- "email" : "<%= owner[:email] %>"
17
- },
18
- "image" : "<%= image_url %>",
19
- "categories": ["<% categories.join('\",\"') %>"],
20
- "explicit" : "<%= explicit %>",
21
- "items" : [<% items.collect{|item| %>{
22
- "title" : "<%= item.tag.title || item.tag2.TIT2 %>",
23
- "author" : "<%= item.tag2.TP1 || item.tag2.TPE1 %>",
24
- "subtitle" : "<%= item.tag2.SUBTITLE %>",
25
- "summary" : "<%= item.tag2.TT3 %>",
26
- "image" : "<%= item.image_url %>",
27
- "enclosure" : {
28
- "url" : "<%= item.url %>",
29
- "length" : "<%= item.file_size %>",
30
- "type" : "audio/mp3"
31
- },
32
- "guid" : "<%= item.uuid %>",
33
- "pubDate" : "<%= item.pub_date.to_formatted_s(:rfc822) %>",
34
- "duration" : "<%= item.duration.to_i %>",
35
- "keywords" : "<%= item.keywords %>"
36
- }
37
- <% }.join(',') %>
38
- ]
39
- }
40
- }
1
+ {
2
+ "generator" : {
3
+ "name" : "Dropcaster",
4
+ "version" : "<%= Dropcaster::VERSION%>"
5
+ },
6
+ "channel" : {
7
+ "title" : "<%= title %>",
8
+ "link" : "<%= url %>",
9
+ "description" : "<%= description %>",
10
+ "language" : "<%= language %>",
11
+ "copyright" : "<%= copyright %>",
12
+ "subtitle" : "<%= subtitle %>",
13
+ "author" : "<%= author %>",
14
+ "owner" : {
15
+ "name" : "<%= owner[:name] %>",
16
+ "email" : "<%= owner[:email] %>"
17
+ },
18
+ "image" : "<%= image_url %>",
19
+ "categories": ["<% categories.join('\",\"') %>"],
20
+ "explicit" : "<%= explicit %>",
21
+ "items" : [<% items.collect{|item| %>{
22
+ "title" : "<%= item.tag.title || item.tag2.TIT2 %>",
23
+ "author" : "<%= item.tag2.TP1 || item.tag2.TPE1 %>",
24
+ "subtitle" : "<%= item.tag2.SUBTITLE %>",
25
+ "summary" : "<%= item.tag2.TT3 %>",
26
+ "image" : "<%= item.image_url %>",
27
+ "enclosure" : {
28
+ "url" : "<%= item.url %>",
29
+ "length" : "<%= item.file_size %>",
30
+ "type" : "audio/mp3"
31
+ },
32
+ "guid" : "<%= item.uuid %>",
33
+ "pubDate" : "<%= item.pub_date.to_formatted_s(:rfc822) %>",
34
+ "duration" : "<%= item.duration.to_i %>",
35
+ "keywords" : "<%= item.keywords %>"
36
+ }
37
+ <% }.join(',') %>
38
+ ]
39
+ }
40
+ }
data/test/helper.rb CHANGED
@@ -1,14 +1,10 @@
1
- require 'rubygems'
2
- require 'test/unit'
3
- require 'dropcaster'
4
-
5
- $:.unshift File.join(File.dirname(__FILE__), *%w[.. test unit])
6
- $:.unshift File.join(File.dirname(__FILE__), *%w[.. test extensions])
7
-
8
- require 'windows'
9
-
10
- module DropcasterTest
11
- FIXTURES_DIR = File.join(File.dirname(__FILE__), 'fixtures')
12
- FIXTURE_ITUNES_MP3 = File.join(FIXTURES_DIR, 'iTunes.mp3')
13
- NS_ITUNES = "itunes:http://www.itunes.com/dtds/podcast-1.0.dtd"
14
- end
1
+ require 'minitest/autorun'
2
+ require 'dropcaster'
3
+
4
+ require_relative 'extensions/windows'
5
+
6
+ module DropcasterTest
7
+ FIXTURES_DIR = File.join(File.dirname(__FILE__), 'fixtures')
8
+ FIXTURE_ITUNES_MP3 = File.join(FIXTURES_DIR, 'iTunes.mp3')
9
+ NS_ITUNES = "itunes:http://www.itunes.com/dtds/podcast-1.0.dtd"
10
+ end