tilia-vobject 4.0.0.pre.alpha2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (193) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +19 -0
  3. data/.rubocop.yml +32 -0
  4. data/.simplecov +4 -0
  5. data/.travis.yml +3 -0
  6. data/CHANGELOG.sabre.md +626 -0
  7. data/CONTRIBUTING.md +25 -0
  8. data/Gemfile +17 -0
  9. data/Gemfile.lock +68 -0
  10. data/LICENSE +27 -0
  11. data/LICENSE.sabre +27 -0
  12. data/README.md +63 -0
  13. data/Rakefile +17 -0
  14. data/bin/vobject +7 -0
  15. data/lib/tilia/v_object/birthday_calendar_generator.rb +142 -0
  16. data/lib/tilia/v_object/cli.rb +582 -0
  17. data/lib/tilia/v_object/component/available.rb +107 -0
  18. data/lib/tilia/v_object/component/v_alarm.rb +114 -0
  19. data/lib/tilia/v_object/component/v_availability.rb +128 -0
  20. data/lib/tilia/v_object/component/v_calendar.rb +468 -0
  21. data/lib/tilia/v_object/component/v_card.rb +457 -0
  22. data/lib/tilia/v_object/component/v_event.rb +127 -0
  23. data/lib/tilia/v_object/component/v_free_busy.rb +81 -0
  24. data/lib/tilia/v_object/component/v_journal.rb +75 -0
  25. data/lib/tilia/v_object/component/v_time_zone.rb +51 -0
  26. data/lib/tilia/v_object/component/v_todo.rb +147 -0
  27. data/lib/tilia/v_object/component.rb +591 -0
  28. data/lib/tilia/v_object/date_time_parser.rb +486 -0
  29. data/lib/tilia/v_object/document.rb +218 -0
  30. data/lib/tilia/v_object/element_list.rb +18 -0
  31. data/lib/tilia/v_object/eof_exception.rb +8 -0
  32. data/lib/tilia/v_object/free_busy_data.rb +149 -0
  33. data/lib/tilia/v_object/free_busy_generator.rb +465 -0
  34. data/lib/tilia/v_object/i_tip/broker.rb +909 -0
  35. data/lib/tilia/v_object/i_tip/i_tip_exception.rb +9 -0
  36. data/lib/tilia/v_object/i_tip/message.rb +109 -0
  37. data/lib/tilia/v_object/i_tip/same_organizer_for_all_components_exception.rb +13 -0
  38. data/lib/tilia/v_object/i_tip.rb +10 -0
  39. data/lib/tilia/v_object/node.rb +192 -0
  40. data/lib/tilia/v_object/parameter.rb +327 -0
  41. data/lib/tilia/v_object/parse_exception.rb +7 -0
  42. data/lib/tilia/v_object/parser/json.rb +149 -0
  43. data/lib/tilia/v_object/parser/mime_dir.rb +543 -0
  44. data/lib/tilia/v_object/parser/parser.rb +61 -0
  45. data/lib/tilia/v_object/parser/xml/element/key_value.rb +60 -0
  46. data/lib/tilia/v_object/parser/xml/element.rb +11 -0
  47. data/lib/tilia/v_object/parser/xml.rb +322 -0
  48. data/lib/tilia/v_object/parser.rb +10 -0
  49. data/lib/tilia/v_object/property/binary.rb +96 -0
  50. data/lib/tilia/v_object/property/boolean.rb +57 -0
  51. data/lib/tilia/v_object/property/flat_text.rb +52 -0
  52. data/lib/tilia/v_object/property/float_value.rb +107 -0
  53. data/lib/tilia/v_object/property/i_calendar/cal_address.rb +49 -0
  54. data/lib/tilia/v_object/property/i_calendar/date.rb +15 -0
  55. data/lib/tilia/v_object/property/i_calendar/date_time.rb +330 -0
  56. data/lib/tilia/v_object/property/i_calendar/duration.rb +65 -0
  57. data/lib/tilia/v_object/property/i_calendar/period.rb +124 -0
  58. data/lib/tilia/v_object/property/i_calendar/recur.rb +173 -0
  59. data/lib/tilia/v_object/property/i_calendar.rb +14 -0
  60. data/lib/tilia/v_object/property/integer_value.rb +60 -0
  61. data/lib/tilia/v_object/property/text.rb +352 -0
  62. data/lib/tilia/v_object/property/time.rb +85 -0
  63. data/lib/tilia/v_object/property/unknown.rb +30 -0
  64. data/lib/tilia/v_object/property/uri.rb +78 -0
  65. data/lib/tilia/v_object/property/utc_offset.rb +56 -0
  66. data/lib/tilia/v_object/property/v_card/date.rb +31 -0
  67. data/lib/tilia/v_object/property/v_card/date_and_or_time.rb +343 -0
  68. data/lib/tilia/v_object/property/v_card/date_time.rb +22 -0
  69. data/lib/tilia/v_object/property/v_card/language_tag.rb +41 -0
  70. data/lib/tilia/v_object/property/v_card/time_stamp.rb +74 -0
  71. data/lib/tilia/v_object/property/v_card.rb +13 -0
  72. data/lib/tilia/v_object/property.rb +532 -0
  73. data/lib/tilia/v_object/reader.rb +73 -0
  74. data/lib/tilia/v_object/recur/event_iterator.rb +417 -0
  75. data/lib/tilia/v_object/recur/no_instances_exception.rb +11 -0
  76. data/lib/tilia/v_object/recur/r_date_iterator.rb +138 -0
  77. data/lib/tilia/v_object/recur/r_rule_iterator.rb +717 -0
  78. data/lib/tilia/v_object/recur.rb +10 -0
  79. data/lib/tilia/v_object/settings.rb +32 -0
  80. data/lib/tilia/v_object/splitter/i_calendar.rb +95 -0
  81. data/lib/tilia/v_object/splitter/splitter_interface.rb +31 -0
  82. data/lib/tilia/v_object/splitter/v_card.rb +56 -0
  83. data/lib/tilia/v_object/splitter.rb +9 -0
  84. data/lib/tilia/v_object/string_util.rb +58 -0
  85. data/lib/tilia/v_object/time_zone_data/exchange_zones.rb +96 -0
  86. data/lib/tilia/v_object/time_zone_data/lotus_zones.rb +104 -0
  87. data/lib/tilia/v_object/time_zone_data/php_zones.rb +49 -0
  88. data/lib/tilia/v_object/time_zone_data/windows_zones.rb +121 -0
  89. data/lib/tilia/v_object/time_zone_data.rb +10 -0
  90. data/lib/tilia/v_object/time_zone_util.rb +213 -0
  91. data/lib/tilia/v_object/uuid_util.rb +51 -0
  92. data/lib/tilia/v_object/v_card_converter.rb +354 -0
  93. data/lib/tilia/v_object/version.rb +9 -0
  94. data/lib/tilia/v_object/writer.rb +56 -0
  95. data/lib/tilia/v_object.rb +45 -0
  96. data/lib/tilia/vobject.rb +1 -0
  97. data/resources/schema/xcal.rng +1192 -0
  98. data/resources/schema/xcard.rng +388 -0
  99. data/test/test_helper.rb +56 -0
  100. data/test/v_object/attach_issue_test.rb +19 -0
  101. data/test/v_object/birthday_calendar_generator_test.rb +463 -0
  102. data/test/v_object/cli_mock.rb +19 -0
  103. data/test/v_object/cli_test.rb +460 -0
  104. data/test/v_object/component/available_test.rb +59 -0
  105. data/test/v_object/component/v_alarm_test.rb +160 -0
  106. data/test/v_object/component/v_availability_test.rb +388 -0
  107. data/test/v_object/component/v_calendar_test.rb +646 -0
  108. data/test/v_object/component/v_card_test.rb +258 -0
  109. data/test/v_object/component/v_event_test.rb +85 -0
  110. data/test/v_object/component/v_free_busy_test.rb +59 -0
  111. data/test/v_object/component/v_journal_test.rb +85 -0
  112. data/test/v_object/component/v_time_zone_test.rb +47 -0
  113. data/test/v_object/component/v_todo_test.rb +172 -0
  114. data/test/v_object/component_test.rb +419 -0
  115. data/test/v_object/date_time_parser_test.rb +526 -0
  116. data/test/v_object/document_test.rb +71 -0
  117. data/test/v_object/element_list_test.rb +27 -0
  118. data/test/v_object/em_client_test.rb +53 -0
  119. data/test/v_object/empty_parameter_test.rb +65 -0
  120. data/test/v_object/empty_value_issue_test.rb +25 -0
  121. data/test/v_object/fake_component.rb +21 -0
  122. data/test/v_object/free_busy_data_test.rb +285 -0
  123. data/test/v_object/free_busy_generator_test.rb +637 -0
  124. data/test/v_object/google_colon_escaping_test.rb +27 -0
  125. data/test/v_object/i_calendar/attach_parse_test.rb +24 -0
  126. data/test/v_object/i_tip/broker_attendee_reply_test.rb +1042 -0
  127. data/test/v_object/i_tip/broker_delete_event_test.rb +175 -0
  128. data/test/v_object/i_tip/broker_new_event_test.rb +440 -0
  129. data/test/v_object/i_tip/broker_process_message_test.rb +153 -0
  130. data/test/v_object/i_tip/broker_process_reply_test.rb +402 -0
  131. data/test/v_object/i_tip/broker_tester.rb +71 -0
  132. data/test/v_object/i_tip/broker_update_event_test.rb +763 -0
  133. data/test/v_object/i_tip/evolution_test.rb +2644 -0
  134. data/test/v_object/i_tip/message_test.rb +25 -0
  135. data/test/v_object/issue153.vcf +352 -0
  136. data/test/v_object/issue153_test.rb +12 -0
  137. data/test/v_object/issue26_test.rb +25 -0
  138. data/test/v_object/issue36_work_around_test.rb +37 -0
  139. data/test/v_object/issue40_test.rb +26 -0
  140. data/test/v_object/issue64.vcf +351 -0
  141. data/test/v_object/issue64_test.rb +17 -0
  142. data/test/v_object/issue96_test.rb +22 -0
  143. data/test/v_object/issue_undefined_index_test.rb +24 -0
  144. data/test/v_object/j_cal_test.rb +150 -0
  145. data/test/v_object/j_card_test.rb +192 -0
  146. data/test/v_object/line_folding_issue_test.rb +19 -0
  147. data/test/v_object/mock_document.rb +6 -0
  148. data/test/v_object/parameter_test.rb +109 -0
  149. data/test/v_object/parser/json_test.rb +370 -0
  150. data/test/v_object/parser/mime_dir_test.rb +14 -0
  151. data/test/v_object/parser/quoted_printable_test.rb +78 -0
  152. data/test/v_object/parser/xml_test.rb +2563 -0
  153. data/test/v_object/property/binary_test.rb +12 -0
  154. data/test/v_object/property/boolean_test.rb +18 -0
  155. data/test/v_object/property/compound_test.rb +43 -0
  156. data/test/v_object/property/float_test.rb +20 -0
  157. data/test/v_object/property/i_calendar/cal_address_test.rb +26 -0
  158. data/test/v_object/property/i_calendar/date_time_test.rb +303 -0
  159. data/test/v_object/property/i_calendar/duration_test.rb +14 -0
  160. data/test/v_object/property/i_calendar/recur_test.rb +39 -0
  161. data/test/v_object/property/text_test.rb +81 -0
  162. data/test/v_object/property/v_card/date_and_or_time_test.rb +205 -0
  163. data/test/v_object/property/v_card/language_tag_test.rb +35 -0
  164. data/test/v_object/property_test.rb +338 -0
  165. data/test/v_object/reader_test.rb +403 -0
  166. data/test/v_object/recur/event_iterator/by_month_in_daily_test.rb +52 -0
  167. data/test/v_object/recur/event_iterator/by_set_pos_hang_test.rb +55 -0
  168. data/test/v_object/recur/event_iterator/expand_floating_times_test.rb +109 -0
  169. data/test/v_object/recur/event_iterator/fifth_tuesday_problem_test.rb +45 -0
  170. data/test/v_object/recur/event_iterator/incorrect_expand_test.rb +53 -0
  171. data/test/v_object/recur/event_iterator/infinite_loop_problem_test.rb +75 -0
  172. data/test/v_object/recur/event_iterator/issue48_test.rb +43 -0
  173. data/test/v_object/recur/event_iterator/issue50_test.rb +123 -0
  174. data/test/v_object/recur/event_iterator/main_test.rb +1222 -0
  175. data/test/v_object/recur/event_iterator/missing_overridden_test.rb +55 -0
  176. data/test/v_object/recur/event_iterator/no_instances_test.rb +32 -0
  177. data/test/v_object/recur/event_iterator/override_first_event_test.rb +106 -0
  178. data/test/v_object/recur/r_date_iterator_test.rb +44 -0
  179. data/test/v_object/recur/r_rule_iterator_test.rb +608 -0
  180. data/test/v_object/recurrence_iterator/UntilRespectsTimezoneTest.ics +39 -0
  181. data/test/v_object/slash_r_test.rb +15 -0
  182. data/test/v_object/splitter/i_calendar_test.rb +299 -0
  183. data/test/v_object/splitter/v_card_test.rb +173 -0
  184. data/test/v_object/string_util_test.rb +37 -0
  185. data/test/v_object/test_case.rb +42 -0
  186. data/test/v_object/time_zone_util_test.rb +271 -0
  187. data/test/v_object/uuid_util_test.rb +18 -0
  188. data/test/v_object/v_card21_test.rb +43 -0
  189. data/test/v_object/v_card_converter_test.rb +419 -0
  190. data/test/v_object/version_test.rb +15 -0
  191. data/test/v_object/writer_test.rb +33 -0
  192. data/tilia-vobject.gemspec +17 -0
  193. metadata +308 -0
