Skip to content

Don't let a custom $config->dbInitCommand silently drop the connection charset #594

Description

@outflux3

Short description

$config->dbCharset is applied to the DB connection only via the default
$config->dbInitCommand (SET NAMES '{charset}'). Overriding dbInitCommand
— e.g. the common SET time_zone = '...' recipe — silently drops the charset,
so the connection falls back to the MySQL server default with no warning. On a
latin1-default server this silently double-encodes all edited content (UTF-8
stored through a latin1 connection), typically discovered days later.

Reproduce

  1. Set $config->dbInitCommand = "SET time_zone = '-04:00'"; (no SET NAMES).
  2. On a server whose default charset is latin1, edit any page with accented
    text / smart quotes.
  3. Content is now double-encoded at rest; no notice anywhere.

Root cause (WireDatabasePDO::getInstance)

  • charset is only injected into MYSQL_ATTR_INIT_COMMAND; the DSN
    (socket/name/host/port) carries no charset= parameter.
  • So dbCharset depends entirely on dbInitCommand containing SET NAMES.

Proposed

  1. Prevent: also set the charset in the PDO DSN (;charset={$charset}), or
    apply SET NAMES independently of the user-overridable dbInitCommand, so
    the charset survives an override.
  2. Warn (defense in depth): after connect, if the session
    character_set_connection doesn't match $config->dbCharset, add a
    superuser admin notice — mirroring the existing DB-time-vs-PHP-time warning.
    (Cheap: one @@character_set_connection read, gated to admin/superuser.)

Why it matters

dbInitCommand is a documented, commonly-overridden setting, and the failure
is silent, data-corrupting, and hard to diagnose after the fact.

Note:
I built a small diagnostics module that confirms the mismatch is reliably detectable at runtime; Likely to be released soon, it can detect these types of issues and repair double and triple encoded and do a lot more; but i think during the development of the module came to the conclusion that it would be nice for the core to be protected from someone inadvertently overriding the connection charset - something that i've seen in the forums and is risky for certain hosting environments (as happened to 2 sites i worked on).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions