Webhook Payload Schema Validation
Validate raw webhook payloads against the embedded EmailReceivedEvent JSON Schema in the Go SDK, using ValidateEmailReceivedEvent (error-raising) or SafeValidateEmailReceivedEvent (error-collecting).
The Go SDK embeds the canonical webhook JSON Schema (generated from json-schema/email-received-event.schema.json in the monorepo) and exposes ValidateEmailReceivedEvent, the function that checks an already-JSON-decoded webhook payload against it. It takes a decoded value (map[string]any or similar), not raw bytes.
Most callers never call it directly. primitive.Receive(...) and primitive.HandleWebhook(...) run this validation internally after signature verification; see Receiving and Verifying Webhooks. Reach for ValidateEmailReceivedEvent directly when you already have a parsed payload from somewhere else (a stored fixture, a replayed delivery, a test) and want the schema check without re-running signature verification.
ValidateEmailReceivedEvent#
ValidateEmailReceivedEvent validates a decoded payload against the embedded email.received schema and returns a typed *EmailReceivedEvent on success or an error on failure.
package main
import (
"encoding/json"
"fmt"
"log"
"os"
primitive "github.com/primitivedotdev/sdks/sdk-go"
)
func main() {
raw, err := os.ReadFile("stored-delivery.json")
if err != nil {
log.Fatal(err)
}
var payload map[string]any
if err := json.Unmarshal(raw, &payload); err != nil {
log.Fatal(err)
}
event, err := primitive.ValidateEmailReceivedEvent(payload)
if err != nil {
log.Fatalf("invalid email.received payload: %v", err)
}
fmt.Println(event.Email.Headers.Subject)
}
| Aspect | Detail |
|---|---|
| Input | A decoded value (for example map[string]any from json.Unmarshal, or the result of primitive.ParseJSONBody) |
| Success return | *EmailReceivedEvent, nil |
| Failure return | nil, error |
| Used internally by | primitive.HandleWebhook, primitive.Receive, and primitive.ParseWebhookEvent (for the email.received case) |
See Error Handling for the Go SDK's error types, including WebhookValidationError, WebhookPayloadError, and WebhookVerificationError.
Parsing raw bytes first#
primitive.ParseJSONBody turns a raw request body into the decoded value this validator expects, rejecting empty bodies, invalid UTF-8, and trailing content after the JSON value with a WebhookPayloadError. It also strips a leading UTF-8 BOM.
parsed, err := primitive.ParseJSONBody(rawBody)
if err != nil {
log.Fatal(err)
}
event, err := primitive.ValidateEmailReceivedEvent(parsed)
if err != nil {
log.Fatal(err)
}
_ = event
Where the schema comes from#
The embedded schema is generated, not hand-maintained inside sdk-go. Its source of truth is json-schema/email-received-event.schema.json at the monorepo root, and changing the webhook contract means editing that file and running make go-generate from the repo root rather than editing anything under sdk-go. See Monorepo Structure and Release Process for the regeneration workflow and Webhook Schema Codegen for how the schema compiles into per-language model and validator modules.
Relationship to unknown event types#
Strict schema validation applies only to email.received. ParseWebhookEvent routes payment.* bodies to a typed PaymentEvent, interaction.* bodies to InteractionEvent, and everything else to UnknownEvent for forward compatibility, so a future event type never fails validation. See Webhook Event Types for the full catalog and the X-Webhook-Event header discriminator.
Next steps#
See how signature verification and this schema check compose inside Receive and HandleWebhook.
Error HandlingLook up WebhookValidationError and every other error type the Go SDK returns.
Webhook Schema CodegenTrace how the shared schema file compiles into the Go SDK's embedded validator.
Webhook Event TypesUnderstand the email, payment, and interaction event catalog and the X-Webhook-Event header.
Was this page helpful?