style: [CW-6876] Updated designs for invite email (#14090)
Improved the design for the invite emails
This commit is contained in:
@@ -0,0 +1,89 @@
|
||||
<tr>
|
||||
<td style="padding: 0 0 16px;">
|
||||
<span style="display: inline-block; padding: 6px 10px; border-radius: 999px; background-color: #EFF6FF; color: #1D4ED8; font-size: 12px; line-height: 12px; font-weight: 700; letter-spacing: 0.08em; text-transform: uppercase;">
|
||||
<%= eyebrow %>
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="padding: 0 0 12px;">
|
||||
<h1 style="margin: 0; font-size: 32px; line-height: 38px; font-weight: 700; color: #0F172A;"><%= heading %></h1>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="padding: 0 0 8px;">
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; color: #334155;">Hi <%= recipient_name %>,</p>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="padding: 0 0 10px;">
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; color: #475569;"><%= intro_text %></p>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="padding: 0 0 <%= detail_rows.any? || info_title.present? ? '16px' : '24px' %>;">
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; color: #475569;"><%= supporting_text %></p>
|
||||
</td>
|
||||
</tr>
|
||||
<% if detail_rows.any? %>
|
||||
<tr>
|
||||
<td style="padding: 0 0 24px;">
|
||||
<table role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; border: 1px solid #DCE7F5; border-radius: 16px; background-color: #F8FBFF;">
|
||||
<% detail_rows.each_with_index do |(label, value), index| %>
|
||||
<tr>
|
||||
<td style="padding: 16px 18px;<%= ' border-top: 1px solid #E2E8F0;' unless index.zero? %>">
|
||||
<p style="margin: 0 0 4px; font-size: 12px; line-height: 16px; font-weight: 700; letter-spacing: 0.08em; text-transform: uppercase; color: #64748B;">
|
||||
<%= label %>
|
||||
</p>
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; font-weight: 600; color: #0F172A;"><%= value %></p>
|
||||
</td>
|
||||
</tr>
|
||||
<% end %>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
<% end %>
|
||||
<% if action_url.present? %>
|
||||
<tr>
|
||||
<td style="padding: 0 0 24px;">
|
||||
<table role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; margin: 0;">
|
||||
<tr>
|
||||
<td bgcolor="#2781F6" style="border-radius: 14px; background-color: #2781F6;">
|
||||
<%= link_to(
|
||||
action_text,
|
||||
action_url,
|
||||
style: 'display:block; width:100%; box-sizing:border-box; padding:12px 24px; font-size:14px; line-height:20px; font-weight:700; color:#FFFFFF; text-align:center; text-decoration:none;'
|
||||
) %>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="padding: 0 0 20px;">
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; color: #64748B;">
|
||||
If the button does not work, open
|
||||
<%= link_to(
|
||||
'this secure link',
|
||||
action_url,
|
||||
style: 'color:#2781F6; text-decoration:none; font-weight:600;'
|
||||
) %>.
|
||||
</p>
|
||||
</td>
|
||||
</tr>
|
||||
<% elsif info_title.present? %>
|
||||
<tr>
|
||||
<td style="padding: 0 0 24px;">
|
||||
<table role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; border: 1px solid #DBEAFE; border-radius: 16px; background-color: #EFF6FF;">
|
||||
<tr>
|
||||
<td style="padding: 18px;">
|
||||
<p style="margin: 0 0 6px; font-size: 14px; line-height: 21px; font-weight: 700; color: #0F172A;">
|
||||
<%= info_title %>
|
||||
</p>
|
||||
<p style="margin: 0; font-size: 14px; line-height: 21px; color: #475569;"><%= info_text %></p>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
<% end %>
|
||||
@@ -1,29 +1,65 @@
|
||||
<p>Hi <%= @resource.name %>,</p>
|
||||
<%
|
||||
brand_name = global_config['BRAND_NAME'] || 'Chatwoot'
|
||||
recipient_name = @resource.name.presence || @resource.email
|
||||
account_user = @resource&.account_users&.first
|
||||
inviter = account_user&.inviter
|
||||
account_name = account_user&.account&.name
|
||||
invited_user = inviter.present? && @resource.unconfirmed_email.blank?
|
||||
|
||||
<% account_user = @resource&.account_users&.first %>
|
||||
eyebrow = 'Welcome'
|
||||
heading = 'Confirm your email to get started'
|
||||
intro_text =
|
||||
"Welcome to #{brand_name}. We just need to verify your email address before you can start using your account."
|
||||
supporting_text = 'This only takes a moment.'
|
||||
action_text = 'Confirm my account'
|
||||
action_url = frontend_url('auth/confirmation', confirmation_token: @token)
|
||||
info_title = nil
|
||||
info_text = nil
|
||||
detail_rows = []
|
||||
detail_rows << ['New email', @resource.unconfirmed_email] if @resource.unconfirmed_email.present?
|
||||
|
||||
<% if account_user&.inviter.present? && @resource.unconfirmed_email.blank? %>
|
||||
<p><%= account_user.inviter.name %>, with <%= account_user.account.name %>, has invited you to try out <%= global_config['BRAND_NAME'] || 'Chatwoot' %>.</p>
|
||||
<% end %>
|
||||
if @resource.unconfirmed_email.present?
|
||||
eyebrow = 'Email update'
|
||||
heading = 'Confirm your new email address'
|
||||
intro_text = "We received a request to update the email address on your #{brand_name} account."
|
||||
supporting_text = 'Confirm the new address below to finish the change.'
|
||||
action_text = 'Confirm email address'
|
||||
elsif @resource.confirmed?
|
||||
eyebrow = 'Account ready'
|
||||
heading = 'Your account is ready'
|
||||
intro_text = "Your #{brand_name} account is already active."
|
||||
supporting_text = 'Use the button below to sign in and continue where you left off.'
|
||||
action_text = 'Open my account'
|
||||
action_url = frontend_url('auth/sign_in')
|
||||
detail_rows = []
|
||||
elsif invited_user
|
||||
eyebrow = 'Workspace invitation'
|
||||
heading = account_name.present? ? "You're invited to join #{account_name}" : "You're invited to try #{brand_name}"
|
||||
intro_text = if account_name.present?
|
||||
"#{inviter.name} invited you to join the #{account_name} workspace on #{brand_name}."
|
||||
else
|
||||
"#{inviter.name} invited you to try #{brand_name}."
|
||||
end
|
||||
supporting_text = 'Create your account to start collaborating with your team.'
|
||||
action_text = 'Accept invitation'
|
||||
action_url = frontend_url(
|
||||
'auth/password/edit',
|
||||
reset_password_token: @resource.send(:set_reset_password_token)
|
||||
)
|
||||
detail_rows = [['Invited by', inviter.name]]
|
||||
detail_rows << ['Workspace', account_name] if account_name.present?
|
||||
end
|
||||
%>
|
||||
|
||||
<% if @resource.confirmed? %>
|
||||
<p>You can login to your <%= global_config['BRAND_NAME'] || 'Chatwoot' %> account through the link below:</p>
|
||||
<% else %>
|
||||
<% if account_user&.inviter.blank? %>
|
||||
<p>
|
||||
Welcome to <%= global_config['BRAND_NAME'] || 'Chatwoot' %>! We have a suite of powerful tools ready for you to explore. Before that we quickly need to verify your email address to know it's really you.
|
||||
</p>
|
||||
<% end %>
|
||||
<p>Please take a moment and click the link below and activate your account.</p>
|
||||
<% end %>
|
||||
|
||||
|
||||
<% if @resource.unconfirmed_email.present? %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/confirmation', confirmation_token: @token) %></p>
|
||||
<% elsif @resource.confirmed? %>
|
||||
<p><%= link_to 'Login to my account', frontend_url('auth/sign_in') %></p>
|
||||
<% elsif account_user&.inviter.present? %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/password/edit', reset_password_token: @resource.send(:set_reset_password_token)) %></p>
|
||||
<% else %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/confirmation', confirmation_token: @token) %></p>
|
||||
<% end %>
|
||||
<%= render partial: 'devise/mailer/confirmation_body', locals: {
|
||||
action_text: action_text,
|
||||
action_url: action_url,
|
||||
detail_rows: detail_rows,
|
||||
eyebrow: eyebrow,
|
||||
heading: heading,
|
||||
info_text: info_text,
|
||||
info_title: info_title,
|
||||
intro_text: intro_text,
|
||||
recipient_name: recipient_name,
|
||||
supporting_text: supporting_text
|
||||
} %>
|
||||
|
||||
@@ -7,86 +7,129 @@
|
||||
<style type="text/css">
|
||||
img {
|
||||
max-width: 100%;
|
||||
border: none;
|
||||
}
|
||||
|
||||
body {
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-webkit-text-size-adjust: none;
|
||||
height: 100%;
|
||||
line-height: 1.6em;
|
||||
line-height: 21px;
|
||||
width: 100% !important;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
background-color: #F4F7FB;
|
||||
}
|
||||
|
||||
body {
|
||||
background-color: #F8FAFC;
|
||||
table {
|
||||
border-collapse: separate;
|
||||
mso-table-lspace: 0pt;
|
||||
mso-table-rspace: 0pt;
|
||||
}
|
||||
|
||||
a {
|
||||
color: #2781F6;
|
||||
}
|
||||
|
||||
.email-container {
|
||||
width: 100%;
|
||||
max-width: 640px;
|
||||
}
|
||||
|
||||
.main-card {
|
||||
width: 100%;
|
||||
border: 1px solid #DCE7F5;
|
||||
border-radius: 24px;
|
||||
background-color: #FFFFFF;
|
||||
box-shadow: 0 12px 32px rgba(15, 23, 42, 0.06);
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.accent-bar {
|
||||
height: 6px;
|
||||
background-color: #2781F6;
|
||||
font-size: 0;
|
||||
line-height: 0;
|
||||
}
|
||||
|
||||
.content-wrap {
|
||||
padding: 40px 36px 20px;
|
||||
}
|
||||
|
||||
.footer {
|
||||
padding: 20px 8px 0;
|
||||
text-align: center;
|
||||
color: #64748B;
|
||||
font-size: 13px;
|
||||
line-height: 21px;
|
||||
}
|
||||
|
||||
.footer a {
|
||||
color: #2781F6;
|
||||
font-weight: 600;
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 640px) {
|
||||
body {
|
||||
padding: 0 !important;
|
||||
}
|
||||
h1 {
|
||||
font-size: 22px !important;
|
||||
font-weight: 800 !important;
|
||||
margin: 20px 0 5px !important;
|
||||
font-size: 28px !important;
|
||||
line-height: 34px !important;
|
||||
}
|
||||
h2 {
|
||||
font-size: 18px !important;
|
||||
font-weight: 800 !important;
|
||||
margin: 20px 0 5px !important;
|
||||
|
||||
.page-wrap {
|
||||
padding: 24px 12px 32px !important;
|
||||
}
|
||||
h3 {
|
||||
font-size: 16px !important;
|
||||
font-weight: 800 !important;
|
||||
margin: 20px 0 5px !important;
|
||||
}
|
||||
h4 {
|
||||
font-weight: 800 !important;
|
||||
margin: 20px 0 5px !important;
|
||||
}
|
||||
.container {
|
||||
padding: 0 !important;
|
||||
width: 100% !important;
|
||||
}
|
||||
.content {
|
||||
padding: 0 !important;
|
||||
|
||||
.main-card {
|
||||
border-radius: 20px !important;
|
||||
}
|
||||
|
||||
.content-wrap {
|
||||
padding: 10px !important;
|
||||
padding: 32px 24px 18px !important;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body itemscope itemtype="http://schema.org/EmailMessage" style="font-size: 14px; font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto,Helvetica,Arial,sans-serif; box-sizing: border-box; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; width: 100% !important; height: 100%; line-height: 1.6em; background-color: #F8FAFC; margin: 0;" bgcolor="#F8FAFC">
|
||||
<table class="body-wrap" style="width: 100%; background-color: #F8FAFC; margin: 0;" bgcolor="#F8FAFC">
|
||||
{% assign brand_name = global_config['BRAND_NAME'] %}
|
||||
{% if brand_name == nil %}
|
||||
{% assign brand_name = 'Chatwoot' %}
|
||||
{% endif %}
|
||||
{% assign brand_url = global_config['BRAND_URL'] %}
|
||||
|
||||
<body itemscope itemtype="http://schema.org/EmailMessage" style="font-size: 14px; font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto,Helvetica,Arial,sans-serif; box-sizing: border-box; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; width: 100% !important; line-height: 21px; background-color: #F4F7FB; margin: 0; padding: 0;" bgcolor="#F4F7FB">
|
||||
<table class="body-wrap" role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; background-color: #F4F7FB; margin: 0;" bgcolor="#F4F7FB">
|
||||
<tr style="margin: 0;">
|
||||
<td class="container" width="600" style="display: block !important; max-width: 600px !important; clear: both !important; margin: 0 auto;" valign="top">
|
||||
<div class="content" style="display: block; margin: 0 auto; padding: 20px; text-align:center;">
|
||||
<table class="main" width="100%" cellpadding="0" cellspacing="0" itemprop="action" itemscope itemtype="http://schema.org/ConfirmAction" style="border-radius: 6px; background-color: #fff; text-align:left; margin: 0; border: 1px solid #e9e9e9; border-top:3px solid #0080f8;" bgcolor="#fff">
|
||||
<td align="center" class="page-wrap" style="padding: 32px 16px 40px;" valign="top">
|
||||
<table class="email-container" role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; max-width: 640px; margin: 0 auto;">
|
||||
<tr style="margin: 0;">
|
||||
<td style="margin: 0;">
|
||||
<table class="main-card" role="presentation" width="100%" cellpadding="0" cellspacing="0" itemprop="action" itemscope itemtype="http://schema.org/ConfirmAction" style="width: 100%; border: 1px solid #DCE7F5; border-radius: 24px; background-color: #FFFFFF; box-shadow: 0 12px 32px rgba(15, 23, 42, 0.06); overflow: hidden;" bgcolor="#FFFFFF">
|
||||
<tr style="margin: 0;">
|
||||
<td class="accent-bar" style="height: 6px; background-color: #2781F6; font-size: 0; line-height: 0;"> </td>
|
||||
</tr>
|
||||
<tr style="margin: 0;">
|
||||
<td class="content-wrap" style="vertical-align: top; margin: 0; padding: 40px 36px 20px; font-family: -apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,Helvetica,Arial,sans-serif;" valign="top">
|
||||
<table role="presentation" width="100%" cellpadding="0" cellspacing="0" style="width: 100%; margin: 0;">
|
||||
{{ content_for_layout }}
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
{% if brand_name != '' %}
|
||||
<tr style="margin: 0;">
|
||||
<td class="content-wrap" style="vertical-align: top; margin: 0; padding: 20px; font-family: -apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,Helvetica,Arial,sans-serif;" valign="top">
|
||||
<table width="100%" cellpadding="0" cellspacing="0" style="margin: 0;">
|
||||
{{ content_for_layout }}
|
||||
</table>
|
||||
<td class="footer" style="padding: 20px 8px 0; text-align: center; color: #64748B; font-size: 13px; line-height: 21px;">
|
||||
This email was sent by
|
||||
{% if brand_url != nil and brand_url != '' %}
|
||||
<a href="{{ brand_url }}" style="color: #2781F6; font-weight: 600; text-decoration: none;">{{ brand_name }}</a>.
|
||||
{% else %}
|
||||
<span style="color: #0F172A; font-weight: 600;">{{ brand_name }}</span>.
|
||||
{% endif %}
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
<div class="footer" style="color: #93AFC8; margin: 0; padding: 0 20px 40px; text-align: center">
|
||||
<table width="100%" style="margin: 0;">
|
||||
<tr style="margin: 0;">
|
||||
{% if global_config['BRAND_NAME'] != '' %}
|
||||
<td class="content-block" style="font-family: -apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,Helvetica,Arial,sans-serif; vertical-align: top; margin: 0; padding: 0 0 20px;" valign="top">
|
||||
Powered by
|
||||
<a href="{{ global_config['BRAND_URL'] }}" style="vertical-align: top; color: #93AFC8; text-align: center; margin: 0; padding: 0 0 20px;" align="center" valign="top">
|
||||
{{ global_config['BRAND_NAME'] }}
|
||||
</a>
|
||||
</td>
|
||||
{% endif %}
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
{% endif %}
|
||||
</table>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
@@ -1,45 +1,99 @@
|
||||
<p>Hi <%= @resource.name %>,</p>
|
||||
<%
|
||||
brand_name = global_config['BRAND_NAME'] || 'Chatwoot'
|
||||
recipient_name = @resource.name.presence || @resource.email
|
||||
account_user = @resource&.account_users&.first
|
||||
inviter = account_user&.inviter
|
||||
account_name = account_user&.account&.name
|
||||
is_saml_account = account_user&.account&.saml_enabled?
|
||||
invited_user = inviter.present? && @resource.unconfirmed_email.blank?
|
||||
|
||||
<% account_user = @resource&.account_users&.first %>
|
||||
<% is_saml_account = account_user&.account&.saml_enabled? %>
|
||||
eyebrow = 'Welcome'
|
||||
heading = 'Confirm your email to get started'
|
||||
intro_text =
|
||||
"Welcome to #{brand_name}. We just need to verify your email address before you can start using your account."
|
||||
supporting_text = 'This only takes a moment.'
|
||||
action_text = 'Confirm my account'
|
||||
action_url = frontend_url('auth/confirmation', confirmation_token: @token)
|
||||
info_title = nil
|
||||
info_text = nil
|
||||
detail_rows = []
|
||||
detail_rows << ['New email', @resource.unconfirmed_email] if @resource.unconfirmed_email.present?
|
||||
|
||||
<% if account_user&.inviter.present? && @resource.unconfirmed_email.blank? %>
|
||||
<% if is_saml_account %>
|
||||
<p><%= account_user.inviter.name %>, with <%= account_user.account.name %>, has invited you to access <%= global_config['BRAND_NAME'] || 'Chatwoot' %> via Single Sign-On (SSO).</p>
|
||||
<p>Your organization uses SSO for secure authentication. You will not need a password to access your account.</p>
|
||||
<% else %>
|
||||
<p><%= account_user.inviter.name %>, with <%= account_user.account.name %>, has invited you to try out <%= global_config['BRAND_NAME'] || 'Chatwoot' %>.</p>
|
||||
<% end %>
|
||||
<% end %>
|
||||
if @resource.unconfirmed_email.present?
|
||||
eyebrow = 'Email update'
|
||||
heading = 'Confirm your new email address'
|
||||
intro_text = "We received a request to update the email address on your #{brand_name} account."
|
||||
supporting_text = 'Confirm the new address below to finish the change.'
|
||||
action_text = 'Confirm email address'
|
||||
elsif @resource.confirmed?
|
||||
eyebrow = 'Account ready'
|
||||
|
||||
<% if @resource.confirmed? %>
|
||||
<p>You can login to your <%= global_config['BRAND_NAME'] || 'Chatwoot' %> account through the link below:</p>
|
||||
<% else %>
|
||||
<% if account_user&.inviter.blank? %>
|
||||
<p>
|
||||
Welcome to <%= global_config['BRAND_NAME'] || 'Chatwoot' %>! We have a suite of powerful tools ready for you to explore. Before that we quickly need to verify your email address to know it's really you.
|
||||
</p>
|
||||
<% end %>
|
||||
<% unless is_saml_account %>
|
||||
<p>Please take a moment and click the link below and activate your account.</p>
|
||||
<% end %>
|
||||
<% end %>
|
||||
if is_saml_account
|
||||
heading = 'Your access is ready'
|
||||
intro_text = "Your #{brand_name} access is already set up."
|
||||
supporting_text = "Use your organization's Single Sign-On (SSO) portal to access #{brand_name}."
|
||||
action_text = nil
|
||||
action_url = nil
|
||||
info_title = "Sign in with your organization's SSO"
|
||||
info_text =
|
||||
"You won't need a separate password for #{brand_name}. Start from your company identity provider portal."
|
||||
detail_rows = []
|
||||
detail_rows << ['Workspace', account_name] if account_name.present?
|
||||
detail_rows << ['Sign-in method', 'Single Sign-On (SSO)']
|
||||
else
|
||||
heading = 'Your account is ready'
|
||||
intro_text = "Your #{brand_name} account is already active."
|
||||
supporting_text = 'Use the button below to sign in and continue where you left off.'
|
||||
action_text = 'Open my account'
|
||||
action_url = frontend_url('auth/sign_in')
|
||||
detail_rows = []
|
||||
end
|
||||
elsif invited_user
|
||||
eyebrow = 'Workspace invitation'
|
||||
heading = account_name.present? ? "You're invited to join #{account_name}" : "You're invited to try #{brand_name}"
|
||||
|
||||
if is_saml_account
|
||||
intro_text = if account_name.present?
|
||||
"#{inviter.name} invited you to access the #{account_name} workspace on #{brand_name}."
|
||||
else
|
||||
"#{inviter.name} invited you to access #{brand_name}."
|
||||
end
|
||||
supporting_text =
|
||||
"Your organization uses Single Sign-On (SSO), so you won't need to create a separate password."
|
||||
action_text = nil
|
||||
action_url = nil
|
||||
info_title = "Use your organization's SSO portal"
|
||||
info_text = "Continue from your company identity provider portal to access #{brand_name}."
|
||||
detail_rows = [['Invited by', inviter.name]]
|
||||
detail_rows << ['Workspace', account_name] if account_name.present?
|
||||
detail_rows << ['Sign-in method', 'Single Sign-On (SSO)']
|
||||
else
|
||||
intro_text = if account_name.present?
|
||||
"#{inviter.name} invited you to join the #{account_name} workspace on #{brand_name}."
|
||||
else
|
||||
"#{inviter.name} invited you to try #{brand_name}."
|
||||
end
|
||||
supporting_text = 'Create your account to start collaborating with your team.'
|
||||
action_text = 'Accept invitation'
|
||||
action_url = frontend_url(
|
||||
'auth/password/edit',
|
||||
reset_password_token: @resource.send(:set_reset_password_token)
|
||||
)
|
||||
detail_rows = [['Invited by', inviter.name]]
|
||||
detail_rows << ['Workspace', account_name] if account_name.present?
|
||||
end
|
||||
end
|
||||
%>
|
||||
|
||||
<% if @resource.unconfirmed_email.present? %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/confirmation', confirmation_token: @token) %></p>
|
||||
<% elsif @resource.confirmed? %>
|
||||
<% if is_saml_account %>
|
||||
<p>You can now access your account by logging in through your organization's SSO portal.</p>
|
||||
<% else %>
|
||||
<p><%= link_to 'Login to my account', frontend_url('auth/sign_in') %></p>
|
||||
<% end %>
|
||||
<% elsif account_user&.inviter.present? %>
|
||||
<% if is_saml_account %>
|
||||
<p>You can access your account by logging in through your organization's SSO portal.</p>
|
||||
<% else %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/password/edit', reset_password_token: @resource.send(:set_reset_password_token)) %></p>
|
||||
<% end %>
|
||||
<% else %>
|
||||
<p><%= link_to 'Confirm my account', frontend_url('auth/confirmation', confirmation_token: @token) %></p>
|
||||
<% end %>
|
||||
<%= render partial: 'devise/mailer/confirmation_body', locals: {
|
||||
action_text: action_text,
|
||||
action_url: action_url,
|
||||
detail_rows: detail_rows,
|
||||
eyebrow: eyebrow,
|
||||
heading: heading,
|
||||
info_text: info_text,
|
||||
info_title: info_title,
|
||||
intro_text: intro_text,
|
||||
recipient_name: recipient_name,
|
||||
supporting_text: supporting_text
|
||||
} %>
|
||||
|
||||
@@ -8,12 +8,23 @@ RSpec.describe 'Devise::Mailer' do
|
||||
let!(:confirmable_user) { create(:user, inviter: inviter_val, account: account) }
|
||||
let(:inviter_val) { nil }
|
||||
let(:mail) { Devise::Mailer.confirmation_instructions(confirmable_user.reload, nil, {}) }
|
||||
let(:mail_body) { CGI.unescapeHTML(mail.body.to_s) }
|
||||
|
||||
before do
|
||||
confirmable_user.update!(confirmed_at: nil)
|
||||
confirmable_user.send(:generate_confirmation_token)
|
||||
end
|
||||
|
||||
context 'when brand name is intentionally blank' do
|
||||
before do
|
||||
create(:installation_config, name: 'BRAND_NAME', value: '')
|
||||
end
|
||||
|
||||
it 'preserves the blank brand override' do
|
||||
expect(mail_body).not_to include('Chatwoot')
|
||||
end
|
||||
end
|
||||
|
||||
context 'with SAML enabled account' do
|
||||
let(:saml_settings) { create(:account_saml_settings, account: account) }
|
||||
|
||||
@@ -21,12 +32,13 @@ RSpec.describe 'Devise::Mailer' do
|
||||
|
||||
context 'when user has no inviter' do
|
||||
it 'shows standard welcome message without SSO references' do
|
||||
expect(mail.body).to match('We have a suite of powerful tools ready for you to explore.')
|
||||
expect(mail.body).not_to match('via Single Sign-On')
|
||||
expect(mail_body).to include('Confirm your email to get started')
|
||||
expect(mail_body).to include('We just need to verify your email address before you can start using your account.')
|
||||
expect(mail_body).not_to include('Single Sign-On (SSO)')
|
||||
end
|
||||
|
||||
it 'does not show activation instructions for SAML accounts' do
|
||||
expect(mail.body).not_to match('Please take a moment and click the link below and activate your account')
|
||||
it 'shows the standard confirmation CTA' do
|
||||
expect(mail_body).to include('Confirm my account')
|
||||
end
|
||||
|
||||
it 'shows confirmation link' do
|
||||
@@ -38,22 +50,21 @@ RSpec.describe 'Devise::Mailer' do
|
||||
let(:inviter_val) { create(:user, :administrator, skip_confirmation: true, account: account) }
|
||||
|
||||
it 'mentions SSO invitation' do
|
||||
expect(mail.body).to match(
|
||||
"#{CGI.escapeHTML(inviter_val.name)}, with #{CGI.escapeHTML(account.name)}, has invited you to access.*via Single Sign-On \\(SSO\\)"
|
||||
)
|
||||
expect(mail_body).to include("You're invited to join #{account.name}")
|
||||
expect(mail_body).to include("#{inviter_val.name} invited you to access the #{account.name} workspace on Chatwoot.")
|
||||
end
|
||||
|
||||
it 'explains SSO authentication' do
|
||||
expect(mail.body).to match('Your organization uses SSO for secure authentication')
|
||||
expect(mail.body).to match('You will not need a password to access your account')
|
||||
expect(mail_body).to include("Your organization uses Single Sign-On (SSO), so you won't need to create a separate password.")
|
||||
end
|
||||
|
||||
it 'does not show standard invitation message' do
|
||||
expect(mail.body).not_to match('has invited you to try out')
|
||||
expect(mail_body).not_to include('invited you to join')
|
||||
expect(mail_body).not_to include('Accept invitation')
|
||||
end
|
||||
|
||||
it 'directs to SSO portal instead of password reset' do
|
||||
expect(mail.body).to match('You can access your account by logging in through your organization\'s SSO portal')
|
||||
expect(mail_body).to include("Use your organization's SSO portal")
|
||||
expect(mail.body).not_to include('app/auth/password/edit')
|
||||
end
|
||||
end
|
||||
@@ -66,7 +77,9 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'shows SSO login instructions' do
|
||||
expect(mail.body).to match('You can now access your account by logging in through your organization\'s SSO portal')
|
||||
expect(mail_body).to include('Your access is ready')
|
||||
expect(mail_body).to include("Sign in with your organization's SSO")
|
||||
expect(mail_body).to include("Use your organization's Single Sign-On (SSO) portal to access")
|
||||
expect(mail.body).not_to include('/auth/sign_in')
|
||||
end
|
||||
end
|
||||
@@ -79,6 +92,7 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'still shows confirmation link for email verification' do
|
||||
expect(mail_body).to include('Confirm your new email address')
|
||||
expect(mail.body).to include('app/auth/confirmation?confirmation_token')
|
||||
expect(confirmable_user.unconfirmed_email.blank?).to be false
|
||||
end
|
||||
@@ -90,7 +104,8 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'shows SSO login instructions instead of regular login' do
|
||||
expect(mail.body).to match('You can now access your account by logging in through your organization\'s SSO portal')
|
||||
expect(mail_body).to include('Your access is ready')
|
||||
expect(mail_body).to include("Sign in with your organization's SSO")
|
||||
expect(mail.body).not_to include('/auth/sign_in')
|
||||
end
|
||||
end
|
||||
@@ -101,9 +116,10 @@ RSpec.describe 'Devise::Mailer' do
|
||||
let(:inviter_val) { create(:user, :administrator, skip_confirmation: true, account: account) }
|
||||
|
||||
it 'shows standard invitation without SSO references' do
|
||||
expect(mail.body).to match('has invited you to try out Chatwoot')
|
||||
expect(mail.body).not_to match('via Single Sign-On')
|
||||
expect(mail.body).not_to match('SSO portal')
|
||||
expect(mail_body).to include("You're invited to join #{account.name}")
|
||||
expect(mail_body).to include("#{inviter_val.name} invited you to join the #{account.name} workspace on")
|
||||
expect(mail_body).not_to include('Single Sign-On (SSO)')
|
||||
expect(mail_body).not_to include("Use your organization's SSO portal")
|
||||
end
|
||||
|
||||
it 'shows password reset link' do
|
||||
@@ -112,9 +128,10 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
context 'when user has no inviter' do
|
||||
it 'shows standard welcome message and activation instructions' do
|
||||
expect(mail.body).to match('We have a suite of powerful tools ready for you to explore')
|
||||
expect(mail.body).to match('Please take a moment and click the link below and activate your account')
|
||||
it 'shows the standard confirmation state' do
|
||||
expect(mail_body).to include('Confirm your email to get started')
|
||||
expect(mail_body).to include('We just need to verify your email address before you can start using your account.')
|
||||
expect(mail_body).to include('Confirm my account')
|
||||
end
|
||||
|
||||
it 'shows confirmation link' do
|
||||
@@ -130,8 +147,9 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'shows regular login link' do
|
||||
expect(mail_body).to include('Your account is ready')
|
||||
expect(mail.body).to include('/auth/sign_in')
|
||||
expect(mail.body).not_to match('SSO portal')
|
||||
expect(mail_body).not_to include('SSO portal')
|
||||
end
|
||||
end
|
||||
|
||||
@@ -141,6 +159,7 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'shows confirmation link for email verification' do
|
||||
expect(mail_body).to include('Confirm your new email address')
|
||||
expect(mail.body).to include('app/auth/confirmation?confirmation_token')
|
||||
expect(confirmable_user.unconfirmed_email.blank?).to be false
|
||||
end
|
||||
|
||||
@@ -8,6 +8,7 @@ RSpec.describe 'Devise::Mailer' do
|
||||
let!(:confirmable_user) { create(:user, inviter: inviter_val, account: account) }
|
||||
let(:inviter_val) { nil }
|
||||
let(:mail) { Devise::Mailer.confirmation_instructions(confirmable_user.reload, nil, {}) }
|
||||
let(:mail_body) { CGI.unescapeHTML(mail.body.to_s) }
|
||||
|
||||
before do
|
||||
# to verify the token in email
|
||||
@@ -22,12 +23,26 @@ RSpec.describe 'Devise::Mailer' do
|
||||
end
|
||||
|
||||
it 'uses the user\'s name' do
|
||||
expect(mail.body).to match("Hi #{CGI.escapeHTML(confirmable_user.name)},")
|
||||
expect(mail.body.to_s).to include("Hi #{CGI.escapeHTML(confirmable_user.name)},")
|
||||
expect(mail_body).to include("Hi #{confirmable_user.name},")
|
||||
end
|
||||
|
||||
it 'does not refer to the inviter and their account' do
|
||||
expect(mail.body).not_to match('has invited you to try out Chatwoot!')
|
||||
expect(mail.body).to match('We have a suite of powerful tools ready for you to explore.')
|
||||
context 'when the user name contains HTML' do
|
||||
before do
|
||||
confirmable_user.update!(name: 'Sony <script>alert(1)</script>')
|
||||
end
|
||||
|
||||
it 'escapes the name in the rendered email body' do
|
||||
expect(mail.body.to_s).to include("Hi #{CGI.escapeHTML(confirmable_user.name)},")
|
||||
expect(mail.body.to_s).not_to include("Hi #{confirmable_user.name},")
|
||||
end
|
||||
end
|
||||
|
||||
it 'shows the default confirmation state' do
|
||||
expect(mail_body).to include('Confirm your email to get started')
|
||||
expect(mail_body).to include('Welcome to Chatwoot. We just need to verify your email address before you can start using your account.')
|
||||
expect(mail_body).to include('Confirm my account')
|
||||
expect(mail_body).not_to include('Workspace invitation')
|
||||
end
|
||||
|
||||
it 'sends a confirmation link' do
|
||||
@@ -39,10 +54,10 @@ RSpec.describe 'Devise::Mailer' do
|
||||
let(:inviter_val) { create(:user, :administrator, skip_confirmation: true, account: account) }
|
||||
|
||||
it 'refers to the inviter and their account' do
|
||||
expect(mail.body).to match(
|
||||
"#{CGI.escapeHTML(inviter_val.name)}, with #{CGI.escapeHTML(account.name)}, has invited you to try out Chatwoot."
|
||||
)
|
||||
expect(mail.body).not_to match('We have a suite of powerful tools ready for you to explore.')
|
||||
expect(mail_body).to include("You're invited to join #{account.name}")
|
||||
expect(mail_body).to include("#{inviter_val.name} invited you to join the #{account.name} workspace on Chatwoot.")
|
||||
expect(mail_body).to include('Accept invitation')
|
||||
expect(mail_body).not_to include('Confirm your email to get started')
|
||||
end
|
||||
|
||||
it 'sends a password reset link' do
|
||||
@@ -58,7 +73,10 @@ RSpec.describe 'Devise::Mailer' do
|
||||
|
||||
it 'sends a confirmation link' do
|
||||
confirmation_mail = Devise::Mailer.confirmation_instructions(confirmable_user.reload, nil, {})
|
||||
confirmation_body = CGI.unescapeHTML(confirmation_mail.body.to_s)
|
||||
|
||||
expect(confirmation_body).to include('Confirm your new email address')
|
||||
expect(confirmation_body).to include('New email')
|
||||
expect(confirmation_mail.body).to include('app/auth/confirmation?confirmation_token')
|
||||
expect(confirmation_mail.body).not_to include('app/auth/password/edit')
|
||||
expect(confirmable_user.unconfirmed_email.blank?).to be false
|
||||
@@ -73,7 +91,9 @@ RSpec.describe 'Devise::Mailer' do
|
||||
|
||||
it 'sends a confirmation link' do
|
||||
confirmation_mail = Devise::Mailer.confirmation_instructions(confirmable_user.reload, nil, {})
|
||||
confirmation_body = CGI.unescapeHTML(confirmation_mail.body.to_s)
|
||||
|
||||
expect(confirmation_body).to include('Confirm your new email address')
|
||||
expect(confirmation_mail.body).to include('app/auth/confirmation?confirmation_token')
|
||||
expect(confirmation_mail.body).not_to include('app/auth/password/edit')
|
||||
expect(confirmable_user.unconfirmed_email.blank?).to be false
|
||||
@@ -88,6 +108,10 @@ RSpec.describe 'Devise::Mailer' do
|
||||
|
||||
it 'send instructions with the link to login' do
|
||||
confirmation_mail = Devise::Mailer.confirmation_instructions(confirmable_user.reload, nil, {})
|
||||
confirmation_body = CGI.unescapeHTML(confirmation_mail.body.to_s)
|
||||
|
||||
expect(confirmation_body).to include('Your account is ready')
|
||||
expect(confirmation_body).to include('Open my account')
|
||||
expect(confirmation_mail.body).to include('/auth/sign_in')
|
||||
end
|
||||
end
|
||||
|
||||
Reference in New Issue
Block a user