phacility/phabricator · error · AphrontConnectionLostQueryException
2006
2006
Error message
#%d: %s This error may occur if your configured MySQL "wait_timeout" or "max_allowed_packet" values are too small. This may also indicate that something used the MySQL "KILL <process>" command to kill the connection running the query.
What it means
MySQL errno 2006 'MySQL server has gone away', translated by throwCommonException() into AphrontConnectionLostQueryException with appended guidance. 'Gone away' specifically means the client's connection was already dead when it tried to use it: exceeded wait_timeout, a packet larger than max_allowed_packet (either direction), the server killing the connection (KILL, OOM, restart), or a network device dropping the session.
Source
Thrown at src/infrastructure/storage/connection/mysql/AphrontBaseMySQLDatabaseConnection.php:336
$errno = $this->getErrorCode($connection);
$error = $this->getErrorDescription($connection);
}
$this->throwQueryCodeException($errno, $error);
}
private function throwCommonException($errno, $error) {
$message = pht('#%d: %s', $errno, $error);
switch ($errno) {
case 2013: // Connection Dropped
throw new AphrontConnectionLostQueryException($message);
case 2006: // Gone Away
$more = pht(
'This error may occur if your configured MySQL "wait_timeout" or '.
'"max_allowed_packet" values are too small. This may also indicate '.
'that something used the MySQL "KILL <process>" command to kill '.
'the connection running the query.');
throw new AphrontConnectionLostQueryException("{$message}\n\n{$more}");
case 1213: // Deadlock
throw new AphrontDeadlockQueryException($message);
case 1205: // Lock wait timeout exceeded
throw new AphrontLockTimeoutQueryException($message);
case 1062: // Duplicate Key
// NOTE: In some versions of MySQL we get a key name back here, but
// older versions just give us a key index ("key 2") so it's not
// portable to parse the key out of the error and attach it to the
// exception.
throw new AphrontDuplicateKeyQueryException($message);
case 1044: // Access denied to database
case 1142: // Access denied to table
case 1143: // Access denied to column
case 1227: // Access denied (e.g., no SUPER for SHOW SLAVE STATUS).
// See T13622. Try to help users figure out that this is a GRANT
// problem.
View on GitHub (pinned to 5720a38cfe)
Solutions
- Retry the operation — Phabricator's worker infrastructure retries connection-lost exceptions automatically, so single occurrences are usually self-healing
- Raise max_allowed_packet on the server (and client) if large payloads trigger it
- Raise wait_timeout (or keep connections busy) if idle daemons are being cut off
- Check mysqld logs / audit who issued KILL if the message appears during normal packet sizes
Example fix
# before (my.cnf) max_allowed_packet = 16M wait_timeout = 60 # after max_allowed_packet = 64M wait_timeout = 600 # then restart mysqld; retry the failed operation
Defensive patterns
Strategy: retry
Try / catch
try {
$rows = queryfx_all($conn, $sql);
} catch (AphrontConnectionLostQueryException $ex) {
if (preg_match('/^#2006:/', $ex->getMessage())) {
// gone away: fresh connection, then retry once
$conn = $object->establishConnection('r');
$rows = queryfx_all($conn, $sql);
} else {
throw $ex;
}
} Prevention
- Set max_allowed_packet (server and client) above your largest payload
- Set wait_timeout above your daemons' longest idle gap, or schedule periodic keepalive queries
- If a monitoring system kills long queries, exclude Phabricator's legitimate long-running reports/exports
When it happens
Trigger: A daemon holds a connection idle longer than the server's wait_timeout, then issues a query; writing a blob larger than max_allowed_packet; an operator or monitoring system running KILL on long queries; mysqld restarted or was OOM-killed.
Common situations: Phabricator daemons idle overnight between task bursts; large file/repository metadata writes exceeding the default 16MB max_allowed_packet; aggressive connectionkillers in managed MySQL.
Understand the failure class
- Timeouts: ETIMEDOUT, deadlines, and hung requests — what actually expires when a request times out.
Related errors
- #%d: %s
- Attempting to issue a write query on a read-only connection
- 1213
- 1205
- Unable to establish a connection to any database host (while
AI-assisted analysis of phacility/phabricator@5720a38cfe (2026-08-21).
Data as JSON: /api/errors/46c617acf517c69e.
Report an issue: GitHub.