aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Gemfile4
-rw-r--r--Gemfile.lock9
-rw-r--r--app/controllers/admin_general_controller.rb7
-rw-r--r--app/controllers/admin_request_controller.rb13
-rw-r--r--app/controllers/application_controller.rb5
-rw-r--r--app/controllers/request_controller.rb8
-rw-r--r--app/models/contact_mailer.rb1
-rw-r--r--app/models/foi_attachment.rb2
-rw-r--r--app/models/info_request_event.rb1
-rw-r--r--app/views/admin_general/timeline.rhtml2
-rw-r--r--app/views/admin_request/hidden_user_explanation.rhtml2
-rw-r--r--app/views/general/_orglink.rhtml4
-rw-r--r--app/views/layouts/admin.rhtml16
-rw-r--r--app/views/layouts/default.rhtml25
-rw-r--r--app/views/request/_bubble.rhtml2
-rw-r--r--app/views/request/_sidebar.rhtml2
-rw-r--r--config/boot.rb2
-rw-r--r--config/crontab.ugly2
-rw-r--r--config/initializers/theme_loader.rb6
-rw-r--r--config/packages1
-rw-r--r--config/purge-varnish-debian.ugly14
-rw-r--r--config/routes.rb12
-rw-r--r--lib/public_body_categories.rb2
-rwxr-xr-xscript/alert-comment-on-request4
-rwxr-xr-xscript/alert-new-response-reminders4
-rwxr-xr-xscript/alert-not-clarified-request4
-rwxr-xr-xscript/alert-overdue-requests6
-rwxr-xr-xscript/alert-tracks-daemon4
-rw-r--r--script/cache-incoming-emails4
-rwxr-xr-xscript/check-recent-requests-sent4
-rwxr-xr-xscript/clear-caches4
-rwxr-xr-xscript/delete-old-things9
-rwxr-xr-xscript/handle-mail-replies182
-rwxr-xr-xscript/handle-mail-replies.rb180
-rwxr-xr-xscript/load-exim-logs13
-rwxr-xr-xscript/rails-post-deploy19
-rwxr-xr-xscript/runner2
-rwxr-xr-xscript/stop-new-responses-on-old-requests4
-rw-r--r--spec/integration/errors_spec.rb2
39 files changed, 306 insertions, 281 deletions
diff --git a/Gemfile b/Gemfile
index 0a2e1f927..542970145 100644
--- a/Gemfile
+++ b/Gemfile
@@ -1,5 +1,5 @@
# Work around bug in Debian Squeeze - see https://github.com/sebbacon/alaveteli/pull/297#issuecomment-4101012
-if File.exist? "/etc/debian_version" and File.open("/etc/debian_version").read.strip == "6.0.4"
+if File.exist? "/etc/debian_version" and File.open("/etc/debian_version").read.strip =~ /^6\.0\.[45]$/
if File.exist? "/lib/libuuid.so.1"
require 'dl'
DL::dlopen('/lib/libuuid.so.1')
@@ -30,7 +30,7 @@ gem 'test-unit', '~> 1.2.3' if RUBY_VERSION.to_f >= 1.9
gem 'vpim'
gem 'will_paginate', '~> 2.3.11'
# when 1.2.9 is released by the maintainer, we can stop using this fork:
-gem 'xapian-full', '~> 1.2.9', :git => 'git://github.com/sebbacon/xapian-full.git'
+gem 'xapian-full-alaveteli', '~> 1.2.9.4'
gem 'xml-simple'
gem 'zip'
diff --git a/Gemfile.lock b/Gemfile.lock
index 084ce19f3..e7c089a4a 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -1,9 +1,3 @@
-GIT
- remote: git://github.com/sebbacon/xapian-full.git
- revision: 8f0f827d5964b28daa72c756e40caabfa2981fd0
- specs:
- xapian-full (1.2.9)
-
GEM
remote: http://rubygems.org/
specs:
@@ -61,6 +55,7 @@ GEM
ruby-ole (1.2.11.2)
vpim (0.695)
will_paginate (2.3.16)
+ xapian-full-alaveteli (1.2.9.4)
xml-simple (1.1.0)
zip (2.0.2)
@@ -90,6 +85,6 @@ DEPENDENCIES
ruby-msg (~> 1.5.0)
vpim
will_paginate (~> 2.3.11)
- xapian-full (~> 1.2.9)!
+ xapian-full-alaveteli (~> 1.2.9.4)
xml-simple
zip
diff --git a/app/controllers/admin_general_controller.rb b/app/controllers/admin_general_controller.rb
index c83ae0f37..2c961dfc5 100644
--- a/app/controllers/admin_general_controller.rb
+++ b/app/controllers/admin_general_controller.rb
@@ -79,11 +79,12 @@ class AdminGeneralController < AdminController
end
def debug
+ @http_auth_user = admin_http_auth_user
@current_commit = `git log -1 --format="%H"`
- @current_branch = `git branch | grep "\*" | awk '{print $2}'`
+ @current_branch = `git branch | perl -ne 'print $1 if /^\\* (.*)/'`
@current_version = `git describe --always --tags`
- repo = `git remote show origin -n | grep Fetch | awk '{print $3}' | sed -re 's/.*:(.*).git/\\1/'`
- @github_origin = "https://github.com/#{repo.strip}/tree/"
+ repo = `git remote show origin -n | perl -ne 'print $1 if m{Fetch URL: .*github\\.com[:/](.*)\\.git}'`
+ @github_origin = "https://github.com/#{repo}/tree/"
@request_env = request.env
end
end
diff --git a/app/controllers/admin_request_controller.rb b/app/controllers/admin_request_controller.rb
index 522e1cd39..fd1405319 100644
--- a/app/controllers/admin_request_controller.rb
+++ b/app/controllers/admin_request_controller.rb
@@ -340,15 +340,24 @@ class AdminRequestController < AdminController
def hide_request
ActiveRecord::Base.transaction do
+ subject = params[:subject]
explanation = params[:explanation]
info_request = InfoRequest.find(params[:id])
- info_request.set_described_state(params[:reason])
info_request.prominence = "requester_only"
+
+ info_request.log_event("hide", {
+ :editor => admin_http_auth_user(),
+ :reason => params[:reason],
+ :subject => subject,
+ :explanation => explanation
+ })
+
+ info_request.set_described_state(params[:reason])
info_request.save!
ContactMailer.deliver_from_admin_message(
info_request.user,
- "hello",
+ subject,
params[:explanation]
)
flash[:notice] = _("Your message to {{recipient_user_name}} has been sent",:recipient_user_name=>CGI.escapeHTML(info_request.user.name))
diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb
index e305e90f4..41adf1848 100644
--- a/app/controllers/application_controller.rb
+++ b/app/controllers/application_controller.rb
@@ -202,7 +202,7 @@ class ApplicationController < ActionController::Base
# return stub path so admin can expire it
first_three_digits = info_request.id.to_s()[0..2]
path = "views/request/#{first_three_digits}/#{info_request.id}"
- foi_cache_path = File.join(File.dirname(__FILE__), '../../cache')
+ foi_cache_path = File.expand_path(File.join(File.dirname(__FILE__), '../../cache'))
return File.join(foi_cache_path, path)
end
def foi_fragment_cache_exists?(key_path)
@@ -345,9 +345,6 @@ class ApplicationController < ActionController::Base
return "*unknown*";
end
end
- def assign_http_auth_user
- @http_auth_user = admin_http_auth_user
- end
# Convert URL name for sort by order, to Xapian query
def order_to_sort_by(sortby)
diff --git a/app/controllers/request_controller.rb b/app/controllers/request_controller.rb
index 94fbcde29..bd2bfc974 100644
--- a/app/controllers/request_controller.rb
+++ b/app/controllers/request_controller.rb
@@ -656,6 +656,12 @@ class RequestController < ApplicationController
def report_request
info_request = InfoRequest.find_by_url_title(params[:url_title])
+ return if !authenticated?(
+ :web => _("To report this FOI request"),
+ :email => _("Then you can report the request '{{title}}'", :title => info_request.title),
+ :email_subject => _("Report an offensive or unsuitable request")
+ )
+
if !info_request.attention_requested
info_request.set_described_state('attention_requested')
info_request.attention_requested = true # tells us if attention has ever been requested
@@ -839,7 +845,7 @@ class RequestController < ApplicationController
)
updated = Digest::SHA1.hexdigest(info_request.get_last_event.created_at.to_i.to_s + info_request.updated_at.to_i.to_s)
@url_path = "/download/#{updated[0..1]}/#{updated}/#{params[:url_title]}.zip"
- file_path = File.join(File.dirname(__FILE__), '../../cache/zips', @url_path)
+ file_path = File.expand_path(File.join(File.dirname(__FILE__), '../../cache/zips', @url_path))
if !File.exists?(file_path)
FileUtils.mkdir_p(File.dirname(file_path))
Zip::ZipFile.open(file_path, Zip::ZipFile::CREATE) { |zipfile|
diff --git a/app/models/contact_mailer.rb b/app/models/contact_mailer.rb
index 800fe54e4..6e781d48c 100644
--- a/app/models/contact_mailer.rb
+++ b/app/models/contact_mailer.rb
@@ -52,6 +52,7 @@ class ContactMailer < ApplicationMailer
:from_user => @from,
:recipient_user => recipient_user,
}
+ bcc MySociety::Config::get("CONTACT_EMAIL")
end
end
diff --git a/app/models/foi_attachment.rb b/app/models/foi_attachment.rb
index f3e3d7e00..9bbf0988f 100644
--- a/app/models/foi_attachment.rb
+++ b/app/models/foi_attachment.rb
@@ -42,7 +42,7 @@ class FoiAttachment < ActiveRecord::Base
if rails_env.nil? || rails_env.empty?
raise "$RAILS_ENV is not set"
end
- base_dir = File.join(File.dirname(__FILE__), "../../cache", "attachments_#{rails_env}")
+ base_dir = File.expand_path(File.join(File.dirname(__FILE__), "../../cache", "attachments_#{rails_env}"))
return File.join(base_dir, self.hexdigest[0..2])
end
diff --git a/app/models/info_request_event.rb b/app/models/info_request_event.rb
index a410328b0..9a4f6d9fe 100644
--- a/app/models/info_request_event.rb
+++ b/app/models/info_request_event.rb
@@ -51,6 +51,7 @@ class InfoRequestEvent < ActiveRecord::Base
'destroy_outgoing', # deleted an outgoing message (in admin interface)
'redeliver_incoming', # redelivered an incoming message elsewhere (in admin interface)
'move_request', # changed user or public body (in admin interface)
+ 'hide', # hid a request (in admin interface)
'manual', # you did something in the db by hand
'response',
diff --git a/app/views/admin_general/timeline.rhtml b/app/views/admin_general/timeline.rhtml
index 39a4b3e36..eecab4823 100644
--- a/app/views/admin_general/timeline.rhtml
+++ b/app/views/admin_general/timeline.rhtml
@@ -65,6 +65,8 @@
had incoming message deleted by administrator <strong><%=h event.params[:editor] %></strong>.
<% elsif event.event_type == 'destroy_outgoing' %>
had outgoing message deleted by administrator <strong><%=h event.params[:editor] %></strong>.
+ <% elsif event.event_type == 'hide' %>
+ was hidden by administrator <strong><%=h event.params[:editor] %></strong>.
<% elsif event.event_type == 'redeliver_outgoing' %>
had incoming message redelivered to another request by administrator <strong><%=h event.params[:editor] %></strong>.
<% elsif event.event_type == 'response' %>
diff --git a/app/views/admin_request/hidden_user_explanation.rhtml b/app/views/admin_request/hidden_user_explanation.rhtml
index aaea49fb6..64387ffee 100644
--- a/app/views/admin_request/hidden_user_explanation.rhtml
+++ b/app/views/admin_request/hidden_user_explanation.rhtml
@@ -2,7 +2,7 @@ Dear <%= name_to %>,
Your request '<%= info_request.title %>' at <%= info_request_url %> has been reviewed by moderators.
-We consider it <% if reason == 'not_foi' %>is not a valid FOI request<% else %>to be vexatious<% end%>, and have therefore hidden it from other users. Please reply to this email if you would like to discuss this decision further.
+We consider it <% if reason == 'not_foi' %>is not a valid FOI request<% else %>to be vexatious<% end%>, and have therefore hidden it from other users. You will still be able to view it while logged in to the site. Please reply to this email if you would like to discuss this decision further.
Yours,
diff --git a/app/views/general/_orglink.rhtml b/app/views/general/_orglink.rhtml
index 7d74dbaac..fbe688d85 100644
--- a/app/views/general/_orglink.rhtml
+++ b/app/views/general/_orglink.rhtml
@@ -1,2 +1,2 @@
-<%-# Put the link to your organisation here, or leave blank -%>
-<%= link_to image_tag('logo.png'), frontpage_url, :id=>'logo' %>
+<%# Put the link to your organisation here, or leave blank %>
+<%= link_to image_tag('logo.png'), frontpage_url, :id=>'logo' %>
diff --git a/app/views/layouts/admin.rhtml b/app/views/layouts/admin.rhtml
index 65670538d..d85eecbf2 100644
--- a/app/views/layouts/admin.rhtml
+++ b/app/views/layouts/admin.rhtml
@@ -13,15 +13,15 @@
<p>
<strong><%= link_to 'Alaveteli', main_url('/') %> admin:</strong>
- <%= link_to 'Summary', admin_general_index_path %>
- | <%= link_to 'Timeline', admin_timeline_path %>
- | <%= link_to 'Stats', admin_stats_path %>
- | <%= link_to 'Debug', admin_debug_path %>
+ <%= link_to 'Summary', admin_url("") %>
+ | <%= link_to 'Timeline', admin_url("timeline") %>
+ | <%= link_to 'Stats', admin_url("stats") %>
+ | <%= link_to 'Debug', admin_url("debug") %>
<strong>View:</strong>
- <%= link_to 'Authorities', admin_body_list_path %>
- | <%= link_to 'Requests', admin_request_list_path %>
- | <%= link_to 'Users', admin_user_list_path %>
- | <%= link_to 'Tracks', admin_track_list_path %>
+ <%= link_to 'Authorities', admin_url("body/list") %>
+ | <%= link_to 'Requests', admin_url("request/list") %>
+ | <%= link_to 'Users', admin_url("user/list") %>
+ | <%= link_to 'Tracks', admin_url("track/list") %>
</p>
<%= render :partial => 'general/locale_switcher' %>
diff --git a/app/views/layouts/default.rhtml b/app/views/layouts/default.rhtml
index bc9dfb02d..ed0a52e85 100644
--- a/app/views/layouts/default.rhtml
+++ b/app/views/layouts/default.rhtml
@@ -147,7 +147,6 @@
<%= render :partial => 'general/footer' %>
- <%= render :partial => 'general/before_body_end' %>
</div>
<div id="other-country-notice"></div>
<div id="link_box"><span class="close-button">X</span>
@@ -157,18 +156,20 @@
</div>
<%
ga_code = MySociety::Config.get('GA_CODE', '')
- unless ga_code.empty?
- %>
- <script>
- var gaJsHost = (("https:" == document.location.protocol) ? "https://ssl." : "http://www.");
- document.write(unescape("%3Cscript src='" + gaJsHost + "google-analytics.com/ga.js' type='text/javascript'%3E%3C/script%3E"));
- </script>
- <script>
- var pageTracker = _gat._getTracker("<%=ga_code%>");
- pageTracker._trackPageview();
- </script>
- <% end %>
+
+ unless ga_code.empty? %>
+ <script>
+ var gaJsHost = (("https:" == document.location.protocol) ? "https://ssl." : "http://www.");
+ document.write(unescape("%3Cscript src='" + gaJsHost + "google-analytics.com/ga.js' type='text/javascript'%3E%3C/script%3E"));
+ </script>
+ <script>
+ var pageTracker = _gat._getTracker("<%=ga_code%>");
+ pageTracker._trackPageview();
+ </script>
+
+ <% end %>
+ <%= render :partial => 'general/before_body_end' %>
</body>
</html>
diff --git a/app/views/request/_bubble.rhtml b/app/views/request/_bubble.rhtml
index 87079e9ea..331c2163e 100644
--- a/app/views/request/_bubble.rhtml
+++ b/app/views/request/_bubble.rhtml
@@ -13,7 +13,7 @@
:file_name => a.display_filename + '.html')
%>
<% img_filename = "icon_" + a.content_type.sub('/', '_') + "_large.png"
- full_filename = File.join(File.dirname(__FILE__), "../../../public/images", img_filename)
+ full_filename = File.expand_path(File.join(File.dirname(__FILE__), "../../../public/images", img_filename))
if File.exist?(full_filename) %>
<a href="<%=attachment_url%>"><img class="attachment_image" alt="Attachment" src="/images/<%=img_filename%>"></a>
<% else %>
diff --git a/app/views/request/_sidebar.rhtml b/app/views/request/_sidebar.rhtml
index bca142fa9..956b3988b 100644
--- a/app/views/request/_sidebar.rhtml
+++ b/app/views/request/_sidebar.rhtml
@@ -13,7 +13,7 @@
<% else %>
<p><%= _('Requests for personal information and vexatious requests are not considered valid for FOI purposes (<a href="/help/about">read more</a>).') %>
<p><%= ('If you believe this request is not suitable, you can report it for attention by the site administrators') %></p>
- <%= link_to _("Report this request"), report_path, :class => "link_button_green" %>
+ <%= link_to _("Report this request"), report_path, :class => "link_button_green", :method => "POST" %>
<% end %>
<% end %>
<h2><%= _("Act on what you've learnt") %></h2>
diff --git a/config/boot.rb b/config/boot.rb
index 943029408..906a2bace 100644
--- a/config/boot.rb
+++ b/config/boot.rb
@@ -6,7 +6,7 @@
# better. Look for a config/rails_env file, and read stuff from there if
# it exists. Put just a line like this in there:
# ENV['RAILS_ENV'] = 'production'
-rails_env_file = File.join(File.dirname(__FILE__), 'rails_env.rb')
+rails_env_file = File.expand_path(File.join(File.dirname(__FILE__), 'rails_env.rb'))
if File.exists?(rails_env_file)
require rails_env_file
end
diff --git a/config/crontab.ugly b/config/crontab.ugly
index 0bbcd2616..dc660e18f 100644
--- a/config/crontab.ugly
+++ b/config/crontab.ugly
@@ -13,7 +13,7 @@ MAILTO=cron-!!(*= $site *)!!@mysociety.org
*/5 * * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/change-xapian-database.lock "/data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/update-xapian-index verbose=true" >> /data/vhost/!!(*= $vhost *)!!/logs/update-xapian-index.log || echo "stalled?"
# Every 10 minutes
5,15,25,35,45,55 * * * * !!(*= $user *)!! /etc/init.d/foi-alert-tracks check
-5,15,25,35,45,55 * * * * !!(*= $user *)!! /etc/init.d/purge-varnish check
+5,15,25,35,45,55 * * * * !!(*= $user *)!! /etc/init.d/foi-purge-varnish check
# Once an hour
09 * * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/alert-comment-on-request.lock /data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/alert-comment-on-request || echo "stalled?"
diff --git a/config/initializers/theme_loader.rb b/config/initializers/theme_loader.rb
index 4ddce6910..8908dc07e 100644
--- a/config/initializers/theme_loader.rb
+++ b/config/initializers/theme_loader.rb
@@ -1,5 +1,9 @@
+# This is a global array of route extensions. Alaveteli modules may add to it.
+# It is used by our config/routes.rb to decide which route extension files to load.
+$alaveteli_route_extensions = []
+
theme_urls = MySociety::Config.get("THEME_URLS", [])
-if ENV["RAILS_ENV"] != "test" # Don't let the theme interfere with Alaveteli specs
+if ENV["RAILS_ENV"] != "test" # Don't let the themes interfere with Alaveteli specs
for url in theme_urls.reverse
theme_name = url.sub(/.*\/(.*).git/, "\\1")
theme_main_include = File.expand_path "../../../vendor/plugins/#{theme_name}/lib/alavetelitheme.rb", __FILE__
diff --git a/config/packages b/config/packages
index 47d84a380..b59c61b47 100644
--- a/config/packages
+++ b/config/packages
@@ -33,3 +33,4 @@ libpq-dev
uuid-dev
ruby1.8-dev
build-essential
+bundler
diff --git a/config/purge-varnish-debian.ugly b/config/purge-varnish-debian.ugly
index 3e77c09c3..1a9259da8 100644
--- a/config/purge-varnish-debian.ugly
+++ b/config/purge-varnish-debian.ugly
@@ -6,11 +6,11 @@
# Required-Stop: $local_fs $syslog
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
-# Short-Description: purge-varnish is a daemon running the Alaveteli email alerts
-# Description: purge-varnish send Alaveteli email alerts as required
+# Short-Description: purge-varnish is a daemon purging the Alaveteli varnish cache
+# Description: purge-varnish purge the Alaveteli varnish cache
### END INIT INFO
#
-# !!(*= $daemon_name *)!! Start the Alaveteli email alert daemon
+# !!(*= $daemon_name *)!! Start the Alaveteli email purge-varnish daemon
NAME=!!(*= $daemon_name *)!!
DAEMON=/data/vhost/!!(*= $vhost *)!!/alaveteli/script/runner
@@ -42,7 +42,7 @@ case "$1" in
quietly_start_daemon
if [ $? -ne 1 ]
then
- echo "Alaveteli alert daemon was not running; now restarted"
+ echo "Alaveteli purge-varnish daemon was not running; now restarted"
exit 1
else
exit 0
@@ -50,17 +50,17 @@ case "$1" in
;;
start)
- echo -n "Starting Alaveteli alert daemon: $NAME"
+ echo -n "Starting Alaveteli purge-varnish daemon: $NAME"
start_daemon
;;
stop)
- echo -n "Stopping Alaveteli alert daemon: $NAME"
+ echo -n "Stopping Alaveteli purge-varnish daemon: $NAME"
stop_daemon
;;
restart)
- echo -n "Restarting Alaveteli alert daemon: $NAME"
+ echo -n "Restarting Alaveteli purge-varnish daemon: $NAME"
stop_daemon
start_daemon
;;
diff --git a/config/routes.rb b/config/routes.rb
index 0ba8139c2..814deb760 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -7,7 +7,9 @@
# $Id: routes.rb,v 1.92 2009-10-14 22:01:27 francis Exp $
# Allow easy extension from themes. Note these will have the highest priority.
-load File.join('config', 'custom-routes.rb')
+$alaveteli_route_extensions.each do |f|
+ load File.join('config', f)
+end
ActionController::Routing::Routes.draw do |map|
@@ -66,7 +68,13 @@ ActionController::Routing::Routes.draw do |map|
request.upload_response "/upload/request/:url_title", :action => 'upload_response'
request.download_entire_request '/request/:url_title/download', :action => 'download_entire_request'
- request.report '/request/:url_title/report', :action => 'report_request'
+
+ # It would be nice to add :conditions => { :method => :post } to this next one,
+ # because it ought not really to be available as a GET request since it changes
+ # the server state. Unfortunately this doesn’t play well with the PostRedirect
+ # mechanism, which assumes all post-login actions are available via GET, so we
+ # refrain.
+ request.report '/request/:url_title/report', :action => 'report_request'
end
diff --git a/lib/public_body_categories.rb b/lib/public_body_categories.rb
index 796b1d53d..b8058bf9e 100644
--- a/lib/public_body_categories.rb
+++ b/lib/public_body_categories.rb
@@ -16,7 +16,7 @@ class PublicBodyCategories
@with_description = @with_headings.select() { |a| a.instance_of?(Array) }
@tags = @with_description.map() { |a| a[0] }
@by_tag = Hash[*@with_description.map() { |a| a[0..1] }.flatten]
- @singular_by_tag = Hash[*@with_description.map() { |a| [a[0],a[2]] }.flatten]
+ @singular_by_tag = Hash[*@with_description.map() { |a| [a[0],a[2]] }.flatten]
end
def PublicBodyCategories.get
diff --git a/script/alert-comment-on-request b/script/alert-comment-on-request
index bfca2663f..74782aa13 100755
--- a/script/alert-comment-on-request
+++ b/script/alert-comment-on-request
@@ -1,7 +1,7 @@
#!/bin/bash
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'RequestMailer.alert_comment_on_request'
+bundle exec ./runner 'RequestMailer.alert_comment_on_request'
diff --git a/script/alert-new-response-reminders b/script/alert-new-response-reminders
index d52381750..59fa76df1 100755
--- a/script/alert-new-response-reminders
+++ b/script/alert-new-response-reminders
@@ -1,7 +1,7 @@
#!/bin/bash
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'RequestMailer.alert_new_response_reminders'
+bundle exec ./runner 'RequestMailer.alert_new_response_reminders'
diff --git a/script/alert-not-clarified-request b/script/alert-not-clarified-request
index bfdbeaff5..a38fbc70e 100755
--- a/script/alert-not-clarified-request
+++ b/script/alert-not-clarified-request
@@ -1,7 +1,7 @@
#!/bin/bash
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'RequestMailer.alert_not_clarified_request'
+bundle exec ./runner 'RequestMailer.alert_not_clarified_request'
diff --git a/script/alert-overdue-requests b/script/alert-overdue-requests
index f6549e5b6..46450f1f2 100755
--- a/script/alert-overdue-requests
+++ b/script/alert-overdue-requests
@@ -1,7 +1,5 @@
#!/bin/bash
-LOC=`dirname $0`
-
-"$LOC/runner" 'RequestMailer.alert_overdue_requests()'
-
+cd "`dirname "$0"`"
+bundle exec ./runner 'RequestMailer.alert_overdue_requests()'
diff --git a/script/alert-tracks-daemon b/script/alert-tracks-daemon
index 9064eaa05..43712ae68 100755
--- a/script/alert-tracks-daemon
+++ b/script/alert-tracks-daemon
@@ -1,6 +1,6 @@
#!/bin/sh
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" --daemon TrackMailer.alert_tracks_loop
+bundle exec ./runner --daemon TrackMailer.alert_tracks_loop
diff --git a/script/cache-incoming-emails b/script/cache-incoming-emails
index a84a713d6..0b3069bd7 100644
--- a/script/cache-incoming-emails
+++ b/script/cache-incoming-emails
@@ -4,6 +4,6 @@
# Will take a while to run! Can use after clear-caches to refresh the database
# level caches if you like.
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'IncomingMessage.find_each() { |im| print "info request " + im.info_request.id.to_s + ", incoming message " + im.id.to_s + ": " + im.extract_attachments!.count.to_s + " attachments extracted to " + im.foi_attachments[0].directory + "; main body folded: " + im.get_main_body_text_folded.size.to_s + " attachment clipped:" + im.get_attachment_text_clipped.size.to_s + "\n" }'
+bundle exec ./runner 'IncomingMessage.find_each() { |im| print "info request " + im.info_request.id.to_s + ", incoming message " + im.id.to_s + ": " + im.extract_attachments!.count.to_s + " attachments extracted to " + im.foi_attachments[0].directory + "; main body folded: " + im.get_main_body_text_folded.size.to_s + " attachment clipped:" + im.get_attachment_text_clipped.size.to_s + "\n" }'
diff --git a/script/check-recent-requests-sent b/script/check-recent-requests-sent
index df5baf10a..588c6b73a 100755
--- a/script/check-recent-requests-sent
+++ b/script/check-recent-requests-sent
@@ -1,8 +1,8 @@
#!/bin/bash
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'EximLog.check_recent_requests_have_been_sent'
+bundle exec ./runner 'EximLog.check_recent_requests_have_been_sent'
diff --git a/script/clear-caches b/script/clear-caches
index be1d3d017..43fec2811 100755
--- a/script/clear-caches
+++ b/script/clear-caches
@@ -2,9 +2,9 @@
# Clear the cache of attachment and body text.
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" "ActiveRecord::Base.connection.execute(\"update incoming_messages set cached_attachment_text_clipped = null, cached_main_body_text_unfolded = null, cached_main_body_text_folded = null, sent_at = null, subject = null, mail_from = null, mail_from_domain = null, valid_to_reply_to = null, last_parsed = null\")"
+bundle exec ./runner "ActiveRecord::Base.connection.execute(\"update incoming_messages set cached_attachment_text_clipped = null, cached_main_body_text_unfolded = null, cached_main_body_text_folded = null, sent_at = null, subject = null, mail_from = null, mail_from_domain = null, valid_to_reply_to = null, last_parsed = null\")"
# Remove page cache (do it in two stages so live site gets cache cleared faster)
rm -fr $LOC/../old-cache
diff --git a/script/delete-old-things b/script/delete-old-things
index 1d8cf645b..063d85e1f 100755
--- a/script/delete-old-things
+++ b/script/delete-old-things
@@ -1,9 +1,6 @@
#!/bin/bash
-LOC=`dirname $0`
-
-"$LOC/runner" 'PostRedirect.delete_old_post_redirects()'
-
-"$LOC/runner" 'TrackThingsSentEmail.delete_old_track_things_sent_email()'
-
+cd "`dirname "$0"`"
+bundle exec ./runner 'PostRedirect.delete_old_post_redirects()'
+bundle exec ./runner 'TrackThingsSentEmail.delete_old_track_things_sent_email()'
diff --git a/script/handle-mail-replies b/script/handle-mail-replies
index 7590f5848..ad4b3719e 100755
--- a/script/handle-mail-replies
+++ b/script/handle-mail-replies
@@ -1,180 +1,4 @@
-#!/usr/bin/env ruby
-# -*- coding: utf-8 -*-
+#!/bin/bash
-# Handle email responses sent to us.
-#
-# This script is invoked as a pipe command, i.e. with the raw email message on stdin.
-# - If a message is identified as a permanent bounce, the user is marked as having a
-# bounced address, and will not be sent any more messages.
-# - If a message is identified as an out-of-office autoreply, it is discarded.
-# - Any other messages are forwarded to config.get("FORWARD_NONBOUNCE_RESPONSES_TO")
-
-
-# We want to avoid loading rails unless we need it, so we start by just loading the
-# config file ourselves.
-$alaveteli_dir = File.join(File.dirname(__FILE__), '..')
-$:.push(File.join($alaveteli_dir, "commonlib", "rblib"))
-load "config.rb"
-MySociety::Config.set_file(File.join($alaveteli_dir, 'config', 'general'), true)
-MySociety::Config.load_default
-
-require 'action_mailer'
-
-def main(in_test_mode)
- Dir.chdir($alaveteli_dir) do
- raw_message = $stdin.read
- begin
- message = TMail::Mail.parse(raw_message)
- rescue
- # Error parsing message. Just pass it on, to be on the safe side.
- forward_on(raw_message) unless in_test_mode
- return 0
- end
-
- pfas = permanently_failed_addresses(message)
- if !pfas.empty?
- if in_test_mode
- puts pfas
- else
- pfas.each do |pfa|
- record_bounce(pfa, raw_message)
- end
- end
- return 1
- end
-
- # If we are still here, there are no permanent failures,
- # so if the message is a multipart/report then it must be
- # reporting a temporary failure. In this case we discard it
- if message.content_type == "multipart/report"
- return 1
- end
-
- # Another style of temporary failure message
- subject = message.header_string("Subject")
- if message.content_type == "multipart/mixed" && subject == "Delivery Status Notification (Delay)"
- return 1
- end
-
- # Discard out-of-office messages
- if is_oof?(message)
- return 2 # Use a different return code, to distinguish OOFs from bounces
- end
-
- # Otherwise forward the message on
- forward_on(raw_message) unless in_test_mode
- return 0
- end
-end
-
-def permanently_failed_addresses(message)
- if message.header_string("Return-Path") == "<>"
- # Some sort of auto-response
-
- # Check for Exim’s X-Failed-Recipients header
- failed_recipients = message.header_string("X-Failed-Recipients")
- if !failed_recipients.nil?
- # The X-Failed-Recipients header contains the email address that failed
- # Check for the words "This is a permanent error." in the body, to indicate
- # a permanent failure
- if message.body =~ /This is a permanent error./
- return failed_recipients.split(/,\s*/)
- end
- end
-
- # Next, look for multipart/report
- if message.content_type == "multipart/report"
- permanently_failed_recipients = []
- message.parts.each do |part|
- if part.content_type == "message/delivery-status"
- sections = part.body.split(/\r?\n\r?\n/)
- # The first section is a generic header; subsequent sections
- # represent a particular recipient. Since we
- sections[1..-1].each do |section|
- if section !~ /^Status: (\d)/ || $1 != '5'
- # Either we couldn’t find the Status field, or it was a transient failure
- break
- end
- if section =~ /^Final-Recipient: rfc822;(.+)/
- permanently_failed_recipients.push($1)
- end
- end
- end
- end
- if !permanently_failed_recipients.empty?
- return permanently_failed_recipients
- end
- end
- end
-
- subject = message.header_string("Subject")
- # Then look for the style we’ve seen in WebShield bounces
- # (These do not have a return path of <> in the cases I have seen.)
- if subject == "Returned Mail: Error During Delivery"
- if message.body =~ /^\s*---- Failed Recipients ----\s*((?:<[^>]+>\n)+)/
- return $1.scan(/<([^>]+)>/).flatten
- end
- end
-
- return []
-end
-
-def is_oof?(message)
- # Check for out-of-office
-
- if message.header_string("X-POST-MessageClass") == "9; Autoresponder"
- return true
- end
-
- subject = message.header_string("Subject").downcase
- if message.header_string("Return-Path") == "<>"
- if subject.start_with? "out of office: "
- return true
- end
- if subject.start_with? "automatic reply: "
- return true
- end
- end
-
- if message.header_string("Auto-Submitted") == "auto-generated"
- if subject =~ /out of( the)? office/
- return true
- end
- end
-
- if subject.start_with? "out of office autoreply:"
- return true
- end
- if subject == "out of office"
- return true
- end
- if subject == "out of office reply"
- return true
- end
- if subject.end_with? "is out of the office"
- return true
- end
- return false
-end
-
-def forward_on(raw_message)
- forward_non_bounces_to = MySociety::Config.get("FORWARD_NONBOUNCE_RESPONSES_TO", "user-support@localhost")
- IO.popen("/usr/sbin/sendmail -i #{forward_non_bounces_to}", "w") do |f|
- f.write(raw_message);
- f.close;
- end
-end
-
-def load_rails
- require File.join('config', 'boot')
- require Rails.root + '/config/environment'
-end
-
-def record_bounce(email_address, bounce_message)
- load_rails
- User.record_bounce_for_email(email_address, bounce_message)
-end
-
-in_test_mode = (ARGV[0] == "--test")
-status = main(in_test_mode)
-exit(status) if in_test_mode
+cd "`dirname "$0"`"
+exec bundle exec ./handle-mail-replies.rb
diff --git a/script/handle-mail-replies.rb b/script/handle-mail-replies.rb
new file mode 100755
index 000000000..cc15fe35a
--- /dev/null
+++ b/script/handle-mail-replies.rb
@@ -0,0 +1,180 @@
+#!/usr/bin/env ruby
+# -*- coding: utf-8 -*-
+
+# Handle email responses sent to us.
+#
+# This script is invoked as a pipe command, i.e. with the raw email message on stdin.
+# - If a message is identified as a permanent bounce, the user is marked as having a
+# bounced address, and will not be sent any more messages.
+# - If a message is identified as an out-of-office autoreply, it is discarded.
+# - Any other messages are forwarded to config.get("FORWARD_NONBOUNCE_RESPONSES_TO")
+
+
+# We want to avoid loading rails unless we need it, so we start by just loading the
+# config file ourselves.
+$alaveteli_dir = File.expand_path(File.join(File.dirname(__FILE__), '..'))
+$:.push(File.join($alaveteli_dir, "commonlib", "rblib"))
+load "config.rb"
+MySociety::Config.set_file(File.join($alaveteli_dir, 'config', 'general'), true)
+MySociety::Config.load_default
+
+require 'action_mailer'
+
+def main(in_test_mode)
+ Dir.chdir($alaveteli_dir) do
+ raw_message = $stdin.read
+ begin
+ message = TMail::Mail.parse(raw_message)
+ rescue
+ # Error parsing message. Just pass it on, to be on the safe side.
+ forward_on(raw_message) unless in_test_mode
+ return 0
+ end
+
+ pfas = permanently_failed_addresses(message)
+ if !pfas.empty?
+ if in_test_mode
+ puts pfas
+ else
+ pfas.each do |pfa|
+ record_bounce(pfa, raw_message)
+ end
+ end
+ return 1
+ end
+
+ # If we are still here, there are no permanent failures,
+ # so if the message is a multipart/report then it must be
+ # reporting a temporary failure. In this case we discard it
+ if message.content_type == "multipart/report"
+ return 1
+ end
+
+ # Another style of temporary failure message
+ subject = message.header_string("Subject")
+ if message.content_type == "multipart/mixed" && subject == "Delivery Status Notification (Delay)"
+ return 1
+ end
+
+ # Discard out-of-office messages
+ if is_oof?(message)
+ return 2 # Use a different return code, to distinguish OOFs from bounces
+ end
+
+ # Otherwise forward the message on
+ forward_on(raw_message) unless in_test_mode
+ return 0
+ end
+end
+
+def permanently_failed_addresses(message)
+ if message.header_string("Return-Path") == "<>"
+ # Some sort of auto-response
+
+ # Check for Exim’s X-Failed-Recipients header
+ failed_recipients = message.header_string("X-Failed-Recipients")
+ if !failed_recipients.nil?
+ # The X-Failed-Recipients header contains the email address that failed
+ # Check for the words "This is a permanent error." in the body, to indicate
+ # a permanent failure
+ if message.body =~ /This is a permanent error./
+ return failed_recipients.split(/,\s*/)
+ end
+ end
+
+ # Next, look for multipart/report
+ if message.content_type == "multipart/report"
+ permanently_failed_recipients = []
+ message.parts.each do |part|
+ if part.content_type == "message/delivery-status"
+ sections = part.body.split(/\r?\n\r?\n/)
+ # The first section is a generic header; subsequent sections
+ # represent a particular recipient. Since we
+ sections[1..-1].each do |section|
+ if section !~ /^Status: (\d)/ || $1 != '5'
+ # Either we couldn’t find the Status field, or it was a transient failure
+ break
+ end
+ if section =~ /^Final-Recipient: rfc822;(.+)/
+ permanently_failed_recipients.push($1)
+ end
+ end
+ end
+ end
+ if !permanently_failed_recipients.empty?
+ return permanently_failed_recipients
+ end
+ end
+ end
+
+ subject = message.header_string("Subject")
+ # Then look for the style we’ve seen in WebShield bounces
+ # (These do not have a return path of <> in the cases I have seen.)
+ if subject == "Returned Mail: Error During Delivery"
+ if message.body =~ /^\s*---- Failed Recipients ----\s*((?:<[^>]+>\n)+)/
+ return $1.scan(/<([^>]+)>/).flatten
+ end
+ end
+
+ return []
+end
+
+def is_oof?(message)
+ # Check for out-of-office
+
+ if message.header_string("X-POST-MessageClass") == "9; Autoresponder"
+ return true
+ end
+
+ subject = message.header_string("Subject").downcase
+ if message.header_string("Return-Path") == "<>"
+ if subject.start_with? "out of office: "
+ return true
+ end
+ if subject.start_with? "automatic reply: "
+ return true
+ end
+ end
+
+ if message.header_string("Auto-Submitted") == "auto-generated"
+ if subject =~ /out of( the)? office/
+ return true
+ end
+ end
+
+ if subject.start_with? "out of office autoreply:"
+ return true
+ end
+ if subject == "out of office"
+ return true
+ end
+ if subject == "out of office reply"
+ return true
+ end
+ if subject.end_with? "is out of the office"
+ return true
+ end
+ return false
+end
+
+def forward_on(raw_message)
+ forward_non_bounces_to = MySociety::Config.get("FORWARD_NONBOUNCE_RESPONSES_TO", "user-support@localhost")
+ IO.popen("/usr/sbin/sendmail -i #{forward_non_bounces_to}", "w") do |f|
+ f.write(raw_message);
+ f.close;
+ end
+end
+
+def load_rails
+ require File.join('config', 'boot')
+ require Rails.root + '/config/environment'
+end
+
+def record_bounce(email_address, bounce_message)
+ load_rails
+ User.record_bounce_for_email(email_address, bounce_message)
+end
+
+in_test_mode = (ARGV[0] == "--test")
+status = main(in_test_mode)
+exit(status) if in_test_mode
diff --git a/script/load-exim-logs b/script/load-exim-logs
index 7e7f37a35..5ca0c66f8 100755
--- a/script/load-exim-logs
+++ b/script/load-exim-logs
@@ -1,21 +1,20 @@
#!/bin/bash
-LOC=`dirname $0`
+LOC=`dirname "$0"`
# Specific file if specified
if [ x$1 != x ]
then
- "$LOC/runner" 'EximLog.load_file("'$1'")'
+ f=`abspath "$1"`
+ cd "$LOC"
+ bundle exec ./runner 'EximLog.load_file("'$f'")'
exit
fi
# Load in last three days worth of logs (if they've been modified)
+cd "$LOC"
LATEST=$( ls /var/log/exim4/exim-mainlog-* 2>/dev/null | sort | tail -3 )
for X in $LATEST
do
- # echo "doing $X"
- "$LOC/runner" 'EximLog.load_file("'$X'")'
+ bundle exec ./runner 'EximLog.load_file("'$X'")'
done
-
-
-
diff --git a/script/rails-post-deploy b/script/rails-post-deploy
index 575b995f9..193d0bbec 100755
--- a/script/rails-post-deploy
+++ b/script/rails-post-deploy
@@ -45,10 +45,10 @@ else
mkdir -p log
fi
# link the "downloads" directory in the cache to somewhere it can be served
-if [ ! -e $APP_DIR/public/download ]
+if [ ! -e "$APP_DIR/public/download" ]
then
- mkdir -p $APP_DIR/cache/zips/download
- ln -s $APP_DIR/cache/zips/download $APP_DIR/public/
+ mkdir -p "$APP_DIR/cache/zips/download"
+ ln -s "$APP_DIR/cache/zips/download" "$APP_DIR/public/"
fi
cd log
@@ -74,19 +74,20 @@ then
echo "ENV['RAILS_ENV'] ||= 'production'" > config/rails_env.rb
fi
+bundle_install_options=""
if [ "$OPTION_STAGING_SITE" = "0" ]
then
- bundle exec bundle install --without development:test --deployment
-else
- bundle exec bundle install
+ bundle_install_options="--without development:test --deployment"
fi
+bundle install $bundle_install_options
+
if [ -n "$OPTION_THEME_URLS" ]
then
for THEME in "${OPTION_THEME_URLS[@]}"
do
- echo "Installing $THEME..."
- script/plugin install --force $THEME
+ echo "Installing $THEME..."
+ script/plugin install --force $THEME
done
fi
@@ -94,7 +95,7 @@ fi
if [ -n "$OPTION_THEME_URL" ]
then
echo "Installing $OPTION_THEME_URL using deprecated THEME_URL..."
- script/plugin install --force $OPTION_THEME_URL
+ script/plugin install --force $OPTION_THEME_URL
fi
# upgrade database
diff --git a/script/runner b/script/runner
index 6b0bc0a08..2bd5e9aa7 100755
--- a/script/runner
+++ b/script/runner
@@ -3,7 +3,7 @@
daemon_mode = !ARGV.empty? && ARGV[0] == "--daemon"
script_dir = File.dirname(__FILE__)
-alaveteli_dir = File.join(script_dir, "..")
+alaveteli_dir = File.expand_path(File.join(script_dir, ".."))
Dir.chdir(alaveteli_dir) do
require File.join(alaveteli_dir, 'config', 'boot')
diff --git a/script/stop-new-responses-on-old-requests b/script/stop-new-responses-on-old-requests
index 77189cf0b..1e325403e 100755
--- a/script/stop-new-responses-on-old-requests
+++ b/script/stop-new-responses-on-old-requests
@@ -1,7 +1,7 @@
#!/bin/bash
-LOC=`dirname $0`
+cd "`dirname "$0"`"
-"$LOC/runner" 'InfoRequest.stop_new_responses_on_old_requests()'
+bundle exec ./runner 'InfoRequest.stop_new_responses_on_old_requests()'
diff --git a/spec/integration/errors_spec.rb b/spec/integration/errors_spec.rb
index ec2e1c376..4424b58c6 100644
--- a/spec/integration/errors_spec.rb
+++ b/spec/integration/errors_spec.rb
@@ -33,7 +33,7 @@ describe "When rendering errors" do
end
it "should render a 403 for attempts at directory listing for attachments" do
# make a fake cache
- foi_cache_path = File.join(File.dirname(__FILE__), '../../cache')
+ foi_cache_path = File.expand_path(File.join(File.dirname(__FILE__), '../../cache'))
FileUtils.mkdir_p(File.join(foi_cache_path, "views/en/request/101/101/response/1/attach/html/1"))
get("/request/101/response/1/attach/html/1/" )
response.code.should == "403"