Host Talk / Why your site slows down at 3 p.m.

Why your site slows down at 3 p.m.

HOST TALK

9 min read · 2,080 words

A common support ticket reads something like: the site is fast in the morning and crawls in the afternoon, nothing has changed, what is going on? There are only a few usual suspects, and the pattern of when it happens is the best clue. A slowdown at the same time every day points at something scheduled. A slowdown that follows traffic points at limits or caching. A slowdown that comes and goes with no rhythm at all often points outside your server.

The trap is to start fixing before you have looked. Upgrading to a bigger plan feels like action, and sometimes it helps, but if the cause is a backup plugin that reads the whole database at 3 p.m., a larger plan just gives the backup more room to be slow in. This article works through the five usual causes in the order that is cheapest to check, with the evidence each one leaves behind.

Throughout, the goal is the same: match the slow period to a log line, a graph or a timestamp, so that the fix is based on what happened rather than a guess.

Start with the shape of the problem

Before opening any panel, write down four facts. What time does it start, and what time does it end? Is it every day, or only weekdays? Is every page slow or only some (the checkout, the search, the admin area)? And is it slow for everyone, or only for people in one place? Those four answers rule out half the possibilities.

A cheap way to get numbers is to time the same page repeatedly with curl, once an hour for a day, from your own machine:

curl -o /dev/null -s -w "%{time_starttransfer} %{time_total}\n" https://example.com/

The first figure is the time until the first byte arrived, which is the server thinking. The second is the total. If the first figure balloons during the slow period, the server is the problem. If the first figure stays small and the total grows, the page is heavy or a third-party resource is slow to load. The page weight tool helps with the second case.

09:00 10:00 11:00 12:00 13:00 14:00 15:00 16:00 17:00 18:00 1.6 s Illustrative time to first byte, by hour of the day
What a daily pattern looks like when you plot it: flat, a climb, a spike, and a recovery.

Scheduled tasks

WordPress uses its own pseudo-scheduler, WP-Cron, which runs when visitors arrive rather than at a fixed time on a clock. Backup plugins, security scans, newsletter sends and search-index rebuilds often run through it. If a heavy job starts at 3 p.m. every day, so does your slowdown.

The visitor-triggered design has two drawbacks. A job can only start when someone loads a page, so on a quiet site it runs late, and on a busy site several visitors can trigger checks at the same moment. Moving heavy jobs to quiet hours, and running them with real server cron instead of visitor-triggered cron, usually helps. The change takes two steps: turn off the built-in trigger in wp-config.php, then call the script from the system scheduler.

define( 'DISABLE_WP_CRON', true );

*/5 * * * * curl -s https://example.com/wp-cron.php?doing_wp_cron > /dev/null 2>&1

