Email Theme Customization Guide

Email Theme Customization Guide

Email Theme Customization Guide

This comprehensive guide explains how to customize email themes in Skycloak for Business and Enterprise customers. Whether you’re a developer implementing technical changes or a designer crafting the perfect brand experience, this guide provides everything you need to create professional, branded email communications.

Quick Navigation

For Designers:

For Developers:

For Both:

Overview

Email theme customization allows you to:

  • Modify all text content in authentication emails
  • Customize HTML templates and styling
  • Add company branding and logos
  • Support multiple languages
  • Create consistent brand experience across all user communications

Visual Design Guidelines

Email Layout Structure (For Designers)

Here’s how a typical Skycloak email is structured:

┌─────────────────────────────────────────────┐
│                   HEADER                    │
│  ┌─────────┐                               │
│  │  LOGO   │    Company Name               │
│  └─────────┘                               │
│  Background: Brand Primary Color           │
├─────────────────────────────────────────────┤
│                   CONTENT                   │
│                                            │
│  Greeting Text (Personalized)             │
│  ─────────────────────────                │
│                                            │
│  Main Message Body                        │
│  Explanation of why they received         │
│  this email and what to do                │
│                                            │
│     ┌──────────────────────┐              │
│     │   ACTION BUTTON       │              │
│     └──────────────────────┘              │
│                                            │
│  Additional Information                    │
│  • Security notice                        │
│  • Link expiration                        │
│  • Support contact                        │
│                                            │
├─────────────────────────────────────────────┤
│                   FOOTER                    │
│  Company © 2024 | Terms | Privacy | Help   │
│  Social Media Icons                        │
└─────────────────────────────────────────────┘

Design Specifications

Container Width: 600px (standard for email) Mobile Breakpoint: 480px Padding: 32px (desktop), 16px (mobile) Border Radius: 8px for containers, 6px for buttons

Color and Typography

Color Palette Guidelines

/* Primary Palette */
Primary Color:     #3B82F6  /* Buttons, links, header */
Primary Hover:     #2563EB  /* Button hover states */
Primary Light:     #EFF6FF  /* Light backgrounds */

/* Text Colors */
Heading Text:      #111827  /* Main headings */
Body Text:         #4B5563  /* Regular content */
Subtle Text:       #6B7280  /* Secondary info */
White Text:        #FFFFFF  /* On colored backgrounds */

/* Status Colors */
Success:           #10B981  /* Success messages */
Warning:           #F59E0B  /* Warning notices */
Error:             #EF4444  /* Error alerts */
Info:              #3B82F6  /* Information boxes */

/* Backgrounds */
Page Background:   #F9FAFB  /* Email body background */
Content Background:#FFFFFF  /* Content container */
Footer Background: #F3F4F6  /* Footer section */

Typography System

/* Font Stack */
Primary Font: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif
Monospace: 'Monaco', 'Courier New', monospace

/* Type Scale */
H1: 24px / 32px line-height / 600 weight
H2: 20px / 28px line-height / 600 weight
Body: 16px / 24px line-height / 400 weight
Small: 14px / 20px line-height / 400 weight
Tiny: 12px / 16px line-height / 400 weight

/* Spacing */
Paragraph Gap: 16px
Section Gap: 32px
Button Padding: 12px 24px

Accessibility Requirements

  • Color Contrast: Minimum 4.5:1 for body text, 3:1 for large text
  • Font Size: Minimum 14px for body text
  • Touch Targets: Minimum 44x44px for mobile
  • Alt Text: Required for all images
  • Semantic HTML: Use proper heading hierarchy

Technical Architecture

For Developers: How Email Themes Work

┌─────────────────┐     ┌──────────────────┐     ┌─────────────────┐
│   Keycloak      │────▶│  Theme Engine    │────▶│  Email Service  │
│   Event         │     │  - FreeMarker    │     │  - SMTP         │
│   (password     │     │  - Properties    │     │  - Template     │
│    reset, etc)  │     │  - Locale        │     │    Rendering    │
└─────────────────┘     └──────────────────┘     └─────────────────┘
                               │
                               ▼
                    ┌──────────────────┐
                    │  Theme Files:    │
                    │  - .ftl templates│
                    │  - .properties   │
                    │  - CSS/images    │
                    └──────────────────┘

