aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--app/assets/stylesheets/responsive/_user_layout.scss4
-rw-r--r--app/controllers/admin_request_controller.rb25
-rw-r--r--app/controllers/admin_spam_addresses_controller.rb4
-rw-r--r--app/controllers/request_controller.rb33
-rw-r--r--app/controllers/user_controller.rb15
-rw-r--r--app/models/info_request_batch.rb8
-rw-r--r--app/models/outgoing_message.rb70
-rw-r--r--app/views/admin_request/_incoming_message_actions.html.erb2
-rw-r--r--app/views/admin_spam_addresses/index.html.erb4
-rw-r--r--app/views/user/show.html.erb3
-rw-r--r--config/general.yml-example3
-rw-r--r--config/routes.rb2
-rw-r--r--spec/controllers/admin_spam_addresses_controller_spec.rb4
-rw-r--r--spec/controllers/request_controller_spec.rb20
-rw-r--r--spec/controllers/user_controller_spec.rb12
-rw-r--r--spec/factories/outgoing_messages.rb10
-rw-r--r--spec/fixtures/info_request_events.yml4
-rw-r--r--spec/models/info_request_spec.rb11
18 files changed, 176 insertions, 58 deletions
diff --git a/app/assets/stylesheets/responsive/_user_layout.scss b/app/assets/stylesheets/responsive/_user_layout.scss
index a568a5fa3..84ddbf562 100644
--- a/app/assets/stylesheets/responsive/_user_layout.scss
+++ b/app/assets/stylesheets/responsive/_user_layout.scss
@@ -4,4 +4,8 @@
#search_form {
margin-top: 2rem;
}
+
+ #request_latest_status {
+ width: 300px;
+ }
}
diff --git a/app/controllers/admin_request_controller.rb b/app/controllers/admin_request_controller.rb
index 21120e4ad..8f023bf12 100644
--- a/app/controllers/admin_request_controller.rb
+++ b/app/controllers/admin_request_controller.rb
@@ -37,7 +37,30 @@ class AdminRequestController < AdminController
def resend
@outgoing_message = OutgoingMessage.find(params[:outgoing_message_id])
- @outgoing_message.resend_message
+ @outgoing_message.prepare_message_for_resend
+
+ mail_message = case @outgoing_message.message_type
+ when 'initial_request'
+ OutgoingMailer.initial_request(
+ @outgoing_message.info_request,
+ @outgoing_message
+ ).deliver
+ when 'followup'
+ OutgoingMailer.followup(
+ @outgoing_message.info_request,
+ @outgoing_message,
+ @outgoing_message.incoming_message_followup
+ ).deliver
+ else
+ raise "Message id #{id} has type '#{message_type}' which cannot be resent"
+ end
+
+ @outgoing_message.record_email_delivery(
+ mail_message.to_addrs.join(', '),
+ mail_message.message_id,
+ 'resent'
+ )
+
flash[:notice] = "Outgoing message resent"
redirect_to admin_request_show_url(@outgoing_message.info_request)
end
diff --git a/app/controllers/admin_spam_addresses_controller.rb b/app/controllers/admin_spam_addresses_controller.rb
index f5c7e93da..fff7e2a4a 100644
--- a/app/controllers/admin_spam_addresses_controller.rb
+++ b/app/controllers/admin_spam_addresses_controller.rb
@@ -10,7 +10,7 @@ class AdminSpamAddressesController < AdminController
if @spam_address.save
notice = "#{ @spam_address.email } has been added to the spam addresses list"
- redirect_to spam_addresses_path, :notice => notice
+ redirect_to admin_spam_addresses_path, :notice => notice
else
@spam_addresses = SpamAddress.all
render :index
@@ -21,7 +21,7 @@ class AdminSpamAddressesController < AdminController
@spam_address = SpamAddress.find(params[:id])
@spam_address.destroy
notice = "#{ @spam_address.email } has been removed from the spam addresses list"
- redirect_to spam_addresses_path, :notice => notice
+ redirect_to admin_spam_addresses_path, :notice => notice
end
end
diff --git a/app/controllers/request_controller.rb b/app/controllers/request_controller.rb
index 3fa0ef0ce..9e2c291dc 100644
--- a/app/controllers/request_controller.rb
+++ b/app/controllers/request_controller.rb
@@ -365,8 +365,21 @@ class RequestController < ApplicationController
end
# This automatically saves dependent objects, such as @outgoing_message, in the same transaction
@info_request.save!
- # TODO: send_message needs the database id, so we send after saving, which isn't ideal if the request broke here.
- @outgoing_message.send_message
+
+ # TODO: Sending the message needs the database id, so we send after
+ # saving, which isn't ideal if the request broke here.
+ if @outgoing_message.sendable?
+ mail_message = OutgoingMailer.initial_request(
+ @outgoing_message.info_request,
+ @outgoing_message
+ ).deliver
+
+ @outgoing_message.record_email_delivery(
+ mail_message.to_addrs.join(', '),
+ mail_message.message_id
+ )
+ end
+
flash[:notice] = _("<p>Your {{law_used_full}} request has been <strong>sent on its way</strong>!</p>
<p><strong>We will email you</strong> when there is a response, or after {{late_number_of_days}} working days if the authority still hasn't
replied by then.</p>
@@ -668,13 +681,27 @@ class RequestController < ApplicationController
end
# Send a follow up message
- @outgoing_message.send_message
+ @outgoing_message.sendable?
+
+ mail_message = OutgoingMailer.followup(
+ @outgoing_message.info_request,
+ @outgoing_message,
+ @outgoing_message.incoming_message_followup
+ ).deliver
+
+ @outgoing_message.record_email_delivery(
+ mail_message.to_addrs.join(', '),
+ mail_message.message_id
+ )
+
@outgoing_message.save!
+
if @outgoing_message.what_doing == 'internal_review'
flash[:notice] = _("Your internal review request has been sent on its way.")
else
flash[:notice] = _("Your follow up message has been sent on its way.")
end
+
redirect_to request_url(@info_request)
end
else
diff --git a/app/controllers/user_controller.rb b/app/controllers/user_controller.rb
index f23343ddb..baeaab18a 100644
--- a/app/controllers/user_controller.rb
+++ b/app/controllers/user_controller.rb
@@ -49,13 +49,28 @@ class UserController < ApplicationController
# TODO: really should just use SQL query here rather than Xapian.
if @show_requests
begin
+
+ request_states = @display_user.info_requests.pluck(:described_state).uniq
+
+ option_item = Struct.new(:value, :text)
+ @request_states = request_states.map do |state|
+ option_item.new(state, InfoRequest.get_status_description(state))
+ end
+
requests_query = 'requested_by:' + @display_user.url_name
comments_query = 'commented_by:' + @display_user.url_name
if !params[:user_query].nil?
requests_query += " " + params[:user_query]
comments_query += " " + params[:user_query]
@match_phrase = _("{{search_results}} matching '{{query}}'", :search_results => "", :query => params[:user_query])
+
+ unless params[:request_latest_status].blank?
+ requests_query << ' latest_status:' << params[:request_latest_status]
+ comments_query << ' latest_status:' << params[:request_latest_status]
+ @match_phrase << _(" filtered by status: '{{status}}'", :status => params[:request_latest_status])
+ end
end
+
@xapian_requests = perform_search([InfoRequestEvent], requests_query, 'newest', 'request_collapse')
@xapian_comments = perform_search([InfoRequestEvent], comments_query, 'newest', nil)
diff --git a/app/models/info_request_batch.rb b/app/models/info_request_batch.rb
index d7c5eb9af..8a5ebeaba 100644
--- a/app/models/info_request_batch.rb
+++ b/app/models/info_request_batch.rb
@@ -46,7 +46,13 @@ class InfoRequestBatch < ActiveRecord::Base
self.sent_at = Time.now
self.save!
end
- created.each{ |info_request| info_request.outgoing_messages.first.send_message }
+ created.each do |info_request|
+ outgoing_message = info_request.outgoing_messages.first
+
+ outgoing_message.sendable?
+ mail_message = OutgoingMailer.initial_request(outgoing_message.info_request, outgoing_message).deliver
+ outgoing_message.record_email_delivery(mail_message.to_addrs.join(', '), mail_message.message_id)
+ end
return unrequestable
end
diff --git a/app/models/outgoing_message.rb b/app/models/outgoing_message.rb
index 9424113fc..fa83c7381 100644
--- a/app/models/outgoing_message.rb
+++ b/app/models/outgoing_message.rb
@@ -171,57 +171,42 @@ class OutgoingMessage < ActiveRecord::Base
MySociety::Validate.contains_postcode?(body)
end
- # Deliver outgoing message
- # Note: You can test this from script/console with, say:
- # InfoRequest.find(1).outgoing_messages[0].send_message
- def send_message(log_event_type = 'sent')
+ def record_email_delivery(to_addrs, message_id, log_event_type = 'sent')
+ self.last_sent_at = Time.now
+ self.status = 'sent'
+ save!
+
+ log_event_type = "followup_#{ log_event_type }" if message_type == 'followup'
+
+ info_request.log_event(log_event_type, { :email => to_addrs,
+ :outgoing_message_id => id,
+ :smtp_message_id => message_id })
+ set_info_request_described_state
+ end
+
+ def sendable?
if status == 'ready'
if message_type == 'initial_request'
- self.last_sent_at = Time.now
- self.status = 'sent'
- self.save!
-
- mail_message = OutgoingMailer.initial_request(info_request, self).deliver
- self.info_request.log_event(log_event_type, {
- :email => mail_message.to_addrs.join(", "),
- :outgoing_message_id => self.id,
- :smtp_message_id => mail_message.message_id
- })
- self.info_request.set_described_state('waiting_response')
+ return true
elsif message_type == 'followup'
- self.last_sent_at = Time.now
- self.status = 'sent'
- self.save!
-
- mail_message = OutgoingMailer.followup(info_request, self, incoming_message_followup).deliver
- self.info_request.log_event('followup_' + log_event_type, {
- :email => mail_message.to_addrs.join(", "),
- :outgoing_message_id => self.id,
- :smtp_message_id => mail_message.message_id
- })
- if info_request.described_state == 'waiting_clarification'
- self.info_request.set_described_state('waiting_response')
- end
- if what_doing == 'internal_review'
- self.info_request.set_described_state('internal_review')
- end
+ return true
else
- raise "Message id #{id} has type '#{message_type}' which send_message can't handle"
+ raise "Message id #{id} has type '#{message_type}' which cannot be sent"
end
elsif status == 'sent'
raise "Message id #{id} has already been sent"
else
- raise "Message id #{id} not in state for send_message"
+ raise "Message id #{id} not in state for sending"
end
end
# An admin function
- def resend_message
+ def prepare_message_for_resend
if ['initial_request', 'followup'].include?(message_type) and status == 'sent'
self.status = 'ready'
- send_message('resent')
else
- raise "Message id #{id} has type '#{message_type}' status '#{status}' which resend_message can't handle"
+ raise "Message id #{id} has type '#{message_type}' status " \
+ "'#{status}' which prepare_message_for_resend can't handle"
end
end
@@ -303,6 +288,19 @@ class OutgoingMessage < ActiveRecord::Base
private
+ def set_info_request_described_state
+ if message_type == 'initial_request'
+ info_request.set_described_state('waiting_response')
+ elsif message_type == 'followup'
+ if info_request.described_state == 'waiting_clarification'
+ info_request.set_described_state('waiting_response')
+ end
+ if what_doing == 'internal_review'
+ info_request.set_described_state('internal_review')
+ end
+ end
+ end
+
def set_default_letter
self.body = get_default_message if body.nil?
end
diff --git a/app/views/admin_request/_incoming_message_actions.html.erb b/app/views/admin_request/_incoming_message_actions.html.erb
index dd50eb047..22effcce5 100644
--- a/app/views/admin_request/_incoming_message_actions.html.erb
+++ b/app/views/admin_request/_incoming_message_actions.html.erb
@@ -25,7 +25,7 @@
<div class="control-group">
<label class="control-label">Mark <code>To:</code> address as spam</label>
<div class="controls">
- <%= link_to 'Spam Addresses', spam_addresses_path %>
+ <%= link_to 'Spam Addresses', admin_spam_addresses_path %>
</div>
</div>
diff --git a/app/views/admin_spam_addresses/index.html.erb b/app/views/admin_spam_addresses/index.html.erb
index 9846bc017..7a11f70e1 100644
--- a/app/views/admin_spam_addresses/index.html.erb
+++ b/app/views/admin_spam_addresses/index.html.erb
@@ -16,7 +16,7 @@
<div class="row">
<div class="span12">
- <%= form_for(@spam_address, :html => { :class => 'form-inline' }) do |f| -%>
+ <%= form_for(@spam_address, :url => admin_spam_addresses_path, :html => { :class => 'form-inline' }) do |f| -%>
<%= error_messages_for @spam_address %>
<%= f.text_field :email, :class => 'input-xxlarge', :placeholder => 'Enter email' %>
<%= f.submit 'Add Spam Address', :class => 'btn btn-warning' %>
@@ -39,7 +39,7 @@
<% @spam_addresses.each do |spam| %>
<tr>
<td><%= spam.email %></td>
- <td><%= link_to 'Remove', spam,
+ <td><%= link_to 'Remove', admin_spam_address_path(spam),
:method => :delete,
:confirm => 'This is permanent! Are you sure?',
:class => 'btn btn-mini btn-danger' %></td>
diff --git a/app/views/user/show.html.erb b/app/views/user/show.html.erb
index 7ae577565..b23f74326 100644
--- a/app/views/user/show.html.erb
+++ b/app/views/user/show.html.erb
@@ -121,6 +121,9 @@
<%= form_tag(show_user_url, :method => "get", :id=>"search_form") do %>
<div>
<%= text_field_tag(:user_query, params[:user_query], {:title => "type your search term here" }) %>
+ <%= select_tag :request_latest_status,
+ options_from_collection_for_select(@request_states, 'value', 'text', params[:request_latest_status]),
+ :prompt => _('Filter by Request Status (optional)') %>
<% if @is_you %>
<%= submit_tag(_("Search your contributions")) %>
<% else %>
diff --git a/config/general.yml-example b/config/general.yml-example
index a80784712..ac96b5e50 100644
--- a/config/general.yml-example
+++ b/config/general.yml-example
@@ -1,6 +1,9 @@
# general.yml-example:
# Example values for the "general" config file.
#
+# Documentation on configuring Alaveteli is available at
+# http://alaveteli.org/docs/customising/
+#
# Configuration parameters, in YAML syntax.
#
# Copy this file to one called "general.yml" in the same directory. Or
diff --git a/config/routes.rb b/config/routes.rb
index fd832a2ad..ff99e884c 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -270,7 +270,7 @@ Alaveteli::Application.routes.draw do
####
#### AdminSpamAddresses controller
- scope '/admin' do
+ scope '/admin', :as => 'admin' do
resources :spam_addresses,
:controller => 'admin_spam_addresses',
:only => [:index, :create, :destroy]
diff --git a/spec/controllers/admin_spam_addresses_controller_spec.rb b/spec/controllers/admin_spam_addresses_controller_spec.rb
index da1e9bb5a..a1e434159 100644
--- a/spec/controllers/admin_spam_addresses_controller_spec.rb
+++ b/spec/controllers/admin_spam_addresses_controller_spec.rb
@@ -37,7 +37,7 @@ describe AdminSpamAddressesController do
it 'redirects to the index action if successful' do
SpamAddress.any_instance.stub(:save).and_return(true)
post :create, :spam_address => spam_params
- expect(response).to redirect_to(spam_addresses_path)
+ expect(response).to redirect_to(admin_spam_addresses_path)
end
it 'notifies the admin the spam address has been created' do
@@ -83,7 +83,7 @@ describe AdminSpamAddressesController do
end
it 'redirects to the index action' do
- expect(response).to redirect_to(spam_addresses_path)
+ expect(response).to redirect_to(admin_spam_addresses_path)
end
end
diff --git a/spec/controllers/request_controller_spec.rb b/spec/controllers/request_controller_spec.rb
index f7c935af3..6c0f4573e 100644
--- a/spec/controllers/request_controller_spec.rb
+++ b/spec/controllers/request_controller_spec.rb
@@ -1827,7 +1827,15 @@ describe RequestController, "when sending a followup message" do
# make the followup
session[:user_id] = users(:bob_smith_user).id
- post :show_response, :outgoing_message => { :body => "What a useless response! You suck.", :what_doing => 'normal_sort' }, :id => info_requests(:fancy_dog_request).id, :incoming_message_id => incoming_messages(:useless_incoming_message), :submitted_followup => 1
+
+ post :show_response,
+ :outgoing_message => {
+ :body => "What a useless response! You suck.",
+ :what_doing => 'normal_sort'
+ },
+ :id => info_requests(:fancy_dog_request).id,
+ :incoming_message_id => incoming_messages(:useless_incoming_message),
+ :submitted_followup => 1
# check it worked
deliveries = ActionMailer::Base.deliveries
@@ -1982,7 +1990,15 @@ describe RequestController, "sending overdue request alerts" do
:info_request_id => chicken_request.id,
:body => 'Some text',
:what_doing => 'normal_sort')
- outgoing_message.send_message
+
+ outgoing_message.sendable?
+ mail_message = OutgoingMailer.followup(
+ outgoing_message.info_request,
+ outgoing_message,
+ outgoing_message.incoming_message_followup
+ ).deliver
+ outgoing_message.record_email_delivery(mail_message.to_addrs.join(', '), mail_message.message_id)
+
outgoing_message.save!
chicken_request = InfoRequest.find(chicken_request.id)
diff --git a/spec/controllers/user_controller_spec.rb b/spec/controllers/user_controller_spec.rb
index e4854fe6b..413d395c5 100644
--- a/spec/controllers/user_controller_spec.rb
+++ b/spec/controllers/user_controller_spec.rb
@@ -21,7 +21,8 @@ describe UserController, "when redirecting a show request to a canonical url" do
it 'should not redirect a long canonical name that has a numerical suffix' do
User.stub!(:find).with(:first, anything()).and_return(mock_model(User,
:url_name => 'bob_smithbob_smithbob_smithbob_s_2',
- :name => 'Bob Smith Bob Smith Bob Smith Bob Smith'))
+ :name => 'Bob Smith Bob Smith Bob Smith Bob Smith',
+ :info_requests => []))
User.stub!(:find).with(:all, anything()).and_return([])
get :show, :url_name => 'bob_smithbob_smithbob_smithbob_s_2'
response.should be_success
@@ -107,6 +108,15 @@ describe UserController, "when showing a user" do
]
end
+ it 'filters by the given request status' do
+ get :show, :url_name => 'bob_smith',
+ :user_query => 'money',
+ :request_latest_status => 'waiting_response'
+ assigns[:xapian_requests].results.map{|x|x[:model].info_request}.should =~ [
+ info_requests(:naughty_chicken_request)
+ ]
+ end
+
it "should not show unconfirmed users" do
begin
get :show, :url_name => "unconfirmed_user"
diff --git a/spec/factories/outgoing_messages.rb b/spec/factories/outgoing_messages.rb
index 3887d3f48..e11cbdfb9 100644
--- a/spec/factories/outgoing_messages.rb
+++ b/spec/factories/outgoing_messages.rb
@@ -10,7 +10,9 @@ FactoryGirl.define do
body 'Some information please'
what_doing 'normal_sort'
end
+
end
+
factory :internal_review_request do
ignore do
status 'ready'
@@ -18,6 +20,7 @@ FactoryGirl.define do
body 'I want a review'
what_doing 'internal_review'
end
+
end
# FIXME: This here because OutgoingMessage has an after_initialize,
@@ -30,9 +33,14 @@ FactoryGirl.define do
:message_type => message_type,
:body => body,
:what_doing => what_doing }) }
+
after_create do |outgoing_message|
- outgoing_message.send_message
+ outgoing_message.sendable?
+ outgoing_message.record_email_delivery(
+ 'test@example.com',
+ 'ogm-14+537f69734b97c-1ebd@localhost')
end
+
end
end
diff --git a/spec/fixtures/info_request_events.yml b/spec/fixtures/info_request_events.yml
index b2f40cc37..23ef80cc2 100644
--- a/spec/fixtures/info_request_events.yml
+++ b/spec/fixtures/info_request_events.yml
@@ -31,8 +31,10 @@ silly_outgoing_message_event:
info_request_id: 103
event_type: sent
created_at: 2007-10-14 10:41:12.686264
- described_state:
outgoing_message_id: 2
+ calculated_state: waiting_response
+ described_state: waiting_response
+ last_described_at: 2007-10-14 10:41:12.686264
useless_incoming_message_event:
id: 902
params_yaml: "--- \n\
diff --git a/spec/models/info_request_spec.rb b/spec/models/info_request_spec.rb
index afb8e0949..9ad616ea5 100644
--- a/spec/models/info_request_spec.rb
+++ b/spec/models/info_request_spec.rb
@@ -848,9 +848,11 @@ describe InfoRequest do
context "a series of events on a request" do
it "should have sensible events after the initial request has been made" do
# An initial request is sent
- # The logic that changes the status when a message is sent is mixed up
- # in OutgoingMessage#send_message. So, rather than extract it (or call it)
- # let's just duplicate what it does here for the time being.
+ # FIXME: The logic that changes the status when a message
+ # is sent is mixed up in
+ # OutgoingMessage#record_email_delivery. So, rather than
+ # extract it (or call it) let's just duplicate what it does
+ # here for the time being.
request.log_event('sent', {})
request.set_described_state('waiting_response')
@@ -919,7 +921,8 @@ describe InfoRequest do
request.log_event("status_update", {})
request.set_described_state("waiting_response")
# A normal follow up is sent
- # This is normally done in OutgoingMessage#send_message
+ # This is normally done in
+ # OutgoingMessage#record_email_delivery
request.log_event('followup_sent', {})
request.set_described_state('waiting_response')