Introdução: "Seu logotipo não funciona e o banco de dados está chorando"
\n\nSe você já escreveu um script PHP que trabalha com MySQL, provavelmente já se deparou com esta frase assustadora:
\nWarning: mysql_fetch_array() expects parameter 1 to be resource, boolean given.
Vamos combinar desde já: isso não é o fim do mundo. É apenas um sinal do PHP dizendo: "Ei, não consigo pegar dados disso que você me passou!".
\n\nNeste tutorial, vamos entender por que o erro mysql_fetch_array() expects parameter 1 to be resource ocorre, como corrigi-lo e, o mais importante — como nunca mais vê-lo (spoiler: migrando para PDO ou MySQLi).
Este artigo foi escrito especialmente para o pythonlib.ru — um portal educacional onde ensinamos a programar sem dor de cabeça. Vamos nessa!
\n\nPor que o PHP está gritando com o parâmetro? (causas)
\n\nPara entender a raiz do problema, vamos lembrar como funcionam as antigas funções mysql_* (sim, aquelas obsoletas desde o PHP 5.5).
Um código típico de iniciante se parece com isso:
\n// Conexão\n$link = mysql_connect('localhost', 'usuario', 'senha');\nmysql_select_db('teste');\n\n// Consulta (com erro)\n$result = mysql_query("SELECT * FROM usuarios WHERE id = '1");\n\n// Tentativa de leitura\nwhile($row = mysql_fetch_array($result)) { // Erro!\n echo $row['nome'];\n}\n\nO que há de errado aqui? Tudo! Mas o principal: mysql_query() retornou false, e não um resource. Por quê?
- \n
- Erro de sintaxe no SQL — a aspas não foi fechada. \n
- Sem conexão com o banco —
mysql_connect()retornou false. \n - Banco de dados não selecionado —
mysql_select_db()falhou. \n - Tabela não existe. \n
Quando mysql_query() falha, ele retorna false (tipo booleano), e não um resource. Você tenta passar false para mysql_fetch_array(), que espera um resource. Conflito! Daí o erro.
Quais funções são afetadas?
\n- \n
mysql_fetch_array()\n mysql_fetch_assoc()\n mysql_fetch_row()\n mysql_num_rows()\n mysql_data_seek()\n
Todas elas gritam a mesma coisa: "expects parameter 1 to be resource".
\n\nCorreção passo a passo (para código legado)
\n\nSe você tem um projeto legado e ainda não pode atualizar o PHP (embora eu recomende fortemente), veja como detectar e corrigir o erro.
\n\nPasso 1. Verifique a conexão
\n$link = mysql_connect('localhost', 'usuario', 'senha');\nif (!$link) {\n die('Erro de conexão: ' . mysql_error());\n}\n\nPasso 2. Verifique a seleção do banco
\nif (!mysql_select_db('meu_banco')) {\n die('Não foi possível selecionar o banco: ' . mysql_error());\n}\n\nPasso 3. Faça a consulta com verificação
\n$sql = "SELECT * FROM usuarios WHERE id = 1";\n$result = mysql_query($sql);\n\nif (!$result) {\n die('Erro na consulta: ' . mysql_error());\n}\n\n// Agora pode usar com segurança\nwhile($row = mysql_fetch_assoc($result)) {\n echo $row['nome'];\n}\n\nPercebeu a diferença? Verificamos cada etapa. Se mysql_query() retornar false — interrompemos com uma mensagem de erro, em vez de passar false adiante.
Por que isso ainda funciona? (contexto histórico)
\n\nNo Stack Overflow, essa pergunta já acumulou milhares de visualizações. E não é surpresa: muitos servidores ainda rodam PHP 5.x, e vários tutoriais (até no YouTube) ensinam com mysql_*.
Mas lembre-se de uma vez por todas: a extensão mysql está obsoleta e foi removida no PHP 7.0. Se você está escrevendo código novo — use mysqli ou PDO.