libxml4r 0.0.0 → 0.2.6

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. data/.autotest +30 -0
  2. data/README.rdoc +113 -9
  3. data/Rakefile +2 -1
  4. data/VERSION +1 -1
  5. data/lib/libxml4r.rb +229 -0
  6. data/libxml4r.gemspec +98 -0
  7. data/test/test_helper.rb +39 -0
  8. data/test/test_libxml4r.rb +34 -3
  9. data/test/test_xml_modifiers.rb +57 -0
  10. data/test/test_xml_outputters.rb +53 -0
  11. data/test/test_xml_readers.rb +59 -0
  12. data/test/xml/atom.xml +13 -0
  13. data/test/xml/books.xml +146 -0
  14. data/test/xml/breakfast_menu.xml +38 -0
  15. data/test/xml/document.xml +49 -0
  16. data/test/xml/merge_bug_data.xml +58 -0
  17. data/test/xml/namespaces.xml +22 -0
  18. data/test/xml/parts_system.xml +31 -0
  19. data/test/xml/plant_catalog.xml +336 -0
  20. data/test/xml/recipie.xml +18 -0
  21. data/test/xml/rss1.xml +58 -0
  22. data/test/xml/rss2.xml +56 -0
  23. data/test/xml/ruby_lang.xhtml +238 -0
  24. data/test/xml/rubynet.xml +79 -0
  25. data/test/xml/shiporder.xls +86 -0
  26. data/test/xml/shiporder.xml +23 -0
  27. data/test/xml/shiporder.xsd +31 -0
  28. data/test/xml/soap_create_path.xml +15 -0
  29. data/test/xml/soap_create_path_response.xml +16 -0
  30. data/test/xml/soap_create_reservation.xml +25 -0
  31. data/test/xml/soap_create_reservation_response.xml +64 -0
  32. data/test/xml/soap_get_price.xml +11 -0
  33. data/test/xml/soap_get_price_response.xml +11 -0
  34. data/test/xml/soap_manufacturer_names_response.xml +27 -0
  35. data/test/xml/soap_order_item.xml +17 -0
  36. data/test/xml/soap_order_item_response.xml +10 -0
  37. data/test/xml/soap_refresh_path.xml +15 -0
  38. data/test/xml/soap_refresh_path_response.xml +16 -0
  39. data/test/xml/soap_teardown_path.xml +15 -0
  40. data/test/xml/soap_teardown_path_response.xml +16 -0
  41. metadata +52 -3
