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 24pxAccessibility 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
- Event Trigger: User action triggers email (e.g., password reset)
-
Template Selection: Keycloak selects appropriate
.ftltemplate -
Properties Loading: Loads
messages_en.propertiesfor text content - Variable Injection: Replaces placeholders with actual values
- HTML Generation: FreeMarker processes template to HTML
- 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 SetupCustomizing 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} TeamAdding 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 3GCollaboration 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-linksQA 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
- Navigate to your realm’s Branding page
- In the Custom Theme section, click “Download Theme”
- Save the ZIP file to your local machine
- Extract the ZIP file to a working directory
Step 2: Modify the Theme
Quick Text Changes (Most Common)
- Navigate to
email/messages/messages_en.properties - 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
- Edit HTML templates in
email/html/for structure changes - Modify CSS in
template.ftlfor styling - Add custom images or assets as needed
Step 3: Test Your Changes Locally (Optional)
-
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 Copy your theme to Keycloak’s theme directory
Select the theme in realm settings
Trigger test emails to verify changes
Step 4: Package Your Theme
- Ensure all files are in the correct structure
- Create a new ZIP file:
cd your-theme-directory zip -r custom-email-theme.zip email/ login/
Step 5: Upload to Skycloak
- Navigate to Branding → Custom Theme
- Click “Upload Theme”
- Select your modified ZIP file
- Wait for validation (usually takes 30 seconds)
- Click “Apply Branding” to deploy
Step 6: Verify Your Changes
- Trigger a test email (e.g., password reset)
- Check that all customizations are applied
- Test across different email clients
- Verify links and dynamic content work correctly
Best Practices
Message Properties Best Practices
- Keep Original Keys: Don’t delete default properties, just modify values
-
Escape Special Characters: Use
''for single quotes in messages -
Test Variables: Ensure all
{n}placeholders are preserved -
Use Line Continuations: For multi-line messages, use
\at line end -
Document Changes: Add comments to track customizations:
# CUSTOMIZED: Updated for ACME Corp branding emailVerificationSubject=Welcome to ACME - Verify Your Email
Template Best Practices
- Mobile Responsive: Always test on mobile devices
- Inline CSS: Use inline styles for better email client support
-
Fallback Values: Use
${variable!'default'}syntax - Image Hosting: Host images on reliable CDN
- Alt Text: Always include alt text for images
- Test Extensively: Test in multiple email clients (Gmail, Outlook, Apple Mail)
Security Considerations
- Sanitize Content: Never output user input without escaping
- Validate URLs: Ensure all links use HTTPS
- Avoid JavaScript: Most email clients block JavaScript
- 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 TeamBranded 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} TeamTroubleshooting
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:
\u00E9for é - 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
.ftlfiles
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
- Figma Email Templates: Email Design System
- Email Inspiration: Really Good Emails
- Accessibility Checker: WAVE
- Color Contrast: WebAIM Contrast Checker
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:
- Message Properties: The primary tool for text customization
- FreeMarker Templates: For structural and layout changes
- Download → Modify → Upload: Simple workflow for customizations
- Multi-language Support: Reach global audiences
- 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.