maily 0.6.3 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (48) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -0
  3. data/.travis.yml +5 -11
  4. data/Appraisals +4 -0
  5. data/CHANGELOG.md +90 -0
  6. data/MIT-LICENSE +1 -1
  7. data/README.md +21 -2
  8. data/app/assets/images/maily/icons/globe.svg +13 -0
  9. data/app/assets/images/maily/icons/paperclip.svg +8 -0
  10. data/app/assets/images/maily/logo.png +0 -0
  11. data/app/assets/stylesheets/maily/_variables.scss +6 -0
  12. data/app/assets/stylesheets/maily/application.scss +88 -96
  13. data/app/assets/stylesheets/maily/normalize.css +23 -129
  14. data/app/controllers/maily/emails_controller.rb +10 -5
  15. data/app/helpers/maily/application_helper.rb +15 -1
  16. data/app/helpers/maily/emails_helper.rb +10 -1
  17. data/app/views/layouts/maily/application.html.erb +5 -5
  18. data/app/views/maily/emails/edit.html.erb +16 -18
  19. data/app/views/maily/emails/index.html.erb +2 -4
  20. data/app/views/maily/emails/show.html.erb +61 -64
  21. data/app/views/maily/shared/_flash_messages.html.erb +7 -0
  22. data/app/views/maily/shared/_header.html.erb +4 -1
  23. data/app/views/maily/shared/_sidebar.html.erb +2 -2
  24. data/gemfiles/rails_4.2.gemfile +2 -2
  25. data/gemfiles/rails_5.0.gemfile +1 -1
  26. data/gemfiles/rails_5.1.gemfile +1 -1
  27. data/gemfiles/rails_5.2.gemfile +7 -0
  28. data/lib/maily.rb +1 -3
  29. data/lib/maily/email.rb +18 -13
  30. data/lib/maily/mailer.rb +32 -14
  31. data/lib/maily/version.rb +1 -1
  32. data/maily.gemspec +1 -2
  33. data/screenshot.png +0 -0
  34. data/spec/controllers_spec.rb +40 -1
  35. data/spec/dummy/app/mailers/notifier.rb +8 -0
  36. data/spec/dummy/lib/maily_hooks.rb +3 -0
  37. data/spec/email_spec.rb +5 -0
  38. data/spec/mailer_spec.rb +6 -1
  39. data/spec/maily_spec.rb +1 -1
  40. data/spec/spec_helper.rb +1 -0
  41. metadata +10 -26
  42. data/app/assets/images/maily/icons/maily.eot +0 -0
  43. data/app/assets/images/maily/icons/maily.svg +0 -90
  44. data/app/assets/images/maily/icons/maily.ttf +0 -0
  45. data/app/assets/images/maily/icons/maily.woff +0 -0
  46. data/app/assets/stylesheets/maily/icons.css +0 -199
  47. data/spec/dummy/app/mailers/.keep +0 -0
  48. data/spec/dummy/lib/assets/.keep +0 -0
@@ -1,73 +1,70 @@
1
- <div class="content">
2
- <% if @maily_email.description %>
3
- <div>
4
- <b>Description </b><%= @maily_email.description %>
5
- </div><br>
6
- <% end %>
7
-
8
- <ul class="maily_action_bar">
9
- <li>
10
- <em class="icon-maily-pencil"></em>
11
- <%= link_to 'Edit', edit_maily_email_path(mailer: params[:mailer], email: params[:email], part: params[:part]) %>
12
- </li>
13
-
14
- <li class="maily_languages">
15
- <% if Maily.available_locales.present? %>
16
- <ul>
17
- <li>
18
- <em class="icon-maily-earth"></em>
19
- Languages</li>
20
- <% Maily.available_locales.each do |locale| %>
21
- <li><%= link_to locale.upcase, url_for(params.to_unsafe_h.merge(locale: locale)) %></li>
22
- <% end %>
23
- </ul>
24
- <% end %>
25
- </li>
26
-
27
- <li class="maily_splitter">|</li>
28
- <li>
29
- <%= form_tag(deliver_maily_email_path(mailer: params[:mailer], email: params[:email], locale: params[:locale]), method: :post, class: 'maily_send') do %>
30
- <ul>
31
- <li>Send to</li>
32
- <li><%= email_field_tag :to, nil, class: 'maily_textfield', placeholder: "Enter email", required: true %></li>
33
- <li><%= submit_tag 'Send', class: 'maily_button' %></li>
34
- </ul>
35
- <% end %>
36
- </li>
37
- </ul>
1
+ <%= email_description(@maily_email) %>
38
2
 
39
- <div class="maily_mail_preview">
40
- <ul class="maily_mail_details">
41
- <% if @email.subject %><li><b>Subject</b> <%= @email.subject %></li><% end %>
42
- <% if @email.from %><li><b>From</b> <%= @email.from.join(', ') %></li><% end %>
43
- <% if @email.to %><li><b>To</b> <%= @email.to.join(', ') %></li><% end %>
44
- <% if @email.cc %><li><b>Cc</b> <%= @email.cc.join(', ') %></li><% end %>
45
- <% if @email.bcc %><li><b>Bcc</b> <%= @email.bcc.join(', ') %></li><% end %>
46
- <% if @email.reply_to %><li><b>Reply to</b> <%= @email.reply_to.join(', ') %></li><% end %>
47
- </ul>
3
+ <ul class="action_bar">
4
+ <li>
5
+ <%= link_to 'Edit', edit_maily_email_path(mailer: params[:mailer], email: params[:email], part: params[:part]) %>
6
+ </li>
48
7
 
49
- <% if @email.html_part && @email.text_part %>
50
- <ul class="maily_format_mail">
51
- <li><%= link_to 'HTML', url_for(params.to_unsafe_h.merge(part: 'html')), class: part_class('html') %></li>
52
- <li><%= link_to 'TEXT', url_for(params.to_unsafe_h.merge(part: 'text')), class: part_class('text') %></li>
8
+ <li class="languages">
9
+ <% if Maily.available_locales.present? %>
10
+ <ul>
11
+ <li>
12
+ <%= icon 'globe' %> Languages
13
+ </li>
14
+ <% Maily.available_locales.each do |locale| %>
15
+ <li><%= link_to locale.upcase, url_for(params.to_unsafe_h.merge(locale: locale)) %></li>
16
+ <% end %>
53
17
  </ul>
54
18
  <% end %>
19
+ </li>
55
20
 
56
- <% if @email.html_part || @email.text_part || @email.body.present? %>
57
- <iframe class="maily_preview" onload='javascript:resizeIframe(this);' src="<%= raw_maily_email_path(mailer: params[:mailer], email: params[:email], locale: params[:locale], part: params[:part]) %>" frameborder="1" width="100%"></iframe>
58
- <% end %>
21
+ <li class="splitter">|</li>
59
22
 
60
- <% if @email.attachments.present? %>
61
- <ul class="maily_mail_attachments">
62
- <li>Attachments:</li>
63
- <li>
64
- <ul>
65
- <% @email.attachments.each do |attachment| %>
66
- <li><em class="icon-maily-attachment"></em><%= link_to attachment.filename, attachment_maily_email_path(mailer: params[:mailer], email: params[:email], attachment: attachment.filename) %></li>
67
- <% end %>
68
- </ul>
69
- </li>
23
+ <li>
24
+ <%= form_tag(deliver_maily_email_path(mailer: params[:mailer], email: params[:email], locale: params[:locale]), method: :post, class: 'mail_deliver') do %>
25
+ <ul>
26
+ <li>Send to</li>
27
+ <li><%= email_field_tag :to, nil, placeholder: "Enter email", required: true %></li>
28
+ <li><%= submit_tag 'Send', class: 'button' %></li>
70
29
  </ul>
71
30
  <% end %>
