Skip to content

Extension event envelope

ExtensionEvent is the in-process payload delivered to an extension that implements IEventExtension. Every extension event uses the same envelope; the event name determines whether Data has an event-specific shape.

public record ExtensionEvent(
string EventType,
string EntityType,
int EntityId,
Dictionary<string, object?>? Data = null)
{
public string CanonicalEventType { get; init; } = EventType;
}

The following JSON shows the equivalent property values for reference. Cove passes the C# object directly and does not serialize an HTTP request.

{
"eventType": "video.updated",
"canonicalEventType": "video.updated",
"entityType": "video",
"entityId": 42,
"data": null
}
C# propertyJSON notationRuntime typeContract
CanonicalEventTypecanonicalEventTypestringStable canonical name. Route new handlers on this value.
EventTypeeventTypestringCompatibility event name. It can retain a legacy spelling.
EntityTypeentityTypestringLowercase kind of the affected entity.
EntityIdentityIdintCove database identifier of the affected entity.
DatadataDictionary<string, object?>?Event-specific values, or null when the event has no additional payload.

CanonicalEventType and EventType normally match. Audio and text lifecycle notifications retain dotless compatibility names in EventType, while CanonicalEventType uses the documented noun.verb form.

FamilyCanonical namesData shape
Entity lifecycle<entity>.created, <entity>.updated, <entity>.deletednull
Ratingsrating.created, rating.updated, rating.deleted{ "entity": { "userId", "aspect", "value" } }

Only EntityEvent values cross this extension boundary. Internal job progress and server lifecycle events are not ExtensionEvent payloads.

  • Route on CanonicalEventType unless maintaining a handler for a legacy EventType value.
  • Treat the payload as an invalidation signal and fetch current entity state when needed.
  • Expect a deleted entity to be unavailable by the time its handler runs.
  • Make handlers idempotent because delivery is best effort and is not an audit log.
  • Make handlers safe for concurrent execution; independently queued events can overlap.
  • Do not assume replay, retry, or global ordering.