Why Your WooCommerce Sale Started at the Wrong Time (and How to Fix It)
WooCommerce Tips · Scheduling & Timezones
Your Sale Went Live at the Wrong Time
Why WooCommerce timezone confusion makes scheduled sales fire hours early or late — and the exact steps to make sure your next campaign starts when you actually intend it to.
You set the Black Friday sale to start at midnight. You woke up to check and it had been running since 7pm the night before. Or it hadn’t started yet and it was already 5am. You check your settings, everything looks right — and yet something clearly went wrong.
This is one of the most common scheduling frustrations with WooCommerce, and it almost always comes down to the same thing: the time you entered and the time the server used are not the same. Not because anything is broken. Because there are three different time references involved, and they don’t automatically agree with each other.
The real cause: three different time references in your store
When you type “midnight” into a WooCommerce sale start time, you are working with your local time — the time on your phone, in your city, your sense of when midnight is. But the server your site runs on lives somewhere else. And WordPress, by default, tries to mediate between the two.
Here are the three time references at play:
- Your local time — the time you are thinking in when you set up a sale. Eastern, Pacific, AEST, whatever your day operates on.
- Your WordPress site timezone — what you have configured in Settings → General → Timezone. This is what WordPress treats as “the store’s time.”
- UTC (the server’s baseline) — servers store timestamps in UTC (Coordinated Universal Time) internally. UTC is also how scheduled tasks are queued and compared.
The failure mode looks like this: your server is in a UTC data center. Your WordPress timezone is set to UTC (or was never changed from the default). You type “midnight” into the scheduler. Midnight in your timezone is 5am UTC — so the server reads “midnight” as 5am your time, or runs it at midnight UTC which is 7pm your time. The numbers are right, the timezone is wrong, and the sale fires at the wrong moment.
A wrong timezone setting is also a wrong campaign schedule
If you have several scheduled campaigns — a weekend sale, a seasonal event, a recurring flash deal — and your WordPress timezone is incorrect, every single one of them is miscalculated. One setting, cascading into every campaign you have ever created.
How WordPress timezone settings actually work
Go to Settings → General in your WordPress admin. The Timezone field is the single source of truth WordPress uses when it needs to convert between UTC and “local time.” It affects scheduled posts, cron events, and anything that schedules something for a future real-world moment.
WordPress gives you two ways to set this:
- Named timezone (e.g. “America/New_York”, “Australia/Sydney”) — this is the correct approach. Named timezones understand Daylight Saving Time transitions automatically. “America/New_York” is UTC-5 in winter and UTC-4 in summer, and WordPress will apply the correct offset at the correct time.
- UTC offset (e.g. “UTC+5”) — a fixed offset. This does not adjust for DST. If you are in a region that observes Daylight Saving Time and you use a fixed UTC offset, your scheduled events will be off by one hour for half the year.
Most hosting setups default to UTC or UTC+0 unless you change it during install. If you have never explicitly set your WordPress timezone and your store is in a non-UTC timezone, this is the first place to look.
Use a named timezone, not a UTC offset
Go to Settings → General and pick your city from the named timezone list (e.g. “America/Chicago”, “Europe/London”, “Asia/Tokyo”) rather than a fixed UTC offset. Named timezones handle Daylight Saving Time automatically, so your midnight sale stays at midnight even when the clocks shift.
Once you save the correct timezone, WordPress will use it for all time-based calculations going forward. Existing scheduled tasks that were queued with the wrong offset, though, may still fire at the wrong time — they were queued in UTC and that timestamp does not change. Re-save those campaigns to recalculate the UTC trigger time from your corrected site timezone.
How Smart Cycle Discounts handles timezone scheduling
This is worth understanding in some detail, because it directly affects what you see in the scheduler and how your input is stored.
When you enter a start date and time in the Smart Cycle Discounts campaign wizard, the plugin reads your WordPress site timezone (via wp_timezone_string()) and uses it to interpret your input. The date and time you enter are treated as local time in your site timezone — not UTC. The plugin then converts that local time to UTC internally, which is what gets stored in the database and used to queue the ActionScheduler event that fires campaign activation.
The conversion step, confirmed in the plugin’s compiler code, works like this: if you type “December 1 at 12:00am” and your WordPress timezone is “America/Chicago” (UTC-6), the plugin converts that to 2025-12-01 06:00:00 UTC and schedules the activation hook at that UTC timestamp. The campaign goes live at the moment that corresponds to midnight in Chicago — not midnight UTC.
This also means the timezone label stored with the campaign is the timezone in effect at the time you saved it. If you later change your WordPress timezone setting and re-save the campaign, the plugin will recalculate the UTC timestamps using the new timezone and update the schedule accordingly.
How the timezone check works at runtime
What happens for recurring continuous campaigns
For recurring campaigns running in continuous mode (a daily window that repeats on schedule), SCD checks whether the current time falls within the defined daily window every time a product price is requested. It does this by reading the campaign’s stored timezone, converting the current moment to that timezone, and comparing the hour:minute against the campaign’s start and end time. So “10pm to 2am” means 10pm to 2am in your site timezone — not UTC.
If your sale is firing at the wrong local time and you have confirmed your WordPress timezone is correct, the most likely explanation is that the campaign was saved before you fixed the timezone. Re-open the campaign, adjust nothing, and save it again. This forces a recalculation and re-queues the activation event with the correct UTC timestamp.
For a broader look at all the reasons a WooCommerce scheduled sale can fail to go live — including WP-Cron reliability, caching, and variable product issues — the guide on every reason a WooCommerce scheduled sale doesn’t start walks through each cause with a specific fix.
How to enter start and end times correctly in SCD
The campaign wizard’s Schedule step asks for a start date, start time, end date, and end time. All of these should be entered in your local time — the time your customers will experience. If you want a Black Friday sale to begin the moment the clock strikes midnight on the US East Coast, and your WordPress timezone is set to “America/New_York,” you enter November 28 at 12:00am. The plugin handles the UTC conversion.
A few specifics worth knowing:
- Start time defaults to 00:00 if you do not enter one. So a campaign with only a start date and no start time will activate at midnight in your site timezone.
- End time defaults to 23:59 if you enter an end date but leave the time blank. So “ends December 1” means the campaign expires at 11:59pm on December 1 in your site timezone.
- For recurring campaigns, the start and end time you enter define the daily active window. If your recurring sale runs 10am to 6pm, enter exactly those times — the plugin will activate and deactivate the discount within that window every day the recurrence is scheduled to run.
-
Confirm your WordPress site timezone first
Go to Settings → General → Timezone. Set it to a named timezone matching your store’s operating location. Save changes. This takes 30 seconds and is the foundation every campaign schedule is built on.
-
Enter campaign dates and times in your local time
In the SCD campaign wizard, Step 4 (Schedule), enter the start and end times as you experience them. If you want the sale to go live at midnight for your customers, type 12:00 AM. The plugin converts to UTC automatically.
-
Check the Campaign Health score before launching
Campaign Health will flag scheduling issues before you go live. If there is a timing conflict, an overlapping campaign, or a schedule that looks unusual, it surfaces that on the review step. It is a useful sanity check especially before high-stakes events.
Overnight time windows that cross midnight
This one catches people off guard. Suppose you want a recurring flash sale that runs from 11pm to 1am every Friday night — two hours that straddle midnight. You might worry: how does the plugin know that 12:30am belongs to the “11pm Friday” window and not a separate Saturday window?
The answer, confirmed in the plugin code: the plugin detects overnight windows and handles them correctly. When it compares the start and end time and the end time is earlier than the start time — for example, start 22:00 and end 02:00 — it recognizes this as an overnight window. Instead of checking whether the current time falls between start and end (which would always be false for an end time earlier than start), it checks whether the current time is either after the start or before the end. That means 23:30, 00:15, and 01:45 all correctly resolve to “within the window.”
What overnight window detection actually checks
The logic in is_within_time_window(): if end_time < start_time, the window is overnight. Active when: current_time ≥ start_time or current_time ≤ end_time. If end_time ≥ start_time, it is a normal daytime window: active when current_time is between start and end. All comparisons are made in the campaign’s stored timezone, not UTC.
One practical implication: if you set a recurring campaign with an overnight window, the campaign will be active during the cross-midnight portion on both the day it starts and the early hours of the following day. A “10pm to 2am Friday” window will show the sale price at 1am on Saturday — which is exactly what you want from a shopper’s perspective, but is worth confirming in your own testing before a high-traffic launch.
If you are planning to use recurring campaigns — including overnight windows — the guide on how recurring WooCommerce discount campaigns work in SCD covers the continuous vs. instances modes in detail, including how the daily window interacts with the recurrence pattern.
How to sanity-check before a big launch
Big sales — Black Friday, a product launch event, a timed clearance window — have a higher cost if something goes wrong. A midnight start at the wrong time means half your customers see full price when they expected a deal, or the sale is technically still running when you told your email list it had ended. That is worth preventing with a five-minute check before you go live.
The basic pre-launch checklist
- Go to Settings → General and confirm your timezone is correct and is a named timezone (not a UTC offset), especially if your region observes Daylight Saving Time.
- Open the campaign in SCD and check the start and end dates and times listed. Compare them against the actual local time you intend the sale to go live.
- Check Campaign Health on the review step. If it flags a scheduling concern — conflicts, timing issues, wrong status — investigate before publishing.
- If this is a repeat sale (you ran it last year or last month), confirm the new campaign was saved after your current WordPress timezone setting. Do not rely on a duplicated campaign that may have been created under a different timezone.
- For a midnight launch: consider scheduling for 12:05am instead of 12:00am. This avoids edge cases where DST transitions or server time drift could push the event just past midnight before it queues.
Testing a scheduled campaign before the real event
The most reliable way to test a scheduled campaign is to set it for a few minutes in the future on a staging or development copy of your store, let it activate naturally, and verify the product prices update correctly at the expected local time. This confirms not just that the campaign has a valid schedule, but that caching and price filters are working together the way you expect.
If you have ever hit a situation where the prices did not update even after the campaign activated — usually a caching issue — the deeper troubleshooting guide on WooCommerce scheduled sales not starting covers cache clearing and other activation-time issues.
The 11-hour Black Friday delay
A store owner sets a Black Friday sale for midnight. The WordPress timezone is set to UTC. The store is based in New York (UTC-5). At midnight UTC — which is 7pm New York time the previous evening — the sale fires. Customers who visit at 7pm see discounted prices before they were supposed to. The email that was scheduled to go out at midnight local time goes out at 5am UTC (midnight New York). By the time the midnight email lands, the “exclusive early access” has been live for five hours. The framing is ruined and the urgency is gone. The fix is one setting: change the WordPress timezone to “America/New_York.”
Frequently asked questions
My WordPress timezone is already correct but the sale still fired at the wrong time. What else should I check?
If the campaign was created or last saved while your timezone was set incorrectly, the UTC timestamp stored in the database reflects the old (wrong) timezone. Re-open the campaign, make no changes, and save it again. This forces SCD to recalculate the UTC activation time using your current timezone setting and re-queue the ActionScheduler event. Also verify that ActionScheduler itself is running — you can check it under WooCommerce → Status → Scheduled Actions. A large backlog of pending actions can delay activation.
Does the timezone setting affect when the campaign expires, not just when it starts?
Yes. Both the start time and end time are stored as UTC timestamps, both calculated from your site timezone at save time. If your timezone was wrong when you saved the campaign, the deactivation event is also scheduled at the wrong UTC time. The same fix applies: re-save the campaign after correcting the timezone.
I changed my WordPress timezone but my existing campaigns didn’t update. Do I need to do something?
Correct — changing the WordPress timezone does not automatically update existing campaigns. Campaigns store their UTC timestamps at save time. To apply the new timezone to an existing campaign, open it in the SCD wizard and save it. The compiler will read your new timezone setting and recalculate starts_at and ends_at in UTC. If you have multiple campaigns, update each one.
If my store serves customers in multiple timezones, which timezone should I use for scheduling?
Use the timezone that matches your store’s primary operating region or where most of your promotional communication is targeted. SCD uses a single site timezone for campaign scheduling — it is not designed to fire different start times per customer timezone. If you want to target a global midnight launch, pick the timezone that matters most to your biggest customer segment and schedule accordingly. Some merchants run separate campaigns for different regional promotions in that case.
Does Daylight Saving Time affect my scheduled campaigns?
It can, if your timezone uses DST and you are using a fixed UTC offset instead of a named timezone. With a named timezone (e.g. “America/New_York”), WordPress and SCD automatically adjust for DST transitions. With a fixed UTC offset (e.g. “UTC-5”), the offset never changes, so a campaign set for midnight in winter will run at 1am in summer after the clocks shift. Use named timezones to avoid this.
Can I override the timezone for a specific campaign independently of my WordPress setting?
The campaign wizard reads the site timezone from your WordPress settings — there is no separate per-campaign timezone override field in the current version. The campaign stores the timezone that was in effect when it was saved. Changing the site timezone and re-saving the campaign is the mechanism for updating it.
Key Takeaways
- Timezone mismatch is the most common cause of sales firing at the wrong local time. The fix starts in Settings → General, not in the campaign itself.
- Use a named timezone (e.g. “America/Chicago”) rather than a fixed UTC offset — named timezones adjust for Daylight Saving Time automatically.
- Smart Cycle Discounts treats your input as local time in your WordPress site timezone and converts it to UTC at save time. You enter the time you mean; the plugin handles the math.
- Re-saving a campaign recalculates its UTC timestamps using the current timezone setting. If you fixed your timezone after creating campaigns, re-save each affected campaign.
- Overnight windows (e.g. 10pm to 2am) are handled correctly — the plugin detects when an end time falls before the start time and applies the correct overnight comparison logic.
- Before a big launch, verify your timezone setting, check Campaign Health in the wizard, and consider doing a quick test on staging to confirm prices update at the expected local time.
Schedules That Fire When You Intend
Smart Cycle Discounts converts your local time to UTC automatically, handles overnight windows, and uses ActionScheduler for reliable campaign activation. Free to start, no credit card required.