From 976226b5de303ed852744c0291c280d1e5fd538f Mon Sep 17 00:00:00 2001 From: kou Date: Sat, 31 Jan 2004 16:10:53 +0000 Subject: * lib/rss/parser.rb (RSS::Parser): added @@default_parser. Used XML parser became selectable. * test/rss/test_parser.rb: added tests for RSS::Parser.default_parser. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@5594 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- lib/rss/parser.rb | 85 ++++++++++++++++++++++++++++++++++++-------------- lib/rss/rexmlparser.rb | 10 ++++-- lib/rss/xmlparser.rb | 12 ++++--- lib/rss/xmlscanner.rb | 8 +++-- 4 files changed, 83 insertions(+), 32 deletions(-) (limited to 'lib/rss') diff --git a/lib/rss/parser.rb b/lib/rss/parser.rb index 39ccdfbc36..6434206ae3 100644 --- a/lib/rss/parser.rb +++ b/lib/rss/parser.rb @@ -1,3 +1,5 @@ +require "forwardable" + require "rss/rss" module RSS @@ -19,6 +21,14 @@ module RSS class XMLParserNotFound < Error def initialize super("available XML parser does not found in " << + "#{AVAILABLE_PARSER_LIBRARIES.inspect}.") + end + end + + class NotValidXMLParser < Error + def initialize(parser) + super("#{parser} is not available XML parser. " << + "available XML parser is " << "#{AVAILABLE_PARSERS.inspect}.") end end @@ -32,10 +42,49 @@ module RSS end end + class Parser + + extend Forwardable + + class << self + + @@default_parser = nil + + def default_parser + @@default_parser || AVAILABLE_PARSERS.first + end + + def default_parser=(new_value) + if AVAILABLE_PARSERS.include?(new_value) + @@default_parser = new_value + else + raise NotValidXMLParser.new(new_value) + end + end + + def parse(rss, do_validate=true, ignore_unknown_element=true, parser_class=default_parser) + parser = new(rss, parser_class) + parser.do_validate = do_validate + parser.ignore_unknown_element = ignore_unknown_element + parser.parse + end + + end + + def_delegators(:@parser, :parse, :rss, + :ignore_unknown_element, + :ignore_unknown_element=, :do_validate, + :do_validate=) + + def initialize(rss, parser_class=self.class.default_parser) + @parser = parser_class.new(rss) + end + end + class BaseParser def initialize(rss) - @listener = Listener.new + @listener = listener.new @rss = rss end @@ -66,15 +115,6 @@ module RSS @listener.rss end - class << self - def parse(rss, do_validate=true, ignore_unknown_element=true) - parser = new(rss) - parser.do_validate = do_validate - parser.ignore_unknown_element = ignore_unknown_element - parser.parse - end - end - end class BaseListener @@ -296,7 +336,7 @@ module RSS @last_element.send(setter, next_element) @last_element = next_element @proc_stack.push Proc.new { |text, tags| - p @last_element.class if $DEBUG + p(@last_element.class) if $DEBUG @last_element.content = text if klass.have_content? @last_element.validate_for_stream(tags) if @do_validate @last_element = previous @@ -305,26 +345,25 @@ module RSS end - unless const_defined? :AVAILABLE_PARSERS - AVAILABLE_PARSERS = [ - "rss/xmlparser", - "rss/xmlscanner", - "rss/rexmlparser", + unless const_defined? :AVAILABLE_PARSER_LIBRARIES + AVAILABLE_PARSER_LIBRARIES = [ + ["rss/xmlparser", :XMLParserParser], + ["rss/xmlscanner", :XMLScanParser], + ["rss/rexmlparser", :REXMLParser], ] end - loaded = false - AVAILABLE_PARSERS.each do |parser| + AVAILABLE_PARSERS = [] + + AVAILABLE_PARSER_LIBRARIES.each do |lib, parser| begin - require parser - loaded = true - break + require lib + AVAILABLE_PARSERS.push(const_get(parser)) rescue LoadError end end - unless loaded + if AVAILABLE_PARSERS.empty? raise XMLParserNotFound end end - diff --git a/lib/rss/rexmlparser.rb b/lib/rss/rexmlparser.rb index b3d801597a..541ff82fc3 100644 --- a/lib/rss/rexmlparser.rb +++ b/lib/rss/rexmlparser.rb @@ -8,9 +8,14 @@ end module RSS - class Parser < BaseParser + class REXMLParser < BaseParser private + + def listener + REXMLListener + end + def _parse begin REXML::Document.parse_stream(@rss, @listener) @@ -25,11 +30,10 @@ module RSS end - class Listener < BaseListener + class REXMLListener < BaseListener include REXML::StreamListener include ListenerMixin - def xmldecl(version, encoding, standalone) super diff --git a/lib/rss/xmlparser.rb b/lib/rss/xmlparser.rb index 32061805a6..5a62ce00a1 100644 --- a/lib/rss/xmlparser.rb +++ b/lib/rss/xmlparser.rb @@ -13,7 +13,7 @@ end module RSS - class XMLParser < ::XML::Parser + class REXMLLikeXMLParser < ::XML::Parser include XML::Encoding_ja @@ -39,12 +39,16 @@ module RSS end - class Parser < BaseParser + class XMLParserParser < BaseParser private + def listener + XMLParserListener + end + def _parse begin - parser = XMLParser.new + parser = REXMLLikeXMLParser.new parser.listener = @listener parser.parse(@rss) rescue XMLParserError => e @@ -54,7 +58,7 @@ module RSS end - class Listener < BaseListener + class XMLParserListener < BaseListener include ListenerMixin diff --git a/lib/rss/xmlscanner.rb b/lib/rss/xmlscanner.rb index 81dae96df5..2a80b00e69 100644 --- a/lib/rss/xmlscanner.rb +++ b/lib/rss/xmlscanner.rb @@ -2,9 +2,13 @@ require 'xmlscan/scanner' module RSS - class Parser < BaseParser + class XMLScanParser < BaseParser private + def listener + XMLScanListener + end + def _parse begin XMLScan::XMLScanner.new(@listener).parse(@rss) @@ -15,7 +19,7 @@ module RSS end - class Listener < BaseListener + class XMLScanListener < BaseListener include XMLScan::Visitor include ListenerMixin -- cgit v1.2.3