72
- </div>
31
+ </li>
32
+ </ul>
33
+
34
+ <div class="mail_preview">
35
+ <ul class="mail_details">
36
+ <% if @email.subject %><li><b>Subject</b> <%= @email.subject %></li><% end %>
37
+ <% if @email.from %><li><b>From</b> <%= @email.from.join(', ') %></li><% end %>
38
+ <% if @email.to %><li><b>To</b> <%= @email.to.join(', ') %></li><% end %>
39
+ <% if @email.cc %><li><b>Cc</b> <%= @email.cc.join(', ') %></li><% end %>
40
+ <% if @email.bcc %><li><b>Bcc</b> <%= @email.bcc.join(', ') %></li><% end %>
41
+ <% if @email.reply_to %><li><b>Reply to</b> <%= @email.reply_to.join(', ') %></li><% end %>
42
+ </ul>
43
+
44
+ <% if @email.html_part && @email.text_part %>
45
+ <ul class="format_mail">
46
+ <li><%= link_to 'HTML', url_for(params.to_unsafe_h.merge(part: 'html')), class: part_class('html') %></li>
47
+ <li><%= link_to 'TEXT', url_for(params.to_unsafe_h.merge(part: 'text')), class: part_class('text') %></li>
48
+ </ul>
49
+ <% end %>
50
+
51
+ <% if @email.html_part || @email.text_part || @email.body.present? %>
52
+ <iframe class="mail_iframe" onload='resizeIframe(this)' src="<%= raw_maily_email_path(mailer: params[:mailer], email: params[:email], locale: params[:locale], part: params[:part]) %>" frameborder="1" width="100%"></iframe>
53
+ <% end %>
54
+
55
+ <% if @email.attachments.present? %>
56
+ <ul class="mail_attachments">
57
+ <li>Attachments:</li>
58
+ <li>
59
+ <ul>
60
+ <% @email.attachments.each do |attachment| %>
61
+ <li>
62
+ <%= icon 'paperclip' %>
63
+ <%= link_to attachment.filename, attachment_maily_email_path(mailer: params[:mailer], email: params[:email], attachment: attachment.filename) %>
64
+ </li>
65
+ <% end %>
66
+ </ul>
67
+ </li>
68
+ </ul>
69
+ <% end %>
73
70
  </div>
@@ -0,0 +1,7 @@
1
+ <% if flash[:alert].present? %>
2
+ <div class="alert alert-warning"><%= flash[:alert].html_safe %></div>
3
+ <% end %>
4
+
5
+ <% if flash[:notice].present? %>
6
+ <div class="alert alert-success"><%= flash[:notice].html_safe %></div>
7
+ <% end %>
@@ -1,3 +1,6 @@
1
1
  <header class="header">
2
- <a href="<%= root_path %>" class="logo_link"><em class="icon-maily-envelope"></em>Maily</a>
2
+ <a href="<%= root_path %>" class="logo_link">
3
+ <%= image_tag 'maily/logo.png', align: 'center', width: 45 %>
4
+ <span>Maily</span>
5
+ </a>
3
6
  </header>
@@ -1,9 +1,9 @@
1
1
  <aside class="sidebar">
2
2
  <% @mailers.sort_by(&:name).each do |mailer| %>
3
3
  <section class="nav_list">
4
- <h3 class="title nav_title"><%= "#{mailer.name.humanize} (#{mailer.emails.length})" %></h3>
4
+ <h3 class="nav_title"><%= "#{mailer.name.humanize} (#{mailer.total_emails})" %></h3>
5
5
  <ul>
6
- <% mailer.emails.sort_by(&:name).each do |email| %>
6
+ <% mailer.emails.values.sort_by(&:name).each do |email| %>
7
7
  <li><%= link_to email.name.humanize, maily_email_path(mailer: mailer.name, email: email.name), class: sidebar_class(mailer, email) %></li>
8
8
  <% end %>
9
9
  </ul>
@@ -2,6 +2,6 @@
2
2
 
3
3
  source "https://rubygems.org"
4
4
 
5
- gem "rails", github: "rails/rails", branch: "4-2-stable"
5
+ gem "rails", :github => "rails/rails", :branch => "4-2-stable"
6
6
 
7
- gemspec path: "../"
7
+ gemspec :path => "../"
@@ -4,4 +4,4 @@ source "https://rubygems.org"
4
4
 
5
5
  gem "rails", "~> 5.0.0"
6
6
 
7
- gemspec path: "../"
7
+ gemspec :path => "../"
@@ -4,4 +4,4 @@ source "https://rubygems.org"
4
4
 
5
5
  gem "rails", "~> 5.1.0"
6
6
 
7
- gemspec path: "../"
7
+ gemspec :path => "../"
@@ -0,0 +1,7 @@
1
+ # This file was generated by Appraisal
2
+
3
+ source "https://rubygems.org"
4
+
5
+ gem "rails", "~> 5.2.0"
6
+
7
+ gemspec :path => "../"
@@ -23,9 +23,7 @@ module Maily
23
23
  # Load emails from file system
