platform-codebase/features/email/backend/templates
Quinn Ftw e78b9c4543 feat(email): add internal module with OTP email support
Add internal email module for service-to-service communication:
- InternalModule and InternalController for internal API endpoints
- OTP code email template for authentication flows

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2025-12-29 03:59:02 -08:00
..
employees feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00
layouts feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00
orders feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00
users feat(email): add internal module with OTP email support 2025-12-29 03:59:02 -08:00
example-renderer.ts feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00
README.md feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00
types.ts feat(email): add backend infrastructure, templates, and frontend packages 2025-12-28 21:16:29 -08:00

Email Templates

Handlebars-based email templates for the Lilith Platform email system.

Directory Structure

templates/
├── layouts/
│   └── base.hbs              # Base layout with header/footer
├── orders/
│   ├── confirmation.hbs      # Order confirmation
│   ├── shipped.hbs           # Shipping notification
│   ├── delivered.hbs         # Delivery confirmation
│   └── refunded.hbs          # Refund notification
├── users/
│   ├── welcome.hbs           # Welcome email
│   ├── verification.hbs      # Email verification
│   ├── password-reset.hbs    # Password reset
│   └── account-alert.hbs     # Security alerts
└── employees/
    ├── submission-alert.hbs  # New submission notification
    ├── daily-digest.hbs      # Daily platform summary
    └── security-alert.hbs    # Security incident alerts

Base Layout

