Commit d215b23272bc035473d4d686d57f81bb5e99f412

Authored by Victor Costa
1 parent e083ea4a

Option to choose template to send email to members

app/controllers/my_profile/email_templates_controller.rb 0 → 100644
... ... @@ -0,0 +1,63 @@
  1 +class EmailTemplatesController < MyProfileController
  2 +
  3 + protect 'send_mail_to_members', :profile
  4 +
  5 + def index
  6 + @email_templates = profile.email_templates
  7 + end
  8 +
  9 + def show
  10 + @email_template = profile.email_templates.find(params[:id])
  11 +
  12 + respond_to do |format|
  13 + format.html # show.html.erb
  14 + format.json { render json: @email_template }
  15 + end
  16 + end
  17 +
  18 + def show_parsed
  19 + @email_template = profile.email_templates.find(params[:id])
  20 + template_params = {:profile => profile, :environment => environment}
  21 + render json: {:parsed_body => @email_template.parsed_body(template_params), :parsed_subject => @email_template.parsed_subject(template_params)}
  22 + end
  23 +
  24 + def new
  25 + @email_template = profile.email_templates.build
  26 + end
  27 +
  28 + def edit
  29 + @email_template = profile.email_templates.find(params[:id])
  30 + end
  31 +
  32 + def create
  33 + @email_template = profile.email_templates.build(params[:email_template], :owner => profile)
  34 +
  35 + if @email_template.save
  36 + session[:notice] = _('Email template was successfully created.')
  37 + redirect_to url_for(:action => :index)
  38 + else
  39 + render action: "new"
  40 + end
  41 + end
  42 +
  43 + def update
  44 + @email_template = profile.email_templates.find(params[:id])
  45 +
  46 + if @email_template.update_attributes(params[:email_template])
  47 + session[:notice] = _('Email template was successfully updated.')
  48 + redirect_to url_for(:action => :index)
  49 + else
  50 + render action: "edit"
  51 + end
  52 + end
  53 +
  54 + def destroy
  55 + @email_template = profile.email_templates.find(params[:id])
  56 + @email_template.destroy
  57 +
  58 + respond_to do |format|
  59 + format.html { redirect_to url_for(:action => :index)}
  60 + format.json { head :no_content }
  61 + end
  62 + end
  63 +end
... ...
app/controllers/public/profile_controller.rb
... ... @@ -353,6 +353,7 @@ class ProfileController &lt; PublicController
353 353  
354 354 def send_mail
355 355 @mailing = profile.mailings.build(params[:mailing])
  356 + @email_templates = profile.email_templates
356 357 if request.post?
357 358 @mailing.locale = locale
358 359 @mailing.person = user
... ...
app/models/email_template.rb
... ... @@ -4,6 +4,8 @@ class EmailTemplate &lt; ActiveRecord::Base
4 4  
5 5 attr_accessible :template_type, :subject, :body, :owner, :name
6 6  
  7 + validates_presence_of :name
  8 +
7 9 def parsed_body(params)
8 10 @parsed_body ||= parse(body, params)
9 11 end
... ...
app/models/environment.rb
... ... @@ -982,6 +982,10 @@ class Environment &lt; ActiveRecord::Base
982 982 self.licenses.any?
983 983 end
984 984  
  985 + def to_liquid
  986 + HashWithIndifferentAccess.new :name => name
  987 + end
  988 +
985 989 private
986 990  
987 991 def default_language_available
... ...
app/models/profile.rb
... ... @@ -151,6 +151,8 @@ class Profile &lt; ActiveRecord::Base
151 151  
152 152 has_many :comments_received, :class_name => 'Comment', :through => :articles, :source => :comments
153 153  
  154 + has_many :email_templates, :foreign_key => :owner_id
  155 +
154 156 # Although this should be a has_one relation, there are no non-silly names for
155 157 # a foreign key on article to reference the template to which it is
156 158 # welcome_page... =P
... ... @@ -471,6 +473,10 @@ class Profile &lt; ActiveRecord::Base
471 473 self.articles.find(:all, options)
472 474 end
473 475  
  476 + def to_liquid
  477 + HashWithIndifferentAccess.new :name => name, :identifier => identifier
  478 + end
  479 +
