AIWorkflow AutomationOperationsSchema

Why the AI Gets the Date Wrong in Your Automation

An AI model has no clock, so in an automation it resolves words like tomorrow and next Tuesday against whatever date the prompt gives it, or against a guess from its training data if the prompt gives none. The common fix of putting today's date at the top of the system prompt is wrong twice: the correct anchor is when the source message was sent, in the sender's time zone, not when the automation runs, and a changing date at the top of the prompt breaks prompt caching. Pass the source timestamp and time zone with each record, have the model return the date phrase verbatim, and resolve and check the date in code.

Alexey YushkinFounder, GENERAL INFORMATICS3 min read

An AI model has no clock. When your automation asks it to turn "tomorrow" or "next Tuesday" into a date, it works from whatever date the prompt contains, and if the prompt has none, it guesses one from its training data. The usual fix is to put today's date at the top of the system prompt, and in an automation that is wrong twice. The date that matters is when the customer wrote the message, in their time zone, not when your workflow happens to run. And a date that changes at the top of the prompt breaks prompt caching on both Anthropic and OpenAI.

Every guide on this topic stops at "tell the model what day it is." That is correct for a chat window, where the person typing and the model reading share the same moment. An automation breaks that assumption. Messages sit in inboxes, queues, batches, and retry loops. The run happens later than the writing, sometimes by days.

Why does the AI think it is a different day, or a different year?

Through the API, the model sees exactly what you send and nothing else. The ChatGPT, Claude, and Gemini apps seem to know the date because the product adds it to the conversation before your message arrives. Your n8n node or Zapier step does not do that unless you tell it to.

With no date in the prompt, the model does not say it does not know. It picks one. The guess tends to sit near the end of its training data, so "March 3" with no year becomes March 3 of a year that has already passed, and a follow-up email written by the model mentions "this year" and means last year. Nothing errors. The field fills with a valid date that is wrong.

That part is the easy failure, and adding a date to the prompt fixes it. The harder failures start once you add one.

Which "today" should the automation use?

There are at least four candidates for "today" in a normal automation, and they disagree more often than you would expect. Here is one message run through each.

A customer in San Diego emails at 9:40 PM on Friday, September 25, 2026: "Can your tech come by tomorrow morning?" The email's Date header reads Fri, 25 Sep 2026 21:40:00 -0700. Your workflow picks it up from a queue on Monday morning.

Anchor the automation usesWhat "today" is"Tomorrow" resolves toRight?
Sender's local time, from the Date headerFriday, Sept 25Saturday, Sept 26Yes
Server clock in UTC when the email arrivedSaturday, Sept 26 (04:40 UTC)Sunday, Sept 27No
Run time, Monday morning after a weekend backlogMonday, Sept 28Tuesday, Sept 29No
No date in the promptWhatever the model assumesA guess, possibly in another yearNo

Only the first row matches what the customer meant, and it is the one the standard advice skips. "Put the current date in the system prompt" produces row two or row three, depending on when the run happens.

The gap between writing and running is not an edge case. Some of the ways it opens up:

  • Queues and business-hours processing. Anything received after hours and handled the next morning shifts by a day.
  • Batch APIs. Anthropic's Message Batches API says most batches finish within an hour, but results can take up to 24 hours before a batch expires. Stamping the date at submission or at processing gives different answers for anything near midnight. We compare batch and live calls in batch vs real-time AI calls.
  • Retries. A call that failed Friday and succeeded Saturday on retry now reads "tomorrow" as Sunday.
  • Backfills and replays. Rerun last month's inbox through a new extraction step with "today" set to the run date and every relative date in the history moves to this month. See backfilling an automation over existing records.

The time zone half is just as specific. Every US state sits behind UTC, so a late-evening message anywhere in the continental US is already stamped with the next day in UTC. An email Date header carries the sender's offset (RFC 5322 requires the zone). Twilio's date_sent and date_created on a message are GMT only, so for SMS you need the time zone from the contact record or, failing that, the business's own. A web form can capture the browser's zone with Intl.DateTimeFormat().resolvedOptions().timeZone and send it with the submission. This is the same class of bug as a date that shows up one day off between systems, except here the model is the step doing the shifting.

Where should the date go in the prompt?

At the end, next to the record, and never at the top of the system prompt.

Prompt caching discounts the longest identical opening of your prompt. Anthropic builds the cache in the order tools, then system, then messages, and its documentation says a change at any level invalidates that level and every level after it. Its caching guide uses a per-request timestamp as the example of content that produces no cache hits when it sits inside the cached prefix. OpenAI's guide, as of September 2026, says the same thing directly: if instructions contain timestamps or other dynamic content, put them at the end rather than the beginning.

