1--TEST--
2MySQL PDOStatement->nextRowSet() with PDO::MYSQL_ATTR_MULTI_STATEMENTS either true or false
3--EXTENSIONS--
4pdo_mysql
5--SKIPIF--
6<?php
7require_once(__DIR__ . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc');
8MySQLPDOTest::skip();
9$db = MySQLPDOTest::factory();
10$row = $db->query('SELECT VERSION() as _version')->fetch(PDO::FETCH_ASSOC);
11$matches = array();
12if (!preg_match('/^(\d+)\.(\d+)\.(\d+)/ismU', $row['_version'], $matches))
13    die(sprintf("skip Cannot determine MySQL Server version\n"));
14
15$version = $matches[1] * 10000 + $matches[2] * 100 + $matches[3];
16if ($version < 50000)
17    die(sprintf("skip Need MySQL Server 5.0.0+, found %d.%02d.%02d (%d)\n",
18        $matches[1], $matches[2], $matches[3], $version));
19?>
20--FILE--
21<?php
22    require_once(__DIR__ . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc');
23    $db = MySQLPDOTest::factory();
24    $db->setAttribute(PDO::ATTR_STRINGIFY_FETCHES, true);
25
26    MySQLPDOTest::createTestTable($db);
27
28    function test_proc($db) {
29
30        $db->exec('DROP PROCEDURE IF EXISTS p');
31        $db->exec('CREATE PROCEDURE p() BEGIN SELECT id FROM test ORDER BY id ASC LIMIT 3; SELECT id, label FROM test WHERE id < 4 ORDER BY id DESC LIMIT 3; END;');
32        $stmt = $db->query('CALL p()');
33        do {
34            var_dump($stmt->fetchAll(PDO::FETCH_ASSOC));
35        } while ($stmt->nextRowSet());
36        var_dump($stmt->nextRowSet());
37
38    }
39
40    try {
41
42        // Using native PS for proc, since emulated fails.
43        printf("Native PS...\n");
44        foreach (array(false, true) as $multi) {
45            $value = $multi ? 'true' : 'false';
46            echo "\nTesting with PDO::MYSQL_ATTR_MULTI_STATEMENTS set to {$value}\n";
47            $dsn = MySQLPDOTest::getDSN();
48            $user = PDO_MYSQL_TEST_USER;
49            $pass = PDO_MYSQL_TEST_PASS;
50            $db = new PDO($dsn, $user, $pass, array(PDO::MYSQL_ATTR_MULTI_STATEMENTS => $multi));
51            $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_WARNING);
52            $db->setAttribute(PDO::ATTR_STRINGIFY_FETCHES, true);
53            $db->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, 1);
54            $db->setAttribute(PDO::ATTR_EMULATE_PREPARES, 0);
55            test_proc($db);
56
57            $db = new PDO($dsn, $user, $pass, array(PDO::MYSQL_ATTR_MULTI_STATEMENTS => $multi));
58            $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_WARNING);
59            $db->setAttribute(PDO::ATTR_STRINGIFY_FETCHES, true);
60            $db->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, 0);
61            $db->setAttribute(PDO::ATTR_EMULATE_PREPARES, 0);
62
63            test_proc($db);
64
65            // Switch back to emulated prepares to verify multi statement attribute.
66            $db->setAttribute(PDO::ATTR_EMULATE_PREPARES, 1);
67            // This will fail when $multi is false.
68            $stmt = $db->query("SELECT * FROM test; INSERT INTO test (id, label) VALUES (99, 'x')");
69            if ($stmt !== false) {
70                $stmt->closeCursor();
71            }
72            $info = $db->errorInfo();
73            var_dump($info[0]);
74        }
75        @$db->exec('DROP PROCEDURE IF EXISTS p');
76
77    } catch (PDOException $e) {
78        printf("[001] %s [%s] %s\n",
79            $e->getMessage(), $db->errorCode(), implode(' ', $db->errorInfo()));
80    }
81
82    print "done!";
83?>
84--CLEAN--
85<?php
86require __DIR__ . '/mysql_pdo_test.inc';
87MySQLPDOTest::dropTestTable();
88?>
89--EXPECTF--
90Native PS...
91
92Testing with PDO::MYSQL_ATTR_MULTI_STATEMENTS set to false
93array(3) {
94  [0]=>
95  array(1) {
96    ["id"]=>
97    string(1) "1"
98  }
99  [1]=>
100  array(1) {
101    ["id"]=>
102    string(1) "2"
103  }
104  [2]=>
105  array(1) {
106    ["id"]=>
107    string(1) "3"
108  }
109}
110array(3) {
111  [0]=>
112  array(2) {
113    ["id"]=>
114    string(1) "3"
115    ["label"]=>
116    string(1) "c"
117  }
118  [1]=>
119  array(2) {
120    ["id"]=>
121    string(1) "2"
122    ["label"]=>
123    string(1) "b"
124  }
125  [2]=>
126  array(2) {
127    ["id"]=>
128    string(1) "1"
129    ["label"]=>
130    string(1) "a"
131  }
132}
133array(0) {
134}
135bool(false)
136array(3) {
137  [0]=>
138  array(1) {
139    ["id"]=>
140    string(1) "1"
141  }
142  [1]=>
143  array(1) {
144    ["id"]=>
145    string(1) "2"
146  }
147  [2]=>
148  array(1) {
149    ["id"]=>
150    string(1) "3"
151  }
152}
153array(3) {
154  [0]=>
155  array(2) {
156    ["id"]=>
157    string(1) "3"
158    ["label"]=>
159    string(1) "c"
160  }
161  [1]=>
162  array(2) {
163    ["id"]=>
164    string(1) "2"
165    ["label"]=>
166    string(1) "b"
167  }
168  [2]=>
169  array(2) {
170    ["id"]=>
171    string(1) "1"
172    ["label"]=>
173    string(1) "a"
174  }
175}
176array(0) {
177}
178bool(false)
179
180Warning: PDO::query(): SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your %s server version for the right syntax to use near 'INSERT INTO test (id, label) VALUES (99, 'x')' at line 1 in %s on line %d
181string(5) "42000"
182
183Testing with PDO::MYSQL_ATTR_MULTI_STATEMENTS set to true
184array(3) {
185  [0]=>
186  array(1) {
187    ["id"]=>
188    string(1) "1"
189  }
190  [1]=>
191  array(1) {
192    ["id"]=>
193    string(1) "2"
194  }
195  [2]=>
196  array(1) {
197    ["id"]=>
198    string(1) "3"
199  }
200}
201array(3) {
202  [0]=>
203  array(2) {
204    ["id"]=>
205    string(1) "3"
206    ["label"]=>
207    string(1) "c"
208  }
209  [1]=>
210  array(2) {
211    ["id"]=>
212    string(1) "2"
213    ["label"]=>
214    string(1) "b"
215  }
216  [2]=>
217  array(2) {
218    ["id"]=>
219    string(1) "1"
220    ["label"]=>
221    string(1) "a"
222  }
223}
224array(0) {
225}
226bool(false)
227array(3) {
228  [0]=>
229  array(1) {
230    ["id"]=>
231    string(1) "1"
232  }
233  [1]=>
234  array(1) {
235    ["id"]=>
236    string(1) "2"
237  }
238  [2]=>
239  array(1) {
240    ["id"]=>
241    string(1) "3"
242  }
243}
244array(3) {
245  [0]=>
246  array(2) {
247    ["id"]=>
248    string(1) "3"
249    ["label"]=>
250    string(1) "c"
251  }
252  [1]=>
253  array(2) {
254    ["id"]=>
255    string(1) "2"
256    ["label"]=>
257    string(1) "b"
258  }
259  [2]=>
260  array(2) {
261    ["id"]=>
262    string(1) "1"
263    ["label"]=>
264    string(1) "a"
265  }
266}
267array(0) {
268}
269bool(false)
270string(5) "00000"
271done!
272