mysql_fetch_array() expects parameter 1 to be resource (or mysqli_result), boolean given

1,00
р.
Я пытаюсь получить данные из таблицы MySQL, но вылезает одна из этих ошибок:
mysql_fetch_array() expects parameter 1 to be resource, boolean given
или
mysqli_fetch_array() expects parameter 1 to be mysqli_result, boolean given
Вот мой код:
$username = $_POST['username'] $password = $_POST['password'] $result = mysql_query("SELECT * FROM Users WHERE UserName LIKE $username")
while($row = mysql_fetch_array($result)) { echo $row['FirstName'] }
Оригинальный вопрос.

Ответ
Как избежать такой ошибки
Эта ошибка - вторичная. И в правильно спроектированном приложении возникать в принципе не должна.
Она лишь сигнализирует о том, что предыдущая функция, которая выполняла SQL запрос, окончилась неудачей, но при этом о причине неудачи никакой информации не несёт.
Чтобы таких ошибок в коде не возникало, необходимо получить сообщение об ошибке из базы данных. Но делать это надо с умом, а не так, как советуют неспециалисты, десятилетиями переписывая друг у друга один и тот же код, не понимая его смысла и не сталкиваясь с результатами его работы (весьма плачевными) на практике.
Mysqli
Чтобы транслировать ошибки базы данных в ошибки РНР, в mysqli не нужно проверять результат каждой функции. Вместо этого достаточно перед коннектом написать вот такую строчку:
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT)
и тогда все ошибки БД будут порождать исключения, которые по умолчанию становятся фатальными ошибками РНР, а значит при ошибке запроса программист будет немедленно проинформирован точно так же, как о любых других возникающих в работе скрипта ошибках. А до ошибки "expects parameter" дело уже не дойдет.
mysql_query
Внимание! Этой функции уже много лет не существует в языке. И это значит что ваш код настолько древний, что он не будет работать на большинстве хостингов. Но если все же приходится копаться в этом экскременте мамонта, то взывая функцию mysql_query(), необходимо всегда проверять результат её работы и выбрасывать ошибку РНР с реальным сообщением об ошибке от БД:
$sql = "SELECT ..." $res = mysql_query($sql) or trigger_error(mysql_error()." in ". $sql)
Как вообще увидеть сообщение об ошибке
Предыдущие рекомендации показывают, как в принципе заставить БД сообщать об ошибках. Но чтобы увидеть ошибку, надо также соответствующим образом настроить РНР
В локальном/тестовом окружении
error_reporting всегда в значении E_ALL log_errors в значении 1 (это бывает полезно) display_errors в значении to 1
На боевом сервере
error_reporting всегда в значении E_ALL log_errors установить в 1 display_errors установить в 0

Таким образом на локальном сервере ошибки будут отображаться на экране, а на боевом - писаться в лог ошибок, где их можно будет посмотреть
Что нельзя делать при обработке ошибок
Никаких echo и die(). Ошибки базы данных должны всегда транслироваться в ошибки РНР и выводиться туда, куда выводятся все остальные. Если на сайте запрещен вывод ошибок в браузер, то ошибки БД не должны быть исключением из этого правила.
Как исправить ошибку
Надо прочитать сообщение об ошибке.
Это звучит банальностью, но на удивление никто из неспециалистов раздающих советы никогда этого не упоминает! При том что прочтение текста ошибки помогает в сто раз лучше шаманских телодвижений типа "пересчитайте все кавычки":
Во-первых, mysql сразу скажет, в чем суть ошибки. Если в базе нет таблицы, к которой мы обращаемся, или сервер весь целиком упал, то пересчитывать кавычки бесполезно. Во-вторых, если ошибка все-таки в синтаксисе, то mysql точно укажет место где её искать - она процитирует кусок запроса, начинающийся сразу за ошибкой.
Как раз и навсегда избавиться от ошибок синтаксиса, вызванных данными
Если проблема всё-таки в синтаксисе, и при этом вызвана переданными в запрос данными, то Самой Дурацкой Идеей будет "экранировать ваши значения с помощью mysql_real_escape_string()". И уж тем более глупостью будет применять эту функцию для защиты от SQL инъекций. Она не для этого предназначена.
Для того, чтобы навсегда избавиться от любых проблем, связанных с передаваемыми в запрос переменными, необходимо перестать вставлять их в строку запроса напрямую. А делать это только через посредника, называемого "плейсхолдер".
Таким образом, для данного запроса код с использованием mysqli будет таким
$username = $_POST['username'] $stmt = $conn->prepare("SELECT * FROM Users WHERE UserName LIKE ?") $stmt->bind_param("s", $username) $stmt->execute() $result = $stmt->get_result() while($row = mysql_fetch_array($result)) { echo $row['FirstName'] }
Да, получилось длинновато. Поэтому (и по многим другим причинам) вмето mysqli рекомендуется использовать PDO:
$username = $_POST['username'] $stmt = $conn->prepare("SELECT * FROM Users WHERE UserName LIKE ?") $stmt->execute([$username]) while($row = $stmt->fetch()) { echo $row['FirstName'] }