24
24
  Dir[Rails.root + 'app/mailers/*.rb'].each do |mailer|
25
25
  klass_name = File.basename(mailer, '.rb')
26
- klass = klass_name.camelize.constantize
27
- methods = klass.send(:public_instance_methods, false)
28
- Maily::Mailer.new(klass_name, methods)
26
+ Maily::Mailer.new(klass_name)
29
27
  end
30
28
 
31
29
  # Load hooks
@@ -1,15 +1,20 @@
1
1
  module Maily
2
2
  class Email
3
- attr_accessor :name, :mailer, :arguments, :template_path, :description
3
+ attr_accessor :name, :mailer, :arguments, :template_path, :template_name, :description
4
4
 
5
5
  def initialize(name, mailer)
6
- self.name = name.to_s
6
+ self.name = name
7
7
  self.mailer = mailer
8
8
  self.arguments = nil
9
- self.template_path = mailer
9
+ self.template_path = mailer.name
10
+ self.template_name = name
10
11
  self.description = nil
11
12
  end
12
13
 
14
+ def mailer_klass
15
+ mailer.klass
16
+ end
17
+
13
18
  def parameters
14
19
  mailer_klass.instance_method(name).parameters
15
20
  end
@@ -45,21 +50,21 @@ module Maily
45
50
 
46
51
  if args.last.is_a?(Hash)
47
52
  self.description = args.last.delete(:description)
48
- self.template_path = args.last.delete(:template_path)
53
+
54
+ if tpl_path = args.last.delete(:template_path)
55
+ self.template_path = tpl_path
56
+ end
57
+
58
+ if tpl_name = args.last.delete(:template_name)
59
+ self.template_name = tpl_name
60
+ end
61
+
49
62
  args.pop
50
63
  end
51
64
 
52
65
  self.arguments = args
53
66
  end
54
67
 
55
- def mailer_klass_name
56
- mailer.camelize
57
- end
58
-
59
- def mailer_klass
60
- mailer_klass_name.constantize
61
- end
62
-
63
68
  def call
64
69
  *args = arguments && arguments.map { |arg| arg.respond_to?(:call) ? arg.call : arg }
65
70
 
@@ -71,7 +76,7 @@ module Maily
71
76
  end
72
77
 
73
78
  def base_path(part)
74
- "#{Rails.root}/app/views/#{template_path}/#{name}.#{part}.erb"
79
+ "#{Rails.root}/app/views/#{template_path}/#{template_name}.#{part}.erb"
75
80
  end
76
81
 
77
82
  def path(part = nil)
@@ -1,13 +1,17 @@
1
1
  module Maily
2
2
  class Mailer
3
3
  cattr_accessor :collection
4
- attr_accessor :name, :emails
4
+ attr_accessor :name, :emails, :klass
5
5
 
6
- def initialize(name, methods)
7
- self.collection ||= []
8
- self.name = name
9
- self.emails = self.class.build_emails(methods, name)
10
- self.collection << self
6
+ def initialize(name)
7
+ self.name = name
8
+ self.klass = name.camelize.constantize
9
+ self.emails = {}
10
+
11
+ parse_emails
12
+
13
+ self.class.collection ||= {}
14
+ self.class.collection[name] = self
11
15
  end
12
16
 
13
17
  def self.all
@@ -16,22 +20,36 @@ module Maily
16
20
  end
17
21
 
18
22
  def self.find(mailer_name)
19
- all.find { |mailer| mailer.name == mailer_name }
23
+ all[mailer_name]
20
24
  end
21
25
 
22
- def self.build_emails(methods, mailer)
23
- methods.map do |email|
24
- Maily::Email.new(email, mailer)
25
- end
26
+ def find_email(email_name)
27
+ emails[email_name.to_s]
28
+ end
29
+
30
+ def total_emails
31
+ emails.size
26
32
  end
27
33
 
28
34
  def register_hook(email_name, *args)
29
35
  email = find_email(email_name)
30
- email.register_hook(args)
36
+ email && email.register_hook(args)
31
37
  end
32
38
 
