urss 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/.gemrc +1 -0
- data/.gitignore +17 -0
- data/.gpairrc +1 -0
- data/.rspec +2 -0
- data/.rvmrc +1 -0
- data/.travis.yml +7 -0
- data/Gemfile +9 -0
- data/LICENSE +22 -0
- data/README.md +47 -0
- data/Rakefile +8 -0
- data/lib/urss.rb +23 -0
- data/lib/urss/feed.rb +17 -0
- data/lib/urss/feed/atom.rb +20 -0
- data/lib/urss/feed/atom_entry.rb +44 -0
- data/lib/urss/feed/entry.rb +20 -0
- data/lib/urss/feed/rss.rb +27 -0
- data/lib/urss/feed/rss_entry.rb +49 -0
- data/lib/urss/media.rb +31 -0
- data/lib/urss/rss.rb +28 -0
- data/lib/urss/version.rb +3 -0
- data/spec/spec_helper.rb +17 -0
- data/spec/support/fixtures/atom.xml +45 -0
- data/spec/support/fixtures/media_rss.xml +465 -0
- data/spec/support/fixtures/not-rss.xml +8 -0
- data/spec/support/fixtures/rss09.rdf +79 -0
- data/spec/support/fixtures/rss20.xml +818 -0
- data/spec/support/fixtures/ruby.rss +395 -0
- data/spec/support/fixtures/stackoverflow.com.xml +1344 -0
- data/spec/support/fixtures/wax.rss +358 -0
- data/spec/support/webmocks.rb +6 -0
- data/spec/urss/feed/atom_entry_spec.rb +22 -0
- data/spec/urss/feed/atom_spec.rb +57 -0
- data/spec/urss/feed/entry_spec.rb +42 -0
- data/spec/urss/feed/rss_entry_spec.rb +22 -0
- data/spec/urss/feed/rss_spec.rb +79 -0
- data/spec/urss/feed_atom_spec.rb +27 -0
- data/spec/urss/feed_spec.rb +32 -0
- data/spec/urss/media_spec.rb +37 -0
- data/spec/urss/rss_spec.rb +25 -0
- data/spec/urss_spec.rb +540 -0
- data/urss.gemspec +19 -0
- metadata +129 -0
@@ -0,0 +1,22 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Feed::Rss::Entry do
|
4
|
+
|
5
|
+
describe "Class Methods" do
|
6
|
+
describe "#build" do
|
7
|
+
describe "argument" do
|
8
|
+
it "should raise an Urss::NotANokogiriInstance exception when passing something different than a Nokogiri::XML::Element instance" do
|
9
|
+
lambda {
|
10
|
+
subject.class.build("I'm not a Nokogiri::XML::Element instance")
|
11
|
+
}.should raise_error(Urss::NotANokogiriInstance)
|
12
|
+
end
|
13
|
+
it "should not raise an Urss::NotANokogiriInstance when passing a Nokogiri::XML::Element instance" do
|
14
|
+
lambda {
|
15
|
+
subject.class.build(Nokogiri::XML::Element.new("item", Nokogiri::XML::Document.new))
|
16
|
+
}.should_not raise_error(Urss::NotANokogiriInstance)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Feed::Rss do
|
4
|
+
|
5
|
+
describe "Attributes" do
|
6
|
+
it "should have an attribute :title" do
|
7
|
+
subject.should respond_to(:title)
|
8
|
+
subject.should respond_to(:title=)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should have an attribute :url" do
|
12
|
+
subject.should respond_to(:url)
|
13
|
+
subject.should respond_to(:url=)
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should have an attribute :description" do
|
17
|
+
subject.should respond_to(:description)
|
18
|
+
subject.should respond_to(:description=)
|
19
|
+
end
|
20
|
+
|
21
|
+
it "should have an attribute :updated_at" do
|
22
|
+
subject.should respond_to(:updated_at)
|
23
|
+
subject.should respond_to(:updated_at=)
|
24
|
+
end
|
25
|
+
|
26
|
+
it "should have an attribute :entries" do
|
27
|
+
subject.should respond_to(:entries)
|
28
|
+
subject.should respond_to(:entries=)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe "Class Methods" do
|
33
|
+
it "should respond to build" do
|
34
|
+
subject.class.should respond_to(:build)
|
35
|
+
end
|
36
|
+
describe "#build" do
|
37
|
+
describe "arguments" do
|
38
|
+
it "should raise an ArgumentError when passing no argument" do
|
39
|
+
lambda {
|
40
|
+
subject.class.build
|
41
|
+
}.should raise_error(ArgumentError)
|
42
|
+
end
|
43
|
+
it "should raise an Urss::NotANokogiriInstance exception when passing something different than a Nokogiri::XML::Document instance as first parameter" do
|
44
|
+
lambda {
|
45
|
+
subject.class.build("I'm not a Nokogiri::XML::Document instance", nil, nil)
|
46
|
+
}.should raise_error(Urss::NotANokogiriInstance)
|
47
|
+
end
|
48
|
+
it "should not raise an Urss::NotANokogiriInstance when passing a Nokogiri::XML::Document instance as first parameter" do
|
49
|
+
lambda {
|
50
|
+
subject.class.build(Nokogiri::XML::NodeSet.new, nil, nil)
|
51
|
+
}.should_not raise_error(Urss::NotANokogiriInstance)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
describe "Instance Methods" do
|
58
|
+
describe "#entries" do
|
59
|
+
context "without entries" do
|
60
|
+
it "should return an empty array" do
|
61
|
+
subject.entries.should be_an_instance_of(Array)
|
62
|
+
subject.entries.should be_empty
|
63
|
+
end
|
64
|
+
end
|
65
|
+
context "with entries" do
|
66
|
+
before do
|
67
|
+
nokogiri = Nokogiri::XML(open(File.join(File.dirname(__FILE__), "..", "..", "support", "fixtures", "rss20.xml")))
|
68
|
+
@urss_rss = Urss::Feed::Rss.build(nokogiri.xpath("//channel"), nil, "channel")
|
69
|
+
end
|
70
|
+
it "should return an array of Urss::Entry" do
|
71
|
+
@urss_rss.entries.should be_an_instance_of(Array)
|
72
|
+
@urss_rss.entries.should_not be_empty
|
73
|
+
@urss_rss.entries.all?{|entry| entry.should be_an_instance_of(Urss::Feed::Rss::Entry)}
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Feed::Atom do
|
4
|
+
|
5
|
+
describe "Instance Methods" do
|
6
|
+
describe "#entries" do
|
7
|
+
context "without entries" do
|
8
|
+
it "should return an empty array" do
|
9
|
+
subject.entries.should be_an_instance_of(Array)
|
10
|
+
subject.entries.should be_empty
|
11
|
+
end
|
12
|
+
end
|
13
|
+
context "with entries" do
|
14
|
+
before do
|
15
|
+
nokogiri = Nokogiri::XML(open(File.join(File.dirname(__FILE__), "..", "support", "fixtures", "atom.xml")))
|
16
|
+
@urss_rss = Urss::Feed::Atom.build(nokogiri.xpath("//xmlns:feed"), "xmlns:", "feed")
|
17
|
+
end
|
18
|
+
it "should return an array of Urss::Entry" do
|
19
|
+
@urss_rss.entries.should be_an_instance_of(Array)
|
20
|
+
@urss_rss.entries.should_not be_empty
|
21
|
+
@urss_rss.entries.all?{|entry| entry.should be_an_instance_of(Urss::Feed::Atom::Entry)}
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Feed do
|
4
|
+
|
5
|
+
describe "Attributes" do
|
6
|
+
it "should have an attribute :title" do
|
7
|
+
subject.should respond_to(:title)
|
8
|
+
subject.should respond_to(:title=)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should have an attribute :url" do
|
12
|
+
subject.should respond_to(:url)
|
13
|
+
subject.should respond_to(:url=)
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should have an attribute :description" do
|
17
|
+
subject.should respond_to(:description)
|
18
|
+
subject.should respond_to(:description=)
|
19
|
+
end
|
20
|
+
|
21
|
+
it "should have an attribute :updated_at" do
|
22
|
+
subject.should respond_to(:updated_at)
|
23
|
+
subject.should respond_to(:updated_at=)
|
24
|
+
end
|
25
|
+
|
26
|
+
it "should have an attribute :entries" do
|
27
|
+
subject.should respond_to(:entries)
|
28
|
+
subject.should respond_to(:entries=)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Media do
|
4
|
+
|
5
|
+
describe "Attributes" do
|
6
|
+
it "should have an attribute :content_url" do
|
7
|
+
subject.should respond_to(:content_url)
|
8
|
+
subject.should respond_to(:content_url=)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should have an attribute :title" do
|
12
|
+
subject.should respond_to(:title)
|
13
|
+
subject.should respond_to(:title=)
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should have an attribute :thumbnail_url" do
|
17
|
+
subject.should respond_to(:thumbnail_url)
|
18
|
+
subject.should respond_to(:thumbnail_url=)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
describe "Instance methods" do
|
23
|
+
describe "#update" do
|
24
|
+
it "should raise an Urss::NotANokogiriInstance exception when passing something different than a Nokogiri::XML::Element instance" do
|
25
|
+
lambda {
|
26
|
+
subject.update("I'm not a Nokogiri::XML::Element instance")
|
27
|
+
}.should raise_error(Urss::NotANokogiriInstance)
|
28
|
+
end
|
29
|
+
it "should not raise an Urss::NotANokogiriInstance when passing a Nokogiri::XML::Element instance" do
|
30
|
+
lambda {
|
31
|
+
subject.update(Nokogiri::XML::Element.new("item", Nokogiri::XML::Document.new))
|
32
|
+
}.should_not raise_error(Urss::NotANokogiriInstance)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Urss::Rss do
|
4
|
+
|
5
|
+
describe "Class Methods" do
|
6
|
+
it "should respond to build" do
|
7
|
+
subject.class.should respond_to(:build)
|
8
|
+
end
|
9
|
+
describe "#build" do
|
10
|
+
describe "argument" do
|
11
|
+
it "should raise an Urss::NotANokogiriInstance exception when passing something different than a Nokogiri::XML::Document instance" do
|
12
|
+
lambda {
|
13
|
+
subject.class.build("I'm not a Nokogiri::XML::Document instance")
|
14
|
+
}.should raise_error(Urss::NotANokogiriInstance)
|
15
|
+
end
|
16
|
+
it "should not raise an Urss::NotANokogiriInstance when passing a Nokogiri::XML::Document instance" do
|
17
|
+
lambda {
|
18
|
+
subject.class.build(Nokogiri::XML::Document.new)
|
19
|
+
}.should_not raise_error
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
end
|
data/spec/urss_spec.rb
ADDED
@@ -0,0 +1,540 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require "spec_helper"
|
3
|
+
|
4
|
+
describe Urss do
|
5
|
+
|
6
|
+
it "should respond to at method" do
|
7
|
+
subject.should respond_to(:at)
|
8
|
+
end
|
9
|
+
describe "#at" do
|
10
|
+
describe "argument" do
|
11
|
+
context "when passing a string of a URL" do
|
12
|
+
it "should accept it" do
|
13
|
+
lambda {
|
14
|
+
subject.at("http://tech.rufy.com")
|
15
|
+
}.should_not raise_error
|
16
|
+
end
|
17
|
+
end
|
18
|
+
context "when passing an empty string" do
|
19
|
+
it "should raise an ArgumentError" do
|
20
|
+
lambda {
|
21
|
+
subject.at("")
|
22
|
+
}.should raise_error(ArgumentError)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
context "when passing nil" do
|
26
|
+
it "should raise an ArgumentError" do
|
27
|
+
lambda {
|
28
|
+
subject.at(nil)
|
29
|
+
}.should raise_error(ArgumentError)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
context "when passing a Fixnum" do
|
33
|
+
it "should raise an ArgumentError" do
|
34
|
+
lambda {
|
35
|
+
subject.at(1)
|
36
|
+
}.should raise_error(ArgumentError)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
context "when passing a Hash" do
|
40
|
+
it "should raise an ArgumentError" do
|
41
|
+
lambda {
|
42
|
+
subject.at({})
|
43
|
+
}.should raise_error(ArgumentError)
|
44
|
+
end
|
45
|
+
end
|
46
|
+
context "when passing a Array" do
|
47
|
+
it "should raise an ArgumentError" do
|
48
|
+
lambda {
|
49
|
+
subject.at([])
|
50
|
+
}.should raise_error(ArgumentError)
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
context "RSS 0.9" do
|
56
|
+
context "when parsing the rss09.xml example file at http://slashdot.org/" do
|
57
|
+
before { @parsed_rss = subject.at("http://slashdot.org/") }
|
58
|
+
it "should return an instance of Urss::Feed::Rss" do
|
59
|
+
@parsed_rss.should be_an_instance_of(Urss::Feed::Rss)
|
60
|
+
end
|
61
|
+
describe "Urss::Rss" do
|
62
|
+
describe "title" do
|
63
|
+
it "should return \"Slashdot\"" do
|
64
|
+
@parsed_rss.title.should == "Slashdot"
|
65
|
+
end
|
66
|
+
end
|
67
|
+
describe "url" do
|
68
|
+
it "should return \"http://slashdot.org/\"" do
|
69
|
+
@parsed_rss.url.should == "http://slashdot.org/"
|
70
|
+
end
|
71
|
+
end
|
72
|
+
describe "description" do
|
73
|
+
it "should return \"News for nerds, stuff that matters\"" do
|
74
|
+
@parsed_rss.description.should == "News for nerds, stuff that matters"
|
75
|
+
end
|
76
|
+
end
|
77
|
+
describe "updated_at" do
|
78
|
+
it "should return \"2005-09-09T02:52:31-07:00\"" do
|
79
|
+
@parsed_rss.updated_at.should == "2005-09-09T02:52:31-07:00"
|
80
|
+
end
|
81
|
+
end
|
82
|
+
describe"entries" do
|
83
|
+
describe "size" do
|
84
|
+
it "should be 10" do
|
85
|
+
@parsed_rss.entries.size.should be 10
|
86
|
+
end
|
87
|
+
end
|
88
|
+
describe "first" do
|
89
|
+
before { @first_parsed_rss = @parsed_rss.entries.first }
|
90
|
+
describe "title" do
|
91
|
+
it "should return \"JBoss - A Developer's Notebook\"" do
|
92
|
+
@first_parsed_rss.title.should == "JBoss - A Developer's Notebook"
|
93
|
+
end
|
94
|
+
end
|
95
|
+
describe "url" do
|
96
|
+
it "should return \"http://books.slashdot.org/article.pl?sid=05/08/29/1319236&from=rss\"" do
|
97
|
+
@first_parsed_rss.url.should == "http://books.slashdot.org/article.pl?sid=05/08/29/1319236&from=rss"
|
98
|
+
end
|
99
|
+
end
|
100
|
+
describe "comments_url" do
|
101
|
+
it "should be empty" do
|
102
|
+
@first_parsed_rss.comments_url.should be_empty
|
103
|
+
end
|
104
|
+
end
|
105
|
+
describe "created_at" do
|
106
|
+
it "should return \"2005-09-09T02:52:31-07:00\"" do
|
107
|
+
@first_parsed_rss.created_at.should == "2005-09-09T02:52:31-07:00"
|
108
|
+
end
|
109
|
+
end
|
110
|
+
describe "author" do
|
111
|
+
it "should be empty" do
|
112
|
+
@first_parsed_rss.author.should be_empty
|
113
|
+
end
|
114
|
+
end
|
115
|
+
describe "categories" do
|
116
|
+
it "should be empty" do
|
117
|
+
@first_parsed_rss.categories.should be_empty
|
118
|
+
end
|
119
|
+
end
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
context "RSS 2.0" do
|
127
|
+
context "without media" do
|
128
|
+
context "when parsing the rss20.xml example file at http://tech.rufy.com" do
|
129
|
+
before { @parsed_rss = subject.at("http://tech.rufy.com") }
|
130
|
+
it "should return an instance of Urss::Feed::Rss" do
|
131
|
+
@parsed_rss.should be_an_instance_of(Urss::Feed::Rss)
|
132
|
+
end
|
133
|
+
describe "Urss::Rss" do
|
134
|
+
describe "title" do
|
135
|
+
it "should return \"Technoblog\"" do
|
136
|
+
@parsed_rss.title.should == "Technoblog"
|
137
|
+
end
|
138
|
+
end
|
139
|
+
describe "url" do
|
140
|
+
it "should return \"http://tech.rufy.com\"" do
|
141
|
+
@parsed_rss.url.should == "http://tech.rufy.com"
|
142
|
+
end
|
143
|
+
end
|
144
|
+
describe "description" do
|
145
|
+
it "should return \"Lucas Carlson's jounal of the technical ramblings. Contains tutorials, howto's, and rants and ravings.\"" do
|
146
|
+
@parsed_rss.description.should == "Lucas Carlson's jounal of the technical ramblings. Contains tutorials, howto's, and rants and ravings."
|
147
|
+
end
|
148
|
+
end
|
149
|
+
describe "updated_at" do
|
150
|
+
it "should return \"Thu, 25 Aug 2005 00:16:16 +0000\"" do
|
151
|
+
@parsed_rss.updated_at.should == "Thu, 25 Aug 2005 00:16:16 +0000"
|
152
|
+
end
|
153
|
+
end
|
154
|
+
describe"entries" do
|
155
|
+
describe "size" do
|
156
|
+
it "should be 10" do
|
157
|
+
@parsed_rss.entries.size.should be 10
|
158
|
+
end
|
159
|
+
end
|
160
|
+
describe "first" do
|
161
|
+
before { @first_parsed_rss = @parsed_rss.entries.first }
|
162
|
+
describe "title" do
|
163
|
+
it "should return \"some_string.starts_with? “Foo” || some_string.ends_with? “bar.”\"" do
|
164
|
+
@first_parsed_rss.title.should == "some_string.starts_with? “Foo” || some_string.ends_with? “bar.”"
|
165
|
+
end
|
166
|
+
end
|
167
|
+
describe "url" do
|
168
|
+
it "should return \"http://feeds.feedburner.com/rufytech?m=68\"" do
|
169
|
+
@first_parsed_rss.url.should == "http://feeds.feedburner.com/rufytech?m=68"
|
170
|
+
end
|
171
|
+
end
|
172
|
+
describe "comments_url" do
|
173
|
+
it "should return \"http://tech.rufy.com/entry/82#comments\"" do
|
174
|
+
@first_parsed_rss.comments_url.should == "http://tech.rufy.com/entry/82#comments"
|
175
|
+
end
|
176
|
+
end
|
177
|
+
describe "created_at" do
|
178
|
+
it "should return \"Wed, 24 Aug 2005 13:33:34 +0000\"" do
|
179
|
+
@first_parsed_rss.created_at.should == "Wed, 24 Aug 2005 13:33:34 +0000"
|
180
|
+
end
|
181
|
+
end
|
182
|
+
describe "author" do
|
183
|
+
it "should return \"Lucas Carlson\"" do
|
184
|
+
@first_parsed_rss.author.should == "Lucas Carlson"
|
185
|
+
end
|
186
|
+
end
|
187
|
+
describe "categories" do
|
188
|
+
it "should return \"Programming, Ruby\"" do
|
189
|
+
@first_parsed_rss.categories.should == "Programming, Ruby"
|
190
|
+
end
|
191
|
+
end
|
192
|
+
describe "content" do
|
193
|
+
it "should return the description content" do
|
194
|
+
@first_parsed_rss.content.should ==
|
195
|
+
"""I also liked:
|
196
|
+
|
197
|
+
|
198
|
+
x = s.startswith('Go')
|
199
|
+
x = s.endswith('Go')
|
200
|
+
|
201
|
+
|
202
|
+
So I made:
|
203
|
+
|
204
|
+
|
205
|
+
class String
|
206
|
+
def starts_with?(str)
|
207
|
+
self.index( str ) == 0
|
208
|
+
end
|
209
|
+
|
210
|
+
def ends_with?(str)
|
211
|
+
self.rindex( str ) == self.length - str.length
|
212
|
+
end
|
213
|
+
end
|
214
|
+
|
215
|
+
|
216
|
+
So you can do this:
|
217
|
+
|
218
|
+
|
219
|
+
some_string.starts_with? 'Foo' || some_string.ends_with? 'bar.'"""
|
220
|
+
end
|
221
|
+
end
|
222
|
+
end
|
223
|
+
describe "last" do
|
224
|
+
before { @last_parsed_rss = @parsed_rss.entries.last }
|
225
|
+
describe "title" do
|
226
|
+
it "should return \"A wish: Abolition of passing data with flags and symbol-like options when calling Unix programs\"" do
|
227
|
+
@last_parsed_rss.title.should == "A wish: Abolition of passing data with flags and symbol-like options when calling Unix programs"
|
228
|
+
end
|
229
|
+
end
|
230
|
+
describe "url" do
|
231
|
+
it "should return \"http://feeds.feedburner.com/rufytech?m=59\"" do
|
232
|
+
@last_parsed_rss.url.should == "http://feeds.feedburner.com/rufytech?m=59"
|
233
|
+
end
|
234
|
+
end
|
235
|
+
describe "comments_url" do
|
236
|
+
it "should return \"http://tech.rufy.com/entry/73#comments\"" do
|
237
|
+
@last_parsed_rss.comments_url.should == "http://tech.rufy.com/entry/73#comments"
|
238
|
+
end
|
239
|
+
end
|
240
|
+
describe "created_at" do
|
241
|
+
it "should return \"Tue, 19 Jul 2005 00:16:03 +0000\"" do
|
242
|
+
@last_parsed_rss.created_at.should == "Tue, 19 Jul 2005 00:16:03 +0000"
|
243
|
+
end
|
244
|
+
end
|
245
|
+
describe "author" do
|
246
|
+
it "should return \"Lucas Carlson\"" do
|
247
|
+
@last_parsed_rss.author.should == "Lucas Carlson"
|
248
|
+
end
|
249
|
+
end
|
250
|
+
describe "categories" do
|
251
|
+
it "should return \"Programming, Ruby\"" do
|
252
|
+
@last_parsed_rss.categories.should == "General"
|
253
|
+
end
|
254
|
+
end
|
255
|
+
describe "content" do
|
256
|
+
it "should return the description content" do
|
257
|
+
@last_parsed_rss.content.should ==
|
258
|
+
"""I wish I could call every program on the command line like this:
|
259
|
+
|
260
|
+
mysql -v :user foo :password bar :host rufy.com :port 3306
|
261
|
+
|
262
|
+
For me, this is much easier to type than what I would currently need to do:
|
263
|
+
|
264
|
+
mysql -v --user foo --password bar --host rufy.com --port 3306
|
265
|
+
|
266
|
+
The difference between -- and : is huge for me [...]"""
|
267
|
+
end
|
268
|
+
end
|
269
|
+
end
|
270
|
+
end
|
271
|
+
end
|
272
|
+
end
|
273
|
+
end
|
274
|
+
context "with media" do
|
275
|
+
context "when parsing the media_rss.xml example file at http://www.flickr.com/photos/herval/" do
|
276
|
+
before { @parsed_rss = subject.at("http://www.flickr.com/photos/herval/") }
|
277
|
+
it "should return an instance of Urss::Feed::Rss" do
|
278
|
+
@parsed_rss.should be_an_instance_of(Urss::Feed::Rss)
|
279
|
+
end
|
280
|
+
describe "Urss::Rss" do
|
281
|
+
describe "title" do
|
282
|
+
it "should return \"Uploads from herval\"" do
|
283
|
+
@parsed_rss.title.should == "Uploads from herval"
|
284
|
+
end
|
285
|
+
end
|
286
|
+
describe"entries" do
|
287
|
+
describe "size" do
|
288
|
+
it "should be 20" do
|
289
|
+
@parsed_rss.entries.size.should be 20
|
290
|
+
end
|
291
|
+
end
|
292
|
+
describe "first" do
|
293
|
+
before { @first_parsed_rss = @parsed_rss.entries.first }
|
294
|
+
describe "title" do
|
295
|
+
it "should return \"Woof?\"" do
|
296
|
+
@first_parsed_rss.title.should == "Woof?"
|
297
|
+
end
|
298
|
+
end
|
299
|
+
describe "medias" do
|
300
|
+
describe "size" do
|
301
|
+
it "should be 1" do
|
302
|
+
@first_parsed_rss.medias.size.should be 1
|
303
|
+
end
|
304
|
+
end
|
305
|
+
describe "first" do
|
306
|
+
before { @first_parsed_rss_first_media = @first_parsed_rss.medias.first }
|
307
|
+
describe "title" do
|
308
|
+
it "should return \"Woof?\"" do
|
309
|
+
@first_parsed_rss_first_media.title.should == "Woof?"
|
310
|
+
end
|
311
|
+
end
|
312
|
+
describe "content_url" do
|
313
|
+
it "should return \"http://farm5.static.flickr.com/4040/4671960608_10cb945d5c_o.jpg\"" do
|
314
|
+
@first_parsed_rss_first_media.content_url.should == "http://farm5.static.flickr.com/4040/4671960608_10cb945d5c_o.jpg"
|
315
|
+
end
|
316
|
+
end
|
317
|
+
describe "thumbnail_url" do
|
318
|
+
it "should return \"http://farm5.static.flickr.com/4040/4671960608_954d2297bc_s.jpg\"" do
|
319
|
+
@first_parsed_rss_first_media.thumbnail_url.should == "http://farm5.static.flickr.com/4040/4671960608_954d2297bc_s.jpg"
|
320
|
+
end
|
321
|
+
end
|
322
|
+
end
|
323
|
+
end
|
324
|
+
end
|
325
|
+
end
|
326
|
+
end
|
327
|
+
end
|
328
|
+
context "when parsing the wax.rss example file at http://waxluxembourg.com/feed/" do
|
329
|
+
before { @parsed_rss = subject.at("http://waxluxembourg.com/feed/") }
|
330
|
+
it "should return an instance of Urss::Feed::Rss" do
|
331
|
+
@parsed_rss.should be_an_instance_of(Urss::Feed::Rss)
|
332
|
+
end
|
333
|
+
describe "Urss::Rss" do
|
334
|
+
describe "title" do
|
335
|
+
it "should be empty" do
|
336
|
+
@parsed_rss.title.should be_empty
|
337
|
+
end
|
338
|
+
end
|
339
|
+
describe"entries" do
|
340
|
+
describe "size" do
|
341
|
+
it "should be 15" do
|
342
|
+
@parsed_rss.entries.size.should be 15
|
343
|
+
end
|
344
|
+
end
|
345
|
+
describe "first" do
|
346
|
+
before { @first_parsed_rss = @parsed_rss.entries.first }
|
347
|
+
describe "title" do
|
348
|
+
it "should return \"THEFT SOUND lancent leur premier single (+ BONUS NOISE Launch)\"" do
|
349
|
+
@first_parsed_rss.title.should == "THEFT SOUND lancent leur premier single (+ BONUS NOISE Launch)"
|
350
|
+
end
|
351
|
+
end
|
352
|
+
describe "medias" do
|
353
|
+
describe "size" do
|
354
|
+
it "should be 3" do
|
355
|
+
@first_parsed_rss.medias.size.should be 3
|
356
|
+
end
|
357
|
+
end
|
358
|
+
describe "first" do
|
359
|
+
before { @first_parsed_rss_first_media = @first_parsed_rss.medias.first }
|
360
|
+
describe "title" do
|
361
|
+
it "should return \"waxluxembourg\"" do
|
362
|
+
@first_parsed_rss_first_media.title.should == "waxluxembourg"
|
363
|
+
end
|
364
|
+
end
|
365
|
+
describe "content_url" do
|
366
|
+
it "should return \"http://0.gravatar.com/avatar/634d08c41b3cc7c64c1a09ed707d4555?s=96&d=identicon&r=G\"" do
|
367
|
+
@first_parsed_rss_first_media.content_url.should == "http://0.gravatar.com/avatar/634d08c41b3cc7c64c1a09ed707d4555?s=96&d=identicon&r=G"
|
368
|
+
end
|
369
|
+
end
|
370
|
+
describe "thumbnail_url" do
|
371
|
+
it "should be nil" do
|
372
|
+
@first_parsed_rss_first_media.thumbnail_url.should be_nil
|
373
|
+
end
|
374
|
+
end
|
375
|
+
end
|
376
|
+
describe "second" do
|
377
|
+
before { @first_parsed_rss_second_media = @first_parsed_rss.medias[1] }
|
378
|
+
describe "title" do
|
379
|
+
it "should return \"THEFT SOUND\"" do
|
380
|
+
@first_parsed_rss_second_media.title.should == "THEFT SOUND"
|
381
|
+
end
|
382
|
+
end
|
383
|
+
describe "content_url" do
|
384
|
+
it "should return \"http://waxluxembourg.files.wordpress.com/2012/04/551557_356816914364777_274950432551426_1019108_1284055009_n.jpg\"" do
|
385
|
+
@first_parsed_rss_second_media.content_url.should == "http://waxluxembourg.files.wordpress.com/2012/04/551557_356816914364777_274950432551426_1019108_1284055009_n.jpg"
|
386
|
+
end
|
387
|
+
end
|
388
|
+
describe "thumbnail_url" do
|
389
|
+
it "should be nil" do
|
390
|
+
@first_parsed_rss_second_media.thumbnail_url.should be_nil
|
391
|
+
end
|
392
|
+
end
|
393
|
+
end
|
394
|
+
describe "last" do
|
395
|
+
before { @first_parsed_rss_last_media = @first_parsed_rss.medias.last }
|
396
|
+
describe "title" do
|
397
|
+
it "should return \"533064_10150700559083071_504538070_9376611_944848102_n\"" do
|
398
|
+
@first_parsed_rss_last_media.title.should == "533064_10150700559083071_504538070_9376611_944848102_n"
|
399
|
+
end
|
400
|
+
end
|
401
|
+
describe "content_url" do
|
402
|
+
it "should return \"http://waxluxembourg.files.wordpress.com/2012/04/533064_10150700559083071_504538070_9376611_944848102_n.jpg?w=212\"" do
|
403
|
+
@first_parsed_rss_last_media.content_url.should == "http://waxluxembourg.files.wordpress.com/2012/04/533064_10150700559083071_504538070_9376611_944848102_n.jpg?w=212"
|
404
|
+
end
|
405
|
+
end
|
406
|
+
describe "thumbnail_url" do
|
407
|
+
it "should be nil" do
|
408
|
+
@first_parsed_rss_last_media.thumbnail_url.should be_nil
|
409
|
+
end
|
410
|
+
end
|
411
|
+
end
|
412
|
+
end
|
413
|
+
end
|
414
|
+
end
|
415
|
+
end
|
416
|
+
end
|
417
|
+
end
|
418
|
+
end
|
419
|
+
|
420
|
+
context "Atom" do
|
421
|
+
context "when parsing the atom.xml example file at http://example.org/feed.atom" do
|
422
|
+
before { @parsed_rss = subject.at("http://example.org/feed.atom") }
|
423
|
+
it "should return an instance of Urss::Feed::Atom" do
|
424
|
+
@parsed_rss.should be_an_instance_of(Urss::Feed::Atom)
|
425
|
+
end
|
426
|
+
describe "Urss::Rss" do
|
427
|
+
describe "title" do
|
428
|
+
it "should return \"dive into mark\"" do
|
429
|
+
@parsed_rss.title.should == "dive into mark"
|
430
|
+
end
|
431
|
+
end
|
432
|
+
describe "url" do
|
433
|
+
it "should return \"http://example.org/feed.atom\"" do
|
434
|
+
@parsed_rss.url.should == "http://example.org/feed.atom"
|
435
|
+
end
|
436
|
+
end
|
437
|
+
describe "description" do
|
438
|
+
it "should return \"A emlot/em of effort\n went into making this effortless\"" do
|
439
|
+
@parsed_rss.description.should == "A emlot/em of effort\n went into making this effortless"
|
440
|
+
end
|
441
|
+
end
|
442
|
+
describe "updated_at" do
|
443
|
+
it "should return \"2005-07-31T12:29:29Z\"" do
|
444
|
+
@parsed_rss.updated_at.should == "2005-07-31T12:29:29Z"
|
445
|
+
end
|
446
|
+
end
|
447
|
+
describe"entries" do
|
448
|
+
describe "size" do
|
449
|
+
it "should be 1" do
|
450
|
+
@parsed_rss.entries.size.should be 1
|
451
|
+
end
|
452
|
+
end
|
453
|
+
describe "first" do
|
454
|
+
before { @first_parsed_rss = @parsed_rss.entries.first }
|
455
|
+
describe "title" do
|
456
|
+
it "should return \"Atom draft-07 snapshot\"" do
|
457
|
+
@first_parsed_rss.title.should == "Atom draft-07 snapshot"
|
458
|
+
end
|
459
|
+
end
|
460
|
+
describe "url" do
|
461
|
+
it "should return \"http://example.org/2005/04/02/atom\"" do
|
462
|
+
@first_parsed_rss.url.should == "http://example.org/2005/04/02/atom"
|
463
|
+
end
|
464
|
+
end
|
465
|
+
describe "comments_url" do
|
466
|
+
it "should be empty" do
|
467
|
+
@first_parsed_rss.comments_url.should be_nil
|
468
|
+
end
|
469
|
+
end
|
470
|
+
describe "created_at" do
|
471
|
+
it "should return \"2003-12-13T08:29:29-04:00\"" do
|
472
|
+
@first_parsed_rss.created_at.should == "2003-12-13T08:29:29-04:00"
|
473
|
+
end
|
474
|
+
end
|
475
|
+
describe "author" do
|
476
|
+
it "should return \"Mark Pilgrim\"" do
|
477
|
+
@first_parsed_rss.author.should == "Mark Pilgrim"
|
478
|
+
end
|
479
|
+
end
|
480
|
+
describe "categories" do
|
481
|
+
it "should be empty" do
|
482
|
+
@first_parsed_rss.categories.should be_empty
|
483
|
+
end
|
484
|
+
end
|
485
|
+
end
|
486
|
+
end
|
487
|
+
end
|
488
|
+
end
|
489
|
+
end
|
490
|
+
end
|
491
|
+
|
492
|
+
describe "check README.md example" do
|
493
|
+
it "should not failed! =)" do
|
494
|
+
rss = Urss.at("http://www.ruby-lang.org/en/feeds/news.rss")
|
495
|
+
rss.title.should == "Ruby News"
|
496
|
+
rss.url.should == "http://www.ruby-lang.org/en/feeds/news.rss/"
|
497
|
+
rss.description.should == "The latest news from Ruby-Lang.org."
|
498
|
+
rss.updated_at.should be_empty
|
499
|
+
rss.entries.size.should be 10
|
500
|
+
rss.entries.first.title.should == "Ruby 1.9.3-p194 is released"
|
501
|
+
rss.entries.first.created_at.should == "Fri, 20 Apr 2012 03:19:04 GMT"
|
502
|
+
rss.entries.first.url.should == "http://www.ruby-lang.org/en/news/2012/04/20/ruby-1-9-3-p194-is-released/"
|
503
|
+
rss.entries.first.content.should ==
|
504
|
+
"""<p>Ruby 1.9.3-p194 is released.</p><p>This release include Security Fix for RubyGems: SSL server verification failure for remote repository.
|
505
|
+
And many bugs are fixed in this release.</p> <h2><a name=\"label-0\" id=\"label-0\">Security Fix for RubyGems: SSL server verification failure for remote repository</a></h2><!-- RDLabel: \"Security Fix for RubyGems: SSL server verification failure for remote repository\" --><p>This release includes two security fixes in RubyGems.</p><ul>
|
506
|
+
<li>Turn on verification of server SSL certs</li>
|
507
|
+
<li>Disallow redirects from https to http</li>
|
508
|
+
</ul><p>Users who uses https source in .gemrc or /etc/gemrc are encouraged to
|
509
|
+
upgrade to 1.9.3-p194.</p><p>Following is excerpted from RubyGems 1.8.23 release note [1].</p><p>\"This release increases the security used when RubyGems is talking to
|
510
|
+
an https server. If you use a custom RubyGems server over SSL, this
|
511
|
+
release will cause RubyGems to no longer connect unless your SSL cert
|
512
|
+
is globally valid.</p><p>You can configure SSL certificate usage in RubyGems through the :ssl_ca_cert and :ssl_verify_mode options in ~/.gemrc and /etc/gemrc.
|
513
|
+
The recommended way is to set :ssl_ca_cert to the CA certificate for
|
514
|
+
your server or a certificate bundle containing your CA certification.</p><p>You may also set :ssl_verify_mode to 0 to completely disable SSL
|
515
|
+
certificate checks, but this is not recommended.\"</p><p>Credit to John Firebaugh for reporting this issue.</p><p>[1] <a href=\"https://github.com/rubygems/rubygems/blob/1.8/History.txt\"><URL:https://github.com/rubygems/rubygems/blob/1.8/History.txt></a></p><h2><a name=\"label-1\" id=\"label-1\">Fixes</a></h2><!-- RDLabel: \"Fixes\" --><ul>
|
516
|
+
<li>Security Fix for RubyGems: SSL server verification failure for remote repository</li>
|
517
|
+
<li>other bug fixes</li>
|
518
|
+
</ul><p>See <a href=\"https://bugs.ruby-lang.org/projects/ruby-193/issues?set_filter=1&status_id=5\">tickets</a> and <a href=\"http://svn.ruby-lang.org/repos/ruby/tags/v1_9_3_194/ChangeLog\">ChangeLog</a> for details.</p><h2><a name=\"label-2\" id=\"label-2\">Downloads</a></h2><!-- RDLabel: \"Downloads\" --><ul>
|
519
|
+
<li><a href=\"http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.tar.bz2\"><URL:http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.tar.bz2></a>
|
520
|
+
<ul>
|
521
|
+
<li>SIZE: 9841223 bytes</li>
|
522
|
+
<li>MD5: 2278eff4cfed3cbc0653bc73085caa34</li>
|
523
|
+
<li>SHA256: a9d1ea9eaea075c60048369a63b35b3b5a06a30aa214a3d990e0bb71212db8fa</li>
|
524
|
+
</ul></li>
|
525
|
+
<li><a href=\"http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.tar.gz\"><URL:http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.tar.gz></a>
|
526
|
+
<ul>
|
527
|
+
<li>SIZE: 12432239 bytes</li>
|
528
|
+
<li>MD5: bc0c715c69da4d1d8bd57069c19f6c0e</li>
|
529
|
+
<li>SHA256: 46e2fa80be7efed51bd9cdc529d1fe22ebc7567ee0f91db4ab855438cf4bd8bb</li>
|
530
|
+
</ul></li>
|
531
|
+
<li><a href=\"http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.zip\"><URL:http://ftp.ruby-lang.org/pub/ruby/1.9/ruby-1.9.3-p194.zip></a>
|
532
|
+
<ul>
|
533
|
+
<li>SIZE: 13898712 bytes</li>
|
534
|
+
<li>MD5: 77e67b15234e442d4a3dcc450bc70fea</li>
|
535
|
+
<li>SHA256: 77474cfb92385b3a0b4c346553048bc65bfe68d4f220128329671a0234cb124d</li>
|
536
|
+
</ul></li>
|
537
|
+
</ul>"""
|
538
|
+
end
|
539
|
+
end
|
540
|
+
end
|