474 480 class << self
475 481  
476 482 # finds a profile by its identifier. This method is a shortcut to
... ...
app/views/email_templates/_form.html.erb 0 → 100644
... ... @@ -0,0 +1,30 @@
  1 +<%= form_for(@email_template, :url => {:controller => :email_templates, :action => @email_template.persisted? ? :update : :create, :id => @email_template.id}) do |f| %>
  2 +
  3 + <%= error_messages_for :email_template if @email_template.errors.any? %>
  4 +
  5 + <div class="template-fields">
  6 + <div class="header-fields">
  7 + <%= labelled_form_field(_('Template Name:'), f.text_field(:name)) %>
  8 + <%= labelled_form_field(_('Subject:'), f.text_field(:subject)) %>
  9 + </div>
  10 + <div class="available-params">
  11 + <div class="reference">
  12 + <a target="_blank" href="https://github.com/Shopify/liquid/wiki/Liquid-for-Designers"><%= _('Template language reference') %></a>
  13 + </div>
  14 + <div class="label">
  15 + <%= _('The following parameters may be used in subject and body:') %>
  16 + </div>
  17 + <div class="values">
  18 + {{profile.name}}, {{profile.identifier}}, {{environment.name}}
  19 + </div>
  20 + </div>
  21 + <%= render :file => 'shared/tiny_mce' %>
  22 + <%= labelled_form_field(_('Body:'), f.text_area(:body, :class => 'mceEditor')) %>
  23 + </div>
  24 +
  25 + <div class="actions">
  26 + <%= submit_button(:save, _('Save')) %>
  27 + <%= button(:back, _('Back'), :controller => :email_templates) %>
  28 + </div>
  29 +
  30 +<% end %>
... ...
app/views/email_templates/edit.html.erb 0 → 100644
... ... @@ -0,0 +1,3 @@
  1 +<h1>Editing Email Template</h1>
  2 +
  3 +<%= render 'form' %>
... ...
app/views/email_templates/index.html.erb 0 → 100644
... ... @@ -0,0 +1,23 @@
  1 +<h1><%= _('Email Templates') %></h1>
  2 +
  3 +<table>
  4 + <tr>
  5 + <th><%= _('Name') %></th>
  6 + <th></th>
  7 + </tr>
  8 +
  9 +<% @email_templates.each do |email_template| %>
  10 + <tr>
  11 + <td><%= email_template.name %></td>
  12 + <td>
  13 + <%= link_to 'Edit', url_for(:controller => :email_templates, :action => :edit, :id => email_template.id) %>
  14 + <%= link_to 'Destroy', url_for(:controller => :email_templates, :action => :destroy, :id => email_template.id), method: :delete, data: { confirm: 'Are you sure?' } %>
  15 + </td>
  16 + </tr>
  17 +<% end %>
  18 +</table>
  19 +
  20 +<br />
  21 +
  22 +<%= button(:new, _('New template'), :controller => :email_templates, :action => :new) %>
  23 +<%= button(:back, _('Back to control panel'), :controller => :profile_editor) %>
... ...
app/views/email_templates/new.html.erb 0 → 100644
... ... @@ -0,0 +1,3 @@
  1 +<h1>New Email Template</h1>
  2 +
  3 +<%= render 'form' %>
... ...
app/views/email_templates/show.html.erb 0 → 100644
... ... @@ -0,0 +1,5 @@
  1 +<p id="notice"><%= notice %></p>
  2 +
  3 +
  4 +<%= link_to 'Edit', url_for(:controller => :email_templates, :action => :edit, :id => @email_template.id) %> |
  5 +<%= link_to 'Back', url_for(:controller => :email_templates) %>
... ...
app/views/profile/send_mail.html.erb
... ... @@ -4,6 +4,12 @@
4 4  
5 5 <%= error_messages_for :mailing %>
6 6  
  7 +<div class="template-selection">
  8 + <% if @email_templates.present? %>
  9 + <%= labelled_form_field(_('Select a template:'), select_tag(:template, options_from_collection_for_select(@email_templates, :id, :name), :include_blank => true, 'data-url' => url_for(:controller => 'email_templates', :action => 'show_parsed'))) %>
  10 + <% end %>
  11 +</div>
  12 +
