SecurityFour documented controls

Transactional email security, in layers.

tinyRelay secures transactional email at each hop. Your API key travels in a request header, API calls are accepted only from IP addresses we allowlist for you, webhooks are signed and sent from one fixed IP, and tracked links can hide their destination in a tamper-proof token.

Your app
203.0.113.24
Gate
key · IP
tinyRelay
sends
X-RELAY-ACCESS-TOKENAPI key header · POST /email/campaignValid key
203.0.113.24Calling IPAllowlisted
Accepted202 with a requestId
Your app
198.51.100.7
Gate
key · IP
tinyRelay
sends
X-RELAY-ACCESS-TOKENAPI key header · POST /email/campaignValid key
198.51.100.7Calling IPNot on your allowlist
Not acceptedCalls only from IPs you gave us
Your app
203.0.113.24
Gate
key · IP
tinyRelay
sends
X-RELAY-ACCESS-TOKENAPI key header · POST /email/campaignMissing
203.0.113.24Calling IPAllowlisted
401 UnauthorizedKey missing or invalid

Illustrative IPs. Header, allowlisting and 401 from the docs.

Four layers

One documented control at each hop.

From your app to the email itself, each step of a send has its own protection. Hover a layer to hold it.

01
LAYER 1 · YOUR APP → TINYRELAY

API key in a header

Every API call carries your key in X-RELAY-ACCESS-TOKEN. Keep it server-side, never in client code or a public repo.

02
LAYER 2 · NETWORK

IP allowlisting

You give us the IP addresses you call from at setup. Those are the addresses allowlisted for your API calls.

03
LAYER 3 · TINYRELAY → YOUR ENDPOINT

Signed webhooks, one IP

HMAC-SHA256 signatures with a per-endpoint secret, sent from 3.229.12.181.

04
LAYER 4 · THE EMAIL ITSELF

Link wrapping

X-Link-Wrapping: true hides tracked destinations in an opaque, tamper-proof token.

Request lifecycle

Follow one email. See the control at every hop.

A send touches three places: your app, tinyRelay and your webhook endpoint. Pick a stop to see what protects it and what is yours to do.

Your app calls tinyRelay.

Two checks apply to every API call: it must carry a valid key, and it must come from an IP address you gave us during setup, which we allowlist for security.

CONTROLS
  • API key in the X-RELAY-ACCESS-TOKEN header
  • Calling IP addresses allowlisted at setup
  • 401 when the key is missing or invalid
YOURS TO DO
  • Keep keys and SMTP credentials in a secret store
  • Never ship the key in client-side code or a public repository
  • Send us your new IPs before your infrastructure changes

tinyRelay sends the email.

Mail goes out from sender domains you shared with us, signed with DKIM. You decide per request whether links are tracked and whether tracked links reveal where they go.

CONTROLS
  • DKIM signing via tec1._domainkey CNAME
  • disableTrackingLinks: no rewriting, no open pixel
  • X-Link-Wrapping: destinations in a tamper-proof token
YOURS TO DO
  • Turn tracking off for sign-in codes and reset links if you prefer
  • Validate DKIM and SPF with PUT /domain/dns/check

tinyRelay reports back.

Every event is signed with your endpoint's own secret and posted from one IP address. The signature, not the IP, is what proves the request is ours.

CONTROLS
  • svix-id, svix-timestamp and svix-signature headers
  • HMAC-SHA256 over id.timestamp.body
  • Sent from 3.229.12.181
YOURS TO DO
  • Verify every request in constant time
  • Reject stale timestamps; five minutes is a reasonable tolerance
  • Deduplicate on svix-id
Signed webhooks

Allowlisting an IP is not authentication.

Anything that can reach your endpoint can post to it. So every webhook request is signed, and your handler checks three headers before it trusts the body.

YOUR SIGNING SECRET

Each endpoint has its own secret, never shared across accounts. You receive it when your endpoint is configured. Store it with your other credentials.

REPLAY PROTECTION

svix-timestamp is signed with the body, so rejecting old timestamps stops a captured, valid request from being replayed later.

ROTATION

Contact support to rotate a secret. While it rotates, both the old and new secret sign each request.

Check a request, step by step

What a correct handler does before it reads the payload.

1
Raw body, untouched
Sign the bytes exactly as received, not parsed and re-serialised JSON.
2
svix-timestamp in tolerance
Unix seconds, compared with your clock.
3
HMAC-SHA256 matches
Over {svix-id}.{svix-timestamp}.{body}, compared in constant time with each v1 signature.
Not checked yetVerify sample request
Guide: verify webhook signatures →
For your security review

What is documented, and what to ask us.

Security questionnaires go faster when both sides know where the facts are. Everything on the left is in the tinyRelay docs. Everything on the right, ask our team directly.

Documented today

In the docs
  • API key authentication in the X-RELAY-ACCESS-TOKEN header
  • Calling IP addresses allowlisted for API access
  • Webhooks signed with HMAC-SHA256 through Svix, one secret per endpoint
  • Webhooks sent from 3.229.12.181
  • At-least-once delivery, 24-hour duplicate suppression, 5-day payload retention for replay
  • Webhook secret rotation through support
  • Optional link wrapping with a tamper-proof token
  • DKIM signing with a CNAME on your domain
tinyRelay docs: setup and authentication →

Ask our team

Not published here
  • Compliance certifications, for example SOC 2 or ISO 27001Ask
  • Data processing agreement (DPA)Ask
  • Data residency and hosting regionsAsk
  • Retention of message content and logsAsk
  • API key rotation processAsk
  • Uptime commitments and status pageAsk
Ask our team

Related: how email webhooks are delivered, domain authentication and deliverability, and how onboarding works.

FAQ

Security questions.

If yours is not here, it is probably in the list above. Ask us.

Webhook signing docs →
How is the tinyRelay API authenticated?

With an API key sent in the X-RELAY-ACCESS-TOKEN header, issued at onboarding. Calls are also limited to the IP addresses you gave us, which are allowlisted.

Check the signature. Each request carries svix-id, svix-timestamp and svix-signature headers, and the signature is an HMAC-SHA256 over the ID, timestamp and raw body with your endpoint's secret. The sending IP, 3.229.12.181, is not proof on its own.

With X-Link-Wrapping: true, tracked links hide the destination inside an opaque, tamper-proof token instead of a readable redirectUrl parameter. That keeps destination URLs out of the message body, where blocklist scanners can read them.

We do not list compliance certifications, a DPA or data residency options on this site. Ask our team what is available for your security review.

Contact support. Rotation is not yet available through the API. During a rotation, requests are signed with both the old and the new secret, so accept a request if any listed signature verifies.

Get started

Send transactional email with a service that reports back.

SMTP relay or REST API, standalone or alongside tinyEmail. Tell us what you send and our team sets you up.