The second line goes in the crontab (or the panel's cron page). The cron helper will build the schedule expression if you are not fluent in it. Then look inside the backup or scan plugin and move its start time to the small hours.

Bots

A surprising share of traffic is not human. Search engines, AI crawlers, uptime monitors, vulnerability scanners and scraping tools all request pages, sometimes thousands an hour. A crawler that follows every filter combination in a shop can generate hundreds of thousands of distinct URLs, each of which needs PHP and the database to answer.

Your access log will show which user agents and addresses are responsible. On a server you can count requests per address in a given hour:

grep "05/Oct/2026:15" access.log | awk '{print $1}' | sort | uniq -c | sort -rn | head

If a few addresses account for most of the lines, you have found the load. A firewall rule or a rate limit often removes most of it at no cost to real visitors. For well-behaved crawlers, a robots.txt rule or crawl-delay is a polite first step; for scanners, which ignore it, blocking is the only language they understand. See firewalls and WAFs in this series for how that works.

Resource limits

On shared hosting, your account has caps on CPU, memory and simultaneous processes. Providers describe them differently, but the effect is the same: when you reach the cap, requests queue or fail, often with a 503 or a "resource limit reached" page. The panel often shows a usage graph; if it flattens at a ceiling during the slow period, you have found the limit.

account limit flat top = throttled requests queue here Illustrative CPU use through the day
A flat top on a usage graph is the signature of a limit being hit rather than of a busy site.

Caching reduces how often PHP has to run and is usually the cheapest fix. A page cache turns a request that needs twenty database queries into a file read. If the graph still sits on the ceiling after caching is working, then a larger plan is a reasonable decision, and you will know why you are buying it.

What differs by hosting type

TypeLimits look likeWhere to look
SharedPer-account caps on CPU, memory, processes, I/OPanel usage graphs, 503 responses
VPSFixed CPU cores and RAM; swapping when memory runs outtop, free -m, provider graphs
DedicatedHardware limits only; bottlenecks are usually your own configurationSame tools, plus disk and database metrics
Managed WordPressCaps on visits, PHP workers and storageDashboard analytics, worker count

The database

Large tables without suitable indexes, a plugin that saves too much to the options table, or a huge number of expired transient records can make queries crawl. A slow query log, or a profiling plugin on a staging copy, will show the culprit quickly. Typical findings: one query that scans a table of a million rows for every page view, or an options table with tens of megabytes of autoloaded data that is read on every request.

On a server you control, switch on the slow query log for a day and look at the top entries:

SET GLOBAL slow_query_log = 1;
SET GLOBAL long_query_time = 1;

Queries over one second are almost always worth a look. Cleaning expired transients and deleting plugin data you no longer use are safe first steps, after a backup.

Something external

Sometimes the slow thing is not your server at all. An embedded video, a tracking script, a font service or a chat widget may be slow to respond, and the page waits. The waterfall in your browser's developer tools (Network tab, reload with the cache disabled) shows it plainly: one long bar from another domain, with everything after it held up.

That slowness often varies by time of day too, because the outside service has its own busy period. If time to first byte from curl stays low while the page feels slow in the browser, suspect this. Load such scripts later, or remove the ones that earn nothing.

Caching in practice

Since caching is the cheapest fix, it is worth knowing what it actually does. A WordPress page is assembled on request: PHP loads the theme and plugins, runs a series of database queries, and builds the HTML. A page cache saves the finished HTML and serves that file to the next visitor, skipping PHP and the database altogether. For a news article read by ten thousand people, the page is built once instead of ten thousand times.

Three things stop it working. Pages that differ per visitor (a basket, an account page) cannot be shared, so good cache rules exclude them. Query strings that vary, such as tracking parameters added by email campaigns, can make every visit look like a new URL unless the cache is told to ignore them. And a cache that is emptied too often, for instance by a plugin that clears everything whenever a comment arrives, protects very little. Check for a response header showing a hit or a miss:

curl -sI https://example.com/ | grep -i -E "cache|age"

Repeat the request twice. If the second answer is not faster, or the header never says hit, the cache is not doing its job.

What to do while you investigate

If the slow period is costing you customers today, there are holding measures that do not need a diagnosis. Pause the backup or scan plugin for a day and see whether the pattern moves. Turn on the host's built-in cache if it has one. Block an obviously abusive address you found in the log. Each of these is reversible, and each gives you information: if pausing the backup makes the slow period disappear, you have your answer without touching anything permanent.

Avoid changing several things at once. If you pause a plugin, add a cache and raise the memory limit in one go and the site speeds up, you will not know which change did it, and the problem will return the next time one of them is undone. Keep a short list of what you changed and when.

Do not run heavy diagnostics, such as a full site scan or a profiler, on a live site during the slow window. They add to the load you are trying to understand.

Reading the access log for the slow hour

The access log is a diary of every request. For a slowdown, three questions matter: how many requests arrived, who sent them, and what did they ask for? Compare the slow hour with a quiet one. If the slow hour has ten times the requests, you have a traffic problem, whether human or not. If the count is similar but the slow hour has far more requests to one URL such as /wp-admin/admin-ajax.php or a search page, a single feature is the culprit. If the counts are equal and nothing stands out, the load is probably on the server side: a scheduled job, the database, or a neighbour.

grep "05/Oct/2026:15" access.log | awk '{print $7}' | sort | uniq -c | sort -rn | head

That prints the most requested paths for the 15:00 hour. A path appearing thousands of times that you do not recognise deserves a look before anything else.

A worked example

A village theatre's ticket site is quick until mid-afternoon, then pages take eight seconds. Curl shows the first byte arriving after seven seconds at 15:10 and after 0.4 seconds at 11:00. That is the server. The access log shows nothing unusual in volume. The WordPress cron list shows a backup job scheduled for 15:00, and the panel graph shows CPU on the account's ceiling from 15:00 to 15:40.

Moving the backup to 03:00 removes the slowdown. Total cost: five minutes and no change of plan. The same symptom could equally have been a crawler or a database problem, and the process would have been the same.

Checking it yourself

  1. Record when the slowness starts and ends, for several days.
  2. Time the first byte with curl at intervals, from outside.
  3. Open the panel's usage graph for those hours.
  4. Count requests per address in the access log for the same hour.
  5. List scheduled tasks and compare their times with the slow window.
  6. Check the browser waterfall for slow third-party requests.

The method is the same in each case: find the pattern in time, find the matching log or graph, and change one thing at a time. Guessing and upgrading to a larger plan is expensive and often does nothing. The troubleshooting guide and the uptime calculator are useful companions.

Quick answers

Is it my host's fault?

Occasionally, when a neighbour on a crowded server uses too much. The test is if your own graphs and logs show a cause. If they show nothing and the slowness remains, send support your timings.

Will a CDN fix it?

For static files and cached pages, yes. For logged-in or checkout pages that must be built fresh each time, much less.

How much PHP memory should I allow?

Enough for the heaviest legitimate page, which for many WordPress sites is 256 MB. If you need far more, find out what is eating it.

Why does it only happen on weekdays?

Often because a business process runs then: an import, a newsletter, a stock update. Check what your team schedules, as well as what the software does.

PreviousWhat a control panel actually doesNextIP addresses, and why there are two kinds

More from Host Talk

Host Talk

When a CDN helps, and when it gets in the way

A content delivery network sits between your visitors and your server. It keeps copies of your files in many...

Host Talk

How automatic certificate renewal works

Automatic renewal sounds like magic, but the mechanism is simple: a program proves to a certificate authority...

Host Talk

Backups: full, incremental, snapshots and the 3-2-1 rule

A backup is a copy you can restore from. Everything else is detail, but the details decide whether the copy...