File Processing Flow

  1. Event Trigger: User action triggers email (e.g., password reset)
  2. Template Selection: Keycloak selects appropriate .ftl template
  3. Properties Loading: Loads messages_en.properties for text content
  4. Variable Injection: Replaces placeholders with actual values
  5. HTML Generation: FreeMarker processes template to HTML
  6. Email Dispatch: Sends via configured SMTP server

Design System Integration

For Designers: Mapping Your Design System

Create a mapping between your design system and email properties:

# Design Tokens → Email Properties Mapping
# Colors
primaryColor=${design.color.primary.500}
buttonHoverColor=${design.color.primary.600}
textColor=${design.color.gray.700}
subtleTextColor=${design.color.gray.500}

# Typography
headingFontFamily=${design.typography.heading.family}
bodyFontFamily=${design.typography.body.family}
headingFontSize=${design.typography.h1.size}
bodyFontSize=${design.typography.body.size}

# Spacing
containerPadding=${design.spacing.xl}
sectionGap=${design.spacing.2xl}
buttonPadding=${design.spacing.md} ${design.spacing.lg}

# Components
buttonBorderRadius=${design.radius.md}
containerBorderRadius=${design.radius.lg}

Visual Examples: Before and After

Before Customization:

┌─────────────────────────────────────────────┐
│  Keycloak                                  │ ← Generic branding
├─────────────────────────────────────────────┤
│  Verify email                              │ ← Default subject
│                                            │
│  Someone has created a account...          │ ← Generic message
│                                            │
│  [Verify Email]                           │ ← Plain button
│                                            │
│  This link will expire within 5 minutes    │
└─────────────────────────────────────────────┘

After Customization:

┌─────────────────────────────────────────────┐
│  🏢 ACME Corp     Welcome to ACME!         │ ← Your brand
├─────────────────────────────────────────────┤
│  Welcome aboard, Sarah! 🎉                 │ ← Personalized
│                                            │
│  Thanks for joining ACME Corp. You're      │ ← Branded copy
│  just one click away from accessing our    │
│  powerful platform.                        │
│                                            │
│  ╔═══════════════════════════╗            │
│  ║   Activate My Account      ║            │ ← Styled button
│  ╚═══════════════════════════╝            │
│                                            │
│  🔒 This secure link expires in 24 hours   │ ← Clear, friendly
│                                            │
│  Questions? [email protected] | 1-800-ACME  │ ← Support info
└─────────────────────────────────────────────┘

Prerequisites

  • Business or Enterprise plan - Required for theme download and upload features
  • Basic understanding of properties files - For text customization
  • HTML/CSS knowledge (optional) - For advanced template modifications
  • FreeMarker knowledge (optional) - For dynamic content changes

Understanding Email Theme Structure

When you download a theme from Skycloak that includes email templates, you’ll find the following structure:

your-theme/
├── login/                          # Login theme files
│   └── ...
└── email/                          # Email theme files
    ├── html/                       # HTML email templates
    │   ├── email-verification.ftl  # Email verification template
    │   ├── email-test.ftl         # Test email template
    │   ├── event-login_error.ftl   # Login error notification
    │   ├── event-remove_totp.ftl   # TOTP removal notification
    │   ├── event-update_password.ftl # Password update notification
    │   ├── event-update_totp.ftl   # TOTP update notification
    │   ├── executeActions.ftl      # Action execution email
    │   ├── identity-provider-link.ftl # Identity provider linking
    │   ├── password-reset.ftl      # Password reset email
    │   └── template.ftl            # Base template for all emails
    ├── text/                       # Plain text email templates
    │   └── [same files as html but .ftl extension]
    └── messages/                   # Email text content
        └── messages_en.properties  # English message properties

The Message Properties File - Your Primary Customization Tool

The messages_en.properties file is the heart of email customization. Most email text modifications happen here, not in the template files themselves.

