
The Supabase Dashboard Said Healthy, but `supabase db push` Kept Timing Out — Here’s Why
The Supabase Dashboard Said Healthy, but supabase db push Kept Timing Out — Here’s Why
While working on one of my projects, I ran supabase db push to apply my local database migrations to the remote Supabase database.
Instead of completing successfully, the CLI returned an error similar to this:
Initialising login role...
Connecting to remote database...
failed to connect to postgres:
failed to connect to `host=db.<project-ref>.supabase.co user=cli_login_postgres database=postgres`:
failed to write startup message:
i/o timeout
At the same time, the Supabase dashboard showed the project status as Healthy.
So what was actually happening?
The important thing to understand is that a healthy Supabase project does not necessarily mean that every client can successfully connect to its PostgreSQL database.
What Does "Healthy" Actually Mean?
When the Supabase dashboard shows your project as healthy, it generally indicates that the services running within the Supabase infrastructure are operational.
Your local CLI connection follows a different network path:
Your Computer
↓
Your Local Network
↓
Your ISP / VPN / Firewall
↓
Internet Routing
↓
Supabase PostgreSQL
A failure anywhere along this path can prevent the CLI from connecting even though the database itself is running normally.
Look Closely at the Error
One of the most useful parts of the error message is the network address:
read tcp [2403:...]:49156 -> [2406:...]:5432: i/o timeout
Both addresses contain colons and follow the IPv6 address format.
This tells us that the connection attempt was happening over IPv6.
If your ISP or local network provides partial or unreliable IPv6 connectivity, your system may successfully resolve the database hostname to an IPv6 address but fail when attempting to establish the actual connection.
The result is an i/o timeout.
Why the Dashboard Can Still Work
Opening the Supabase dashboard and connecting directly to PostgreSQL are not the same thing.
Your browser primarily communicates with Supabase services over HTTPS, typically using port 443.
A direct PostgreSQL connection commonly uses port 5432.
Therefore, this can happen:
Supabase Dashboard → Works
Supabase API → Works
Your Application → Works
Direct PostgreSQL Connection → Fails
supabase db push → Fails
The database can be perfectly healthy while your network is unable to establish the required direct connection.
Possible Causes
Several issues can cause this behaviour.
1. IPv6 Routing Problems
Your network may advertise IPv6 support without providing a stable route to the destination.
This is particularly worth investigating when the CLI error contains IPv6 addresses.
2. Port 5432 Is Blocked
Some corporate networks, public Wi-Fi networks, firewalls or ISPs may restrict outgoing connections to database ports.
3. VPN or Proxy Interference
A VPN can change how traffic is routed and may prevent direct PostgreSQL connections.
Try temporarily disconnecting from the VPN and running the command again.
4. DNS Resolution Issues
The database hostname may resolve differently depending on your DNS provider or network.
You can inspect the resolution using:
nslookup db.<project-ref>.supabase.co
5. Temporary Network Routing Issues
Sometimes the problem exists somewhere between your ISP and the destination infrastructure.
In this situation, switching networks can immediately confirm the issue.
For example, try:
- Your regular Wi-Fi
- A mobile hotspot
- Another broadband connection
If the command works on another network, the problem is likely related to your original network rather than your Supabase project.
Test the Database Port
You can test whether your machine can reach the PostgreSQL port using:
nc -vz db.<project-ref>.supabase.co 5432
If the connection times out, it indicates that your machine cannot establish a connection to that host and port.
That significantly narrows down the problem.
What About the PostHog Warning?
You may also see something like:
posthog WARN: sending request
context deadline exceeded
This is generally related to the Supabase CLI attempting to send telemetry data.
It is usually not the main reason your database operation failed.
However, if both PostHog requests and PostgreSQL connections are timing out, it can be another indication that something is wrong with your local network connectivity.
The PostgreSQL connection error is the one you should focus on.
Direct Connection vs Connection Pooler
Supabase provides different ways to connect to PostgreSQL.
A direct database connection and a pooled connection are not necessarily routed in exactly the same way.
Depending on your environment and network support, one connection method may work while another does not.
This is especially relevant in environments where direct IPv6 connectivity is unavailable or unreliable.
Always check the connection options provided in your project's Supabase dashboard and use the connection method appropriate for your environment.
A Simple Troubleshooting Flow
When supabase db push fails while your project remains healthy, I usually recommend checking the problem in this order:
Is the Supabase project healthy?
↓
Yes
↓
Does the error show an IPv6 connection?
↓
Test using another network
↓
Test port 5432 connectivity
↓
Disable VPN or proxy temporarily
↓
Check DNS resolution
↓
Compare direct and pooled connection options
↓
Run the CLI with --debug
You can get additional information from the CLI using:
supabase db push --debug
The Key Takeaway
A green Healthy status tells you that the Supabase project is operational.
It does not guarantee that your computer has a working network path to the PostgreSQL server.
When you encounter an i/o timeout, especially when the error contains IPv6 addresses, investigate the connection between your machine and the database before assuming that Supabase itself is down.
The quickest diagnostic test is often surprisingly simple:
Try running the same command from another network.
If it suddenly works, you have already eliminated a large number of possible causes.
The next time your Supabase dashboard says everything is healthy while the CLI refuses to connect, the database may not be the problem at all.
Sometimes, the real issue is simply the route between your machine and the database.