Highlights
Standalone Activities are now GA
With the following updates, Standalone Activities are now generally available (GA)!
- Renamed the standalone activity
client.StartActivityOptions.Detailsoption toStaticDetails,
andclient.ActivityExecutionDescription.GetDetailstoGetStaticDetails. - Added missing description fields:
ExecutionTimeandTotalHeartbeatCount. - Corrected stand-alone activity API documentation to use activity terminology, document that
GetActivityHandleOptions.RunIDmay be empty to target the latest run, and describe
TerminateActivityOptions.Reasonas a termination reason. - Added opt-in payload fields to
client.DescribeActivityOptions:IncludeInput,
IncludeOutcome,IncludeHeartbeatDetailsandIncludeLastFailure. - Standalone activity client calls now supply
converter.ActivitySerializationContextwhen encoding
and decoding activity payloads:ExecuteActivity(input and static summary/details),
ActivityHandle.Describe(heartbeat details, last failure, and static summary/details), and
ActivityHandle.Get(result and failure). - Standalone activities started from a redelivered Nexus operation handler now reuse the Nexus
request ID, preventing duplicate Nexus links when an idempotent start resolves to the original run. client.ActivityHandlenow supports operator commands for standalone activities:Pause,
Unpause,UpdateOptionsandRestoreOriginalOptions. Operator commands remain experimental.- Standalone Activities as Nexus operations remain experimental.
Local Activity memory savings
Local activity scheduling no longer uses a fixed 100,000-entry task queue. The queue now grows
with demand, avoiding both the up-front allocation and a possible worker deadlock when the queue
and all local activity execution slots were full.
Other Notable Changes
Added
- Worker heartbeats now report the Go runtime version (plus RoadRunner, when the SDK is embedded in
a RoadRunner binary), detected hosting environments (Docker, Kubernetes, and common cloud
platforms), and the operating system and architecture. This is sent
once per worker with the first heartbeat accepted by the server and can be turned off with
client.Options.DisableWorkerEnvironmentInfo. - Added
converter.NexusSerializationContextsupport for Nexus callers and handlers. Callers use
it for inputs, results, and failures; handlers use it for inputs, synchronous results, and
failures. Asynchronous handler results and detached standalone handles are not yet supported.
StandaloneUSE_EXISTINGhandles use their start request's context. - Added
temporal.NewPayloadValidationErrorto create non-retryable application errors with
optional structured details for payload validation failures. Passingnilomits details. - Added Go 1.27+ generic methods on the experimental
temporalnexus.NexusClientfor starting
workflow-, activity-, and workflow-update-backed Nexus operations. - Workflow task completions larger than the gRPC request size limit are now paginated automatically
when the namespace supports it. Paginated workflow task completions require Temporal Server 1.32.0
or later. - The
temporal_activity_execution_failedandtemporal_local_activity_execution_failedworker
metrics now carry afailure_reasonattribute. Each is now split into one time series per
reason, which may affect existing dashboards. - Added support for Workflow Queries as Nexus Operations.
💥 Breaking Changes
- Raised the minimum supported Go version from 1.25.4 to 1.26.0.
- Description payload fields that previously came back unconditionally are now opt-in and must be
requested viaclient.DescribeActivityOptions:GetHeartbeatDetails(IncludeHeartbeatDetails)
andGetLastFailure(IncludeLastFailure). - Experimental external storage:
converter.StorageDriverSelector.SelectDrivernow receives a
converter.StorageDriverSelectContextinstead of aconverter.StorageDriverStoreContext.
Update the parameter type; the new type carries the sameContextandTargetfields. - Local activity results are now serialized with the local activity's
ActivitySerializationContext
(IsLocal=true) instead of the workflow serialization context. Users of a context-aware
DataConverterorPayloadCodecwhose encoding depends on the serialization context (for example
context-derived encryption keys or AAD) may fail to decode local activity results recorded in
histories written by earlier SDK versions, both on replay and when continuing an open workflow. - Experimental
workflow.WorkflowRandomStream'sUint64now derives its value by callingRead
internally instead of the underlying generator'sUint64method directly, givingRead/Uint64
interleaving on the same stream a stable, well-defined byte ordering (previously undefined per the
standard libraryChaCha8.Readdoc). This only changes output for aUint64call that immediately
follows aReadcall whose length is not a multiple of 8 bytes on the same stream; pureUint64
streams and 8-byte-aligned interleaving are unaffected. Open workflows created on SDK v1.48.0+ that
hit the affected pattern may compute a different value, and therefore may make a different decision,
on replay after upgrading. - Activity, local activity and child workflow serialization contexts are now applied to the
worker-configuredDataConverterandFailureConverterinstead of the converter already carrying
the current workflow context. A context-aware converter that composed contexts (deriving its state
from both the workflow and the activity context) now sees only the activity or child workflow
context, and one whoseWithSerializationContextreturned a converter that is no longer
context-aware now receives the activity or child workflow context it previously never saw.
Fixed
- Workflow autoscaling now favors sticky polls when sticky work is backlogged, while allowing
normal polls to use spare slots once sticky reaches its autoscaling target. - The
PayloadDownloadDurationandPayloadUploadDurationfields on the workflow task duration log
now report the wall-clock time external storage was in flight. Previously each batch's duration was
summed, over-reporting the time whenever storage operations ran concurrently. temporal.IsWorkflowExecutionAlreadyStartedErrornow detects wrapped
serviceerror.WorkflowExecutionAlreadyStartederrors.- Malformed Nexus link errors now log the link URL and parse error under stable structured fields.
- Legacy query task processing failures are now reported through
RespondQueryTaskCompletedinstead of
RespondWorkflowTaskFailed, allowing query callers to receive the failure instead of timing out. - Local activity results are now serialized with the local activity's
ActivitySerializationContext
(IsLocal=true) on both ends. Previously the result was encoded with the plain worker data converter
but decoded through the workflow serialization context, so a context-awareDataConverteror
PayloadCodecsaw mismatched contexts for local activity results. - Workflow replays no longer retain one-shot workflow state in the process-wide sticky cache.
- Added disabled-by-default SDK flag 9 for deterministic workflow child-context cancellation.
Currently no behavior is changed by default, a future PR will flip this flag on by
default. DefaultFailureConverter.FailureToErrornow correctly decodesLastHeartbeatDetailsfor a
reset-workflow failure. Previously the raw payload proto was treated as a single detail value,
so callingDetails()on the resultingApplicationErrorreturnedErrTooManyArginstead of
decoding it.- Added documentation that function literals (closures) shouldn't be registered as
workflow functions or activity functions without an alias. - Query results are now checked against the server's blob-size error limit after
external storage has had a chance to offload them, matching how update and activity
results of the same size already behaved. A query result large enough to be offloaded
toclient.Options.ExternalStorageis now stored instead of failing locally with
TMPRL1103. As a consequence, aStorageDriverfailure while storing an oversized
query result now fails the workflow task instead of returning a failed query result.
What's Changed
- Prettify the release script by @dplyukhin in #2579
- bump to go 1.26, run go fix by @yuandrew in #2530
- Combine cilium/ebpf and gRPC dependency updates by @yuandrew in #2585
- Bump Staticcheck for Go 1.27 and flag intentional findings by @Quinn-With-Two-Ns in #2593
- Add payload validation error factory by @bergundy in #2586
- Clarify Standalone activity option documentation by @Quinn-With-Two-Ns in #2591
- docs: clarify AI contribution expectations by @tconley1428 in #2536
- Apply activity serialization context to local activity results by @xepozz in #2562
- Document PayloadCodec failure behavior by @yuandrew in #2592
- Omit nil payload validation details by @bergundy in #2598
- contrib/googleadk: harden replay-safe telemetry wrappers by @DABH in #2573
- contrib/googleadk: recreate spans during replay with deterministic IDs by @DABH in #2581
- Isolate the workflow replayer cache by @ali-khokhar-nvidia in #2596
- Add generic methods to NexusClient by @Quinn-With-Two-Ns in #2604
- [SDK Sentinel] Synchronize workflow versions before deployment option updates by @sdk-sentinel-bot in #2603
- NEXUS-550: Nexus Operation Query support by @mavemuri in #2508
- Add SDK Sentinel PR responder by @Sushisource in #2607
- [SDK Sentinel] Fix delayed Nexus update test race by @sdk-sentinel-bot in #2597
- feat(metrics): emit failure_reason on existing activity failure metrics by @jmaeagle99 in #2606
- [SDK Sentinel] Fix worker deployment version readiness flake by @sdk-sentinel-bot in #2601
- Decode LastHeartbeatDetails for reset-workflow failures by @mittalpk in #2522
- fix(metrics): label payload limit failures as PayloadsTooLarge by @jmaeagle99 in #2609
- Fix structured logging for malformed Nexus links by @AbuBakkarBinAkmal in #2602
- Bump actions/create-github-app-token from 2.2.2 to 3.2.0 by @dependabot[bot] in #2623
- Stabilize waitServerReady timeout test by @yuandrew in #2612
- [SDK Sentinel] Stabilize child and parent cancellation integration test by @sdk-sentinel-bot in #2620
- Use shared changelog workflow by @Sushisource in #2624
- contrib/googleadk: adopt adk/v2 v2.2.0 and multi-decision confirmation resumes by @DABH in #2538
- Skip newer Go syntax in doclink by @yuandrew in #2618
- Group unit tests by module by @yuandrew in #2615
- [SDK Sentinel] Test graceful-shutdown poll context directly by @sdk-sentinel-bot in #2627
- Detect wrapped already-started errors by @yuandrew in #2631
- Expose internal APIs to sibling SDK packages for system nexus by @dplyukhin in #2634
- [SDK Sentinel] [SDK Sentinel] Isolate Cloud TestBasic workflow IDs by @sdk-sentinel-bot in #2635
- feat: workflow command pagination by @jmaeagle99 in #2617
- 💥 feat(extstore): pass a dedicated select context to the driver selector by @jmaeagle99 in #2637
- fix(extstore): update GCS driver metadata to be consistent with GCS docs. by @cconstable in #2577
- test: run categorized integration tests against Cloud by @THardy98 in #2576
- [SDK Sentinel] Stabilize payload-limit termination test by @sdk-sentinel-bot in #2632
- bump gRPC dep to v1.83.1 by @yuandrew in #2655
- fix(test): stabilize workflow task pagination integration test by @jmaeagle99 in #2645
- Expand Nexus + SAA test coverage by @Quinn-With-Two-Ns in #2633
- Restore tests skipped for flakiness by @yuandrew in #2613
- Add GCP Cloud Run OpenTelemetry support by @seanbollin in #2588
- Report runtime environment information in worker heartbeats by @Sushisource in #2647
- Preserve child context cancellation order by @yuandrew in #2608
- Fix legacy query task failure reporting by @kritibehl in #2639
- fix(extstore): report wall-clock duration for storage metrics by @jmaeagle99 in #2658
- fix: offload oversized query results to external storage by @ghaskins in #2641
- Fix: Balance sticky and normal workflow slot admission for Autoscaling by @yuandrew in #2643
- Fix tracing test workflow collision by @yuandrew in #2664
- [SDK Sentinel] Fix OpenTelemetry tracing test workflow collisions by @sdk-sentinel-bot in #2665
- [SDK Sentinel] Stabilize waitServerReady timeout test by @sdk-sentinel-bot in #2657
- Replace big LA tunnel with linked list by @Sushisource in #2662
- Bump actions/setup-go from 6.5.0 to 7.0.0 by @dependabot[bot] in #2505
- Add endpoint-aware serialization for Nexus operations by @JoshuaFrenchwood in #2644
- [SDK Sentinel] Stabilize tracing span propagation assertion by @sdk-sentinel-bot in #2672
- Add hints that function literals aren't supported by @dplyukhin in #2659
- chore: bump google.golang.org/grpc from 1.83.1 to 1.83.2 by @dplyukhin in #2679
- 💥 Rename Standalone Activity Details to StaticDetails by @GregoryTravis in #2681
- Use
ActivitySerializationContextfor standalone activities by @GregoryTravis in #2680 - Standalone Activities operator commands and optional payloads by @GregoryTravis in #2646
- [SDK Sentinel] Synchronize local activity cancellation test by @sdk-sentinel-bot in #2682
- Fix task handler cache teardown by @yuandrew in #2638
- Fix/2547 random stream interleaving by @AyushKashyapII in #2666
- Explain wait server timeout test bound by @yuandrew in #2687
- Remove Experimental tag from Standalone Activities by @GregoryTravis in #2690
New Contributors
- @ali-khokhar-nvidia made their first contribution in #2596
- @mittalpk made their first contribution in #2522
- @AbuBakkarBinAkmal made their first contribution in #2602
- @seanbollin made their first contribution in #2588
- @ghaskins made their first contribution in #2641
- @JoshuaFrenchwood made their first contribution in #2644
- @GregoryTravis made their first contribution in #2681
- @AyushKashyapII made their first contribution in #2666
Full Changelog: v1.48.0...v1.49.0