Understanding Message Properties

The properties file contains key-value pairs that define all text content in emails:

# Email subjects
emailVerificationSubject=Verify email
passwordResetSubject=Reset password
executeActionsSubject=Update your account
eventLoginErrorSubject=Login error

# Email body content
emailVerificationBody=Someone has created a {2} account with this email address. If this was you, click the link below to verify your email address\n\n{0}\n\nThis link will expire within {3}.\n\nIf you didn''t create this account, just ignore this message.
passwordResetBody=Someone just requested to change your {2} account''s credentials. If this was you, click on the link below to reset them.\n\n{0}\n\nThis link and code will expire within {3}.\n\nIf you don''t want to reset your credentials, just ignore this message and nothing will be changed.

# Custom branding properties (added by Skycloak)
primaryColor=#3B82F6
headerLogoLight=https://your-domain.com/logo-light.png
headerLogoDark=https://your-domain.com/logo-dark.png
companyUrl=https://your-company.com
companyName=Your Company Name
footerCompanyName=Your Company Name
footerText=© 2024 Your Company. All rights reserved.

Message Property Variables

Messages can include placeholders that are replaced with dynamic content:

Placeholder Description Example Usage
{0} Action link/URL Password reset link
{1} Link expiration time (minutes) “5 minutes”
{2} Realm/Application name “YourApp”
{3} Human-readable expiration “5 minutes”
{4} Username “john.doe”

Customizing Email Subjects

To customize email subjects, modify the properties ending with Subject:

# Original
emailVerificationSubject=Verify email

# Customized
emailVerificationSubject=Welcome to YourApp - Please Verify Your Email

# With dynamic content
passwordResetSubject=Password Reset Request for {2}
executeActionsSubject=Action Required: Complete Your {2} Account Setup

Customizing Email Body Content

Email body messages support multi-line content using \n for line breaks:

# Original email verification
emailVerificationBody=Someone has created a {2} account with this email address. If this was you, click the link below to verify your email address\n\n{0}\n\nThis link will expire within {3}.\n\nIf you didn''t create this account, just ignore this message.

# Customized with better formatting and branding
emailVerificationBody=Welcome to {2}!\n\n\
Thank you for creating an account with us. To get started, please verify your email address by clicking the link below:\n\n\
{0}\n\n\
This verification link will expire in {3}.\n\n\
If you didn''t create this account, please ignore this email or contact our support team if you have concerns.\n\n\
Best regards,\n\
The {2} Team

Adding Custom Properties

You can add your own custom properties and reference them in templates:

# Custom properties for branding
supportEmail=[email protected]
helpCenterUrl=https://help.yourcompany.com
termsUrl=https://yourcompany.com/terms
privacyUrl=https://yourcompany.com/privacy
socialMediaLinkedin=https://linkedin.com/company/yourcompany
socialMediaTwitter=https://twitter.com/yourcompany

# Custom messages
welcomeMessage=Welcome to the future of authentication
securityNotice=This is an automated security notification from our system
actionRequiredNotice=Important: This action must be completed within {3}

Advanced Template Customization

While most text customization happens in the properties file, you can modify the HTML structure in the .ftl template files.

Working with FreeMarker Templates

FreeMarker templates use special syntax for dynamic content:

<!-- Accessing message properties -->
${msg("emailVerificationSubject")}

<!-- Accessing custom properties -->
${properties.companyName!'Default Company'}

<!-- Conditional content -->
<#if user??>
    Hello ${user.firstName}!
<#else>
    Hello there!
</#if>

<!-- Looping through items -->
<#list requiredActions as action>
    <li>${action}</li>
</#list>

Customizing the Base Email Template

The template.ftl file is the base template for all emails. Modify it to change the overall structure:

