class TaskJuggler::XMLElement
This class models an XML node that may contain other XML nodes. XML element trees can be constructed with the class constructor and converted into XML.
Public Class Methods
new(name, attributes = {}, selfClosing = false) { |block| ... }
click to toggle source
Construct a new XML element and include it in an existing XMLElement
tree.
# File lib/taskjuggler/XMLElement.rb, line 23 def initialize(name, attributes = {}, selfClosing = false, &block) if (name.nil? && attributes.length > 0) || (!name.nil? && !name.is_a?(String)) raise ArgumentError, "Name must be nil or a String " end @name = name attributes.each do |n, v| if n.nil? || v.nil? raise ArgumentError, "Attribute name (#{n}) or value (#{v}) may not be nil" end unless v.is_a?(String) raise ArgumentError, "Attribute value of #{n} must be a String" end end @attributes = attributes # This can be set to true if <name /> is legal for this element. @selfClosing = selfClosing @children = block ? yield(block) : [] # Allow blocks with single elements not to be Arrays. They will be # automatically converted into Arrays here. unless @children.is_a?(Array) @children = [ @children ] else @children.flatten! end # Convert all children that are text String objects into XMLText # objects. @children.collect! do |c| c.is_a?(String) ? XMLText.new(c) : c end # Make sure we have no nil objects in the list. @children.delete_if { |c| c.nil? } # Now all children must be XMLElement objects. @children.each do |c| unless c.is_a?(XMLElement) raise ArgumentError, "Element must be of type XMLElement, not #{c.class}: #{c.inspect}" end end end
Public Instance Methods
<<(arg)
click to toggle source
Add a new child or a set of new childs to the element.
# File lib/taskjuggler/XMLElement.rb, line 71 def <<(arg) # If the argument is an array, we have to insert each element # individually. if arg.is_a?(XMLElement) @children << arg elsif arg.is_a?(String) @children << XMLText.new(arg) elsif arg.is_a?(Array) # Delete all nil entries arg.delete_if { |i| i.nil? } # Check that the rest are really all XMLElement objects. arg.each do |i| unless i.is_a?(XMLElement) raise ArgumentError, "Element must be of type XMLElement, not #{i.class}: #{i.inspect}" end end @children += arg elsif arg.nil? # Do nothing. Insertions of nil are simply ignored. else raise "Elements must be of type XMLElement not #{arg.class}" end self end
[](attribute)
click to toggle source
Return the value of attribute attribute.
# File lib/taskjuggler/XMLElement.rb, line 105 def [](attribute) @attributes[attribute] end
[]=(attribute, value)
click to toggle source
Add or change attribute to value.
# File lib/taskjuggler/XMLElement.rb, line 98 def []=(attribute, value) raise ArgumentError, "Attribute value #{value} is not a String" unless value.is_a?(String) @attributes[attribute] = value end
to_s(indent = 0)
click to toggle source
Return the element and all sub elements as properly formatted XML.
# File lib/taskjuggler/XMLElement.rb, line 111 def to_s(indent = 0) out = '<' + @name @attributes.keys.sort.each do |attrName| out << " #{attrName}=\"#{escape(@attributes[attrName], true)}\"" end if @children.empty? && @selfClosing out << '/>' else out << '>' @children.each do |child| # We only insert newlines for multiple childs and after a tag has been # closed. if @children.size > 1 && !child.is_a?(XMLText) && out[-1] == ?> out << "\n" + indentation(indent + 1) end out << child.to_s(indent + 1) end out << "\n" + indentation(indent) if @children.size > 1 && out[-1] == ?> out << '</' + @name + '>' end end
Protected Instance Methods
escape(str, quotes = false)
click to toggle source
Escape special characters in input String
str.
# File lib/taskjuggler/XMLElement.rb, line 136 def escape(str, quotes = false) out = '' str.each_utf8_char do |c| case c when '&' out << '&' when '"' out << '\"' else out << c end end out end
indentation(indent)
click to toggle source
# File lib/taskjuggler/XMLElement.rb, line 151 def indentation(indent) ' ' * indent end