feedparser 1.1.1 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Manifest.txt +36 -7
- data/README.md +145 -10
- data/Rakefile +1 -1
- data/lib/feedparser.rb +3 -0
- data/lib/feedparser/author.rb +39 -0
- data/lib/feedparser/builder/atom.rb +64 -17
- data/lib/feedparser/builder/json.rb +46 -10
- data/lib/feedparser/builder/rss.rb +94 -15
- data/lib/feedparser/feed.rb +30 -6
- data/lib/feedparser/generator.rb +34 -0
- data/lib/feedparser/item.rb +31 -6
- data/lib/feedparser/tag.rb +23 -0
- data/lib/feedparser/version.rb +2 -2
- data/test/feeds/books/nostarch.rss +125 -0
- data/test/feeds/books/oreilly.feedburner.atom +387 -0
- data/test/feeds/books/pragprog.rss +148 -0
- data/test/feeds/byparker.json +4 -4
- data/test/feeds/daringfireball.atom +8 -1
- data/test/feeds/daringfireball.json +28 -0
- data/test/feeds/googlegroups.atom +2 -2
- data/test/feeds/googlegroups2.atom +1 -1
- data/test/feeds/headius.atom +6 -5
- data/test/feeds/inessential.json +13 -4
- data/test/feeds/jsonfeed.json +8 -3
- data/test/feeds/{lambdatheultimate.rss2 → lambdatheultimate.rss} +0 -0
- data/test/feeds/{learnenough.atom → learnenough.feedburner.atom} +12 -9
- data/test/feeds/news/nytimes-blogs-bits.rss +333 -0
- data/test/feeds/news/nytimes-paul-krugman.rss +60 -0
- data/test/feeds/news/nytimes-tech.rss +653 -0
- data/test/feeds/news/nytimes-thomas-l-friedman.rss +80 -0
- data/test/feeds/news/nytimes.rss +607 -0
- data/test/feeds/news/washingtonpost-blogs-innovations.rss +183 -0
- data/test/feeds/news/washingtonpost-politics.rss +35 -0
- data/test/feeds/news/washingtonpost-world.rss +29 -0
- data/test/feeds/ongoing.atom +1619 -0
- data/test/feeds/osm/blog.openstreetmap.rss +252 -0
- data/test/feeds/osm/blogs.openstreetmap.rss +585 -0
- data/test/feeds/osm/mapbox.rss +1883 -0
- data/test/feeds/{railstutorial.atom → railstutorial.feedburner.atom} +28 -27
- data/test/feeds/{rubyflow.rss2 → rubyflow.feedburner.rss} +7 -3
- data/test/feeds/{rubymine.rss2 → rubymine.feedburner.rss} +5 -6
- data/test/feeds/scripting.rss +881 -0
- data/test/feeds/{sitepoint.rss2 → sitepoint.rss} +8 -9
- data/test/feeds/spec/atom/author.atom +48 -0
- data/test/feeds/spec/atom/authors.atom +70 -0
- data/test/feeds/spec/atom/categories.atom +66 -0
- data/test/feeds/spec/json/microblog.json +11 -2
- data/test/feeds/spec/json/tags.json +33 -0
- data/test/feeds/spec/rss/author.rss +41 -0
- data/test/feeds/spec/rss/categories.rss +64 -0
- data/test/feeds/spec/rss/creator.rss +38 -0
- data/test/feeds/{xkcd.rss2 → xkcd.rss} +0 -0
- data/test/helper.rb +21 -16
- data/test/test_atom.rb +1 -1
- data/test/test_atom_live.rb +1 -1
- data/test/test_authors.rb +26 -0
- data/test/test_books.rb +25 -0
- data/test/test_feeds.rb +4 -2
- data/test/test_rss.rb +4 -4
- data/test/test_tags.rb +25 -0
- metadata +39 -10
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 520ebca7dbff20c3347536869aa6dcfd87d68ddc
|
4
|
+
data.tar.gz: 5378e9fc3d8038ed61d085999fcb7d1ab3e1f041
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 40cc695312a0007da9e569fd05dd35d6621e08367248191eea645c77a93ed5e64c58c0febd9b9d5762177751b3e9c712adbcd52c1ec951e9125c085719f37734
|
7
|
+
data.tar.gz: 96fb8f2c92a83447cc5598b667a3a5036d66c93305b3a624a9f6081e4489b43f5bf37b51cc61959f0ad1a621bd6d1c456a514a1c501e7112179f00d6f1c55cfb
|
data/Manifest.txt
CHANGED
@@ -3,13 +3,19 @@ Manifest.txt
|
|
3
3
|
README.md
|
4
4
|
Rakefile
|
5
5
|
lib/feedparser.rb
|
6
|
+
lib/feedparser/author.rb
|
6
7
|
lib/feedparser/builder/atom.rb
|
7
8
|
lib/feedparser/builder/json.rb
|
8
9
|
lib/feedparser/builder/rss.rb
|
9
10
|
lib/feedparser/feed.rb
|
11
|
+
lib/feedparser/generator.rb
|
10
12
|
lib/feedparser/item.rb
|
11
13
|
lib/feedparser/parser.rb
|
14
|
+
lib/feedparser/tag.rb
|
12
15
|
lib/feedparser/version.rb
|
16
|
+
test/feeds/books/nostarch.rss
|
17
|
+
test/feeds/books/oreilly.feedburner.atom
|
18
|
+
test/feeds/books/pragprog.rss
|
13
19
|
test/feeds/byparker.json
|
14
20
|
test/feeds/daringfireball.atom
|
15
21
|
test/feeds/daringfireball.json
|
@@ -19,22 +25,45 @@ test/feeds/headius.atom
|
|
19
25
|
test/feeds/inessential.json
|
20
26
|
test/feeds/intertwingly.atom
|
21
27
|
test/feeds/jsonfeed.json
|
22
|
-
test/feeds/lambdatheultimate.
|
23
|
-
test/feeds/learnenough.atom
|
24
|
-
test/feeds/
|
25
|
-
test/feeds/
|
26
|
-
test/feeds/
|
28
|
+
test/feeds/lambdatheultimate.rss
|
29
|
+
test/feeds/learnenough.feedburner.atom
|
30
|
+
test/feeds/news/nytimes-blogs-bits.rss
|
31
|
+
test/feeds/news/nytimes-paul-krugman.rss
|
32
|
+
test/feeds/news/nytimes-tech.rss
|
33
|
+
test/feeds/news/nytimes-thomas-l-friedman.rss
|
34
|
+
test/feeds/news/nytimes.rss
|
35
|
+
test/feeds/news/washingtonpost-blogs-innovations.rss
|
36
|
+
test/feeds/news/washingtonpost-politics.rss
|
37
|
+
test/feeds/news/washingtonpost-world.rss
|
38
|
+
test/feeds/ongoing.atom
|
39
|
+
test/feeds/osm/blog.openstreetmap.rss
|
40
|
+
test/feeds/osm/blogs.openstreetmap.rss
|
41
|
+
test/feeds/osm/mapbox.rss
|
42
|
+
test/feeds/railstutorial.feedburner.atom
|
43
|
+
test/feeds/rubyflow.feedburner.rss
|
44
|
+
test/feeds/rubymine.feedburner.rss
|
27
45
|
test/feeds/rubyonrails.atom
|
28
|
-
test/feeds/
|
46
|
+
test/feeds/scripting.rss
|
47
|
+
test/feeds/sitepoint.rss
|
48
|
+
test/feeds/spec/atom/author.atom
|
49
|
+
test/feeds/spec/atom/authors.atom
|
50
|
+
test/feeds/spec/atom/categories.atom
|
29
51
|
test/feeds/spec/json/example.json
|
30
52
|
test/feeds/spec/json/microblog.json
|
53
|
+
test/feeds/spec/json/tags.json
|
54
|
+
test/feeds/spec/rss/author.rss
|
55
|
+
test/feeds/spec/rss/categories.rss
|
56
|
+
test/feeds/spec/rss/creator.rss
|
31
57
|
test/feeds/xkcd.atom
|
32
|
-
test/feeds/xkcd.
|
58
|
+
test/feeds/xkcd.rss
|
33
59
|
test/helper.rb
|
34
60
|
test/test_atom.rb
|
35
61
|
test/test_atom_live.rb
|
62
|
+
test/test_authors.rb
|
63
|
+
test/test_books.rb
|
36
64
|
test/test_dates.rb
|
37
65
|
test/test_feeds.rb
|
38
66
|
test/test_json.rb
|
39
67
|
test/test_rss.rb
|
40
68
|
test/test_rss_live.rb
|
69
|
+
test/test_tags.rb
|
data/README.md
CHANGED
@@ -11,14 +11,21 @@ feedparser gem - web feed parser and normalizer (Atom, RSS 2.0, JSON, etc.)
|
|
11
11
|
|
12
12
|
## What's News?
|
13
13
|
|
14
|
-
May/2017: Added support for reading feeds in the new [JSON Feed](https://jsonfeed.org) format in - surprise, surprise - JSON.
|
14
|
+
May/2017: Added support for reading feeds in the new [JSON Feed](https://jsonfeed.org) format in - surprise, surprise - JSON.
|
15
|
+
|
16
|
+
## What's a Web Feed?
|
17
|
+
|
18
|
+
See the [Awesome Feeds](https://github.com/statictimes/awesome-feeds) page ».
|
19
|
+
|
15
20
|
|
16
21
|
|
17
22
|
## Usage
|
18
23
|
|
24
|
+
|
19
25
|
### Structs
|
20
26
|
|
21
|
-
Feed • Item
|
27
|
+
Feed • Item • Author • Tag • Generator
|
28
|
+
|
22
29
|
|
23
30
|
![](feed-models.png)
|
24
31
|
|
@@ -30,7 +37,7 @@ Note: uses question mark (`?`) for optional elements (otherwise assume required
|
|
30
37
|
|
31
38
|
**Title 'n' Summary**
|
32
39
|
|
33
|
-
Note: The Feed parser will remove all html tags and attributes from the title (RSS 2.0+Atom),
|
40
|
+
Note: The Feed parser will remove all html tags and attributes from the title (RSS 2.0+Atom),
|
34
41
|
description (RSS 2.0) and subtitle (Atom) content and will unescape HTML entities e.g. `&` becomes & and so on - always
|
35
42
|
resulting in plain vanilla text.
|
36
43
|
|
@@ -47,7 +54,7 @@ resulting in plain vanilla text.
|
|
47
54
|
| `feed.updated` | `lastBuildDate`? | RFC-822 format | `updated` | ISO 801 format |
|
48
55
|
| `feed.published` | `pubDate`? | RFC-822 format | - | |
|
49
56
|
|
50
|
-
Note: Check - for RSS 2.0 set feed.updated to pubDate or lastBuildDate if only one present? if both present - map as above.
|
57
|
+
Note: Check - for RSS 2.0 set feed.updated to pubDate or lastBuildDate if only one present? if both present - map as above.
|
51
58
|
|
52
59
|
|
53
60
|
RFC-822 date format e.g. Wed, 14 Jan 2015 19:48:57 +0100
|
@@ -74,12 +81,14 @@ class Feed
|
|
74
81
|
end
|
75
82
|
```
|
76
83
|
|
84
|
+
(Source: [`lib/feedparser/feed.rb`](https://github.com/feedparser/feedparser/blob/master/lib/feedparser/feed.rb))
|
85
|
+
|
77
86
|
|
78
87
|
### `Item` Struct
|
79
88
|
|
80
89
|
**Title 'n' Summary**
|
81
90
|
|
82
|
-
Note: The Feed parser will remove all html tags and attributes from the title (RSS 2.0+Atom),
|
91
|
+
Note: The Feed parser will remove all html tags and attributes from the title (RSS 2.0+Atom),
|
83
92
|
description (RSS 2.0) and summary (Atom) content
|
84
93
|
and will unescape HTML entities e.g. `&` becomes & and so on - always
|
85
94
|
resulting in plain vanilla text.
|
@@ -98,7 +107,7 @@ Note: The content element will assume html content.
|
|
98
107
|
|
99
108
|
| Feed Struct | RSS 2.0 | Notes | Atom | Notes | JSON | Notes |
|
100
109
|
| ------------------ | ----------------- | ----------- | ------------- | ----------- | ----------------- | ----------- |
|
101
|
-
| `item.title` | `title` | plain text | `title` | plain text | `title`? | plain text |
|
110
|
+
| `item.title` | `title` | plain text | `title` | plain text | `title`? | plain text |
|
102
111
|
| `item.summary` | `description` | plain text | `summary`? | plain text | -tbd- | |
|
103
112
|
| `item.content` | `content`? | html | `content`? | html | `content_html (*)`| html |
|
104
113
|
|
@@ -129,6 +138,23 @@ class Item
|
|
129
138
|
end
|
130
139
|
```
|
131
140
|
|
141
|
+
(Source: [`lib/feedparser/item.rb`](https://github.com/feedparser/feedparser/blob/master/lib/feedparser/item.rb))
|
142
|
+
|
143
|
+
|
144
|
+
### `Author` Struct
|
145
|
+
|
146
|
+
(Source: [`lib/feedparser/author.rb`](https://github.com/feedparser/feedparser/blob/master/lib/feedparser/author.rb))
|
147
|
+
|
148
|
+
|
149
|
+
### `Tag` Struct
|
150
|
+
|
151
|
+
(Source: [`lib/feedparser/tag.rb`](https://github.com/feedparser/feedparser/blob/master/lib/feedparser/tag.rb))
|
152
|
+
|
153
|
+
### `Generator` Struct
|
154
|
+
|
155
|
+
(Source: [`lib/feedparser/generator.rb`](https://github.com/feedparser/feedparser/blob/master/lib/feedparser/generator.rb))
|
156
|
+
|
157
|
+
|
132
158
|
|
133
159
|
### Read Feed Example
|
134
160
|
|
@@ -136,22 +162,131 @@ end
|
|
136
162
|
require 'open-uri'
|
137
163
|
require 'feedparser'
|
138
164
|
|
139
|
-
txt = open( 'http://openfootball.github.io/
|
165
|
+
txt = open( 'http://openfootball.github.io/feed.xml' ).read
|
140
166
|
|
141
167
|
feed = FeedParser::Parser.parse( txt )
|
142
|
-
|
168
|
+
|
169
|
+
puts feed.title
|
170
|
+
# => "football.db - Open Football Data"
|
171
|
+
|
172
|
+
puts feed.url
|
173
|
+
# => "http://openfootball.github.io/"
|
174
|
+
|
175
|
+
puts feed.items[0].title
|
176
|
+
# => "football.db - League Quick Starter Sample - Mauritius Premier League - Create Your Own Repo/League(s) from Scratch"
|
177
|
+
|
178
|
+
puts feed.items[0].url
|
179
|
+
# => "http://openfootball.github.io/2015/08/30/league-quick-starter.html"
|
180
|
+
|
181
|
+
puts feed.items[0].updated
|
182
|
+
# => Sun, 30 Aug 2015 00:00:00 +0000
|
183
|
+
|
184
|
+
puts feed.items[0].content
|
185
|
+
# => "Added a new quick starter sample using the Mauritius Premier League to get you started..."
|
186
|
+
|
187
|
+
...
|
143
188
|
```
|
144
189
|
|
145
190
|
or reading a feed in the new [JSON Feed](https://jsonfeed.org) format in - surprise, surprise - JSON;
|
146
191
|
note: nothing changes :-)
|
147
192
|
|
148
193
|
```
|
149
|
-
txt = open( '
|
194
|
+
txt = open( 'http://openfootball.github.io/feed.json' ).read
|
150
195
|
|
151
196
|
feed = FeedParser::Parser.parse( txt )
|
152
|
-
|
197
|
+
|
198
|
+
puts feed.title
|
199
|
+
# => "football.db - Open Football Data"
|
200
|
+
|
201
|
+
puts feed.url
|
202
|
+
# => "http://openfootball.github.io/"
|
203
|
+
|
204
|
+
puts feed.items[0].title
|
205
|
+
# => "football.db - League Quick Starter Sample - Mauritius Premier League - Create Your Own Repo/League(s) from Scratch"
|
206
|
+
|
207
|
+
puts feed.items[0].url
|
208
|
+
# => "http://openfootball.github.io/2015/08/30/league-quick-starter.html"
|
209
|
+
|
210
|
+
puts feed.items[0].updated
|
211
|
+
# => Sun, 30 Aug 2015 00:00:00 +0000
|
212
|
+
|
213
|
+
puts feed.items[0].content_text
|
214
|
+
# => "Added a new quick starter sample using the Mauritius Premier League to get you started..."
|
215
|
+
|
216
|
+
...
|
153
217
|
```
|
154
218
|
|
219
|
+
## Samples
|
220
|
+
|
221
|
+
### Feed Reader
|
222
|
+
|
223
|
+
_Planet Feed Reader in 20 Lines of Ruby_
|
224
|
+
|
225
|
+
`planet.rb`:
|
226
|
+
|
227
|
+
``` ruby
|
228
|
+
require 'open-uri'
|
229
|
+
require 'feedparser'
|
230
|
+
require 'erb'
|
231
|
+
|
232
|
+
# step 1) read a list of web feeds
|
233
|
+
|
234
|
+
FEED_URLS = [
|
235
|
+
'http://vienna-rb.at/atom.xml',
|
236
|
+
'http://weblog.rubyonrails.org/feed/atom.xml',
|
237
|
+
'http://www.ruby-lang.org/en/feeds/news.rss',
|
238
|
+
'http://openfootball.github.io/feed.json',
|
239
|
+
]
|
240
|
+
|
241
|
+
items = []
|
242
|
+
|
243
|
+
FEED_URLS.each do |url|
|
244
|
+
feed = FeedParser::Parser.parse( open( url ).read )
|
245
|
+
items += feed.items
|
246
|
+
end
|
247
|
+
|
248
|
+
# step 2) mix up all postings in a new page
|
249
|
+
|
250
|
+
FEED_ITEM_TEMPLATE = <<EOS
|
251
|
+
<% items.each do |item| %>
|
252
|
+
<div class="item">
|
253
|
+
<h2><a href="<%= item.url %>"><%= item.title %></a></h2>
|
254
|
+
<div><%= item.content %></div>
|
255
|
+
</div>
|
256
|
+
<% end %>
|
257
|
+
EOS
|
258
|
+
|
259
|
+
puts ERB.new( FEED_ITEM_TEMPLATE ).result
|
260
|
+
```
|
261
|
+
|
262
|
+
Run the script:
|
263
|
+
|
264
|
+
```
|
265
|
+
$ ruby ./planet.rb
|
266
|
+
```
|
267
|
+
|
268
|
+
Prints:
|
269
|
+
|
270
|
+
```
|
271
|
+
<div class="item">
|
272
|
+
<h2><a href="http://vienna-rb.at/blog/2017/11/06/picks/">Picks / what the vienna.rb team thinks is worth sharing this week</a></h2>
|
273
|
+
<div>
|
274
|
+
<h3>6/11 Picks!!</h3>
|
275
|
+
<p>In a series on this website we'll entertain YOU with our picks...
|
276
|
+
...
|
277
|
+
```
|
278
|
+
|
279
|
+
## Real World Usage
|
280
|
+
|
281
|
+
See the Planet Pluto feed reader family:
|
282
|
+
|
283
|
+
- [Planet Pluto](https://github.com/feedreader) - static planet website generator
|
284
|
+
- [Planet Pluto Live](https://github.com/plutolive) - dynamic (live) planet web apps (using Sinatra, Rails, etc.)
|
285
|
+
|
286
|
+
|
287
|
+
Add your tools, scripts, apps here! Let us know.
|
288
|
+
|
289
|
+
|
155
290
|
|
156
291
|
## Install
|
157
292
|
|
data/Rakefile
CHANGED
@@ -8,7 +8,7 @@ Hoe.spec 'feedparser' do
|
|
8
8
|
self.summary = 'feedparser - web feed parser and normalizer (RSS 2.0, Atom, JSON, etc.)'
|
9
9
|
self.description = summary
|
10
10
|
|
11
|
-
self.urls = ['https://github.com/
|
11
|
+
self.urls = ['https://github.com/feedparser/feedparser']
|
12
12
|
|
13
13
|
self.author = 'Gerald Bauer'
|
14
14
|
self.email = 'wwwmake@googlegroups.com'
|
data/lib/feedparser.rb
CHANGED
@@ -0,0 +1,39 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
module FeedParser
|
4
|
+
|
5
|
+
class Author
|
6
|
+
|
7
|
+
attr_accessor :name
|
8
|
+
attr_accessor :url
|
9
|
+
## note: uri is an alias for url
|
10
|
+
alias :uri :url ## add atom alias for uri - why? why not?
|
11
|
+
alias :uri= :url=
|
12
|
+
|
13
|
+
def email?() @email.nil? == false; end
|
14
|
+
attr_accessor :email
|
15
|
+
|
16
|
+
def avatar?() @avatar.nil? == false; end
|
17
|
+
attr_accessor :avatar # todo/check: use avatar_url ?? used by json feed -check if always a url
|
18
|
+
|
19
|
+
|
20
|
+
## todo: add role - why? why not?
|
21
|
+
## e.g. add contributor (atom)
|
22
|
+
## or managingEditor (rss) or webMaster (rss) - why? why not??
|
23
|
+
|
24
|
+
attr_accessor :text # note: holds "unparsed" text (content) line form dc:creator or rss:author
|
25
|
+
|
26
|
+
|
27
|
+
def to_s
|
28
|
+
## note: to_s - allows to use just author in templates
|
29
|
+
## will by default return name if present or as fallback "unparsed" text line
|
30
|
+
if @name ## not blank
|
31
|
+
@name
|
32
|
+
else
|
33
|
+
@text
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
end # class Author
|
38
|
+
|
39
|
+
end # module FeedParser
|
@@ -22,7 +22,7 @@ class AtomFeedBuilder
|
|
22
22
|
|
23
23
|
|
24
24
|
|
25
|
-
def build_feed( atom_feed )
|
25
|
+
def build_feed( atom_feed ) ## fix/todo: rename atom_feed to atom or wire or xml or in ???
|
26
26
|
feed = Feed.new
|
27
27
|
feed.format = 'atom'
|
28
28
|
|
@@ -36,9 +36,8 @@ class AtomFeedBuilder
|
|
36
36
|
atom_feed.links.each_with_index do |link,i|
|
37
37
|
logger.debug " atom | feed.link[#{i+1}] rel=>#{link.rel}< : #{link.rel.class.name} type=>#{link.type}< href=>#{link.href}<"
|
38
38
|
|
39
|
-
if link.rel == 'self'
|
39
|
+
if feed.feed_url.nil? && link.rel == 'self'
|
40
40
|
feed.feed_url = link.href
|
41
|
-
break
|
42
41
|
end
|
43
42
|
end
|
44
43
|
|
@@ -74,18 +73,19 @@ class AtomFeedBuilder
|
|
74
73
|
end
|
75
74
|
|
76
75
|
|
77
|
-
if atom_feed.updated
|
78
|
-
feed.
|
76
|
+
if atom_feed.updated && atom_feed.updated.content ## note: content might be nil if <updated></updated> empty
|
77
|
+
feed.updated_local = handle_date( atom_feed.updated, 'feed.updated' )
|
78
|
+
feed.updated = feed.updated_local.utc
|
79
79
|
end
|
80
80
|
|
81
81
|
if atom_feed.generator
|
82
82
|
## Note: remove (strip) leading and trailing spaces and newlines
|
83
|
-
feed.generator = atom_feed.generator.content.strip
|
83
|
+
feed.generator.name = atom_feed.generator.content.strip
|
84
84
|
logger.debug " atom | feed.generator.content >#{atom_feed.generator.content}< : #{atom_feed.generator.content.class.name}"
|
85
85
|
|
86
86
|
# pp atom_feed.generator
|
87
|
-
feed.
|
88
|
-
feed.
|
87
|
+
feed.generator.version = atom_feed.generator.version
|
88
|
+
feed.generator.url = atom_feed.generator.uri
|
89
89
|
logger.debug " atom | feed.generator.version >#{atom_feed.generator.version}< : #{atom_feed.generator.version.class.name}"
|
90
90
|
logger.debug " atom | feed.generator.uri >#{atom_feed.generator.uri}< : #{atom_feed.generator.uri.class.name}"
|
91
91
|
end
|
@@ -95,17 +95,52 @@ class AtomFeedBuilder
|
|
95
95
|
end
|
96
96
|
|
97
97
|
|
98
|
-
|
98
|
+
## check for authors
|
99
|
+
atom_feed.authors.each do |atom_author|
|
100
|
+
feed.authors << build_author( atom_author )
|
101
|
+
end
|
102
|
+
|
103
|
+
## check for categories/tags
|
104
|
+
atom_feed.categories.each do |atom_cat|
|
105
|
+
feed.tags << build_tag( atom_cat )
|
106
|
+
end
|
107
|
+
|
108
|
+
|
99
109
|
atom_feed.items.each do |atom_item|
|
100
|
-
items <<
|
110
|
+
feed.items << build_item( atom_item )
|
101
111
|
end
|
102
|
-
feed.items = items
|
103
112
|
|
104
113
|
feed # return new feed
|
105
114
|
end # method build_feed_from_atom
|
106
115
|
|
107
116
|
|
108
|
-
def
|
117
|
+
def build_author( atom_author )
|
118
|
+
## pp atom_author
|
119
|
+
author = Author.new
|
120
|
+
|
121
|
+
## note: always strip leading n trailing spaces (from content)
|
122
|
+
author.name = atom_author.name.content.strip if atom_author.name
|
123
|
+
author.url = atom_author.uri.content.strip if atom_author.uri
|
124
|
+
author.email = atom_author.email.content.strip if atom_author.email
|
125
|
+
|
126
|
+
author
|
127
|
+
end # build_author
|
128
|
+
|
129
|
+
|
130
|
+
def build_tag( atom_cat )
|
131
|
+
## pp atom_cat
|
132
|
+
tag = Tag.new
|
133
|
+
|
134
|
+
## note: always strip leading n trailing spaces
|
135
|
+
## and add if preset (not blank/empty e.g. not nil or "")
|
136
|
+
tag.name = atom_cat.term.strip if atom_cat.term && !atom_cat.term.empty?
|
137
|
+
tag.scheme = atom_cat.scheme.strip if atom_cat.scheme && !atom_cat.scheme.empty?
|
138
|
+
|
139
|
+
tag
|
140
|
+
end # build_tag
|
141
|
+
|
142
|
+
|
143
|
+
def build_item( atom_item )
|
109
144
|
item = Item.new # Item.new
|
110
145
|
|
111
146
|
item.title = handle_content( atom_item.title, 'item.title' )
|
@@ -136,12 +171,14 @@ class AtomFeedBuilder
|
|
136
171
|
end
|
137
172
|
|
138
173
|
|
139
|
-
if atom_item.updated
|
140
|
-
item.
|
174
|
+
if atom_item.updated && atom_item.updated.content
|
175
|
+
item.updated_local = handle_date( atom_item.updated, 'item.updated' )
|
176
|
+
item.updated = item.updated_local.utc
|
141
177
|
end
|
142
178
|
|
143
|
-
if atom_item.published
|
144
|
-
item.
|
179
|
+
if atom_item.published && atom_item.published.content
|
180
|
+
item.published_local = handle_date( atom_item.published, 'item.published' )
|
181
|
+
item.published = item.published_local.utc
|
145
182
|
end
|
146
183
|
|
147
184
|
|
@@ -156,8 +193,18 @@ class AtomFeedBuilder
|
|
156
193
|
item.summary = handle_content( atom_item.summary, 'item.summary' )
|
157
194
|
end
|
158
195
|
|
196
|
+
## check for authors
|
197
|
+
atom_item.authors.each do |atom_author|
|
198
|
+
item.authors << build_author( atom_author )
|
199
|
+
end
|
200
|
+
|
201
|
+
## check for categories/tags
|
202
|
+
atom_item.categories.each do |atom_cat|
|
203
|
+
item.tags << build_tag( atom_cat )
|
204
|
+
end
|
205
|
+
|
159
206
|
item
|
160
|
-
end # method
|
207
|
+
end # method build_item
|
161
208
|
|
162
209
|
|
163
210
|
|