rails_mail 0.9.4 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +7 -1
- data/app/controllers/rails_mail/emails_controller.rb +1 -5
- data/app/frontend/rails_mail/application.js +2 -2
- data/app/frontend/rails_mail/modules/redirect_controller.js +5 -2
- data/app/models/rails_mail/email.rb +26 -8
- data/app/views/layouts/rails_mail/_head.html.erb +16 -0
- data/app/views/layouts/rails_mail/application.html.erb +5 -21
- data/app/views/rails_mail/emails/_email_tabs.html.erb +28 -0
- data/app/views/rails_mail/emails/destroy.turbo_stream.erb +15 -17
- data/app/views/rails_mail/emails/destroy_all.turbo_stream.erb +3 -1
- data/app/views/rails_mail/emails/index.turbo_stream.erb +1 -1
- data/app/views/rails_mail/emails/show.html.erb +5 -4
- data/app/views/rails_mail/shared/_email.html.erb +10 -10
- data/app/views/rails_mail/shared/_email_sidebar.html.erb +1 -1
- data/lib/generators/rails_mail/install/templates/initializer.rb +2 -2
- data/lib/rails_mail/configuration.rb +6 -6
- data/lib/rails_mail/delivery_method.rb +13 -1
- data/lib/rails_mail/version.rb +1 -1
- data/lib/rails_mail.rb +4 -16
- metadata +5 -4
- data/app/views/rails_mail/emails/_show.html.erb +0 -50
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 74639c1eeda1941950ff03fed49be529f335fc3e1e6e9896afd8ce9a636daaa6
|
4
|
+
data.tar.gz: bd46e033763529b995f444ef78d0390404d088d816e46300cf59bec3efbf3719
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4d1899db5ec6f5d1373c50e3dcc737be3a0156c01bbb60c8291e32a9ca5a8f0902451c7c90478ff4967624d1e372e842862067e9229ae634757f2518f311f557
|
7
|
+
data.tar.gz: 24845fe1ef0b59edcc0257f0b1cf695b2e5872b38d0dd8f5d5afb1989401684cc4e2aa0e5764ea74f90ec4279a829443ee42e6cde6eb9ec84a7d65e321f727bc
|
data/README.md
CHANGED
@@ -91,11 +91,17 @@ RailsMail can be configured through an initializer:
|
|
91
91
|
RailsMail.configure do |config|
|
92
92
|
# Optional authentication callback
|
93
93
|
# (if using Authlogic. If using Devise see the Authentication section)
|
94
|
-
config.
|
94
|
+
config.authenticate do
|
95
95
|
user_session = UserSession.find
|
96
96
|
raise ActionController::RoutingError.new('Not Found') unless user_session&.user&.admin?
|
97
97
|
end
|
98
98
|
|
99
|
+
# Optional decide whether to show the clear button
|
100
|
+
# Useful if you want devs in local envs to be able to clear all emails, but not in staging
|
101
|
+
config.show_clear_all_button do
|
102
|
+
Rails.env.development?
|
103
|
+
end
|
104
|
+
|
99
105
|
# Delete emails older than the specified duration
|
100
106
|
config.trim_emails_older_than = 30.days
|
101
107
|
|
@@ -19,11 +19,7 @@ module RailsMail
|
|
19
19
|
@email = Email.find(params[:id])
|
20
20
|
session[:current_email_id] = @email.id
|
21
21
|
|
22
|
-
|
23
|
-
render partial: "rails_mail/emails/show", locals: { email: @email }
|
24
|
-
else
|
25
|
-
render :index
|
26
|
-
end
|
22
|
+
render :show
|
27
23
|
end
|
28
24
|
|
29
25
|
def destroy
|
@@ -9,8 +9,8 @@ const application = Application.start();
|
|
9
9
|
|
10
10
|
application.register("email-highlight", EmailHighlightController);
|
11
11
|
application.register("redirect", RedirectController);
|
12
|
-
application.register('auto-submit', AutoSubmit)
|
13
|
-
application.register('timeago', Timeago)
|
12
|
+
application.register('auto-submit', AutoSubmit);
|
13
|
+
application.register('timeago', Timeago);
|
14
14
|
|
15
15
|
window.Stimulus = Application.start();
|
16
16
|
|
@@ -3,7 +3,10 @@ import { Controller } from 'stimulus'
|
|
3
3
|
export default class extends Controller {
|
4
4
|
static values = { url: String }
|
5
5
|
connect () {
|
6
|
-
//
|
6
|
+
// Need to remove the element
|
7
|
+
// Otherwise, if we revisit this page using a Turbo page cache
|
8
|
+
// it may end up redirecting again
|
9
|
+
this.element.remove();
|
7
10
|
Turbo.visit(this.urlValue)
|
8
11
|
}
|
9
|
-
}
|
12
|
+
}
|
@@ -1,6 +1,7 @@
|
|
1
1
|
module RailsMail
|
2
2
|
class Email < ApplicationRecord
|
3
|
-
|
3
|
+
include RailsMail::Engine.routes.url_helpers
|
4
|
+
store_accessor :data, :from, :to, :cc, :bcc, :subject, :html_part, :text_part, :content_type, :attachments
|
4
5
|
|
5
6
|
validates :from, presence: true
|
6
7
|
validates :to, presence: true
|
@@ -13,28 +14,45 @@ module RailsMail
|
|
13
14
|
}
|
14
15
|
|
15
16
|
def text?
|
16
|
-
content_type&.include?("text/plain")
|
17
|
+
content_type&.include?("text/plain") || content_type&.include?("multipart/alternative")
|
17
18
|
end
|
18
19
|
|
19
20
|
def html?
|
20
|
-
content_type&.include?("text/html")
|
21
|
+
content_type&.include?("text/html") || content_type&.include?("multipart/alternative")
|
21
22
|
end
|
22
23
|
|
23
24
|
def next_email
|
24
25
|
RailsMail::Email.where("id < ?", id).last || RailsMail::Email.first
|
25
26
|
end
|
26
27
|
|
28
|
+
def html_body
|
29
|
+
return nil unless html?
|
30
|
+
|
31
|
+
html_part["raw_source"]
|
32
|
+
end
|
33
|
+
|
34
|
+
def text_body
|
35
|
+
return nil unless text?
|
36
|
+
|
37
|
+
text_part["raw_source"]
|
38
|
+
end
|
39
|
+
|
27
40
|
private
|
28
41
|
|
29
42
|
def broadcast_email
|
30
|
-
return unless defined?(::
|
43
|
+
return unless defined?(::ActionCable)
|
31
44
|
|
32
|
-
|
33
|
-
"rails_mail:emails",
|
34
|
-
target: "email-sidebar",
|
45
|
+
html = ApplicationController.render(
|
35
46
|
partial: "rails_mail/shared/email",
|
36
|
-
locals: { email: self }
|
47
|
+
locals: { email: self, email_path: email_path(self) }
|
37
48
|
)
|
49
|
+
|
50
|
+
turbo_stream = RailsMail::TurboHelper::TurboStreamBuilder.new.prepend(
|
51
|
+
target: "email-sidebar",
|
52
|
+
content: html
|
53
|
+
)
|
54
|
+
|
55
|
+
ActionCable.server.broadcast("rails_mail:emails", turbo_stream)
|
38
56
|
rescue StandardError => e
|
39
57
|
Rails.logger.error "RailsMail::Email#broadcast_email failed: #{e.message}"
|
40
58
|
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
|
2
|
+
<head>
|
3
|
+
<title>RailsMail - <%= yield(:title) if content_for?(:title) %></title>
|
4
|
+
<meta name="viewport" content="width=device-width,initial-scale=1">
|
5
|
+
<%= action_cable_meta_tag if defined?(::ActionCable) %>
|
6
|
+
<%= csrf_meta_tags %>
|
7
|
+
<%= csp_meta_tag %>
|
8
|
+
<%= tag.link rel: "stylesheet", href: frontend_static_path(:style, format: :css, v: RailsMail::VERSION, locale: nil), nonce: content_security_policy_nonce %>
|
9
|
+
|
10
|
+
<%= tag.script "", src: frontend_static_path(:tailwind, format: :js, v: RailsMail::VERSION, locale: nil), nonce: content_security_policy_nonce %>
|
11
|
+
|
12
|
+
<% importmaps = RailsMail::FrontendsController.js_modules.keys.index_with { |module_name| frontend_module_path(module_name, format: :js, locale: nil) } %>
|
13
|
+
<%= tag.script({ imports: importmaps }.to_json.html_safe, type: "importmap", nonce: content_security_policy_nonce) %>
|
14
|
+
<%= tag.script "", type: "module", nonce: content_security_policy_nonce do %> import "application"; <% end %>
|
15
|
+
|
16
|
+
</head>
|
@@ -1,20 +1,6 @@
|
|
1
1
|
<!DOCTYPE html>
|
2
2
|
<html>
|
3
|
-
|
4
|
-
<title>RailsMail - <%= yield(:title) if content_for?(:title) %></title>
|
5
|
-
<meta name="viewport" content="width=device-width,initial-scale=1">
|
6
|
-
<%= action_cable_meta_tag if defined?(::ActionCable) %>
|
7
|
-
<%= csrf_meta_tags %>
|
8
|
-
<%= csp_meta_tag %>
|
9
|
-
<%= tag.link rel: "stylesheet", href: frontend_static_path(:style, format: :css, v: RailsMail::VERSION, locale: nil), nonce: content_security_policy_nonce %>
|
10
|
-
|
11
|
-
<%= tag.script "", src: frontend_static_path(:tailwind, format: :js, v: RailsMail::VERSION, locale: nil), nonce: content_security_policy_nonce %>
|
12
|
-
|
13
|
-
<% importmaps = RailsMail::FrontendsController.js_modules.keys.index_with { |module_name| frontend_module_path(module_name, format: :js, locale: nil) } %>
|
14
|
-
<%= tag.script({ imports: importmaps }.to_json.html_safe, type: "importmap", nonce: content_security_policy_nonce) %>
|
15
|
-
<%= tag.script "", type: "module", nonce: content_security_policy_nonce do %> import "application"; <% end %>
|
16
|
-
|
17
|
-
</head>
|
3
|
+
<%= render "layouts/rails_mail/head" %>
|
18
4
|
|
19
5
|
<body class="bg-gray-100">
|
20
6
|
<div class="flex h-screen relative">
|
@@ -22,7 +8,7 @@
|
|
22
8
|
<input type="checkbox" class="hidden peer" id="sidebar-toggle">
|
23
9
|
|
24
10
|
<!-- Collapsed menu button -->
|
25
|
-
<label for="sidebar-toggle" class="lg:hidden fixed top-4 left-4 z-20 p-2 rounded-md text-gray-600 hover:text-gray-900 hover:bg-gray-100 cursor-pointer peer-checked:hidden">
|
11
|
+
<label for="sidebar-toggle" class="lg:hidden fixed top-4 left-4 z-20 p-2 rounded-md text-gray-600 hover:text-gray-900 hover:bg-gray-100 cursor-pointer peer-checked:hidden bg-gray-200">
|
26
12
|
<svg xmlns="http://www.w3.org/2000/svg" class="h-6 w-6" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
27
13
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
|
28
14
|
</svg>
|
@@ -33,7 +19,7 @@
|
|
33
19
|
<div class="flex-none p-4">
|
34
20
|
<div class="flex items-center justify-between w-full">
|
35
21
|
<!-- Menu icon (visible only on mobile) -->
|
36
|
-
<label for="sidebar-toggle" class="lg:hidden p-2 rounded-md text-gray-600 hover:text-gray-900 hover:bg-gray-100 cursor-pointer">
|
22
|
+
<label for="sidebar-toggle" class="lg:hidden p-2 rounded-md text-gray-600 hover:text-gray-900 hover:bg-gray-100 cursor-pointer bg-gray-200">
|
37
23
|
<svg xmlns="http://www.w3.org/2000/svg" class="h-6 w-6" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
38
24
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
|
39
25
|
</svg>
|
@@ -45,7 +31,7 @@
|
|
45
31
|
<% end %>
|
46
32
|
|
47
33
|
<!-- Clear All button (or empty div for spacing when button is hidden) -->
|
48
|
-
<% if instance_eval(&RailsMail.
|
34
|
+
<% if instance_eval(&RailsMail.show_clear_all_button_callback) %>
|
49
35
|
<%= button_to destroy_all_emails_path,
|
50
36
|
class: "text-sm text-gray-600 hover:text-gray-900",
|
51
37
|
form: { data: { turbo_confirm: "Are you sure you want to clear all emails?" } },
|
@@ -81,9 +67,7 @@
|
|
81
67
|
<!-- Main content -->
|
82
68
|
<div class="flex-1 overflow-y-auto lg:ml-0">
|
83
69
|
<div class="p-8 lg:p-8 sm:p-4">
|
84
|
-
|
85
|
-
<%= yield %>
|
86
|
-
</turbo-frame>
|
70
|
+
<%= yield %>
|
87
71
|
</div>
|
88
72
|
</div>
|
89
73
|
</div>
|
@@ -0,0 +1,28 @@
|
|
1
|
+
<div class="prose max-w-none break-words">
|
2
|
+
<input type="radio" name="email_tab" id="html_tab" class="hidden peer/html" <%= email.html? ? 'checked' : '' %> <%= email.html? ? '' : 'disabled' %> />
|
3
|
+
<label
|
4
|
+
for="html_tab"
|
5
|
+
class="px-4 py-2 text-sm font-medium cursor-pointer peer-checked/html:text-blue-600 peer-checked/html:border-blue-600 peer-checked/html:border-b-2 peer-disabled/html:text-gray-400 peer-disabled/html:cursor-not-allowed">
|
6
|
+
HTML
|
7
|
+
</label>
|
8
|
+
|
9
|
+
<input type="radio" name="email_tab" id="text_tab" class="hidden peer/text" <%= email.text? ? (!email.html? ? 'checked' : '') : 'disabled' %> />
|
10
|
+
<label
|
11
|
+
for="text_tab"
|
12
|
+
class="px-4 py-2 text-sm font-medium cursor-pointer peer-checked/text:text-blue-600 peer-checked/text:border-blue-600 peer-checked/text:border-b-2 peer-disabled/text:text-gray-400 peer-disabled/text:cursor-not-allowed">
|
13
|
+
Text
|
14
|
+
</label>
|
15
|
+
|
16
|
+
<div class="hidden peer-checked/html:block mt-3">
|
17
|
+
<% if email.html? %>
|
18
|
+
<%= sanitize(email.html_body,
|
19
|
+
tags: ActionView::Base.sanitized_allowed_tags + ['table', 'tbody', 'tr', 'td'],
|
20
|
+
attributes: ActionView::Base.sanitized_allowed_attributes + ['style']) %>
|
21
|
+
<% end %>
|
22
|
+
</div>
|
23
|
+
<div class="hidden peer-checked/text:block mt-3 bg-black text-white font-mono p-4 rounded">
|
24
|
+
<% if email.text? %>
|
25
|
+
<%= simple_format email.text_body %>
|
26
|
+
<% end %>
|
27
|
+
</div>
|
28
|
+
</div>
|
@@ -1,21 +1,19 @@
|
|
1
1
|
<turbo-stream action="remove" target="<%= dom_id(@email) %>">
|
2
2
|
</turbo-stream>
|
3
3
|
|
4
|
-
<% if RailsMail::Email.count
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
<% elsif @email.id == @current_email_id.to_i%>
|
11
|
-
<turbo-stream action="update" target="email_content">
|
12
|
-
<template>
|
13
|
-
<div class="" data-controller="redirect" data-redirect-url-value="<%= email_path(@email.next_email) %>">
|
14
|
-
<div class="flex justify-center items-center min-h-screen">
|
15
|
-
<div class="animate-spin rounded-full h-12 w-12 border-b-2 border-gray-900"></div>
|
16
|
-
</div>
|
17
|
-
</div>
|
18
|
-
</template>
|
19
|
-
</turbo-stream>
|
4
|
+
<% path_to_visit = if RailsMail::Email.count.zero?
|
5
|
+
root_path
|
6
|
+
else
|
7
|
+
email_path(@email.next_email)
|
8
|
+
end
|
9
|
+
%>
|
20
10
|
|
21
|
-
|
11
|
+
<turbo-stream action="update" target="email_content">
|
12
|
+
<template>
|
13
|
+
<div class="" data-controller="redirect" data-redirect-url-value="<%= path_to_visit %>">
|
14
|
+
<div class="flex justify-center items-center min-h-screen">
|
15
|
+
<div class="animate-spin rounded-full h-12 w-12 border-b-2 border-gray-900"></div>
|
16
|
+
</div>
|
17
|
+
</div>
|
18
|
+
</template>
|
19
|
+
</turbo-stream>
|
@@ -4,6 +4,8 @@
|
|
4
4
|
</turbo-stream>
|
5
5
|
<turbo-stream action="update" target="email_content">
|
6
6
|
<template>
|
7
|
-
|
7
|
+
<div data-controller="redirect" data-redirect-url-value="<%= emails_path %>">
|
8
|
+
<%= render(partial: "rails_mail/emails/empty_state", formats: [ :html ]) %>
|
9
|
+
</div>
|
8
10
|
</template>
|
9
11
|
</turbo-stream>
|
@@ -1,7 +1,7 @@
|
|
1
1
|
<turbo-stream action="update" target="email-sidebar">
|
2
2
|
<template>
|
3
3
|
<% @emails&.each do |email| %>
|
4
|
-
<%= render partial: "rails_mail/shared/email", locals: {email: email}, formats: [:html] %>
|
4
|
+
<%= render partial: "rails_mail/shared/email", locals: {email: email, email_path: email_path(email) }, formats: [:html] %>
|
5
5
|
<% end %>
|
6
6
|
</template>
|
7
7
|
</turbo-stream>
|
@@ -1,7 +1,8 @@
|
|
1
1
|
<%= rails_mail_turbo_frame_tag "email_content" do %>
|
2
|
-
<div class="bg-white shadow rounded-lg"
|
2
|
+
<div class="bg-white shadow rounded-lg" data-email-id="<%= @email.id %>"
|
3
|
+
data-email-highlight-current-id-value="<%= @email.id %>">
|
3
4
|
<div class="px-6 py-4 border-b border-gray-200">
|
4
|
-
<h1 class="text-2xl font-semibold text-gray-900"><%= @email.subject %></h1>
|
5
|
+
<h1 class="text-2xl font-semibold text-gray-900 break-words"><%= @email.subject %></h1>
|
5
6
|
<div class="mt-2 text-sm text-gray-600">
|
6
7
|
<div>From: <%= @email.from %></div>
|
7
8
|
<div>To: <%= @email.to.join(", ") %></div>
|
@@ -35,8 +36,8 @@
|
|
35
36
|
</div>
|
36
37
|
<% end %>
|
37
38
|
|
38
|
-
<div
|
39
|
-
<%=
|
39
|
+
<div>
|
40
|
+
<%= render "email_tabs", email: @email %>
|
40
41
|
</div>
|
41
42
|
</div>
|
42
43
|
</div>
|
@@ -2,7 +2,7 @@
|
|
2
2
|
on_current_page = current_page?(RailsMail::Engine.routes.url_helpers.email_path(email))
|
3
3
|
highlight_class = on_current_page ? 'bg-gray-300' : ''
|
4
4
|
%>
|
5
|
-
<%= content_tag :div, id: dom_id(email), class: "group flex items-center px-3 py-2 hover:bg-gray-200 #{highlight_class} active:bg-gray-300 focus:bg-gray-300" do %>
|
5
|
+
<%= content_tag :div, id: dom_id(email), class: "group flex items-center px-3 py-2 hover:bg-gray-200 #{highlight_class} active:bg-gray-300 focus:bg-gray-300", data: {testid: "email-row"} do %>
|
6
6
|
<%= link_to RailsMail::Engine.routes.url_helpers.email_path(email),
|
7
7
|
class: "flex-1 min-w-0 rounded-md",
|
8
8
|
data: {
|
@@ -27,15 +27,15 @@
|
|
27
27
|
</div>
|
28
28
|
<% end %>
|
29
29
|
|
30
|
-
<%= button_to email_path
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
30
|
+
<%= button_to email_path,
|
31
|
+
method: :delete,
|
32
|
+
class: "hidden group-hover:block p-1 hover:bg-gray-300 rounded",
|
33
|
+
form: {
|
34
|
+
data: {
|
35
|
+
turbo_confirm: "Are you sure you want to delete this email?",
|
36
|
+
turbo_frame: "_top"
|
37
|
+
},
|
38
|
+
} do %>
|
39
39
|
<svg xmlns="http://www.w3.org/2000/svg" class="h-4 w-4 text-gray-500 transition-colors" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
40
40
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M19 7l-.867 12.142A2 2 0 0116.138 21H7.862a2 2 0 01-1.995-1.858L5 7m5 4v6m4-6v6m1-10V4a1 1 0 00-1-1h-4a1 1 0 00-1 1v3M4 7h16" />
|
41
41
|
</svg>
|
@@ -4,14 +4,14 @@ Rails.configuration.to_prepare do
|
|
4
4
|
RailsMail.configure do |config|
|
5
5
|
# Authentication setup
|
6
6
|
# if left blank, authentication is skipped
|
7
|
-
# config.
|
7
|
+
# config.authenticate do
|
8
8
|
# Example implementation for Authlogic:
|
9
9
|
# user_session = UserSession.find
|
10
10
|
# msg = Rails.env.development? ? 'Forbidden - make sure you have the correct permission in config/initializers/rails_mail.rb' : 'Not Found'
|
11
11
|
# raise ActionController::RoutingError.new(msg) unless user_session&.user&.admin?
|
12
12
|
# end
|
13
13
|
|
14
|
-
config.
|
14
|
+
config.show_clear_all_button do
|
15
15
|
# show clear button in development
|
16
16
|
# and prefer to trim in non-development environments
|
17
17
|
# to prevent accidental deletion of emails
|
@@ -1,29 +1,29 @@
|
|
1
1
|
module RailsMail
|
2
2
|
class Configuration
|
3
|
-
attr_accessor :authentication_callback, :
|
3
|
+
attr_accessor :authentication_callback, :show_clear_all_button_callback,
|
4
4
|
:trim_emails_older_than, :trim_emails_max_count,
|
5
5
|
:enqueue_trim_job
|
6
6
|
|
7
7
|
def initialize
|
8
8
|
@authentication_callback = nil
|
9
|
-
@
|
9
|
+
@show_clear_all_button_callback = nil
|
10
10
|
@trim_emails_older_than = nil
|
11
11
|
@trim_emails_max_count = nil
|
12
12
|
@enqueue_trim_job = ->(email) { RailsMail::TrimEmailsJob.perform_later }
|
13
13
|
end
|
14
14
|
|
15
|
-
def
|
15
|
+
def authenticate(&callback)
|
16
16
|
unless callback.nil? || callback.respond_to?(:call)
|
17
17
|
raise ArgumentError, "authentication_callback must be nil or respond to #call"
|
18
18
|
end
|
19
19
|
@authentication_callback = callback
|
20
20
|
end
|
21
21
|
|
22
|
-
def
|
22
|
+
def show_clear_all_button(&callback)
|
23
23
|
unless callback.nil? || callback.respond_to?(:call)
|
24
|
-
raise ArgumentError, "
|
24
|
+
raise ArgumentError, "show_clear_all_button must be nil or respond to #call"
|
25
25
|
end
|
26
|
-
@
|
26
|
+
@show_clear_all_button_callback = callback
|
27
27
|
end
|
28
28
|
end
|
29
29
|
end
|
@@ -10,7 +10,8 @@ module RailsMail
|
|
10
10
|
cc: mail.cc,
|
11
11
|
bcc: mail.bcc,
|
12
12
|
subject: mail.subject,
|
13
|
-
|
13
|
+
text_part: extract_mail_body_by_type(mail, "text/plain"),
|
14
|
+
html_part: extract_mail_body_by_type(mail, "text/html"),
|
14
15
|
content_type: mail.content_type,
|
15
16
|
attachments: mail.attachments.map { |a| { filename: a.filename, content_type: a.content_type.split(";").first } }
|
16
17
|
)
|
@@ -18,5 +19,16 @@ module RailsMail
|
|
18
19
|
Rails.logger.error("Failed to deliver email: #{e.message}")
|
19
20
|
raise e
|
20
21
|
end
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def extract_mail_body_by_type(mail, mime_type)
|
26
|
+
if mail.multipart?
|
27
|
+
part = mail.parts.find { |p| p.content_type.start_with?(mime_type) }
|
28
|
+
part ? part.body.as_json : nil
|
29
|
+
elsif mail.content_type.start_with?(mime_type)
|
30
|
+
mail.body.as_json
|
31
|
+
end
|
32
|
+
end
|
21
33
|
end
|
22
34
|
end
|
data/lib/rails_mail/version.rb
CHANGED
data/lib/rails_mail.rb
CHANGED
@@ -17,24 +17,12 @@ module RailsMail
|
|
17
17
|
@configuration = Configuration.new
|
18
18
|
end
|
19
19
|
|
20
|
-
def authentication_callback
|
21
|
-
|
22
|
-
@authentication_callback || ->(request) { true }
|
20
|
+
def authentication_callback
|
21
|
+
configuration.authentication_callback || ->(request) { true }
|
23
22
|
end
|
24
23
|
|
25
|
-
def
|
26
|
-
|
27
|
-
@show_clear_button || ->(request) { true }
|
24
|
+
def show_clear_all_button_callback
|
25
|
+
configuration.show_clear_all_button || ->(request) { true }
|
28
26
|
end
|
29
27
|
end
|
30
|
-
|
31
|
-
# class Configuration
|
32
|
-
# def authentication_callback(&block)
|
33
|
-
# RailsMail.authentication_callback(&block)
|
34
|
-
# end
|
35
|
-
|
36
|
-
# def show_clear_button(&block)
|
37
|
-
# RailsMail.show_clear_button?(&block)
|
38
|
-
# end
|
39
|
-
# end
|
40
28
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rails_mail
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.10.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Peter Philips
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2025-
|
11
|
+
date: 2025-04-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -81,12 +81,13 @@ files:
|
|
81
81
|
- app/helpers/rails_mail/turbo_helper.rb
|
82
82
|
- app/jobs/rails_mail/trim_emails_job.rb
|
83
83
|
- app/models/rails_mail/email.rb
|
84
|
+
- app/views/layouts/rails_mail/_head.html.erb
|
84
85
|
- app/views/layouts/rails_mail/_title.html.erb
|
85
86
|
- app/views/layouts/rails_mail/application.html.erb
|
86
87
|
- app/views/rails_mail/emails/_email.html.erb
|
88
|
+
- app/views/rails_mail/emails/_email_tabs.html.erb
|
87
89
|
- app/views/rails_mail/emails/_empty_state.html.erb
|
88
90
|
- app/views/rails_mail/emails/_form.html.erb
|
89
|
-
- app/views/rails_mail/emails/_show.html.erb
|
90
91
|
- app/views/rails_mail/emails/destroy.turbo_stream.erb
|
91
92
|
- app/views/rails_mail/emails/destroy_all.turbo_stream.erb
|
92
93
|
- app/views/rails_mail/emails/edit.html.erb
|
@@ -129,7 +130,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
129
130
|
- !ruby/object:Gem::Version
|
130
131
|
version: '0'
|
131
132
|
requirements: []
|
132
|
-
rubygems_version: 3.5.
|
133
|
+
rubygems_version: 3.5.22
|
133
134
|
signing_key:
|
134
135
|
specification_version: 4
|
135
136
|
summary: Database-backed Action Mailer delivery method with web interface
|
@@ -1,50 +0,0 @@
|
|
1
|
-
<%= rails_mail_turbo_frame_tag "email_content" do %>
|
2
|
-
<div class="bg-white shadow rounded-lg" data-email-id="<%= email.id %>"
|
3
|
-
data-email-highlight-current-id-value="<%= email.id %>">
|
4
|
-
<div class="px-6 py-4 border-b border-gray-200">
|
5
|
-
<h1 class="text-2xl font-semibold text-gray-900"><%= email.subject %></h1>
|
6
|
-
<div class="mt-2 text-sm text-gray-600">
|
7
|
-
<div>From: <%= email.from %></div>
|
8
|
-
<div>To: <%= email.to.join(", ") %></div>
|
9
|
-
<% if email.cc.present? %>
|
10
|
-
<div>CC: <%= email.cc.join(", ") %></div>
|
11
|
-
<% end %>
|
12
|
-
<% if email.bcc.present? %>
|
13
|
-
<div>BCC: <%= email.bcc.join(", ") %></div>
|
14
|
-
<% end %>
|
15
|
-
<div class="text-gray-400 mt-1">
|
16
|
-
<%= email.created_at.strftime("%B %d, %Y at %I:%M %p") %>
|
17
|
-
</div>
|
18
|
-
</div>
|
19
|
-
</div>
|
20
|
-
|
21
|
-
<div class="px-6 py-4">
|
22
|
-
<% if email.attachments.present? %>
|
23
|
-
<div class="mb-4 p-4 bg-gray-50 rounded-md">
|
24
|
-
<h3 class="text-sm font-medium text-gray-900 mb-2">Attachments</h3>
|
25
|
-
<div class="space-y-2">
|
26
|
-
<% email.attachments.each do |attachment| %>
|
27
|
-
<div class="flex items-center text-sm">
|
28
|
-
<svg class="h-5 w-5 text-gray-400 mr-2" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
29
|
-
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15.172 7l-6.586 6.586a2 2 0 102.828 2.828l6.414-6.586a4 4 0 00-5.656-5.656l-6.415 6.585a6 6 0 108.486 8.486L20.5 13" />
|
30
|
-
</svg>
|
31
|
-
<span><%= attachment["filename"] %></span>
|
32
|
-
<span class="ml-2 text-gray-500">(<%= attachment["content_type"] %>)</span>
|
33
|
-
</div>
|
34
|
-
<% end %>
|
35
|
-
</div>
|
36
|
-
</div>
|
37
|
-
<% end %>
|
38
|
-
|
39
|
-
<div class="prose max-w-none">
|
40
|
-
<% if email.html? %>
|
41
|
-
<%= sanitize(email.body,
|
42
|
-
tags: ActionView::Base.sanitized_allowed_tags + ['table', 'tbody', 'tr', 'td'],
|
43
|
-
attributes: ActionView::Base.sanitized_allowed_attributes + ['style']) %>
|
44
|
-
<% else %>
|
45
|
-
<%= simple_format email.body %>
|
46
|
-
<% end %>
|
47
|
-
</div>
|
48
|
-
</div>
|
49
|
-
</div>
|
50
|
-
<% end %>
|