Conversation
The generator stages the pinned API tree, applies the stream branch's diff and regenerates only the files it touches. Core moves to `moe/AI-198-api-protos-on-85b71d7`, which is the commit main pins plus that same diff on its `api_upstream`, so the vendored tree regenerates byte-for-byte from the pin and `check-protos` agrees.
This was referenced Sep 25, 2026
The stream commands name a stream rather than an id, and an appended batch records its end offset rather than a count. Core moves to the matching protos-only branch so the vendored tree still regenerates from the pin.
Core moves to the protos-only branch that carries the new StreamStartPosition message and the start_position field, so the vendored tree regenerates from the pin.
Core moves to the protos-only branch that carries the Wake message, the wakes field on the workflow task poll response and the WakeWorkflowExecution call, so the vendored tree and the bridge client regenerate from the pin.
…the clients. Core moves to the protos-only branch commit that carries the notification channel: the Notification message, the five channel calls, the subscribe command and event, the notifications on the scheduled Workflow Task event, and the bridge's command and activation job for them. The vendored tree, the payload visitor and the bridge client regenerate from the pin.
The protos pin carries ChannelSubscriptionInfo on the describe response and the UnsubscribeNotificationChannel command, event and failed cause. The pin refuses the lang command the way it refuses the subscribe, so the layers above pin the delivery Core before a workflow can unsubscribe.
A standalone activity can own a channel too, so the five channel requests and both `linked_to` fields carry `common.v1.Execution` in place of `WorkflowExecution`, with the old numbers reserved.
The previous shape was never released, so the five channel requests and both `linked_to` fields reuse the numbers `workflow_execution` and the old `linked_to` had, with nothing reserved. Names and types are unchanged.
Owner
Author
|
Replaced by #19, #20, #21, #22, #23, #24, #25, #26, #27, #28, #29, #30, #31, #32, #33, #34, #35, #36, #37, #38, #39, #40, #41, #42, #43, #44, #45, #46, #47, #48, #49, #50, #51, #52, #53, #54 and #55. Same content, split into 37 PRs in the v3 series: the notification channel first, then the streaming interface, then native streams and the rest. The branch stays as a pin. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR vendors the stream and notification channel additions to the public API protos.
What changed?
temporalio/api/stream/v1/is new. It holdsStreamRecord,StreamRecordKindandStreamStartPosition. Every provider in the series moves that record, with the user's value inbodyas an ordinary payload, so a codec applies.command/v1,enums/v1andhistory/v1gain the subscribe and append stream commands, their command types, the two workflow stream event types and the new failed causes.workflowservice/v1gains the fields that travel with them.temporalio/api/notification/v1/is new. It holdsNotification,ChannelKind,ChannelListenerandWorkflowListener.workflowservice/v1gainsNotifyChannel,RegisterChannelListener,UnregisterChannelListener,PollChannelandDescribeChannel;command/v1gains theSubscribeNotificationChannelandUnsubscribeNotificationChannelcommands,history/v1the subscribed and unsubscribed events and thenotificationsfield on the scheduled Workflow Task event, andenums/v1their command types, event types and failed causes. The bridge protos gain the matching commands and theNotificationsReceivedactivation job, andservices_generated.pyandclient_rpc_generated.rscarry the five calls.workflow/v1gainsChannelSubscriptionInfo, andDescribeWorkflowExecutionResponsegainschannel_subscriptions: the channels a run stands on, with the counter it last accepted, the pending and scheduled notifications and the linked channel's counts.Notification.linked_tonames the owner as acommon.v1.Execution, the five channel requests take an optionalexecutionthat addresses it, andDescribeChannelResponsereportskindandlinked_to.temporalio/bridge/sdk-corepins a protos-only Core branch. It's the commitmainalready pins, with the api branch's stream and channel diff applied to itsapi_upstreamand the two bridge protos.scripts/gen_stream_api_protos.pystages the pinned API protos, applies the api branch's diff, and regenerates only the files that diff touches.Nothing imports these modules yet. The three layers on top are written against them.
Part of AI-198 (epic AI-37).
Why?
The stream protos live on an api branch that upstream Core doesn't pin. Regenerating everything from that branch would pull in unrelated api churn and bury the stream diff. The Core repin lets
poe gen-protosreproduce this tree byte for byte, which is whatcheck-protosasserts. The script stays because the next api branch update needs it again.Two kinds of channel because most listeners are one workflow. An independent channel pays its own writes per notification on top of the listener's; a channel kept in the listener's own state makes a notification one write on the owner, the same write that schedules its task, and needs no subscribe command.
How did you test it?
I ran
uv run poe lintand the unit suite without the stream cases underuv run pytest, plustests/test_service.py, which checks the generated service surface against the protos. A one-off script round-trips aStreamRecordthrough the vendored modules. The PR adds no tests of its own, since it's generated code only.