7 13 <%= form_for :mailing, :url => {:action => 'send_mail'}, :html => {:id => 'mailing-form'} do |f| %>
8 14  
9 15 <%= labelled_form_field(_('Subject:'), f.text_field(:subject)) %>
... ...
app/views/profile_editor/index.html.erb
... ... @@ -72,6 +72,8 @@
72 72  
73 73 <%= control_panel_button(_('Edit welcome page'), 'welcome-page', :action => 'welcome_page') if has_welcome_page %>
74 74  
  75 + <%= control_panel_button(_('Email Templates'), 'email-templates', :controller => :email_templates) if profile.organization? %>
  76 +
75 77 <% @plugins.dispatch(:control_panel_buttons).each do |button| %>
76 78 <%= control_panel_button(button[:title], button[:icon], button[:url], button[:html_options]) %>
77 79 <% end %>
... ...
public/javascripts/application.js
... ... @@ -28,6 +28,7 @@
28 28 *= require catalog.js
29 29 *= require autogrow.js
30 30 *= require require_login.js
  31 +*= require email_templates.js
31 32 */
32 33  
33 34 // scope for noosfero stuff
... ...
public/javascripts/email_templates.js 0 → 100644
... ... @@ -0,0 +1,10 @@
  1 +jQuery(document).ready(function($) {
  2 + $('.template-selection select').change(function() {
  3 + if(!$(this).val()) return;
  4 +
  5 + $.getJSON($(this).data('url'), {id: $(this).val()}, function(data) {
  6 + $('#mailing-form #mailing_subject').val(data.parsed_subject);
  7 + $('#mailing-form .mceEditor').val(data.parsed_body);
  8 + });
  9 + });
  10 +});
... ...
public/proposal-app 0 → 160000
... ... @@ -0,0 +1 @@
  1 +Subproject commit e7ad7849b3ef685639d4c5c0bef7b323255e2afa
... ...
public/stylesheets/application.css
... ... @@ -14,6 +14,7 @@
14 14 * views specifics
15 15 *= require chat
16 16 *= require search
  17 + *= require email-templates
17 18 */
18 19  
19 20 /* browser fixes */
... ... @@ -4658,6 +4659,9 @@ h1#agenda-title {
4658 4659 .controller-profile_editor a.control-panel-design-editor {
4659 4660 background-image: url(../images/control-panel/preferences-desktop-wallpaper.png)
4660 4661 }
  4662 +.controller-profile_editor a.control-panel-email-templates {
  4663 + background-image: url(../images/control-panel/email.png)
  4664 +}
4661 4665 .controller-profile_editor .msie6 a.control-panel-design-editor {
4662 4666 background-image: url(../images/control-panel/preferences-desktop-wallpaper.gif)
4663 4667 }
... ...
public/stylesheets/email-templates.css 0 → 100644
... ... @@ -0,0 +1,15 @@
  1 +.template-fields .header-fields, .template-fields .available-params {
  2 + width: 48%;
  3 + display: inline-block;
  4 +}
  5 +.template-fields .available-params .values {
  6 + color: rgb(111, 111, 111);
  7 +}
  8 +.template-fields .available-params .reference {
  9 + text-align: right;
  10 +}
  11 +.template-fields .available-params .reference a {
  12 + color: rgb(32, 101, 229);
  13 + text-decoration: none;
  14 + font-size: 10px;
  15 +}