data/.autotest ADDED
@@ -0,0 +1,30 @@
1
+ # -*- ruby -*-
2
+
3
+ Autotest.add_hook :initialize do |at|
4
+ at.clear_mappings # Do not remove this line
5
+
6
+ # Put your additional test files here
7
+ extra_mappings_pfx = "test/"
8
+ extra_mappings = {
9
+ "libxml4r.rb" => [
10
+ "test_xml_readers.rb",
11
+ "test_xml_modifiers.rb",
12
+ "test_xml_outputters.rb"]
13
+ }
14
+
15
+ # Do not edit below these lines
16
+
17
+ at.add_mapping /^lib\/.*\.rb$/ do |f, _|
18
+ m=f.gsub /.*\//, "" # Strip leading path from #{f}
19
+ a=extra_mappings["#{m}"]
20
+ a.nil? ? a=[] : a=a.map {|e| extra_mappings_pfx+e}
21
+ # at.files_matching(/test\/test_#{m}$/) + a
22
+ ["test/test_#{m}"] + a
23
+ end
24
+
25
+ at.add_mapping /^test\/test.*\.rb$/ do |f, _|
26
+ at.files_matching(/#{f}/)
27
+ end
28
+
29
+ end
30
+
data/README.rdoc CHANGED
@@ -1,17 +1,121 @@
1
1
  = libxml4r
2
2
 
3
- Description goes here.
3
+ {libxml4r}[http://github.com/dreamcat4/libxml4r/tree/master] is a light set of methods and bolt-ons which aren't maintained by the core {libxml ruby library}[http://libxml.rubyforge.org/install.xml]. These methods aim to provide a more convenient API interface which is provided and documented separately, but actually mixed in to extend the original LibXML::classes. Using these methods should significantly reduce the lines of code needed to perform the most common operations of accessing and manipulating an xml document structure.
4
4
 
5
- == Note on Patches/Pull Requests
5
+ For a full list of methods, please refer to the {RDoc Documentation}[http://rdoc.info/projects/dreamcat4/libxml4r]
6
+ and also the {Libxml-Ruby RDocs}[http://libxml.rubyforge.org/rdoc/]
7
+
8
+ For benkchmarks / performance comparison see http://cfis.savagexi.com/2008/07/16/resurrecting-libxml-ruby
9
+
10
+ == Installation
11
+
12
+ gem sources -a http://gemcutter.org
13
+ gem install libxml4r
14
+
15
+ == Getting started
16
+
17
+ You can call +to_xmldoc+ on any xml string to convert it into an XML::Document
18
+
19
+ >> s = '<foo id="1"><author>p. bogle</author><bar>content</bar><bar>cont2</bar></foo>'
20
+ >> doc = s.to_xmldoc
21
+
22
+ The +node["/xpath"]+ method returns the first Node matching the given {xpath}[http://www.w3schools.com/XPath/xpath_syntax.asp]
23
+
24
+ >> doc.node["author"]
25
+ => <author>p. bogle</author>
26
+
27
+ The +nodes["/xpath"]+ method returns an array of Nodes matching the given {xpath}[http://www.w3schools.com/XPath/xpath_syntax.asp]
28
+
29
+ >> doc.nodes["/foo/bar"]
30
+ => [<bar>content</bar>, <bar>content2</bar>]
31
+
32
+ +nodes[]+ can be called with a block to iterate through each of the matching nodes
33
+
34
+ >> doc.nodes["bar"] do |bar| puts bar.xpath; end
35
+ /foo/bar[1]
36
+ /foo/bar[2]
37
+
38
+ You can call +node[]+ on another node to iterate and search within a smaller context of the document
39
+
40
+ >> foo = doc.node["/foo"]
41
+ >> foo.node["author"]
42
+ => <author>p. bogle</author>
43
+
44
+ >> foo.nodes["/bar"].each {|node| puts node.inner_xml}
45
+ => "content2"
46
+ => "cont2"
47
+
48
+ For more information about XPath syntax, please see http://www.w3schools.com/XPath/xpath_syntax.asp
49
+
50
+ == Removing the whitespace nodes amongst our data nodes
51
+
52
+ ::LibXML::XML.default_keep_blanks = false
53
+
54
+ Put this line at the beginning, before parsing the xml document. Othewise libxml interpolates all the 'real' data nodes with string nodes of the whitespace found between them. So `node.next` will point to the next *data* node, and not something like `"\n "`. This is the "right" thing to do, whenever expecting to walk along or iterate over the parsed doc tree.
55
+
56
+ == Namespace Stripping
57
+
58
+ The handling of default namespaces in libxml-ruby is extremely awkward and cumbersome as it requires passing along an array of namespace strings with every find() method call. It also represents ambiguity concerning the href of the default namespace.
59
+
60
+ Suppose you had a namespaced XML source with xmlns:= directives like this
61
+
62
+ >> document.to_xml
63
+ <?xml version="1.0" encoding="UTF-8"?>
64
+ <feed xmlns="http://www.w3.org/2005/Atom"
65
+ xmlns:openSearch="http://a9.com/-/spec/opensearchrss/1.0/"
66
+ xmlns:gContact="http://schemas.google.com/contact/2008\"
67
+ xmlns:gd="http://schemas.google.com/g/2005">
68
+ <title type=\"text\">Phil Bogle's Contacts</title>
69
+ ...
70
+ </feed>
71
+
72
+ With libxml4r its possible to do:
73
+
74
+ >> document.strip!
75
+
76
+ And be left with plain xml which can be parsed more easily and without the need for specifying any confusing namespace directives
77
+
78
+ >> document.to_xml
79
+ <?xml version="1.0" encoding="UTF-8"?>
80
+ <feed>
81
+ <title type=\"text\">Phil Bogle's Contacts</title>
82
+ ...
83
+ </feed>
84
+
85
+ >> document.node["/feed/title"].inner_xml
86
+ => "Phil Bogle's Contacts"
87
+
88
+ After manipulating your data model, a default namespace can later be re-applied on the top-level node. However its generally not recommended to use more than one namespace within the same xml document.
89
+
90
+ == A Complete example
91
+
92
+ Here we combine our usage of both the `libxml-ruby`, and `libxml4r` functions, which results in much smaller and more compact code. Its just a case of using the right tool for the right job.
93
+
94
+ ::LibXML::XML.default_keep_blanks = false
95
+ @string = File.read(@launchd_plist)
96
+ @doc = @string.to_xmldoc.strip!
97
+ @doc = doc.node["/plist/dict"]
98
+ @nodes_plist_keys = @doc.nodes["key"]
99
+ @plist_keys_values = @nodes_xml_keys.collect {|n| [n.inner_xml, n.next] }
100
+
101
+ == Final words
102
+
103
+ Its well worth it spending some time to understand the libxml-ruby api and xpath. Its well worth it to go back and revisit all of the links dotted around this page. Those documentation are absoloutely invaluable. 100% the best.
104
+
105
+ == Notes on Patches/Pull Requests
6
106
 
7
- * Fork the project.
107
+ * Fork the project, and create a topic branch as per {these instructions}[http://wiki.opscode.com/display/opscode/Working+with+Git].
8
108
  * Make your feature addition or bug fix.
9
- * Add tests for it. This is important so I don't break it in a
10
- future version unintentionally.
11
- * Commit, do not mess with rakefile, version, or history.
12
- (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
13
- * Send me a pull request. Bonus points for topic branches.
109
+ * Include documentation for it.
110
+ * Include a regression test for it. So I don't break it in a future version unintentionally.
14
111
 
15
112
  == Copyright
16
113
 
17
- Copyright (c) 2010 dreamcat4. See LICENSE for details.
114
+ Copyright (c) 2009 Dreamcat4. See LICENSE for details.
115
+
116
+ == Contribution, Credits
117
+
118
+ This project was started on the top of Phil Bogle's libxml_helper.rb[http://thebogles.com/blog/an-hpricot-style-interface-to-libxml#]. Most methods have been renamed to represent the api styling of the libxml project. Some coding examples here are also adapted from Phil's original explanatory texts.
119
+
120
+ Copyright (c) 2008 Phil Bogle.
121
+ Copyright (c) 2009-2010 Dreamcat4.
data/Rakefile CHANGED
@@ -6,10 +6,11 @@ begin
6
6
  Jeweler::Tasks.new do |gem|
7
7
  gem.name = "libxml4r"
8
8
  gem.summary = %Q{Libxml4r provides convenience methods around the core libxml-ruby classes.}
9
- gem.description = %Q{Libxml4r is a light set of methods and bolt-ons which aren't maintained by the core libxml ruby library. These methods aim to provide a more easy to use xml API. All libxml4r methods are mixed into the original LibXML::classes. (This gem was previously called libxml-bindings).}
9
+ gem.description = %Q{Libxml4r is a light set of methods and bolt-ons which aren't maintained by the core libxml ruby library. These methods aim to provide a more easy to use xml API. All libxml4r methods are mixed into the original LibXML::classes. (This gem was previously called libxml4r).}
10
10
  gem.email = "dreamcat4@gmail.com"
11
11
  gem.homepage = "http://github.com/dreamcat4/libxml4r"
12
12
  gem.authors = ["dreamcat4"]
13
+ gem.add_dependency("libxml-ruby", ">= 1.1.3")
13
14
  gem.add_development_dependency "thoughtbot-shoulda", ">= 0"
14
15
  gem.add_development_dependency "yard", ">= 0"
15
16
  # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.0
1
+ 0.2.6
data/lib/libxml4r.rb CHANGED
@@ -0,0 +1,229 @@
1
+ require "xml/libxml"
2
+
3
+ class Module #:nodoc:
4
+ alias_method :method_alias, :alias_method
5
+ end
6
+
7
+ module Libxml4r #:nodoc:
8
+
9
+ module XML #:nodoc:
10
+ module Document
11
+
12
+ # :call-seq:
13
+ # doc.last = node -> XML::Node
14
+ #
15
+ # Appends +node+ to the end of the list of nodes at this level
16
+ def last=(node)
17
+ self.last? ? self.root.sibling=node : self.root = node
18
+ end
19
+
20
+ # :call-seq:
21
+ # doc.node["/xpath"] -> XML::Node
22
+ #
23
+ # Returns the first Node object matching +"/xpath"+, or +nil+ if no object could not be found.
24
+ #
25
+ # *Note* its usually recommended to remove all namespaces with strip! before xpath traversal.
26
+ def node()
27
+ self.root.node()
28
+ end
29
+
30
+ def node_at(xpath) #:nodoc:
31
+ self.root.node_at(xpath)
32
+ end
33
+
34
+ # :call-seq:
35
+ # doc.nodes["/xpath"] -> [XML::Node, XML::Node, XML::Node, ...]
36
+ #
37
+ # Returns an array containing all nodes matching +"/xpath"+, or +nil+ if no object could not be found.
38
+ #
39
+ # *Note* its usually recommended to remove all namespaces with strip! before xpath traversal.
40
+ def nodes()
41
+ self.root.nodes()
42
+ end
43
+
44
+ def nodes_at(xpath) #:nodoc:
45
+ self.root.search(xpath)
46
+ end
47
+
48
+ # :call-seq:
49
+ # doc.strip! -> XML::Document
50
+ # doc.strip_namespaces! -> XML::Document
51
+ #
52
+ # Strip all namespaces from this XML::Document.
53
+ # replaces the root node with a stripped XML::Node (and children)
54
+ #
55
+ # *Note* Xml elements with a namespace context are usually omited from xpath search criteria.
56
+ #
57
+ # See: http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/XPath.html
58
+ def strip!
59
+ # Parse xml
60
+ xml_str = self.to_s
61
+ # puts "xml_str=#{xml_str}\\n"
62
+ xml_str.gsub! /\ ?(soap|xmlns)(:\w*)?=\"[^\"]*\"/, ""
63
+ xml_str.gsub! /\<\w*:/, "<"
64
+ xml_str.gsub! /\<\/\w*:/, "</"
65
+ # puts "xml_str=#{xml_str}\\n"
66
+ xml_doc_stripped = xml_str.to_xmldoc
67
+ self.root = xml_doc_stripped.root.copy(true)
68
+ return self
69
+ end
70
+ alias_method :strip_namespaces!, :strip!
71
+
72
+ # :call-seq:
73
+ # doc.to_xml -> String
74
+ #
75
+ # Alias for XML::Document.to_s[http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/Document.html#M000458]
76
+ def to_xml
77
+ return self.to_s
78
+ end
79
+ # alias_method :to_xml, :to_s
80
+
81
+ end
82
+
83
+ module Node
84
+
85
+ class SearchNodes #:nodoc:
86
+ def initialize(options)
87
+ @node = options[:node]
88
+ @return_many = options[:return_many]
89
+ end
90
+ def [](args)
91
+ @return_many ? @node.nodes_at(args) : @node.node_at(args)
92
+ end
93
+ end
94
+
95
+ # :call-seq:
96
+ # self.inner_html -> String
97
+ #
98
+ # Alias for XML::Node.inner_xml[http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/Node.html#M000188]
99
+ def inner_html
100
+ self.inner_xml
101
+ end
102
+ # alias_method :inner_html, :inner_xml
103
+
104
+ # :call-seq:
105
+ # self.last = XML::Node -> XML::Node
106
+ #
107
+ # Alias for XML::Node.sibling=[http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/Node.html#M000223]
108
+ def last=(node)
109
+ return self.sibling = node
110
+ end
111
+ # alias_method :last=, :sibling=
112
+
113
+ # :call-seq:
114
+ # self.node["/xpath"] -> XML::Node
115
+ #
116
+ # Returns the first Node object matching +"/xpath"+, or +nil+ if no object could not be found.
117
+ # The path searched is relative to the node from which node[] was called.
118
+ #
119
+ # *Note* its usually recommended to remove all namespaces with strip! before xpath traversal.
120
+ def node()
121
+ return SearchNodes.new(:node => self, :return_many => false)
122
+ end
123
+
124
+ def node_at(xpath) #:nodoc:
125
+ self.find_first(xpath)
126
+ end
127
+
128
+ # :call-seq:
129
+ # self.nodes["/xpath"] -> [XML::Node, XML::Node, XML::Node, ...]
130
+ #
131
+ # Returns an array containing all nodes matching +"/xpath"+, or +nil+ if no object could not be found.
132
+ # The path searched is relative to the node from which node[] was called.
133
+ #
134
+ # *Note* its usually recommended to remove all namespaces with strip! before xpath traversal.
135
+ def nodes()
136
+ return SearchNodes.new(:node => self, :return_many => true)
137
+ end
138
+
139
+ def nodes_at(xpath) #:nodoc:
140
+ results = self.find(xpath).to_a
141
+ if block_given?
142
+ results.each do |result|
143
+ yield result
144
+ end
145
+ end
146
+ return results
147
+ end
148
+
149
+ # # :call-seq:
150
+ # # self.replace!(other_node) -> XML::Node
151
+ # #
152
+ # # Replaces the current XML::Node with +other_node+.
153
+ # # remove! is called on self, and it's handle will become lost.
154
+ # def replace!(other_node)
155
+ # node_node_parent = parent if parent?
156
+ # new_node_doc = self.doc if ! parent?
157
+ # self.remove!
158
+ # doc.root = other_node if new_node_doc
159
+ # parent << other_node if parent
160
+ # return other_node
161
+ # end
162
+
163
+ # # :call-seq:
164
+ # # self.strip! -> XML::Node
165
+ # # self.strip_namespaces! -> XML::Node
166
+ # #
167
+ # # Strip namespaces from this XML::Node and all its children.
168
+ # # replaces this XML::Node with the stripped XML::Node (and children)
169
+ # #
170
+ # # *Note* Xml elements with a namespace context are usually omited from xpath search criteria.
171
+ # #
172
+ # # See: http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/XPath.html
173
+ # def strip!
174
+ # # Parse xml
175
+ # xml_str = self.to_s
176
+ # # puts "xml_str=#{xml_str}\\n"
177
+ # xml_str.gsub! /\ ?(soap|xmlns)(:\w*)?=\"[^\"]*\"/, ""
178
+ # xml_str.gsub! /\<\w*:/, "<"
179
+ # xml_str.gsub! /\<\/\w*:/, "</"
180
+ # # puts "xml_str=#{xml_str}\\n"
181
+ # xml_node_stripped = xml_str.to_xmldoc
182
+ # new_node = xml_doc_stripped.root.copy(true)
183
+ # self.replace new_node
184
+ # return new_node
185
+ # end
186
+ #
187
+ # alias_method :strip_namespaces!, :strip!
188
+
189
+ # :call-seq:
190
+ # self.to_xml -> String
191
+ #
192
+ # Alias for XML::Node.to_s[http://libxml.rubyforge.org/rdoc/classes/LibXML/XML/Node.html#M000216]
193
+ def to_xml
194
+ return self.to_s
195
+ end
196
+ # alias_method :to_xml, :to_s
197
+
198
+ end
199
+ end
200
+
201
+ module String
202
+ # :call-seq:
203
+ # str.to_xmldoc -> XML::Document
204
+ #
205
+ # Returns an XML Document object, or +nil+ if str could not be parsed as valid xml.
206
+ #
207
+ # The resulting libxml instance can be parsed, manipulated, and converted back to a string.
208
+ def to_xmldoc
209
+ return ::XML::Parser.string(self).parse
210
+ end
211
+ end
212
+
213
+ end
214
+
215
+ # Mix into the standard ruby classes
216
+ module LibXML
217
+ module XML #:nodoc:
218
+ class Document #:nodoc:
219
+ include ::Libxml4r::XML::Document
220
+ end
221
+
222
+ class Node #:nodoc:
223
+ include ::Libxml4r::XML::Node
224
+ end
225
+ end
226
+ end
227
+ class String #:nodoc:
228
+ include ::Libxml4r::String
229
+ end
data/libxml4r.gemspec ADDED
@@ -0,0 +1,98 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{libxml4r}
8
+ s.version = "0.2.6"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["dreamcat4"]
12
+ s.date = %q{2010-03-09}
13
+ s.description = %q{Libxml4r is a light set of methods and bolt-ons which aren't maintained by the core libxml ruby library. These methods aim to provide a more easy to use xml API. All libxml4r methods are mixed into the original LibXML::classes. (This gem was previously called libxml4r).}
14
+ s.email = %q{dreamcat4@gmail.com}
15
+ s.extra_rdoc_files = [
16
+ "LICENSE",
17
+ "README.rdoc"
18
+ ]
19
+ s.files = [
20
+ ".autotest",
21
+ ".document",
22
+ ".gitignore",
23
+ "LICENSE",
24
+ "README.rdoc",
25
+ "Rakefile",
26
+ "VERSION",
27
+ "lib/libxml4r.rb",
28
+ "libxml4r.gemspec",
29
+ "test/helper.rb",
30
+ "test/test_helper.rb",
31
+ "test/test_libxml4r.rb",
32
+ "test/test_xml_modifiers.rb",
33
+ "test/test_xml_outputters.rb",
34
+ "test/test_xml_readers.rb",
35
+ "test/xml/atom.xml",
36
+ "test/xml/books.xml",
37
+ "test/xml/breakfast_menu.xml",
38
+ "test/xml/document.xml",
39
+ "test/xml/merge_bug_data.xml",
40
+ "test/xml/namespaces.xml",
41
+ "test/xml/parts_system.xml",
42
+ "test/xml/plant_catalog.xml",
43
+ "test/xml/recipie.xml",
44
+ "test/xml/rss1.xml",
45
+ "test/xml/rss2.xml",
46
+ "test/xml/ruby_lang.xhtml",
47
+ "test/xml/rubynet.xml",
48
+ "test/xml/shiporder.xls",
49
+ "test/xml/shiporder.xml",
50
+ "test/xml/shiporder.xsd",
51
+ "test/xml/soap_create_path.xml",
52
+ "test/xml/soap_create_path_response.xml",
53
+ "test/xml/soap_create_reservation.xml",
54
+ "test/xml/soap_create_reservation_response.xml",
55
+ "test/xml/soap_get_price.xml",
56
+ "test/xml/soap_get_price_response.xml",
57
+ "test/xml/soap_manufacturer_names_response.xml",
58
+ "test/xml/soap_order_item.xml",
59
+ "test/xml/soap_order_item_response.xml",
60
+ "test/xml/soap_refresh_path.xml",
61
+ "test/xml/soap_refresh_path_response.xml",
62
+ "test/xml/soap_teardown_path.xml",
63
+ "test/xml/soap_teardown_path_response.xml"
64
+ ]
65
+ s.homepage = %q{http://github.com/dreamcat4/libxml4r}
66
+ s.rdoc_options = ["--charset=UTF-8"]
67
+ s.require_paths = ["lib"]
68
+ s.rubygems_version = %q{1.3.5}
69
+ s.summary = %q{Libxml4r provides convenience methods around the core libxml-ruby classes.}
70
+ s.test_files = [
71
+ "test/helper.rb",
72
+ "test/test_helper.rb",
73
+ "test/test_libxml4r.rb",
74
+ "test/test_xml_modifiers.rb",
75
+ "test/test_xml_outputters.rb",
76
+ "test/test_xml_readers.rb"
77
+ ]
78
+
79
+ if s.respond_to? :specification_version then
80
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
81
+ s.specification_version = 3
82
+
83
+ if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0') then
84
+ s.add_runtime_dependency(%q<libxml-ruby>, [">= 1.1.3"])
85
+ s.add_development_dependency(%q<thoughtbot-shoulda>, [">= 0"])
86
+ s.add_development_dependency(%q<yard>, [">= 0"])
87
+ else
88
+ s.add_dependency(%q<libxml-ruby>, [">= 1.1.3"])
89
+ s.add_dependency(%q<thoughtbot-shoulda>, [">= 0"])
90
+ s.add_dependency(%q<yard>, [">= 0"])
91
+ end
92
+ else
93
+ s.add_dependency(%q<libxml-ruby>, [">= 1.1.3"])
94
+ s.add_dependency(%q<thoughtbot-shoulda>, [">= 0"])
95
+ s.add_dependency(%q<yard>, [">= 0"])
96
+ end
97
+ end
98
+