rubysl-rss 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (55) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +17 -0
  3. data/.travis.yml +8 -0
  4. data/Gemfile +4 -0
  5. data/LICENSE +25 -0
  6. data/README.md +29 -0
  7. data/Rakefile +1 -0
  8. data/lib/rss.rb +1 -0
  9. data/lib/rss/0.9.rb +428 -0
  10. data/lib/rss/1.0.rb +452 -0
  11. data/lib/rss/2.0.rb +111 -0
  12. data/lib/rss/atom.rb +749 -0
  13. data/lib/rss/content.rb +31 -0
  14. data/lib/rss/content/1.0.rb +10 -0
  15. data/lib/rss/content/2.0.rb +12 -0
  16. data/lib/rss/converter.rb +162 -0
  17. data/lib/rss/dublincore.rb +161 -0
  18. data/lib/rss/dublincore/1.0.rb +13 -0
  19. data/lib/rss/dublincore/2.0.rb +13 -0
  20. data/lib/rss/dublincore/atom.rb +17 -0
  21. data/lib/rss/image.rb +193 -0
  22. data/lib/rss/itunes.rb +410 -0
  23. data/lib/rss/maker.rb +44 -0
  24. data/lib/rss/maker/0.9.rb +467 -0
  25. data/lib/rss/maker/1.0.rb +434 -0
  26. data/lib/rss/maker/2.0.rb +223 -0
  27. data/lib/rss/maker/atom.rb +172 -0
  28. data/lib/rss/maker/base.rb +868 -0
  29. data/lib/rss/maker/content.rb +21 -0
  30. data/lib/rss/maker/dublincore.rb +124 -0
  31. data/lib/rss/maker/entry.rb +163 -0
  32. data/lib/rss/maker/feed.rb +429 -0
  33. data/lib/rss/maker/image.rb +111 -0
  34. data/lib/rss/maker/itunes.rb +242 -0
  35. data/lib/rss/maker/slash.rb +33 -0
  36. data/lib/rss/maker/syndication.rb +18 -0
  37. data/lib/rss/maker/taxonomy.rb +118 -0
  38. data/lib/rss/maker/trackback.rb +61 -0
  39. data/lib/rss/parser.rb +541 -0
  40. data/lib/rss/rexmlparser.rb +54 -0
  41. data/lib/rss/rss.rb +1312 -0
  42. data/lib/rss/slash.rb +49 -0
  43. data/lib/rss/syndication.rb +67 -0
  44. data/lib/rss/taxonomy.rb +145 -0
  45. data/lib/rss/trackback.rb +288 -0
  46. data/lib/rss/utils.rb +111 -0
  47. data/lib/rss/xml-stylesheet.rb +105 -0
  48. data/lib/rss/xml.rb +71 -0
  49. data/lib/rss/xmlparser.rb +93 -0
  50. data/lib/rss/xmlscanner.rb +121 -0
  51. data/lib/rubysl/rss.rb +2 -0
  52. data/lib/rubysl/rss/rss.rb +19 -0
  53. data/lib/rubysl/rss/version.rb +5 -0
  54. data/rubysl-rss.gemspec +23 -0
  55. metadata +153 -0
