class KafoParsers::DocParser

Constants

ATTRIBUTE_LINE
HEADER_CONDITION

Attributes

conditions[R]
docs[R]
groups[R]
types[R]

Public Class Methods

new(text) click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 11
def initialize(text)
  @text           = text
  @nesting_buffer = []
  @docs           = {}
  @groups         = {}
  @conditions     = {}
  @types          = Hash.new('string')
  @rdoc           = rdoc_parser.parse(@text)
end

Public Instance Methods

parse(items = @rdoc.parts) click to toggle source

items is array of RDoc::Markup::* on one level

# File lib/kafo_parsers/doc_parser.rb, line 24
def parse(items = @rdoc.parts)
  items.each do |item|
    if item.is_a?(RDoc::Markup::Heading)
      parse_header(item)
    elsif item.is_a?(RDoc::Markup::List) && item.respond_to?(:items)
      parse(item.items)
    elsif item.is_a?(RDoc::Markup::ListItem)
      parse_paragraph(item)
    end
  end
  self
end

Private Instance Methods

current_condition() click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 109
def current_condition
  condition = @nesting_buffer.map(&:condition).select { |c| !c.nil? }.join(' && ')
  condition.empty? ? nil : condition
end
current_groups() click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 101
def current_groups
  @nesting_buffer.map(&:name)
end
current_level() click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 105
def current_level
  current_nesting.nil? ? 0 : current_nesting.level
end
current_nesting() click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 114
def current_nesting
  @nesting_buffer.last
end
nesting(heading) click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 92
def nesting(heading)
  if heading.text =~ HEADER_CONDITION
    text, condition = $1, $2
  else
    text, condition = heading.text, nil
  end
  Nesting.new(text.strip, heading.level, condition)
end
parse_attributes(parameter, attributes) click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 54
def parse_attributes(parameter, attributes)
  condition = nil
  attributes.each do |attribute|
    data        = attribute.match(ATTRIBUTE_LINE)
    name, value = data[1], data[2]

    case name
      when 'type'
        @types[parameter] = value
      when 'condition'
        if condition.nil?
          condition = value
        else
          raise KafoParsers::DocParseError, "Two or more conditions defined for #{name}"
        end
      else
        raise KafoParsers::DocParseError, "Unknown attribute #{name}"
    end

  end
  condition              = [current_condition, condition].compact.join(' && ')
  @conditions[parameter] = condition.empty? ? nil : condition
end
parse_header(heading) click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 78
def parse_header(heading)
  if heading.level > current_level
    @nesting_buffer.push nesting(heading)
  elsif heading.level == current_level
    @nesting_buffer.pop
    @nesting_buffer.push nesting(heading)
  else
    while current_level >= heading.level do
      @nesting_buffer.pop
    end
    @nesting_buffer.push nesting(heading)
  end
end
parse_paragraph(para) click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 39
def parse_paragraph(para)
  # Skip rdoc paras that aren't paragraphs
  return unless (para.parts.to_s.scan("RDoc::Markup::Paragraph") == ["RDoc::Markup::Paragraph"])
  # RDoc (>= 4) makes label an array
  label = para.label.is_a?(Array) ? para.label.first : para.label
  # Documentation must be a list - if there's no label then skip
  return if label.nil?
  key              = label.gsub(/[^A-Za-z0-9_-]/, '')
  @groups[key]     = current_groups
  text_parts       = para.parts.first.parts.map!(&:strip)
  attributes, docs = text_parts.partition { |line| line =~ ATTRIBUTE_LINE }
  parse_attributes(key, attributes)
  @docs[key] = docs
end
rdoc_parser() click to toggle source
# File lib/kafo_parsers/doc_parser.rb, line 118
def rdoc_parser
  if RDoc::Markup.respond_to?(:parse)
    RDoc::Markup
  else # RDoc < 3.10.0
    RDoc::Markup::Parser
  end
end