@@ -0,0 +1,2563 @@
1
+ require 'test_helper'
2
+ require 'v_object/test_case'
3
+
4
+ module Tilia
5
+ module VObject
6
+ class XmlTest < TestCase
7
+ # Check this equality:
8
+ # XML -> object model -> MIME Dir.
9
+ def assert_xml_equals_to_mime_dir(xml, mimedir)
10
+ component = Tilia::VObject::Reader.read_xml(xml)
11
+ assert_v_obj_equals(mimedir, component)
12
+ end
13
+
14
+ # Check this (reflexive) equality:
15
+ # XML -> object model -> MIME Dir -> object model -> XML.
16
+ def assert_xml_reflexively_equals_to_mime_dir(xml, mimedir)
17
+ assert_xml_equals_to_mime_dir(xml, mimedir)
18
+
19
+ component = Tilia::VObject::Reader.read(mimedir)
20
+ assert_equal(Hash.from_xml(xml), Hash.from_xml(Tilia::VObject::Writer.write_xml(component)))
21
+ end
22
+
23
+ def test_rfc6321_example1
24
+ xml = <<XML
25
+ <?xml version="1.0" encoding="UTF-8"?>
26
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
27
+ <vcalendar>
28
+ <properties>
29
+ <calscale>
30
+ <text>GREGORIAN</text>
31
+ </calscale>
32
+ <prodid>
33
+ <text>-//Example Inc.//Example Calendar//EN</text>
34
+ </prodid>
35
+ <version>
36
+ <text>2.0</text>
37
+ </version>
38
+ </properties>
39
+ <components>
40
+ <vevent>
41
+ <properties>
42
+ <dtstamp>
43
+ <date-time>2008-02-05T19:12:24Z</date-time>
44
+ </dtstamp>
45
+ <dtstart>
46
+ <date>2008-10-06</date>
47
+ </dtstart>
48
+ <summary>
49
+ <text>Planning meeting</text>
50
+ </summary>
51
+ <uid>
52
+ <text>4088E990AD89CB3DBB484909</text>
53
+ </uid>
54
+ </properties>
55
+ </vevent>
56
+ </components>
57
+ </vcalendar>
58
+ </icalendar>
59
+ XML
60
+
61
+ # VERSION comes first because this is required by vCard 4.0.
62
+ vobj = <<VOBJ
63
+ BEGIN:VCALENDAR
64
+ VERSION:2.0
65
+ CALSCALE:GREGORIAN
66
+ PRODID:-//Example Inc.//Example Calendar//EN
67
+ BEGIN:VEVENT
68
+ DTSTAMP:20080205T191224Z
69
+ DTSTART;VALUE=DATE:20081006
70
+ SUMMARY:Planning meeting
71
+ UID:4088E990AD89CB3DBB484909
72
+ END:VEVENT
73
+ END:VCALENDAR
74
+ VOBJ
75
+
76
+ assert_xml_equals_to_mime_dir(xml, vobj)
77
+ end
78
+
79
+ def test_rfc6321_example2
80
+ xml = <<XML
81
+ <?xml version="1.0" encoding="UTF-8" ?>
82
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
83
+ <vcalendar>
84
+ <properties>
85
+ <prodid>
86
+ <text>-//Example Inc.//Example Client//EN</text>
87
+ </prodid>
88
+ <version>
89
+ <text>2.0</text>
90
+ </version>
91
+ </properties>
92
+ <components>
93
+ <vtimezone>
94
+ <properties>
95
+ <last-modified>
96
+ <date-time>2004-01-10T03:28:45Z</date-time>
97
+ </last-modified>
98
+ <tzid><text>US/Eastern</text></tzid>
99
+ </properties>
100
+ <components>
101
+ <daylight>
102
+ <properties>
103
+ <dtstart>
104
+ <date-time>2000-04-04T02:00:00</date-time>
105
+ </dtstart>
106
+ <rrule>
107
+ <recur>
108
+ <freq>YEARLY</freq>
109
+ <byday>1SU</byday>
110
+ <bymonth>4</bymonth>
111
+ </recur>
112
+ </rrule>
113
+ <tzname>
114
+ <text>EDT</text>
115
+ </tzname>
116
+ <tzoffsetfrom>
117
+ <utc-offset>-05:00</utc-offset>
118
+ </tzoffsetfrom>
119
+ <tzoffsetto>
120
+ <utc-offset>-04:00</utc-offset>
121
+ </tzoffsetto>
122
+ </properties>
123
+ </daylight>
124
+ <standard>
125
+ <properties>
126
+ <dtstart>
127
+ <date-time>2000-10-26T02:00:00</date-time>
128
+ </dtstart>
129
+ <rrule>
130
+ <recur>
131
+ <freq>YEARLY</freq>
132
+ <byday>-1SU</byday>
133
+ <bymonth>10</bymonth>
134
+ </recur>
135
+ </rrule>
136
+ <tzname>
137
+ <text>EST</text>
138
+ </tzname>
139
+ <tzoffsetfrom>
140
+ <utc-offset>-04:00</utc-offset>
141
+ </tzoffsetfrom>
142
+ <tzoffsetto>
143
+ <utc-offset>-05:00</utc-offset>
144
+ </tzoffsetto>
145
+ </properties>
146
+ </standard>
147
+ </components>
148
+ </vtimezone>
149
+ <vevent>
150
+ <properties>
151
+ <dtstamp>
152
+ <date-time>2006-02-06T00:11:21Z</date-time>
153
+ </dtstamp>
154
+ <dtstart>
155
+ <parameters>
156
+ <tzid><text>US/Eastern</text></tzid>
157
+ </parameters>
158
+ <date-time>2006-01-02T12:00:00</date-time>
159
+ </dtstart>
160
+ <duration>
161
+ <duration>PT1H</duration>
162
+ </duration>
163
+ <rrule>
164
+ <recur>
165
+ <freq>DAILY</freq>
166
+ <count>5</count>
167
+ </recur>
168
+ </rrule>
169
+ <rdate>
170
+ <parameters>
171
+ <tzid><text>US/Eastern</text></tzid>
172
+ </parameters>
173
+ <period>
174
+ <start>2006-01-02T15:00:00</start>
175
+ <duration>PT2H</duration>
176
+ </period>
177
+ </rdate>
178
+ <summary>
179
+ <text>Event #2</text>
180
+ </summary>
181
+ <description>
182
+ <text>We are having a meeting all this week at 12
183
+ pm for one hour, with an additional meeting on the first day
184
+ 2 hours long.&#x0a;Please bring your own lunch for the 12 pm
185
+ meetings.</text>
186
+ </description>
187
+ <uid>
188
+ <text>00959BC664CA650E933C892C@example.com</text>
189
+ </uid>
190
+ </properties>
191
+ </vevent>
192
+ <vevent>
193
+ <properties>
194
+ <dtstamp>
195
+ <date-time>2006-02-06T00:11:21Z</date-time>
196
+ </dtstamp>
197
+ <dtstart>
198
+ <parameters>
199
+ <tzid><text>US/Eastern</text></tzid>
200
+ </parameters>
201
+ <date-time>2006-01-04T14:00:00</date-time>
202
+ </dtstart>
203
+ <duration>
204
+ <duration>PT1H</duration>
205
+ </duration>
206
+ <recurrence-id>
207
+ <parameters>
208
+ <tzid><text>US/Eastern</text></tzid>
209
+ </parameters>
210
+ <date-time>2006-01-04T12:00:00</date-time>
211
+ </recurrence-id>
212
+ <summary>
213
+ <text>Event #2 bis</text>
214
+ </summary>
215
+ <uid>
216
+ <text>00959BC664CA650E933C892C@example.com</text>
217
+ </uid>
218
+ </properties>
219
+ </vevent>
220
+ </components>
221
+ </vcalendar>
222
+ </icalendar>
223
+ XML
224
+ vobj = <<VOBJ
225
+ BEGIN:VCALENDAR
226
+ VERSION:2.0
227
+ PRODID:-//Example Inc.//Example Client//EN
228
+ BEGIN:VTIMEZONE
229
+ LAST-MODIFIED:20040110T032845Z
230
+ TZID:US/Eastern
231
+ BEGIN:DAYLIGHT
232
+ DTSTART:20000404T020000
233
+ RRULE:FREQ=YEARLY;BYDAY=1SU;BYMONTH=4
234
+ TZNAME:EDT
235
+ TZOFFSETFROM:-0500
236
+ TZOFFSETTO:-0400
237
+ END:DAYLIGHT
238
+ BEGIN:STANDARD
239
+ DTSTART:20001026T020000
240
+ RRULE:FREQ=YEARLY;BYDAY=-1SU;BYMONTH=10
241
+ TZNAME:EST
242
+ TZOFFSETFROM:-0400
243
+ TZOFFSETTO:-0500
244
+ END:STANDARD
245
+ END:VTIMEZONE
246
+ BEGIN:VEVENT
247
+ DTSTAMP:20060206T001121Z
248
+ DTSTART;TZID=US/Eastern:20060102T120000
249
+ DURATION:PT1H
250
+ RRULE:FREQ=DAILY;COUNT=5
251
+ RDATE;TZID=US/Eastern;VALUE=PERIOD:20060102T150000/PT2H
252
+ SUMMARY:Event #2
253
+ DESCRIPTION:We are having a meeting all this week at 12\\npm for one hour\\,
254
+ with an additional meeting on the first day\\n2 hours long.\\nPlease bring y
255
+ our own lunch for the 12 pm\\nmeetings.
256
+ UID:00959BC664CA650E933C892C@example.com
257
+ END:VEVENT
258
+ BEGIN:VEVENT
259
+ DTSTAMP:20060206T001121Z
260
+ DTSTART;TZID=US/Eastern:20060104T140000
261
+ DURATION:PT1H
262
+ RECURRENCE-ID;TZID=US/Eastern:20060104T120000
263
+ SUMMARY:Event #2 bis
264
+ UID:00959BC664CA650E933C892C@example.com
265
+ END:VEVENT
266
+ END:VCALENDAR
267
+ VOBJ
268
+ vobj.gsub!('hour\\,', 'hour\\, ') # there was a space at EOL the editor always ate
269
+
270
+ component = Tilia::VObject::Reader.read_xml(xml)
271
+ assert_v_obj_equals(vobj, Tilia::VObject::Writer.write(component))
272
+ end
273
+
274
+ # iCalendar Stream.
275
+ def test_rfc6321_section3_2
276
+ xml = <<XML
277
+ <?xml version="1.0" encoding="UTF-8"?>
278
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
279
+ <vcalendar/>
280
+ </icalendar>
281
+ XML
282
+
283
+ vobj = <<VOBJ
284
+ BEGIN:VCALENDAR
285
+ END:VCALENDAR
286
+ VOBJ
287
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
288
+ end
289
+
290
+ # All components exist.
291
+ def test_rfc6321_section3_3
292
+ xml = <<XML
293
+ <?xml version="1.0" encoding="UTF-8"?>
294
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
295
+ <vcalendar>
296
+ <components>
297
+ <vtimezone/>
298
+ <vevent/>
299
+ <vtodo/>
300
+ <vjournal/>
301
+ <vfreebusy/>
302
+ <standard/>
303
+ <daylight/>
304
+ <valarm/>
305
+ </components>
306
+ </vcalendar>
307
+ </icalendar>
308
+ XML
309
+
310
+ vobj = <<VOBJ
311
+ BEGIN:VCALENDAR
312
+ BEGIN:VTIMEZONE
313
+ END:VTIMEZONE
314
+ BEGIN:VEVENT
315
+ END:VEVENT
316
+ BEGIN:VTODO
317
+ END:VTODO
318
+ BEGIN:VJOURNAL
319
+ END:VJOURNAL
320
+ BEGIN:VFREEBUSY
321
+ END:VFREEBUSY
322
+ BEGIN:STANDARD
323
+ END:STANDARD
324
+ BEGIN:DAYLIGHT
325
+ END:DAYLIGHT
326
+ BEGIN:VALARM
327
+ END:VALARM
328
+ END:VCALENDAR
329
+ VOBJ
330
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
331
+ end
332
+
333
+ # Properties, Special Cases, GEO.
334
+ def test_rfc6321_section3_4_1_2
335
+ xml = <<XML
336
+ <?xml version="1.0" encoding="UTF-8"?>
337
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
338
+ <vcalendar>
339
+ <properties>
340
+ <geo>
341
+ <latitude>37.386013</latitude>
342
+ <longitude>-122.082932</longitude>
343
+ </geo>
344
+ </properties>
345
+ </vcalendar>
346
+ </icalendar>
347
+ XML
348
+
349
+ vobj = <<VOBJ
350
+ BEGIN:VCALENDAR
351
+ GEO:37.386013;-122.082932
352
+ END:VCALENDAR
353
+ VOBJ
354
+
355
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
356
+ end
357
+
358
+ # Properties, Special Cases, REQUEST-STATUS.
359
+ def test_rfc6321_section3_4_1_3
360
+ # Example 1 of RFC5545, Section 3.8.8.3.
361
+ xml = <<XML
362
+ <?xml version="1.0" encoding="UTF-8"?>
363
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
364
+ <vcalendar>
365
+ <properties>
366
+ <request-status>
367
+ <code>2.0</code>
368
+ <description>Success</description>
369
+ </request-status>
370
+ </properties>
371
+ </vcalendar>
372
+ </icalendar>
373
+ XML
374
+ vobj = <<VOBJ
375
+ BEGIN:VCALENDAR
376
+ REQUEST-STATUS:2.0;Success
377
+ END:VCALENDAR
378
+ VOBJ
379
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
380
+
381
+ # Example 2 of RFC5545, Section 3.8.8.3.
382
+ xml = <<XML
383
+ <?xml version="1.0" encoding="UTF-8"?>
384
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
385
+ <vcalendar>
386
+ <properties>
387
+ <request-status>
388
+ <code>3.1</code>
389
+ <description>Invalid property value</description>
390
+ <data>DTSTART:96-Apr-01</data>
391
+ </request-status>
392
+ </properties>
393
+ </vcalendar>
394
+ </icalendar>
395
+ XML
396
+ vobj = <<VOBJ
397
+ BEGIN:VCALENDAR
398
+ REQUEST-STATUS:3.1;Invalid property value;DTSTART:96-Apr-01
399
+ END:VCALENDAR
400
+ VOBJ
401
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
402
+
403
+ # Example 3 of RFC5545, Section 3.8.8.3.
404
+ xml = <<XML
405
+ <?xml version="1.0" encoding="UTF-8"?>
406
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
407
+ <vcalendar>
408
+ <properties>
409
+ <request-status>
410
+ <code>2.8</code>
411
+ <description>Success, repeating event ignored. Scheduled as a single event.</description>
412
+ <data>RRULE:FREQ=WEEKLY;INTERVAL=2</data>
413
+ </request-status>
414
+ </properties>
415
+ </vcalendar>
416
+ </icalendar>
417
+ XML
418
+ vobj = <<VOBJ
419
+ BEGIN:VCALENDAR
420
+ REQUEST-STATUS:2.8;Success\\, repeating event ignored. Scheduled as a single
421
+ event.;RRULE:FREQ=WEEKLY\\;INTERVAL=2
422
+ END:VCALENDAR
423
+ VOBJ
424
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
425
+
426
+ # Example 4 of RFC5545, Section 3.8.8.3.
427
+ xml = <<XML
428
+ <?xml version="1.0" encoding="UTF-8"?>
429
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
430
+ <vcalendar>
431
+ <properties>
432
+ <request-status>
433
+ <code>4.1</code>
434
+ <description>Event conflict. Date-time is busy.</description>
435
+ </request-status>
436
+ </properties>
437
+ </vcalendar>
438
+ </icalendar>
439
+ XML
440
+ vobj = <<VOBJ
441
+ BEGIN:VCALENDAR
442
+ REQUEST-STATUS:4.1;Event conflict. Date-time is busy.
443
+ END:VCALENDAR
444
+ VOBJ
445
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
446
+
447
+ # Example 5 of RFC5545, Section 3.8.8.3.
448
+ xml = <<XML
449
+ <?xml version="1.0" encoding="UTF-8"?>
450
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
451
+ <vcalendar>
452
+ <properties>
453
+ <request-status>
454
+ <code>3.7</code>
455
+ <description>Invalid calendar user</description>
456
+ <data>ATTENDEE:mailto:jsmith@example.com</data>
457
+ </request-status>
458
+ </properties>
459
+ </vcalendar>
460
+ </icalendar>
461
+ XML
462
+ vobj = <<VOBJ
463
+ BEGIN:VCALENDAR
464
+ REQUEST-STATUS:3.7;Invalid calendar user;ATTENDEE:mailto:jsmith@example.com
465
+ END:VCALENDAR
466
+ VOBJ
467
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
468
+ end
469
+
470
+ # Values, Binary.
471
+ def test_rfc6321_section3_6_1
472
+ xml = <<XML
473
+ <?xml version="1.0" encoding="UTF-8"?>
474
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
475
+ <vcalendar>
476
+ <properties>
477
+ <attach>
478
+ <binary>SGVsbG8gV29ybGQh</binary>
479
+ </attach>
480
+ </properties>
481
+ </vcalendar>
482
+ </icalendar>
483
+ XML
484
+ vobj = <<VOBJ
485
+ BEGIN:VCALENDAR
486
+ ATTACH:SGVsbG8gV29ybGQh
487
+ END:VCALENDAR
488
+ VOBJ
489
+ assert_xml_equals_to_mime_dir(xml, vobj)
490
+
491
+ # In vCard 4, BINARY no longer exists and is replaced by URI.
492
+ xml = <<XML
493
+ <?xml version="1.0" encoding="UTF-8"?>
494
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
495
+ <vcalendar>
496
+ <properties>
497
+ <attach>
498
+ <uri>SGVsbG8gV29ybGQh</uri>
499
+ </attach>
500
+ </properties>
501
+ </vcalendar>
502
+ </icalendar>
503
+ XML
504
+ vobj = <<VOBJ
505
+ BEGIN:VCALENDAR
506
+ ATTACH:SGVsbG8gV29ybGQh
507
+ END:VCALENDAR
508
+ VOBJ
509
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
510
+ end
511
+
512
+ # Values, Boolean.
513
+ def test_rfc6321_section3_6_2
514
+ xml = <<XML
515
+ <?xml version="1.0" encoding="UTF-8"?>
516
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
517
+ <vcalendar>
518
+ <properties>
519
+ <attendee>
520
+ <parameters>
521
+ <rsvp><boolean>true</boolean></rsvp>
522
+ </parameters>
523
+ <cal-address>mailto:cyrus@example.com</cal-address>
524
+ </attendee>
525
+ </properties>
526
+ </vcalendar>
527
+ </icalendar>
528
+ XML
529
+ vobj = <<VOBJ
530
+ BEGIN:VCALENDAR
531
+ ATTENDEE;RSVP=true:mailto:cyrus@example.com
532
+ END:VCALENDAR
533
+ VOBJ
534
+ assert_xml_equals_to_mime_dir(xml, vobj)
535
+ end
536
+
537
+ # Values, Calendar User Address.
538
+ def test_rfc6321_section3_6_3
539
+ xml = <<XML
540
+ <?xml version="1.0" encoding="UTF-8"?>
541
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
542
+ <vcalendar>
543
+ <properties>
544
+ <attendee>
545
+ <cal-address>mailto:cyrus@example.com</cal-address>
546
+ </attendee>
547
+ </properties>
548
+ </vcalendar>
549
+ </icalendar>
550
+ XML
551
+ vobj = <<VOBJ
552
+ BEGIN:VCALENDAR
553
+ ATTENDEE:mailto:cyrus@example.com
554
+ END:VCALENDAR
555
+ VOBJ
556
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
557
+ end
558
+
559
+ # Values, Date.
560
+ def test_rfc6321_section3_6_4
561
+ xml = <<XML
562
+ <?xml version="1.0" encoding="UTF-8"?>
563
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
564
+ <vcalendar>
565
+ <properties>
566
+ <dtstart>
567
+ <date>2011-05-17</date>
568
+ </dtstart>
569
+ </properties>
570
+ </vcalendar>
571
+ </icalendar>
572
+ XML
573
+ vobj = <<VOBJ
574
+ BEGIN:VCALENDAR
575
+ DTSTART;VALUE=DATE:20110517
576
+ END:VCALENDAR
577
+ VOBJ
578
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
579
+ end
580
+
581
+ # Values, Date-Time.
582
+ def test_rfc6321_section3_6_5
583
+ xml = <<XML
584
+ <?xml version="1.0" encoding="UTF-8"?>
585
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
586
+ <vcalendar>
587
+ <properties>
588
+ <dtstart>
589
+ <date-time>2011-05-17T12:00:00</date-time>
590
+ </dtstart>
591
+ </properties>
592
+ </vcalendar>
593
+ </icalendar>
594
+ XML
595
+ vobj = <<VOBJ
596
+ BEGIN:VCALENDAR
597
+ DTSTART:20110517T120000
598
+ END:VCALENDAR
599
+ VOBJ
600
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
601
+ end
602
+
603
+ # Values, Duration.
604
+ def test_rfc6321_section3_6_6
605
+ xml = <<XML
606
+ <?xml version="1.0" encoding="UTF-8"?>
607
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
608
+ <vcalendar>
609
+ <properties>
610
+ <duration>
611
+ <duration>P1D</duration>
612
+ </duration>
613
+ </properties>
614
+ </vcalendar>
615
+ </icalendar>
616
+ XML
617
+ vobj = <<VOBJ
618
+ BEGIN:VCALENDAR
619
+ DURATION:P1D
620
+ END:VCALENDAR
621
+ VOBJ
622
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
623
+ end
624
+
625
+ # Values, Float.
626
+ def test_rfc6321_section3_6_7
627
+ # GEO uses <float /> with a positive and a non-negative numbers.
628
+ test_rfc6321_section3_4_1_2
629
+ end
630
+
631
+ # Values, Integer.
632
+ def test_rfc6321_section3_6_8
633
+ xml = <<XML
634
+ <?xml version="1.0" encoding="UTF-8"?>
635
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
636
+ <vcalendar>
637
+ <properties>
638
+ <foo>
639
+ <integer>42</integer>
640
+ </foo>
641
+ </properties>
642
+ </vcalendar>
643
+ </icalendar>
644
+ XML
645
+ vobj = <<VOBJ
646
+ BEGIN:VCALENDAR
647
+ FOO:42
648
+ END:VCALENDAR
649
+ VOBJ
650
+ assert_xml_equals_to_mime_dir(xml, vobj)
651
+
652
+ xml = <<XML
653
+ <?xml version="1.0" encoding="UTF-8"?>
654
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
655
+ <vcalendar>
656
+ <properties>
657
+ <foo>
658
+ <integer>-42</integer>
659
+ </foo>
660
+ </properties>
661
+ </vcalendar>
662
+ </icalendar>
663
+ XML
664
+ vobj = <<VOBJ
665
+ BEGIN:VCALENDAR
666
+ FOO:-42
667
+ END:VCALENDAR
668
+ VOBJ
669
+ assert_xml_equals_to_mime_dir(xml, vobj)
670
+ end
671
+
672
+ # Values, Period of Time.
673
+ def test_rfc6321_section3_6_9
674
+ xml = <<XML
675
+ <?xml version="1.0" encoding="UTF-8"?>
676
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
677
+ <vcalendar>
678
+ <properties>
679
+ <freebusy>
680
+ <period>
681
+ <start>2011-05-17T12:00:00</start>
682
+ <duration>P1H</duration>
683
+ </period>
684
+ </freebusy>
685
+ </properties>
686
+ </vcalendar>
687
+ </icalendar>
688
+ XML
689
+ vobj = <<VOBJ
690
+ BEGIN:VCALENDAR
691
+ FREEBUSY:20110517T120000/P1H
692
+ END:VCALENDAR
693
+ VOBJ
694
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
695
+
696
+ xml = <<XML
697
+ <?xml version="1.0" encoding="UTF-8"?>
698
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
699
+ <vcalendar>
700
+ <properties>
701
+ <freebusy>
702
+ <period>
703
+ <start>2011-05-17T12:00:00</start>
704
+ <end>2012-05-17T12:00:00</end>
705
+ </period>
706
+ </freebusy>
707
+ </properties>
708
+ </vcalendar>
709
+ </icalendar>
710
+ XML
711
+ vobj = <<VOBJ
712
+ BEGIN:VCALENDAR
713
+ FREEBUSY:20110517T120000/20120517T120000
714
+ END:VCALENDAR
715
+ VOBJ
716
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
717
+ end
718
+
719
+ # Values, Recurrence Rule.
720
+ def test_rfc6321_section3_6_10
721
+ xml = <<XML
722
+ <?xml version="1.0" encoding="UTF-8"?>
723
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
724
+ <vcalendar>
725
+ <properties>
726
+ <rrule>
727
+ <recur>
728
+ <freq>YEARLY</freq>
729
+ <count>5</count>
730
+ <byday>-1SU</byday>
731
+ <bymonth>10</bymonth>
732
+ </recur>
733
+ </rrule>
734
+ </properties>
735
+ </vcalendar>
736
+ </icalendar>
737
+ XML
738
+ vobj = <<VOBJ
739
+ BEGIN:VCALENDAR
740
+ RRULE:FREQ=YEARLY;COUNT=5;BYDAY=-1SU;BYMONTH=10
741
+ END:VCALENDAR
742
+ VOBJ
743
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
744
+ end
745
+
746
+ # Values, Text.
747
+ def test_rfc6321_section3_6_11
748
+ xml = <<XML
749
+ <?xml version="1.0" encoding="UTF-8"?>
750
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
751
+ <vcalendar>
752
+ <properties>
753
+ <calscale>
754
+ <text>GREGORIAN</text>
755
+ </calscale>
756
+ </properties>
757
+ </vcalendar>
758
+ </icalendar>
759
+ XML
760
+ vobj = <<VOBJ
761
+ BEGIN:VCALENDAR
762
+ CALSCALE:GREGORIAN
763
+ END:VCALENDAR
764
+ VOBJ
765
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
766
+ end
767
+
768
+ # Values, Time.
769
+ def test_rfc6321_section3_6_12
770
+ xml = <<XML
771
+ <?xml version="1.0" encoding="UTF-8"?>
772
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
773
+ <vcalendar>
774
+ <properties>
775
+ <foo>
776
+ <time>12:00:00</time>
777
+ </foo>
778
+ </properties>
779
+ </vcalendar>
780
+ </icalendar>
781
+ XML
782
+ vobj = <<VOBJ
783
+ BEGIN:VCALENDAR
784
+ FOO:120000
785
+ END:VCALENDAR
786
+ VOBJ
787
+ assert_xml_equals_to_mime_dir(xml, vobj)
788
+ end
789
+
790
+ # Values, URI.
791
+ def test_rfc6321_section3_6_13
792
+ xml = <<XML
793
+ <?xml version="1.0" encoding="UTF-8"?>
794
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
795
+ <vcalendar>
796
+ <properties>
797
+ <attach>
798
+ <uri>http://calendar.example.com</uri>
799
+ </attach>
800
+ </properties>
801
+ </vcalendar>
802
+ </icalendar>
803
+ XML
804
+ vobj = <<VOBJ
805
+ BEGIN:VCALENDAR
806
+ ATTACH:http://calendar.example.com
807
+ END:VCALENDAR
808
+ VOBJ
809
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
810
+ end
811
+
812
+ # Values, UTC Offset.
813
+ def test_rfc6321_section3_6_14
814
+ # Example 1 of RFC5545, Section 3.3.14.
815
+ xml = <<XML
816
+ <?xml version="1.0" encoding="UTF-8"?>
817
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
818
+ <vcalendar>
819
+ <properties>
820
+ <tzoffsetfrom>
821
+ <utc-offset>-05:00</utc-offset>
822
+ </tzoffsetfrom>
823
+ </properties>
824
+ </vcalendar>
825
+ </icalendar>
826
+ XML
827
+ vobj = <<VOBJ
828
+ BEGIN:VCALENDAR
829
+ TZOFFSETFROM:-0500
830
+ END:VCALENDAR
831
+ VOBJ
832
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
833
+
834
+ # Example 2 of RFC5545, Section 3.3.14.
835
+ xml = <<XML
836
+ <?xml version="1.0" encoding="UTF-8"?>
837
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
838
+ <vcalendar>
839
+ <properties>
840
+ <tzoffsetfrom>
841
+ <utc-offset>+01:00</utc-offset>
842
+ </tzoffsetfrom>
843
+ </properties>
844
+ </vcalendar>
845
+ </icalendar>
846
+ XML
847
+ vobj = <<VOBJ
848
+ BEGIN:VCALENDAR
849
+ TZOFFSETFROM:+0100
850
+ END:VCALENDAR
851
+ VOBJ
852
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
853
+ end
854
+
855
+ # Handling Unrecognized Properties or Parameters.
856
+ def test_rfc6321_section5
857
+ xml = <<XML
858
+ <?xml version="1.0" encoding="UTF-8"?>
859
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
860
+ <vcalendar>
861
+ <properties>
862
+ <x-property>
863
+ <unknown>20110512T120000Z</unknown>
864
+ </x-property>
865
+ </properties>
866
+ </vcalendar>
867
+ </icalendar>
868
+ XML
869
+ vobj = <<VOBJ
870
+ BEGIN:VCALENDAR
871
+ X-PROPERTY:20110512T120000Z
872
+ END:VCALENDAR
873
+ VOBJ
874
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
875
+
876
+ xml = <<XML
877
+ <?xml version="1.0" encoding="UTF-8"?>
878
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
879
+ <vcalendar>
880
+ <properties>
881
+ <dtstart>
882
+ <parameters>
883
+ <x-param>
884
+ <text>PT30M</text>
885
+ </x-param>
886
+ </parameters>
887
+ <date-time>2011-05-12T13:00:00Z</date-time>
888
+ </dtstart>
889
+ </properties>
890
+ </vcalendar>
891
+ </icalendar>
892
+ XML
893
+ vobj = <<VOBJ
894
+ BEGIN:VCALENDAR
895
+ DTSTART;X-PARAM=PT30M:20110512T130000Z
896
+ END:VCALENDAR
897
+ VOBJ
898
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
899
+ end
900
+
901
+ def test_r_date_with_date_time
902
+ xml = <<XML
903
+ <?xml version="1.0" encoding="UTF-8"?>
904
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
905
+ <vcalendar>
906
+ <properties>
907
+ <rdate>
908
+ <date-time>2008-02-05T19:12:24Z</date-time>
909
+ </rdate>
910
+ </properties>
911
+ </vcalendar>
912
+ </icalendar>
913
+ XML
914
+ vobj = <<VOBJ
915
+ BEGIN:VCALENDAR
916
+ RDATE:20080205T191224Z
917
+ END:VCALENDAR
918
+ VOBJ
919
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
920
+
921
+ xml = <<XML
922
+ <?xml version="1.0" encoding="UTF-8"?>
923
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
924
+ <vcalendar>
925
+ <properties>
926
+ <rdate>
927
+ <date-time>2008-02-05T19:12:24Z</date-time>
928
+ <date-time>2009-02-05T19:12:24Z</date-time>
929
+ </rdate>
930
+ </properties>
931
+ </vcalendar>
932
+ </icalendar>
933
+ XML
934
+ vobj = <<VOBJ
935
+ BEGIN:VCALENDAR
936
+ RDATE:20080205T191224Z,20090205T191224Z
937
+ END:VCALENDAR
938
+ VOBJ
939
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
940
+ end
941
+
942
+ def test_r_date_with_date
943
+ xml = <<XML
944
+ <?xml version="1.0" encoding="UTF-8"?>
945
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
946
+ <vcalendar>
947
+ <properties>
948
+ <rdate>
949
+ <date>2008-10-06</date>
950
+ </rdate>
951
+ </properties>
952
+ </vcalendar>
953
+ </icalendar>
954
+ XML
955
+ vobj = <<VOBJ
956
+ BEGIN:VCALENDAR
957
+ RDATE:20081006
958
+ END:VCALENDAR
959
+ VOBJ
960
+ assert_xml_equals_to_mime_dir(xml, vobj)
961
+
962
+ xml = <<XML
963
+ <?xml version="1.0" encoding="UTF-8"?>
964
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
965
+ <vcalendar>
966
+ <properties>
967
+ <rdate>
968
+ <date>2008-10-06</date>
969
+ <date>2009-10-06</date>
970
+ <date>2010-10-06</date>
971
+ </rdate>
972
+ </properties>
973
+ </vcalendar>
974
+ </icalendar>
975
+ XML
976
+ vobj = <<VOBJ
977
+ BEGIN:VCALENDAR
978
+ RDATE:20081006,20091006,20101006
979
+ END:VCALENDAR
980
+ VOBJ
981
+ assert_xml_equals_to_mime_dir(xml, vobj)
982
+ end
983
+
984
+ def test_r_date_with_period
985
+ xml = <<XML
986
+ <?xml version="1.0" encoding="UTF-8"?>
987
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
988
+ <vcalendar>
989
+ <properties>
990
+ <rdate>
991
+ <parameters>
992
+ <tzid>
993
+ <text>US/Eastern</text>
994
+ </tzid>
995
+ </parameters>
996
+ <period>
997
+ <start>2006-01-02T15:00:00</start>
998
+ <duration>PT2H</duration>
999
+ </period>
1000
+ </rdate>
1001
+ </properties>
1002
+ </vcalendar>
1003
+ </icalendar>
1004
+ XML
1005
+ vobj = <<VOBJ
1006
+ BEGIN:VCALENDAR
1007
+ RDATE;TZID=US/Eastern;VALUE=PERIOD:20060102T150000/PT2H
1008
+ END:VCALENDAR
1009
+ VOBJ
1010
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1011
+
1012
+ xml = <<XML
1013
+ <?xml version="1.0" encoding="UTF-8"?>
1014
+ <icalendar xmlns="urn:ietf:params:xml:ns:icalendar-2.0">
1015
+ <vcalendar>
1016
+ <properties>
1017
+ <rdate>
1018
+ <parameters>
1019
+ <tzid>
1020
+ <text>US/Eastern</text>
1021
+ </tzid>
1022
+ </parameters>
1023
+ <period>
1024
+ <start>2006-01-02T15:00:00</start>
1025
+ <duration>PT2H</duration>
1026
+ </period>
1027
+ <period>
1028
+ <start>2008-01-02T15:00:00</start>
1029
+ <duration>PT1H</duration>
1030
+ </period>
1031
+ </rdate>
1032
+ </properties>
1033
+ </vcalendar>
1034
+ </icalendar>
1035
+ XML
1036
+ vobj = <<VOBJ
1037
+ BEGIN:VCALENDAR
1038
+ RDATE;TZID=US/Eastern;VALUE=PERIOD:20060102T150000/PT2H,20080102T150000/PT1
1039
+ H
1040
+ END:VCALENDAR
1041
+ VOBJ
1042
+ assert_xml_equals_to_mime_dir(xml, vobj)
1043
+ end
1044
+
1045
+ # Basic example.
1046
+ def test_rfc6351_basic
1047
+ xml = <<XML
1048
+ <?xml version="1.0" encoding="UTF-8"?>
1049
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1050
+ <vcard>
1051
+ <fn>
1052
+ <text>J. Doe</text>
1053
+ </fn>
1054
+ <n>
1055
+ <surname>Doe</surname>
1056
+ <given>J.</given>
1057
+ <additional/>
1058
+ <prefix/>
1059
+ <suffix/>
1060
+ </n>
1061
+ </vcard>
1062
+ </vcards>
1063
+ XML
1064
+ vobj = <<VOBJ
1065
+ BEGIN:VCARD
1066
+ VERSION:4.0
1067
+ FN:J. Doe
1068
+ N:Doe;J.;;;
1069
+ END:VCARD
1070
+ VOBJ
1071
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1072
+ end
1073
+
1074
+ # Example 1.
1075
+ def test_rfc6351_example1
1076
+ xml = <<XML
1077
+ <?xml version="1.0" encoding="UTF-8"?>
1078
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1079
+ <vcard>
1080
+ <fn>
1081
+ <text>J. Doe</text>
1082
+ </fn>
1083
+ <n>
1084
+ <surname>Doe</surname>
1085
+ <given>J.</given>
1086
+ <additional/>
1087
+ <prefix/>
1088
+ <suffix/>
1089
+ </n>
1090
+ <x-file>
1091
+ <parameters>
1092
+ <mediatype>
1093
+ <text>image/jpeg</text>
1094
+ </mediatype>
1095
+ </parameters>
1096
+ <unknown>alien.jpg</unknown>
1097
+ </x-file>
1098
+ <x1:a href="http://www.example.com" xmlns:x1="http://www.w3.org/1999/xhtml">My web page!</x1:a>
1099
+ </vcard>
1100
+ </vcards>
1101
+ XML
1102
+ vobj = <<VOBJ
1103
+ BEGIN:VCARD
1104
+ VERSION:4.0
1105
+ FN:J. Doe
1106
+ N:Doe;J.;;;
1107
+ X-FILE;MEDIATYPE=image/jpeg:alien.jpg
1108
+ XML:<a xmlns="http://www.w3.org/1999/xhtml" href="http://www.example.com">M
1109
+ y web page!</a>
1110
+ END:VCARD
1111
+ VOBJ
1112
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1113
+ end
1114
+
1115
+ # Design Considerations.
1116
+ def test_rfc6351_section5
1117
+ xml = <<XML
1118
+ <?xml version="1.0" encoding="UTF-8"?>
1119
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1120
+ <vcard>
1121
+ <tel>
1122
+ <parameters>
1123
+ <type>
1124
+ <text>voice</text>
1125
+ <text>video</text>
1126
+ </type>
1127
+ </parameters>
1128
+ <uri>tel:+1-555-555-555</uri>
1129
+ </tel>
1130
+ </vcard>
1131
+ </vcards>
1132
+ XML
1133
+ vobj = <<VOBJ
1134
+ BEGIN:VCARD
1135
+ VERSION:4.0
1136
+ TEL;TYPE="voice,video":tel:+1-555-555-555
1137
+ END:VCARD
1138
+ VOBJ
1139
+ assert_xml_equals_to_mime_dir(xml, vobj)
1140
+
1141
+ xml = <<XML
1142
+ <?xml version="1.0" encoding="UTF-8"?>
1143
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1144
+ <vcard>
1145
+ <tel>
1146
+ <parameters>
1147
+ <type>
1148
+ <text>voice</text>
1149
+ <text>video</text>
1150
+ </type>
1151
+ </parameters>
1152
+ <text>tel:+1-555-555-555</text>
1153
+ </tel>
1154
+ </vcard>
1155
+ </vcards>
1156
+ XML
1157
+ vobj = <<VOBJ
1158
+ BEGIN:VCARD
1159
+ VERSION:4.0
1160
+ TEL;TYPE="voice,video":tel:+1-555-555-555
1161
+ END:VCARD
1162
+ VOBJ
1163
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1164
+ end
1165
+
1166
+ # Design Considerations.
1167
+ def test_rfc6351_section5_group
1168
+ xml = <<XML
1169
+ <?xml version="1.0" encoding="UTF-8"?>
1170
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1171
+ <vcard>
1172
+ <tel>
1173
+ <text>tel:+1-555-555-556</text>
1174
+ </tel>
1175
+ <group name="contact">
1176
+ <tel>
1177
+ <text>tel:+1-555-555-555</text>
1178
+ </tel>
1179
+ <fn>
1180
+ <text>Gordon</text>
1181
+ </fn>
1182
+ </group>
1183
+ <group name="media">
1184
+ <fn>
1185
+ <text>Gordon</text>
1186
+ </fn>
1187
+ </group>
1188
+ </vcard>
1189
+ </vcards>
1190
+ XML
1191
+ vobj = <<VOBJ
1192
+ BEGIN:VCARD
1193
+ VERSION:4.0
1194
+ TEL:tel:+1-555-555-556
1195
+ contact.TEL:tel:+1-555-555-555
1196
+ contact.FN:Gordon
1197
+ media.FN:Gordon
1198
+ END:VCARD
1199
+ VOBJ
1200
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1201
+ end
1202
+
1203
+ # Extensibility.
1204
+ def test_rfc6351_section5_1_no_namespace
1205
+ xml = <<XML
1206
+ <?xml version="1.0" encoding="UTF-8"?>
1207
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1208
+ <vcard>
1209
+ <x-my-prop>
1210
+ <parameters>
1211
+ <pref>
1212
+ <integer>1</integer>
1213
+ </pref>
1214
+ </parameters>
1215
+ <text>value goes here</text>
1216
+ </x-my-prop>
1217
+ </vcard>
1218
+ </vcards>
1219
+ XML
1220
+ vobj = <<VOBJ
1221
+ BEGIN:VCARD
1222
+ VERSION:4.0
1223
+ X-MY-PROP;PREF=1:value goes here
1224
+ END:VCARD
1225
+ VOBJ
1226
+ assert_xml_equals_to_mime_dir(xml, vobj)
1227
+ end
1228
+
1229
+ # Section 4.3.1 of Relax NG Schema: value-date.
1230
+ def test_rfc6351_value_date_with_year_month_day
1231
+ xml = <<XML
1232
+ <?xml version="1.0" encoding="UTF-8"?>
1233
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1234
+ <vcard>
1235
+ <bday>
1236
+ <date-and-or-time>20150128</date-and-or-time>
1237
+ </bday>
1238
+ </vcard>
1239
+ </vcards>
1240
+ XML
1241
+ vobj = <<VOBJ
1242
+ BEGIN:VCARD
1243
+ VERSION:4.0
1244
+ BDAY:20150128
1245
+ END:VCARD
1246
+ VOBJ
1247
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1248
+ end
1249
+
1250
+ # Section 4.3.1 of Relax NG Schema: value-date.
1251
+ def test_rfc6351_value_date_with_year_month
1252
+ xml = <<XML
1253
+ <?xml version="1.0" encoding="UTF-8"?>
1254
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1255
+ <vcard>
1256
+ <bday>
1257
+ <date-and-or-time>2015-01</date-and-or-time>
1258
+ </bday>
1259
+ </vcard>
1260
+ </vcards>
1261
+ XML
1262
+ vobj = <<VOBJ
1263
+ BEGIN:VCARD
1264
+ VERSION:4.0
1265
+ BDAY:2015-01
1266
+ END:VCARD
1267
+ VOBJ
1268
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1269
+ end
1270
+
1271
+ # Section 4.3.1 of Relax NG Schema: value-date.
1272
+ def test_rfc6351_value_date_with_month
1273
+ xml = <<XML
1274
+ <?xml version="1.0" encoding="UTF-8"?>
1275
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1276
+ <vcard>
1277
+ <bday>
1278
+ <date-and-or-time>--01</date-and-or-time>
1279
+ </bday>
1280
+ </vcard>
1281
+ </vcards>
1282
+ XML
1283
+ vobj = <<VOBJ
1284
+ BEGIN:VCARD
1285
+ VERSION:4.0
1286
+ BDAY:--01
1287
+ END:VCARD
1288
+ VOBJ
1289
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1290
+ end
1291
+
1292
+ # Section 4.3.1 of Relax NG Schema: value-date.
1293
+ def test_rfc6351_value_date_with_month_day
1294
+ xml = <<XML
1295
+ <?xml version="1.0" encoding="UTF-8"?>
1296
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1297
+ <vcard>
1298
+ <bday>
1299
+ <date-and-or-time>--0128</date-and-or-time>
1300
+ </bday>
1301
+ </vcard>
1302
+ </vcards>
1303
+ XML
1304
+ vobj = <<VOBJ
1305
+ BEGIN:VCARD
1306
+ VERSION:4.0
1307
+ BDAY:--0128
1308
+ END:VCARD
1309
+ VOBJ
1310
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1311
+ end
1312
+
1313
+ # Section 4.3.1 of Relax NG Schema: value-date.
1314
+ def test_rfc6351_value_date_with_day
1315
+ xml = <<XML
1316
+ <?xml version="1.0" encoding="UTF-8"?>
1317
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1318
+ <vcard>
1319
+ <bday>
1320
+ <date-and-or-time>---28</date-and-or-time>
1321
+ </bday>
1322
+ </vcard>
1323
+ </vcards>
1324
+ XML
1325
+ vobj = <<VOBJ
1326
+ BEGIN:VCARD
1327
+ VERSION:4.0
1328
+ BDAY:---28
1329
+ END:VCARD
1330
+ VOBJ
1331
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1332
+ end
1333
+
1334
+ # Section 4.3.2 of Relax NG Schema: value-time.
1335
+ def test_rfc6351_value_time_with_hour
1336
+ xml = <<XML
1337
+ <?xml version="1.0" encoding="UTF-8"?>
1338
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1339
+ <vcard>
1340
+ <bday>
1341
+ <date-and-or-time>13</date-and-or-time>
1342
+ </bday>
1343
+ </vcard>
1344
+ </vcards>
1345
+ XML
1346
+ vobj = <<VOBJ
1347
+ BEGIN:VCARD
1348
+ VERSION:4.0
1349
+ BDAY:13
1350
+ END:VCARD
1351
+ VOBJ
1352
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1353
+ end
1354
+
1355
+ # Section 4.3.2 of Relax NG Schema: value-time.
1356
+ def test_rfc6351_value_time_with_hour_minute
1357
+ xml = <<XML
1358
+ <?xml version="1.0" encoding="UTF-8"?>
1359
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1360
+ <vcard>
1361
+ <bday>
1362
+ <date-and-or-time>1353</date-and-or-time>
1363
+ </bday>
1364
+ </vcard>
1365
+ </vcards>
1366
+ XML
1367
+ vobj = <<VOBJ
1368
+ BEGIN:VCARD
1369
+ VERSION:4.0
1370
+ BDAY:1353
1371
+ END:VCARD
1372
+ VOBJ
1373
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1374
+ end
1375
+
1376
+ # Section 4.3.2 of Relax NG Schema: value-time.
1377
+ def test_rfc6351_value_time_with_hour_minute_second
1378
+ xml = <<XML
1379
+ <?xml version="1.0" encoding="UTF-8"?>
1380
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1381
+ <vcard>
1382
+ <bday>
1383
+ <date-and-or-time>135301</date-and-or-time>
1384
+ </bday>
1385
+ </vcard>
1386
+ </vcards>
1387
+ XML
1388
+ vobj = <<VOBJ
1389
+ BEGIN:VCARD
1390
+ VERSION:4.0
1391
+ BDAY:135301
1392
+ END:VCARD
1393
+ VOBJ
1394
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1395
+ end
1396
+
1397
+ # Section 4.3.2 of Relax NG Schema: value-time.
1398
+ def test_rfc6351_value_time_with_minute
1399
+ xml = <<XML
1400
+ <?xml version="1.0" encoding="UTF-8"?>
1401
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1402
+ <vcard>
1403
+ <bday>
1404
+ <date-and-or-time>-53</date-and-or-time>
1405
+ </bday>
1406
+ </vcard>
1407
+ </vcards>
1408
+ XML
1409
+ vobj = <<VOBJ
1410
+ BEGIN:VCARD
1411
+ VERSION:4.0
1412
+ BDAY:-53
1413
+ END:VCARD
1414
+ VOBJ
1415
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1416
+ end
1417
+
1418
+ # Section 4.3.2 of Relax NG Schema: value-time.
1419
+ def test_rfc6351_value_time_with_minute_second
1420
+ xml = <<XML
1421
+ <?xml version="1.0" encoding="UTF-8"?>
1422
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1423
+ <vcard>
1424
+ <bday>
1425
+ <date-and-or-time>-5301</date-and-or-time>
1426
+ </bday>
1427
+ </vcard>
1428
+ </vcards>
1429
+ XML
1430
+ vobj = <<VOBJ
1431
+ BEGIN:VCARD
1432
+ VERSION:4.0
1433
+ BDAY:-5301
1434
+ END:VCARD
1435
+ VOBJ
1436
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1437
+ end
1438
+
1439
+ # Section 4.3.2 of Relax NG Schema: value-time.
1440
+ def test_rfc6351_value_time_with_second
1441
+ assert(true)
1442
+
1443
+ # According to the Relax NG Schema, there is a conflict between
1444
+ # value-date and value-time. The --01 syntax can only match a
1445
+ # value-date because of the higher priority set in
1446
+ # value-date-and-or-time. So we basically skip this test.
1447
+ #
1448
+ # xml = <<XML
1449
+ # <?xml version="1.0" encoding="UTF-8"?>
1450
+ # <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1451
+ # <vcard>
1452
+ # <bday>
1453
+ # <date-and-or-time>--01</date-and-or-time>
1454
+ # </bday>
1455
+ # </vcard>
1456
+ # </vcards>
1457
+ # XML
1458
+ # vobj = <<VOBJ
1459
+ # BEGIN:VCARD
1460
+ # VERSION:4.0
1461
+ # BDAY:--01
1462
+ # END:VCARD
1463
+ # VOBJ
1464
+ # assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1465
+ end
1466
+
1467
+ # Section 4.3.2 of Relax NG Schema: value-time.
1468
+ def test_rfc6351_value_time_with_second_z
1469
+ xml = <<XML
1470
+ <?xml version="1.0" encoding="UTF-8"?>
1471
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1472
+ <vcard>
1473
+ <bday>
1474
+ <date-and-or-time>--01Z</date-and-or-time>
1475
+ </bday>
1476
+ </vcard>
1477
+ </vcards>
1478
+ XML
1479
+ vobj = <<VOBJ
1480
+ BEGIN:VCARD
1481
+ VERSION:4.0
1482
+ BDAY:--01Z
1483
+ END:VCARD
1484
+ VOBJ
1485
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1486
+ end
1487
+
1488
+ # Section 4.3.2 of Relax NG Schema: value-time.
1489
+ def test_rfc6351_value_time_with_second_tz
1490
+ xml = <<XML
1491
+ <?xml version="1.0" encoding="UTF-8"?>
1492
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1493
+ <vcard>
1494
+ <bday>
1495
+ <date-and-or-time>--01+1234</date-and-or-time>
1496
+ </bday>
1497
+ </vcard>
1498
+ </vcards>
1499
+ XML
1500
+ vobj = <<VOBJ
1501
+ BEGIN:VCARD
1502
+ VERSION:4.0
1503
+ BDAY:--01+1234
1504
+ END:VCARD
1505
+ VOBJ
1506
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1507
+ end
1508
+
1509
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1510
+ def test_rfc6351_value_date_time_with_year_month_day_hour
1511
+ xml = <<XML
1512
+ <?xml version="1.0" encoding="UTF-8"?>
1513
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1514
+ <vcard>
1515
+ <bday>
1516
+ <date-and-or-time>20150128T13</date-and-or-time>
1517
+ </bday>
1518
+ </vcard>
1519
+ </vcards>
1520
+ XML
1521
+ vobj = <<VOBJ
1522
+ BEGIN:VCARD
1523
+ VERSION:4.0
1524
+ BDAY:20150128T13
1525
+ END:VCARD
1526
+ VOBJ
1527
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1528
+ end
1529
+
1530
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1531
+ def test_rfc6351_value_date_time_with_month_day_hour
1532
+ xml = <<XML
1533
+ <?xml version="1.0" encoding="UTF-8"?>
1534
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1535
+ <vcard>
1536
+ <bday>
1537
+ <date-and-or-time>--0128T13</date-and-or-time>
1538
+ </bday>
1539
+ </vcard>
1540
+ </vcards>
1541
+ XML
1542
+ vobj = <<VOBJ
1543
+ BEGIN:VCARD
1544
+ VERSION:4.0
1545
+ BDAY:--0128T13
1546
+ END:VCARD
1547
+ VOBJ
1548
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1549
+ end
1550
+
1551
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1552
+ def test_rfc6351_value_date_time_with_day_hour
1553
+ xml = <<XML
1554
+ <?xml version="1.0" encoding="UTF-8"?>
1555
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1556
+ <vcard>
1557
+ <bday>
1558
+ <date-and-or-time>---28T13</date-and-or-time>
1559
+ </bday>
1560
+ </vcard>
1561
+ </vcards>
1562
+ XML
1563
+ vobj = <<VOBJ
1564
+ BEGIN:VCARD
1565
+ VERSION:4.0
1566
+ BDAY:---28T13
1567
+ END:VCARD
1568
+ VOBJ
1569
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1570
+ end
1571
+
1572
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1573
+ def test_rfc6351_value_date_time_with_day_hour_minute
1574
+ xml = <<XML
1575
+ <?xml version="1.0" encoding="UTF-8"?>
1576
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1577
+ <vcard>
1578
+ <bday>
1579
+ <date-and-or-time>---28T1353</date-and-or-time>
1580
+ </bday>
1581
+ </vcard>
1582
+ </vcards>
1583
+ XML
1584
+ vobj = <<VOBJ
1585
+ BEGIN:VCARD
1586
+ VERSION:4.0
1587
+ BDAY:---28T1353
1588
+ END:VCARD
1589
+ VOBJ
1590
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1591
+ end
1592
+
1593
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1594
+ def test_rfc6351_value_date_time_with_day_hour_minute_second
1595
+ xml = <<XML
1596
+ <?xml version="1.0" encoding="UTF-8"?>
1597
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1598
+ <vcard>
1599
+ <bday>
1600
+ <date-and-or-time>---28T135301</date-and-or-time>
1601
+ </bday>
1602
+ </vcard>
1603
+ </vcards>
1604
+ XML
1605
+ vobj = <<VOBJ
1606
+ BEGIN:VCARD
1607
+ VERSION:4.0
1608
+ BDAY:---28T135301
1609
+ END:VCARD
1610
+ VOBJ
1611
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1612
+ end
1613
+
1614
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1615
+ def test_rfc6351_value_date_time_with_day_hour_z
1616
+ xml = <<XML
1617
+ <?xml version="1.0" encoding="UTF-8"?>
1618
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1619
+ <vcard>
1620
+ <bday>
1621
+ <date-and-or-time>---28T13Z</date-and-or-time>
1622
+ </bday>
1623
+ </vcard>
1624
+ </vcards>
1625
+ XML
1626
+ vobj = <<VOBJ
1627
+ BEGIN:VCARD
1628
+ VERSION:4.0
1629
+ BDAY:---28T13Z
1630
+ END:VCARD
1631
+ VOBJ
1632
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1633
+ end
1634
+
1635
+ # Section 4.3.3 of Relax NG Schema: value-date-time.
1636
+ def test_rfc6351_value_date_time_with_day_hour_tz
1637
+ xml = <<XML
1638
+ <?xml version="1.0" encoding="UTF-8"?>
1639
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1640
+ <vcard>
1641
+ <bday>
1642
+ <date-and-or-time>---28T13+1234</date-and-or-time>
1643
+ </bday>
1644
+ </vcard>
1645
+ </vcards>
1646
+ XML
1647
+ vobj = <<VOBJ
1648
+ BEGIN:VCARD
1649
+ VERSION:4.0
1650
+ BDAY:---28T13+1234
1651
+ END:VCARD
1652
+ VOBJ
1653
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1654
+ end
1655
+
1656
+ # Property: SOURCE.
1657
+ def test_rfc6350_section6_1_3
1658
+ xml = <<XML
1659
+ <?xml version="1.0" encoding="UTF-8"?>
1660
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1661
+ <vcard>
1662
+ <source>
1663
+ <uri>ldap://ldap.example.com/cn=Babs%20Jensen,%20o=Babsco,%20c=US</uri>
1664
+ </source>
1665
+ </vcard>
1666
+ </vcards>
1667
+ XML
1668
+ vobj = <<VOBJ
1669
+ BEGIN:VCARD
1670
+ VERSION:4.0
1671
+ SOURCE:ldap://ldap.example.com/cn=Babs%20Jensen\\,%20o=Babsco\\,%20c=US
1672
+ END:VCARD
1673
+ VOBJ
1674
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1675
+ end
1676
+
1677
+ # Property: KIND.
1678
+ def test_rfc6350_section6_1_4
1679
+ xml = <<XML
1680
+ <?xml version="1.0" encoding="UTF-8"?>
1681
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1682
+ <vcard>
1683
+ <kind>
1684
+ <text>individual</text>
1685
+ </kind>
1686
+ </vcard>
1687
+ </vcards>
1688
+ XML
1689
+ vobj = <<VOBJ
1690
+ BEGIN:VCARD
1691
+ VERSION:4.0
1692
+ KIND:individual
1693
+ END:VCARD
1694
+ VOBJ
1695
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1696
+ end
1697
+
1698
+ # Property: FN.
1699
+ def test_rfc6350_section6_2_1
1700
+ xml = <<XML
1701
+ <?xml version="1.0" encoding="UTF-8"?>
1702
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1703
+ <vcard>
1704
+ <fn>
1705
+ <text>Mr. John Q. Public, Esq.</text>
1706
+ </fn>
1707
+ </vcard>
1708
+ </vcards>
1709
+ XML
1710
+ vobj = <<VOBJ
1711
+ BEGIN:VCARD
1712
+ VERSION:4.0
1713
+ FN:Mr. John Q. Public\\, Esq.
1714
+ END:VCARD
1715
+ VOBJ
1716
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1717
+ end
1718
+
1719
+ # Property: N.
1720
+ def test_rfc6350_section6_2_2
1721
+ xml = <<XML
1722
+ <?xml version="1.0" encoding="UTF-8"?>
1723
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1724
+ <vcard>
1725
+ <n>
1726
+ <surname>Stevenson</surname>
1727
+ <given>John</given>
1728
+ <additional>Philip,Paul</additional>
1729
+ <prefix>Dr.</prefix>
1730
+ <suffix>Jr.,M.D.,A.C.P.</suffix>
1731
+ </n>
1732
+ </vcard>
1733
+ </vcards>
1734
+ XML
1735
+ vobj = <<VOBJ
1736
+ BEGIN:VCARD
1737
+ VERSION:4.0
1738
+ N:Stevenson;John;Philip\\,Paul;Dr.;Jr.\\,M.D.\\,A.C.P.
1739
+ END:VCARD
1740
+ VOBJ
1741
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1742
+ end
1743
+
1744
+ # Property: NICKNAME.
1745
+ def test_rfc6350_section6_2_3
1746
+ xml = <<XML
1747
+ <?xml version="1.0" encoding="UTF-8"?>
1748
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1749
+ <vcard>
1750
+ <nickname>
1751
+ <text>Jim</text>
1752
+ <text>Jimmie</text>
1753
+ </nickname>
1754
+ </vcard>
1755
+ </vcards>
1756
+ XML
1757
+ vobj = <<VOBJ
1758
+ BEGIN:VCARD
1759
+ VERSION:4.0
1760
+ NICKNAME:Jim,Jimmie
1761
+ END:VCARD
1762
+ VOBJ
1763
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1764
+ end
1765
+
1766
+ # Property: PHOTO.
1767
+ def test_rfc6350_section6_2_4
1768
+ xml = <<XML
1769
+ <?xml version="1.0" encoding="UTF-8"?>
1770
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1771
+ <vcard>
1772
+ <photo>
1773
+ <uri>http://www.example.com/pub/photos/jqpublic.gif</uri>
1774
+ </photo>
1775
+ </vcard>
1776
+ </vcards>
1777
+ XML
1778
+ vobj = <<VOBJ
1779
+ BEGIN:VCARD
1780
+ VERSION:4.0
1781
+ PHOTO:http://www.example.com/pub/photos/jqpublic.gif
1782
+ END:VCARD
1783
+ VOBJ
1784
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1785
+ end
1786
+
1787
+ def test_rfc6350_section6_2_5
1788
+ xml = <<XML
1789
+ <?xml version="1.0" encoding="UTF-8"?>
1790
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1791
+ <vcard>
1792
+ <bday>
1793
+ <date-and-or-time>19531015T231000Z</date-and-or-time>
1794
+ </bday>
1795
+ </vcard>
1796
+ </vcards>
1797
+ XML
1798
+ vobj = <<VOBJ
1799
+ BEGIN:VCARD
1800
+ VERSION:4.0
1801
+ BDAY:19531015T231000Z
1802
+ END:VCARD
1803
+ VOBJ
1804
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1805
+ end
1806
+
1807
+ def test_rfc6350_section6_2_6
1808
+ xml = <<XML
1809
+ <?xml version="1.0" encoding="UTF-8"?>
1810
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1811
+ <vcard>
1812
+ <anniversary>
1813
+ <date-and-or-time>19960415</date-and-or-time>
1814
+ </anniversary>
1815
+ </vcard>
1816
+ </vcards>
1817
+ XML
1818
+ vobj = <<VOBJ
1819
+ BEGIN:VCARD
1820
+ VERSION:4.0
1821
+ ANNIVERSARY:19960415
1822
+ END:VCARD
1823
+ VOBJ
1824
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1825
+ end
1826
+
1827
+ # Property: GENDER.
1828
+ def test_rfc6350_section6_2_7
1829
+ xml = <<XML
1830
+ <?xml version="1.0" encoding="UTF-8"?>
1831
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1832
+ <vcard>
1833
+ <gender>
1834
+ <sex>Jim</sex>
1835
+ <text>Jimmie</text>
1836
+ </gender>
1837
+ </vcard>
1838
+ </vcards>
1839
+ XML
1840
+ vobj = <<VOBJ
1841
+ BEGIN:VCARD
1842
+ VERSION:4.0
1843
+ GENDER:Jim;Jimmie
1844
+ END:VCARD
1845
+ VOBJ
1846
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1847
+ end
1848
+
1849
+ # Property: ADR.
1850
+ def test_rfc6350_section6_3_1
1851
+ xml = <<XML
1852
+ <?xml version="1.0" encoding="UTF-8"?>
1853
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1854
+ <vcard>
1855
+ <adr>
1856
+ <pobox/>
1857
+ <ext/>
1858
+ <street>123 Main Street</street>
1859
+ <locality>Any Town</locality>
1860
+ <region>CA</region>
1861
+ <code>91921-1234</code>
1862
+ <country>U.S.A.</country>
1863
+ </adr>
1864
+ </vcard>
1865
+ </vcards>
1866
+ XML
1867
+ vobj = <<VOBJ
1868
+ BEGIN:VCARD
1869
+ VERSION:4.0
1870
+ ADR:;;123 Main Street;Any Town;CA;91921-1234;U.S.A.
1871
+ END:VCARD
1872
+ VOBJ
1873
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1874
+ end
1875
+
1876
+ # Property: TEL.
1877
+ def test_rfc6350_section6_4_1
1878
+ # Quoting RFC:
1879
+ # > Value type: By default, it is a single free-form text value (for
1880
+ # > backward compatibility with vCard 3), but it SHOULD be reset to a
1881
+ # > URI value. It is expected that the URI scheme will be "tel", as
1882
+ # > specified in [RFC3966], but other schemes MAY be used.
1883
+ #
1884
+ # So first, we test xCard/URI to vCard/URI.
1885
+ # Then, we test xCard/TEXT to vCard/TEXT to xCard/TEXT.
1886
+ xml = <<XML
1887
+ <?xml version="1.0" encoding="UTF-8"?>
1888
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1889
+ <vcard>
1890
+ <tel>
1891
+ <parameters>
1892
+ <type>
1893
+ <text>home</text>
1894
+ </type>
1895
+ </parameters>
1896
+ <uri>tel:+33-01-23-45-67</uri>
1897
+ </tel>
1898
+ </vcard>
1899
+ </vcards>
1900
+ XML
1901
+ vobj = <<VOBJ
1902
+ BEGIN:VCARD
1903
+ VERSION:4.0
1904
+ TEL;TYPE=home:tel:+33-01-23-45-67
1905
+ END:VCARD
1906
+ VOBJ
1907
+ assert_xml_equals_to_mime_dir(xml, vobj)
1908
+
1909
+ xml = <<XML
1910
+ <?xml version="1.0" encoding="UTF-8"?>
1911
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1912
+ <vcard>
1913
+ <tel>
1914
+ <parameters>
1915
+ <type>
1916
+ <text>home</text>
1917
+ </type>
1918
+ </parameters>
1919
+ <text>tel:+33-01-23-45-67</text>
1920
+ </tel>
1921
+ </vcard>
1922
+ </vcards>
1923
+ XML
1924
+ vobj = <<VOBJ
1925
+ BEGIN:VCARD
1926
+ VERSION:4.0
1927
+ TEL;TYPE=home:tel:+33-01-23-45-67
1928
+ END:VCARD
1929
+ VOBJ
1930
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1931
+ end
1932
+
1933
+ # Property: EMAIL.
1934
+ def test_rfc6350_section6_4_2
1935
+ xml = <<XML
1936
+ <?xml version="1.0" encoding="UTF-8"?>
1937
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1938
+ <vcard>
1939
+ <email>
1940
+ <parameters>
1941
+ <type>
1942
+ <text>work</text>
1943
+ </type>
1944
+ </parameters>
1945
+ <text>jqpublic@xyz.example.com</text>
1946
+ </email>
1947
+ </vcard>
1948
+ </vcards>
1949
+ XML
1950
+ vobj = <<VOBJ
1951
+ BEGIN:VCARD
1952
+ VERSION:4.0
1953
+ EMAIL;TYPE=work:jqpublic@xyz.example.com
1954
+ END:VCARD
1955
+ VOBJ
1956
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1957
+ end
1958
+
1959
+ # Property: IMPP.
1960
+ def test_rfc6350_section6_4_3
1961
+ xml = <<XML
1962
+ <?xml version="1.0" encoding="UTF-8"?>
1963
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1964
+ <vcard>
1965
+ <impp>
1966
+ <parameters>
1967
+ <pref>
1968
+ <text>1</text>
1969
+ </pref>
1970
+ </parameters>
1971
+ <uri>xmpp:alice@example.com</uri>
1972
+ </impp>
1973
+ </vcard>
1974
+ </vcards>
1975
+ XML
1976
+ vobj = <<VOBJ
1977
+ BEGIN:VCARD
1978
+ VERSION:4.0
1979
+ IMPP;PREF=1:xmpp:alice@example.com
1980
+ END:VCARD
1981
+ VOBJ
1982
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
1983
+ end
1984
+
1985
+ # Property: LANG.
1986
+ def test_rfc6350_section6_4_4
1987
+ xml = <<XML
1988
+ <?xml version="1.0" encoding="UTF-8"?>
1989
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
1990
+ <vcard>
1991
+ <lang>
1992
+ <parameters>
1993
+ <type>
1994
+ <text>work</text>
1995
+ </type>
1996
+ <pref>
1997
+ <text>2</text>
1998
+ </pref>
1999
+ </parameters>
2000
+ <language-tag>en</language-tag>
2001
+ </lang>
2002
+ </vcard>
2003
+ </vcards>
2004
+ XML
2005
+ vobj = <<VOBJ
2006
+ BEGIN:VCARD
2007
+ VERSION:4.0
2008
+ LANG;TYPE=work;PREF=2:en
2009
+ END:VCARD
2010
+ VOBJ
2011
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2012
+ end
2013
+
2014
+ # Property: TZ.
2015
+ def test_rfc6350_section6_5_1
2016
+ xml = <<XML
2017
+ <?xml version="1.0" encoding="UTF-8"?>
2018
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2019
+ <vcard>
2020
+ <tz>
2021
+ <text>Raleigh/North America</text>
2022
+ </tz>
2023
+ </vcard>
2024
+ </vcards>
2025
+ XML
2026
+ vobj = <<VOBJ
2027
+ BEGIN:VCARD
2028
+ VERSION:4.0
2029
+ TZ:Raleigh/North America
2030
+ END:VCARD
2031
+ VOBJ
2032
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2033
+ end
2034
+
2035
+ # Property: GEO.
2036
+ def test_rfc6350_section6_5_2
2037
+ xml = <<XML
2038
+ <?xml version="1.0" encoding="UTF-8"?>
2039
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2040
+ <vcard>
2041
+ <geo>
2042
+ <uri>geo:37.386013,-122.082932</uri>
2043
+ </geo>
2044
+ </vcard>
2045
+ </vcards>
2046
+ XML
2047
+ vobj = <<VOBJ
2048
+ BEGIN:VCARD
2049
+ VERSION:4.0
2050
+ GEO:geo:37.386013\\,-122.082932
2051
+ END:VCARD
2052
+ VOBJ
2053
+ assert_xml_equals_to_mime_dir(xml, vobj)
2054
+
2055
+ xml = <<XML
2056
+ <?xml version="1.0" encoding="UTF-8"?>
2057
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2058
+ <vcard>
2059
+ <geo>
2060
+ <text>geo:37.386013,-122.082932</text>
2061
+ </geo>
2062
+ </vcard>
2063
+ </vcards>
2064
+ XML
2065
+ vobj = <<VOBJ
2066
+ BEGIN:VCARD
2067
+ VERSION:4.0
2068
+ GEO:geo:37.386013\\,-122.082932
2069
+ END:VCARD
2070
+ VOBJ
2071
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2072
+ end
2073
+
2074
+ # Property: TITLE.
2075
+ def test_rfc6350_section6_6_1
2076
+ xml = <<XML
2077
+ <?xml version="1.0" encoding="UTF-8"?>
2078
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2079
+ <vcard>
2080
+ <title>
2081
+ <text>Research Scientist</text>
2082
+ </title>
2083
+ </vcard>
2084
+ </vcards>
2085
+ XML
2086
+ vobj = <<VOBJ
2087
+ BEGIN:VCARD
2088
+ VERSION:4.0
2089
+ TITLE:Research Scientist
2090
+ END:VCARD
2091
+ VOBJ
2092
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2093
+ end
2094
+
2095
+ # Property: ROLE.
2096
+ def test_rfc6350_section6_6_2
2097
+ xml = <<XML
2098
+ <?xml version="1.0" encoding="UTF-8"?>
2099
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2100
+ <vcard>
2101
+ <role>
2102
+ <text>Project Leader</text>
2103
+ </role>
2104
+ </vcard>
2105
+ </vcards>
2106
+ XML
2107
+ vobj = <<VOBJ
2108
+ BEGIN:VCARD
2109
+ VERSION:4.0
2110
+ ROLE:Project Leader
2111
+ END:VCARD
2112
+ VOBJ
2113
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2114
+ end
2115
+
2116
+ # Property: LOGO.
2117
+ def test_rfc6350_section6_6_3
2118
+ xml = <<XML
2119
+ <?xml version="1.0" encoding="UTF-8"?>
2120
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2121
+ <vcard>
2122
+ <logo>
2123
+ <uri>http://www.example.com/pub/logos/abccorp.jpg</uri>
2124
+ </logo>
2125
+ </vcard>
2126
+ </vcards>
2127
+ XML
2128
+ vobj = <<VOBJ
2129
+ BEGIN:VCARD
2130
+ VERSION:4.0
2131
+ LOGO:http://www.example.com/pub/logos/abccorp.jpg
2132
+ END:VCARD
2133
+ VOBJ
2134
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2135
+ end
2136
+
2137
+ # Property: ORG.
2138
+ def test_rfc6350_section6_6_4
2139
+ xml = <<XML
2140
+ <?xml version="1.0" encoding="UTF-8"?>
2141
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2142
+ <vcard>
2143
+ <org>
2144
+ <text>ABC, Inc.</text>
2145
+ <text>North American Division</text>
2146
+ <text>Marketing</text>
2147
+ </org>
2148
+ </vcard>
2149
+ </vcards>
2150
+ XML
2151
+ vobj = <<VOBJ
2152
+ BEGIN:VCARD
2153
+ VERSION:4.0
2154
+ ORG:ABC\, Inc.;North American Division;Marketing
2155
+ END:VCARD
2156
+ VOBJ
2157
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2158
+ end
2159
+
2160
+ # Property: MEMBER.
2161
+ def test_rfc6350_section6_6_5
2162
+ xml = <<XML
2163
+ <?xml version="1.0" encoding="UTF-8"?>
2164
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2165
+ <vcard>
2166
+ <member>
2167
+ <uri>urn:uuid:03a0e51f-d1aa-4385-8a53-e29025acd8af</uri>
2168
+ </member>
2169
+ </vcard>
2170
+ </vcards>
2171
+ XML
2172
+ vobj = <<VOBJ
2173
+ BEGIN:VCARD
2174
+ VERSION:4.0
2175
+ MEMBER:urn:uuid:03a0e51f-d1aa-4385-8a53-e29025acd8af
2176
+ END:VCARD
2177
+ VOBJ
2178
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2179
+
2180
+ xml = <<XML
2181
+ <?xml version="1.0" encoding="UTF-8"?>
2182
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2183
+ <vcard>
2184
+ <member>
2185
+ <uri>mailto:subscriber1@example.com</uri>
2186
+ </member>
2187
+ <member>
2188
+ <uri>xmpp:subscriber2@example.com</uri>
2189
+ </member>
2190
+ <member>
2191
+ <uri>sip:subscriber3@example.com</uri>
2192
+ </member>
2193
+ <member>
2194
+ <uri>tel:+1-418-555-5555</uri>
2195
+ </member>
2196
+ </vcard>
2197
+ </vcards>
2198
+ XML
2199
+ vobj = <<VOBJ
2200
+ BEGIN:VCARD
2201
+ VERSION:4.0
2202
+ MEMBER:mailto:subscriber1@example.com
2203
+ MEMBER:xmpp:subscriber2@example.com
2204
+ MEMBER:sip:subscriber3@example.com
2205
+ MEMBER:tel:+1-418-555-5555
2206
+ END:VCARD
2207
+ VOBJ
2208
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2209
+ end
2210
+
2211
+ # Property: RELATED.
2212
+ def test_rfc6350_section6_6_6
2213
+ xml = <<XML
2214
+ <?xml version="1.0" encoding="UTF-8"?>
2215
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2216
+ <vcard>
2217
+ <related>
2218
+ <parameters>
2219
+ <type>
2220
+ <text>friend</text>
2221
+ </type>
2222
+ </parameters>
2223
+ <uri>urn:uuid:f81d4fae-7dec-11d0-a765-00a0c91e6bf6</uri>
2224
+ </related>
2225
+ </vcard>
2226
+ </vcards>
2227
+ XML
2228
+ vobj = <<VOBJ
2229
+ BEGIN:VCARD
2230
+ VERSION:4.0
2231
+ RELATED;TYPE=friend:urn:uuid:f81d4fae-7dec-11d0-a765-00a0c91e6bf6
2232
+ END:VCARD
2233
+ VOBJ
2234
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2235
+ end
2236
+
2237
+ # Property: CATEGORIES.
2238
+ def test_rfc6350_section6_7_1
2239
+ xml = <<XML
2240
+ <?xml version="1.0" encoding="UTF-8"?>
2241
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2242
+ <vcard>
2243
+ <categories>
2244
+ <text>INTERNET</text>
2245
+ <text>IETF</text>
2246
+ <text>INDUSTRY</text>
2247
+ <text>INFORMATION TECHNOLOGY</text>
2248
+ </categories>
2249
+ </vcard>
2250
+ </vcards>
2251
+ XML
2252
+ vobj = <<VOBJ
2253
+ BEGIN:VCARD
2254
+ VERSION:4.0
2255
+ CATEGORIES:INTERNET,IETF,INDUSTRY,INFORMATION TECHNOLOGY
2256
+ END:VCARD
2257
+ VOBJ
2258
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2259
+ end
2260
+
2261
+ # Property: NOTE.
2262
+ def test_rfc6350_section6_7_2
2263
+ xml = <<XML
2264
+ <?xml version="1.0" encoding="UTF-8"?>
2265
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2266
+ <vcard>
2267
+ <note>
2268
+ <text>Foo, bar</text>
2269
+ </note>
2270
+ </vcard>
2271
+ </vcards>
2272
+ XML
2273
+ vobj = <<VOBJ
2274
+ BEGIN:VCARD
2275
+ VERSION:4.0
2276
+ NOTE:Foo\\, bar
2277
+ END:VCARD
2278
+ VOBJ
2279
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2280
+ end
2281
+
2282
+ # Property: PRODID.
2283
+ def test_rfc6350_section6_7_3
2284
+ xml = <<XML
2285
+ <?xml version="1.0" encoding="UTF-8"?>
2286
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2287
+ <vcard>
2288
+ <prodid>
2289
+ <text>-//ONLINE DIRECTORY//NONSGML Version 1//EN</text>
2290
+ </prodid>
2291
+ </vcard>
2292
+ </vcards>
2293
+ XML
2294
+ vobj = <<VOBJ
2295
+ BEGIN:VCARD
2296
+ VERSION:4.0
2297
+ PRODID:-//ONLINE DIRECTORY//NONSGML Version 1//EN
2298
+ END:VCARD
2299
+ VOBJ
2300
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2301
+ end
2302
+
2303
+ def test_rfc6350_section6_7_4
2304
+ xml = <<XML
2305
+ <?xml version="1.0" encoding="UTF-8"?>
2306
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2307
+ <vcard>
2308
+ <rev>
2309
+ <timestamp>19951031T222710Z</timestamp>
2310
+ </rev>
2311
+ </vcard>
2312
+ </vcards>
2313
+ XML
2314
+ vobj = <<VOBJ
2315
+ BEGIN:VCARD
2316
+ VERSION:4.0
2317
+ REV:19951031T222710Z
2318
+ END:VCARD
2319
+ VOBJ
2320
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2321
+ end
2322
+
2323
+ # Property: SOUND.
2324
+ def test_rfc6350_section6_7_5
2325
+ xml = <<XML
2326
+ <?xml version="1.0" encoding="UTF-8"?>
2327
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2328
+ <vcard>
2329
+ <sound>
2330
+ <uri>CID:JOHNQPUBLIC.part8.19960229T080000.xyzMail@example.com</uri>
2331
+ </sound>
2332
+ </vcard>
2333
+ </vcards>
2334
+ XML
2335
+ vobj = <<VOBJ
2336
+ BEGIN:VCARD
2337
+ VERSION:4.0
2338
+ SOUND:CID:JOHNQPUBLIC.part8.19960229T080000.xyzMail@example.com
2339
+ END:VCARD
2340
+ VOBJ
2341
+ assert_xml_equals_to_mime_dir(xml, vobj)
2342
+
2343
+ xml = <<XML
2344
+ <?xml version="1.0" encoding="UTF-8"?>
2345
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2346
+ <vcard>
2347
+ <sound>
2348
+ <text>CID:JOHNQPUBLIC.part8.19960229T080000.xyzMail@example.com</text>
2349
+ </sound>
2350
+ </vcard>
2351
+ </vcards>
2352
+ XML
2353
+ vobj = <<VOBJ
2354
+ BEGIN:VCARD
2355
+ VERSION:4.0
2356
+ SOUND:CID:JOHNQPUBLIC.part8.19960229T080000.xyzMail@example.com
2357
+ END:VCARD
2358
+ VOBJ
2359
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2360
+ end
2361
+
2362
+ # Property: UID.
2363
+ def test_rfc6350_section6_7_6
2364
+ xml = <<XML
2365
+ <?xml version="1.0" encoding="UTF-8"?>
2366
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2367
+ <vcard>
2368
+ <uid>
2369
+ <text>urn:uuid:f81d4fae-7dec-11d0-a765-00a0c91e6bf6</text>
2370
+ </uid>
2371
+ </vcard>
2372
+ </vcards>
2373
+ XML
2374
+ vobj = <<VOBJ
2375
+ BEGIN:VCARD
2376
+ VERSION:4.0
2377
+ UID:urn:uuid:f81d4fae-7dec-11d0-a765-00a0c91e6bf6
2378
+ END:VCARD
2379
+ VOBJ
2380
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2381
+ end
2382
+
2383
+ # Property: CLIENTPIDMAP.
2384
+ def test_rfc6350_section6_7_7
2385
+ xml = <<XML
2386
+ <?xml version="1.0" encoding="UTF-8"?>
2387
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2388
+ <vcard>
2389
+ <clientpidmap>
2390
+ <sourceid>1</sourceid>
2391
+ <uri>urn:uuid:3df403f4-5924-4bb7-b077-3c711d9eb34b</uri>
2392
+ </clientpidmap>
2393
+ </vcard>
2394
+ </vcards>
2395
+ XML
2396
+ vobj = <<VOBJ
2397
+ BEGIN:VCARD
2398
+ VERSION:4.0
2399
+ CLIENTPIDMAP:1;urn:uuid:3df403f4-5924-4bb7-b077-3c711d9eb34b
2400
+ END:VCARD
2401
+ VOBJ
2402
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2403
+ end
2404
+
2405
+ # Property: URL.
2406
+ def test_rfc6350_section6_7_8
2407
+ xml = <<XML
2408
+ <?xml version="1.0" encoding="UTF-8"?>
2409
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2410
+ <vcard>
2411
+ <url>
2412
+ <uri>http://example.org/restaurant.french/~chezchic.html</uri>
2413
+ </url>
2414
+ </vcard>
2415
+ </vcards>
2416
+ XML
2417
+ vobj = <<VOBJ
2418
+ BEGIN:VCARD
2419
+ VERSION:4.0
2420
+ URL:http://example.org/restaurant.french/~chezchic.html
2421
+ END:VCARD
2422
+ VOBJ
2423
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2424
+ end
2425
+
2426
+ # Property: VERSION.
2427
+ def test_rfc6350_section6_7_9
2428
+ xml = <<XML
2429
+ <?xml version="1.0" encoding="UTF-8"?>
2430
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2431
+ <vcard/>
2432
+ </vcards>
2433
+ XML
2434
+ vobj = <<VOBJ
2435
+ BEGIN:VCARD
2436
+ VERSION:4.0
2437
+ END:VCARD
2438
+ VOBJ
2439
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2440
+ end
2441
+
2442
+ # Property: KEY.
2443
+ def test_rfc6350_section6_8_1
2444
+ xml = <<XML
2445
+ <?xml version="1.0" encoding="UTF-8"?>
2446
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2447
+ <vcard>
2448
+ <key>
2449
+ <parameters>
2450
+ <mediatype>
2451
+ <text>application/pgp-keys</text>
2452
+ </mediatype>
2453
+ </parameters>
2454
+ <text>ftp://example.com/keys/jdoe</text>
2455
+ </key>
2456
+ </vcard>
2457
+ </vcards>
2458
+ XML
2459
+ vobj = <<VOBJ
2460
+ BEGIN:VCARD
2461
+ VERSION:4.0
2462
+ KEY;MEDIATYPE=application/pgp-keys:ftp://example.com/keys/jdoe
2463
+ END:VCARD
2464
+ VOBJ
2465
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2466
+ end
2467
+
2468
+ # Property: FBURL.
2469
+ def test_rfc6350_section6_9_1
2470
+ xml = <<XML
2471
+ <?xml version="1.0" encoding="UTF-8"?>
2472
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2473
+ <vcard>
2474
+ <fburl>
2475
+ <parameters>
2476
+ <pref>
2477
+ <text>1</text>
2478
+ </pref>
2479
+ </parameters>
2480
+ <uri>http://www.example.com/busy/janedoe</uri>
2481
+ </fburl>
2482
+ </vcard>
2483
+ </vcards>
2484
+ XML
2485
+ vobj = <<VOBJ
2486
+ BEGIN:VCARD
2487
+ VERSION:4.0
2488
+ FBURL;PREF=1:http://www.example.com/busy/janedoe
2489
+ END:VCARD
2490
+ VOBJ
2491
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2492
+ end
2493
+
2494
+ # Property: CALADRURI.
2495
+ def test_rfc6350_section6_9_2
2496
+ xml = <<XML
2497
+ <?xml version="1.0" encoding="UTF-8"?>
2498
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2499
+ <vcard>
2500
+ <caladruri>
2501
+ <uri>http://example.com/calendar/jdoe</uri>
2502
+ </caladruri>
2503
+ </vcard>
2504
+ </vcards>
2505
+ XML
2506
+ vobj = <<VOBJ
2507
+ BEGIN:VCARD
2508
+ VERSION:4.0
2509
+ CALADRURI:http://example.com/calendar/jdoe
2510
+ END:VCARD
2511
+ VOBJ
2512
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2513
+ end
2514
+
2515
+ # Property: CALURI.
2516
+ def test_rfc6350_section6_9_3
2517
+ xml = <<XML
2518
+ <?xml version="1.0" encoding="UTF-8"?>
2519
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2520
+ <vcard>
2521
+ <caluri>
2522
+ <parameters>
2523
+ <pref>
2524
+ <text>1</text>
2525
+ </pref>
2526
+ </parameters>
2527
+ <uri>http://cal.example.com/calA</uri>
2528
+ </caluri>
2529
+ </vcard>
2530
+ </vcards>
2531
+ XML
2532
+ vobj = <<VOBJ
2533
+ BEGIN:VCARD
2534
+ VERSION:4.0
2535
+ CALURI;PREF=1:http://cal.example.com/calA
2536
+ END:VCARD
2537
+ VOBJ
2538
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2539
+ end
2540
+
2541
+ # Property: CAPURI.
2542
+ def test_rfc6350_section_a_3
2543
+ xml = <<XML
2544
+ <?xml version="1.0" encoding="UTF-8"?>
2545
+ <vcards xmlns="urn:ietf:params:xml:ns:vcard-4.0">
2546
+ <vcard>
2547
+ <capuri>
2548
+ <uri>http://cap.example.com/capA</uri>
2549
+ </capuri>
2550
+ </vcard>
2551
+ </vcards>
2552
+ XML
2553
+ vobj = <<VOBJ
2554
+ BEGIN:VCARD
2555
+ VERSION:4.0
2556
+ CAPURI:http://cap.example.com/capA
2557
+ END:VCARD
2558
+ VOBJ
2559
+ assert_xml_reflexively_equals_to_mime_dir(xml, vobj)
2560
+ end
2561
+ end
2562
+ end
2563
+ end