Alex Stanfield 609e7a1bf8 Fix schedule action delay after refresh (#11588)
## What changed?
- Record a buffered start's desired time when a refresh (non-long-poll
watch) observes the prior action complete, not just when the long-poll
watcher does.
- Gate the new state mutation behind a new version,
`RefreshCompletionDesiredTime` (14) -- `BufferedStarts[0].DesiredTime`
flows into the continue-as-new `Input`, which is replay-checked history,
so this can't be applied unconditionally to histories recorded below the
gate. 13 is already claimed by the in-flight `MigrationHandoffFixes`
work, so this is numbered 14; `CurrentTweakablePolicies.Version` is left
at `TriggerImmediatelyTimestamp` (12), so this PR does not itself
activate anything. `processWatcherResult` branches strictly on the
version (old codepath unchanged, new codepath gated) rather than folding
the version check into a boolean expression, so it's visually obvious
the old path is untouched on replay.
- Only backdate `DesiredTime` on the refresh path when the prior
action's `CloseTime` is genuinely after the next start's own due time --
i.e. it was actually blocked waiting on the prior action -- **and** the
start's own resolved overlap policy actually waits for a running
workflow to finish at all. A start resolved to `ALLOW_ALL` is never
blocked by a running workflow (`processBuffer` starts it regardless of
`isRunning`), so backdating it to an unrelated close time would
understate its real delay. This check is shared with `ProcessBuffer` via
a new `IgnoresRunningWorkflow` helper in `buffer.go`, so the two places
that need to agree on "does this policy wait for a running workflow"
can't drift apart.
- `refreshWorkflows` calls the backdate logic once per tracked execution
in `RunningWorkflows`. If a run still has multiple tracked executions
(e.g. `ALLOW_ALL` runs inherited from before a
pre-`DontTrackOverlapping` version ceiling was lifted), only move the
recorded close time forward -- a later-processed but earlier-closing
execution must not overwrite a genuinely later close already recorded
earlier in the same pass, or the reported delay understates how long the
start was actually blocked.
- The whole backdate decision is extracted into a pure, directly
unit-testable function, `shouldBackdateDesiredTime`.

## Why?
`processWatcherResult` only set `DesiredTime` when `long` was true (the
long-poll path). When a refresh discovered the prior action had
completed instead, `DesiredTime` stayed unset, so `ScheduleActionDelay`
fell back to the scheduled time instead of the prior action's close time
-- inflating the reported delay for back-to-back buffered actions.
Review then surfaced two follow-on correctness gaps in the fix itself:
it didn't account for `ALLOW_ALL` starts that were never actually
blocked, and it could pick the wrong close time when refreshing multiple
tracked executions in one pass.
2026-08-28 15:40:25 -05:00
2026-08-20 09:47:39 -07:00
2025-04-07 18:42:37 -07:00

Temporal—durable execution platform

GitHub Release GitHub License Code Coverage Community Go Report Card

Introduction   •   Getting Started   •   Contributing   •   Temporal Docs   •   Temporal 101

Introduction

Temporal is a durable execution platform that enables developers to build scalable applications without sacrificing productivity or reliability. The Temporal server executes units of application logic called Workflows in a resilient manner that automatically handles intermittent failures, and retries failed operations.

Temporal is a mature technology that originated as a fork of Uber's Cadence. It is developed by Temporal Technologies, a startup by the creators of Cadence.

image

Getting Started

Download and Start Temporal Server Locally

Execute the following commands to start a pre-built image along with all the dependencies.

brew install temporal
temporal server start-dev

Refer to Temporal CLI documentation for more installation options.

Run the Samples

Clone or download samples for Go or Java and run them with the local Temporal server. We have a number of HelloWorld type scenarios available, as well as more advanced ones. Note that the sets of samples are currently different between Go and Java.

Use CLI

Use Temporal CLI to interact with the running Temporal server.

temporal operator namespace list
temporal workflow list

Use Temporal Web UI

Try Temporal Web UI by opening http://localhost:8233 for viewing your sample workflows executing on Temporal.

Repository

This repository contains the source code of the Temporal server. To implement Workflows, Activities and Workers, use one of the supported languages.

Contributing

We'd love your help in making Temporal great.

Helpful links to get started:

License

MIT License

Languages
Go 99.5%
Shell 0.2%
PLpgSQL 0.2%
Makefile 0.1%