1--TEST--
2Prepared Statements and SELECT UNION
3--SKIPIF--
4<?php
5require_once('skipif.inc');
6require_once('skipifemb.inc');
7require_once('skipifconnectfailure.inc');
8?>
9--FILE--
10<?php
11	require_once("connect.inc");
12	require_once("table.inc");
13
14	// Regular (non-prepared) queries
15	print "Using CAST('somestring' AS CHAR)...\n";
16	if (!($res = $link->query("SELECT CAST('one' AS CHAR) AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST('two' AS CHAR)")))
17		printf("[001] [%d] %s\n", $link->errno, $link->error);
18
19	$data = array();
20	while ($row = $res->fetch_assoc()) {
21		$data[] = $row['column1'];
22		var_dump($row['column1']);
23	}
24	$res->free();
25
26	// Prepared Statements
27	if (!($stmt = $link->prepare("SELECT CAST('one' AS CHAR) AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST('two' AS CHAR)")))
28		printf("[002] [%d] %s\n", $link->errno, $link->error);
29
30	$column1 = null;
31	if (!$stmt->execute() || !$stmt->bind_result($column1))
32		printf("[003] [%d] %s\n", $stmt->errno, $stmt->error);
33
34	$index = 0;
35	while ($stmt->fetch()) {
36		if ($data[$index] != $column1) {
37			printf("[004] Row %d, expecting %s/%s got %s/%s\n",
38				$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
39		}
40		$index++;
41	}
42	$stmt->close();
43
44	if ($IS_MYSQLND) {
45		/*
46		Advantage mysqlnd -
47		The metadata mysqlnd has available after prepare is better than
48		the one made available by the MySQL Client Library (libmysql).
49		"libmysql" will give wrong results and that is OK -
50		http://bugs.mysql.com/bug.php?id=47483
51		*/
52		if (!($stmt = $link->prepare("SELECT CAST('one' AS CHAR) AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST('two' AS CHAR)")))
53			printf("[005] [%d] %s\n", $link->errno, $link->error);
54
55		$column1 = null;
56		/* Note: bind_result before execute */
57		if (!$stmt->bind_result($column1) || !$stmt->execute())
58			printf("[006] [%d] %s\n", $stmt->errno, $stmt->error);
59
60		$index = 0;
61		while ($stmt->fetch()) {
62			if ($data[$index] != $column1) {
63				printf("[007] Row %d, expecting %s/%s got %s/%s\n",
64					$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
65			}
66			$index++;
67		}
68		$stmt->close();
69	}
70
71	// Regular (non-prepared) queries
72	print "Mixing CAST('somestring'AS CHAR), integer and CAST(integer AS CHAR)...\n";
73	if (!($res = $link->query("SELECT 1 AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST(2 AS CHAR)")))
74		printf("[008] [%d] %s\n", $link->errno, $link->error);
75
76	$data = array();
77	while ($row = $res->fetch_assoc()) {
78		$data[] = $row['column1'];
79	}
80	$res->free();
81
82	// Prepared Statements
83	if (!($stmt = $link->prepare("SELECT 1 AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST(2 AS CHAR)")))
84		printf("[009] [%d] %s\n", $link->errno, $link->error);
85
86	$column1 = null;
87	if (!$stmt->execute() || !$stmt->bind_result($column1))
88		printf("[010] [%d] %s\n", $stmt->errno, $stmt->error);
89
90	$index = 0;
91	while ($stmt->fetch()) {
92		if ($data[$index] != $column1) {
93			printf("[011] Row %d, expecting %s/%s got %s/%s\n",
94				$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
95		}
96		var_dump($column1);
97		$index++;
98	}
99	$stmt->close();
100
101	if ($IS_MYSQLND) {
102		/* Advantage mysqlnd - see above... */
103		if (!($stmt = $link->prepare("SELECT 1 AS column1 UNION SELECT CAST('three' AS CHAR) UNION SELECT CAST(2 AS CHAR)")))
104			printf("[012] [%d] %s\n", $link->errno, $link->error);
105
106		$column1 = null;
107		if (!$stmt->bind_result($column1) || !$stmt->execute())
108			printf("[013] [%d] %s\n", $stmt->errno, $stmt->error);
109
110		$index = 0;
111		while ($stmt->fetch()) {
112			if ($data[$index] != $column1) {
113				printf("[014] Row %d, expecting %s/%s got %s/%s\n",
114					$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
115			}
116			$index++;
117		}
118		$stmt->close();
119	}
120
121	print "Using integer only...\n";
122	if (!($res = $link->query("SELECT 1 AS column1 UNION SELECT 303 UNION SELECT 2")))
123		printf("[015] [%d] %s\n", $link->errno, $link->error);
124
125	$data = array();
126	while ($row = $res->fetch_assoc()) {
127		$data[] = $row['column1'];
128	}
129	$res->free();
130
131	// Prepared Statements
132	if (!($stmt = $link->prepare("SELECT 1 AS column1 UNION SELECT 303 UNION SELECT 2")))
133		printf("[016] [%d] %s\n", $link->errno, $link->error);
134
135	$column1 = null;
136	if (!$stmt->execute() || !$stmt->bind_result($column1))
137		printf("[017] [%d] %s\n", $stmt->errno, $stmt->error);
138
139	$index = 0;
140	while ($stmt->fetch()) {
141		if ($data[$index] != $column1) {
142			printf("[018] Row %d, expecting %s/%s got %s/%s\n",
143				$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
144		}
145		var_dump($column1);
146		$index++;
147	}
148	$stmt->close();
149
150	if ($IS_MYSQLND) {
151		/* Advantage mysqlnd - see above */
152		if (!($stmt = $link->prepare("SELECT 1 AS column1 UNION SELECT 303 UNION SELECT 2")))
153			printf("[019] [%d] %s\n", $link->errno, $link->error);
154
155		$column1 = null;
156		if (!$stmt->bind_result($column1) || !$stmt->execute())
157			printf("[020] [%d] %s\n", $stmt->errno, $stmt->error);
158
159		$index = 0;
160		while ($stmt->fetch()) {
161			if ($data[$index] != $column1) {
162				printf("[021] Row %d, expecting %s/%s got %s/%s\n",
163					$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
164			}
165			$index++;
166		}
167		$stmt->close();
168	}
169
170	print "Testing bind_param(), strings only...\n";
171	$two = 'two';
172	$three = 'three';
173	if (!($stmt = $link->prepare("SELECT 'one' AS column1 UNION SELECT ? UNION SELECT ?")))
174		printf("[022] [%d] %s\n", $stmt->errno, $stmt->error);
175
176	$column1 = null;
177	if (!$stmt->bind_param('ss', $three, $two) || !$stmt->execute() || !$stmt->bind_result($column1))
178		printf("[023] [%d] %s\n", $stmt->errno, $stmt->error);
179
180	$index = 0;
181	$data = array();
182	while ($stmt->fetch()) {
183		$data[$index++] = $column1;
184		var_dump($column1);
185	}
186	$stmt->close();
187
188	if ($IS_MYSQLND) {
189		/* Advantage mysqlnd - see above */
190		$two = 'two';
191		$three = 'three';
192		if (!($stmt = $link->prepare("SELECT 'one' AS column1 UNION SELECT ? UNION SELECT ?")))
193			printf("[024] [%d] %s\n", $stmt->errno, $stmt->error);
194
195		$column1 = null;
196		if (!$stmt->bind_param('ss', $three, $two) || !$stmt->bind_result($column1) || !$stmt->execute())
197			printf("[025] [%d] %s\n", $stmt->errno, $stmt->error);
198
199		$index = 0;
200		while ($stmt->fetch()) {
201			if ($data[$index] != $column1) {
202				printf("[26] Row %d, expecting %s/%s, got %s/%s\n",
203					$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
204			}
205			$index++;
206		}
207		$stmt->close();
208	}
209
210	print "Testing bind_param(), strings only, with CAST AS CHAR...\n";
211	$two = 'two';
212	$three = 'three beers are more than enough';
213	if (!($stmt = $link->prepare("SELECT CAST('one' AS CHAR) AS column1 UNION SELECT CAST(? AS CHAR) UNION SELECT CAST(? AS CHAR)")))
214		printf("[027] [%d] %s\n", $stmt->errno, $stmt->error);
215
216	$column1 = null;
217	if (!$stmt->bind_param('ss', $three, $two) || !$stmt->execute() || !$stmt->bind_result($column1))
218		printf("[028] [%d] %s\n", $stmt->errno, $stmt->error);
219
220	$index = 0;
221	$data = array();
222	while ($stmt->fetch()) {
223		$data[$index++] = $column1;
224		var_dump($column1);
225	}
226	$stmt->close();
227
228	if ($IS_MYSQLND) {
229		/* Advantage mysqlnd - see above */
230		$two = 'two';
231		$three = 'three beers are more than enough';
232		if (!($stmt = $link->prepare("SELECT CAST('one' AS CHAR) AS column1 UNION SELECT CAST(? AS CHAR) UNION SELECT CAST(? AS CHAR)")))
233			printf("[029] [%d] %s\n", $stmt->errno, $stmt->error);
234
235		$column1 = null;
236		if (!$stmt->bind_param('ss', $three, $two) || !$stmt->bind_result($column1) || !$stmt->execute())
237			printf("[030] [%d] %s\n", $stmt->errno, $stmt->error);
238
239		$index = 0;
240		while ($stmt->fetch()) {
241			if ($data[$index] != $column1) {
242				printf("[31] Row %d, expecting %s/%s, got %s/%s\n",
243					$index + 1, gettype($data[$index]), $data[$index], gettype($column1), $column1);
244			}
245			$index++;
246		}
247		$stmt->close();
248	}
249
250	$link->close();
251
252	print "done!";
253?>
254--EXPECTF--
255Using CAST('somestring' AS CHAR)...
256%unicode|string%(3) "one"
257%unicode|string%(5) "three"
258%unicode|string%(3) "two"
259Mixing CAST('somestring'AS CHAR), integer and CAST(integer AS CHAR)...
260%unicode|string%(1) "1"
261%unicode|string%(5) "three"
262%unicode|string%(1) "2"
263Using integer only...
264int(1)
265int(303)
266int(2)
267Testing bind_param(), strings only...
268%unicode|string%(3) "one"
269%unicode|string%(5) "three"
270%unicode|string%(3) "two"
271Testing bind_param(), strings only, with CAST AS CHAR...
272%unicode|string%(3) "one"
273%unicode|string%(32) "three beers are more than enough"
274%unicode|string%(3) "two"
275done!
276