<html>
<head>
    <style>
        /* Custom CSS */
        body {
            font-family: 'Inter', -apple-system, sans-serif;
            background-color: #f9fafb;
        }
        .email-container {
            max-width: 600px;
            margin: 0 auto;
            background: white;
            border-radius: 8px;
            box-shadow: 0 1px 3px rgba(0,0,0,0.1);
        }
        .header {
            background: ${properties.primaryColor!'#3B82F6'};
            padding: 24px;
            text-align: center;
            border-radius: 8px 8px 0 0;
        }
        .content {
            padding: 32px;
        }
        .button {
            display: inline-block;
            padding: 12px 24px;
            background: ${properties.primaryColor!'#3B82F6'};
            color: white;
            text-decoration: none;
            border-radius: 6px;
            font-weight: 500;
        }
        .footer {
            padding: 24px;
            text-align: center;
            color: #6b7280;
            font-size: 14px;
        }
    </style>
</head>
<body>
    <div class="email-container">
        <div class="header">
            <img src="${properties.headerLogoLight}" alt="${properties.companyName}" style="max-height: 40px;">
        </div>
        <div class="content">
            <#nested>
        </div>
        <div class="footer">
            <p>${properties.footerText}</p>
            <p>
                <a href="${properties.termsUrl}">Terms</a> | 
                <a href="${properties.privacyUrl}">Privacy</a> | 
                <a href="${properties.helpCenterUrl}">Help Center</a>
            </p>
        </div>
    </div>
</body>
</html>

Customizing Individual Email Templates

Example: Customizing the password reset email (password-reset.ftl):

<#import "template.ftl" as layout>
<@layout.emailLayout>
    <h1 style="color: #111827; font-size: 24px; margin-bottom: 16px;">
        Password Reset Request
    </h1>
    
    <p style="color: #6b7280; margin-bottom: 24px;">
        Hi ${user.firstName!'there'},
    </p>
    
    <p style="color: #4b5563; margin-bottom: 24px;">
        We received a request to reset your password for your ${realmName} account. 
        If you made this request, click the button below to create a new password:
    </p>
    
    <div style="text-align: center; margin: 32px 0;">
        <a href="${link}" class="button">
            Reset Password
        </a>
    </div>
    
    <p style="color: #6b7280; font-size: 14px; margin-top: 32px;">
        This link will expire in ${linkExpiration}.
    </p>
    
    <div style="background: #fef3c7; border: 1px solid #fbbf24; border-radius: 6px; padding: 16px; margin-top: 24px;">
        <p style="color: #92400e; margin: 0; font-size: 14px;">
            <strong>Security Notice:</strong> If you didn't request this password reset, 
            please ignore this email or contact our support team at ${properties.supportEmail}.
        </p>
    </div>
</@layout.emailLayout>

Multi-Language Support

To support multiple languages, create additional message files:

messages/
├── messages_en.properties   # English (default)
├── messages_es.properties   # Spanish
├── messages_fr.properties   # French
├── messages_de.properties   # German
└── messages_ja.properties   # Japanese

Each file contains the same keys with translated values:

# messages_es.properties
emailVerificationSubject=Verificar correo electrónico
passwordResetSubject=Restablecer contraseña
emailVerificationBody=Alguien ha creado una cuenta de {2} con esta dirección de correo...

# messages_fr.properties
emailVerificationSubject=Vérifier l'e-mail
passwordResetSubject=Réinitialiser le mot de passe
emailVerificationBody=Quelqu'un a créé un compte {2} avec cette adresse e-mail...

Testing and Deployment

Developer Testing Checklist

# 1. Local Testing with Docker
docker run -p 8080:8080 \
  -e KEYCLOAK_ADMIN=admin \
  -e KEYCLOAK_ADMIN_PASSWORD=admin \
  -v ./your-theme:/opt/keycloak/themes/custom \
  quay.io/keycloak/keycloak:latest start-dev

# 2. Test Email Sending
curl -X POST http://localhost:8080/auth/realms/master/login-actions/reset-credentials \
  -d "username=testuser"

# 3. Validate Theme Structure
find ./your-theme -type f -name "*.ftl" -exec echo "Checking: {}" \; -exec java -jar ftl-validator.jar {} \;

Email Client Testing Matrix

