Aditya Sharma

WordPress Error Establishing a Database Connection: Real Fix

On this page, 10 sections

“Error establishing a database connection” means PHP could not open a connection to MySQL or MariaDB with the credentials and host in wp-config.php. WordPress prints it when mysqli_real_connect() fails. The message does not say why, so test the connection outside WordPress first.

Almost every article tells you to check four things in order. This one shows where the message comes from in core, how to get the real MySQL error out of it, and when the problem is a corrupt table and not a connection at all.

I read WordPress 7.1.3 source and vendor docs on 11 October 2026. I did not break a database to reproduce the error, and I ran nothing on a live site. The two connection failures I did run locally are marked below.

Where the message comes from

In wp-includes/class-wpdb.php, the db_connect() method calls mysqli_real_connect(). If the connection error number is set, WordPress builds the message you see. The built-in text lists three checks: the username and password, the host name, and whether the database server is running.

Then dead_db() in wp-includes/functions.php decides what to show. If a file called wp-content/db-error.php exists, WordPress loads that instead. Inside wp-admin or during install, it shows the raw $wpdb->error. On the front end you get the terse page.

This is why two sites with the same failure show different screens. A host that ships a custom db-error.php hides the default text. Check for that file before you assume the page is what WordPress would print.

There is a second thing worth knowing. A drop-in at wp-content/db.php replaces the database class entirely. Core loads it in require_wp_db() in wp-includes/load.php. Caching and database plugins use it, and a broken one produces the same page.

Get the real error

The browser page never shows the MySQL error number. Get it from the command line, with the same values that are in wp-config.php. From an SSH session on the server:

mysql -h localhost -u DB_USER -p DB_NAME -e "SELECT 1;"

If the command line is not available, this PHP file does the same job. Run it with php db-test.php over SSH, not from the browser, and delete it afterwards, because it holds the password.

<?php
// db-test.php. Run over SSH, then delete.
mysqli_report( MYSQLI_REPORT_OFF );
$c = mysqli_connect( 'localhost', 'DB_USER', 'DB_PASSWORD', 'DB_NAME' );
echo $c ? "connected\n" : 'errno ' . mysqli_connect_errno() . ': ' . mysqli_connect_error() . "\n";

The output tells you which of three problems you have: wrong credentials, a host or socket that cannot be reached, or a server that is down or full.

Host and socket problems

The PHP manual says that when possible, pipes are used instead of TCP/IP, and that TCP/IP is used if a host name and port are given together, for example localhost:3308. In practice, localhost means the Unix socket and 127.0.0.1 means TCP. They fail differently.

I ran both against a machine with no database server, using PHP 8.5.10. Both returned error 2002, with different text:

  • mysqli_connect('127.0.0.1'): errno 2002, “Connection refused”. Nothing is listening on the TCP port.
  • mysqli_connect('localhost'): errno 2002, “No such file or directory”. The socket file does not exist.

The second message is the useful one. It says the socket path is wrong or the server is not running, which is a different fix from a wrong password. In core, parse_db_host() splits a socket off the host string by looking for :/, so a host like localhost:/var/run/mysqld/mysqld.sock is valid in DB_HOST.

Server down or out of connections

If the command line connects and WordPress does not, compare the values. If neither connects, the server may be stopped or full. The MariaDB documentation lists max_connections with a default of 151 and a range of 10 to 100,000.

It can be changed at runtime. The same page says MariaDB keeps one extra connection for an administrator, so you can usually still log in when users are locked out.

My reading, not something I measured: each PHP request that reaches WordPress opens its own connection through db_connect(). A traffic spike, or a slow query that keeps requests open, can use up the pool.

The page then fails for visitors while the database is healthy. That is a capacity problem, and a restart only hides it. Finding the slow query in WordPress covers locating what holds connections open.

Raising max_connections is a server setting, not a WordPress one. It also raises memory use, so treat it as a stopgap while you find the cause.

When the connection is fine and a table is broken

Sometimes the message appears only in wp-admin, or only after a crash. WordPress has a repair screen for that, and it is off by default. In wp-admin/maint/repair.php the script refuses to run unless WP_ALLOW_REPAIR is defined.

It runs CHECK TABLE on each table and REPAIR TABLE only on tables that fail the check, and OPTIMIZE TABLE if you choose the second button.

define( 'WP_ALLOW_REPAIR', true );

Add that line to wp-config.php and open /wp-admin/maint/repair.php on your site. The developer documentation notes that the page needs no login, so anyone who finds the URL can run it. Remove the line as soon as you are done. The script itself reminds you to do that.

Take a backup before you repair anything. What a WordPress backup must contain lists what to include so you can roll back.

The wp-config values to check

The four constants are DB_NAME, DB_USER, DB_PASSWORD and DB_HOST. A trailing space in the password, a changed database user after a migration, and a host of localhost on a server that uses a remote database are the usual mismatches.

wp-config constants that change behaviour covers the others that matter. After changing a value, test again with the command line before you reload the site, so you know which side was wrong.

How this was checked

I read class-wpdb.php, functions.php, load.php and wp-admin/maint/repair.php from the WordPress 7.1.3 tag on GitHub on 11 October 2026, plus the wp-config documentation, the PHP mysqli manual and the MariaDB server variables page.

I ran the two connection failures above locally and ran php -l on the PHP snippet. I did not reproduce a corrupt table or a full connection pool. I could not verify specific MySQL error numbers such as 1045 or 1040, because the error reference pages I tried either failed to load or returned 403, so I do not quote them.

Questions people ask

Why does the error appear only sometimes?

Intermittent failures point to a full connection pool or a database server that restarts. A wrong password fails every time.

Is it safe to leave WP_ALLOW_REPAIR on?

No. The documentation says the repair page needs no login. Enable it only while you use it.

Does the message mean my data is gone?

Not by itself. The message means the connection failed. The data is usually still in the database.

Do this today

Run the mysql command above with the values from your wp-config.php. The error it prints is the real one, and it tells you which section of this post to follow.

Resources

Tell me where I am wrong

Your email is not published and I do not add it to any list. Corrections with a source are the ones I act on fastest.