Class: Icalendar::Parser
- Inherits:
-
Object
- Object
- Icalendar::Parser
- Defined in:
- lib/icalendar/parser.rb
Defined Under Namespace
Classes: ParseError
Constant Summary collapse
- CLEAN_BAD_WRAPPING_GSUB_REGEX =
/\r?\n[ \t]/.freeze
- WRAP_PROPERTY_VALUE_DELIMETER_REGEX =
/(?<!\\)([,;])/.freeze
- WRAP_PROPERTY_VALUE_SPLIT_REGEX =
/(?<!\\)[;,]/.freeze
- WRAP_IN_ARRAY_REGEX_1 =
/(?<!\\)[,;]/.freeze
- WRAP_IN_ARRAY_REGEX_2 =
/(?<!\\);/.freeze
- GET_WRAPPER_CLASS_GSUB_REGEX =
/(?:\A|-)(.)/.freeze
Instance Attribute Summary collapse
-
#component_class ⇒ Object
writeonly
Sets the attribute component_class.
-
#source ⇒ Object
readonly
Returns the value of attribute source.
-
#strict ⇒ Object
readonly
Returns the value of attribute strict.
-
#timezone_store ⇒ Object
readonly
Returns the value of attribute timezone_store.
-
#verbose ⇒ Object
readonly
Returns the value of attribute verbose.
Class Method Summary collapse
Instance Method Summary collapse
- #get_wrapper_class(component, fields) ⇒ Object
-
#initialize(source, strict = false, verbose = false) ⇒ Parser
constructor
A new instance of Parser.
- #parse ⇒ Object
- #parse_property(component, fields = nil) ⇒ Object
- #strict? ⇒ Boolean
- #verbose? ⇒ Boolean
- #wrap_in_array?(klass, value, multi_property) ⇒ Boolean
- #wrap_property_value(component, fields, multi_property) ⇒ Object
Constructor Details
#initialize(source, strict = false, verbose = false) ⇒ Parser
Returns a new instance of Parser.
29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 |
# File 'lib/icalendar/parser.rb', line 29 def initialize(source, strict = false, verbose = false) if source.respond_to? :gets @source = source elsif source.respond_to? :to_s @source = StringIO.new source.to_s, 'r' else msg = 'Icalendar::Parser.new must be called with a String or IO object' Icalendar.fatal msg fail ArgumentError, msg end read_in_data @strict = strict @verbose = verbose @timezone_store = TimezoneStore.new end |
Instance Attribute Details
#component_class=(value) ⇒ Object
Sets the attribute component_class
9 10 11 |
# File 'lib/icalendar/parser.rb', line 9 def component_class=(value) @component_class = value end |
#source ⇒ Object (readonly)
Returns the value of attribute source.
10 11 12 |
# File 'lib/icalendar/parser.rb', line 10 def source @source end |
#strict ⇒ Object (readonly)
Returns the value of attribute strict.
10 11 12 |
# File 'lib/icalendar/parser.rb', line 10 def strict @strict end |
#timezone_store ⇒ Object (readonly)
Returns the value of attribute timezone_store.
10 11 12 |
# File 'lib/icalendar/parser.rb', line 10 def timezone_store @timezone_store end |
#verbose ⇒ Object (readonly)
Returns the value of attribute verbose.
10 11 12 |
# File 'lib/icalendar/parser.rb', line 10 def verbose @verbose end |
Class Method Details
.clean_bad_wrapping(source) ⇒ Object
14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
# File 'lib/icalendar/parser.rb', line 14 def self.clean_bad_wrapping(source) content = if source.respond_to? :read source.read elsif source.respond_to? :to_s source.to_s else msg = 'Icalendar::Parser.clean_bad_wrapping must be called with a String or IO object' Icalendar.fatal msg fail ArgumentError, msg end encoding = content.encoding content.force_encoding(Encoding::ASCII_8BIT) content.gsub(CLEAN_BAD_WRAPPING_GSUB_REGEX, "").force_encoding(encoding) end |
Instance Method Details
#get_wrapper_class(component, fields) ⇒ Object
110 111 112 113 114 115 116 117 118 119 120 |
# File 'lib/icalendar/parser.rb', line 110 def get_wrapper_class(component, fields) klass = component.class.default_property_types[fields[:name]] if !fields[:params]['value'].nil? klass_name = fields[:params].delete('value').first unless klass_name.upcase == klass.value_type klass_name = "Icalendar::Values::#{klass_name.downcase.gsub(GET_WRAPPER_CLASS_GSUB_REGEX) { |m| m[-1].upcase }}" klass = Object.const_get klass_name if Object.const_defined?(klass_name) end end klass end |
#parse ⇒ Object
45 46 47 48 49 50 51 52 53 54 |
# File 'lib/icalendar/parser.rb', line 45 def parse components = [] while (fields = next_fields) component = component_class.new if fields[:name] == 'begin' && fields[:value].downcase == component.ical_name.downcase components << parse_component(component) end end components end |
#parse_property(component, fields = nil) ⇒ Object
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 |
# File 'lib/icalendar/parser.rb', line 56 def parse_property(component, fields = nil) fields = next_fields if fields.nil? prop_name = %w(class method name).include?(fields[:name]) ? "ip_#{fields[:name]}" : fields[:name] multi_property = component.class.multiple_properties.include? prop_name prop_value = wrap_property_value component, fields, multi_property begin method_name = if multi_property "append_#{prop_name}" else "#{prop_name}=" end component.send method_name, prop_value rescue NoMethodError => nme if strict? Icalendar.logger.error "No method \"#{method_name}\" for component #{component}" raise nme else Icalendar.logger.warn "No method \"#{method_name}\" for component #{component}. Appending to custom." if verbose? component.append_custom_property prop_name, prop_value end end end |
#strict? ⇒ Boolean
122 123 124 |
# File 'lib/icalendar/parser.rb', line 122 def strict? !!@strict end |
#verbose? ⇒ Boolean
126 127 128 |
# File 'lib/icalendar/parser.rb', line 126 def verbose? @verbose end |
#wrap_in_array?(klass, value, multi_property) ⇒ Boolean
103 104 105 106 |
# File 'lib/icalendar/parser.rb', line 103 def wrap_in_array?(klass, value, multi_property) klass.value_type != 'RECUR' && ((multi_property && value =~ WRAP_IN_ARRAY_REGEX_1) || value =~ WRAP_IN_ARRAY_REGEX_2) end |
#wrap_property_value(component, fields, multi_property) ⇒ Object
83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 |
# File 'lib/icalendar/parser.rb', line 83 def wrap_property_value(component, fields, multi_property) klass = get_wrapper_class component, fields if wrap_in_array? klass, fields[:value], multi_property delimiter = fields[:value].match(WRAP_PROPERTY_VALUE_DELIMETER_REGEX)[1] Icalendar::Values::Helpers::Array.new fields[:value].split(WRAP_PROPERTY_VALUE_SPLIT_REGEX), klass, fields[:params], delimiter: delimiter else klass.new fields[:value], fields[:params] end rescue Icalendar::Values::DateTime::FormatError => fe raise fe if strict? fields[:params]['value'] = ['DATE'] retry end |