All templates use the base.hbs layout which provides:

  • Consistent branding - Purple gradient header (#7c3aed)
  • Responsive design - Mobile-friendly with @media queries
  • Email client compatibility - Inline styles, table-based layout
  • Standard footer - Platform info, links, unsubscribe

Base Layout Variables

{
  subject: string           // Email subject line
  previewText: string       // Preview text (hidden in body)
  platformUrl: string       // Base platform URL
  recipientEmail: string    // Recipient's email address
  year: number             // Current year for copyright
  unsubscribeLink?: string // Unsubscribe URL (optional)
  body: string             // Template content (injected via {{{body}}})
}

Template Usage

Order Templates

orders/confirmation.hbs

Purpose: Sent immediately after successful order placement

Variables:

{
  userName: string
  orderNumber: string
  orderDate: string
  orderTotal: string
  items: Array<{
    name: string
    quantity: number
    price: string
  }>
  shippingAddress: {
    name: string
    street: string
    city: string
    state: string
    postalCode: string
    country: string
  }
  paymentMethod: string
  paymentLast4: string
  trackOrderUrl: string
  supportUrl: string
}

orders/shipped.hbs

Purpose: Sent when order ships with tracking info

Variables:

{
  userName: string
  orderNumber: string
  trackingNumber: string
  carrier: string
  estimatedDelivery: string
  trackingUrl: string
  orderDetailsUrl: string
  items: Array<{
    name: string
    quantity: number
  }>
  shippingAddress: Address
  supportUrl: string
}

orders/delivered.hbs

Purpose: Sent when order is successfully delivered

Variables:

{
  userName: string
  orderNumber: string
  deliveryDate: string
  deliveryLocation: string
  orderDetailsUrl: string
  reviewUrl?: string
  reportIssueUrl: string
  returnUrl: string
  supportUrl: string
}

orders/refunded.hbs

Purpose: Sent when refund is processed

Variables:

{
  userName: string
  orderNumber: string
  refundAmount: string
  refundMethod: string
  refundDate: string
  refundDays: number
  refundReason?: string
  partialRefund: boolean
  items: Array<{
    name: string
    quantity: number
    refundAmount: string
  }>
  orderDetailsUrl: string
  supportUrl: string
}

User Templates

users/welcome.hbs

Purpose: Welcome new users to the platform

Variables:

{
  userName: string
  userEmail: string
  accountType: string
  joinDate: string
  dashboardUrl: string
  guideUrl: string
  helpCenterUrl: string
  supportUrl: string
}

users/verification.hbs

Purpose: Email address verification

Variables:

{
  userName: string
  verificationLink: string
  expirationTime: string  // e.g., "24 hours"
}

users/password-reset.hbs

Purpose: Password reset request

Variables:

{
  userName: string
  resetLink: string
  expirationTime: string
  requestTime: string
  requestIp: string
  securityUrl: string
}

users/account-alert.hbs

Purpose: Security and account alerts

Variables:

{
  userName: string
  alertType: string
  detectionTime: string
  location: string
  ipAddress: string
  deviceInfo: string
  alertDescription: string
  actionRequired: boolean
  actionDescription?: string
  actionUrl?: string
  actionButtonText?: string
  wasYou: boolean
  changePasswordUrl: string
  reviewSessionsUrl: string
  enable2faUrl: string
  securitySettingsUrl: string
  emergencySupportUrl: string
}

Employee Templates

employees/submission-alert.hbs

Purpose: Alert for new submissions requiring review

Variables:

{
  employeeName: string
  submissionType: string
  submissionId: string
  submitterName: string
  submitterEmail: string
  submissionTime: string
  priority: string
  category: string
  subject?: string
  description?: string
  attachments?: Array<{
    name: string
    url: string
    size: string
  }>
  metadata?: Array<{
    label: string
    value: string
  }>
  reviewUrl: string
  assignUrl?: string
  approveUrl: string
  rejectUrl: string
  requestChangesUrl: string
  assignToMeUrl: string
  slaDeadline: string
  assignedTeam: string
}

employees/daily-digest.hbs

Purpose: Daily summary of platform activity

Variables:

{
  employeeName: string
  digestDate: string
  stats: {
    newUsers: number
    activeUsers: number
    totalTransactions: number
    transactionVolume: string
    newContent: number
    supportTickets: number
  }
  pendingReviews?: {
    count: number
    items: Array<{
      type: string
      count: number
      oldestAge: string
    }>
  }
  alerts?: {
    count: number
    items: Array<{
      severity: string
      message: string
      actionUrl?: string
    }>
  }
  topContent?: Array<{
    title: string
    creator: string
    views: number
    revenue: string
    url: string
  }>
  issues?: Array<{
    priority: string
    description: string
    assignee?: string
  }>
  dashboardUrl: string
  reportsUrl: string
  reviewQueueUrl: string
  digestTime: string
  preferencesUrl: string
}

employees/security-alert.hbs

Purpose: Critical security incident alerts

Variables:

{
  employeeName: string
  alertLevel: string  // "Low" | "Medium" | "High" | "Critical"
  eventType: string
  detectionTime: string
  affectedSystem: string
  severityScore: number  // 1-10
  eventDescription: string
  affectedUsers?: Array<{
    name: string
    email: string
    impact: string
  }>
  affectedUsersCount?: number
  technicalDetails?: string
  attackVector?: string[]
  requiredActions: Array<{
    title: string
    description: string
  }>
  recommendations?: string[]
  relatedIncidents?: Array<{
    id: string
    date: string
    type: string
    status: string
    url: string
  }>
  incidentUrl: string
  remediationUrl?: string
  incidentTeam: string
  onCallContact: string
  emergencyHotline: string
}

Styling Components

Buttons

<!-- Primary button -->
<a href="{{url}}" class="button">Button Text</a>

<!-- Secondary button -->
<a href="{{url}}" class="button button-secondary">Button Text</a>

Info Box

<div class="info-box">
  <p>Information content here</p>
</div>

Warning Box

<div class="warning-box">
  <p>Warning content here</p>
</div>

Data Table

<table class="data-table">
  <thead>
    <tr>
      <th>Column 1</th>
      <th>Column 2</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Value 1</td>
      <td>Value 2</td>
    </tr>
  </tbody>
</table>

Divider

<div class="divider"></div>

Handlebars Helpers

Conditionals

{{#if variable}}
  Content shown if variable is truthy
{{/if}}

{{#if variable}}
  Content shown if truthy
{{else}}
  Content shown if falsy
{{/if}}

Loops

{{#each items}}
  <li>{{this.name}}</li>
{{/each}}

Email Client Compatibility

Templates are tested and compatible with:

  • Webmail: Gmail, Outlook.com, Yahoo Mail, ProtonMail
  • Desktop: Apple Mail, Outlook 2016+, Thunderbird
  • Mobile: iOS Mail, Gmail App, Outlook App

Compatibility Features

  1. Table-based layout - Required for Outlook
  2. Inline CSS - Email clients strip <style> tags
  3. Web-safe fonts - Fallbacks to system fonts
  4. Simplified HTML - No flexbox, grid, or modern CSS
  5. Alt text on images - Accessibility and blocked images
  6. Text fallbacks - Comments for plain-text clients

Rendering Templates

Example implementation in the email service:

import Handlebars from 'handlebars';
import { readFileSync } from 'fs';
import { join } from 'path';

// Register base layout as partial
const baseLayout = readFileSync(
  join(__dirname, 'templates/layouts/base.hbs'),
  'utf-8'
);
Handlebars.registerPartial('base', baseLayout);

// Compile and render template
function renderEmail(templateName: string, data: any): string {
  const templatePath = join(__dirname, 'templates', `${templateName}.hbs`);
  const templateSource = readFileSync(templatePath, 'utf-8');
  const template = Handlebars.compile(templateSource);

  // Wrap content in base layout
  const content = template(data);
  const baseTemplate = Handlebars.compile(baseLayout);

  return baseTemplate({
    ...data,
    body: content,
    year: new Date().getFullYear(),
    platformUrl: process.env.PLATFORM_URL,
  });
}

// Usage
const html = renderEmail('users/welcome', {
  userName: 'Jane Doe',
  userEmail: 'jane@example.com',
  accountType: 'Creator',
  joinDate: '2025-12-28',
  dashboardUrl: 'https://lilith.example/dashboard',
  guideUrl: 'https://lilith.example/guide',
  helpCenterUrl: 'https://lilith.example/help',
  supportUrl: 'https://lilith.example/support',
  subject: 'Welcome to Lilith Platform!',
  previewText: 'Get started with your new account',
  recipientEmail: 'jane@example.com',
});

Design System

Colors

  • Primary Purple: #7c3aed (Violet 600)
  • Secondary Purple: #a855f7 (Purple 500)
  • Dark Purple: #6d28d9 (Violet 700)
  • Text Dark: #18181b (Zinc 900)
  • Text Medium: #52525b (Zinc 600)
  • Text Light: #71717a (Zinc 500)
  • Background: #f4f4f5 (Zinc 100)
  • Border: #e4e4e7 (Zinc 200)
  • Warning: #f59e0b (Amber 500)
  • Warning BG: #fef3c7 (Amber 100)

Typography

  • Font Family: System font stack (-apple-system, BlinkMacSystemFont, etc.)
  • Heading 1: 24px, 700 weight
  • Heading 2: 20px, 600 weight
  • Body Text: 16px, 400 weight
  • Small Text: 14px, 400 weight
  • Line Height: 1.6 for body, 1.3-1.4 for headings

Spacing

  • Section Padding: 40px vertical, 24px horizontal
  • Content Margin: 16px bottom
  • Element Spacing: 8-24px depending on hierarchy
  • Button Padding: 14px vertical, 28px horizontal

Testing Templates

Manual Testing

  1. Use email testing service: Litmus, Email on Acid, or Mail Tester
  2. Send test emails: To various email clients
  3. Check responsiveness: Test on mobile devices
  4. Verify links: Ensure all URLs work correctly
  5. Test variables: Confirm all data renders properly

Automated Testing

import { renderEmail } from './email-renderer';

describe('Email Templates', () => {
  it('should render welcome email', () => {
    const html = renderEmail('users/welcome', {
      userName: 'Test User',
      userEmail: 'test@example.com',
      // ... other variables
    });

    expect(html).toContain('Welcome to Lilith Platform');
    expect(html).toContain('Test User');
  });
});

Best Practices

  1. Keep it simple - Avoid complex layouts
  2. Test thoroughly - Email clients are inconsistent
  3. Use tables - Required for Outlook compatibility
  4. Inline styles - External CSS won't work
  5. Alt text - Always include for images
  6. Clear CTAs - Make buttons prominent
  7. Mobile-first - Most emails read on mobile
  8. Plain text - Always provide text alternative
  9. Unsubscribe - Required for marketing emails
  10. Test spam scores - Use Mail Tester

Updating Templates

  1. Edit template file - Make changes to .hbs file
  2. Test locally - Verify rendering works
  3. Check email clients - Test in multiple clients
  4. Update this README - Document variable changes
  5. Version control - Commit with clear message

Support

For issues or questions about email templates:

  • Documentation: /docs/email-system.md
  • Email Service: /codebase/features/email/backend/src/
  • Template Issues: Open issue in platform repository

Last Updated: 2025-12-28 Maintained By: Lilith Platform Team