opmlparser 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CHANGELOG.md +4 -0
- data/Manifest.txt +11 -0
- data/README.md +259 -0
- data/Rakefile +28 -0
- data/lib/opmlparser.rb +175 -0
- data/lib/opmlparser/version.rb +20 -0
- data/test/helper.rb +7 -0
- data/test/outlines/category.opml.xml +9 -0
- data/test/outlines/places_lived.opml.xml +42 -0
- data/test/outlines/states.opml.xml +90 -0
- data/test/test_opml.rb +44 -0
- metadata +89 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 1455ca218d239221d91a9a7a6e7e0abeded5eec6
|
4
|
+
data.tar.gz: 7c0235eae9f9f68a4d265fc6e6201626d4fa8959
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: f195f8738c2982242ff251e31ec1595c3af4b1d00cde8d5c2141bf80dd93afb8b777c80e1dff62fe7f403526743a5569aac068d5dac487bcc7e1d5468294c171
|
7
|
+
data.tar.gz: 2eba54b6d6cd14b72b188ffbdd7e1bdc668bedc1a76e5de11a5006e99f8b08ac75a94e087f50a9b6f36a921ba896657b4b2688d5d11161d4ada6d45c5ac22316
|
data/CHANGELOG.md
ADDED
data/Manifest.txt
ADDED
data/README.md
ADDED
@@ -0,0 +1,259 @@
|
|
1
|
+
# opmlparser gem - read / parse outlines (incl. feed subscription lists) in the OPML (Outline Processor Markup Language) format in xml
|
2
|
+
|
3
|
+
|
4
|
+
* home :: [github.com/feedreader/pluto](https://github.com/feedreader/pluto)
|
5
|
+
* bugs :: [github.com/feedreader/pluto/issues](https://github.com/feedreader/pluto/issues)
|
6
|
+
* gem :: [rubygems.org/gems/opmlparser](https://rubygems.org/gems/opmlparser)
|
7
|
+
* rdoc :: [rubydoc.info/gems/opmlparser](http://rubydoc.info/gems/opmlparser)
|
8
|
+
* forum :: [groups.google.com/group/wwwmake](http://groups.google.com/group/wwwmake)
|
9
|
+
|
10
|
+
|
11
|
+
## Usage
|
12
|
+
|
13
|
+
`OPML.load` • `OPML.load_file`
|
14
|
+
|
15
|
+
|
16
|
+
Option 1) `OPML.load` - load from string. Example:
|
17
|
+
|
18
|
+
``` ruby
|
19
|
+
hash = OPML.load( <<TXT )
|
20
|
+
<opml version="1.1">
|
21
|
+
<head>
|
22
|
+
<title>Planet Ruby</title>
|
23
|
+
<dateCreated>Mon, 02 Mar 2020 08:21:56 -0000</dateCreated>
|
24
|
+
</head>
|
25
|
+
<body>
|
26
|
+
<outline text="Ruby Lang News" xmlUrl="http://www.ruby-lang.org/en/feeds/news.rss"/>
|
27
|
+
<outline text="JRuby Lang News" xmlUrl="http://www.jruby.org/atom.xml"/>
|
28
|
+
<outline text="RubyGems News" xmlUrl="http://blog.rubygems.org/atom.xml"/>
|
29
|
+
<outline text="Sinatra News" xmlUrl="http://sinatrarb.com/feed.xml"/>
|
30
|
+
<outline text="Hanami News" xmlUrl="https://hanamirb.org/atom.xml"/>
|
31
|
+
<outline text="Jekyll News" xmlUrl="http://jekyllrb.com/feed.xml"/>
|
32
|
+
</body>
|
33
|
+
</opml>
|
34
|
+
TXT
|
35
|
+
```
|
36
|
+
|
37
|
+
|
38
|
+
Option 2) `OPML.load_file` - load from file (shortcut). Example:
|
39
|
+
|
40
|
+
``` ruby
|
41
|
+
hash = OPML.load_file( './planet.opml.xml' )
|
42
|
+
```
|
43
|
+
|
44
|
+
|
45
|
+
All together now. Example:
|
46
|
+
|
47
|
+
``` ruby
|
48
|
+
require 'opmlparser'
|
49
|
+
|
50
|
+
xml = <<TXT
|
51
|
+
<opml version="1.1">
|
52
|
+
<head>
|
53
|
+
<title>Planet Ruby</title>
|
54
|
+
<dateCreated>Mon, 02 Mar 2020 08:21:56 -0000</dateCreated>
|
55
|
+
</head>
|
56
|
+
<body>
|
57
|
+
<outline text="Ruby Lang News" xmlUrl="http://www.ruby-lang.org/en/feeds/news.rss"/>
|
58
|
+
<outline text="JRuby Lang News" xmlUrl="http://www.jruby.org/atom.xml"/>
|
59
|
+
<outline text="RubyGems News" xmlUrl="http://blog.rubygems.org/atom.xml"/>
|
60
|
+
<outline text="Sinatra News" xmlUrl="http://sinatrarb.com/feed.xml"/>
|
61
|
+
<outline text="Hanami News" xmlUrl="https://hanamirb.org/atom.xml"/>
|
62
|
+
<outline text="Jekyll News" xmlUrl="http://jekyllrb.com/feed.xml"/>
|
63
|
+
</body>
|
64
|
+
</opml>
|
65
|
+
TXT
|
66
|
+
|
67
|
+
hash = OPML.load( xml )
|
68
|
+
pp hash
|
69
|
+
```
|
70
|
+
|
71
|
+
resulting in:
|
72
|
+
|
73
|
+
``` ruby
|
74
|
+
{"meta"=>
|
75
|
+
{"title"=>"Planet Ruby",
|
76
|
+
"dateCreated"=>"Mon, 02 Mar 2020 08:21:56 -0000"},
|
77
|
+
"outline"=>
|
78
|
+
[{"text"=>"Ruby Lang News", "xmlUrl"=>"http://www.ruby-lang.org/en/feeds/news.rss"},
|
79
|
+
{"text"=>"JRuby Lang News", "xmlUrl"=>"http://www.jruby.org/atom.xml"},
|
80
|
+
{"text"=>"RubyGems News", "xmlUrl"=>"http://blog.rubygems.org/atom.xml"},
|
81
|
+
{"text"=>"Sinatra News", "xmlUrl"=>"http://sinatrarb.com/feed.xml"},
|
82
|
+
{"text"=>"Hanami News", "xmlUrl"=>"https://hanamirb.org/atom.xml"},
|
83
|
+
{"text"=>"Jekyll News", "xmlUrl"=>"http://jekyllrb.com/feed.xml"}]}
|
84
|
+
```
|
85
|
+
|
86
|
+
to access use:
|
87
|
+
|
88
|
+
``` ruby
|
89
|
+
hash['meta']['title'] #=> "Planet Ruby"
|
90
|
+
hash['outline'][0]['text'] #=> "Ruby Lang News"
|
91
|
+
hash['outline'][0]['xmlUrl'] #=> "http://www.ruby-lang.org/en/feeds/news.rss"
|
92
|
+
hash['outline'][1]['text'] #=> "JRuby Lang News"
|
93
|
+
hash['outline'][1]['xmlUrl'] #=> "http://www.jruby.org/atom.xml"
|
94
|
+
```
|
95
|
+
|
96
|
+
|
97
|
+
What about using a "type-safe" outline struct(ure)?
|
98
|
+
|
99
|
+
`Outline.parse` • `Outline.read`
|
100
|
+
|
101
|
+
Option 1) `Outline.parse` - parse from string. Example:
|
102
|
+
|
103
|
+
``` ruby
|
104
|
+
outline = Outline.parse( <<TXT )
|
105
|
+
<opml version="1.1">
|
106
|
+
<head>
|
107
|
+
<title>Planet Ruby</title>
|
108
|
+
<dateCreated>Mon, 02 Mar 2020 08:21:56 -0000</dateCreated>
|
109
|
+
</head>
|
110
|
+
<body>
|
111
|
+
<outline text="Ruby Lang News" xmlUrl="http://www.ruby-lang.org/en/feeds/news.rss"/>
|
112
|
+
<outline text="JRuby Lang News" xmlUrl="http://www.jruby.org/atom.xml"/>
|
113
|
+
<outline text="RubyGems News" xmlUrl="http://blog.rubygems.org/atom.xml"/>
|
114
|
+
<outline text="Sinatra News" xmlUrl="http://sinatrarb.com/feed.xml"/>
|
115
|
+
<outline text="Hanami News" xmlUrl="https://hanamirb.org/atom.xml"/>
|
116
|
+
<outline text="Jekyll News" xmlUrl="http://jekyllrb.com/feed.xml"/>
|
117
|
+
</body>
|
118
|
+
</opml>
|
119
|
+
TXT
|
120
|
+
```
|
121
|
+
|
122
|
+
Option 2) `Outline.read` - read from file (shortcut). Example:
|
123
|
+
|
124
|
+
``` ruby
|
125
|
+
outline = Outline.read( './planet.opml.xml' )
|
126
|
+
```
|
127
|
+
|
128
|
+
to access use:
|
129
|
+
|
130
|
+
``` ruby
|
131
|
+
outline.meta.title #=> "Planet Ruby"
|
132
|
+
outline[0].text #=> "Ruby Lang News"
|
133
|
+
outline[0].xml_url #=> "http://www.ruby-lang.org/en/feeds/news.rss"
|
134
|
+
outline[1].text #=> "JRuby Lang News"
|
135
|
+
outline[1].xml_url #=> "http://www.jruby.org/atom.xml"
|
136
|
+
```
|
137
|
+
|
138
|
+
|
139
|
+
What about "non-flat" nested tree outlines?
|
140
|
+
|
141
|
+
Example - `states.opml.xml`:
|
142
|
+
|
143
|
+
``` xml
|
144
|
+
<opml version="2.0">
|
145
|
+
<head>
|
146
|
+
<title>states.opml</title>
|
147
|
+
<dateCreated>Tue, 15 Mar 2005 16:35:45 GMT</dateCreated>
|
148
|
+
<dateModified>Thu, 14 Jul 2005 23:41:05 GMT</dateModified>
|
149
|
+
<ownerName>Dave Winer</ownerName>
|
150
|
+
<ownerEmail>dave@scripting.com</ownerEmail>
|
151
|
+
</head>
|
152
|
+
<body>
|
153
|
+
<outline text="United States">
|
154
|
+
<outline text="Far West">
|
155
|
+
<outline text="Alaska"/>
|
156
|
+
<outline text="California"/>
|
157
|
+
<outline text="Hawaii"/>
|
158
|
+
<outline text="Nevada">
|
159
|
+
<outline text="Reno" created="Tue, 12 Jul 2005 23:56:35 GMT"/>
|
160
|
+
<outline text="Las Vegas" created="Tue, 12 Jul 2005 23:56:37 GMT"/>
|
161
|
+
<outline text="Ely" created="Tue, 12 Jul 2005 23:56:39 GMT"/>
|
162
|
+
<outline text="Gerlach" created="Tue, 12 Jul 2005 23:56:47 GMT"/>
|
163
|
+
</outline>
|
164
|
+
<outline text="Oregon"/>
|
165
|
+
<outline text="Washington"/>
|
166
|
+
</outline>
|
167
|
+
<outline text="Great Plains">
|
168
|
+
<outline text="Kansas"/>
|
169
|
+
<outline text="Nebraska"/>
|
170
|
+
<outline text="North Dakota"/>
|
171
|
+
<outline text="Oklahoma"/>
|
172
|
+
<outline text="South Dakota"/>
|
173
|
+
</outline>
|
174
|
+
<outline text="Mid-Atlantic">
|
175
|
+
<outline text="Delaware"/>
|
176
|
+
<outline text="Maryland"/>
|
177
|
+
<outline text="New Jersey"/>
|
178
|
+
<outline text="New York"/>
|
179
|
+
<outline text="Pennsylvania"/>
|
180
|
+
</outline>
|
181
|
+
<outline text="Midwest">
|
182
|
+
<outline text="Illinois"/>
|
183
|
+
<outline text="Indiana"/>
|
184
|
+
<outline text="Iowa"/>
|
185
|
+
<outline text="Kentucky"/>
|
186
|
+
<outline text="Michigan"/>
|
187
|
+
<outline text="Minnesota"/>
|
188
|
+
<outline text="Missouri"/>
|
189
|
+
<outline text="Ohio"/>
|
190
|
+
<outline text="West Virginia"/>
|
191
|
+
<outline text="Wisconsin"/>
|
192
|
+
</outline>
|
193
|
+
<outline text="Mountains">
|
194
|
+
<outline text="Colorado"/>
|
195
|
+
<outline text="Idaho"/>
|
196
|
+
<outline text="Montana"/>
|
197
|
+
<outline text="Utah"/>
|
198
|
+
<outline text="Wyoming"/>
|
199
|
+
</outline>
|
200
|
+
<outline text="New England">
|
201
|
+
<outline text="Connecticut"/>
|
202
|
+
<outline text="Maine"/>
|
203
|
+
<outline text="Massachusetts"/>
|
204
|
+
<outline text="New Hampshire"/>
|
205
|
+
<outline text="Rhode Island"/>
|
206
|
+
<outline text="Vermont"/>
|
207
|
+
</outline>
|
208
|
+
<outline text="South">
|
209
|
+
<outline text="Alabama"/>
|
210
|
+
<outline text="Arkansas"/>
|
211
|
+
<outline text="Florida"/>
|
212
|
+
<outline text="Georgia"/>
|
213
|
+
<outline text="Louisiana"/>
|
214
|
+
<outline text="Mississippi"/>
|
215
|
+
<outline text="North Carolina"/>
|
216
|
+
<outline text="South Carolina"/>
|
217
|
+
<outline text="Tennessee"/>
|
218
|
+
<outline text="Virginia"/>
|
219
|
+
</outline>
|
220
|
+
<outline text="Southwest">
|
221
|
+
<outline text="Arizona"/>
|
222
|
+
<outline text="New Mexico"/>
|
223
|
+
<outline text="Texas"/>
|
224
|
+
</outline>
|
225
|
+
</outline>
|
226
|
+
</body>
|
227
|
+
</opml>
|
228
|
+
```
|
229
|
+
|
230
|
+
Yes, use `OPML.load` / `load_file`. To access use:
|
231
|
+
|
232
|
+
``` ruby
|
233
|
+
hash['outline'][0]['text'] #=> "United States"
|
234
|
+
hash['outline'][0]['outline'][0]['text'] #=> "Far West"
|
235
|
+
hash['outline'][0]['outline'][0]['outline'][0]['text'] #=> "Alaska"
|
236
|
+
hash['outline'][0]['outline'][1]['text'] #=> "Great Plains"
|
237
|
+
```
|
238
|
+
|
239
|
+
Or use `Outline.parse` / `read`. To access use:
|
240
|
+
|
241
|
+
``` ruby
|
242
|
+
outline[0].text #=> "United States"
|
243
|
+
outline[0][0].text #=> "Far West"
|
244
|
+
outline[0][0][0].text #=> "Alaska"
|
245
|
+
outline[0][1].text #=> "Great Plains"
|
246
|
+
```
|
247
|
+
|
248
|
+
That's all for now.
|
249
|
+
|
250
|
+
|
251
|
+
## License
|
252
|
+
|
253
|
+
The `opmlparser` scripts are dedicated to the public domain.
|
254
|
+
Use it as you please with no restrictions whatsoever.
|
255
|
+
|
256
|
+
## Questions? Comments?
|
257
|
+
|
258
|
+
Send them along to the [wwwmake Forum/Mailing List](http://groups.google.com/group/wwwmake).
|
259
|
+
Thanks!
|
data/Rakefile
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'hoe'
|
2
|
+
require './lib/opmlparser/version.rb'
|
3
|
+
|
4
|
+
Hoe.spec 'opmlparser' do
|
5
|
+
|
6
|
+
self.version = OPML::VERSION
|
7
|
+
|
8
|
+
self.summary = "opmlparser - read / parse outlines (incl. feed subscription lists) in the OPML (Outline Processor Markup Language) format in xml"
|
9
|
+
self.description = summary
|
10
|
+
|
11
|
+
self.urls = ['https://github.com/feedreader/pluto']
|
12
|
+
|
13
|
+
self.author = 'Gerald Bauer'
|
14
|
+
self.email = 'wwwmake@googlegroups.com'
|
15
|
+
|
16
|
+
# switch extension to .markdown for gihub formatting
|
17
|
+
self.readme_file = 'README.md'
|
18
|
+
self.history_file = 'CHANGELOG.md'
|
19
|
+
|
20
|
+
self.extra_deps = []
|
21
|
+
|
22
|
+
self.licenses = ['Public Domain']
|
23
|
+
|
24
|
+
self.spec_extras = {
|
25
|
+
required_ruby_version: '>= 2.2.2'
|
26
|
+
}
|
27
|
+
|
28
|
+
end
|
data/lib/opmlparser.rb
ADDED
@@ -0,0 +1,175 @@
|
|
1
|
+
require 'pp'
|
2
|
+
require 'date'
|
3
|
+
require 'time'
|
4
|
+
require 'rexml/Document'
|
5
|
+
|
6
|
+
|
7
|
+
# our own code
|
8
|
+
require 'opmlparser/version' # note: let version always go first
|
9
|
+
|
10
|
+
|
11
|
+
|
12
|
+
module OPML
|
13
|
+
|
14
|
+
def self.load( xml )
|
15
|
+
parse( xml, outlinify: false )
|
16
|
+
end
|
17
|
+
|
18
|
+
def self.load_file( path )
|
19
|
+
xml = File.open( path, 'r:utf-8' ) { |f| f.read }
|
20
|
+
load( xml )
|
21
|
+
end
|
22
|
+
|
23
|
+
|
24
|
+
#####################################
|
25
|
+
### helper methods
|
26
|
+
## (internal) helper method
|
27
|
+
def self.parse( xml, outlinify: false )
|
28
|
+
opml = REXML::Document.new( xml )
|
29
|
+
|
30
|
+
### parse head
|
31
|
+
meta = {}
|
32
|
+
opml.elements['opml/head'].elements.each do |el|
|
33
|
+
meta[ el.name ] = el.text
|
34
|
+
end
|
35
|
+
|
36
|
+
## parse body
|
37
|
+
outline = []
|
38
|
+
parse_outline( outline, opml.elements['opml/body'], outlinify: outlinify )
|
39
|
+
|
40
|
+
if outlinify
|
41
|
+
Outline.new( { 'meta' => Outline::Meta.new( meta ),
|
42
|
+
'outline' => outline } )
|
43
|
+
else
|
44
|
+
{ 'meta' => meta,
|
45
|
+
'outline' => outline }
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def self.parse_outline( outlines, node, outlinify:)
|
50
|
+
node.elements.each( 'outline' ) do |el|
|
51
|
+
outline = {}
|
52
|
+
|
53
|
+
el.attributes.each do |attr|
|
54
|
+
outline[ attr[0] ] = attr[1]
|
55
|
+
end
|
56
|
+
|
57
|
+
if el.elements.size > 0
|
58
|
+
children = []
|
59
|
+
parse_outline( children, el, outlinify: outlinify )
|
60
|
+
outline[ 'outline' ] = children
|
61
|
+
end
|
62
|
+
|
63
|
+
## todo/fix: find a better name - use easyaccess or something?
|
64
|
+
## outlinify - wrap hash for easy access in Outline class
|
65
|
+
outlines << if outlinify ## wrap in Outline
|
66
|
+
Outline.new( outline )
|
67
|
+
else
|
68
|
+
outline
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
|
74
|
+
class Outline
|
75
|
+
def self.parse( xml )
|
76
|
+
Parser.new( xml ).parse
|
77
|
+
end
|
78
|
+
def self.read( path )
|
79
|
+
xml = File.open( path, 'r:utf-8' ) { |f| f.read }
|
80
|
+
parse( xml )
|
81
|
+
end
|
82
|
+
|
83
|
+
class << self ## add aliases
|
84
|
+
alias_method :load, :parse ## todo/check: add load alias - why? why not?
|
85
|
+
alias_method :load_file, :read ## todo/check: add load_file alias - why? why not?
|
86
|
+
end
|
87
|
+
|
88
|
+
|
89
|
+
class Parser
|
90
|
+
def initialize( xml )
|
91
|
+
@xml = xml
|
92
|
+
end
|
93
|
+
|
94
|
+
def parse
|
95
|
+
OPML.parse( @xml, outlinify: true )
|
96
|
+
end
|
97
|
+
end # class Parser
|
98
|
+
|
99
|
+
|
100
|
+
class Meta
|
101
|
+
def initialize( h )
|
102
|
+
@h = h
|
103
|
+
end
|
104
|
+
|
105
|
+
def [](key) @h[key]; end
|
106
|
+
|
107
|
+
def title() @h['title']; end
|
108
|
+
def dateCreated() @h['dateCreated' ]; end
|
109
|
+
alias_method :date_created, :dateCreated
|
110
|
+
alias_method :created, :dateCreated
|
111
|
+
|
112
|
+
def dateModified() @h['dateModified']; end
|
113
|
+
alias_method :date_modified, :dateModified
|
114
|
+
alias_method :modified, :dateModified
|
115
|
+
|
116
|
+
def ownerName() @h['ownerName']; end
|
117
|
+
alias_method :owner_name, :ownerName
|
118
|
+
|
119
|
+
def ownerEmail() @h['ownerEmail']; end
|
120
|
+
alias_method :owner_email, :ownerEmail
|
121
|
+
|
122
|
+
def ownerId() @h['ownerId']; end
|
123
|
+
alias_method :owner_id, :ownerId
|
124
|
+
end # class Meta
|
125
|
+
|
126
|
+
|
127
|
+
|
128
|
+
def initialize( h )
|
129
|
+
@h = h
|
130
|
+
end
|
131
|
+
|
132
|
+
def [](index)
|
133
|
+
if index.is_a?(Integer)
|
134
|
+
h = @h['outline'][index]
|
135
|
+
h = Outline.new( h ) if h.is_a?(Hash) ## allow "on-demand" use/wrapping too - why? why not?
|
136
|
+
h
|
137
|
+
else ## assume index is a text key
|
138
|
+
@h[ index ]
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
## array delegates for outline children
|
143
|
+
## todo/fix: check if outline can be nil? !!!!
|
144
|
+
def size() @h['outline'].size; end
|
145
|
+
alias_method :length, :size
|
146
|
+
|
147
|
+
def each( &blk ) @h['outline'].each( &blk ); end
|
148
|
+
|
149
|
+
|
150
|
+
def text() @h['text']; end
|
151
|
+
def xmlUrl() @h['xmlUrl']; end
|
152
|
+
alias_method :xml_url, :xmlUrl
|
153
|
+
|
154
|
+
def url() @h['url']; end
|
155
|
+
def htmlUrl() @h['htmlUrl']; end
|
156
|
+
alias_method :html_url, :htmlUrl
|
157
|
+
|
158
|
+
def created() @h['created']; end
|
159
|
+
def title() @h['title']; end
|
160
|
+
def type() @h['type']; end
|
161
|
+
def category() @h['category']; end
|
162
|
+
|
163
|
+
|
164
|
+
def meta() @h['meta']; end
|
165
|
+
end # class Outline
|
166
|
+
end # module OPML
|
167
|
+
|
168
|
+
|
169
|
+
## add some convenience shortcuts
|
170
|
+
Outline = OPML::Outline
|
171
|
+
|
172
|
+
|
173
|
+
|
174
|
+
# say hello
|
175
|
+
puts OPML.banner if $DEBUG || (defined?($RUBYLIBS_DEBUG) && $RUBYLIBS_DEBUG)
|
@@ -0,0 +1,20 @@
|
|
1
|
+
|
2
|
+
module OPML
|
3
|
+
MAJOR = 0 ## todo: namespace inside version or something - why? why not??
|
4
|
+
MINOR = 1
|
5
|
+
PATCH = 0
|
6
|
+
VERSION = [MAJOR,MINOR,PATCH].join('.')
|
7
|
+
|
8
|
+
def self.version
|
9
|
+
VERSION
|
10
|
+
end
|
11
|
+
|
12
|
+
def self.banner
|
13
|
+
"opmlparser/#{VERSION} on Ruby #{RUBY_VERSION} (#{RUBY_RELEASE_DATE}) [#{RUBY_PLATFORM}]"
|
14
|
+
end
|
15
|
+
|
16
|
+
def self.root
|
17
|
+
"#{File.expand_path( File.dirname(File.dirname(File.dirname(__FILE__))) )}"
|
18
|
+
end
|
19
|
+
end # module OPML
|
20
|
+
|
data/test/helper.rb
ADDED
@@ -0,0 +1,9 @@
|
|
1
|
+
<opml version="2.0">
|
2
|
+
<head>
|
3
|
+
<title>Illustrating the category attribute</title>
|
4
|
+
<dateCreated>Mon, 31 Oct 2005 19:23:00 GMT</dateCreated>
|
5
|
+
</head>
|
6
|
+
<body>
|
7
|
+
<outline text="The Mets are the best team in baseball." category="/Philosophy/Baseball/Mets,/Tourism/New York" created="Mon, 31 Oct 2005 18:21:33 GMT"/>
|
8
|
+
</body>
|
9
|
+
</opml>
|
@@ -0,0 +1,42 @@
|
|
1
|
+
<opml version="2.0">
|
2
|
+
<head>
|
3
|
+
<title>placesLived.opml</title>
|
4
|
+
<dateCreated>Mon, 27 Feb 2006 12:09:48 GMT</dateCreated>
|
5
|
+
<dateModified>Mon, 27 Feb 2006 12:11:44 GMT</dateModified>
|
6
|
+
<ownerName>Dave Winer</ownerName>
|
7
|
+
<ownerId>http://www.opml.org/profiles/sendMail?usernum=1</ownerId>
|
8
|
+
<expansionState>1, 2, 5, 10, 13, 15</expansionState>
|
9
|
+
<vertScrollState>1</vertScrollState>
|
10
|
+
<windowTop>242</windowTop>
|
11
|
+
<windowLeft>329</windowLeft>
|
12
|
+
<windowBottom>665</windowBottom>
|
13
|
+
<windowRight>547</windowRight>
|
14
|
+
</head>
|
15
|
+
<body>
|
16
|
+
<outline text="Places I've lived">
|
17
|
+
<outline text="Boston">
|
18
|
+
<outline text="Cambridge"/>
|
19
|
+
<outline text="West Newton"/>
|
20
|
+
</outline>
|
21
|
+
<outline text="Bay Area">
|
22
|
+
<outline text="Mountain View"/>
|
23
|
+
<outline text="Los Gatos"/>
|
24
|
+
<outline text="Palo Alto"/>
|
25
|
+
<outline text="Woodside"/>
|
26
|
+
</outline>
|
27
|
+
<outline text="New Orleans">
|
28
|
+
<outline text="Uptown"/>
|
29
|
+
<outline text="Metairie"/>
|
30
|
+
</outline>
|
31
|
+
<outline text="Wisconsin">
|
32
|
+
<outline text="Madison"/>
|
33
|
+
</outline>
|
34
|
+
<outline text="Florida" type="include" url="http://hosting.opml.org/dave/florida.opml"/>
|
35
|
+
<outline text="New York">
|
36
|
+
<outline text="Jackson Heights"/>
|
37
|
+
<outline text="Flushing"/>
|
38
|
+
<outline text="The Bronx"/>
|
39
|
+
</outline>
|
40
|
+
</outline>
|
41
|
+
</body>
|
42
|
+
</opml>
|
@@ -0,0 +1,90 @@
|
|
1
|
+
<opml version="2.0">
|
2
|
+
<head>
|
3
|
+
<title>states.opml</title>
|
4
|
+
<dateCreated>Tue, 15 Mar 2005 16:35:45 GMT</dateCreated>
|
5
|
+
<dateModified>Thu, 14 Jul 2005 23:41:05 GMT</dateModified>
|
6
|
+
<ownerName>Dave Winer</ownerName>
|
7
|
+
<ownerEmail>dave@scripting.com</ownerEmail>
|
8
|
+
<expansionState>1, 6, 13, 16, 18, 20</expansionState>
|
9
|
+
<vertScrollState>1</vertScrollState>
|
10
|
+
<windowTop>106</windowTop>
|
11
|
+
<windowLeft>106</windowLeft>
|
12
|
+
<windowBottom>558</windowBottom>
|
13
|
+
<windowRight>479</windowRight>
|
14
|
+
</head>
|
15
|
+
<body>
|
16
|
+
<outline text="United States">
|
17
|
+
<outline text="Far West">
|
18
|
+
<outline text="Alaska"/>
|
19
|
+
<outline text="California"/>
|
20
|
+
<outline text="Hawaii"/>
|
21
|
+
<outline text="Nevada">
|
22
|
+
<outline text="Reno" created="Tue, 12 Jul 2005 23:56:35 GMT"/>
|
23
|
+
<outline text="Las Vegas" created="Tue, 12 Jul 2005 23:56:37 GMT"/>
|
24
|
+
<outline text="Ely" created="Tue, 12 Jul 2005 23:56:39 GMT"/>
|
25
|
+
<outline text="Gerlach" created="Tue, 12 Jul 2005 23:56:47 GMT"/>
|
26
|
+
</outline>
|
27
|
+
<outline text="Oregon"/>
|
28
|
+
<outline text="Washington"/>
|
29
|
+
</outline>
|
30
|
+
<outline text="Great Plains">
|
31
|
+
<outline text="Kansas"/>
|
32
|
+
<outline text="Nebraska"/>
|
33
|
+
<outline text="North Dakota"/>
|
34
|
+
<outline text="Oklahoma"/>
|
35
|
+
<outline text="South Dakota"/>
|
36
|
+
</outline>
|
37
|
+
<outline text="Mid-Atlantic">
|
38
|
+
<outline text="Delaware"/>
|
39
|
+
<outline text="Maryland"/>
|
40
|
+
<outline text="New Jersey"/>
|
41
|
+
<outline text="New York"/>
|
42
|
+
<outline text="Pennsylvania"/>
|
43
|
+
</outline>
|
44
|
+
<outline text="Midwest">
|
45
|
+
<outline text="Illinois"/>
|
46
|
+
<outline text="Indiana"/>
|
47
|
+
<outline text="Iowa"/>
|
48
|
+
<outline text="Kentucky"/>
|
49
|
+
<outline text="Michigan"/>
|
50
|
+
<outline text="Minnesota"/>
|
51
|
+
<outline text="Missouri"/>
|
52
|
+
<outline text="Ohio"/>
|
53
|
+
<outline text="West Virginia"/>
|
54
|
+
<outline text="Wisconsin"/>
|
55
|
+
</outline>
|
56
|
+
<outline text="Mountains">
|
57
|
+
<outline text="Colorado"/>
|
58
|
+
<outline text="Idaho"/>
|
59
|
+
<outline text="Montana"/>
|
60
|
+
<outline text="Utah"/>
|
61
|
+
<outline text="Wyoming"/>
|
62
|
+
</outline>
|
63
|
+
<outline text="New England">
|
64
|
+
<outline text="Connecticut"/>
|
65
|
+
<outline text="Maine"/>
|
66
|
+
<outline text="Massachusetts"/>
|
67
|
+
<outline text="New Hampshire"/>
|
68
|
+
<outline text="Rhode Island"/>
|
69
|
+
<outline text="Vermont"/>
|
70
|
+
</outline>
|
71
|
+
<outline text="South">
|
72
|
+
<outline text="Alabama"/>
|
73
|
+
<outline text="Arkansas"/>
|
74
|
+
<outline text="Florida"/>
|
75
|
+
<outline text="Georgia"/>
|
76
|
+
<outline text="Louisiana"/>
|
77
|
+
<outline text="Mississippi"/>
|
78
|
+
<outline text="North Carolina"/>
|
79
|
+
<outline text="South Carolina"/>
|
80
|
+
<outline text="Tennessee"/>
|
81
|
+
<outline text="Virginia"/>
|
82
|
+
</outline>
|
83
|
+
<outline text="Southwest">
|
84
|
+
<outline text="Arizona"/>
|
85
|
+
<outline text="New Mexico"/>
|
86
|
+
<outline text="Texas"/>
|
87
|
+
</outline>
|
88
|
+
</outline>
|
89
|
+
</body>
|
90
|
+
</opml>
|
data/test/test_opml.rb
ADDED
@@ -0,0 +1,44 @@
|
|
1
|
+
###
|
2
|
+
# to run use
|
3
|
+
# ruby -I ./lib -I ./test test/test_opml.rb
|
4
|
+
|
5
|
+
|
6
|
+
require 'helper'
|
7
|
+
|
8
|
+
|
9
|
+
class TestOpml < MiniTest::Test
|
10
|
+
|
11
|
+
def test_samples_opml
|
12
|
+
h = OPML.load_file( './test/outlines/category.opml.xml' )
|
13
|
+
h = OPML.load_file( './test/outlines/places_lived.opml.xml' )
|
14
|
+
h = OPML.load_file( './test/outlines/states.opml.xml' )
|
15
|
+
|
16
|
+
assert_equal "United States", h['outline'][0]['text']
|
17
|
+
assert_equal "Far West", h['outline'][0]['outline'][0]['text']
|
18
|
+
assert_equal "Alaska", h['outline'][0]['outline'][0]['outline'][0]['text']
|
19
|
+
assert_equal "Great Plains", h['outline'][0]['outline'][1]['text']
|
20
|
+
end
|
21
|
+
|
22
|
+
def test_samples_outline
|
23
|
+
o = Outline.read( './test/outlines/category.opml.xml' )
|
24
|
+
o = Outline.read( './test/outlines/places_lived.opml.xml' )
|
25
|
+
o = Outline.read( './test/outlines/states.opml.xml' )
|
26
|
+
|
27
|
+
assert_equal "United States", o[0].text
|
28
|
+
assert_equal "United States", o[0]['text']
|
29
|
+
|
30
|
+
assert_equal "Far West", o[0][0].text
|
31
|
+
assert_equal "Far West", o[0][0]['text']
|
32
|
+
|
33
|
+
assert_equal "Alaska", o[0][0][0].text
|
34
|
+
assert_equal "Alaska", o[0][0][0]['text']
|
35
|
+
|
36
|
+
assert_equal "Great Plains", o[0][1].text
|
37
|
+
assert_equal "Great Plains", o[0][1]['text']
|
38
|
+
|
39
|
+
## check alias_method
|
40
|
+
o = Outline.load_file( './test/outlines/category.opml.xml' )
|
41
|
+
o = Outline.load_file( './test/outlines/places_lived.opml.xml' )
|
42
|
+
o = Outline.load_file( './test/outlines/states.opml.xml' )
|
43
|
+
end
|
44
|
+
end # class TestOpml
|
metadata
ADDED
@@ -0,0 +1,89 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: opmlparser
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Gerald Bauer
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2020-03-09 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: rdoc
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '4.0'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '4.0'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: hoe
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '3.16'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '3.16'
|
41
|
+
description: opmlparser - read / parse outlines (incl. feed subscription lists) in
|
42
|
+
the OPML (Outline Processor Markup Language) format in xml
|
43
|
+
email: wwwmake@googlegroups.com
|
44
|
+
executables: []
|
45
|
+
extensions: []
|
46
|
+
extra_rdoc_files:
|
47
|
+
- CHANGELOG.md
|
48
|
+
- Manifest.txt
|
49
|
+
- README.md
|
50
|
+
files:
|
51
|
+
- CHANGELOG.md
|
52
|
+
- Manifest.txt
|
53
|
+
- README.md
|
54
|
+
- Rakefile
|
55
|
+
- lib/opmlparser.rb
|
56
|
+
- lib/opmlparser/version.rb
|
57
|
+
- test/helper.rb
|
58
|
+
- test/outlines/category.opml.xml
|
59
|
+
- test/outlines/places_lived.opml.xml
|
60
|
+
- test/outlines/states.opml.xml
|
61
|
+
- test/test_opml.rb
|
62
|
+
homepage: https://github.com/feedreader/pluto
|
63
|
+
licenses:
|
64
|
+
- Public Domain
|
65
|
+
metadata: {}
|
66
|
+
post_install_message:
|
67
|
+
rdoc_options:
|
68
|
+
- "--main"
|
69
|
+
- README.md
|
70
|
+
require_paths:
|
71
|
+
- lib
|
72
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
73
|
+
requirements:
|
74
|
+
- - ">="
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: 2.2.2
|
77
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
78
|
+
requirements:
|
79
|
+
- - ">="
|
80
|
+
- !ruby/object:Gem::Version
|
81
|
+
version: '0'
|
82
|
+
requirements: []
|
83
|
+
rubyforge_project:
|
84
|
+
rubygems_version: 2.5.2
|
85
|
+
signing_key:
|
86
|
+
specification_version: 4
|
87
|
+
summary: opmlparser - read / parse outlines (incl. feed subscription lists) in the
|
88
|
+
OPML (Outline Processor Markup Language) format in xml
|
89
|
+
test_files: []
|