fix(stream): chat insert 400 — insert body must declare snippet.type

The liveChatId fix (TASK 44) worked on the next Test Stream, but every Mock
Chat Input send returned 'YouTube rejected the message (error 400)'. The
runtime log's body: 400 MISSING_REQUIRED_FIELD, domain
youtube.api.v3.LiveChatMessageInsertResponse.Error.

The liveChat/messages.insert snippet requires type ('textMessageEvent' or
'pollEvent') alongside liveChatId and textMessageDetails.messageText; the
TASK 41 body omitted it, and the Good Dog test asserted only liveChatId +
messageText were present — false-green while real YouTube rejected every
send. Fix body + assert type in the same test so the field can never drop
silently again.

Reference: https://developers.google.com/youtube/v3/live/docs/liveChatMessages/insert

Good Dog: ONE integration test (strengthened TestStream_DockTooling...).
Gate: clean build 0 warnings; full vstest 317/318 (the 1 failure is the
known environmental RealMouseDrag flake — passes 3/3 in isolation).
This commit is contained in:
2026-09-25 08:12:05 -07:00
parent 94f015044a
commit 0981a72eea
7 changed files with 101 additions and 33 deletions
+5 -1
View File
@@ -1575,7 +1575,11 @@ These are the hard facts behind every decision. Full list in `TASKS.md`.
which raises the poller's `MessageReceived` seam, marked `ChatMessage.IsSimulated`. **API fact
(researched + hard constraint): `liveChat/messages.insert` only creates `textMessageEvent`s —
SuperChats / memberships / sponsorships cannot be inserted via any API**; simulated non-text
events are local-only by design and never reach YouTube. Scopes `youtube` + `youtube.force-ssl`
events are local-only by design and never reach YouTube. **Insert body shape (fixed 2026-09-25,
TASK 45):** the body MUST include `snippet.type` = `"textMessageEvent"` alongside `liveChatId`
and `textMessageDetails.messageText` — omitting type returns `400 MISSING_REQUIRED_FIELD`
(found live on the next Test Stream; the TASK 41 test had asserted body presence but not
type, so it stayed false-green). Scopes `youtube` + `youtube.force-ssl`
already cover insert. **Real stinger/TTS alert widgets are DONE (TASK 43, shipped
2026-09-24) as the native alert box** — see the next section; Text source (TASK 3 item 16)
and the RewardEvent persistence (item 20) remain open.