aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Gemfile1
-rw-r--r--Gemfile.lock1
-rw-r--r--app/controllers/admin_public_body_controller.rb5
-rw-r--r--app/controllers/public_body_controller.rb124
-rw-r--r--app/models/info_request.rb6
-rw-r--r--app/models/public_body.rb24
-rw-r--r--config/crontab-example2
-rw-r--r--config/general.yml-example5
-rw-r--r--config/initializers/alaveteli.rb1
-rw-r--r--doc/THEMES.md2
-rw-r--r--lib/configuration.rb1
-rw-r--r--lib/tasks/gettext.rake42
-rw-r--r--lib/tasks/stats.rake9
-rw-r--r--public/stylesheets/admin.css77
-rw-r--r--public/stylesheets/alt.css232
-rwxr-xr-xscript/generate_pot.sh22
-rwxr-xr-xscript/update-public-body-stats4
-rw-r--r--spec/controllers/public_body_controller_spec.rb74
-rw-r--r--spec/controllers/request_controller_spec.rb2
-rw-r--r--spec/models/info_request_spec.rb7
-rw-r--r--spec/models/public_body_spec.rb46
-rw-r--r--vendor/plugins/strip_attributes/lib/strip_attributes.rb9
22 files changed, 276 insertions, 420 deletions
diff --git a/Gemfile b/Gemfile
index a323981d3..5fcedc84f 100644
--- a/Gemfile
+++ b/Gemfile
@@ -55,6 +55,7 @@ group :test do
gem 'fakeweb'
gem 'coveralls', :require => false
gem 'webrat'
+ gem 'nokogiri'
end
group :development do
diff --git a/Gemfile.lock b/Gemfile.lock
index 8d5059d7e..15c5245ff 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -270,6 +270,7 @@ DEPENDENCIES
net-http-local
net-purge
newrelic_rpm
+ nokogiri
pg
rack
rails (= 3.1.12)
diff --git a/app/controllers/admin_public_body_controller.rb b/app/controllers/admin_public_body_controller.rb
index ec2a08dbc..e0da234b0 100644
--- a/app/controllers/admin_public_body_controller.rb
+++ b/app/controllers/admin_public_body_controller.rb
@@ -14,6 +14,7 @@ class AdminPublicBodyController < AdminController
def _lookup_query_internal
@locale = self.locale_from_params()
+ underscore_locale = @locale.gsub '-', '_'
I18n.with_locale(@locale) do
@query = params[:query]
if @query == ""
@@ -23,10 +24,10 @@ class AdminPublicBodyController < AdminController
if @page == ""
@page = nil
end
- @public_bodies = PublicBody.joins(:translations).where(@query.nil? ? "public_body_translations.locale = '#{@locale}'" :
+ @public_bodies = PublicBody.joins(:translations).where(@query.nil? ? "public_body_translations.locale = '#{underscore_locale}'" :
["(lower(public_body_translations.name) like lower('%'||?||'%') or
lower(public_body_translations.short_name) like lower('%'||?||'%') or
- lower(public_body_translations.request_email) like lower('%'||?||'%' )) AND (public_body_translations.locale = '#{@locale}')", @query, @query, @query]).paginate :order => "public_body_translations.name", :page => @page, :per_page => 100
+ lower(public_body_translations.request_email) like lower('%'||?||'%' )) AND (public_body_translations.locale = '#{underscore_locale}')", @query, @query, @query]).paginate :order => "public_body_translations.name", :page => @page, :per_page => 100
end
@public_bodies_by_tag = PublicBody.find_by_tag(@query)
end
diff --git a/app/controllers/public_body_controller.rb b/app/controllers/public_body_controller.rb
index 9f692c5ba..02f0ceb19 100644
--- a/app/controllers/public_body_controller.rb
+++ b/app/controllers/public_body_controller.rb
@@ -86,34 +86,45 @@ class PublicBodyController < ApplicationController
def list
long_cache
# XXX move some of these tag SQL queries into has_tag_string.rb
- @query = "%#{params[:public_body_query].nil? ? "" : params[:public_body_query]}%"
+
+ like_query = params[:public_body_query]
+ like_query = "" if like_query.nil?
+ like_query = "%#{like_query}%"
+
@tag = params[:tag]
- @locale = self.locale_from_params()
- default_locale = I18n.default_locale.to_s
- locale_condition = "(upper(public_body_translations.name) LIKE upper(?)
- OR upper(public_body_translations.notes) LIKE upper (?))
- AND public_body_translations.locale = ?
- AND public_bodies.id <> #{PublicBody.internal_admin_body.id}"
+
+ @locale = self.locale_from_params
+ underscore_locale = @locale.gsub '-', '_'
+ underscore_default_locale = I18n.default_locale.to_s.gsub '-', '_'
+
+ where_condition = "public_bodies.id <> #{PublicBody.internal_admin_body.id}"
+ where_parameters = []
+
+ first_letter = false
+
+ base_tag_condition = " AND (SELECT count(*) FROM has_tag_string_tags" \
+ " WHERE has_tag_string_tags.model_id = public_bodies.id" \
+ " AND has_tag_string_tags.model = 'PublicBody'"
+
+ # Restrict the public bodies shown according to the tag
+ # parameter supplied in the URL:
if @tag.nil? or @tag == "all"
@tag = "all"
- conditions = [locale_condition, @query, @query, default_locale]
elsif @tag == 'other'
category_list = PublicBodyCategories::get().tags().map{|c| "'"+c+"'"}.join(",")
- conditions = [locale_condition + ' AND (select count(*) from has_tag_string_tags where has_tag_string_tags.model_id = public_bodies.id
- and has_tag_string_tags.model = \'PublicBody\'
- and has_tag_string_tags.name in (' + category_list + ')) = 0', @query, @query, default_locale]
+ where_condition += base_tag_condition + " AND has_tag_string_tags.name in (#{category_list})) = 0"
elsif @tag.size == 1
@tag.upcase!
- conditions = [locale_condition + ' AND public_body_translations.first_letter = ?', @query, @query, default_locale, @tag]
+ # The first letter queries have to be done on
+ # translations, so just indicate to add that later:
+ first_letter = true
elsif @tag.include?(":")
name, value = HasTagString::HasTagStringTag.split_tag_into_name_value(@tag)
- conditions = [locale_condition + ' AND (select count(*) from has_tag_string_tags where has_tag_string_tags.model_id = public_bodies.id
- and has_tag_string_tags.model = \'PublicBody\'
- and has_tag_string_tags.name = ? and has_tag_string_tags.value = ?) > 0', @query, @query, default_locale, name, value]
+ where_condition += base_tag_condition + " AND has_tag_string_tags.name = ? AND has_tag_string_tags.value = ?) > 0"
+ where_parameters.concat [name, value]
else
- conditions = [locale_condition + ' AND (select count(*) from has_tag_string_tags where has_tag_string_tags.model_id = public_bodies.id
- and has_tag_string_tags.model = \'PublicBody\'
- and has_tag_string_tags.name = ?) > 0', @query, @query, default_locale, @tag]
+ where_condition += base_tag_condition + " AND has_tag_string_tags.name = ?) > 0"
+ where_parameters.concat [@tag]
end
if @tag == "all"
@@ -128,10 +139,45 @@ class PublicBodyController < ApplicationController
@description = _("in the category ‘{{category_name}}’", :category_name=>category_name)
end
end
+
I18n.with_locale(@locale) do
- @public_bodies = PublicBody.where(conditions).joins(:translations).order("public_body_translations.name").paginate(
- :page => params[:page], :per_page => 100
- )
+
+ if AlaveteliConfiguration::public_body_list_fallback_to_default_locale
+ # Unfortunately, when we might fall back to the
+ # default locale, this is a rather complex query:
+ query = %Q{
+ SELECT public_bodies.*, COALESCE(current_locale.name, default_locale.name) AS display_name
+ FROM public_bodies
+ LEFT OUTER JOIN public_body_translations as current_locale
+ ON (public_bodies.id = current_locale.public_body_id
+ AND current_locale.locale = ? AND #{get_public_body_list_translated_condition 'current_locale', first_letter})
+ LEFT OUTER JOIN public_body_translations as default_locale
+ ON (public_bodies.id = default_locale.public_body_id
+ AND default_locale.locale = ? AND #{get_public_body_list_translated_condition 'default_locale', first_letter})
+ WHERE #{where_condition} AND COALESCE(current_locale.name, default_locale.name) IS NOT NULL
+ ORDER BY display_name}
+ sql = [query, underscore_locale, like_query, like_query]
+ sql.push @tag if first_letter
+ sql += [underscore_default_locale, like_query, like_query]
+ sql.push @tag if first_letter
+ sql += where_parameters
+ @public_bodies = PublicBody.paginate_by_sql(
+ sql,
+ :page => params[:page],
+ :per_page => 100)
+ else
+ # The simpler case where we're just searching in the current locale:
+ where_condition = get_public_body_list_translated_condition('public_body_translations', first_letter, true) +
+ ' AND ' + where_condition
+ where_sql = [where_condition, like_query, like_query]
+ where_sql.push @tag if first_letter
+ where_sql += [underscore_locale] + where_parameters
+ @public_bodies = PublicBody.where(where_sql) \
+ .joins(:translations) \
+ .order("public_body_translations.name") \
+ .paginate(:page => params[:page], :per_page => 100)
+ end
+
respond_to do |format|
format.html { render :template => "public_body/list" }
end
@@ -165,27 +211,27 @@ class PublicBodyController < ApplicationController
[[total_column,
[{
- :title => 'Public bodies with the most requests',
- :y_axis => 'Number of requests',
+ :title => _('Public bodies with the most requests'),
+ :y_axis => _('Number of requests'),
:highest => true}]],
['info_requests_successful_count',
[{
- :title => 'Public bodies with the most successful requests',
- :y_axis => 'Percentage of total requests',
+ :title => _('Public bodies with the most successful requests'),
+ :y_axis => _('Percentage of total requests'),
:highest => true},
{
- :title => 'Public bodies with the fewest successful requests',
- :y_axis => 'Percentage of total requests',
+ :title => _('Public bodies with the fewest successful requests'),
+ :y_axis => _('Percentage of total requests'),
:highest => false}]],
['info_requests_overdue_count',
[{
- :title => 'Public bodies with most overdue requests',
- :y_axis => 'Percentage of requests that are overdue',
+ :title => _('Public bodies with most overdue requests'),
+ :y_axis => _('Percentage of requests that are overdue'),
:highest => true}]],
['info_requests_not_held_count',
[{
- :title => 'Public bodies that most frequently replied with "Not Held"',
- :y_axis => 'Percentage of total requests',
+ :title => _('Public bodies that most frequently replied with "Not Held"'),
+ :y_axis => _('Percentage of total requests'),
:highest => true}]]].each do |column, graphs_properties|
graphs_properties.each do |graph_properties|
@@ -207,7 +253,7 @@ class PublicBodyController < ApplicationController
data_to_draw = {
'id' => "#{column}-#{highest ? 'highest' : 'lowest'}",
- 'x_axis' => 'Public Bodies',
+ 'x_axis' => _('Public Bodies'),
'y_axis' => graph_properties[:y_axis],
'errorbars' => percentages,
'title' => graph_properties[:title]}
@@ -236,4 +282,18 @@ class PublicBodyController < ApplicationController
@xapian_requests = perform_search_typeahead(query, PublicBody)
render :partial => "public_body/search_ahead"
end
+
+ private
+ def get_public_body_list_translated_condition(table, first_letter=false, locale=nil)
+ result = "(upper(#{table}.name) LIKE upper(?)" \
+ " OR upper(#{table}.notes) LIKE upper (?))"
+ if first_letter
+ result += " AND #{table}.first_letter = ?"
+ end
+ if locale
+ result += " AND #{table}.locale = ?"
+ end
+ result
+ end
+
end
diff --git a/app/models/info_request.rb b/app/models/info_request.rb
index 91bd37d9f..c0b8e2fca 100644
--- a/app/models/info_request.rb
+++ b/app/models/info_request.rb
@@ -1128,12 +1128,18 @@ public
after_save :update_counter_cache
after_destroy :update_counter_cache
def update_counter_cache
+ PublicBody.skip_callback(:save, :after, :purge_in_cache)
self.public_body.info_requests_not_held_count = InfoRequest.where(
:public_body_id => self.public_body.id,
:described_state => 'not_held').count
self.public_body.info_requests_successful_count = InfoRequest.where(
:public_body_id => self.public_body.id,
:described_state => ['successful', 'partially_successful']).count
+ self.public_body.without_revision do
+ public_body.no_xapian_reindex = true
+ public_body.save
+ end
+ PublicBody.set_callback(:save, :after, :purge_in_cache)
end
def for_admin_column
diff --git a/app/models/public_body.rb b/app/models/public_body.rb
index 300fdb956..3154be632 100644
--- a/app/models/public_body.rb
+++ b/app/models/public_body.rb
@@ -40,6 +40,7 @@ class PublicBody < ActiveRecord::Base
has_many :info_requests, :order => 'created_at desc'
has_many :track_things, :order => 'created_at desc'
has_many :censor_rules, :order => 'created_at desc'
+ attr_accessor :no_xapian_reindex
has_tag_string
before_save :set_api_key, :set_default_publication_scheme
@@ -60,12 +61,23 @@ class PublicBody < ActiveRecord::Base
# XXX - Don't like repeating this!
def calculate_cached_fields(t)
- t.first_letter = t.name.scan(/^./mu)[0].upcase unless t.name.nil? or t.name.empty?
+ PublicBody.set_first_letter(t)
short_long_name = t.name
short_long_name = t.short_name if t.short_name and !t.short_name.empty?
t.url_name = MySociety::Format.simplify_url_part(short_long_name, 'body')
end
+ # Set the first letter on a public body or translation
+ def PublicBody.set_first_letter(instance)
+ unless instance.name.nil? or instance.name.empty?
+ # we use a regex to ensure it works with utf-8/multi-byte
+ first_letter = instance.name.scan(/^./mu)[0].upcase
+ if first_letter != instance.first_letter
+ instance.first_letter = first_letter
+ end
+ end
+ end
+
def translated_versions
translations
end
@@ -130,8 +142,7 @@ class PublicBody < ActiveRecord::Base
# Set the first letter, which is used for faster queries
before_save(:set_first_letter)
def set_first_letter
- # we use a regex to ensure it works with utf-8/multi-byte
- self.first_letter = self.name.scan(/./mu)[0].upcase
+ PublicBody.set_first_letter(self)
end
# If tagged "not_apply", then FOI/EIR no longer applies to authority at all
@@ -177,7 +188,11 @@ class PublicBody < ActiveRecord::Base
end
acts_as_versioned
- self.non_versioned_columns << 'created_at' << 'updated_at' << 'first_letter' << 'api_key' << 'info_requests_count'
+ self.non_versioned_columns << 'created_at' << 'updated_at' << 'first_letter' << 'api_key'
+ self.non_versioned_columns << 'info_requests_count' << 'info_requests_successful_count'
+ self.non_versioned_columns << 'info_requests_not_held_count' << 'info_requests_overdue'
+ self.non_versioned_columns << 'info_requests_overdue_count'
+
class Version
attr_accessor :created_at
@@ -231,6 +246,7 @@ class PublicBody < ActiveRecord::Base
def reindex_requested_from
if self.changes.include?('url_name')
for info_request in self.info_requests
+
for info_request_event in info_request.info_request_events
info_request_event.xapian_mark_needs_index
end
diff --git a/config/crontab-example b/config/crontab-example
index 32baff170..d2c3f6bd9 100644
--- a/config/crontab-example
+++ b/config/crontab-example
@@ -26,6 +26,8 @@ MAILTO=cron-!!(*= $site *)!!@mysociety.org
0 8 * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/alert-not-clarified-request.lock /data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/alert-not-clarified-request || echo "stalled?"
2 4 * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/check-recent-requests-sent.lock /data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/check-recent-requests-sent || echo "stalled?"
45 3 * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/stop-new-responses-on-old-requests.lock /data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/stop-new-responses-on-old-requests || echo "stalled?"
+55 4 * * * !!(*= $user *)!! run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/update-public-body-stats.lock /data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/update-public-body-stats || echo "stalled?"
+
# Only root can restart apache
31 1 * * * root run-with-lockfile -n /data/vhost/!!(*= $vhost *)!!/change-xapian-database.lock "/data/vhost/!!(*= $vhost *)!!/!!(*= $vcspath *)!!/script/compact-xapian-database production" || echo "stalled?"
diff --git a/config/general.yml-example b/config/general.yml-example
index 37b0c2fc9..5f3697a36 100644
--- a/config/general.yml-example
+++ b/config/general.yml-example
@@ -200,3 +200,8 @@ PUBLIC_BODY_STATISTICS_PAGE: false
# The page of statistics for public bodies will only consider public
# bodies that have had at least this number of requests:
MINIMUM_REQUESTS_FOR_STATISTICS: 50
+
+# If only some of the public bodies have been translated into every
+# available locale, you can allow a fallback to the default locale for
+# listing of public bodies.
+PUBLIC_BODY_LIST_FALLBACK_TO_DEFAULT_LOCALE: false
diff --git a/config/initializers/alaveteli.rb b/config/initializers/alaveteli.rb
index 2c6ee2fbc..6e0cf076c 100644
--- a/config/initializers/alaveteli.rb
+++ b/config/initializers/alaveteli.rb
@@ -25,7 +25,6 @@ ALAVETELI_VERSION = '0.13'
# Mime::Type.register "text/richtext", :rtf
# Mime::Type.register "application/x-mobile", :mobile
-# The Rails cache is set up by the Interlock plugin to use memcached
# Domain for URLs (so can work for scripts, not just web pages)
ActionMailer::Base.default_url_options[:host] = AlaveteliConfiguration::domain
diff --git a/doc/THEMES.md b/doc/THEMES.md
index bae7d7665..d6109cdc5 100644
--- a/doc/THEMES.md
+++ b/doc/THEMES.md
@@ -64,7 +64,7 @@ add custom help pages, as described below.
# Branding the site
The core templates that comprise the layout and user interface of an
-Alaveteli site live in `app/views/`. They are use Rails' ERB syntax.
+Alaveteli site live in `app/views/`. They use Rails' ERB syntax.
For example, the template for the home page lives at
`app/views/general/frontpage.html.erb`, and the template for the "about
us" page is at `app/views/help/about.html.erb`.
diff --git a/lib/configuration.rb b/lib/configuration.rb
index d6fd8765f..ab985c8bf 100644
--- a/lib/configuration.rb
+++ b/lib/configuration.rb
@@ -49,6 +49,7 @@ module AlaveteliConfiguration
:NEW_RESPONSE_REMINDER_AFTER_DAYS => [3, 10, 24],
:OVERRIDE_ALL_PUBLIC_BODY_REQUEST_EMAILS => '',
:PUBLIC_BODY_STATISTICS_PAGE => false,
+ :PUBLIC_BODY_LIST_FALLBACK_TO_DEFAULT_LOCALE => false,
:RAW_EMAILS_LOCATION => 'files/raw_emails',
:READ_ONLY => '',
:RECAPTCHA_PRIVATE_KEY => 'x',
diff --git a/lib/tasks/gettext.rake b/lib/tasks/gettext.rake
index ace7205ae..366dfbe88 100644
--- a/lib/tasks/gettext.rake
+++ b/lib/tasks/gettext.rake
@@ -9,27 +9,31 @@ namespace :gettext do
end
end
- desc "Update pot file only, without fuzzy guesses (these are done by Transifex)"
- task :findpot => :environment do
+ desc "Update pot/po files for a theme."
+ task :find_theme => :environment do
+ theme = ENV['THEME']
+ unless theme
+ puts "Usage: Specify an Alaveteli-theme with THEME=[theme directory name]"
+ exit(0)
+ end
load_gettext
- $LOAD_PATH << File.join(File.dirname(__FILE__),'..','..','lib')
- require 'gettext_i18n_rails/haml_parser'
- files = files_to_translate
+ msgmerge = Rails.application.config.gettext_i18n_rails.msgmerge
+ msgmerge ||= %w[--sort-output --no-location --no-wrap]
+ GetText.update_pofiles_org(
+ text_domain,
+ theme_files_to_translate(theme),
+ "version 0.0.1",
+ :po_root => theme_locale_path(theme),
+ :msgmerge => msgmerge
+ )
+ end
- #write found messages to tmp.pot
- temp_pot = "tmp.pot"
- GetText::rgettext(files, temp_pot)
+ def theme_files_to_translate(theme)
+ Dir.glob("{vendor/plugins/#{theme}/lib}/**/*.{rb,erb}")
+ end
- #merge tmp.pot and existing pot
- FileUtils.mkdir_p('locale')
- GetText::msgmerge("locale/app.pot", temp_pot, "alaveteli", :po_root => 'locale', :msgmerge=>[ :no_wrap, :sort_output ])
- Dir.glob("locale/*/app.po") do |po_file|
- GetText::msgmerge(po_file, temp_pot, "alaveteli", :po_root => 'locale', :msgmerge=>[ :no_wrap, :sort_output ])
- end
- File.delete(temp_pot)
- end
+ def theme_locale_path(theme)
+ File.join(Rails.root, "vendor", "plugins", theme, "locale-theme")
+ end
- def files_to_translate
- Dir.glob("{app,lib,config,locale}/**/*.{rb,erb,haml,rhtml}")
- end
end
diff --git a/lib/tasks/stats.rake b/lib/tasks/stats.rake
index 1242575fe..4eda27289 100644
--- a/lib/tasks/stats.rake
+++ b/lib/tasks/stats.rake
@@ -93,8 +93,10 @@ namespace :stats do
desc 'Update statistics in the public_bodies table'
task :update_public_bodies_stats => :environment do
+ verbose = ENV['VERBOSE'] == '1'
PublicBody.all.each do |public_body|
- puts "Counting overdue requests for #{public_body.name}"
+ puts "Counting overdue requests for #{public_body.name}" if verbose
+
# Look for values of 'waiting_response_overdue' and
# 'waiting_response_very_overdue' which aren't directly in the
# described_state column, and instead need to be calculated:
@@ -109,7 +111,10 @@ namespace :stats do
end
end
public_body.info_requests_overdue_count = overdue_count + very_overdue_count
- public_body.save!
+ public_body.no_xapian_reindex = true
+ public_body.without_revision do
+ public_body.save!
+ end
end
end
end
diff --git a/public/stylesheets/admin.css b/public/stylesheets/admin.css
deleted file mode 100644
index 7f8d646d3..000000000
--- a/public/stylesheets/admin.css
+++ /dev/null
@@ -1,77 +0,0 @@
-/* FOIFA admin CSS */
-
-h2 {
- margin-top: 0.2em;
- margin-bottom: 0.5em;
-}
-
-table {
- border-collapse: collapse;
- margin-bottom: 1em;
-}
-
-td, th {
- border: solid 1px #000000;
-}
-td {
- vertical-align: top
-}
-td {
- max-width: 30em;
- overflow: auto;
-}
-
-tr.odd {
- background-color: #bbbbbb;
-}
-
-tr.even {
- background-color: #dddddd;
-}
-
-.entry_changed {
- font-weight: bold;
-}
-
-form {
- margin-bottom: 1em;
-}
-
-#notice {
- color: green;
- border: solid 1px green;
- padding: 1em;
-}
-#error, #errorExplanation {
- color: red;
- border: solid 1px red;
- padding: 1em;
-}
-#tag_help {
- float: right;
- width: 25%;
- margin-top: 0;
-}
-#public_body_form {
- float: left;
- width: 70%;
-}
-
-.forms_on_one_line {
- display: inline;
-}
-
-.user_photo_on_admin {
- float: right;
-}
-
-.user_photo_on_admin img {
- width: 96px;
- height: 96px;
- vertical-align: middle;
- border: 1px solid #dddddd;
- margin-right: 5px;
- padding: 2px;
-}
-
-
diff --git a/public/stylesheets/alt.css b/public/stylesheets/alt.css
deleted file mode 100644
index bf6ba2d16..000000000
--- a/public/stylesheets/alt.css
+++ /dev/null
@@ -1,232 +0,0 @@
-/*------------------------------------------------ global */
-body
-{
- padding: 0px;
- margin: 0px;
- text-align: center;
- font-family: Tahoma, Geneva, sans-serif;
-}
-
-/*------------------------------------------------ banner */
-
-#banner
-{
- position: relative;
- top: 0px;
- left: 0px;
- width: 100%;
- height: 200px;
- margin: 0px;
- background-color: #F0F0F0;
- background-image: url(../images/navimg/bnnr-ifyoudontask.png);
- background-repeat: no-repeat;
- background-position: center top;
- border-color: #993233;
- border-width: 0 0 3px 0;
- border-style: solid;
-}
-
-/*------------------------------------------------ header; not needed? */
-#header
-{ display: none; }
-
-/*------------------------------------------------ search */
-
-#navigation_search
-{
- position: absolute;
- width: 100%;
- left: 0px;
- top: 175px;
- z-index: 150;
- text-align: right;
- -moz-opacity: 0.7!important;
- filter: alpha(opacity= 70)!important;
- opacity: 0.7!important;
-}
- #navigation_search input
- {
- border-color: #010101;
- border-width: 1px;
- border-style: solid;
- background-color: #fff;
- color: #000;
- }
- #navigation_search input#navigation_search_query
- {
- width: 8em;
- }
-
-#navigation_search p { margin: 0 0.6em 0 0; }
-
-/*------------------------------------------------ topnav */
-#topnav
-{
- position: relative;
- top: 0px;
- left: 0px;
- width: 100%;
- height: auto;
- overflow: auto;
- padding: 0px 0px 0px 0px;
- z-index: 100;
- background-color: #000;
- font-size: 0.9em;
-}
-
- #topnav ul
- {
- list-style: none;
- margin: 0px;
- padding: 0px;
- }
-
- #topnav li
- {
- float: left;
- }
-
- #topnav li a, #topnav li a:visited
- {
- display: block;
- margin: 0px;
- padding: 0.15em 0.6em 0.25em 0.8em;
- color: #ADADAD;
- text-decoration: none;
- }
-
- #topnav li a:hover
- { color: #fff; }
-
- #topnav li a:active { }
-
- #topnav li a.on, #topnav li a.on:visited
- {
- font-weight: bold;
- color: #000;
- }
-
- #topnav li a.on:hover {}
-
- #topnav li a.on:active {}
-
-/*-------------------------- login/signup */
-#logged_in_bar
-{
- float: right;
- clear: none;
- font-size: 0.9em;
- z-index: 200;
- padding: 0.20em 10px 0.25em 1em;
- color: #FFF;
-}
- #logged_in_bar a, #logged_in_bar a:visited { color: #92B3FF; }
-
-/*------------------------------------------------ temp stuff */
-#staging, #alpha_notice
-{ display: none;}
-
-#staging
-{
- border-color: #FF201D;
- border-width: 1px;
- border-style: dotted;
- clear: both;
- text-align: center;
- color: #FF201D;
- margin-top: 40px;
-}
-
-#alpha_notice
-{
- padding: 0 20px 0 20px;
- border-color: #FF201D;
- border-width: 1px;
- border-style: dotted;
- background-color: #f0f0f0;
-}
-
-/*------------------------------------------------ wrapper*/
-
-#wrapper
-{
- position: relative;
- clear: both;
- top: 0em;
- padding: 0px;
- margin: 0px auto 1.2em auto;
- max-width: 50em;
- /* = 800px at default size? so 1em = 16px*/
- _width: 50em;
- text-align: left;
-}
-
-/*------------------------------------------------ content */
-
-#content
-{
- position: relative;
- padding: 2em 1em 1em 1em;
-}
-
-h1, h2, h3
-{
- font-family: Trebuchet, Trebuchet MS, Helvetica, sans-serif;
- /*Arial Black, Gadget, sans-serif*/
- font-weight: bold;
- line-height: 1em;
- letter-spacing: 0em;
- color: #555;
-}
- h1 { font-size: 1.8em;}
- h2 { font-size: 1.4em;}
- h3 { font-size: 1em;}
-
-h4, h5, h6
-{}
-
-
-/*---------------- content : recent requests sidebar */
-#find_information
-{
- width: 10.5em;
- float: right;
- clear: none;
- background-color: #e0e0e0;
- background-image: url(../images/navimg/sidebag-bg-wide.png);
- background-repeat: no-repeat;
- background-position: center top;
- padding: 105px 0.25em 0.25em 0.35em;
-}
- #find_information h1
- { font-size: 1.2em; line-height: 0.85em; margin-top: 0px;}
-
- #find_information p
- { font-size: 0.8em; line-height: 1em; }
-
- #find_information input#query
- { width: 12em; }
-
-/*---------------- content : find body */
-#make_requests
-{
- float: left;
- clear: none;
- width: 34em;
- text-align: center;
-}
-
-/*------------------------------------------------ footer */
-
-#footer
-{
- clear: both;
- position: relative;
- background-color: #F0F0F0;
- border-color: #993233;
- border-width: 3px 0 0 0;
- border-style: solid;
- margin: 1em 0 0 0;
- padding: 0.5em 0 0.5em 0;
- font-size: 0.85em;
-} \ No newline at end of file
diff --git a/script/generate_pot.sh b/script/generate_pot.sh
deleted file mode 100755
index c0540c3d9..000000000
--- a/script/generate_pot.sh
+++ /dev/null
@@ -1,22 +0,0 @@
-#!/bin/bash
-
-echo "This is NOT a completed script! Just use it as reference for what to do from the command line, or fix it until it works!"
-exit 1
-
-cd `dirname $0`
-# grab latest po files from Transifex
-tx pull -a -f
-git status | grep app.po | awk '{print $3}' | xargs git add
-git commit -m "Backup latest po files from Transifex"
-
-# now regenerate POT and PO files from Alaveteli source
-bundle exec rake gettext:store_model_attributes
-bundle exec rake gettext:findpot
-
-# upload the result to Transifex
-tx push -t
-
-# re-download (it removes the fuzzy strings and normalises it to the format last committed)
-tx pull -a -f
-git status | grep app.po | awk '{print $3}' | xargs git add
-git commit -m "Updated POT"
diff --git a/script/update-public-body-stats b/script/update-public-body-stats
new file mode 100755
index 000000000..71c2d248c
--- /dev/null
+++ b/script/update-public-body-stats
@@ -0,0 +1,4 @@
+#!/bin/bash
+
+cd `dirname $0`
+bundle exec rake --silent stats:update_public_bodies_stats
diff --git a/spec/controllers/public_body_controller_spec.rb b/spec/controllers/public_body_controller_spec.rb
index 92130f3d0..2d1b1466f 100644
--- a/spec/controllers/public_body_controller_spec.rb
+++ b/spec/controllers/public_body_controller_spec.rb
@@ -1,6 +1,8 @@
# coding: utf-8
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
+require 'nokogiri'
+
describe PublicBodyController, "when showing a body" do
render_views
@@ -78,24 +80,80 @@ describe PublicBodyController, "when listing bodies" do
response.should be_success
end
- it "should list all bodies from default locale, even when there are no translations for selected locale" do
- I18n.with_locale(:en) do
- @english_only = PublicBody.new(:name => 'English only',
- :short_name => 'EO',
- :request_email => 'english@flourish.org',
- :last_edit_editor => 'test',
- :last_edit_comment => '')
- @english_only.save
+ def make_single_language_example(locale)
+ result = nil
+ I18n.with_locale(locale) do
+ case locale
+ when :en
+ result = PublicBody.new(:name => 'English only',
+ :short_name => 'EO')
+ when :es
+ result = PublicBody.new(:name => 'Español Solamente',
+ :short_name => 'ES')
+ else
+ raise StandardError.new "Unknown locale #{locale}"
+ end
+ result.request_email = "#{locale}@example.org"
+ result.last_edit_editor = 'test'
+ result.last_edit_comment = ''
+ result.save
end
+ result
+ end
+
+ it "with no fallback, should only return bodies from the current locale" do
+ @english_only = make_single_language_example :en
+ @spanish_only = make_single_language_example :es
+ get :list, {:locale => 'es'}
+ assigns[:public_bodies].include?(@english_only).should == false
+ assigns[:public_bodies].include?(@spanish_only).should == true
+ end
+
+ it "if fallback is requested, should list all bodies from default locale, even when there are no translations for selected locale" do
+ AlaveteliConfiguration.stub!(:public_body_list_fallback_to_default_locale).and_return(true)
+ @english_only = make_single_language_example :en
get :list, {:locale => 'es'}
assigns[:public_bodies].include?(@english_only).should == true
end
+ it 'if fallback is requested, should still list public bodies only with translations in the current locale' do
+ AlaveteliConfiguration.stub!(:public_body_list_fallback_to_default_locale).and_return(true)
+ @spanish_only = make_single_language_example :es
+ get :list, {:locale => 'es'}
+ assigns[:public_bodies].include?(@spanish_only).should == true
+ end
+
+ it "if fallback is requested, make sure that there are no duplicates listed" do
+ AlaveteliConfiguration.stub!(:public_body_list_fallback_to_default_locale).and_return(true)
+ get :list, {:locale => 'es'}
+ pb_ids = assigns[:public_bodies].map { |pb| pb.id }
+ unique_pb_ids = pb_ids.uniq
+ pb_ids.sort.should === unique_pb_ids.sort
+ end
+
it 'should show public body names in the selected locale language if present' do
get :list, {:locale => 'es'}
response.should contain('El Department for Humpadinking')
end
+ it 'should not show the internal admin authority' do
+ PublicBody.internal_admin_body
+ get :list, {:locale => 'en'}
+ response.should_not contain('Internal admin authority')
+ end
+
+ it 'should order on the translated name, even with the fallback' do
+ # The names of each public body is in:
+ # <span class="head"><a>Public Body Name</a></span>
+ # ... eo extract all of those, and check that they are ordered:
+ AlaveteliConfiguration.stub!(:public_body_list_fallback_to_default_locale).and_return(true)
+ get :list, {:locale => 'es'}
+ parsed = Nokogiri::HTML(response.body)
+ public_body_names = parsed.xpath '//span[@class="head"]/a/text()'
+ public_body_names = public_body_names.map { |pb| pb.to_s }
+ public_body_names.should == public_body_names.sort
+ end
+
it 'should show public body names in the selected locale language if present for a locale with underscores' do
AlaveteliLocalization.set_locales('he_IL en', 'en')
get :list, {:locale => 'he_IL'}
diff --git a/spec/controllers/request_controller_spec.rb b/spec/controllers/request_controller_spec.rb
index 2c605a139..9c4e16c67 100644
--- a/spec/controllers/request_controller_spec.rb
+++ b/spec/controllers/request_controller_spec.rb
@@ -174,7 +174,7 @@ describe RequestController, "when changing things that appear on the request pag
ir.save!
PurgeRequest.all().first.model_id.should == ir.id
end
- it "should not create more than one entry for any given resourcce" do
+ it "should not create more than one entry for any given resource" do
ir = info_requests(:fancy_dog_request)
ir.prominence = 'hidden'
ir.save!
diff --git a/spec/models/info_request_spec.rb b/spec/models/info_request_spec.rb
index 3f2e02189..ab36a201c 100644
--- a/spec/models/info_request_spec.rb
+++ b/spec/models/info_request_spec.rb
@@ -896,8 +896,9 @@ describe InfoRequest do
describe 'when changing a described_state' do
- it "should change the counts on its PublicBody" do
+ it "should change the counts on its PublicBody without saving a new version" do
pb = public_bodies(:geraldine_public_body)
+ old_version_count = pb.versions.count
old_successful_count = pb.info_requests_successful_count
old_not_held_count = pb.info_requests_not_held_count
ir = InfoRequest.new(:external_url => 'http://www.example.com',
@@ -909,15 +910,19 @@ describe InfoRequest do
pb.info_requests_successful_count.should == (old_successful_count + 1)
ir.described_state = 'not_held'
ir.save!
+ pb.reload
pb.info_requests_successful_count.should == old_successful_count
pb.info_requests_not_held_count.should == (old_not_held_count + 1)
ir.described_state = 'successful'
ir.save!
+ pb.reload
pb.info_requests_successful_count.should == (old_successful_count + 1)
pb.info_requests_not_held_count.should == old_not_held_count
ir.destroy
+ pb.reload
pb.info_requests_successful_count.should == old_successful_count
pb.info_requests_successful_count.should == old_not_held_count
+ pb.versions.count.should == old_version_count
end
end
diff --git a/spec/models/public_body_spec.rb b/spec/models/public_body_spec.rb
index 90affaaaa..3578c0e9c 100644
--- a/spec/models/public_body_spec.rb
+++ b/spec/models/public_body_spec.rb
@@ -136,36 +136,32 @@ describe PublicBody, " when saving" do
@public_body = PublicBody.new
end
+ def set_default_attributes(public_body)
+ public_body.name = "Testing Public Body"
+ public_body.short_name = "TPB"
+ public_body.request_email = "request@localhost"
+ public_body.last_edit_editor = "*test*"
+ public_body.last_edit_comment = "This is a test"
+ end
+
it "should not be valid without setting some parameters" do
@public_body.should_not be_valid
end
it "should not be valid with misformatted request email" do
- @public_body.name = "Testing Public Body"
- @public_body.short_name = "TPB"
+ set_default_attributes(@public_body)
@public_body.request_email = "requestBOOlocalhost"
- @public_body.last_edit_editor = "*test*"
- @public_body.last_edit_comment = "This is a test"
@public_body.should_not be_valid
@public_body.should have(1).errors_on(:request_email)
end
it "should save" do
- @public_body.name = "Testing Public Body"
- @public_body.short_name = "TPB"
- @public_body.request_email = "request@localhost"
- @public_body.last_edit_editor = "*test*"
- @public_body.last_edit_comment = "This is a test"
+ set_default_attributes(@public_body)
@public_body.save!
end
it "should update first_letter" do
- @public_body.name = "Testing Public Body"
- @public_body.short_name = "TPB"
- @public_body.request_email = "request@localhost"
- @public_body.last_edit_editor = "*test*"
- @public_body.last_edit_comment = "This is a test"
-
+ set_default_attributes(@public_body)
@public_body.first_letter.should be_nil
@public_body.save!
@public_body.first_letter.should == 'T'
@@ -178,6 +174,26 @@ describe PublicBody, " when saving" do
public_body.name.should == "Mark's Public Body"
end
+
+ it 'should not create a new version when nothing has changed' do
+ @public_body.versions.size.should == 0
+ set_default_attributes(@public_body)
+ @public_body.save!
+ @public_body.versions.size.should == 1
+ @public_body.save!
+ @public_body.versions.size.should == 1
+ end
+
+ it 'should create a new version if something has changed' do
+ @public_body.versions.size.should == 0
+ set_default_attributes(@public_body)
+ @public_body.save!
+ @public_body.versions.size.should == 1
+ @public_body.name = 'Test'
+ @public_body.save!
+ @public_body.versions.size.should == 2
+ end
+
end
describe PublicBody, "when searching" do
diff --git a/vendor/plugins/strip_attributes/lib/strip_attributes.rb b/vendor/plugins/strip_attributes/lib/strip_attributes.rb
index bb93aa9a7..130d10185 100644
--- a/vendor/plugins/strip_attributes/lib/strip_attributes.rb
+++ b/vendor/plugins/strip_attributes/lib/strip_attributes.rb
@@ -8,12 +8,15 @@ module StripAttributes
attribute_names.each do |attribute_name|
value = record[attribute_name]
if value.respond_to?(:strip)
- record[attribute_name] = (value.nil?) ? nil : value.strip
+ stripped = value.strip
+ if stripped != value
+ record[attribute_name] = (value.nil?) ? nil : stripped
+ end
end
end
end
end
-
+
# Necessary because Rails has removed the narrowing of attributes using :only
# and :except on Base#attributes
def self.narrow(attribute_names, options)
@@ -28,7 +31,7 @@ module StripAttributes
attribute_names & only
else
raise ArgumentError, "Options does not specify :except or :only (#{options.keys.inspect})"
- end
+ end
end
end
end