1--TEST-- 2MongoDB\BSON\toPHP(): Tests from serialization specification 3--FILE-- 4<?php 5 6require_once __DIR__ . '/../utils/tools.php'; 7 8class MyClass 9{ 10} 11 12class YourClass implements MongoDB\BSON\Unserializable 13{ 14 function bsonUnserialize(array $data) 15 { 16 foreach ($data as $key => $value) { 17 $this->$key = $value; 18 } 19 $this->unserialized = true; 20 } 21} 22 23class OurClass implements MongoDB\BSON\Persistable 24{ 25 function bsonSerialize() 26 { 27 // Not tested with this test, so return empty array 28 return array(); 29 } 30 31 function bsonUnserialize(array $data) 32 { 33 foreach ($data as $key => $value) { 34 $this->$key = $value; 35 } 36 $this->unserialized = true; 37 } 38} 39 40class TheirClass extends OurClass 41{ 42} 43 44// Create base64-encoded class names for __pclass field's binary data 45$bMyClass = base64_encode('MyClass'); 46$bYourClass = base64_encode('YourClass'); 47$bOurClass = base64_encode('OurClass'); 48$bTheirClass = base64_encode('TheirClass'); 49$bInterface = base64_encode('MongoDB\BSON\Unserializable'); 50 51$testGroups = array( 52 array( 53 'name' => 'DEFAULT TYPEMAP', 54 'typemap' => array(), 55 'tests' => array( 56 '{ "foo": "yes", "bar" : false }', 57 '{ "foo": "no", "array" : [ 5, 6 ] }', 58 '{ "foo": "no", "obj" : { "embedded" : 4.125 } }', 59 '{ "foo": "yes", "__pclass": "MyClass" }', 60 '{ "foo": "yes", "__pclass": { "$binary": "' . $bMyClass . '", "$type": "80" } }', 61 '{ "foo": "yes", "__pclass": { "$binary": "' . $bYourClass . '", "$type": "80" } }', 62 '{ "foo": "yes", "__pclass": { "$binary": "' . $bOurClass . '", "$type": "80" } }', 63 '{ "foo": "yes", "__pclass": { "$binary": "' . $bYourClass . '", "$type": "44" } }', 64 ), 65 ), 66 array( 67 'name' => 'NONEXISTING CLASS', 68 'typemap' => array('root' => 'MissingClass'), 69 'tests' => array( 70 '{ "foo": "yes" }', 71 ), 72 ), 73 array( 74 'name' => 'DOES NOT IMPLEMENT UNSERIALIZABLE', 75 'typemap' => array('root' => 'MyClass'), 76 'tests' => array( 77 '{ "foo": "yes", "__pclass": { "$binary": "' . $bMyClass . '", "$type": "80" } }', 78 ), 79 ), 80 array( 81 'name' => 'IS NOT A CONCRETE CLASS', 82 'typemap' => array('root' => 'MongoDB\BSON\Unserializable'), 83 'tests' => array( 84 '{ "foo": "yes" }', 85 ), 86 ), 87 array( 88 'name' => 'IS NOT A CONCRETE CLASS VIA PCLASS', 89 'typemap' => array('root' => 'YourClass'), 90 'tests' => array( 91 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bInterface . '", "$type": "80" } }', 92 ), 93 ), 94 array( 95 'name' => 'PCLASS OVERRIDES TYPEMAP (1)', 96 'typemap' => array('root' => 'YourClass'), 97 'tests' => array( 98 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bMyClass . '", "$type": "80" } }', 99 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bOurClass . '", "$type": "80" } }', 100 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bTheirClass . '", "$type": "80" } }', 101 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bYourClass . '", "$type": "80" } }', 102 ), 103 ), 104 array( 105 'name' => 'PCLASS OVERRIDES TYPEMAP (2)', 106 'typemap' => array('root' => 'OurClass'), 107 'tests' => array( 108 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bTheirClass . '", "$type": "80" } }', 109 ), 110 ), 111 array( 112 'name' => 'OBJECTS AS ARRAY', 113 'typemap' => array('root' => 'array', 'document' => 'array'), 114 'tests' => array( 115 '{ "foo": "yes", "bar" : false }', 116 '{ "foo": "no", "array" : [ 5, 6 ] }', 117 '{ "foo": "no", "obj" : { "embedded" : 4.125 } }', 118 '{ "foo": "yes", "__pclass": "MyClass" }', 119 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bMyClass . '", "$type": "80" } }', 120 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bOurClass . '", "$type": "80" } }', 121 ), 122 ), 123 array( 124 'name' => 'OBJECTS AS STDCLASS', 125 'typemap' => array('root' => 'object', 'document' => 'object'), 126 'tests' => array( 127 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bMyClass . '", "$type": "80" } }', 128 '{ "foo": "yes", "__pclass" : { "$binary": "' . $bOurClass . '", "$type": "80" } }', 129 ), 130 ), 131); 132 133foreach ($testGroups as $testGroup) { 134 printf("=== %s ===\n\n", $testGroup['name']); 135 136 foreach ($testGroup['tests'] as $test) { 137 echo $test, "\n"; 138 139 $bson = fromJSON($test); 140 try { 141 var_dump(toPHP($bson, $testGroup['typemap'])); 142 } catch (MongoDB\Driver\Exception\Exception $e) { 143 echo $e->getMessage(), "\n"; 144 } 145 146 echo "\n"; 147 } 148 149 echo "\n"; 150} 151 152?> 153===DONE=== 154<?php exit(0); ?> 155--EXPECTF-- 156=== DEFAULT TYPEMAP === 157 158{ "foo": "yes", "bar" : false } 159object(stdClass)#%d (2) { 160 ["foo"]=> 161 string(3) "yes" 162 ["bar"]=> 163 bool(false) 164} 165 166{ "foo": "no", "array" : [ 5, 6 ] } 167object(stdClass)#%d (2) { 168 ["foo"]=> 169 string(2) "no" 170 ["array"]=> 171 array(2) { 172 [0]=> 173 int(5) 174 [1]=> 175 int(6) 176 } 177} 178 179{ "foo": "no", "obj" : { "embedded" : 4.125 } } 180object(stdClass)#%d (2) { 181 ["foo"]=> 182 string(2) "no" 183 ["obj"]=> 184 object(stdClass)#%d (1) { 185 ["embedded"]=> 186 float(4.125) 187 } 188} 189 190{ "foo": "yes", "__pclass": "MyClass" } 191object(stdClass)#%d (2) { 192 ["foo"]=> 193 string(3) "yes" 194 ["__pclass"]=> 195 string(7) "MyClass" 196} 197 198{ "foo": "yes", "__pclass": { "$binary": "TXlDbGFzcw==", "$type": "80" } } 199object(stdClass)#%d (2) { 200 ["foo"]=> 201 string(3) "yes" 202 ["__pclass"]=> 203 object(MongoDB\BSON\Binary)#%d (2) { 204 ["data"]=> 205 string(7) "MyClass" 206 ["type"]=> 207 int(128) 208 } 209} 210 211{ "foo": "yes", "__pclass": { "$binary": "WW91ckNsYXNz", "$type": "80" } } 212object(stdClass)#%d (2) { 213 ["foo"]=> 214 string(3) "yes" 215 ["__pclass"]=> 216 object(MongoDB\BSON\Binary)#%d (2) { 217 ["data"]=> 218 string(9) "YourClass" 219 ["type"]=> 220 int(128) 221 } 222} 223 224{ "foo": "yes", "__pclass": { "$binary": "T3VyQ2xhc3M=", "$type": "80" } } 225object(OurClass)#%d (3) { 226 ["foo"]=> 227 string(3) "yes" 228 ["__pclass"]=> 229 object(MongoDB\BSON\Binary)#%d (2) { 230 ["data"]=> 231 string(8) "OurClass" 232 ["type"]=> 233 int(128) 234 } 235 ["unserialized"]=> 236 bool(true) 237} 238 239{ "foo": "yes", "__pclass": { "$binary": "WW91ckNsYXNz", "$type": "44" } } 240object(stdClass)#%d (2) { 241 ["foo"]=> 242 string(3) "yes" 243 ["__pclass"]=> 244 object(MongoDB\BSON\Binary)#%d (2) { 245 ["data"]=> 246 string(9) "YourClass" 247 ["type"]=> 248 int(68) 249 } 250} 251 252 253=== NONEXISTING CLASS === 254 255{ "foo": "yes" } 256Class MissingClass does not exist 257 258 259=== DOES NOT IMPLEMENT UNSERIALIZABLE === 260 261{ "foo": "yes", "__pclass": { "$binary": "TXlDbGFzcw==", "$type": "80" } } 262Class MyClass does not implement MongoDB\BSON\Unserializable 263 264 265=== IS NOT A CONCRETE CLASS === 266 267{ "foo": "yes" } 268Class MongoDB\BSON\Unserializable is not instantiatable 269 270 271=== IS NOT A CONCRETE CLASS VIA PCLASS === 272 273{ "foo": "yes", "__pclass" : { "$binary": "TW9uZ29EQlxCU09OXFVuc2VyaWFsaXphYmxl", "$type": "80" } } 274object(YourClass)#%d (3) { 275 ["foo"]=> 276 string(3) "yes" 277 ["__pclass"]=> 278 object(MongoDB\BSON\Binary)#%d (2) { 279 ["data"]=> 280 string(27) "MongoDB\BSON\Unserializable" 281 ["type"]=> 282 int(128) 283 } 284 ["unserialized"]=> 285 bool(true) 286} 287 288 289=== PCLASS OVERRIDES TYPEMAP (1) === 290 291{ "foo": "yes", "__pclass" : { "$binary": "TXlDbGFzcw==", "$type": "80" } } 292object(YourClass)#%d (3) { 293 ["foo"]=> 294 string(3) "yes" 295 ["__pclass"]=> 296 object(MongoDB\BSON\Binary)#%d (2) { 297 ["data"]=> 298 string(7) "MyClass" 299 ["type"]=> 300 int(128) 301 } 302 ["unserialized"]=> 303 bool(true) 304} 305 306{ "foo": "yes", "__pclass" : { "$binary": "T3VyQ2xhc3M=", "$type": "80" } } 307object(OurClass)#%d (3) { 308 ["foo"]=> 309 string(3) "yes" 310 ["__pclass"]=> 311 object(MongoDB\BSON\Binary)#%d (2) { 312 ["data"]=> 313 string(8) "OurClass" 314 ["type"]=> 315 int(128) 316 } 317 ["unserialized"]=> 318 bool(true) 319} 320 321{ "foo": "yes", "__pclass" : { "$binary": "VGhlaXJDbGFzcw==", "$type": "80" } } 322object(TheirClass)#%d (3) { 323 ["foo"]=> 324 string(3) "yes" 325 ["__pclass"]=> 326 object(MongoDB\BSON\Binary)#%d (2) { 327 ["data"]=> 328 string(10) "TheirClass" 329 ["type"]=> 330 int(128) 331 } 332 ["unserialized"]=> 333 bool(true) 334} 335 336{ "foo": "yes", "__pclass" : { "$binary": "WW91ckNsYXNz", "$type": "80" } } 337object(YourClass)#%d (3) { 338 ["foo"]=> 339 string(3) "yes" 340 ["__pclass"]=> 341 object(MongoDB\BSON\Binary)#%d (2) { 342 ["data"]=> 343 string(9) "YourClass" 344 ["type"]=> 345 int(128) 346 } 347 ["unserialized"]=> 348 bool(true) 349} 350 351 352=== PCLASS OVERRIDES TYPEMAP (2) === 353 354{ "foo": "yes", "__pclass" : { "$binary": "VGhlaXJDbGFzcw==", "$type": "80" } } 355object(TheirClass)#%d (3) { 356 ["foo"]=> 357 string(3) "yes" 358 ["__pclass"]=> 359 object(MongoDB\BSON\Binary)#%d (2) { 360 ["data"]=> 361 string(10) "TheirClass" 362 ["type"]=> 363 int(128) 364 } 365 ["unserialized"]=> 366 bool(true) 367} 368 369 370=== OBJECTS AS ARRAY === 371 372{ "foo": "yes", "bar" : false } 373array(2) { 374 ["foo"]=> 375 string(3) "yes" 376 ["bar"]=> 377 bool(false) 378} 379 380{ "foo": "no", "array" : [ 5, 6 ] } 381array(2) { 382 ["foo"]=> 383 string(2) "no" 384 ["array"]=> 385 array(2) { 386 [0]=> 387 int(5) 388 [1]=> 389 int(6) 390 } 391} 392 393{ "foo": "no", "obj" : { "embedded" : 4.125 } } 394array(2) { 395 ["foo"]=> 396 string(2) "no" 397 ["obj"]=> 398 array(1) { 399 ["embedded"]=> 400 float(4.125) 401 } 402} 403 404{ "foo": "yes", "__pclass": "MyClass" } 405array(2) { 406 ["foo"]=> 407 string(3) "yes" 408 ["__pclass"]=> 409 string(7) "MyClass" 410} 411 412{ "foo": "yes", "__pclass" : { "$binary": "TXlDbGFzcw==", "$type": "80" } } 413array(2) { 414 ["foo"]=> 415 string(3) "yes" 416 ["__pclass"]=> 417 object(MongoDB\BSON\Binary)#%d (2) { 418 ["data"]=> 419 string(7) "MyClass" 420 ["type"]=> 421 int(128) 422 } 423} 424 425{ "foo": "yes", "__pclass" : { "$binary": "T3VyQ2xhc3M=", "$type": "80" } } 426array(2) { 427 ["foo"]=> 428 string(3) "yes" 429 ["__pclass"]=> 430 object(MongoDB\BSON\Binary)#%d (2) { 431 ["data"]=> 432 string(8) "OurClass" 433 ["type"]=> 434 int(128) 435 } 436} 437 438 439=== OBJECTS AS STDCLASS === 440 441{ "foo": "yes", "__pclass" : { "$binary": "TXlDbGFzcw==", "$type": "80" } } 442object(stdClass)#%d (2) { 443 ["foo"]=> 444 string(3) "yes" 445 ["__pclass"]=> 446 object(MongoDB\BSON\Binary)#%d (2) { 447 ["data"]=> 448 string(7) "MyClass" 449 ["type"]=> 450 int(128) 451 } 452} 453 454{ "foo": "yes", "__pclass" : { "$binary": "T3VyQ2xhc3M=", "$type": "80" } } 455object(stdClass)#%d (2) { 456 ["foo"]=> 457 string(3) "yes" 458 ["__pclass"]=> 459 object(MongoDB\BSON\Binary)#%d (2) { 460 ["data"]=> 461 string(8) "OurClass" 462 ["type"]=> 463 int(128) 464 } 465} 466 467 468===DONE=== 469