So a system prompt that opens with "Current date and time: 2026-09-30 14:07:33" pays full price for the whole instruction block on every call. A date without a time is gentler, since it changes once a day, but it still means the first call after midnight rebuilds the cache, and it is still the wrong anchor. Our prompt caching guide covers the prefix rules in more detail.

The layout we use:

  1. System prompt: instructions, schema, examples. No dates. Identical on every call.
  2. User message, per record: the anchor block, then the content.

The anchor block is short and explicit:

Message sent: 2026-09-25T21:40:00-07:00 (Friday), sender time zone America/Los_Angeles
Business time zone: America/New_York

Include the weekday. A model given only an ISO date has to work out the day of the week itself, and that is exactly the calendar arithmetic you do not want it doing.

Should the model resolve the date, or your code?

Your code. The model's job is to find the date phrase and say what it thinks the phrase means. Converting "next Thursday" into a calendar date is arithmetic, and a date library does it the same way every time. Language models get it right most of the time, which is the dangerous part, because an occasional miss looks exactly like a correct answer.

Ask for three fields instead of one:

{
  "date_expression": "tomorrow morning",
  "resolved_date": "2026-09-26",
  "ambiguous": false
}

Then, in the next step:

  1. Resolve date_expression yourself with a parser such as chrono (JavaScript) or dateparser (Python), against the anchor from the table's first row, in the sender's zone.
  2. Compare your date to resolved_date. If they match, use it.
  3. If they disagree, if ambiguous is true, or if the phrase is empty but the message clearly asks for a time, send the record to a person. Do not book it.

The comparison is cheap and it catches both model mistakes and parser mistakes. It also gives you a log of the phrases your customers actually use, which is useful when you tune the prompt. Enforce the shape with structured outputs so the fields always come back; when the AI returns broken JSON covers how.

Some phrases should always count as ambiguous, whatever the model says:

  • "Next Tuesday" said on a Monday. On Monday, September 28, 2026, it could mean September 29 or October 6. People disagree about this, so no prompt will settle it.
  • "This weekend" said on a Saturday. Today and tomorrow, or next weekend.
  • A bare date like "the 3rd" near a month boundary. On September 30, "the 3rd" is almost certainly October 3, but on September 2 it could be the day after or a month out.
  • Times with no zone from a customer in another state. "Call me at 9" from a Denver customer to a Boston business.

A short confirmation message ("Just to confirm, Tuesday October 6 at 10 AM?") costs one extra text. A wrong booking costs a truck roll and a customer.

What this looks like in a real scheduling workflow

Take an intake flow for a service business: emails and texts come in, an AI step extracts the job type and the requested date, and the workflow creates a tentative appointment. A version built on the standard advice has the current date in its system prompt and runs on a schedule every 15 minutes.

It works in testing, because the tester sends a message and the run picks it up within minutes, in the same time zone. In production it breaks on Friday nights, on Monday mornings after the weekend queue, on every retry that crosses midnight UTC, and on the first backfill. None of those failures raise an error. They produce valid appointments on the wrong day, and someone finds out when the customer calls to ask where the tech is.

The fixed version has four changes: the anchor comes from the message itself, the anchor block moves to the end of the prompt, the model returns the phrase along with its date, and code confirms the date before anything is booked. None of this needs a better model. It needs the automation to pass along a fact the model cannot know on its own. When we build intake and scheduling flows as part of our workflow automation work, this anchor block is standard in every AI step that reads dates.

What to do next

Open the AI step in your automation that extracts dates and check two things. First, where does "today" come from? If it is now() at run time, or a date in the system prompt, replace it with the source message's own timestamp and the sender's time zone. Second, does anything check the model's date before it becomes a booking, a due date, or a reminder? If not, add the phrase-plus-date output and the code comparison above.

If your date-handling AI step feeds scheduling, billing, or customer promises and you want a second pair of eyes on it, we design and build these systems as part of our custom AI software work. Tell us what the workflow does and where the dates come from.

Frequently Asked Questions

SOURCES & CITATIONS

  1. Prompt caching — Anthropichttps://platform.claude.com/docs/en/build-with-claude/prompt-caching
  2. Prompt caching — OpenAIhttps://developers.openai.com/api/docs/guides/prompt-caching
  3. Batch processing (Message Batches API) — Anthropichttps://platform.claude.com/docs/en/build-with-claude/batch-processing
  4. Messages resource (date_sent) — Twiliohttps://www.twilio.com/docs/messaging/api/message-resource

About Alexey Yushkin

Alexey is the founder of GENERAL INFORMATICS LLC. He designs and ships AI and automation systems for businesses and operators across the US.

Connect on LinkedIn

Related reading

Want this kind of system in your business?

We build practical AI and automation systems for operators. Send us your current workflow and we will show you what to automate first.