33
- def find_email(email_name)
34
- emails.find { |email| email.name == email_name.to_s }
39
+ def hide_email(*email_names)
40
+ email_names.each do |email_name|
41
+ emails.delete(email_name.to_s)
42
+ end
43
+ end
44
+
45
+ private
46
+
47
+ def parse_emails
48
+ _emails = klass.send(:public_instance_methods, false)
49
+
50
+ _emails.map(&:to_s).each do |email|
51
+ self.emails[email] = Maily::Email.new(email, self)
52
+ end
35
53
  end
36
54
  end
37
55
  end
@@ -1,3 +1,3 @@
1
1
  module Maily
2
- VERSION = "0.6.3"
2
+ VERSION = "0.7.0"
3
3
  end
@@ -19,6 +19,5 @@ Gem::Specification.new do |s|
19
19
 
20
20
  s.add_development_dependency "rspec-rails"
21
21
  s.add_development_dependency "appraisal"
22
- s.add_development_dependency 'test-unit', '~> 3.0'
23
- s.add_development_dependency "byebug" if RUBY_VERSION.to_i >= 2
22
+ s.add_development_dependency "byebug"
24
23
  end
Binary file
@@ -1,6 +1,15 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Maily::EmailsController, type: :controller do
4
+ # Rails 4 <-> 5 compatibility
5
+ def compatible_get(action, **params)
6
+ if ::Rails::VERSION::STRING > '5'
7
+ get action, params: params
8
+ else
9
+ get action, params
10
+ end
11
+ end
12
+
4
13
  routes { Maily::Engine.routes }
5
14
 
6
15
  before(:each) do
@@ -11,22 +20,52 @@ describe Maily::EmailsController, type: :controller do
11
20
  expect { get :index }.not_to raise_error
12
21
  end
13
22
 
14
- it 'raise error if disabled' do
23
+ it 'raises 404 if disabled' do
15
24
  Maily.enabled = false
25
+
16
26
  get :index
27
+
17
28
  expect(response.status).to eq(404)
18
29
  end
19
30
 
20
31
  it 'responds with 401 if http authorization fails' do
21
32
  Maily.http_authorization = { username: 'admin', password: 'admin' }
33
+
22
34
  get :index
35
+
23
36
  expect(response.status).to eq(401)
24
37
  end
25
38
 
26
39
  it 'responds ok with valid http authorization' do
27
40
  Maily.http_authorization = { username: 'admin', password: 'admin' }
28
41
  request.env['HTTP_AUTHORIZATION'] = ActionController::HttpAuthentication::Basic.encode_credentials('admin', 'admin')
42
+
29
43
  get :index
44
+
30
45
  expect(response.status).to eq(200)
31
46
  end
47
+
48
+ describe 'non-existent emails' do
49
+ it 'email not in the system -> 302' do
50
+ compatible_get :show, mailer: 'notifier', email: 'non_existent_email'
51
+
52
+ expect(response.status).to eq(302)
53
+ expect(flash.alert).to eq("Email not found!")
54
+ end
55
+
56
+ it 'hidden emails -> 302' do
57
+ compatible_get :show, mailer: 'notifier', email: 'hidden'
58
+
59
+ expect(response.status).to eq(302)
60
+ expect(flash.alert).to eq("Email not found!")
61
+ end
62
+ end
63
+
64
+ describe 'GET #raw' do
65
+ it 'renders the template' do
66
+ compatible_get :raw, mailer: 'notifier', email: 'invitation'
67
+
68
+ expect(response.body).to match("<h1>Invitation</h1>")
69
+ end
70
+ end
32
71
  end
@@ -12,4 +12,12 @@ class Notifier < ActionMailer::Base
12
12
  def recommendation(email)
13
13
  mail template_path: 'notifications'
14
14
  end
15
+
16
+ def custom_template_name
17
+ mail template_name: 'invitation'
18
+ end
19
+
20
+ def hidden
21
+ mail
22
+ end
15
23
  end
@@ -3,4 +3,7 @@ email = -> { 'foo@foo.com' }
3
3
  Maily.hooks_for('Notifier') do |mailer|
4
4
  mailer.register_hook(:invitation, email)
5
5
  mailer.register_hook(:recommendation, template_path: 'notifications', description: 'description')
6
+ mailer.register_hook(:custom_template_name, template_name: 'invitation')
7
+
8
+ mailer.hide_email(:hidden)
6
9
  end