By default, all applications in a tenant share a single tenant-level key for signing ID tokens and access tokens. This simplifies key management, but some applications may require stricter isolation for security or compliance reasons.
To support these needs, Mosaic allows you to assign app-specific token signing keys. This enables each application to use its own signing key, leveraging standard OIDC and OAuth libraries. It ensures cryptographic isolation at the app level within the same tenant. Enable app-specific signing keys when you need:
- Key isolation between applications
- Separate key lifecycles per app
- Subdomain-based issuer separation in your architecture
- This feature is optional and must be explicitly enabled per app. When enabled, old keys are properly retired and revoked.
- It is fully backward compatible.
To enable app-specific token signing keys, in the app settings (Admin Portal > Applications > select app):
- Set a unique subdomain for the app based on the app and tenant name (e.g.,
acme-corporation.app.transmitsecurity.io). - Toggle in the Use app-specific token signing keys option.
Once configured, Mosaic provisions a dedicated signing key and manages its lifecycle.
Once enabled, all tokens from the app are signed with its dedicated key—no fallback to the tenant key.
When enabling app-specific token signing:
- Tokens previously signed with the global tenant key remain valid for ~14 days, until they expire naturally.
- Mosaic continues to serve both public keys during this period to support validation.
When disabling app-specific token signing, the admin can choose between:
- Immediately stop honoring tokens signed with the app-specific key.
- Continue honoring those tokens until they expire.
Make sure to include the correct region in your subdomain, depending on your tenant environment:
app— for production in the global/US region, e.g.acme-corporation.app.transmitsecurity.iosbx— for testing and development (sandbox), e.g.acme-corporation.app.sbx.transmitsecurity.ioeu— for production in the European Union, e.g.acme-corporation.app.eu.transmitsecurity.ioca— for production in Canada, e.g.acme-corporation.app.ca.transmitsecurity.io
Tokens issued by the app include:
- The app’s subdomain in the
iss(issuer) claim - A
kid(key ID) header referencing the correct key
Token validation libraries resolve the appropriate key automatically based on these fields.
The following decoded ID token illustrates how app-specific signing is reflected in the token structure:
Header:
{
"alg": "RS256",
"typ": "JWT",
"kid": "appkey-7f439c13"
}Payload:
{
"iss": "https://acme-corporation.app.transmitsecurity.io",
"sub": "user-12345",
"aud": "client-67890",
"exp": 1723588800,
"iat": 1723585200,
"auth_time": 1723585190,
"email": "user@example.com",
"name": "User Example"
}The relying party must validate the token using the correct public key, available at: https://acme-corporation.app.transmitsecurity.io/oidc/jwks. Standard JWT validation libraries can automatically select the correct key using the kid value from the token header.
When validating tokens signed with app-specific keys:
- Use the
issclaim to derive the JWKS endpoint (usually${iss}/oidc/jwks) - Select the correct public key using the
kidin the JWT header - Cache the JWKS response and respect its expiration headers to reduce overhead
- Implement fallback behavior for key rotation if your system enforces strict verification
You can also discover the correct JWKS URI dynamically from the jwks_uri field at: ${iss}/.well-known/openid-configuration
The following events are recorded in admin audit logs:
enableAppSpecificSigningKey: Token signing with an app-specific key was enableddisableAppSpecificSigningKey: Token signing with an app-specific key was disabled