@@ -0,0 +1,31 @@
1
+ require "rss/rss"
2
+
3
+ module RSS
4
+ CONTENT_PREFIX = 'content'
5
+ CONTENT_URI = "http://purl.org/rss/1.0/modules/content/"
6
+
7
+ module ContentModel
8
+ extend BaseModel
9
+
10
+ ELEMENTS = ["#{CONTENT_PREFIX}_encoded"]
11
+
12
+ def self.append_features(klass)
13
+ super
14
+
15
+ klass.install_must_call_validator(CONTENT_PREFIX, CONTENT_URI)
16
+ ELEMENTS.each do |full_name|
17
+ name = full_name[(CONTENT_PREFIX.size + 1)..-1]
18
+ klass.install_text_element(name, CONTENT_URI, "?", full_name)
19
+ end
20
+ end
21
+ end
22
+
23
+ prefix_size = CONTENT_PREFIX.size + 1
24
+ ContentModel::ELEMENTS.each do |full_name|
25
+ name = full_name[prefix_size..-1]
26
+ BaseListener.install_get_text_element(CONTENT_URI, name, full_name)
27
+ end
28
+ end
29
+
30
+ require 'rss/content/1.0'
31
+ require 'rss/content/2.0'
@@ -0,0 +1,10 @@
1
+ require 'rss/1.0'
2
+ require 'rss/content'
3
+
4
+ module RSS
5
+ RDF.install_ns(CONTENT_PREFIX, CONTENT_URI)
6
+
7
+ class RDF
8
+ class Item; include ContentModel; end
9
+ end
10
+ end
@@ -0,0 +1,12 @@
1
+ require "rss/2.0"
2
+ require "rss/content"
3
+
4
+ module RSS
5
+ Rss.install_ns(CONTENT_PREFIX, CONTENT_URI)
6
+
7
+ class Rss
8
+ class Channel
9
+ class Item; include ContentModel; end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,162 @@
1
+ require "rss/utils"
2
+
3
+ module RSS
4
+
5
+ class Converter
6
+
7
+ include Utils
8
+
9
+ def initialize(to_enc, from_enc=nil)
10
+ normalized_to_enc = to_enc.downcase.gsub(/-/, '_')
11
+ from_enc ||= 'utf-8'
12
+ normalized_from_enc = from_enc.downcase.gsub(/-/, '_')
13
+ if normalized_to_enc == normalized_from_enc
14
+ def_same_enc()
15
+ else
16
+ def_diff_enc = "def_to_#{normalized_to_enc}_from_#{normalized_from_enc}"
17
+ if respond_to?(def_diff_enc)
18
+ __send__(def_diff_enc)
19
+ else
20
+ def_else_enc(to_enc, from_enc)
21
+ end
22
+ end
23
+ end
24
+
25
+ def convert(value)
26
+ value
27
+ end
28
+
29
+ def def_convert(depth=0)
30
+ instance_eval(<<-EOC, *get_file_and_line_from_caller(depth))
31
+ def convert(value)
32
+ if value.kind_of?(String)
33
+ #{yield('value')}
34
+ else
35
+ value
36
+ end
37
+ end
38
+ EOC
39
+ end
40
+
41
+ def def_iconv_convert(to_enc, from_enc, depth=0)
42
+ begin
43
+ require "iconv"
44
+ @iconv = Iconv.new(to_enc, from_enc)
45
+ def_convert(depth+1) do |value|
46
+ <<-EOC
47
+ begin
48
+ @iconv.iconv(#{value})
49
+ rescue Iconv::Failure
50
+ raise ConversionError.new(#{value}, "#{to_enc}", "#{from_enc}")
51
+ end
52
+ EOC
53
+ end
54
+ rescue LoadError, ArgumentError, SystemCallError
55
+ raise UnknownConversionMethodError.new(to_enc, from_enc)
56
+ end
57
+ end
58
+
59
+ def def_else_enc(to_enc, from_enc)
60
+ def_iconv_convert(to_enc, from_enc, 0)
61
+ end
62
+
63
+ def def_same_enc()
64
+ def_convert do |value|
65
+ value
66
+ end
67
+ end
68
+
69
+ def def_uconv_convert_if_can(meth, to_enc, from_enc, nkf_arg)
70
+ begin
71
+ require "uconv"
72
+ def_convert(1) do |value|
73
+ <<-EOC
74
+ begin
75
+ Uconv.#{meth}(#{value})
76
+ rescue Uconv::Error
77
+ raise ConversionError.new(#{value}, "#{to_enc}", "#{from_enc}")
78
+ end
79
+ EOC
80
+ end
81
+ rescue LoadError
82
+ require 'nkf'
83
+ if NKF.const_defined?(:UTF8)
84
+ def_convert(1) do |value|
85
+ "NKF.nkf(#{nkf_arg.dump}, #{value})"
86
+ end
87
+ else
88
+ def_iconv_convert(to_enc, from_enc, 1)
89
+ end
90
+ end
91
+ end
92
+
93
+ def def_to_euc_jp_from_utf_8
94
+ def_uconv_convert_if_can('u8toeuc', 'EUC-JP', 'UTF-8', '-We')
95
+ end
96
+
97
+ def def_to_utf_8_from_euc_jp
98
+ def_uconv_convert_if_can('euctou8', 'UTF-8', 'EUC-JP', '-Ew')
99
+ end
100
+
101
+ def def_to_shift_jis_from_utf_8
102
+ def_uconv_convert_if_can('u8tosjis', 'Shift_JIS', 'UTF-8', '-Ws')
103
+ end
104
+
105
+ def def_to_utf_8_from_shift_jis
106
+ def_uconv_convert_if_can('sjistou8', 'UTF-8', 'Shift_JIS', '-Sw')
107
+ end
108
+
109
+ def def_to_euc_jp_from_shift_jis
110
+ require "nkf"
111
+ def_convert do |value|
112
+ "NKF.nkf('-Se', #{value})"
113
+ end
114
+ end
115
+
116
+ def def_to_shift_jis_from_euc_jp
117
+ require "nkf"
118
+ def_convert do |value|
119
+ "NKF.nkf('-Es', #{value})"
120
+ end
121
+ end
122
+
123
+ def def_to_euc_jp_from_iso_2022_jp
124
+ require "nkf"
125
+ def_convert do |value|
126
+ "NKF.nkf('-Je', #{value})"
127
+ end
128
+ end
129
+
130
+ def def_to_iso_2022_jp_from_euc_jp
131
+ require "nkf"
132
+ def_convert do |value|
133
+ "NKF.nkf('-Ej', #{value})"
134
+ end
135
+ end
136
+
137
+ def def_to_utf_8_from_iso_8859_1
138
+ def_convert do |value|
139
+ "#{value}.unpack('C*').pack('U*')"
140
+ end
141
+ end
142
+
143
+ def def_to_iso_8859_1_from_utf_8
144
+ def_convert do |value|
145
+ <<-EOC
146
+ array_utf8 = #{value}.unpack('U*')
147
+ array_enc = []
148
+ array_utf8.each do |num|
149
+ if num <= 0xFF
150
+ array_enc << num
151
+ else
152
+ array_enc.concat "&\#\#{num};".unpack('C*')
153
+ end
154
+ end
155
+ array_enc.pack('C*')
156
+ EOC
157
+ end
158
+ end
159
+
160
+ end
161
+
162
+ end
@@ -0,0 +1,161 @@
1
+ require "rss/rss"
2
+
3
+ module RSS
4
+ DC_PREFIX = 'dc'
5
+ DC_URI = "http://purl.org/dc/elements/1.1/"
6
+
7
+ module BaseDublinCoreModel
8
+ def append_features(klass)
9
+ super
10
+
11
+ return if klass.instance_of?(Module)
12
+ DublinCoreModel::ELEMENT_NAME_INFOS.each do |name, plural_name|
13
+ plural = plural_name || "#{name}s"
14
+ full_name = "#{DC_PREFIX}_#{name}"
15
+ full_plural_name = "#{DC_PREFIX}_#{plural}"
16
+ klass_name = "DublinCore#{Utils.to_class_name(name)}"
17
+ klass.install_must_call_validator(DC_PREFIX, DC_URI)
18
+ klass.install_have_children_element(name, DC_URI, "*",
19
+ full_name, full_plural_name)
20
+ klass.module_eval(<<-EOC, *get_file_and_line_from_caller(0))
21
+ remove_method :#{full_name}
22
+ remove_method :#{full_name}=
23
+ remove_method :set_#{full_name}
24
+
25
+ def #{full_name}
26
+ @#{full_name}.first and @#{full_name}.first.value
27
+ end
28
+
29
+ def #{full_name}=(new_value)
30
+ @#{full_name}[0] = Utils.new_with_value_if_need(#{klass_name}, new_value)
31
+ end
32
+ alias set_#{full_name} #{full_name}=
33
+ EOC
34
+ end
35
+ klass.module_eval(<<-EOC, *get_file_and_line_from_caller(0))
36
+ if method_defined?(:date)
37
+ alias date_without_#{DC_PREFIX}_date= date=
38
+
39
+ def date=(value)
40
+ self.date_without_#{DC_PREFIX}_date = value
41
+ self.#{DC_PREFIX}_date = value
42
+ end
43
+ else
44
+ alias date #{DC_PREFIX}_date
45
+ alias date= #{DC_PREFIX}_date=
46
+ end
47
+
48
+ # For backward compatibility
49
+ alias #{DC_PREFIX}_rightses #{DC_PREFIX}_rights_list
50
+ EOC
51
+ end
52
+ end
53
+
54
+ module DublinCoreModel
55
+
56
+ extend BaseModel
57
+ extend BaseDublinCoreModel
58
+
59
+ TEXT_ELEMENTS = {
60
+ "title" => nil,
61
+ "description" => nil,
62
+ "creator" => nil,
63
+ "subject" => nil,
64
+ "publisher" => nil,
65
+ "contributor" => nil,
66
+ "type" => nil,
67
+ "format" => nil,
68
+ "identifier" => nil,
69
+ "source" => nil,
70
+ "language" => nil,
71
+ "relation" => nil,
72
+ "coverage" => nil,
73
+ "rights" => "rights_list"
74
+ }
75
+
76
+ DATE_ELEMENTS = {
77
+ "date" => "w3cdtf",
78
+ }
79
+
80
+ ELEMENT_NAME_INFOS = DublinCoreModel::TEXT_ELEMENTS.to_a
81
+ DublinCoreModel::DATE_ELEMENTS.each do |name, |
82
+ ELEMENT_NAME_INFOS << [name, nil]
83
+ end
84
+
85
+ ELEMENTS = TEXT_ELEMENTS.keys + DATE_ELEMENTS.keys
86
+
87
+ ELEMENTS.each do |name, plural_name|
88
+ module_eval(<<-EOC, *get_file_and_line_from_caller(0))
89
+ class DublinCore#{Utils.to_class_name(name)} < Element
90
+ include RSS10
91
+
92
+ content_setup
93
+
94
+ class << self
95
+ def required_prefix
96
+ DC_PREFIX
97
+ end
98
+
99
+ def required_uri
100
+ DC_URI
101
+ end
102
+ end
103
+
104
+ @tag_name = #{name.dump}
105
+
106
+ alias_method(:value, :content)
107
+ alias_method(:value=, :content=)
108
+
109
+ def initialize(*args)
110
+ if Utils.element_initialize_arguments?(args)
111
+ super
112
+ else
113
+ super()
114
+ self.content = args[0]
115
+ end
116
+ end
117
+
118
+ def full_name
119
+ tag_name_with_prefix(DC_PREFIX)
120
+ end
121
+
122
+ def maker_target(target)
123
+ target.new_#{name}
124
+ end
125
+
126
+ def setup_maker_attributes(#{name})
127
+ #{name}.content = content
128
+ end
129
+ end
130
+ EOC
131
+ end
132
+
133
+ DATE_ELEMENTS.each do |name, type|
134
+ tag_name = "#{DC_PREFIX}:#{name}"
135
+ module_eval(<<-EOC, *get_file_and_line_from_caller(0))
136
+ class DublinCore#{Utils.to_class_name(name)} < Element
137
+ remove_method(:content=)
138
+ remove_method(:value=)
139
+
140
+ date_writer("content", #{type.dump}, #{tag_name.dump})
141
+
142
+ alias_method(:value=, :content=)
143
+ end
144
+ EOC
145
+ end
146
+ end
147
+
148
+ # For backward compatibility
149
+ DublincoreModel = DublinCoreModel
150
+
151
+ DublinCoreModel::ELEMENTS.each do |name|
152
+ class_name = Utils.to_class_name(name)
153
+ BaseListener.install_class_name(DC_URI, name, "DublinCore#{class_name}")
154
+ end
155
+
156
+ DublinCoreModel::ELEMENTS.collect! {|name| "#{DC_PREFIX}_#{name}"}
157
+ end
158
+
159
+ require 'rss/dublincore/1.0'
160
+ require 'rss/dublincore/2.0'
161
+ require 'rss/dublincore/atom'
@@ -0,0 +1,13 @@
1
+ require "rss/1.0"
2
+ require "rss/dublincore"
3
+
4
+ module RSS
5
+ RDF.install_ns(DC_PREFIX, DC_URI)
6
+
7
+ class RDF
8
+ class Channel; include DublinCoreModel; end
9
+ class Image; include DublinCoreModel; end
10
+ class Item; include DublinCoreModel; end
11
+ class Textinput; include DublinCoreModel; end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ require "rss/2.0"
2
+ require "rss/dublincore"
3
+
4
+ module RSS
5
+ Rss.install_ns(DC_PREFIX, DC_URI)
6
+
7
+ class Rss
8
+ class Channel
9
+ include DublinCoreModel
10
+ class Item; include DublinCoreModel; end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,17 @@
1
+ require "rss/atom"
2
+ require "rss/dublincore"
3
+
4
+ module RSS
5
+ module Atom
6
+ Feed.install_ns(DC_PREFIX, DC_URI)
7
+
8
+ class Feed
9
+ include DublinCoreModel
10
+ class Entry; include DublinCoreModel; end
11
+ end
12
+
13
+ class Entry
14
+ include DublinCoreModel
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,193 @@
1
+ require 'rss/1.0'
2
+ require 'rss/dublincore'
3
+
4
+ module RSS
5
+
6
+ IMAGE_PREFIX = 'image'
7
+ IMAGE_URI = 'http://purl.org/rss/1.0/modules/image/'
8
+
9
+ RDF.install_ns(IMAGE_PREFIX, IMAGE_URI)
10
+
11
+ IMAGE_ELEMENTS = []
12
+
13
+ %w(item favicon).each do |name|
14
+ class_name = Utils.to_class_name(name)
15
+ BaseListener.install_class_name(IMAGE_URI, name, "Image#{class_name}")
16
+ IMAGE_ELEMENTS << "#{IMAGE_PREFIX}_#{name}"
17
+ end
18
+
19
+ module ImageModelUtils
20
+ def validate_one_tag_name(ignore_unknown_element, name, tags)
21
+ if !ignore_unknown_element
22
+ invalid = tags.find {|tag| tag != name}
23
+ raise UnknownTagError.new(invalid, IMAGE_URI) if invalid
24
+ end
25
+ raise TooMuchTagError.new(name, tag_name) if tags.size > 1
26
+ end
27
+ end
28
+
29
+ module ImageItemModel
30
+ include ImageModelUtils
31
+ extend BaseModel
32
+
33
+ def self.append_features(klass)
34
+ super
35
+
36
+ klass.install_have_child_element("item", IMAGE_URI, "?",
37
+ "#{IMAGE_PREFIX}_item")
38
+ klass.install_must_call_validator(IMAGE_PREFIX, IMAGE_URI)
39
+ end
40
+
41
+ class ImageItem < Element
42
+ include RSS10
43
+ include DublinCoreModel
44
+
45
+ @tag_name = "item"
46
+
47
+ class << self
48
+ def required_prefix
49
+ IMAGE_PREFIX
50
+ end
51
+
52
+ def required_uri
53
+ IMAGE_URI
54
+ end
55
+ end
56
+
57
+ install_must_call_validator(IMAGE_PREFIX, IMAGE_URI)
58
+
59
+ [
60
+ ["about", ::RSS::RDF::URI, true],
61
+ ["resource", ::RSS::RDF::URI, false],
62
+ ].each do |name, uri, required|
63
+ install_get_attribute(name, uri, required, nil, nil,
64
+ "#{::RSS::RDF::PREFIX}:#{name}")
65
+ end
66
+
67
+ %w(width height).each do |tag|
68
+ full_name = "#{IMAGE_PREFIX}_#{tag}"
69
+ disp_name = "#{IMAGE_PREFIX}:#{tag}"
70
+ install_text_element(tag, IMAGE_URI, "?",
71
+ full_name, :integer, disp_name)
72
+ BaseListener.install_get_text_element(IMAGE_URI, tag, full_name)
73
+ end
74
+
75
+ alias width= image_width=
76
+ alias width image_width
77
+ alias height= image_height=
78
+ alias height image_height
79
+
80
+ def initialize(*args)
81
+ if Utils.element_initialize_arguments?(args)
82
+ super
83
+ else
84
+ super()
85
+ self.about = args[0]
86
+ self.resource = args[1]
87
+ end
88
+ end
89
+
90
+ def full_name
91
+ tag_name_with_prefix(IMAGE_PREFIX)
92
+ end
93
+
94
+ private
95
+ def maker_target(target)
96
+ target.image_item
97
+ end
98
+
99
+ def setup_maker_attributes(item)
100
+ item.about = self.about
101
+ item.resource = self.resource
102
+ end
103
+ end
104
+ end
105
+
106
+ module ImageFaviconModel
107
+ include ImageModelUtils
108
+ extend BaseModel
109
+
110
+ def self.append_features(klass)
111
+ super
112
+
113
+ unless klass.class == Module
114
+ klass.install_have_child_element("favicon", IMAGE_URI, "?",
115
+ "#{IMAGE_PREFIX}_favicon")
116
+ klass.install_must_call_validator(IMAGE_PREFIX, IMAGE_URI)
117
+ end
118
+ end
119
+
120
+ class ImageFavicon < Element
121
+ include RSS10
122
+ include DublinCoreModel
123
+
124
+ @tag_name = "favicon"
125
+
126
+ class << self
127
+ def required_prefix
128
+ IMAGE_PREFIX
129
+ end
130
+
131
+ def required_uri
132
+ IMAGE_URI
133
+ end
134
+ end
135
+
136
+ [
137
+ ["about", ::RSS::RDF::URI, true, ::RSS::RDF::PREFIX],
138
+ ["size", IMAGE_URI, true, IMAGE_PREFIX],
139
+ ].each do |name, uri, required, prefix|
140
+ install_get_attribute(name, uri, required, nil, nil,
141
+ "#{prefix}:#{name}")
142
+ end
143
+
144
+ AVAILABLE_SIZES = %w(small medium large)
145
+ alias_method :set_size, :size=
146
+ private :set_size
147
+ def size=(new_value)
148
+ if @do_validate and !new_value.nil?
149
+ new_value = new_value.strip
150
+ unless AVAILABLE_SIZES.include?(new_value)
151
+ attr_name = "#{IMAGE_PREFIX}:size"
152
+ raise NotAvailableValueError.new(full_name, new_value, attr_name)
153
+ end
154
+ end
155
+ set_size(new_value)
156
+ end
157
+
158
+ alias image_size= size=
159
+ alias image_size size
160
+
161
+ def initialize(*args)
162
+ if Utils.element_initialize_arguments?(args)
163
+ super
164
+ else
165
+ super()
166
+ self.about = args[0]
167
+ self.size = args[1]
168
+ end
169
+ end
170
+
171
+ def full_name
172
+ tag_name_with_prefix(IMAGE_PREFIX)
173
+ end
174
+
175
+ private
176
+ def maker_target(target)
177
+ target.image_favicon
178
+ end
179
+
180
+ def setup_maker_attributes(favicon)
181
+ favicon.about = self.about
182
+ favicon.size = self.size
183
+ end
184
+ end
185
+
186
+ end
187
+
188
+ class RDF
189
+ class Channel; include ImageFaviconModel; end
190
+ class Item; include ImageItemModel; end
191
+ end
192
+
193
+ end