1<?php 2 3namespace Sabre\VObject; 4 5class ReaderTest extends \PHPUnit_Framework_TestCase { 6 7 function testReadComponent() { 8 9 $data = "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; 10 11 $result = Reader::read($data); 12 13 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 14 $this->assertEquals('VCALENDAR', $result->name); 15 $this->assertEquals(0, count($result->children)); 16 17 } 18 function testReadStream() { 19 20 $data = "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; 21 22 $stream = fopen('php://memory', 'r+'); 23 fwrite($stream, $data); 24 rewind($stream); 25 26 $result = Reader::read($stream); 27 28 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 29 $this->assertEquals('VCALENDAR', $result->name); 30 $this->assertEquals(0, count($result->children)); 31 32 } 33 34 function testReadComponentUnixNewLine() { 35 36 $data = "BEGIN:VCALENDAR\nEND:VCALENDAR"; 37 38 $result = Reader::read($data); 39 40 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 41 $this->assertEquals('VCALENDAR', $result->name); 42 $this->assertEquals(0, count($result->children)); 43 44 } 45 46 function testReadComponentLineFold() { 47 48 $data = "BEGIN:\r\n\tVCALENDAR\r\nE\r\n ND:VCALENDAR"; 49 50 $result = Reader::read($data); 51 52 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 53 $this->assertEquals('VCALENDAR', $result->name); 54 $this->assertEquals(0, count($result->children)); 55 56 } 57 58 /** 59 * @expectedException Sabre\VObject\ParseException 60 */ 61 function testReadCorruptComponent() { 62 63 $data = "BEGIN:VCALENDAR\r\nEND:FOO"; 64 65 $result = Reader::read($data); 66 67 } 68 69 /** 70 * @expectedException Sabre\VObject\ParseException 71 */ 72 function testReadCorruptSubComponent() { 73 74 $data = "BEGIN:VCALENDAR\r\nBEGIN:VEVENT\r\nEND:FOO\r\nEND:VCALENDAR"; 75 76 $result = Reader::read($data); 77 78 } 79 80 function testReadProperty() { 81 82 $data = "BEGIN:VCALENDAR\r\nSUMMARY:propValue\r\nEND:VCALENDAR"; 83 $result = Reader::read($data); 84 85 $result = $result->SUMMARY; 86 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 87 $this->assertEquals('SUMMARY', $result->name); 88 $this->assertEquals('propValue', $result->getValue()); 89 90 } 91 92 function testReadPropertyWithNewLine() { 93 94 $data = "BEGIN:VCALENDAR\r\nSUMMARY:Line1\\nLine2\\NLine3\\\\Not the 4th line!\r\nEND:VCALENDAR"; 95 $result = Reader::read($data); 96 97 $result = $result->SUMMARY; 98 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 99 $this->assertEquals('SUMMARY', $result->name); 100 $this->assertEquals("Line1\nLine2\nLine3\\Not the 4th line!", $result->getValue()); 101 102 } 103 104 function testReadMappedProperty() { 105 106 $data = "BEGIN:VCALENDAR\r\nDTSTART:20110529\r\nEND:VCALENDAR"; 107 $result = Reader::read($data); 108 109 $result = $result->DTSTART; 110 $this->assertInstanceOf('Sabre\\VObject\\Property\\ICalendar\\DateTime', $result); 111 $this->assertEquals('DTSTART', $result->name); 112 $this->assertEquals('20110529', $result->getValue()); 113 114 } 115 116 function testReadMappedPropertyGrouped() { 117 118 $data = "BEGIN:VCALENDAR\r\nfoo.DTSTART:20110529\r\nEND:VCALENDAR"; 119 $result = Reader::read($data); 120 121 $result = $result->DTSTART; 122 $this->assertInstanceOf('Sabre\\VObject\\Property\\ICalendar\\DateTime', $result); 123 $this->assertEquals('DTSTART', $result->name); 124 $this->assertEquals('20110529', $result->getValue()); 125 126 } 127 128 /** 129 * @expectedException Sabre\VObject\ParseException 130 */ 131 function testReadBrokenLine() { 132 133 $data = "BEGIN:VCALENDAR\r\nPROPNAME;propValue"; 134 $result = Reader::read($data); 135 136 } 137 138 function testReadPropertyInComponent() { 139 140 $data = array( 141 "BEGIN:VCALENDAR", 142 "PROPNAME:propValue", 143 "END:VCALENDAR" 144 ); 145 146 $result = Reader::read(implode("\r\n",$data)); 147 148 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 149 $this->assertEquals('VCALENDAR', $result->name); 150 $this->assertEquals(1, count($result->children())); 151 $this->assertInstanceOf('Sabre\\VObject\\Property', $result->children[0]); 152 $this->assertEquals('PROPNAME', $result->children[0]->name); 153 $this->assertEquals('propValue', $result->children[0]->getValue()); 154 155 } 156 157 function testReadNestedComponent() { 158 159 $data = array( 160 "BEGIN:VCALENDAR", 161 "BEGIN:VTIMEZONE", 162 "BEGIN:DAYLIGHT", 163 "END:DAYLIGHT", 164 "END:VTIMEZONE", 165 "END:VCALENDAR" 166 ); 167 168 $result = Reader::read(implode("\r\n",$data)); 169 170 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 171 $this->assertEquals('VCALENDAR', $result->name); 172 $this->assertEquals(1, count($result->children())); 173 $this->assertInstanceOf('Sabre\\VObject\\Component', $result->children[0]); 174 $this->assertEquals('VTIMEZONE', $result->children[0]->name); 175 $this->assertEquals(1, count($result->children[0]->children())); 176 $this->assertInstanceOf('Sabre\\VObject\\Component', $result->children[0]->children[0]); 177 $this->assertEquals('DAYLIGHT', $result->children[0]->children[0]->name); 178 179 180 } 181 182 function testReadPropertyParameter() { 183 184 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue:propValue\r\nEND:VCALENDAR"; 185 $result = Reader::read($data); 186 187 $result = $result->PROPNAME; 188 189 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 190 $this->assertEquals('PROPNAME', $result->name); 191 $this->assertEquals('propValue', $result->getValue()); 192 $this->assertEquals(1, count($result->parameters())); 193 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 194 $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); 195 196 } 197 198 function testReadPropertyRepeatingParameter() { 199 200 $data = "BEGIN:VCALENDAR\r\nPROPNAME;N=1;N=2;N=3,4;N=\"5\",6;N=\"7,8\";N=9,10;N=^'11^':propValue\r\nEND:VCALENDAR"; 201 $result = Reader::read($data); 202 203 $result = $result->PROPNAME; 204 205 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 206 $this->assertEquals('PROPNAME', $result->name); 207 $this->assertEquals('propValue', $result->getValue()); 208 $this->assertEquals(1, count($result->parameters())); 209 $this->assertEquals('N', $result->parameters['N']->name); 210 $this->assertEquals('1,2,3,4,5,6,7,8,9,10,"11"', $result->parameters['N']->getValue()); 211 $this->assertEquals(array(1,2,3,4,5,6,"7,8",9,10,'"11"'), $result->parameters['N']->getParts()); 212 213 } 214 215 function testReadPropertyRepeatingNamelessGuessedParameter() { 216 $data = "BEGIN:VCALENDAR\r\nPROPNAME;WORK;VOICE;PREF:propValue\r\nEND:VCALENDAR"; 217 $result = Reader::read($data); 218 219 $result = $result->PROPNAME; 220 221 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 222 $this->assertEquals('PROPNAME', $result->name); 223 $this->assertEquals('propValue', $result->getValue()); 224 $this->assertEquals(1, count($result->parameters())); 225 $this->assertEquals('TYPE', $result->parameters['TYPE']->name); 226 $this->assertEquals('WORK,VOICE,PREF', $result->parameters['TYPE']->getValue()); 227 $this->assertEquals(array('WORK', 'VOICE', 'PREF'), $result->parameters['TYPE']->getParts()); 228 229 } 230 231 function testReadPropertyNoName() { 232 233 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PRODIGY:propValue\r\nEND:VCALENDAR"; 234 $result = Reader::read($data); 235 236 $result = $result->PROPNAME; 237 238 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 239 $this->assertEquals('PROPNAME', $result->name); 240 $this->assertEquals('propValue', $result->getValue()); 241 $this->assertEquals(1, count($result->parameters())); 242 $this->assertEquals('TYPE', $result->parameters['TYPE']->name); 243 $this->assertTrue($result->parameters['TYPE']->noName); 244 $this->assertEquals('PRODIGY', $result->parameters['TYPE']); 245 246 } 247 248 function testReadPropertyParameterExtraColon() { 249 250 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue:propValue:anotherrandomstring\r\nEND:VCALENDAR"; 251 $result = Reader::read($data); 252 253 $result = $result->PROPNAME; 254 255 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 256 $this->assertEquals('PROPNAME', $result->name); 257 $this->assertEquals('propValue:anotherrandomstring', $result->getValue()); 258 $this->assertEquals(1, count($result->parameters())); 259 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 260 $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); 261 262 } 263 264 function testReadProperty2Parameters() { 265 266 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue;PARAMNAME2=paramvalue2:propValue\r\nEND:VCALENDAR"; 267 $result = Reader::read($data); 268 269 $result = $result->PROPNAME; 270 271 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 272 $this->assertEquals('PROPNAME', $result->name); 273 $this->assertEquals('propValue', $result->getValue()); 274 $this->assertEquals(2, count($result->parameters())); 275 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 276 $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); 277 $this->assertEquals('PARAMNAME2', $result->parameters['PARAMNAME2']->name); 278 $this->assertEquals('paramvalue2', $result->parameters['PARAMNAME2']->getValue()); 279 280 } 281 282 function testReadPropertyParameterQuoted() { 283 284 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=\"paramvalue\":propValue\r\nEND:VCALENDAR"; 285 $result = Reader::read($data); 286 287 $result = $result->PROPNAME; 288 289 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 290 $this->assertEquals('PROPNAME', $result->name); 291 $this->assertEquals('propValue', $result->getValue()); 292 $this->assertEquals(1, count($result->parameters())); 293 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 294 $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); 295 296 } 297 298 function testReadPropertyParameterNewLines() { 299 300 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue1^nvalue2^^nvalue3:propValue\r\nEND:VCALENDAR"; 301 $result = Reader::read($data); 302 303 $result = $result->propname; 304 305 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 306 $this->assertEquals('PROPNAME', $result->name); 307 $this->assertEquals('propValue', $result->getValue()); 308 309 $this->assertEquals(1, count($result->parameters())); 310 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 311 $this->assertEquals("paramvalue1\nvalue2^nvalue3", $result->parameters['PARAMNAME']->getValue()); 312 313 } 314 315 function testReadPropertyParameterQuotedColon() { 316 317 $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=\"param:value\":propValue\r\nEND:VCALENDAR"; 318 $result = Reader::read($data); 319 $result = $result->propname; 320 321 $this->assertInstanceOf('Sabre\\VObject\\Property', $result); 322 $this->assertEquals('PROPNAME', $result->name); 323 $this->assertEquals('propValue', $result->getValue()); 324 $this->assertEquals(1, count($result->parameters())); 325 $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); 326 $this->assertEquals('param:value', $result->parameters['PARAMNAME']->getValue()); 327 328 } 329 330 function testReadForgiving() { 331 332 $data = array( 333 "BEGIN:VCALENDAR", 334 "X_PROP:propValue", 335 "END:VCALENDAR" 336 ); 337 338 $caught = false; 339 try { 340 $result = Reader::read(implode("\r\n",$data)); 341 } catch (ParseException $e) { 342 $caught = true; 343 } 344 345 $this->assertEquals(true, $caught); 346 347 $result = Reader::read(implode("\r\n",$data), Reader::OPTION_FORGIVING); 348 349 $expected = implode("\r\n", array( 350 "BEGIN:VCALENDAR", 351 "X_PROP:propValue", 352 "END:VCALENDAR", 353 "" 354 )); 355 356 $this->assertEquals($expected, $result->serialize()); 357 358 } 359 360 function testReadWithInvalidLine() { 361 362 $data = array( 363 "BEGIN:VCALENDAR", 364 "DESCRIPTION:propValue", 365 "Yes, we've actually seen a file with non-idented property values on multiple lines", 366 "END:VCALENDAR" 367 ); 368 369 $caught = false; 370 try { 371 $result = Reader::read(implode("\r\n",$data)); 372 } catch (ParseException $e) { 373 $caught = true; 374 } 375 376 $this->assertEquals(true, $caught); 377 378 $result = Reader::read(implode("\r\n",$data), Reader::OPTION_IGNORE_INVALID_LINES); 379 380 $expected = implode("\r\n", array( 381 "BEGIN:VCALENDAR", 382 "DESCRIPTION:propValue", 383 "END:VCALENDAR", 384 "" 385 )); 386 387 $this->assertEquals($expected, $result->serialize()); 388 389 } 390 391 /** 392 * Reported as Issue 32. 393 * 394 * @expectedException \Sabre\VObject\ParseException 395 */ 396 public function testReadIncompleteFile() { 397 398 $input = <<<ICS 399BEGIN:VCALENDAR 400VERSION:1.0 401BEGIN:VEVENT 402X-FUNAMBOL-FOLDER:DEFAULT_FOLDER 403X-FUNAMBOL-ALLDAY:0 404DTSTART:20111017T110000Z 405DTEND:20111017T123000Z 406X-MICROSOFT-CDO-BUSYSTATUS:BUSY 407CATEGORIES: 408LOCATION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:Netviewer Meeting 409PRIORITY:1 410STATUS:3 411X-MICROSOFT-CDO-REPLYTIME:20111017T064200Z 412SUMMARY;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:Kopieren: test 413CLASS:PUBLIC 414AALARM: 415RRULE: 416X-FUNAMBOL-BILLINGINFO: 417X-FUNAMBOL-COMPANIES: 418X-FUNAMBOL-MILEAGE: 419X-FUNAMBOL-NOAGING:0 420ATTENDEE;STATUS=NEEDS ACTION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:'Heino' heino@test.com 421ATTENDEE;STATUS=NEEDS ACTION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:'Markus' test@test.com 422ATTENDEE;STATUS=NEEDS AC 423ICS; 424 425 Reader::read($input); 426 427 } 428 429 /** 430 * @expectedException \InvalidArgumentException 431 */ 432 public function testReadBrokenInput() { 433 434 Reader::read(false); 435 436 } 437 438 public function testReadBOM() { 439 440 $data = chr(0xef) . chr(0xbb) . chr(0xbf) . "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; 441 $result = Reader::read($data); 442 443 $this->assertInstanceOf('Sabre\\VObject\\Component', $result); 444 $this->assertEquals('VCALENDAR', $result->name); 445 $this->assertEquals(0, count($result->children)); 446 447 } 448 449} 450