... ...
test/functional/email_templates_controller_test.rb 0 → 100644
... ... @@ -0,0 +1,68 @@
  1 +require 'test_helper'
  2 +
  3 +class EmailTemplatesControllerTest < ActionController::TestCase
  4 +
  5 + setup do
  6 + @profile = fast_create(Community)
  7 + @email_template = EmailTemplate.create!(:name => 'template', :owner => @profile)
  8 + @person = create_user_with_permission('templatemanager', 'send_mail_to_members', @profile)
  9 + login_as(@person.user.login)
  10 + end
  11 +
  12 + attr_accessor :profile, :person
  13 +
  14 + test "should get index" do
  15 + get :index, :profile => profile.identifier
  16 + assert_response :success
  17 + assert_not_nil assigns(:email_templates)
  18 + end
  19 +
  20 + test "should get new" do
  21 + get :new, :profile => profile.identifier
  22 + assert_response :success
  23 + end
  24 +
  25 + test "should create email_template" do
  26 + assert_difference('EmailTemplate.count') do
  27 + post :create, email_template: { :name => 'test' }, :profile => profile.identifier
  28 + end
  29 +
  30 + assert_redirected_to url_for(:action => :index)
  31 + end
  32 +
  33 + test "should show email_template" do
  34 + get :show, id: @email_template, :profile => profile.identifier
  35 + assert_response :success
  36 + end
  37 +
  38 + test "should get edit" do
  39 + get :edit, id: @email_template, :profile => profile.identifier
  40 + assert_response :success
  41 + end
  42 +
  43 + test "should update email_template" do
  44 + put :update, id: @email_template, email_template: { }, :profile => profile.identifier
  45 + assert_redirected_to url_for(:action => :index)
  46 + end
  47 +
  48 + test "should destroy email_template" do
  49 + assert_difference('EmailTemplate.count', -1) do
  50 + delete :destroy, id: @email_template, :profile => profile.identifier
  51 + end
  52 +
  53 + assert_redirected_to url_for(:action => :index)
  54 + end
  55 +
  56 + test "should get parsed template" do
  57 + environment = Environment.default
  58 + @email_template.subject = '{{profile.name}} - {{profile.identifier}}'
  59 + @email_template.body = '{{profile.name}} - {{profile.identifier}} - {{environment.name}}'
  60 + @email_template.save!
  61 + get :show_parsed, id: @email_template, :profile => profile.identifier
  62 + assert_response :success
  63 + json_response = ActiveSupport::JSON.decode(@response.body)
  64 + assert_equal "#{profile.name} - #{profile.identifier}", json_response['parsed_subject']
  65 + assert_equal "#{profile.name} - #{profile.identifier} - #{environment.name}", json_response['parsed_body']
  66 + end
  67 +
  68 +end
... ...
test/functional/profile_editor_controller_test.rb
... ... @@ -626,6 +626,17 @@ class ProfileEditorControllerTest &lt; ActionController::TestCase
626 626 assert_tag :tag => 'a', :attributes => { :href => '/myprofile/default_user/cms' }
627 627 end
628 628  
  629 + should 'display email template link for organizations in control panel' do
  630 + profile = fast_create(Organization)
  631 + get :index, :profile => profile.identifier
  632 + assert_tag :tag => 'a', :attributes => { :href => "/myprofile/#{profile.identifier}/email_templates" }
  633 + end
  634 +
  635 + should 'not display email template link in control panel for person' do
  636 + get :index, :profile => profile.identifier
  637 + assert_no_tag :tag => 'a', :attributes => { :href => "/myprofile/#{profile.identifier}/email_templates" }
  638 + end
  639 +
629 640 should 'offer to create blog in control panel' do
630 641 get :index, :profile => profile.identifier
631 642 assert_tag :tag => 'a', :attributes => { :href => "/myprofile/default_user/cms/new?type=Blog" }
... ...
test/unit/email_template_test.rb
... ... @@ -3,10 +3,10 @@ require_relative &quot;../test_helper&quot;
3 3 class EmailTemplateTest < ActiveSupport::TestCase
4 4  
5 5 should 'filter templates by type' do
6   - EmailTemplate.create!(:template_type => :type1, :subject => 'template1')
7   - EmailTemplate.create!(:template_type => :type2, :subject => 'template2')
8   - EmailTemplate.create!(:template_type => :type2, :subject => 'template3')
9   - assert_equal ['template2', 'template3'], EmailTemplate.find_all_by_template_type(:type2).map(&:subject)
  6 + EmailTemplate.create!(:template_type => :type1, :name => 'template1')
  7 + EmailTemplate.create!(:template_type => :type2, :name => 'template2')
  8 + EmailTemplate.create!(:template_type => :type2, :name => 'template3')
  9 + assert_equal ['template2', 'template3'], EmailTemplate.find_all_by_template_type(:type2).map(&:name)
10 10 end
11 11  
12 12 should 'parse body using params' do
... ...