xref: /PHP-7.1/ext/pdo/tests/pdo_018.phpt (revision 7af945e2)
1--TEST--
2PDO Common: serializing
3--SKIPIF--
4<?php # vim:ft=php
5if (!extension_loaded('pdo')) die('skip');
6if (!interface_exists('Serializable')) die('skip no Serializable interface');
7$dir = getenv('REDIR_TEST_DIR');
8if (false == $dir) die('skip no driver');
9require_once $dir . 'pdo_test.inc';
10PDOTest::skip();
11?>
12--FILE--
13<?php
14if (getenv('REDIR_TEST_DIR') === false) putenv('REDIR_TEST_DIR='.dirname(__FILE__) . '/../../pdo/tests/');
15require_once getenv('REDIR_TEST_DIR') . 'pdo_test.inc';
16$db = PDOTest::factory();
17
18class TestBase implements Serializable
19{
20	public    $BasePub = 'Public';
21	protected $BasePro = 'Protected';
22	private   $BasePri = 'Private';
23
24	function serialize()
25	{
26		$serialized = array();
27		foreach($this as $prop => $val) {
28			$serialized[$prop] = $val;
29		}
30		$serialized = serialize($serialized);
31		echo __METHOD__ . "() = '$serialized'\n";
32		return $serialized;
33	}
34
35	function unserialize($serialized)
36	{
37		echo __METHOD__ . "($serialized)\n";
38		foreach(unserialize($serialized) as $prop => $val) {
39			$this->$prop = '#'.$val;
40		}
41		return true;
42	}
43}
44
45class TestDerived extends TestBase
46{
47	public    $BasePub    = 'DerivedPublic';
48	protected $BasePro    = 'DerivdeProtected';
49	public    $DerivedPub = 'Public';
50	protected $DerivedPro = 'Protected';
51	private   $DerivedPri = 'Private';
52
53	function serialize()
54	{
55		echo __METHOD__ . "()\n";
56		return TestBase::serialize();
57	}
58
59	function unserialize($serialized)
60	{
61		echo __METHOD__ . "()\n";
62		return TestBase::unserialize($serialized);
63	}
64}
65
66class TestLeaf extends TestDerived
67{
68}
69
70$db->exec('CREATE TABLE classtypes(id int NOT NULL PRIMARY KEY, name VARCHAR(20) NOT NULL UNIQUE)');
71$db->exec('INSERT INTO classtypes VALUES(0, \'stdClass\')');
72$db->exec('INSERT INTO classtypes VALUES(1, \'TestBase\')');
73$db->exec('INSERT INTO classtypes VALUES(2, \'TestDerived\')');
74$db->exec('CREATE TABLE test(id int NOT NULL PRIMARY KEY, classtype int, val VARCHAR(255))');
75
76$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
77
78var_dump($db->query('SELECT COUNT(*) FROM classtypes')->fetchColumn());
79var_dump($db->query('SELECT id, name FROM classtypes ORDER by id')->fetchAll(PDO::FETCH_COLUMN|PDO::FETCH_UNIQUE));
80
81$objs = array();
82$objs[0] = new stdClass;
83$objs[1] = new TestBase;
84$objs[2] = new TestDerived;
85$objs[3] = new TestLeaf;
86
87$stmt = $db->prepare('SELECT id FROM classtypes WHERE name=:cname');
88$stmt->bindParam(':cname', $cname);
89
90$ctypes = array();
91
92foreach($objs as $obj)
93{
94	$cname = get_class($obj);
95	$ctype = NULL; /* set default for non stored class name */
96	$stmt->execute();
97	$stmt->bindColumn('id', $ctype);
98	$stmt->fetch(PDO::FETCH_BOUND);
99	$ctypes[$cname] = $ctype;
100}
101
102echo "===TYPES===\n";
103var_dump($ctypes);
104
105unset($stmt);
106
107echo "===INSERT===\n";
108$stmt = $db->prepare('INSERT INTO test VALUES(:id, :classtype, :val)');
109$stmt->bindParam(':id', $idx);
110$stmt->bindParam(':classtype', $ctype);
111$stmt->bindParam(':val', $val);
112
113foreach($objs as $idx => $obj)
114{
115	$ctype = $ctypes[get_class($obj)];
116	if (method_exists($obj, 'serialize'))
117	{
118		$val = $obj->serialize();
119	}
120	else
121	{
122		$val = '';
123	}
124	$stmt->execute();
125}
126
127unset($stmt);
128
129echo "===DATA===\n";
130$res = $db->query('SELECT test.val FROM test')->fetchAll(PDO::FETCH_COLUMN);
131
132switch ($db->getAttribute(PDO::ATTR_DRIVER_NAME)) {
133	case 'dblib':
134		// map whitespace (from early TDS versions) to empty string so the test doesn't diff
135		if ($res[0] === ' ') {
136			$res[0] = '';
137		}
138		break;
139
140	case 'oci':
141		// map NULL to empty string so the test doesn't diff
142		if ($res[0] === null) {
143			$res[0] = '';
144		}
145		break;
146}
147var_dump($res);
148
149echo "===FAILURE===\n";
150try
151{
152	$db->query('SELECT classtypes.name AS name, test.val AS val FROM test LEFT JOIN classtypes ON test.classtype=classtypes.id')->fetchAll(PDO::FETCH_CLASS|PDO::FETCH_CLASSTYPE|PDO::FETCH_SERIALIZE, 'TestLeaf', array());
153}
154catch (PDOException $e)
155{
156	echo 'Exception:';
157	echo $e->getMessage()."\n";
158}
159
160echo "===COUNT===\n";
161var_dump($db->query('SELECT COUNT(*) FROM test LEFT JOIN classtypes ON test.classtype=classtypes.id WHERE (classtypes.id IS NULL OR classtypes.id > 0)')->fetchColumn());
162
163echo "===DATABASE===\n";
164$stmt = $db->prepare('SELECT classtypes.name AS name, test.val AS val FROM test LEFT JOIN classtypes ON test.classtype=classtypes.id WHERE (classtypes.id IS NULL OR classtypes.id > 0)');
165
166$stmt->execute();
167var_dump($stmt->fetchAll(PDO::FETCH_ASSOC));
168
169echo "===FETCHCLASS===\n";
170$stmt->execute();
171var_dump($stmt->fetchAll(PDO::FETCH_CLASS|PDO::FETCH_CLASSTYPE|PDO::FETCH_SERIALIZE, 'TestLeaf'));
172
173
174?>
175--EXPECTF--
176string(1) "3"
177array(3) {
178  [0]=>
179  string(8) "stdClass"
180  [1]=>
181  string(8) "TestBase"
182  [2]=>
183  string(11) "TestDerived"
184}
185===TYPES===
186array(4) {
187  ["stdClass"]=>
188  string(1) "0"
189  ["TestBase"]=>
190  string(1) "1"
191  ["TestDerived"]=>
192  string(1) "2"
193  ["TestLeaf"]=>
194  NULL
195}
196===INSERT===
197TestBase::serialize() = 'a:3:{s:7:"BasePub";s:6:"Public";s:7:"BasePro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}'
198TestDerived::serialize()
199TestBase::serialize() = 'a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}'
200TestDerived::serialize()
201TestBase::serialize() = 'a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}'
202===DATA===
203array(4) {
204  [0]=>
205  string(0) ""
206  [1]=>
207  string(91) "a:3:{s:7:"BasePub";s:6:"Public";s:7:"BasePro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
208  [2]=>
209  string(172) "a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
210  [3]=>
211  string(172) "a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
212}
213===FAILURE===
214Exception:SQLSTATE[HY000]: General error: cannot unserialize class
215===COUNT===
216string(1) "3"
217===DATABASE===
218array(3) {
219  [0]=>
220  array(2) {
221    ["name"]=>
222    string(8) "TestBase"
223    ["val"]=>
224    string(91) "a:3:{s:7:"BasePub";s:6:"Public";s:7:"BasePro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
225  }
226  [1]=>
227  array(2) {
228    ["name"]=>
229    string(11) "TestDerived"
230    ["val"]=>
231    string(172) "a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
232  }
233  [2]=>
234  array(2) {
235    ["name"]=>
236    NULL
237    ["val"]=>
238    string(172) "a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";}"
239  }
240}
241===FETCHCLASS===
242TestBase::unserialize(a:3:{s:7:"BasePub";s:6:"Public";s:7:"BasePro";s:9:"Protected";s:7:"BasePri";s:7:"Private";})
243TestDerived::unserialize()
244TestBase::unserialize(a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";})
245TestDerived::unserialize()
246TestBase::unserialize(a:5:{s:7:"BasePub";s:13:"DerivedPublic";s:7:"BasePro";s:16:"DerivdeProtected";s:10:"DerivedPub";s:6:"Public";s:10:"DerivedPro";s:9:"Protected";s:7:"BasePri";s:7:"Private";})
247array(3) {
248  [0]=>
249  object(TestBase)#%d (3) {
250    ["BasePub"]=>
251    string(7) "#Public"
252    ["BasePro":protected]=>
253    string(10) "#Protected"
254    ["BasePri":"TestBase":private]=>
255    string(8) "#Private"
256  }
257  [1]=>
258  object(TestDerived)#%d (6) {
259    ["BasePub"]=>
260    string(14) "#DerivedPublic"
261    ["BasePro":protected]=>
262    string(17) "#DerivdeProtected"
263    ["DerivedPub"]=>
264    string(7) "#Public"
265    ["DerivedPro":protected]=>
266    string(10) "#Protected"
267    ["DerivedPri":"TestDerived":private]=>
268    string(7) "Private"
269    ["BasePri":"TestBase":private]=>
270    string(8) "#Private"
271  }
272  [2]=>
273  object(TestLeaf)#%d (6) {
274    ["BasePub"]=>
275    string(14) "#DerivedPublic"
276    ["BasePro":protected]=>
277    string(17) "#DerivdeProtected"
278    ["DerivedPub"]=>
279    string(7) "#Public"
280    ["DerivedPro":protected]=>
281    string(10) "#Protected"
282    ["DerivedPri":"TestDerived":private]=>
283    string(7) "Private"
284    ["BasePri":"TestBase":private]=>
285    string(8) "#Private"
286  }
287}
288