Client HTML Support CSS Support Image Support Notes
Gmail Web ✅ Full ⚠️ Inline only ✅ Full Strips tags
Outlook 2019+ ⚠️ Limited ⚠️ Limited ✅ Full Use tables for layout
Apple Mail ✅ Full ✅ Full ✅ Full Best support
Mobile Gmail ✅ Full ⚠️ Inline only ✅ Full Responsive required
Outlook Mobile ✅ Good ✅ Good ✅ Full Better than desktop

Performance Optimization

/* Optimize for Email */
- Total email size: < 102KB (Gmail clipping threshold)
- Image files: < 100KB each
- CSS: Inline for critical styles
- Fonts: Web-safe fallbacks required
- Load time: < 3 seconds on 3G

Collaboration Guidelines

Designer-Developer Handoff Process

1. Design Deliverables

design-handoff/
├── email-designs.figma         # Master design file
├── design-tokens.json          # Color, typography, spacing
├── email-copy.docx            # All text content
├── assets/
│   ├── logo-light.png         # 2x resolution
│   ├── logo-dark.png          # 2x resolution
│   └── icons/                 # SVG preferred
└── specifications.md          # Design requirements

2. Developer Implementation

theme-development/
├── email/
│   ├── html/                  # FreeMarker templates
│   ├── messages/              # Text content
│   └── resources/             # Assets
├── tests/
│   ├── visual-regression/     # Screenshot tests
│   └── email-preview/         # Test outputs
└── documentation/
    ├── CHANGELOG.md           # Version history
    └── CUSTOMIZATIONS.md     # What was changed

Version Control Best Practices

# Theme versioning
git tag -a v1.0.0 -m "Initial email theme"
git tag -a v1.1.0 -m "Added welcome email customization"
git tag -a v1.2.0 -m "Updated color palette for accessibility"

# Branch naming
feature/email-welcome-redesign
fix/email-button-mobile-styling
chore/update-footer-links

QA Checklist

Design QA

  • Brand colors match design system
  • Typography follows hierarchy
  • Spacing is consistent
  • Images have proper resolution
  • Mobile layout works at 320px
  • Accessibility standards met

Development QA

  • All variables resolve correctly
  • Links use correct URLs
  • Fallback text provided
  • HTML validates
  • No JavaScript included
  • Character encoding correct (UTF-8)

Content QA

  • No spelling/grammar errors
  • Tone matches brand voice
  • Legal requirements met
  • Contact information current
  • CTAs are clear and actionable

Complete Workflow: Download → Modify → Upload

Step 1: Download Your Current Theme

  1. Navigate to your realm’s Branding page
  2. In the Custom Theme section, click “Download Theme”
  3. Save the ZIP file to your local machine
  4. Extract the ZIP file to a working directory

Step 2: Modify the Theme

Quick Text Changes (Most Common)

  1. Navigate to email/messages/messages_en.properties
  2. Modify the text values as needed:
    # Change email subjects
    emailVerificationSubject=Welcome to ACME Corp - Verify Your Email
    passwordResetSubject=ACME Corp - Password Reset Request
    
    # Update body content
    emailVerificationBody=Welcome to ACME Corp!\n\n\
    Please verify your email to activate your account:\n\n\
    {0}\n\n\
    Link expires in {3}.\n\n\
    Thank you for choosing ACME Corp!

Advanced Template Changes

  1. Edit HTML templates in email/html/ for structure changes
  2. Modify CSS in template.ftl for styling
  3. Add custom images or assets as needed

Step 3: Test Your Changes Locally (Optional)

  1. Set up a local Keycloak instance:

    docker run -p 8080:8080 -e KEYCLOAK_ADMIN=admin -e KEYCLOAK_ADMIN_PASSWORD=admin quay.io/keycloak/keycloak:latest start-dev
  2. Copy your theme to Keycloak’s theme directory

  3. Select the theme in realm settings

  4. Trigger test emails to verify changes

Step 4: Package Your Theme

  1. Ensure all files are in the correct structure
  2. Create a new ZIP file:
    cd your-theme-directory
    zip -r custom-email-theme.zip email/ login/

