From bc816be5716be927798a1b25eabf6a85b5a9ec79 Mon Sep 17 00:00:00 2001 From: Mikhail Agapov <118179774+mikhail-dcl@users.noreply.github.com> Date: Wed, 22 Jul 2026 17:16:00 +0300 Subject: [PATCH] feat: Pulse pure scenes listeners (#437) * feat: add SceneListenerHandshakeRequest to ClientMessage Scene-listener connect message: signed-fetch auth chain, realm, and an immutable parcel-index AoI. New ClientMessage oneof case (= 8). Co-Authored-By: Claude Fable 5 * feat: scene-listener AoI as parcel rects Replace SceneListenerHandshakeRequest.parcel_indices with inclusive parcel-coordinate rects (sint32) so big scenes announce their AoI in a few bytes. The sum of rect areas is capped server-side. Co-Authored-By: Claude Fable 5 --------- Co-authored-by: Claude Fable 5 --- proto/decentraland/pulse/pulse_client.proto | 22 +++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/proto/decentraland/pulse/pulse_client.proto b/proto/decentraland/pulse/pulse_client.proto index 09760dab..aca97cbd 100644 --- a/proto/decentraland/pulse/pulse_client.proto +++ b/proto/decentraland/pulse/pulse_client.proto @@ -66,6 +66,27 @@ message TeleportRequest { string realm = 5; } +// Inclusive rectangle in parcel coordinates. A single parcel is min == max. +message ParcelRect { + sint32 min_x = 1; + sint32 min_z = 2; + sint32 max_x = 3; + sint32 max_z = 4; +} + +// Scene-listener connect: same signed-fetch auth chain as HandshakeRequest, plus an +// immutable parcel-set area of interest. No initial state — a listener is never a subject. +message SceneListenerHandshakeRequest { + // Signed-fetch headers JSON — identical shape to HandshakeRequest.auth_chain. + bytes auth_chain = 1; + // AoI realm partition — same rules as TeleportRequest.realm. + string realm = 2; + // Announced AoI as inclusive parcel-coordinate rects; fixed for the connection + // lifetime. The sum of rect areas is capped server-side (SceneListener:MaxParcels) — + // overlaps count per rect, so announce disjoint rects. + repeated ParcelRect parcel_rects = 3; +} + message ClientMessage { oneof message { HandshakeRequest handshake = 1; @@ -75,5 +96,6 @@ message ClientMessage { EmoteStart emote_start = 5; EmoteStop emote_stop = 6; TeleportRequest teleport = 7; + SceneListenerHandshakeRequest scene_listener_handshake = 8; } }