Usa charset utf8mb4 y collation utf8mb4_unicode_ci en MySQL y cámbialos mediante phpMyAdmin o comandos ALTER, recuerda también SET NAMES para la conexión.
Charset (conjunto de caracteres) determina qué caracteres puede almacenar la base de datos, y collation determina cómo se comparan y ordenan los caracteres. Un charset incorrecto es la causa más frecuente de que las letras danesas (æ, ø, å) o los emojis se muestren como signos de interrogación o mojibake (p. ej. æ en lugar de æ).
Utiliza utf8mb4 como charset y utf8mb4_unicode_ci como collation. utf8mb4 admite todos los caracteres Unicode, incluidos los emojis.
Cambiar el valor predeterminado para toda la base de datos (solo afecta a tablas nuevas):
utf8mb4_unicode_ci en el menú desplegable.Cambiar una tabla existente (incluyendo todas sus columnas):
Cambiar el valor predeterminado de la base de datos:
ALTER DATABASE mindatabase CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
Cambiar una tabla y todas sus columnas:
ALTER TABLE mintabel CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
En phpMyAdmin puedes cambiar el charset por columna: selecciona la tabla, haz clic en Estructura, haz clic en Cambiar junto a la columna, y elige la nueva ordenación en la definición de la columna.
Generar los comandos ALTER automáticamente:
SELECT CONCAT('ALTER TABLE `', TABLE_NAME, '` CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;')
FROM information_schema.TABLES
WHERE TABLE_SCHEMA = 'mindatabase' AND TABLE_TYPE = 'BASE TABLE';
Ejecuta el resultado en phpMyAdmin bajo la pestaña SQL o mediante la línea de comandos.
El charset de la base de datos y el charset de la conexión son dos cosas diferentes. Incluso si tus tablas están correctamente configuradas a utf8mb4, los caracteres pueden corromperse en tránsito si la conexión entre la aplicación y MySQL utiliza otro charset.
SET NAMES utf8mb4 establece tres variables de sesión a la vez:
character_set_client — lo que el servidor espera recibir del clientecharacter_set_connection — lo que el servidor usa internamente durante el procesamiento de consultascharacter_set_results — lo que el servidor envía de vuelta al clienteSET NAMES utf8mb4 COLLATE utf8mb4_unicode_ci;
Mejor práctica: usa la opción de charset incorporada del controlador en lugar de enviar SET NAMES manualmente. Esto asegura que también funciones como mysqli_real_escape_string() y PDO::quote() utilicen el charset correcto — de lo contrario, en raras ocasiones podrías abrir la puerta a una inyección SQL.
Artículo de la categoría de soporte: MySQL