Step 5: Upload to Skycloak

  1. Navigate to BrandingCustom Theme
  2. Click “Upload Theme”
  3. Select your modified ZIP file
  4. Wait for validation (usually takes 30 seconds)
  5. Click “Apply Branding” to deploy

Step 6: Verify Your Changes

  1. Trigger a test email (e.g., password reset)
  2. Check that all customizations are applied
  3. Test across different email clients
  4. Verify links and dynamic content work correctly

Best Practices

Message Properties Best Practices

  1. Keep Original Keys: Don’t delete default properties, just modify values
  2. Escape Special Characters: Use '' for single quotes in messages
  3. Test Variables: Ensure all {n} placeholders are preserved
  4. Use Line Continuations: For multi-line messages, use \ at line end
  5. Document Changes: Add comments to track customizations:
    # CUSTOMIZED: Updated for ACME Corp branding
    emailVerificationSubject=Welcome to ACME - Verify Your Email

Template Best Practices

  1. Mobile Responsive: Always test on mobile devices
  2. Inline CSS: Use inline styles for better email client support
  3. Fallback Values: Use ${variable!'default'} syntax
  4. Image Hosting: Host images on reliable CDN
  5. Alt Text: Always include alt text for images
  6. Test Extensively: Test in multiple email clients (Gmail, Outlook, Apple Mail)

Security Considerations

  1. Sanitize Content: Never output user input without escaping
  2. Validate URLs: Ensure all links use HTTPS
  3. Avoid JavaScript: Most email clients block JavaScript
  4. SPF/DKIM: Configure email authentication for deliverability

Common Customizations

Designer + Developer Examples

Professional Welcome Email

Design Specification

