Я работаю над обучением использованию подготовленных операторов с mysqli в PHP и, как правило, если у меня возникла проблема с запросом, я просто повторяю его на экране, чтобы увидеть, как он выглядит как первый шаг.
Как я могу сделать это с помощью подготовленного заявления?
Я бы хотел увидеть инструкцию SQL после замены переменных.
Используя подготовленные заявления:
Не существует «построения» SQL-запроса на стороне PHP, поэтому нет способа получить этот запрос.
Это означает, что если вы хотите увидеть SQL-запрос, вы должны использовать SQL-запросы, а не подготовленные операторы.
Для подготовленных операторов, выполняемых с помощью функций API mysql_stmt_prepare () и mysql_stmt_execute () C, сервер записывает строки Prepare и Execute в общий журнал запросов, чтобы вы могли сказать, когда инструкции подготовлены и выполнены.
[…] сервер записывает следующие строки в общий журнал запросов:
Подготовьте [1] SELECT?
Выполнить [1] ВЫБОР 3
Поэтому для целей отладки активируйте общий журнал и следите за этим файлом.
edit: oh, у вопроса есть тег [mysqli] … полностью игнорируется.
Если оператор не выполняется вообще, у вас (двойной / триплексный) проверено, что на этом пути не было ошибок?
echo "<pre>Debug: start</pre>\n"; $mysqli = new mysqli('localhost', 'localonly', 'localonly', 'test'); if ($mysqli->connect_error) { die('Connect Error (' . $mysqli->connect_errno . ') ' . $mysqli->connect_error); } $result = $mysqli->query('CREATE TEMPORARY TABLE foo (id int auto_increment, x int, primary key(id))'); if ( false=== $result) { die('error : '. $mysqli->error); } $stmt = $mysqli->prepare('INSERT INTO foo (x) VALUES (?)'); if ( false===$stmt ) { die ('prepare() failed: ' . $mysqli->error); } $result = $stmt->bind_param('i', $x); if ( false===$result ) { die('bind_param() failed'); } $x = 1; $result = $stmt->execute(); if ( false===$result ) { die('execute() failed: '.$stmt->error); } echo "<pre>Debug: end</pre>\n";
Я обычно делаю это, когда мне нужно отлаживать подготовленный sql с параметрами.
Пример подготовки и выполнения:
$sql = "SELECT VAL1, VAL2 FROM TABLE(?, '?', '?', '?', '?', ?, '?', '?', '?')"; $prep = ibase_prepare( $sql ) or die("Error"); $query = ibase_execute($prep, $param1, $param2, .....) or $err = true; ^^^^^^^^^^^^^^^^^^^^^^^
Легкий способ отладки полученного SQL предложения:
printf( str_replace('?', '%s', $sql), $param1, $param2, ....); ^^^^^^^^^^^^^^^^^^^^^^
Вам нужно только сделать один printf с заменой? на подготовленном SQL одним% s printf будет интерпретироваться как строка и скопировать все параметры, переданные команде execute, в команду завершения sprintf.
Соглашаясь с Pascal MARTIN (+1), я предлагаю другой метод для отладки: var_dump()
или регистрировать каждую переменную, которую вы вставляете в оператор, таким образом вы должны быть в состоянии выяснить, являются ли они неправильными данными или логически неправильным SQL.
Недавно я обновил этот проект, включив интеграцию композитора, модульное тестирование и улучшив обработку принимаемых аргументов по ссылке (для этого требуется обновление до php 5.6).
Я создал набор классов, которые расширяют классы mysqli
по умолчанию и mysqli_stmt
чтобы вы могли просматривать представление потенциальной строки запроса, которая должна обеспечивать то, что вы ищете:
https://github.com/noahheck/E_mysqli
Это замена (близкая к) замены для обычного объекта mysqli
который возвращает пользовательский объект mysqli_stmt
при prepare()
строки запроса. После привязки ваших параметров E_mysqli
позволит вам просмотреть результирующую строку запроса как новое свойство объекта stmt
:
$mysqli = new E_mysqli($dbHost, $dbUser, $dbPass, $dbName); $query = "INSERT INTO registration SET name = ?, email = ?"; $stmt = $mysqli->prepare($query); $stmt->bind_param("ss", $_POST['name'], $_POST['email']); $stmt->execute(); echo $stmt->fullQuery;
приведет к:
INSERT INTO registration SET name = 'John Doe', email = 'john.doe@example.com'
Есть несколько предостережений с использованием этого расширения (объяснено в README в проекте github), но для устранения неполадок проблемных областей вашего приложения или перехода к объектно-ориентированному стилю из процедурного, это должно обеспечить уровень помощи для большинства пользователей.
Как я изложил в проекте github, у меня нет практического опыта использования расширения mysqli
, и этот проект был создан по просьбе пользователей его дочернего проекта, поэтому любые отзывы, которые могут быть предоставлены разработчикам, используя это в производство было бы весьма признательным.
Отказ от ответственности. Как я уже сказал, я сделал это расширение.
Вы можете использовать инструмент Lottip . Идея действует как прокси-сервер MySQL. Он анализирует пакеты MySQL, извлекает запрос и его параметры, чтобы вы могли видеть подготовленные заявления с его содержимым.