Share to Friends News Home News Categories Switch Channel

Destoon + MariaDB 10.x: Why Your Chinese Text Turns to ???? (and the one-line fix)

2026-08-22 22:521090Vector Digital Works

MySQL / MariaDB terminal: SET NAMES utf8 to fix Chinese mojibake

TL;DR — Destoon's database driver compares the MySQL server version as a string instead of a version number. On MariaDB 10.x, "10.6.27-MariaDB" > "4.1" evaluates to false, so SET NAMES 'utf8' is silently skipped, the connection stays on latin1, and every Chinese character collapses into a single ?. The fix is a one-liner: use version_compare().

The symptom

After migrating a Destoon site to a server running MariaDB 10.x (the default database for DirectAdmin, cPanel, 宝塔/BT, and most LNMP stacks), the entire site's Chinese text turned into ????:

Meanwhile the same site on MySQL 5.7 was completely fine. No template changes, no PHP-version issue, no data corruption.

The debugging path (the part that matters)

We first ruled out the usual suspects, because none of them were the cause:

  1. Data intact — a HEX() dump showed the bytes were correct in storage.
  2. Templates fine — the compiled template cache was logically correct.
  3. Connection layer — a minimal probe that replicated Destoon's exact connection path printed conn_charset_now=latin1 and SET NAMES SKIPPED. That was the smoking gun.

The root cause

In module/destoon/db_mysqli.class.php, Destoon decides whether to set the connection charset by comparing the server version as a string:

$version = mysqli_get_server_info($this->connid);
if($version > '4.1' && $this->cfg['db_charset']) {
    mysqli_query($this->connid, "SET NAMES '".$this->cfg['db_charset']."'");
}
if($version > '5.0') {
    mysqli_query($this->connid, "SET SQL_MODE=''");
}

PHP string comparison is lexicographic (character by character, by ASCII value):

That single false on every MariaDB 10.x box is why a "works in dev, breaks in production" mystery happens: your dev box is MySQL 5.x, your production box is MariaDB 10.x.

The fix

Replace string comparison with numeric version comparison:

$version = mysqli_get_server_info($this->connid);
if(version_compare($version, '4.1', '>') && $this->cfg['db_charset']) {
    mysqli_query($this->connid, "SET NAMES '".$this->cfg['db_charset']."'");
}
if(version_compare($version, '5.0', '>')) {
    mysqli_query($this->connid, "SET SQL_MODE=''");
}

version_compare('10.6.27-MariaDB', '4.1', '>') correctly parses 10.6 and returns true.

The result

Why this matters to you

MariaDB 10.x is the default on nearly every shared/VPS control panel. If you run Destoon on MariaDB — or are about to migrate to a host that ships it — you will hit this, regardless of PHP version. Check your db_mysqli.class.php now.

Like 0
Report
Favorite 0
Reward 0
Share 14
Belanjawan 2027: Malaysia Perkukuh Kedudukan Sebagai Hab Pelaburan Berimpak Tinggi, Memacu Syarikat
KUALA LUMPUR, 12 OKTOBER 2026 – Lembaga Pembangunan Pelaburan Malaysia (MIDA) menyambut baik pembentangan Belanjawan 2027 yang bakal mempercepatkan tr

0 comments2026-10-1224

MIDA Anjur Seminar Pelaburan Wilayah Pantai Timur 2026, Perkasa PKS dan Syarikat Tempatan
Akses Terus Kepada Lebih 15 Agensi Kerajaan, Forum Pelaburan Bernilai Tinggi Dan Jaringan Bersama 300 Peserta Industri Dalam Satu Hari, Di Satu Lokasi

0 comments2026-09-0258