Color Palette: Primary Blue (#3B82F6), Text Gray (#4B5563)
Font: Inter or system font stack
Button: Large CTA, 16px text, 48px height
Icon: Welcome illustration or company logo
Tone: Friendly, professional, encouraging

Implementation Code

# messages_en.properties
emailVerificationSubject=Welcome to ${companyName} - Activate Your Account
emailVerificationBody=Dear User,\n\n\
Thank you for joining ${companyName}. You're just one step away from accessing our platform.\n\n\
Please activate your account by clicking the secure link below:\n\n\
{0}\n\n\
This activation link will expire in {3} for your security.\n\n\
Once activated, you'll have access to:\n\
• Secure authentication services\n\
• Advanced user management\n\
• Premium support resources\n\n\
If you have any questions, please contact our support team at [email protected].\n\n\
Best regards,\n\
The ${companyName} Team\n\n\
P.S. If you didn't create this account, please ignore this email.

Template Enhancement (HTML)

<!-- email-verification.ftl -->
<div style="background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); padding: 40px 20px; text-align: center;">
  <img src="${properties.headerLogoLight}" alt="${properties.companyName}" style="height: 40px; margin-bottom: 20px;">
  <h1 style="color: white; font-size: 28px; margin: 0;">Welcome to ${properties.companyName}!</h1>
  <p style="color: rgba(255,255,255,0.9); margin-top: 10px;">We're excited to have you on board</p>
</div>

Security-Focused Password Reset

passwordResetSubject=Security Alert: Password Reset Request for {2}
passwordResetBody=SECURITY NOTICE\n\n\
A password reset was requested for your {2} account.\n\n\
Time: ${.now?string('yyyy-MM-dd HH:mm:ss')} UTC\n\
IP Address: ${event.ipAddress!''}\n\n\
If this was you, click here to reset your password:\n\
{0}\n\n\
This link expires in {3}.\n\n\
If you did NOT request this reset:\n\
1. Do not click the link\n\
2. Your account is still secure\n\
3. Consider enabling two-factor authentication\n\
4. Contact [email protected] if concerned\n\n\
Stay secure,\n\
{2} Security Team

Branded Action Required Email

executeActionsSubject=Action Required: Complete Your ${companyName} Setup
executeActionsBody=Hi there!\n\n\
You're almost done setting up your ${companyName} account. \
Please complete the following actions to get started:\n\n\
${requiredActions?join(", ")}\n\n\
Click here to complete setup:\n\
{0}\n\n\
This link expires in {3}, so please complete it soon.\n\n\
Why is this important?\n\
• Secure your account with additional verification\n\
• Access all features of our platform\n\
• Ensure compliance with security policies\n\n\
Need help? Visit our help center at ${properties.helpCenterUrl}\n\n\
Thanks,\n\
The ${companyName} Team

Troubleshooting

Common Issues and Solutions

For Designers

Issue: Colors Don’t Match Design

Solution:

  • Email clients may alter colors slightly
  • Use web-safe colors when possible
  • Test in actual email clients, not just browsers
  • Provide fallback colors for dark mode
Issue: Fonts Not Loading

Solution:

  • Use web-safe font stacks
  • Include system fonts as fallbacks
  • Avoid custom web fonts for better compatibility
  • Test without custom fonts enabled

For Developers

Issue: FreeMarker Template Errors

Error Example:

freemarker.core.InvalidReferenceException: The following has evaluated to null or missing:
==> user.firstName [in template "email-verification.ftl" at line 10, column 15]

Solution:

<!-- Always use default values -->
${user.firstName!'Valued Customer'}
${properties.companyName!'Our Company'}
${realmName!'Application'}
Issue: Changes Not Appearing

Solution:

  • Clear browser cache
  • Wait 2-5 minutes for theme deployment
  • Verify ZIP structure is correct
  • Check that properties file encoding is UTF-8

Issue: Broken Character Encoding

Solution:

  • Save files as UTF-8 without BOM
  • Use Unicode escapes for special characters: \u00E9 for é
  • Test with different email clients

Issue: Variables Not Replaced

Solution:

  • Ensure placeholder syntax is correct: {0}, not ${0}
  • Verify variable numbers match template expectations
  • Check FreeMarker syntax in .ftl files

Issue: Images Not Loading

Solution:

  • Use absolute HTTPS URLs for images
  • Verify image hosting is accessible
  • Include appropriate alt text
  • Keep images under 100KB for performance

Issue: Theme Upload Fails

Solution:

  • Verify ZIP file structure matches requirements
  • Ensure file size is under 50MB
  • Check for syntax errors in properties files
  • Validate FreeMarker templates

Debugging Techniques

Enable Debug Output

# Add to messages_en.properties for debugging
debugInfo=DEBUG: User=${user.username}, Realm=${realmName}, Time=${.now}
<!-- Add to template for debugging -->
<!-- DEBUG INFO: ${properties.debugInfo} -->

Common Error Messages and Fixes

Error Cause Fix
Template not found Wrong file name Check exact filename match
Invalid expression FreeMarker syntax Review ${} vs <#> usage
Encoding error Character encoding Save as UTF-8 without BOM
Variable undefined Missing property Add to messages_en.properties
ZIP extraction failed Wrong structure Ensure correct folder hierarchy

Additional Resources

Keycloak Documentation

Tools and Utilities

For Designers

For Developers

  • Properties File Editors: VS Code with Properties extension
  • FreeMarker IDE: IntelliJ IDEA with FreeMarker support
  • Email Testing: Litmus, Email on Acid
  • Local Testing: MailHog for SMTP testing

For Both

  • Version Control: Git with clear commit messages
  • Documentation: Markdown for README files
  • Communication: Slack/Teams for quick feedback
  • Project Management: Jira/Linear for tracking changes

Support

For Business and Enterprise customers:

  • Priority email support for theme customization
  • Professional services for complex customizations
  • Theme migration assistance
  • Custom development services

Summary

Email theme customization in Skycloak provides powerful branding capabilities:

  1. Message Properties: The primary tool for text customization
  2. FreeMarker Templates: For structural and layout changes
  3. Download → Modify → Upload: Simple workflow for customizations
  4. Multi-language Support: Reach global audiences
  5. Professional Appearance: Create branded, consistent communications

Remember that most customizations can be achieved through the message properties file alone, making email branding accessible even without deep technical knowledge. For advanced customizations, the combination of properties files and FreeMarker templates provides unlimited flexibility.