aboutsummaryrefslogtreecommitdiffstats
path: root/spec
diff options
context:
space:
mode:
Diffstat (limited to 'spec')
-rw-r--r--spec/controllers/admin_public_body_controller_spec.rb8
-rw-r--r--spec/controllers/admin_request_controller_spec.rb4
-rw-r--r--spec/controllers/admin_track_controller_spec.rb2
-rw-r--r--spec/controllers/admin_user_controller_spec.rb2
-rw-r--r--spec/controllers/comment_controller_spec.rb2
-rw-r--r--spec/controllers/general_controller_spec.rb26
-rw-r--r--spec/controllers/public_body_controller_spec.rb34
-rw-r--r--spec/controllers/request_controller_spec.rb144
-rw-r--r--spec/controllers/request_game_controller_spec.rb2
-rw-r--r--spec/controllers/track_controller_spec.rb8
-rw-r--r--spec/controllers/user_controller_spec.rb17
-rw-r--r--spec/fixtures/files/email-folding-example-1.txt32
-rw-r--r--spec/fixtures/files/email-folding-example-1.txt.expected10
-rw-r--r--spec/fixtures/files/email-folding-example-10.txt52
-rw-r--r--spec/fixtures/files/email-folding-example-10.txt.expected25
-rw-r--r--spec/fixtures/files/email-folding-example-2.txt7
-rw-r--r--spec/fixtures/files/email-folding-example-2.txt.expected4
-rw-r--r--spec/fixtures/files/email-folding-example-3.txt18
-rw-r--r--spec/fixtures/files/email-folding-example-3.txt.expected5
-rw-r--r--spec/fixtures/files/email-folding-example-4.txt37
-rw-r--r--spec/fixtures/files/email-folding-example-4.txt.expected15
-rw-r--r--spec/fixtures/files/email-folding-example-5.txt35
-rw-r--r--spec/fixtures/files/email-folding-example-5.txt.expected24
-rw-r--r--spec/fixtures/files/email-folding-example-6.txt30
-rw-r--r--spec/fixtures/files/email-folding-example-6.txt.expected15
-rw-r--r--spec/fixtures/files/email-folding-example-7.txt30
-rw-r--r--spec/fixtures/files/email-folding-example-7.txt.expected16
-rw-r--r--spec/fixtures/files/email-folding-example-8.txt18
-rw-r--r--spec/fixtures/files/email-folding-example-8.txt.expected6
-rw-r--r--spec/fixtures/files/email-folding-example-9.txt29
-rw-r--r--spec/fixtures/files/email-folding-example-9.txt.expected9
-rw-r--r--spec/fixtures/files/iso8859_2_email.html18
-rw-r--r--spec/fixtures/files/iso8859_2_raw_email.email50
-rw-r--r--spec/fixtures/files/quoted-subject-iso8859-1.email462
-rw-r--r--spec/fixtures/files/track-response-abcmail-oof.email80
-rw-r--r--spec/fixtures/files/track-response-outlook-oof.email587
-rw-r--r--spec/fixtures/foi_attachments.yml1
-rw-r--r--spec/integration/errors_spec.rb22
-rw-r--r--spec/integration/search_request_spec.rb22
-rw-r--r--spec/integration/view_request_spec.rb32
-rw-r--r--spec/lib/tmail_extensions_spec.rb10
-rw-r--r--spec/lib/whatdotheyknow/strip_empty_sessions_spec.rb2
-rw-r--r--spec/models/has_tag_string_tag_spec.rb2
-rw-r--r--spec/models/incoming_message_spec.rb167
-rw-r--r--spec/models/info_request_event_spec.rb25
-rw-r--r--spec/models/info_request_spec.rb16
-rw-r--r--spec/models/outgoing_mailer_spec.rb4
-rw-r--r--spec/models/outgoing_message_spec.rb4
-rw-r--r--spec/models/public_body_spec.rb40
-rw-r--r--spec/models/request_mailer_spec.rb2
-rw-r--r--spec/models/track_thing_spec.rb2
-rw-r--r--spec/models/user_spec.rb14
-rw-r--r--spec/models/xapian_spec.rb81
-rw-r--r--spec/script/handle-mail-replies_spec.rb10
-rw-r--r--spec/spec_helper.rb44
-rw-r--r--spec/views/public_body/show.rhtml_spec.rb2
-rw-r--r--spec/views/request/_after_actions.rhtml_spec.rb2
-rw-r--r--spec/views/request/_describe_state.rhtml_spec.rb2
-rw-r--r--spec/views/request/list.rhtml_spec.rb2
-rw-r--r--spec/views/request/show.rhtml_spec.rb2
-rw-r--r--spec/views/request_game/play.rhtml_spec.rb2
61 files changed, 2157 insertions, 218 deletions
diff --git a/spec/controllers/admin_public_body_controller_spec.rb b/spec/controllers/admin_public_body_controller_spec.rb
index 0a90cd64b..22af3df80 100644
--- a/spec/controllers/admin_public_body_controller_spec.rb
+++ b/spec/controllers/admin_public_body_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe AdminPublicBodyController, "when administering public bodies" do
integrate_views
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
username = MySociety::Config.get('ADMIN_USERNAME', '')
@@ -57,7 +57,7 @@ end
describe AdminPublicBodyController, "when administering public bodies and paying attention to authentication" do
integrate_views
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "disallows non-authenticated users to do anything" do
@request.env["HTTP_AUTHORIZATION"] = ""
@@ -107,7 +107,7 @@ end
describe AdminPublicBodyController, "when administering public bodies with i18n" do
integrate_views
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
username = MySociety::Config.get('ADMIN_USERNAME', '')
@@ -176,7 +176,7 @@ end
describe AdminPublicBodyController, "when creating public bodies with i18n" do
integrate_views
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
username = MySociety::Config.get('ADMIN_USERNAME', '')
diff --git a/spec/controllers/admin_request_controller_spec.rb b/spec/controllers/admin_request_controller_spec.rb
index 6f9af0525..635d73b9e 100644
--- a/spec/controllers/admin_request_controller_spec.rb
+++ b/spec/controllers/admin_request_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe AdminRequestController, "when administering requests" do
integrate_views
- fixtures :info_requests, :outgoing_messages, :users, :info_request_events, :public_bodies, :public_body_translations
+ fixtures :users, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before { basic_auth_login @request }
it "shows the index/list page" do
@@ -41,7 +41,7 @@ end
describe AdminRequestController, "when administering the holding pen" do
integrate_views
- fixtures :info_requests, :incoming_messages, :raw_emails, :users, :public_bodies, :public_body_translations
+ fixtures :users, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
basic_auth_login @request
load_raw_emails_data(raw_emails)
diff --git a/spec/controllers/admin_track_controller_spec.rb b/spec/controllers/admin_track_controller_spec.rb
index 4d5b0ac5e..b87ee9f0e 100644
--- a/spec/controllers/admin_track_controller_spec.rb
+++ b/spec/controllers/admin_track_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe AdminTrackController, "when administering tracks" do
integrate_views
- fixtures :track_things, :users
+ fixtures :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "shows the list page" do
get :list
diff --git a/spec/controllers/admin_user_controller_spec.rb b/spec/controllers/admin_user_controller_spec.rb
index 313f3f328..b2b2d0626 100644
--- a/spec/controllers/admin_user_controller_spec.rb
+++ b/spec/controllers/admin_user_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe AdminUserController, "when administering users" do
integrate_views
- fixtures :users
+ fixtures :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before { basic_auth_login @request }
it "shows the index/list page" do
diff --git a/spec/controllers/comment_controller_spec.rb b/spec/controllers/comment_controller_spec.rb
index 2b0f5eee2..4c14b8d24 100644
--- a/spec/controllers/comment_controller_spec.rb
+++ b/spec/controllers/comment_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe CommentController, "when commenting on a request" do
integrate_views
- fixtures :info_requests, :outgoing_messages, :public_bodies, :public_body_translations, :users, :comments
+ fixtures :users, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should give an error and render 'new' template when body text is just some whitespace" do
post :new, :url_title => info_requests(:naughty_chicken_request).url_title,
diff --git a/spec/controllers/general_controller_spec.rb b/spec/controllers/general_controller_spec.rb
index 1ffbda90d..40a676d61 100644
--- a/spec/controllers/general_controller_spec.rb
+++ b/spec/controllers/general_controller_spec.rb
@@ -2,15 +2,19 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe GeneralController, "when searching" do
integrate_views
- fixtures [ :info_requests,
- :info_request_events,
- :public_bodies,
- :public_body_translations,
- :users,
- :raw_emails,
- :outgoing_messages,
- :incoming_messages,
- :comments ]
+ fixtures [
+ :public_bodies,
+ :public_body_translations,
+ :public_body_versions,
+ :users,
+ :info_requests,
+ :raw_emails,
+ :incoming_messages,
+ :outgoing_messages,
+ :comments,
+ :info_request_events,
+ :track_things,
+ ]
before(:each) do
load_raw_emails_data(raw_emails)
@@ -70,13 +74,13 @@ describe GeneralController, "when searching" do
describe "when using different locale settings" do
home_link_regex = /href=".*\/en"/
it "should generate URLs with a locale prepended when there's more than one locale set" do
- ActionController::Routing::Routes.add_filters(['conditionallyprependlocale'])
+ ActionController::Routing::Routes.add_filters('conditionallyprependlocale')
get :frontpage
response.should have_text(home_link_regex)
end
it "should generate URLs without a locale prepended when there's only one locale set" do
- ActionController::Routing::Routes.add_filters(['conditionallyprependlocale'])
+ ActionController::Routing::Routes.add_filters('conditionallyprependlocale')
old_available_locales = FastGettext.default_available_locales
available_locales = ['en']
FastGettext.default_available_locales = available_locales
diff --git a/spec/controllers/public_body_controller_spec.rb b/spec/controllers/public_body_controller_spec.rb
index c5c9d60e1..8182e1331 100644
--- a/spec/controllers/public_body_controller_spec.rb
+++ b/spec/controllers/public_body_controller_spec.rb
@@ -4,7 +4,7 @@ require 'json'
describe PublicBodyController, "when showing a body" do
integrate_views
- fixtures :public_bodies, :public_body_translations, :public_body_versions
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should be successful" do
get :show, :url_name => "dfh", :view => 'all'
@@ -61,13 +61,28 @@ end
describe PublicBodyController, "when listing bodies" do
integrate_views
- fixtures :public_bodies, :public_body_translations, :public_body_versions
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should be successful" do
get :list
response.should be_success
end
+ it "should list all bodies from default locale, even when there are no translations for selected locale" do
+ PublicBody.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
+ end
+ PublicBody.with_locale(:es) do
+ get :list
+ assigns[:public_bodies].length.should == 3
+ end
+ end
+
it "should list bodies in alphabetical order" do
get :list
@@ -110,7 +125,7 @@ describe PublicBodyController, "when listing bodies" do
get :list, :tag => "other"
response.should render_template('list')
assigns[:public_bodies].should == [ public_bodies(:geraldine_public_body) ]
-
+
get :list
response.should render_template('list')
assigns[:public_bodies].count.should == 2
@@ -142,7 +157,7 @@ end
describe PublicBodyController, "when showing JSON version for API" do
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should be successful" do
get :show, :url_name => "dfh", :format => "json", :view => 'all'
@@ -157,12 +172,12 @@ describe PublicBodyController, "when showing JSON version for API" do
end
describe PublicBodyController, "when doing type ahead searches" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should return nothing for the empty query string" do
get :search_typeahead, :q => ""
response.should render_template('public_body/_search_ahead')
- assigns[:xapian_requests].results.size.should == 0
+ assigns[:xapian_requests].should be_nil
end
it "should return a body matching the given keyword, but not users with a matching description" do
@@ -187,10 +202,9 @@ describe PublicBodyController, "when doing type ahead searches" do
assigns[:xapian_requests].results[0][:model].name.should == public_bodies(:humpadink_public_body).name
end
- it "should return partial matches" do
- get :search_typeahead, :q => "geral" # 'geral' for 'Geraldine'
+ it "should not return matches for short words" do
+ get :search_typeahead, :q => "b"
response.should render_template('public_body/_search_ahead')
- assigns[:xapian_requests].results.size.should == 1
- assigns[:xapian_requests].results[0][:model].name.should == public_bodies(:geraldine_public_body).name
+ assigns[:xapian_requests].should be_nil
end
end
diff --git a/spec/controllers/request_controller_spec.rb b/spec/controllers/request_controller_spec.rb
index 494713a4a..4994c2a8f 100644
--- a/spec/controllers/request_controller_spec.rb
+++ b/spec/controllers/request_controller_spec.rb
@@ -1,9 +1,10 @@
+# -*- coding: utf-8 -*-
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
require 'json'
describe RequestController, "when listing recent requests" do
- fixtures :info_requests, :outgoing_messages, :users, :info_request_events, :public_bodies, :public_body_translations, :incoming_messages, :raw_emails, :comments
+ fixtures :users, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
@@ -51,7 +52,7 @@ end
describe RequestController, "when showing one request" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -104,10 +105,12 @@ describe RequestController, "when showing one request" do
integrate_views
it "should receive incoming messages, send email to creator, and show them" do
+ ir = info_requests(:fancy_dog_request)
+ ir.incoming_messages.each { |x| x.parse_raw_email! }
+
get :show, :url_title => 'why_do_you_have_such_a_fancy_dog'
size_before = assigns[:info_request_events].size
- ir = info_requests(:fancy_dog_request)
receive_incoming_mail('incoming-request-plain.email', ir.incoming_email)
deliveries = ActionMailer::Base.deliveries
deliveries.size.should == 1
@@ -119,6 +122,8 @@ describe RequestController, "when showing one request" do
end
it "should download attachments" do
+ ir = info_requests(:fancy_dog_request)
+ ir.incoming_messages.each { |x| x.parse_raw_email! }
get :show, :url_title => 'why_do_you_have_such_a_fancy_dog'
response.content_type.should == "text/html"
size_before = assigns[:info_request_events].size
@@ -128,7 +133,7 @@ describe RequestController, "when showing one request" do
get :show, :url_title => 'why_do_you_have_such_a_fancy_dog'
(assigns[:info_request_events].size - size_before).should == 1
-
+ ir.reload
get :get_attachment, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt']
response.content_type.should == "text/plain"
response.should have_text(/Second hello/)
@@ -137,19 +142,60 @@ describe RequestController, "when showing one request" do
response.should have_text(/First hello/)
end
+ it "should convert message body to UTF8" do
+ ir = info_requests(:fancy_dog_request)
+ receive_incoming_mail('iso8859_2_raw_email.email', ir.incoming_email)
+ get :show, :url_title => 'why_do_you_have_such_a_fancy_dog'
+ response.should have_text(/tënde/u)
+ end
+
it "should generate valid HTML verson of plain text attachments " do
ir = info_requests(:fancy_dog_request)
receive_incoming_mail('incoming-request-two-same-name.email', ir.incoming_email)
+ ir.reload
get :get_attachment_as_html, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt.html'], :skip_cache => 1
response.content_type.should == "text/html"
response.should have_text(/Second hello/)
end
+ it "should not cause a reparsing of the raw email, even when the result would be a 404 " do
+ ir = info_requests(:fancy_dog_request)
+ receive_incoming_mail('incoming-request-two-same-name.email', ir.incoming_email)
+ ir.reload
+ attachment = IncomingMessage.get_attachment_by_url_part_number(ir.incoming_messages[1].get_attachments_for_display, 2)
+ attachment.body.should have_text(/Second hello/)
+
+ # change the raw_email associated with the message; this only be reparsed when explicitly asked for
+ ir.incoming_messages[1].raw_email.data = ir.incoming_messages[1].raw_email.data.sub("Second", "Third")
+ # asking for an attachment by the wrong filename results
+ # in a 404 for browsing users. This shouldn't cause a
+ # re-parse...
+ lambda {
+ get :get_attachment_as_html, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt.baz.html'], :skip_cache => 1
+ }.should raise_error(ActiveRecord::RecordNotFound)
+
+ attachment = IncomingMessage.get_attachment_by_url_part_number(ir.incoming_messages[1].get_attachments_for_display, 2)
+ attachment.body.should have_text(/Second hello/)
+
+ # ...nor should asking for it by its correct filename...
+ get :get_attachment_as_html, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt.html'], :skip_cache => 1
+ response.should_not have_text(/Third hello/)
+
+ # ...but if we explicitly ask for attachments to be extracted, then they should be
+ force = true
+ ir.incoming_messages[1].parse_raw_email!(force)
+ attachment = IncomingMessage.get_attachment_by_url_part_number(ir.incoming_messages[1].get_attachments_for_display, 2)
+ attachment.body.should have_text(/Second hello/)
+ get :get_attachment_as_html, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt.html'], :skip_cache => 1
+ response.should have_text(/Third hello/)
+ end
+
it "should treat attachments with unknown extensions as binary" do
ir = info_requests(:fancy_dog_request)
receive_incoming_mail('incoming-request-attachment-unknown-extension.email', ir.incoming_email)
+ ir.reload
- get :get_attachment, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.qwglhm']
+ get :get_attachment, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.qwglhm'], :skip_cache => 1
response.content_type.should == "application/octet-stream"
response.should have_text(/an unusual sort of file/)
end
@@ -192,8 +238,9 @@ describe RequestController, "when showing one request" do
ir.user.censor_rules << censor_rule
receive_incoming_mail('incoming-request-two-same-name.email', ir.incoming_email)
+ ir.reload
- get :get_attachment, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt']
+ get :get_attachment, :incoming_message_id => ir.incoming_messages[1].id, :id => ir.id, :part => 2, :file_name => ['hello.txt'], :skip_cache => 1
response.content_type.should == "text/plain"
response.should have_text(/xxxxxx hello/)
end
@@ -202,7 +249,22 @@ describe RequestController, "when showing one request" do
ir = info_requests(:fancy_dog_request)
receive_incoming_mail('incoming-request-two-same-name.email', ir.incoming_email)
+ # XXX this is horrid, but don't know a better way. If we
+ # don't do this, the info_request_event to which the
+ # info_request is attached still uses the unmodified
+ # version from the fixture.
+ #event = info_request_events(:useless_incoming_message_event)
+ ir.reload
+ assert ir.info_request_events[3].incoming_message.get_attachments_for_display.count == 2
+ ir.save!
+ ir.incoming_messages.last.save!
get :show, :url_title => 'why_do_you_have_such_a_fancy_dog'
+ assert assigns[:info_request].info_request_events[3].incoming_message.get_attachments_for_display.count == 2
+ # the issue is that the info_request_events have got cached on them the old info_requests.
+ # where i'm at: trying to replace those fields that got re-read from the raw email. however tests are failing in very strange ways. currently I don't appear to be getting any attachments parsed in at all when in the template (see "*****" in _correspondence.rhtml) but do when I'm in the code.
+
+ # so at this point, assigns[:info_request].incoming_messages[1].get_attachments_for_display is returning stuff, but the equivalent thing in the template isn't.
+ # but something odd is that the above is return a whole load of attachments which aren't there in the controller
response.body.should have_tag("p.attachment strong", /hello.txt/m)
censor_rule = CensorRule.new()
@@ -217,10 +279,17 @@ describe RequestController, "when showing one request" do
end
it "should make a zipfile available, which has a different URL when it changes" do
+ title = 'why_do_you_have_such_a_fancy_dog'
ir = info_requests(:fancy_dog_request)
session[:user_id] = ir.user.id # bob_smith_user
+ get :download_entire_request, :url_title => title
+ assigns[:url_path].should have_text(/#{title}.zip$/)
+ old_path = assigns[:url_path]
+ response.location.should have_text(/#{assigns[:url_path]}$/)
+ zipfile = Zip::ZipFile.open(File.join(File.dirname(__FILE__), "../../cache/zips", old_path)) { |zipfile|
+ zipfile.count.should == 2
+ }
receive_incoming_mail('incoming-request-two-same-name.email', ir.incoming_email)
- title = 'why_do_you_have_such_a_fancy_dog'
get :download_entire_request, :url_title => title
assigns[:url_path].should have_text(/#{title}.zip$/)
old_path = assigns[:url_path]
@@ -232,17 +301,16 @@ describe RequestController, "when showing one request" do
get :download_entire_request, :url_title => title
assigns[:url_path].should have_text(/#{title}.zip$/)
response.location.should have_text(/#{assigns[:url_path]}/)
- assigns[:url_path].should_not == old_path
zipfile = Zip::ZipFile.open(File.join(File.dirname(__FILE__), "../../cache/zips", assigns[:url_path])) { |zipfile|
zipfile.count.should == 4
-zipfile.entries.each {|x| puts x.name}
}
+ assigns[:url_path].should_not == old_path
end
end
end
describe RequestController, "when changing prominence of a request" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -358,7 +426,7 @@ end
describe RequestController, "when creating a new request" do
integrate_views
- fixtures :info_requests, :outgoing_messages, :public_bodies, :public_body_translations, :users
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@user = users(:bob_smith_user)
@@ -542,7 +610,7 @@ end
describe RequestController, "when viewing an individual response for reply/followup" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -589,7 +657,7 @@ end
describe RequestController, "when classifying an information request" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
@dog_request = info_requests(:fancy_dog_request)
@@ -800,7 +868,7 @@ describe RequestController, "when classifying an information request" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /as needing admin/
- mail.from_addrs.to_s.should == @request_owner.name_and_email
+ mail.from_addrs.first.to_s.should == @request_owner.name_and_email
end
it 'should say it is showing advice as to what to do next' do
@@ -925,7 +993,7 @@ end
describe RequestController, "when sending a followup message" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -978,7 +1046,7 @@ describe RequestController, "when sending a followup message" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /What a useless response! You suck./
- mail.to_addrs.to_s.should == "FOI Person <foiperson@localhost>"
+ mail.to_addrs.first.to_s.should == "FOI Person <foiperson@localhost>"
response.should redirect_to(:action => 'show', :url_title => info_requests(:fancy_dog_request).url_title)
@@ -1008,7 +1076,7 @@ end
describe RequestController, "sending overdue request alerts" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -1025,7 +1093,7 @@ describe RequestController, "sending overdue request alerts" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /promptly, as normally/
- mail.to_addrs.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
mail.body =~ /(http:\/\/.*\/c\/(.*))/
mail_url = $1
@@ -1053,7 +1121,7 @@ describe RequestController, "sending overdue request alerts" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /promptly, as normally/
- mail.to_addrs.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
end
it "should send not actually send the overdue alert if the user is banned" do
@@ -1078,7 +1146,7 @@ describe RequestController, "sending overdue request alerts" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /required by law/
- mail.to_addrs.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:naughty_chicken_request).user.name_and_email
mail.body =~ /(http:\/\/.*\/c\/(.*))/
mail_url = $1
@@ -1096,7 +1164,7 @@ end
describe RequestController, "sending unclassified new response reminder alerts" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
@@ -1109,7 +1177,7 @@ describe RequestController, "sending unclassified new response reminder alerts"
deliveries.size.should == 3 # sufficiently late it sends reminders too
mail = deliveries[0]
mail.body.should =~ /To let us know/
- mail.to_addrs.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
mail.body =~ /(http:\/\/.*\/c\/(.*))/
mail_url = $1
mail_token = $2
@@ -1127,7 +1195,7 @@ end
describe RequestController, "clarification required alerts" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -1146,7 +1214,7 @@ describe RequestController, "clarification required alerts" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /asked you to explain/
- mail.to_addrs.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
mail.body =~ /(http:\/\/.*\/c\/(.*))/
mail_url = $1
mail_token = $2
@@ -1181,7 +1249,7 @@ end
describe RequestController, "comment alerts" do
integrate_views
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -1200,7 +1268,7 @@ describe RequestController, "comment alerts" do
deliveries = ActionMailer::Base.deliveries
mail = deliveries[0]
mail.body.should =~ /has annotated your/
- mail.to_addrs.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
mail.body =~ /(http:\/\/.*)/
mail_url = $1
@@ -1243,7 +1311,7 @@ describe RequestController, "comment alerts" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /There are 2 new annotations/
- mail.to_addrs.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
+ mail.to_addrs.first.to_s.should == info_requests(:fancy_dog_request).user.name_and_email
mail.body =~ /(http:\/\/.*)/
mail_url = $1
@@ -1256,7 +1324,7 @@ end
describe RequestController, "when viewing comments" do
integrate_views
- fixtures :users, :raw_emails, :incoming_messages, :info_requests
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -1279,9 +1347,10 @@ end
describe RequestController, "authority uploads a response from the web interface" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users
+ integrate_views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
- before(:all) do
+ before(:each) do
# domain after the @ is used for authentication of FOI officers, so to test it
# we need a user which isn't at localhost.
@normal_user = User.new(:name => "Mr. Normal", :email => "normal-user@flourish.org",
@@ -1335,7 +1404,7 @@ describe RequestController, "authority uploads a response from the web interface
# How do I test a file upload in rails?
# http://stackoverflow.com/questions/1178587/how-do-i-test-a-file-upload-in-rails
- it "should let the requester upload a file" do
+ it "should let the authority upload a file" do
@ir = info_requests(:fancy_dog_request)
incoming_before = @ir.incoming_messages.size
session[:user_id] = @foi_officer_user.id
@@ -1366,7 +1435,7 @@ end
describe RequestController, "when showing JSON version for API" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
@@ -1386,12 +1455,12 @@ describe RequestController, "when showing JSON version for API" do
end
describe RequestController, "when doing type ahead searches" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should return nothing for the empty query string" do
get :search_typeahead, :q => ""
response.should render_template('request/_search_ahead.rhtml')
- assigns[:xapian_requests].results.size.should == 0
+ assigns[:xapian_requests].should be_nil
end
it "should return a request matching the given keyword, but not users with a matching description" do
@@ -1409,11 +1478,10 @@ describe RequestController, "when doing type ahead searches" do
assigns[:xapian_requests].results[1][:model].title.should == info_requests(:naughty_chicken_request).title
end
- it "should return partial matches" do
- get :search_typeahead, :q => "chick" # 'chick' for 'chicken'
+ it "should not return matches for short words" do
+ get :search_typeahead, :q => "a"
response.should render_template('request/_search_ahead.rhtml')
- assigns[:xapian_requests].results.size.should == 1
- assigns[:xapian_requests].results[0][:model].title.should == info_requests(:naughty_chicken_request).title
+ assigns[:xapian_requests].should be_nil
end
end
diff --git a/spec/controllers/request_game_controller_spec.rb b/spec/controllers/request_game_controller_spec.rb
index 4883bfdd6..cc0808ef3 100644
--- a/spec/controllers/request_game_controller_spec.rb
+++ b/spec/controllers/request_game_controller_spec.rb
@@ -2,7 +2,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe RequestGameController, "when playing the game" do
- fixtures :info_requests, :info_request_events, :public_bodies, :public_body_translations, :users, :incoming_messages, :raw_emails, :outgoing_messages # all needed as integrating views
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things # all needed as integrating views
before(:each) do
load_raw_emails_data(raw_emails)
end
diff --git a/spec/controllers/track_controller_spec.rb b/spec/controllers/track_controller_spec.rb
index 435d9a0d3..90d13495f 100644
--- a/spec/controllers/track_controller_spec.rb
+++ b/spec/controllers/track_controller_spec.rb
@@ -36,7 +36,7 @@ end
describe TrackController, "when sending alerts for a track" do
integrate_views
- fixtures :comments, :info_requests, :outgoing_messages, :incoming_messages, :raw_emails, :info_request_events, :users, :track_things, :track_things_sent_emails, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things, :track_things_sent_emails
include LinkToHelper # for main_url
before(:each) do
@@ -58,7 +58,7 @@ describe TrackController, "when sending alerts for a track" do
deliveries.size.should == 1
mail = deliveries[0]
mail.body.should =~ /Alter your subscription/
- mail.to_addrs.to_s.should include(users(:silly_name_user).email)
+ mail.to_addrs.first.to_s.should include(users(:silly_name_user).email)
mail.body =~ /(http:\/\/.*\/c\/(.*))/
mail_url = $1
mail_token = $2
@@ -110,7 +110,7 @@ end
describe TrackController, "when viewing RSS feed for a track" do
integrate_views
- fixtures :info_requests, :outgoing_messages, :incoming_messages, :raw_emails, :info_request_events, :users, :track_things, :comments, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
@@ -136,7 +136,7 @@ end
describe TrackController, "when viewing JSON version of a track feed" do
integrate_views
- fixtures :info_requests, :outgoing_messages, :incoming_messages, :raw_emails, :info_request_events, :users, :track_things, :comments, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
diff --git a/spec/controllers/user_controller_spec.rb b/spec/controllers/user_controller_spec.rb
index b4cc0d6e3..cf50bcc7a 100644
--- a/spec/controllers/user_controller_spec.rb
+++ b/spec/controllers/user_controller_spec.rb
@@ -1,3 +1,4 @@
+# coding: utf-8
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
require 'json'
@@ -7,7 +8,7 @@ require 'json'
describe UserController, "when showing a user" do
integrate_views
- fixtures :users, :outgoing_messages, :incoming_messages, :raw_emails, :info_requests, :info_request_events, :comments, :public_bodies, :public_body_translations
+ fixtures :users, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -27,6 +28,16 @@ describe UserController, "when showing a user" do
response.should render_template('show')
end
+ it "should distinguish between 'my profile' and 'my requests' for logged in users" do
+ session[:user_id] = users(:bob_smith_user).id
+ get :show, :url_name => "bob_smith", :view => 'requests'
+ response.body.should_not include("Change your password")
+ response.body.should include("Freedom of Information requests")
+ get :show, :url_name => "bob_smith", :view => 'profile'
+ response.body.should include("Change your password")
+ response.body.should_not include("Freedom of Information requests")
+ end
+
it "should assign the user" do
get :show, :url_name => "bob_smith"
assigns[:display_user].should == users(:bob_smith_user)
@@ -260,8 +271,8 @@ describe UserController, "when sending another user a message" do
mail = deliveries[0]
mail.body.should include("Bob Smith has used #{MySociety::Config.get('SITE_NAME')} to send you the message below")
mail.body.should include("Just a test!")
- #mail.to_addrs.to_s.should == users(:silly_name_user).name_and_email # XXX fix some nastiness with quoting name_and_email
- mail.from_addrs.to_s.should == users(:bob_smith_user).name_and_email
+ #mail.to_addrs.first.to_s.should == users(:silly_name_user).name_and_email # XXX fix some nastiness with quoting name_and_email
+ mail.from_addrs.first.to_s.should == users(:bob_smith_user).name_and_email
end
end
diff --git a/spec/fixtures/files/email-folding-example-1.txt b/spec/fixtures/files/email-folding-example-1.txt
new file mode 100644
index 000000000..9d0810a36
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-1.txt
@@ -0,0 +1,32 @@
+Dear Mr Pollard,
+
+Thank you for your email of 26 February. Please find a response attached.
+
+Yours faithfully,
+
+On behalf of James Hall, Chief Executive
+Identity and Passport Service
+
+<<9032 C Pollard final response.doc>>
+
+**********************************************************************
+
+This email and any files transmitted with it are confidential and
+
+intended solely for the use of the individual or entity to whom they
+
+are addressed. If you have received this email in error please notify
+
+the system manager.
+
+This footnote also confirms that this email message has been swept for the
+presence of computer viruses.
+
+**********************************************************************
+
+The original of this email was scanned for viruses by the Government
+Secure Intranet virus scanning service supplied by Cable&Wireless in
+partnership with MessageLabs. (CCTM Certificate Number 2007/11/0032.) On
+leaving the GSi this email was certified virus free.
+Communications via the GSi may be automatically logged, monitored and/or
+recorded for legal purposes.
diff --git a/spec/fixtures/files/email-folding-example-1.txt.expected b/spec/fixtures/files/email-folding-example-1.txt.expected
new file mode 100644
index 000000000..801542288
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-1.txt.expected
@@ -0,0 +1,10 @@
+Dear Mr Pollard,
+
+Thank you for your email of 26 February. Please find a response attached.
+
+Yours faithfully,
+
+On behalf of James Hall, Chief Executive
+Identity and Passport Service
+
+<<9032 C Pollard final response.doc>>
diff --git a/spec/fixtures/files/email-folding-example-10.txt b/spec/fixtures/files/email-folding-example-10.txt
new file mode 100644
index 000000000..0fabb7f9c
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-10.txt
@@ -0,0 +1,52 @@
+Please note: it is not possible to reply to this email. To contact the
+Department of Health, please visit the 'Contact us' page on the
+Department’s website.
+
+-----------------------------------------------------------------------------------------
+
+ Apologies that you were not able to read our previous response of 4
+ October. Please find the text of that email below.
+
+Our ref: DE00000642471
+
+Dear Ms Peters Rock,
+
+You requested your correspondence to be treated under the Freedom of
+Information Act.  However, as your correspondence asked for general
+information, rather than requesting recorded information or documentation,
+I should advise you that on this occasion we have not considered your
+correspondence under the provisions of the Act.
+
+I am sorry I cannot be more helpful.
+
+Yours sincerely,
+Simon Dove
+Customer Service Centre
+Department of Health
+
+
+
+
+-------------------------------------------------------------------------------------------------------------------------
+
+
+Please do not reply to this email. To contact the Department of Health,
+please visit the 'Contact us' page on the Department’s website, where you
+can also view our performance against quarterly service targets.
+
+
+- - Disclaimer - -
+This e-mail and any files transmitted with it are confidential. If you are
+not the intended recipient, any reading, printing, storage, disclosure,
+copying or any other action taken in respect of this e-mail is prohibited
+and may be unlawful. If you are not the intended recipient, please notify
+the sender immediately by using the reply function and then permanently
+delete what you have received.
+
+Incoming and outgoing e-mail messages are routinely monitored for
+compliance with the Department of Health's policy on the use of electronic
+communications. For more information on the Department of Health's e-mail
+policy click here http://www.dh.gov.uk/terms
+
+The original of this email was scanned for viruses by the Government Secure Intranet virus scanning service supplied by Cable&Wireless Worldwide in partnership with MessageLabs. (CCTM Certificate Number 2009/09/0052.) On leaving the GSi this email was certified virus free.
+Communications via the GSi may be automatically logged, monitored and/or recorded for legal purposes.
diff --git a/spec/fixtures/files/email-folding-example-10.txt.expected b/spec/fixtures/files/email-folding-example-10.txt.expected
new file mode 100644
index 000000000..e4f704c0e
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-10.txt.expected
@@ -0,0 +1,25 @@
+Please note: it is not possible to reply to this email. To contact the
+Department of Health, please visit the 'Contact us' page on the
+Department’s website.
+
+-----------------------------------------------------------------------------------------
+
+ Apologies that you were not able to read our previous response of 4
+ October. Please find the text of that email below.
+
+Our ref: DE00000642471
+
+Dear Ms Peters Rock,
+
+You requested your correspondence to be treated under the Freedom of
+Information Act.  However, as your correspondence asked for general
+information, rather than requesting recorded information or documentation,
+I should advise you that on this occasion we have not considered your
+correspondence under the provisions of the Act.
+
+I am sorry I cannot be more helpful.
+
+Yours sincerely,
+Simon Dove
+Customer Service Centre
+Department of Health
diff --git a/spec/fixtures/files/email-folding-example-2.txt b/spec/fixtures/files/email-folding-example-2.txt
new file mode 100644
index 000000000..13dd39a69
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-2.txt
@@ -0,0 +1,7 @@
+Preface to the message which we are not interested in
+
+-----------------------------------------------------------------------------------------
+Important message about cheese
+-----------------------------------------------------------------------------------------
+
+Actual footer that contains the word confidential
diff --git a/spec/fixtures/files/email-folding-example-2.txt.expected b/spec/fixtures/files/email-folding-example-2.txt.expected
new file mode 100644
index 000000000..e52fbe443
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-2.txt.expected
@@ -0,0 +1,4 @@
+Preface to the message which we are not interested in
+
+-----------------------------------------------------------------------------------------
+Important message about cheese
diff --git a/spec/fixtures/files/email-folding-example-3.txt b/spec/fixtures/files/email-folding-example-3.txt
new file mode 100644
index 000000000..28a3861f6
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-3.txt
@@ -0,0 +1,18 @@
+Reference : T3241/8
+
+Thank you for your e-mail enquiry of 12th February.
+
+A reply is attached.
+
+**********************************************************************
+This email and any files transmitted with it are private and intended
+solely for the use of the individual or entity to whom they are addressed.
+If you have received this email in error please return it to the address
+it came from telling them it is not for you and then delete it from your system.
+
+This email message has been swept for computer viruses.
+
+**********************************************************************
+
+The original of this email was scanned for viruses by the Government Secure Intranet virus scanning service supplied by Cable&Wireless in partnership with MessageLabs. (CCTM Certificate Number 2007/11/0032.) On leaving the GSi this email was certified virus free.
+Communications via the GSi may be automatically logged, monitored and/or recorded for legal purposes.
diff --git a/spec/fixtures/files/email-folding-example-3.txt.expected b/spec/fixtures/files/email-folding-example-3.txt.expected
new file mode 100644
index 000000000..e2cca4933
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-3.txt.expected
@@ -0,0 +1,5 @@
+Reference : T3241/8
+
+Thank you for your e-mail enquiry of 12th February.
+
+A reply is attached.
diff --git a/spec/fixtures/files/email-folding-example-4.txt b/spec/fixtures/files/email-folding-example-4.txt
new file mode 100644
index 000000000..63b94a35c
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-4.txt
@@ -0,0 +1,37 @@
+<<Freedom of Information request - Contracts or options with Kimberley
+Developments or Waitrose>>
+
+Arthur Pritchard
+Property & Assets Manager
+Tel: 01625 504234
+Fax: 01625 504268
+e-mail: [1][email address]
+
+***********************************************************************************
+The information in this Email and any attachments is personal to the
+sender and the views of the author may not necessarily reflect those
+of Macclesfield Borough Council. The information is strictly confidential
+and is intended only for the named person or organisation to whom it is
+addressed as it may contain privileged and confidential information. If
+you are not the intended recipient do not copy, distribute or use this
+Email, and please notify the sender. Please note that we cannot
+guarantee that this message or any attachment is virus free or has not
+been intercepted and amended.
+***********************************************************************************
+
+Disclaimer
+
+--------------------------------------------------------------------------
+
+This email message has been scanned for viruses by Mimecast.
+Mimecast delivers a complete managed email solution from a single web
+based platform.
+For more information please visit [2]http://www.mimecast.com
+
+--------------------------------------------------------------------------
+
+References
+
+Visible links
+1. mailto:[email address]
+2. http://www.mimecast.com/
diff --git a/spec/fixtures/files/email-folding-example-4.txt.expected b/spec/fixtures/files/email-folding-example-4.txt.expected
new file mode 100644
index 000000000..42334a290
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-4.txt.expected
@@ -0,0 +1,15 @@
+<<Freedom of Information request - Contracts or options with Kimberley
+Developments or Waitrose>>
+
+Arthur Pritchard
+Property & Assets Manager
+Tel: 01625 504234
+Fax: 01625 504268
+e-mail: [1][email address]
+FOLDED_QUOTED_SECTION
+FOLDED_QUOTED_SECTION
+References
+
+Visible links
+1. mailto:[email address]
+2. http://www.mimecast.com/
diff --git a/spec/fixtures/files/email-folding-example-5.txt b/spec/fixtures/files/email-folding-example-5.txt
new file mode 100644
index 000000000..3d0964722
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-5.txt
@@ -0,0 +1,35 @@
+Hi Simon
+
+My apologies for timescale of response. The data forwarded is a public
+register, and is updated on a frequent and regular basis; your request
+unfortunately coincided with annual leave and a monthly update of the
+spreadsheet. As the definition of an HMO under the Housing Act 2004
+differs to that under planning legislation, I have forwarded this and
+your original request on to Andy England, Development Control Manager to
+respond independantly.
+
+If I can be of further assistance please contact me
+
+Barry Turnbull
+Environmental Health Co-ordinator (Housing)
+Housing, Health and Community Safety
+
+--
+
+****************************************************************
+Any opinions expressed are not necessarily those of Penwith
+District Council. This e-mail and any attachments, replies
+and forwarded copies are confidential and are strictly for
+the use of named recipient(s) only. If you have received
+it in error you may not make use of it. Please e-mail us,
+including a copy of the message to, [email address].
+Then delete the e-mail and any copies.
+****************************************************************
+
+**********************************************************************
+This footnote confirms that this message, and any
+attachments, have been screened by McAffee
+Webshield for the presence of virus code.
+
+Penwith District Council
+**********************************************************************
diff --git a/spec/fixtures/files/email-folding-example-5.txt.expected b/spec/fixtures/files/email-folding-example-5.txt.expected
new file mode 100644
index 000000000..fbb0f0f50
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-5.txt.expected
@@ -0,0 +1,24 @@
+Hi Simon
+
+My apologies for timescale of response. The data forwarded is a public
+register, and is updated on a frequent and regular basis; your request
+unfortunately coincided with annual leave and a monthly update of the
+spreadsheet. As the definition of an HMO under the Housing Act 2004
+differs to that under planning legislation, I have forwarded this and
+your original request on to Andy England, Development Control Manager to
+respond independantly.
+
+If I can be of further assistance please contact me
+
+Barry Turnbull
+Environmental Health Co-ordinator (Housing)
+Housing, Health and Community Safety
+
+--
+FOLDED_QUOTED_SECTION
+This footnote confirms that this message, and any
+attachments, have been screened by McAffee
+Webshield for the presence of virus code.
+
+Penwith District Council
+**********************************************************************
diff --git a/spec/fixtures/files/email-folding-example-6.txt b/spec/fixtures/files/email-folding-example-6.txt
new file mode 100644
index 000000000..272d6c9da
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-6.txt
@@ -0,0 +1,30 @@
+Dear Mr. Brown,
+
+Please find attached a reply to your FOI request.
+
+Yours ever,
+
+Adetokunbo Ighodaro
+
+<<FOI 0169-08 final.doc>>
+
+***********************************************************************************
+Visit [1]http://www.fco.gov.uk for British foreign policy news and travel
+advice; and [2]http://www.i-uk.com - the essential guide to the UK.
+
+We keep and use information in line with the Data Protection Act 1998. We
+may release this personal information to other UK government departments
+and public authorities.
+
+Please note that all messages sent and received by members of the Foreign
+& Commonwealth Office and its
+missions overseas may be monitored centrally. This is done to ensure the
+integrity of the system.
+
+***********************************************************************************
+
+References
+
+Visible links
+1. http://www.fco.gov.uk/
+2. http://www.i-uk.com/
diff --git a/spec/fixtures/files/email-folding-example-6.txt.expected b/spec/fixtures/files/email-folding-example-6.txt.expected
new file mode 100644
index 000000000..58021ce12
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-6.txt.expected
@@ -0,0 +1,15 @@
+Dear Mr. Brown,
+
+Please find attached a reply to your FOI request.
+
+Yours ever,
+
+Adetokunbo Ighodaro
+
+<<FOI 0169-08 final.doc>>
+FOLDED_QUOTED_SECTION
+References
+
+Visible links
+1. http://www.fco.gov.uk/
+2. http://www.i-uk.com/ \ No newline at end of file
diff --git a/spec/fixtures/files/email-folding-example-7.txt b/spec/fixtures/files/email-folding-example-7.txt
new file mode 100644
index 000000000..e10fe4657
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-7.txt
@@ -0,0 +1,30 @@
+Mr Hearne,
+Please see attached our response to your request dated 06 March 2008.
+Kind Regards,
+Linda Dempsey
+
+Information Assistant DP/FOI
+Data Protection/Information Security
+Professional Standards
+Leicestershire Constabulary
+http://www.leics.police.uk
+mailto [Leicestershire Constabulary request email]
+Telephone +44 (0) 116 2222222
+Extn 5221 VM No. 8035
+Fax + 44 (0) 116 2485217
+
+<<0001_00035908_Resp_12RESPONSE LETTER_20080408_112311_01.TIF>>
+
+**********
+
+Internet email is not to be treated as a secure means of communication.
+
+Leicestershire Constabulary monitors all internet email activity and content.
+
+This communication is intended for the addressee(s) only. Please notify the sender if received in error. Unauthorised use or disclosure of the content may be unlawful. Opinions expressed in this document may not be official policy.
+
+Thank you for your co-operation.
+
+© Leicestershire Constabulary
+
+**********
diff --git a/spec/fixtures/files/email-folding-example-7.txt.expected b/spec/fixtures/files/email-folding-example-7.txt.expected
new file mode 100644
index 000000000..0ef8fd82b
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-7.txt.expected
@@ -0,0 +1,16 @@
+Mr Hearne,
+Please see attached our response to your request dated 06 March 2008.
+Kind Regards,
+Linda Dempsey
+
+Information Assistant DP/FOI
+Data Protection/Information Security
+Professional Standards
+Leicestershire Constabulary
+http://www.leics.police.uk
+mailto [Leicestershire Constabulary request email]
+Telephone +44 (0) 116 2222222
+Extn 5221 VM No. 8035
+Fax + 44 (0) 116 2485217
+
+<<0001_00035908_Resp_12RESPONSE LETTER_20080408_112311_01.TIF>> \ No newline at end of file
diff --git a/spec/fixtures/files/email-folding-example-8.txt b/spec/fixtures/files/email-folding-example-8.txt
new file mode 100644
index 000000000..c1899e7c8
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-8.txt
@@ -0,0 +1,18 @@
+I will be out of the office starting 11/04/2008 and will not return until
+22/04/2008.
+
+I will respond to your message when I return. If you have any urgent
+queries please ring 02085419088 for Legal Business Support queries or
+contact Eileen Perren for FOI or DP queries
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+This email and any attachments with it are intended for the addressee only.
+It may be confidential and may be the subject of legal and/or professional privilege.
+If you have received this email in error please notify the sender or [email address]
+The content may be personal or contain personal opinions and cannot be taken as an expression of the County Council's position.
+Surrey County Council reserves the right to monitor all incoming and outgoing mail.
+Whilst every care has been taken to check this outgoing e-mail for viruses, it is your responsibility to carry out any checks upon receipt.
+
+Visit the Surrey County Council website - http://www.surreycc.gov.uk
+
+* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
diff --git a/spec/fixtures/files/email-folding-example-8.txt.expected b/spec/fixtures/files/email-folding-example-8.txt.expected
new file mode 100644
index 000000000..b5dc10c0d
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-8.txt.expected
@@ -0,0 +1,6 @@
+I will be out of the office starting 11/04/2008 and will not return until
+22/04/2008.
+
+I will respond to your message when I return. If you have any urgent
+queries please ring 02085419088 for Legal Business Support queries or
+contact Eileen Perren for FOI or DP queries \ No newline at end of file
diff --git a/spec/fixtures/files/email-folding-example-9.txt b/spec/fixtures/files/email-folding-example-9.txt
new file mode 100644
index 000000000..1f3d4c34a
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-9.txt
@@ -0,0 +1,29 @@
+Dear Mr Cross
+
+Freedom of Information Request Reference No: 2008040590
+
+Yours sincerely
+
+MICHAEL HEGARTY
+
+FOI Officer
+
+**********************************************************************************************
+Please Note: Incoming and Outgoing E-mail messages are routinely monitored
+for compliance with our policy on the use of electronic communications.
+
+Interested in Occupational Health & Safety information?
+Please visit the HSE website at the following address to keep yourself up
+to date
+
+www.hse.gov.uk
+
+Or contact HSE Infoline on 0845 345 0055 or email [HSE request email]
+
+**********************************************************************************************
+The original of this email was scanned for viruses by the Government
+Secure Intranet virus scanning service supplied by Cable&Wireless in
+partnership with MessageLabs. (CCTM Certificate Number 2007/11/0032.) On
+leaving the GSi this email was certified virus free.
+Communications via the GSi may be automatically logged, monitored and/or
+recorded for legal purposes.
diff --git a/spec/fixtures/files/email-folding-example-9.txt.expected b/spec/fixtures/files/email-folding-example-9.txt.expected
new file mode 100644
index 000000000..2d2381a34
--- /dev/null
+++ b/spec/fixtures/files/email-folding-example-9.txt.expected
@@ -0,0 +1,9 @@
+Dear Mr Cross
+
+Freedom of Information Request Reference No: 2008040590
+
+Yours sincerely
+
+MICHAEL HEGARTY
+
+FOI Officer
diff --git a/spec/fixtures/files/iso8859_2_email.html b/spec/fixtures/files/iso8859_2_email.html
new file mode 100644
index 000000000..c7384a831
--- /dev/null
+++ b/spec/fixtures/files/iso8859_2_email.html
@@ -0,0 +1,18 @@
+<html>
+<head>
+<style><!--
+.hmmessage P
+{
+margin:0px;
+padding:0px
+}
+body.hmmessage
+{
+font-size: 10pt;
+font-family:Tahoma
+}
+--></style>
+</head>
+<body class='hmmessage'><div dir='ltr'>
+<div>Faleminderit per kerkesen tënde.</div> </div></body>
+</html>
diff --git a/spec/fixtures/files/iso8859_2_raw_email.email b/spec/fixtures/files/iso8859_2_raw_email.email
new file mode 100644
index 000000000..2ac3b2533
--- /dev/null
+++ b/spec/fixtures/files/iso8859_2_raw_email.email
@@ -0,0 +1,50 @@
+From: EMAIL_FROM
+To: FOI Person <EMAIL_TO>
+Bcc:
+Reply-To:
+In-Reply-To: <471f1eae5d1cb_7347..fdbe67386163@cat.tmail>
+Content-Type: multipart/alternative;
+ boundary="_d47fc84f-c9cd-4fb3-ab16-15de158c8eef_"
+Subject: =?iso-8859-2?Q?RE:_Freedo?= =?iso-8859-2?Q?m_of_Infor?=
+ =?iso-8859-2?Q?mation_req?= =?iso-8859-2?Q?uest_-_Sas?=
+ =?iso-8859-2?Q?ia_e_pulav?= =?iso-8859-2?Q?e_t=EB_impor?=
+ =?iso-8859-2?Q?tuara_gjat?= =?iso-8859-2?Q?=EB_vitit_20?= =?iso-8859-2?Q?10?=
+Date: Fri, 30 Sep 2011 11:06:39 +0200
+
+--_d47fc84f-c9cd-4fb3-ab16-15de158c8eef_
+Content-Type: text/plain; charset="iso-8859-2"
+Content-Transfer-Encoding: quoted-printable
+
+
+I nderuari Besnik=2C=20
+Faleminderit per kerkesen t=EBnde.Numri i puleve te importuara ne vitin 201=
+0 ka qene 5 milion e treqind mije sosh (me numra 3=2C500=2C000)
+
+
+--_d47fc84f-c9cd-4fb3-ab16-15de158c8eef_
+Content-Type: text/html; charset="iso-8859-2"
+Content-Transfer-Encoding: quoted-printable
+
+<html>
+<head>
+<style><!--
+.hmmessage P
+{
+margin:0px=3B
+padding:0px
+}
+body.hmmessage
+{
+font-size: 10pt=3B
+font-family:Tahoma
+}
+--></style>
+</head>
+<body class=3D'hmmessage'><div dir=3D'ltr'>
+<div>I nderuari Besnik=2C&nbsp=3B</div><div><br></div><div>Faleminderit per=
+ kerkesen t=EBnde.</div>Numri i puleve te importuara ne vitin 2010 ka qene =
+5 milion e treqind mije sosh (me numra 3=2C500=2C000)<br><br></body>
+</html>=
+
+--_d47fc84f-c9cd-4fb3-ab16-15de158c8eef_--
+
diff --git a/spec/fixtures/files/quoted-subject-iso8859-1.email b/spec/fixtures/files/quoted-subject-iso8859-1.email
new file mode 100644
index 000000000..6ada69905
--- /dev/null
+++ b/spec/fixtures/files/quoted-subject-iso8859-1.email
@@ -0,0 +1,462 @@
+From: =?iso-8859-1?Q?Coordena=E7=E3o_de_Relacionamento=2C_Pesquisa_e_Informa=E7?=
+ =?iso-8859-1?Q?=E3o/CEDI?= <geraldinequango@localhost>
+To: FOI Person <EMAIL_TO>
+MIME-Version: 1.0
+Content-Type: multipart/related;
+ type="multipart/alternative";
+ boundary="----_=_NextPart_001_01CCB66F.F38B15FC"
+Subject: =?iso-8859-1?Q?C=E2mara_Responde=3A__Banco_de_ideias?=
+Date: Fri, 9 Dec 2011 10:42:02 -0200
+
+This is a multi-part message in MIME format.
+
+------_=_NextPart_001_01CCB66F.F38B15FC
+Content-Type: multipart/alternative;
+ boundary="----_=_NextPart_002_01CCB66F.F38B15FC"
+
+
+------_=_NextPart_002_01CCB66F.F38B15FC
+Content-Type: text/plain;
+ charset="iso-8859-1"
+Content-Transfer-Encoding: quoted-printable
+
+=20
+
+Senhor Benedito,
+
+=20
+
+O Centro de Documenta=E7=E3o e Informa=E7=E3o (Cedi) da C=E2mara dos =
+Deputados agradece o seu contato.
+
+=20
+
+Em aten=E7=E3o ao solicitado, informamos que a C=E2mara dos Deputados, =
+por iniciativa da Comiss=E3o de Legisla=E7=E3o Participativa - CLP, =
+criou um "Banco de Id=E9ias" com o objetivo de registrar e reunir =
+id=E9ias de interesse da popula=E7=E3o. As sugest=F5es s=E3o organizadas =
+por temas e ficam =E0s disposi=E7=E3o para consulta de entidades da =
+sociedade civil e parlamentares, que poder=E3o adot=E1-las, =
+aprimorando-as ou n=E3o, para serem transformadas em sugest=E3o de =
+iniciativa legislativa, no caso das entidades da sociedade civil, ou em =
+proposi=E7=E3o legislativa, no caso dos parlamentares. Cabe ressaltar =
+que a Comiss=E3o reserva-se o direito de editar ou resumir os textos =
+recebidos.
+
+A seguir, o endere=E7o eletr=F4nico do Banco de Id=E9ias:=20
+
+=20
+
+http://www2.camara.gov.br/atividade-legislativa/comissoes/comissoes-perma=
+nentes/clp/banideias.htm/banco-de-ideias
+
+=20
+
+Atenciosamente,
+*****************************************************
+Coordena=E7=E3o de Relacionamento, Pesquisa e Informa=E7=E3o - Corpi
+Centro de Documenta=E7=E3o e Informa=E7=E3o - Cedi
+C=E2mara dos Deputados - Anexo II
+Pra=E7a dos Tr=EAs Poderes - Bras=EDlia - DF=20
+70160-900=20
+Tel.: 0-XX-61- 3216-5777; fax: 0-XX-61- 3216-5757=20
+informa.cedi@camara.gov.br <mailto:informa.cedi@camara.gov.br>=20
+*****************************************************
+
+mbb
+
+=20
+
+Solicita=E7=E3o:=20
+
+=20
+
+ Prezado(a) C=E2mara dos Deputados,
+
+ =20
+
+ Gostaria de sugerir que o sal=E1rio de quem trabalha com pol=EDtica
+
+ seja vinculado ao sal=E1rio m=EDnimo.
+
+ =20
+
+ Atenciosamente,
+
+ Benedito P.B.Neto
+
+ =20
+
+ -------------------------------------------------------------------
+
+ =20
+
+ Por favor use esse endere=E7o de email em todas as repostas para =
+este
+
+ pedido:
+
+ leideacesso+request-120-9702221c@queremossaber.org.br
+
+ =20
+
+ Caso este email - informa.cedi@camara.gov.br - seja o endere=E7o
+
+ errado para fazer acesso a informa=E7=E3o por favor nos contate e
+
+ aponte o endere=E7o correto atrav=E9s desse formul=E1rio:
+
+ http://queremossaber.org.br/pt/help/contact
+
+ =20
+
+ Aviso: Esta mensagem e todas as respostas ser=E3o publicadas na
+
+ internet. Leia sobre nossa pol=EDtica de privacidade:
+
+ http://queremossaber.org.br/pt/help/officers
+
+ =20
+
+ Caso voc=EA ache esse servi=E7o =FAtil, por favor entre em contato.
+
+ =20
+
+ =20
+
+ -------------------------------------------------------------------
+
+
+------_=_NextPart_002_01CCB66F.F38B15FC
+Content-Type: text/html;
+ charset="iso-8859-1"
+Content-Transfer-Encoding: quoted-printable
+
+<html xmlns:v=3D"urn:schemas-microsoft-com:vml" =
+xmlns:o=3D"urn:schemas-microsoft-com:office:office" =
+xmlns:w=3D"urn:schemas-microsoft-com:office:word" =
+xmlns:m=3D"http://schemas.microsoft.com/office/2004/12/omml" =
+xmlns=3D"http://www.w3.org/TR/REC-html40"><head><meta =
+http-equiv=3DContent-Type content=3D"text/html; =
+charset=3Diso-8859-1"><meta name=3DGenerator content=3D"Microsoft Word =
+14 (filtered medium)"><!--[if !mso]><style>v\:* =
+{behavior:url(#default#VML);}
+o\:* {behavior:url(#default#VML);}
+w\:* {behavior:url(#default#VML);}
+.shape {behavior:url(#default#VML);}
+</style><![endif]--><style><!--
+/* Font Definitions */
+@font-face
+ {font-family:Calibri;
+ panose-1:2 15 5 2 2 2 4 3 2 4;}
+@font-face
+ {font-family:Tahoma;
+ panose-1:2 11 6 4 3 5 4 4 2 4;}
+/* Style Definitions */
+p.MsoNormal, li.MsoNormal, div.MsoNormal
+ {margin:0cm;
+ margin-bottom:.0001pt;
+ font-size:11.0pt;
+ font-family:"Calibri","sans-serif";
+ mso-fareast-language:EN-US;}
+a:link, span.MsoHyperlink
+ {mso-style-priority:99;
+ color:blue;
+ text-decoration:underline;}
+a:visited, span.MsoHyperlinkFollowed
+ {mso-style-priority:99;
+ color:purple;
+ text-decoration:underline;}
+p.MsoPlainText, li.MsoPlainText, div.MsoPlainText
+ {mso-style-priority:99;
+ mso-style-link:"Texto sem Formata=E7=E3o Char";
+ margin:0cm;
+ margin-bottom:.0001pt;
+ font-size:11.0pt;
+ font-family:"Calibri","sans-serif";
+ mso-fareast-language:EN-US;}
+p.MsoAcetate, li.MsoAcetate, div.MsoAcetate
+ {mso-style-priority:99;
+ mso-style-link:"Texto de bal=E3o Char";
+ margin:0cm;
+ margin-bottom:.0001pt;
+ font-size:8.0pt;
+ font-family:"Tahoma","sans-serif";
+ mso-fareast-language:EN-US;}
+span.TextosemFormataoChar
+ {mso-style-name:"Texto sem Formata=E7=E3o Char";
+ mso-style-priority:99;
+ mso-style-link:"Texto sem Formata=E7=E3o";
+ font-family:"Calibri","sans-serif";}
+span.TextodebaloChar
+ {mso-style-name:"Texto de bal=E3o Char";
+ mso-style-priority:99;
+ mso-style-link:"Texto de bal=E3o";
+ font-family:"Tahoma","sans-serif";}
+.MsoChpDefault
+ {mso-style-type:export-only;
+ font-family:"Calibri","sans-serif";
+ mso-fareast-language:EN-US;}
+@page WordSection1
+ {size:612.0pt 792.0pt;
+ margin:70.85pt 3.0cm 70.85pt 3.0cm;}
+div.WordSection1
+ {page:WordSection1;}
+--></style><!--[if gte mso 9]><xml>
+<o:shapedefaults v:ext=3D"edit" spidmax=3D"1026" />
+</xml><![endif]--><!--[if gte mso 9]><xml>
+<o:shapelayout v:ext=3D"edit">
+<o:idmap v:ext=3D"edit" data=3D"1" />
+</o:shapelayout></xml><![endif]--></head><body lang=3DPT-BR link=3Dblue =
+vlink=3Dpurple><div class=3DWordSection1><p class=3DMsoNormal><span =
+style=3D'mso-fareast-language:PT-BR'><img width=3D566 height=3D58 =
+id=3D"Imagem_x0020_1" src=3D"cid:image001.png@01CCB65F.2FD5C970" =
+alt=3D"Descri=E7=E3o: Logo Corpi_html_1cd70d8a"><o:p></o:p></span></p><p =
+class=3DMsoPlainText> <o:p></o:p></p><p class=3DMsoPlainText>Senhor =
+Benedito,<o:p></o:p></p><p class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoPlainText>O Centro de Documenta=E7=E3o e Informa=E7=E3o =
+(Cedi) da C=E2mara dos Deputados agradece o seu =
+contato.<o:p></o:p></p><p class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoPlainText>Em aten=E7=E3o ao solicitado, informamos que a =
+C=E2mara dos Deputados, por iniciativa da Comiss=E3o de Legisla=E7=E3o =
+Participativa &#8211; CLP, criou um &#8220;Banco de Id=E9ias&#8221; com =
+o objetivo de registrar e reunir id=E9ias de interesse da popula=E7=E3o. =
+As sugest=F5es s=E3o organizadas por temas e ficam =E0s disposi=E7=E3o =
+para consulta de entidades da sociedade civil e parlamentares, que =
+poder=E3o adot=E1-las, aprimorando-as ou n=E3o, para serem transformadas =
+em sugest=E3o de iniciativa legislativa, no caso das entidades da =
+sociedade civil, ou em proposi=E7=E3o legislativa, no caso dos =
+parlamentares. Cabe ressaltar que a Comiss=E3o reserva-se o direito de =
+editar ou resumir os textos recebidos.<o:p></o:p></p><p =
+class=3DMsoPlainText>A seguir, o endere=E7o eletr=F4nico do Banco de =
+Id=E9ias: <o:p></o:p></p><p class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoPlainText>http://www2.camara.gov.br/atividade-legislativa/comi=
+ssoes/comissoes-permanentes/clp/banideias.htm/banco-de-ideias<o:p></o:p><=
+/p><p class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoNormal><span =
+style=3D'font-size:10.0pt;font-family:"Arial","sans-serif";mso-fareast-la=
+nguage:PT-BR'>Atenciosamente,<br>****************************************=
+*************<br>Coordena=E7=E3o de Relacionamento, Pesquisa e =
+Informa=E7=E3o &#8211; Corpi<br>Centro de Documenta=E7=E3o e =
+Informa=E7=E3o &#8211; Cedi<br>C=E2mara dos Deputados &#8211; Anexo =
+II<br>Pra=E7a dos Tr=EAs Poderes &#8211; Bras=EDlia &#8211; DF =
+<br>70160-900 <br>Tel.: 0-XX-61- 3216-5777; fax: 0-XX-61- 3216-5757 =
+<br><a href=3D"mailto:informa.cedi@camara.gov.br"><span =
+style=3D'color:windowtext'>informa.cedi@camara.gov.br</span></a><br>*****=
+************************************************<o:p></o:p></span></p><p =
+class=3DMsoNormal><span =
+style=3D'font-size:8.0pt;font-family:"Arial","sans-serif";mso-fareast-lan=
+guage:PT-BR'>mbb<o:p></o:p></span></p><p =
+class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoPlainText>Solicita=E7=E3o: <o:p></o:p></p><p =
+class=3DMsoPlainText><o:p>&nbsp;</o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 Prezado(a) C=E2mara dos =
+Deputados,<o:p></o:p></p><p class=3DMsoPlainText>=A0=A0=A0=A0 =
+<o:p></o:p></p><p class=3DMsoPlainText>=A0=A0=A0=A0=A0Gostaria de =
+sugerir que o sal=E1rio de quem trabalha com pol=EDtica<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 seja vinculado ao sal=E1rio =
+m=EDnimo.<o:p></o:p></p><p class=3DMsoPlainText>=A0=A0=A0=A0 =
+<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0Atenciosamente,<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 Benedito P.B.Neto<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0-------------------------------------=
+------------------------------<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0Por favor use esse endere=E7o de =
+email em todas as repostas para este<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 pedido:<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 =
+leideacesso+request-120-9702221c@queremossaber.org.br<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0Caso este email - =
+informa.cedi@camara.gov.br - seja o endere=E7o<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 errado para fazer acesso a =
+informa=E7=E3o por favor nos contate e<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 aponte o endere=E7o correto atrav=E9s =
+desse formul=E1rio:<o:p></o:p></p><p class=3DMsoPlainText>=A0=A0=A0=A0 =
+http://queremossaber.org.br/pt/help/contact<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0Aviso: Esta mensagem e todas as =
+respostas ser=E3o publicadas na<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 internet. Leia sobre nossa pol=EDtica =
+de privacidade:<o:p></o:p></p><p class=3DMsoPlainText>=A0=A0=A0=A0 =
+http://queremossaber.org.br/pt/help/officers<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0Caso voc=EA ache esse servi=E7o =
+=FAtil, por favor entre em contato.<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0 <o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0<o:p></o:p></p><p =
+class=3DMsoPlainText>=A0=A0=A0=A0=A0-------------------------------------=
+------------------------------<o:p></o:p></p></div></body></html>
+------_=_NextPart_002_01CCB66F.F38B15FC--
+
+------_=_NextPart_001_01CCB66F.F38B15FC
+Content-Type: image/png;
+ name="image001.png"
+Content-Transfer-Encoding: base64
+Content-ID: <image001.png@01CCB65F.2FD5C970>
+Content-Description: image001.png
+Content-Location: image001.png
+
+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
+SEhISIxR/heHXcIrMvkS1gAAAABJRU5ErkJggg==
+
+------_=_NextPart_001_01CCB66F.F38B15FC-- \ No newline at end of file
diff --git a/spec/fixtures/files/track-response-abcmail-oof.email b/spec/fixtures/files/track-response-abcmail-oof.email
new file mode 100644
index 000000000..5d1733143
--- /dev/null
+++ b/spec/fixtures/files/track-response-abcmail-oof.email
@@ -0,0 +1,80 @@
+Delivered-To: mysociety.robin@gmail.com
+Received: by 10.216.154.212 with SMTP id h62cs265517wek;
+ Fri, 30 Dec 2011 02:03:17 -0800 (PST)
+Received: by 10.227.208.129 with SMTP id gc1mr47630338wbb.4.1325239396543;
+ Fri, 30 Dec 2011 02:03:16 -0800 (PST)
+Return-Path: <Name.Removed@example.gov.uk>
+Received: from wildfire.ukcod.org.uk (wildfire.ukcod.org.uk. [89.238.145.74])
+ by mx.google.com with ESMTPS id ei10si9596065wbb.20.2011.12.30.02.03.16
+ (version=TLSv1/SSLv3 cipher=OTHER);
+ Fri, 30 Dec 2011 02:03:16 -0800 (PST)
+Received-SPF: neutral (google.com: 89.238.145.74 is neither permitted nor denied by best guess record for domain of Name.Removed@example.gov.uk) client-ip=89.238.145.74;
+Authentication-Results: mx.google.com; spf=neutral (google.com: 89.238.145.74 is neither permitted nor denied by best guess record for domain of Name.Removed@example.gov.uk) smtp.mail=Name.Removed@example.gov.uk
+Received: from foi by wildfire.ukcod.org.uk with local (Exim 4.72)
+ (envelope-from <Name.Removed@example.gov.uk>)
+ id 1RgZIs-0000ME-1T
+ for team_delivery@whatdotheyknow.com; Fri, 30 Dec 2011 10:03:10 +0000
+Received: from truro.icritical.com ([93.95.13.13]:51540)
+ by wildfire.ukcod.org.uk with smtp (Exim 4.72)
+ (envelope-from <Name.Removed@example.gov.uk>)
+ id 1RgZIq-0000M6-St
+ for track@whatdotheyknow.com; Fri, 30 Dec 2011 10:03:09 +0000
+Received: (qmail 19136 invoked from network); 30 Dec 2011 10:03:08 -0000
+Received: from localhost (127.0.0.1)
+ by truro.icritical.com with SMTP; 30 Dec 2011 10:03:08 -0000
+Received: from truro.icritical.com ([127.0.0.1])
+ by localhost (truro.icritical.com [127.0.0.1]) (amavisd-new, port 10024)
+ with SMTP id 19122-01 for <track@whatdotheyknow.com>;
+ Fri, 30 Dec 2011 10:03:07 +0000 (GMT)
+Received: (qmail 19112 invoked by uid 599); 30 Dec 2011 10:03:06 -0000
+Received: from unknown (HELO abcmail.example.gov.uk) (213.185.212.82)
+ by truro.icritical.com (qpsmtpd/0.28) with ESMTP; Fri, 30 Dec 2011 10:03:06 +0000
+Subject: AUTO: Name Removed is out of the office (returning 03/01/2012)
+Auto-Submitted: auto-generated
+From: Name.Removed@example.gov.uk
+To: track@whatdotheyknow.com
+Message-ID: <OFF4E36F18.ED02EFA3-ON80257976.00373794-80257976.00373794@example.gov.uk>
+Date: Fri, 30 Dec 2011 10:03:07 +0000
+X-MIMETrack: Serialize by Router on ABCMail/SVR/ABC(Release 8.5.2FP1|November 29, 2010) at
+ 30/12/2011 10:03:07
+MIME-Version: 1.0
+Content-type: text/plain; charset=US-ASCII
+X-Virus-Scanned: by iCritical at truro.icritical.com
+
+
+I am out of the office until 03/01/2012.
+
+I will be out of the office until 3rd January December 2012. I will deal
+with all emails upon my return. If your query is urgent please contact
+Colleague Name on colleague.name@example.gov.uk or 01234 567890.
+
+If you are requesting information under the Freedom of Information Act, the
+Environmental Information Regulations or the Data Protection Act, please
+forward your enquiry to colleague.name@example.gov.uk The Council
+will begin processing your request once it is received by that address.
+
+
+Thanks
+
+Name
+
+
+
+
+
+Note: This is an automated response to your message "Your WhatDoTheyKnow
+email alert" sent on 30/12/2011 06:54:19.
+
+This is the only notification you will receive while this person is away.
+
+
+This e-mail and any files transmitted with it are confidential and
+intended solely for the use of the individual or entity to whom
+they are addressed.
+If you have received this e-mail in error please notify the
+originator of the message. This footer also confirms that this
+e-mail message has been scanned for the presence of computer viruses.
+
+Any views expressed in this message are those of the individual
+sender, except where the sender specifies and with authority,
+states them to be the views of Organisation Name.
diff --git a/spec/fixtures/files/track-response-outlook-oof.email b/spec/fixtures/files/track-response-outlook-oof.email
new file mode 100644
index 000000000..ee5a28b15
--- /dev/null
+++ b/spec/fixtures/files/track-response-outlook-oof.email
@@ -0,0 +1,587 @@
+Delivered-To: mysociety.robin@gmail.com
+Received: by 10.152.24.138 with SMTP id u10cs341636laf;
+ Thu, 8 Dec 2011 02:39:53 -0800 (PST)
+Received: by 10.180.103.131 with SMTP id fw3mr4246912wib.57.1323340792168;
+ Thu, 08 Dec 2011 02:39:52 -0800 (PST)
+Return-Path: <peter@kentadvice.co.uk>
+Received: from wildfire.ukcod.org.uk (wildfire.ukcod.org.uk. [89.238.145.74])
+ by mx.google.com with ESMTPS id ft12si3357577wbb.14.2011.12.08.02.39.51
+ (version=TLSv1/SSLv3 cipher=OTHER);
+ Thu, 08 Dec 2011 02:39:52 -0800 (PST)
+Received-SPF: neutral (google.com: 89.238.145.74 is neither permitted nor denied by best guess record for domain of peter@kentadvice.co.uk) client-ip=89.238.145.74;
+Authentication-Results: mx.google.com; spf=neutral (google.com: 89.238.145.74 is neither permitted nor denied by best guess record for domain of peter@kentadvice.co.uk) smtp.mail=peter@kentadvice.co.uk
+Received: from foi by wildfire.ukcod.org.uk with local (Exim 4.72)
+ (envelope-from <peter@kentadvice.co.uk>)
+ id 1RYbOC-00034X-Vm
+ for team_delivery@whatdotheyknow.com; Thu, 08 Dec 2011 10:39:45 +0000
+Received: from mail-ey0-f173.google.com ([209.85.215.173]:38997)
+ by wildfire.ukcod.org.uk with esmtp (Exim 4.72)
+ (envelope-from <peter@kentadvice.co.uk>)
+ id 1RYbOC-00034L-GF
+ for track@whatdotheyknow.com; Thu, 08 Dec 2011 10:39:44 +0000
+Received: by eaai10 with SMTP id i10so1168752eaa.32
+ for <track@whatdotheyknow.com>; Thu, 08 Dec 2011 02:39:33 -0800 (PST)
+Received: by 10.213.21.148 with SMTP id j20mr131258ebb.87.1323340773446;
+ Thu, 08 Dec 2011 02:39:33 -0800 (PST)
+Received: from PRWin7 (cpc2-tilb7-2-0-cust982.basl.cable.virginmedia.com. [94.168.103.215])
+ by mx.google.com with ESMTPS id 49sm16411187eec.1.2011.12.08.02.39.31
+ (version=TLSv1/SSLv3 cipher=OTHER);
+ Thu, 08 Dec 2011 02:39:32 -0800 (PST)
+From: "Name Removed" <name-removed@example.co.uk>
+To: <track@whatdotheyknow.com>
+Subject: Out of Office reply
+Date: Thu, 8 Dec 2011 10:39:24 -0000
+Message-ID: <00ab01ccb595$aada0070$008e0150$@co.uk>
+MIME-Version: 1.0
+Content-Type: multipart/alternative;
+ boundary="----=_NextPart_000_00AC_01CCB595.AADA0070"
+X-Mailer: Microsoft Office Outlook 12.0
+Thread-Index: Acy1laTpNPAp9QuHRu2X59T70yzpQw==
+Content-Language: en-gb
+
+This is a multi-part message in MIME format.
+
+------=_NextPart_000_00AC_01CCB595.AADA0070
+Content-Type: text/plain;
+ charset="US-ASCII"
+Content-Transfer-Encoding: 7bit
+
+Thank you for your message. I am currently out of the office, with [limited]
+[no] access to e-mail.
+
+I will be returning on [day, date].
+
+If you need assistance before then, you may reach me at [phone number].
+For urgent issues, please contact [name] at [e-mail address] or [telephone
+number].
+
+[Signature]
+
+[Optional: Type your favorite quotation or saying here along with the author
+or source]
+
+------=_NextPart_000_00AC_01CCB595.AADA0070
+Content-Type: text/html;
+ charset="US-ASCII"
+Content-Transfer-Encoding: quoted-printable
+
+<html xmlns:v=3D"urn:schemas-microsoft-com:vml" =
+xmlns:o=3D"urn:schemas-microsoft-com:office:office" =
+xmlns:w=3D"urn:schemas-microsoft-com:office:word" =
+xmlns:x=3D"urn:schemas-microsoft-com:office:excel" =
+xmlns:p=3D"urn:schemas-microsoft-com:office:powerpoint" =
+xmlns:a=3D"urn:schemas-microsoft-com:office:access" =
+xmlns:dt=3D"uuid:C2F41010-65B3-11d1-A29F-00AA00C14882" =
+xmlns:s=3D"uuid:BDC6E3F0-6DA3-11d1-A2A3-00AA00C14882" =
+xmlns:rs=3D"urn:schemas-microsoft-com:rowset" xmlns:z=3D"#RowsetSchema" =
+xmlns:b=3D"urn:schemas-microsoft-com:office:publisher" =
+xmlns:ss=3D"urn:schemas-microsoft-com:office:spreadsheet" =
+xmlns:c=3D"urn:schemas-microsoft-com:office:component:spreadsheet" =
+xmlns:oa=3D"urn:schemas-microsoft-com:office:activation" =
+xmlns:html=3D"http://www.w3.org/TR/REC-html40" =
+xmlns:q=3D"http://schemas.xmlsoap.org/soap/envelope/" xmlns:D=3D"DAV:" =
+xmlns:x2=3D"http://schemas.microsoft.com/office/excel/2003/xml" =
+xmlns:ois=3D"http://schemas.microsoft.com/sharepoint/soap/ois/" =
+xmlns:dir=3D"http://schemas.microsoft.com/sharepoint/soap/directory/" =
+xmlns:ds=3D"http://www.w3.org/2000/09/xmldsig#" =
+xmlns:dsp=3D"http://schemas.microsoft.com/sharepoint/dsp" =
+xmlns:udc=3D"http://schemas.microsoft.com/data/udc" =
+xmlns:xsd=3D"http://www.w3.org/2001/XMLSchema" =
+xmlns:sub=3D"http://schemas.microsoft.com/sharepoint/soap/2002/1/alerts/"=
+ xmlns:ec=3D"http://www.w3.org/2001/04/xmlenc#" =
+xmlns:sp=3D"http://schemas.microsoft.com/sharepoint/" =
+xmlns:sps=3D"http://schemas.microsoft.com/sharepoint/soap/" =
+xmlns:xsi=3D"http://www.w3.org/2001/XMLSchema-instance" =
+xmlns:udcxf=3D"http://schemas.microsoft.com/data/udc/xmlfile" =
+xmlns:wf=3D"http://schemas.microsoft.com/sharepoint/soap/workflow/" =
+xmlns:mver=3D"http://schemas.openxmlformats.org/markup-compatibility/2006=
+" xmlns:m=3D"http://schemas.microsoft.com/office/2004/12/omml" =
+xmlns:mrels=3D"http://schemas.openxmlformats.org/package/2006/relationshi=
+ps" =
+xmlns:ex12t=3D"http://schemas.microsoft.com/exchange/services/2006/types"=
+ =
+xmlns:ex12m=3D"http://schemas.microsoft.com/exchange/services/2006/messag=
+es" xmlns=3D"http://www.w3.org/TR/REC-html40">
+
+<head>
+<META HTTP-EQUIV=3D"Content-Type" CONTENT=3D"text/html; =
+charset=3Dus-ascii">
+
+
+<meta name=3DProgId content=3DWord.Document>
+<meta name=3DGenerator content=3D"Microsoft Word 12">
+<meta name=3DOriginator content=3D"Microsoft Word 12">
+<link rel=3DFile-List href=3D"cid:filelist.xml@01C895B2.35BC4F70">
+<!--[if gte mso 9]><xml>
+ <o:OfficeDocumentSettings>
+ <o:AllowPNG/>
+ <o:TargetScreenSize>1024x768</o:TargetScreenSize>
+ </o:OfficeDocumentSettings>
+</xml><![endif]-->
+<link rel=3DthemeData href=3D"~~themedata~~">
+<link rel=3DcolorSchemeMapping href=3D"~~colorschememapping~~">
+<!--[if gte mso 9]><xml>
+ <w:WordDocument>
+ <w:SpellingState>Clean</w:SpellingState>
+ <w:TrackMoves/>
+ <w:TrackFormatting/>
+ <w:EnvelopeVis/>
+ <w:ValidateAgainstSchemas/>
+ <w:SaveIfXMLInvalid>false</w:SaveIfXMLInvalid>
+ <w:IgnoreMixedContent>false</w:IgnoreMixedContent>
+ <w:AlwaysShowPlaceholderText>false</w:AlwaysShowPlaceholderText>
+ <w:DoNotPromoteQF/>
+ <w:LidThemeOther>EN-US</w:LidThemeOther>
+ <w:LidThemeAsian>X-NONE</w:LidThemeAsian>
+ <w:LidThemeComplexScript>X-NONE</w:LidThemeComplexScript>
+ <w:Compatibility>
+ <w:DoNotExpandShiftReturn/>
+ <w:BreakWrappedTables/>
+ <w:SnapToGridInCell/>
+ <w:WrapTextWithPunct/>
+ <w:UseAsianBreakRules/>
+ <w:DontGrowAutofit/>
+ <w:SplitPgBreakAndParaMark/>
+ <w:DontVertAlignCellWithSp/>
+ <w:DontBreakConstrainedForcedTables/>
+ <w:DontVertAlignInTxbx/>
+ <w:Word11KerningPairs/>
+ <w:CachedColBalance/>
+ </w:Compatibility>
+ <w:BrowserLevel>MicrosoftInternetExplorer4</w:BrowserLevel>
+ <m:mathPr>
+ <m:mathFont m:val=3D"Cambria Math"/>
+ <m:brkBin m:val=3D"before"/>
+ <m:brkBinSub m:val=3D"&#45;-"/>
+ <m:smallFrac m:val=3D"off"/>
+ <m:dispDef/>
+ <m:lMargin m:val=3D"0"/>
+ <m:rMargin m:val=3D"0"/>
+ <m:defJc m:val=3D"centerGroup"/>
+ <m:wrapIndent m:val=3D"1440"/>
+ <m:intLim m:val=3D"subSup"/>
+ <m:naryLim m:val=3D"undOvr"/>
+ </m:mathPr></w:WordDocument>
+</xml><![endif]--><!--[if gte mso 9]><xml>
+ <w:LatentStyles DefLockedState=3D"false" DefUnhideWhenUsed=3D"true"=20
+ DefSemiHidden=3D"true" DefQFormat=3D"false" DefPriority=3D"99"=20
+ LatentStyleCount=3D"267">
+ <w:LsdException Locked=3D"false" Priority=3D"0" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Normal"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"heading 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 7"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 8"/>
+ <w:LsdException Locked=3D"false" Priority=3D"9" QFormat=3D"true" =
+Name=3D"heading 9"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 7"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 8"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" Name=3D"toc 9"/>
+ <w:LsdException Locked=3D"false" Priority=3D"35" QFormat=3D"true" =
+Name=3D"caption"/>
+ <w:LsdException Locked=3D"false" Priority=3D"10" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Title"/>
+ <w:LsdException Locked=3D"false" Priority=3D"1" Name=3D"Default =
+Paragraph Font"/>
+ <w:LsdException Locked=3D"false" Priority=3D"11" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Subtitle"/>
+ <w:LsdException Locked=3D"false" Priority=3D"22" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Strong"/>
+ <w:LsdException Locked=3D"false" Priority=3D"20" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Emphasis"/>
+ <w:LsdException Locked=3D"false" Priority=3D"59" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Table Grid"/>
+ <w:LsdException Locked=3D"false" UnhideWhenUsed=3D"false" =
+Name=3D"Placeholder Text"/>
+ <w:LsdException Locked=3D"false" Priority=3D"1" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"No Spacing"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 1"/>
+ <w:LsdException Locked=3D"false" UnhideWhenUsed=3D"false" =
+Name=3D"Revision"/>
+ <w:LsdException Locked=3D"false" Priority=3D"34" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"List Paragraph"/>
+ <w:LsdException Locked=3D"false" Priority=3D"29" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Quote"/>
+ <w:LsdException Locked=3D"false" Priority=3D"30" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Intense Quote"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 1"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 2"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 3"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 4"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 5"/>
+ <w:LsdException Locked=3D"false" Priority=3D"60" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Shading Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"61" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light List Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"62" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Light Grid Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"63" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 1 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"64" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Shading 2 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"65" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 1 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"66" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium List 2 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"67" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 1 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"68" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 2 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"69" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Medium Grid 3 Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"70" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Dark List Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"71" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Shading Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"72" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful List Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"73" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" Name=3D"Colorful Grid Accent 6"/>
+ <w:LsdException Locked=3D"false" Priority=3D"19" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Subtle Emphasis"/>
+ <w:LsdException Locked=3D"false" Priority=3D"21" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Intense Emphasis"/>
+ <w:LsdException Locked=3D"false" Priority=3D"31" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Subtle Reference"/>
+ <w:LsdException Locked=3D"false" Priority=3D"32" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Intense =
+Reference"/>
+ <w:LsdException Locked=3D"false" Priority=3D"33" SemiHidden=3D"false"=20
+ UnhideWhenUsed=3D"false" QFormat=3D"true" Name=3D"Book Title"/>
+ <w:LsdException Locked=3D"false" Priority=3D"37" =
+Name=3D"Bibliography"/>
+ <w:LsdException Locked=3D"false" Priority=3D"39" QFormat=3D"true" =
+Name=3D"TOC Heading"/>
+ </w:LatentStyles>
+</xml><![endif]-->
+<style>
+<!--
+ /* Font Definitions */
+ @font-face
+ {font-family:"Cambria Math";
+ panose-1:2 4 5 3 5 4 6 3 2 4;
+ mso-font-charset:1;
+ mso-generic-font-family:roman;
+ mso-font-format:other;
+ mso-font-pitch:variable;
+ mso-font-signature:0 0 0 0 0 0;}
+@font-face
+ {font-family:Calibri;
+ panose-1:2 15 5 2 2 2 4 3 2 4;
+ mso-font-charset:0;
+ mso-generic-font-family:swiss;
+ mso-font-pitch:variable;
+ mso-font-signature:-1610611985 1073750139 0 0 159 0;}
+ /* Style Definitions */
+ p.MsoNormal, li.MsoNormal, div.MsoNormal
+ {mso-style-unhide:no;
+ mso-style-qformat:yes;
+ mso-style-parent:"";
+ margin:0in;
+ margin-bottom:.0001pt;
+ mso-pagination:widow-orphan;
+ font-size:11.0pt;
+ font-family:"Calibri","sans-serif";
+ mso-fareast-font-family:Calibri;
+ mso-fareast-theme-font:minor-latin;
+ mso-bidi-font-family:"Times New Roman";}
+a:link, span.MsoHyperlink
+ {mso-style-noshow:yes;
+ mso-style-priority:99;
+ color:blue;
+ text-decoration:underline;
+ text-underline:single;}
+a:visited, span.MsoHyperlinkFollowed
+ {mso-style-noshow:yes;
+ mso-style-priority:99;
+ color:purple;
+ text-decoration:underline;
+ text-underline:single;}
+span.EmailStyle17
+ {mso-style-type:personal;
+ mso-style-noshow:yes;
+ mso-style-unhide:no;
+ font-family:"Calibri","sans-serif";
+ mso-ascii-font-family:Calibri;
+ mso-hansi-font-family:Calibri;
+ color:windowtext;}
+span.EmailStyle18
+ {mso-style-type:personal-reply;
+ mso-style-noshow:yes;
+ mso-style-unhide:no;
+ mso-ansi-font-size:11.0pt;
+ mso-bidi-font-size:11.0pt;
+ font-family:"Calibri","sans-serif";
+ mso-ascii-font-family:Calibri;
+ mso-ascii-theme-font:minor-latin;
+ mso-hansi-font-family:Calibri;
+ mso-hansi-theme-font:minor-latin;
+ mso-bidi-font-family:"Times New Roman";
+ mso-bidi-theme-font:minor-bidi;
+ color:#5F497A;
+ mso-themecolor:accent4;
+ mso-themeshade:191;}
+.MsoChpDefault
+ {mso-style-type:export-only;
+ mso-default-props:yes;
+ font-size:10.0pt;
+ mso-ansi-font-size:10.0pt;
+ mso-bidi-font-size:10.0pt;}
+@page Section1
+ {size:8.5in 11.0in;
+ margin:1.0in 1.0in 1.0in 1.0in;
+ mso-header-margin:.5in;
+ mso-footer-margin:.5in;
+ mso-paper-source:0;}
+div.Section1
+ {page:Section1;}
+-->
+</style>
+<!--[if gte mso 10]>
+<style>
+ /* Style Definitions */=20
+ table.MsoNormalTable
+ {mso-style-name:"Table Normal";
+ mso-tstyle-rowband-size:0;
+ mso-tstyle-colband-size:0;
+ mso-style-noshow:yes;
+ mso-style-priority:99;
+ mso-style-qformat:yes;
+ mso-style-parent:"";
+ mso-padding-alt:0in 5.4pt 0in 5.4pt;
+ mso-para-margin:0in;
+ mso-para-margin-bottom:.0001pt;
+ mso-pagination:widow-orphan;
+ font-size:10.0pt;
+ font-family:"Times New Roman","serif";}
+</style>
+<![endif]--><!--[if gte mso 9]><xml>
+ <o:shapedefaults v:ext=3D"edit" spidmax=3D"1026" />
+</xml><![endif]--><!--[if gte mso 9]><xml>
+ <o:shapelayout v:ext=3D"edit">
+ <o:idmap v:ext=3D"edit" data=3D"1" />
+ </o:shapelayout></xml><![endif]-->
+</head>
+
+<body lang=3DEN-US link=3Dblue vlink=3Dpurple =
+style=3D'tab-interval:.5in'>
+
+<div class=3DSection1>
+
+<p class=3DMsoNormal>Thank you for your message. I am currently out of =
+the
+office, with [limited] [no] access to e-mail.<o:p></o:p></p>
+
+<p class=3DMsoNormal><o:p>&nbsp;</o:p></p>
+
+<p class=3DMsoNormal>I will be returning on [day, date].<o:p></o:p></p>
+
+<p class=3DMsoNormal><o:p>&nbsp;</o:p></p>
+
+<p class=3DMsoNormal>If you need assistance before then, you may reach =
+me at
+[phone number].<o:p></o:p></p>
+
+<p class=3DMsoNormal>For urgent issues, please contact [name] at [e-mail =
+address]
+or [telephone number].<o:p></o:p></p>
+
+<p class=3DMsoNormal><o:p>&nbsp;</o:p></p>
+
+<p class=3DMsoNormal>[Signature]<o:p></o:p></p>
+
+<p class=3DMsoNormal><o:p>&nbsp;</o:p></p>
+
+<p class=3DMsoNormal><i style=3D'mso-bidi-font-style:normal'>[Optional: =
+Type your
+favorite quotation or saying here along with the author or =
+source]<o:p></o:p></i></p>
+
+</div>
+
+</body>
+
+</html>
+
+------=_NextPart_000_00AC_01CCB595.AADA0070--
+
diff --git a/spec/fixtures/foi_attachments.yml b/spec/fixtures/foi_attachments.yml
new file mode 100644
index 000000000..8b1378917
--- /dev/null
+++ b/spec/fixtures/foi_attachments.yml
@@ -0,0 +1 @@
+
diff --git a/spec/integration/errors_spec.rb b/spec/integration/errors_spec.rb
index c64ca79e8..bfb7e5fb5 100644
--- a/spec/integration/errors_spec.rb
+++ b/spec/integration/errors_spec.rb
@@ -2,15 +2,19 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe "When rendering errors" do
- fixtures [ :info_requests,
- :info_request_events,
- :public_bodies,
- :public_body_translations,
- :users,
- :raw_emails,
- :outgoing_messages,
- :incoming_messages,
- :comments ]
+ fixtures [
+ :users,
+ :public_bodies,
+ :public_body_translations,
+ :public_body_versions,
+ :info_requests,
+ :raw_emails,
+ :outgoing_messages,
+ :incoming_messages,
+ :comments,
+ :info_request_events,
+ :track_things,
+ ]
before(:each) do
load_raw_emails_data(raw_emails)
diff --git a/spec/integration/search_request_spec.rb b/spec/integration/search_request_spec.rb
index dcd20c7bd..07839af32 100644
--- a/spec/integration/search_request_spec.rb
+++ b/spec/integration/search_request_spec.rb
@@ -2,15 +2,19 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe "When searching" do
- fixtures [ :info_requests,
- :info_request_events,
- :public_bodies,
- :public_body_translations,
- :users,
- :raw_emails,
- :outgoing_messages,
- :incoming_messages,
- :comments ]
+ fixtures [
+ :users,
+ :public_bodies,
+ :public_body_translations,
+ :public_body_versions,
+ :info_requests,
+ :raw_emails,
+ :outgoing_messages,
+ :incoming_messages,
+ :comments,
+ :info_request_events,
+ :track_things,
+ ]
before(:each) do
emails = raw_emails.clone
diff --git a/spec/integration/view_request_spec.rb b/spec/integration/view_request_spec.rb
new file mode 100644
index 000000000..cf1e4ca6c
--- /dev/null
+++ b/spec/integration/view_request_spec.rb
@@ -0,0 +1,32 @@
+require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
+
+describe "When viewing requests" do
+
+ fixtures [
+ :users,
+ :public_bodies,
+ :public_body_translations,
+ :public_body_versions,
+ :info_requests,
+ :raw_emails,
+ :outgoing_messages,
+ :incoming_messages,
+ :comments,
+ :info_request_events,
+ :track_things,
+ ]
+
+ before(:each) do
+ emails = raw_emails.clone
+ load_raw_emails_data(emails)
+ end
+
+ it "should not make endlessly recursive JSON <link>s" do
+ @dog_request = info_requests(:fancy_dog_request)
+ get "request/#{@dog_request.url_title}?unfold=1"
+ response.body.should_not include("dog?unfold=1.json")
+ response.body.should include("dog.json?unfold=1")
+ end
+
+end
+
diff --git a/spec/lib/tmail_extensions_spec.rb b/spec/lib/tmail_extensions_spec.rb
index c647fe522..6a55c34da 100644
--- a/spec/lib/tmail_extensions_spec.rb
+++ b/spec/lib/tmail_extensions_spec.rb
@@ -1,3 +1,4 @@
+# coding: utf-8
# This is a test of the set_content_type monkey patch in
# lib/tmail_extensions.rb
@@ -27,5 +28,14 @@ describe "when using TMail" do
mail.to.should == ["request-66666-caa77777@whatdotheyknow.com", "foi@example.com"]
end
+ it 'should convert to utf8' do
+ # NB this isn't actually a TMail extension, but is core TMail;
+ # this was just a convenient place to assert the UTF8
+ # conversion is working
+ mail = TMail::Mail.parse(load_file_fixture('iso8859_2_raw_email.email'))
+ mail.subject.should have_text(/gjatë/u)
+ mail.body.is_utf8?.should == true
+ end
+
end
diff --git a/spec/lib/whatdotheyknow/strip_empty_sessions_spec.rb b/spec/lib/whatdotheyknow/strip_empty_sessions_spec.rb
index 1cf5e3d25..9bd5ccb93 100644
--- a/spec/lib/whatdotheyknow/strip_empty_sessions_spec.rb
+++ b/spec/lib/whatdotheyknow/strip_empty_sessions_spec.rb
@@ -1,4 +1,4 @@
-require 'spec_helper'
+require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
describe WhatDoTheyKnow::StripEmptySessions do
def make_response(session_data, response_headers)
diff --git a/spec/models/has_tag_string_tag_spec.rb b/spec/models/has_tag_string_tag_spec.rb
index ba439acb8..1acd2e27d 100644
--- a/spec/models/has_tag_string_tag_spec.rb
+++ b/spec/models/has_tag_string_tag_spec.rb
@@ -1,7 +1,7 @@
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe HasTagString::HasTagStringTag, " when fiddling with tag strings " do
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should be able to make a new tag and save it" do
@tag = HasTagString::HasTagStringTag.new
diff --git a/spec/models/incoming_message_spec.rb b/spec/models/incoming_message_spec.rb
index d6923da21..08d3d89f7 100644
--- a/spec/models/incoming_message_spec.rb
+++ b/spec/models/incoming_message_spec.rb
@@ -1,13 +1,18 @@
+# coding: utf-8
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe IncomingMessage, " when dealing with incoming mail" do
- fixtures :incoming_messages, :raw_emails, :info_requests
+ fixtures :users, :raw_emails, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
@im = incoming_messages(:useless_incoming_message)
load_raw_emails_data(raw_emails)
end
+ after(:all) do
+ ActionMailer::Base.deliveries.clear
+ end
+
it "should return the mail Date header date for sent at" do
@im.sent_at.should == @im.mail.date
end
@@ -17,6 +22,45 @@ describe IncomingMessage, " when dealing with incoming mail" do
TMail::Address.parse(em)
end
+ it "should correctly fold various types of footer" do
+ Dir.glob(File.join(Spec::Runner.configuration.fixture_path, "files", "email-folding-example-*.txt")).each do |file|
+ message = File.read(file)
+ parsed = IncomingMessage.remove_quoted_sections(message)
+ expected = File.read("#{file}.expected")
+ parsed.should include(expected)
+ end
+ end
+
+ it "should correctly convert HTML even when there's a meta tag asserting that it is iso-8859-1 which would normally confuse elinks" do
+ ir = info_requests(:fancy_dog_request)
+ receive_incoming_mail('quoted-subject-iso8859-1.email', ir.incoming_email)
+ message = ir.incoming_messages[1]
+ message.parse_raw_email!
+ message.get_main_body_text_part.charset.should == "iso-8859-1"
+ message.get_main_body_text_internal.should include("política")
+ end
+
+ it "should unquote RFC 2047 headers" do
+ ir = info_requests(:fancy_dog_request)
+ receive_incoming_mail('quoted-subject-iso8859-1.email', ir.incoming_email)
+ message = ir.incoming_messages[1]
+ message.mail_from.should == "Coordenação de Relacionamento, Pesquisa e Informação/CEDI"
+ message.subject.should == "Câmara Responde: Banco de ideias"
+ end
+
+
+ it "should fold multiline sections" do
+ {
+ "foo\n--------\nconfidential" => "foo\nFOLDED_QUOTED_SECTION\n", # basic test
+ "foo\n--------\nbar - confidential" => "foo\nFOLDED_QUOTED_SECTION\n", # allow scorechar inside folded section
+ "foo\n--------\nbar\n--------\nconfidential" => "foo\n--------\nbar\nFOLDED_QUOTED_SECTION\n", # don't assume that anything after a score is a folded section
+ "foo\n--------\nbar\n--------\nconfidential\n--------\nrest" => "foo\n--------\nbar\nFOLDED_QUOTED_SECTION\nrest", # don't assume that a folded section continues to the end of the message
+ "foo\n--------\nbar\n- - - - - - - -\nconfidential\n--------\nrest" => "foo\n--------\nbar\nFOLDED_QUOTED_SECTION\nrest", # allow spaces in the score
+ }.each do |input,output|
+ IncomingMessage.remove_quoted_sections(input).should == output
+ end
+ end
+
end
describe IncomingMessage, "when parsing HTML mail" do
@@ -42,7 +86,7 @@ end
describe IncomingMessage, " display attachments" do
it "should not show slashes in filenames" do
- foi_attachment = FOIAttachment.new()
+ foi_attachment = FoiAttachment.new()
# http://www.whatdotheyknow.com/request/post_commercial_manager_librarie#incoming-17233
foi_attachment.filename = "FOI/09/066 RESPONSE TO FOI REQUEST RECEIVED 21st JANUARY 2009.txt"
expected_display_filename = foi_attachment.filename.gsub(/\//, " ")
@@ -50,10 +94,11 @@ describe IncomingMessage, " display attachments" do
end
it "should not show slashes in subject generated filenames" do
- foi_attachment = FOIAttachment.new()
+ foi_attachment = FoiAttachment.new()
# http://www.whatdotheyknow.com/request/post_commercial_manager_librarie#incoming-17233
foi_attachment.within_rfc822_subject = "FOI/09/066 RESPONSE TO FOI REQUEST RECEIVED 21st JANUARY 2009"
foi_attachment.content_type = 'text/plain'
+ foi_attachment.ensure_filename!
expected_display_filename = foi_attachment.within_rfc822_subject.gsub(/\//, " ") + ".txt"
foi_attachment.display_filename.should == expected_display_filename
end
@@ -79,16 +124,15 @@ describe IncomingMessage, " folding quoted parts of emails" do
end
describe IncomingMessage, " checking validity to reply to" do
- def test_email(result, email, return_path, autosubmitted)
+ def test_email(result, email, return_path, autosubmitted = nil)
@address = mock(TMail::Address)
@address.stub!(:spec).and_return(email)
@return_path = mock(TMail::ReturnPathHeader)
@return_path.stub!(:addr).and_return(return_path)
-
- @autosubmitted = mock(TMail::KeywordsHeader)
- @autosubmitted.stub!(:keys).and_return(autosubmitted)
-
+ if !autosubmitted.nil?
+ @autosubmitted = TMail::UnstructuredHeader.new("auto-submitted", autosubmitted)
+ end
@mail = mock(TMail::Mail)
@mail.stub!(:from_addrs).and_return( [ @address ] )
@mail.stub!(:[]).with("return-path").and_return(@return_path)
@@ -96,50 +140,49 @@ describe IncomingMessage, " checking validity to reply to" do
@incoming_message = IncomingMessage.new()
@incoming_message.stub!(:mail).and_return(@mail)
-
- @incoming_message.valid_to_reply_to?.should == result
+ @incoming_message._calculate_valid_to_reply_to.should == result
end
it "says a valid email is fine" do
- test_email(true, "team@mysociety.org", nil, [])
+ test_email(true, "team@mysociety.org", nil)
end
it "says postmaster email is bad" do
- test_email(false, "postmaster@mysociety.org", nil, [])
+ test_email(false, "postmaster@mysociety.org", nil)
end
it "says Mailer-Daemon email is bad" do
- test_email(false, "Mailer-Daemon@mysociety.org", nil, [])
+ test_email(false, "Mailer-Daemon@mysociety.org", nil)
end
it "says case mangled MaIler-DaemOn email is bad" do
- test_email(false, "MaIler-DaemOn@mysociety.org", nil, [])
+ test_email(false, "MaIler-DaemOn@mysociety.org", nil)
end
it "says Auto_Reply email is bad" do
- test_email(false, "Auto_Reply@mysociety.org", nil, [])
+ test_email(false, "Auto_Reply@mysociety.org", nil)
end
it "says DoNotReply email is bad" do
- test_email(false, "DoNotReply@tube.tfl.gov.uk", nil, [])
+ test_email(false, "DoNotReply@tube.tfl.gov.uk", nil)
end
it "says a filled-out return-path is fine" do
- test_email(true, "team@mysociety.org", "Return-path: <foo@baz.com>", [])
+ test_email(true, "team@mysociety.org", "Return-path: <foo@baz.com>")
end
it "says an empty return-path is bad" do
- test_email(false, "team@mysociety.org", "<>", [])
+ test_email(false, "team@mysociety.org", "<>")
end
it "says an auto-submitted keyword is bad" do
- test_email(false, "team@mysociety.org", nil, ["auto-replied"])
+ test_email(false, "team@mysociety.org", nil, "auto-replied")
end
end
describe IncomingMessage, " checking validity to reply to with real emails" do
- fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users
+ fixtures :users, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
after(:all) do
ActionMailer::Base.deliveries.clear
@@ -163,7 +206,7 @@ describe IncomingMessage, " checking validity to reply to with real emails" do
end
describe IncomingMessage, " when censoring data" do
- fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users
+ fixtures :users, :raw_emails, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
@test_data = "There was a mouse called Stilton, he wished that he was blue."
@@ -262,10 +305,8 @@ describe IncomingMessage, " when censoring data" do
end
it "should apply censor rules to From: addresses" do
- mock_mail = mock('Email object')
- mock_mail.stub!(:from_name_if_present).and_return("Stilton Mouse")
- @im.stub!(:mail).and_return(mock_mail)
-
+ @im.stub!(:mail_from).and_return("Stilton Mouse")
+ @im.stub!(:last_parsed).and_return(Time.now)
safe_mail_from = @im.safe_mail_from
safe_mail_from.should == "Jarlsberg Mouse"
end
@@ -273,7 +314,7 @@ describe IncomingMessage, " when censoring data" do
end
describe IncomingMessage, " when censoring whole users" do
- fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users
+ fixtures :users, :raw_emails, :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
@test_data = "There was a mouse called Stilton, he wished that he was blue."
@@ -304,21 +345,23 @@ end
describe IncomingMessage, " when uudecoding bad messages" do
+ fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users, :foi_attachments
+
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ end
+
it "should be able to do it at all" do
mail_body = load_file_fixture('incoming-request-bad-uuencoding.email')
mail = TMail::Mail.parse(mail_body)
mail.base64_decode
-
- im = IncomingMessage.new
+ im = incoming_messages(:useless_incoming_message)
im.stub!(:mail).and_return(mail)
- ir = InfoRequest.new
- im.info_request = ir
- u = User.new
- ir.user = u
-
- attachments = im.get_main_body_text_uudecode_attachments
- attachments.size.should == 1
- attachments[0].filename.should == 'moo.txt'
+ im.extract_attachments!
+ attachments = im.foi_attachments
+ attachments.size.should == 2
+ attachments[1].filename.should == 'moo.txt'
+ im.get_attachments_for_display.size.should == 1
end
it "should apply censor rules" do
@@ -326,12 +369,9 @@ describe IncomingMessage, " when uudecoding bad messages" do
mail = TMail::Mail.parse(mail_body)
mail.base64_decode
- im = IncomingMessage.new
+ im = incoming_messages(:useless_incoming_message)
im.stub!(:mail).and_return(mail)
- ir = InfoRequest.new
- im.info_request = ir
- u = User.new
- ir.user = u
+ ir = info_requests(:fancy_dog_request)
@censor_rule = CensorRule.new()
@censor_rule.text = "moo"
@@ -339,26 +379,31 @@ describe IncomingMessage, " when uudecoding bad messages" do
@censor_rule.last_edit_editor = "unknown"
@censor_rule.last_edit_comment = "none"
ir.censor_rules << @censor_rule
+ im.extract_attachments!
- attachments = im.get_main_body_text_uudecode_attachments
+ attachments = im.get_attachments_for_display
attachments.size.should == 1
- attachments[0].filename.should == 'bah.txt'
+ attachments[0].display_filename.should == 'bah.txt'
end
end
describe IncomingMessage, "when messages are attached to messages" do
+ fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users, :foi_attachments
+
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ end
+
it "should flatten all the attachments out" do
mail_body = load_file_fixture('incoming-request-attach-attachments.email')
mail = TMail::Mail.parse(mail_body)
mail.base64_decode
- im = IncomingMessage.new
+ im = incoming_messages(:useless_incoming_message)
im.stub!(:mail).and_return(mail)
- ir = InfoRequest.new
- im.info_request = ir
- u = User.new
- ir.user = u
+
+ im.extract_attachments!
attachments = im.get_attachments_for_display
attachments.size.should == 3
@@ -369,17 +414,20 @@ describe IncomingMessage, "when messages are attached to messages" do
end
describe IncomingMessage, "when Outlook messages are attached to messages" do
+ fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users, :foi_attachments
+
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ end
+
it "should flatten all the attachments out" do
mail_body = load_file_fixture('incoming-request-oft-attachments.email')
mail = TMail::Mail.parse(mail_body)
mail.base64_decode
- im = IncomingMessage.new
+ im = incoming_messages(:useless_incoming_message)
im.stub!(:mail).and_return(mail)
- ir = InfoRequest.new
- im.info_request = ir
- u = User.new
- ir.user = u
+ im.extract_attachments!
attachments = im.get_attachments_for_display
attachments.size.should == 2
@@ -389,17 +437,20 @@ describe IncomingMessage, "when Outlook messages are attached to messages" do
end
describe IncomingMessage, "when TNEF attachments are attached to messages" do
+ fixtures :incoming_messages, :raw_emails, :public_bodies, :public_body_translations, :info_requests, :users, :foi_attachments
+
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ end
+
it "should flatten all the attachments out" do
mail_body = load_file_fixture('incoming-request-tnef-attachments.email')
mail = TMail::Mail.parse(mail_body)
mail.base64_decode
- im = IncomingMessage.new
+ im = incoming_messages(:useless_incoming_message)
im.stub!(:mail).and_return(mail)
- ir = InfoRequest.new
- im.info_request = ir
- u = User.new
- ir.user = u
+ im.extract_attachments!
attachments = im.get_attachments_for_display
attachments.size.should == 2
diff --git a/spec/models/info_request_event_spec.rb b/spec/models/info_request_event_spec.rb
index 666f5cb1a..3229284cc 100644
--- a/spec/models/info_request_event_spec.rb
+++ b/spec/models/info_request_event_spec.rb
@@ -50,5 +50,30 @@ describe InfoRequestEvent do
end
end
+
+ describe "doing search/index stuff" do
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
+
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ parse_all_incoming_messages
+ end
+
+ it 'should get search text for outgoing messages' do
+ event = info_request_events(:useless_outgoing_message_event)
+ message = outgoing_messages(:useless_outgoing_message).body
+ event.search_text_main.should == message + "\n\n"
+ end
+
+ it 'should get search text for incoming messages' do
+ event = info_request_events(:useless_incoming_message_event)
+ event.search_text_main.strip.should == "No way! I'm not going to tell you that in a month of Thursdays.\n\nThe Geraldine Quango"
+ end
+
+
+ end
+
+
+
end
diff --git a/spec/models/info_request_spec.rb b/spec/models/info_request_spec.rb
index b82052a0f..b1baa66a2 100644
--- a/spec/models/info_request_spec.rb
+++ b/spec/models/info_request_spec.rb
@@ -3,7 +3,7 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe InfoRequest do
describe "guessing a request from an email" do
- fixtures :info_requests, :public_bodies, :incoming_messages, :raw_emails
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
@im = incoming_messages(:useless_incoming_message)
@@ -74,7 +74,7 @@ describe InfoRequest do
describe " when emailing" do
- fixtures :info_requests, :info_request_events, :outgoing_messages, :public_bodies, :public_body_translations, :users, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@info_request = info_requests(:fancy_dog_request)
@@ -143,8 +143,8 @@ describe InfoRequest do
end
it "should cope with indexing after item is deleted" do
+ IncomingMessage.find(:all).each{|x| x.parse_raw_email!}
rebuild_xapian_index
-
# delete event from underneath indexing; shouldn't cause error
info_request_events(:useless_incoming_message_event).save!
info_request_events(:useless_incoming_message_event).destroy
@@ -154,7 +154,7 @@ describe InfoRequest do
end
describe "when calculating the status" do
- fixtures :info_requests, :info_request_events, :holidays, :public_bodies, :public_body_translations, :outgoing_messages
+ fixtures :holidays, :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@ir = info_requests(:naughty_chicken_request)
@@ -196,7 +196,7 @@ describe InfoRequest do
describe "when using a plugin and calculating the status" do
- fixtures :info_requests
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
InfoRequest.send(:require, File.expand_path(File.dirname(__FILE__) + '/customstates'))
@@ -231,7 +231,7 @@ describe InfoRequest do
describe "when calculating the status for a school" do
- fixtures :info_requests, :info_request_events, :holidays, :public_bodies, :public_body_translations
+ fixtures :holidays, :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@ir = info_requests(:naughty_chicken_request)
@@ -380,8 +380,8 @@ describe InfoRequest do
before do
Time.stub!(:now).and_return(Time.utc(2007, 11, 9, 23, 59))
- @mock_comment_event = mock_model(InfoRequestEvent, :created_at => Time.now - 23.days, :event_type => 'comment')
- @mock_response_event = mock_model(InfoRequestEvent, :created_at => Time.now - 22.days, :event_type => 'response')
+ @mock_comment_event = safe_mock_model(InfoRequestEvent, :created_at => Time.now - 23.days, :event_type => 'comment')
+ @mock_response_event = safe_mock_model(InfoRequestEvent, :created_at => Time.now - 22.days, :event_type => 'response')
@info_request = InfoRequest.new(:prominence => 'normal',
:awaiting_description => true,
:info_request_events => [@mock_response_event, @mock_comment_event])
diff --git a/spec/models/outgoing_mailer_spec.rb b/spec/models/outgoing_mailer_spec.rb
index c96a3fb74..75c8053b4 100644
--- a/spec/models/outgoing_mailer_spec.rb
+++ b/spec/models/outgoing_mailer_spec.rb
@@ -4,7 +4,7 @@ describe OutgoingMailer, " when working out follow up addresses" do
# This is done with fixtures as the code is a bit tangled with the way it
# calls TMail. XXX untangle it and make these tests spread out and using
# mocks. Put parts of the tests in spec/lib/tmail_extensions.rb
- fixtures :info_requests, :incoming_messages, :raw_emails, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -70,7 +70,7 @@ describe OutgoingMailer, " when working out follow up addresses" do
end
describe OutgoingMailer, "when working out follow up subjects" do
- fixtures :info_requests, :incoming_messages, :outgoing_messages, :raw_emails
+ fixtures :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
diff --git a/spec/models/outgoing_message_spec.rb b/spec/models/outgoing_message_spec.rb
index 1956c4d73..58d9f398e 100644
--- a/spec/models/outgoing_message_spec.rb
+++ b/spec/models/outgoing_message_spec.rb
@@ -1,7 +1,7 @@
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe OutgoingMessage, " when making an outgoing message" do
- fixtures :outgoing_messages, :info_requests, :incoming_messages, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@om = outgoing_messages(:useless_outgoing_message)
@@ -38,7 +38,7 @@ end
describe IncomingMessage, " when censoring data" do
- fixtures :outgoing_messages, :info_requests
+ fixtures :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@om = outgoing_messages(:useless_outgoing_message)
diff --git a/spec/models/public_body_spec.rb b/spec/models/public_body_spec.rb
index 33ab8ffdb..07e8f291d 100644
--- a/spec/models/public_body_spec.rb
+++ b/spec/models/public_body_spec.rb
@@ -95,7 +95,7 @@ describe PublicBody, " using machine tags" do
end
describe PublicBody, "when finding_by_tags" do
- fixtures :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@geraldine = public_bodies(:geraldine_public_body)
@@ -173,7 +173,7 @@ describe PublicBody, " when saving" do
end
describe PublicBody, "when searching" do
- fixtures :public_bodies, :public_body_translations, :public_body_versions
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should find by existing url name" do
body = PublicBody.find_by_url_name_with_historic('dfh')
@@ -226,6 +226,18 @@ describe PublicBody, "when searching" do
end
end
+describe PublicBody, " when dealing public body locales" do
+ it "shouldn't fail if it internal_admin_body was created in a locale other than the default" do
+ # first time, do it with the non-default locale
+ PublicBody.with_locale(:es) do
+ PublicBody.internal_admin_body
+ end
+
+ # second time
+ lambda {PublicBody.internal_admin_body }.should_not raise_error(ActiveRecord::RecordInvalid)
+ end
+end
+
describe PublicBody, " when loading CSV files" do
before(:each) do
# InternalBody is created the first time it's accessed, which happens sometimes during imports,
@@ -302,8 +314,8 @@ describe PublicBody, " when loading CSV files" do
notes.size.should == 4
notes.should == [
"line 2: creating new authority 'North West Fake Authority' (locale: en):\n\t\{\"name\":\"North West Fake Authority\",\"request_email\":\"north_west_foi@localhost\",\"home_page\":\"http://northwest.org\"\}",
- "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t\{\"tag_string\":\"scottish\",\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\"\}",
- "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t\{\"tag_string\":\"fake aTag\",\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\"\}",
+ "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t\{\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\",\"tag_string\":\"scottish\"\}",
+ "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t\{\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\",\"tag_string\":\"fake aTag\"\}",
"Notes: Some bodies are in database, but not in CSV file:\n Department for Humpadinking\n Geraldine Quango\nYou may want to delete them manually.\n"
]
@@ -316,7 +328,7 @@ describe PublicBody, " when loading CSV files" do
PublicBody.find_by_name('North West Fake Authority').tag_array_for_search.should == []
PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['scottish']
- PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['fake', 'aTag']
+ PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['aTag', 'fake']
# Import again to check the 'add' tag functionality works
new_tags_file = load_file_fixture('fake-authority-add-tags.rb')
@@ -324,8 +336,8 @@ describe PublicBody, " when loading CSV files" do
# Check tags were added successfully
PublicBody.find_by_name('North West Fake Authority').tag_array_for_search.should == ['aTag']
- PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['scottish', 'aTag']
- PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['fake', 'aTag']
+ PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['aTag', 'scottish']
+ PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['aTag', 'fake']
end
it "should import tags successfully when the import tag is set" do
@@ -334,8 +346,8 @@ describe PublicBody, " when loading CSV files" do
# Check new bodies were imported successfully
PublicBody.find_by_name('North West Fake Authority').tag_array_for_search.should == ['fake']
- PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['scottish', 'fake']
- PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['fake', 'aTag']
+ PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['fake', 'scottish']
+ PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['aTag', 'fake']
# Import again to check the 'replace' tag functionality works
new_tags_file = load_file_fixture('fake-authority-add-tags.rb')
@@ -344,7 +356,7 @@ describe PublicBody, " when loading CSV files" do
# Check tags were added successfully
PublicBody.find_by_name('North West Fake Authority').tag_array_for_search.should == ['aTag']
PublicBody.find_by_name('Scottish Fake Authority').tag_array_for_search.should == ['aTag']
- PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['fake', 'aTag']
+ PublicBody.find_by_name('Fake Authority of Northern Ireland').tag_array_for_search.should == ['aTag', 'fake']
end
it "should create bodies with names in multiple locales" do
@@ -357,9 +369,9 @@ describe PublicBody, " when loading CSV files" do
notes.should == [
"line 2: creating new authority 'North West Fake Authority' (locale: en):\n\t{\"name\":\"North West Fake Authority\",\"request_email\":\"north_west_foi@localhost\",\"home_page\":\"http://northwest.org\"}",
"line 2: creating new authority 'North West Fake Authority' (locale: es):\n\t{\"name\":\"Autoridad del Nordeste\"}",
- "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t{\"tag_string\":\"scottish\",\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\"}",
+ "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t{\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\",\"tag_string\":\"scottish\"}",
"line 3: creating new authority 'Scottish Fake Authority' (locale: es):\n\t{\"name\":\"Autoridad Escocesa\"}",
- "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t{\"tag_string\":\"fake aTag\",\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\"}",
+ "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t{\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\",\"tag_string\":\"fake aTag\"}",
"line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: es):\n\t{\"name\":\"Autoridad Irlandesa\"}",
"Notes: Some bodies are in database, but not in CSV file:\n Department for Humpadinking\n Geraldine Quango\nYou may want to delete them manually.\n"
]
@@ -385,8 +397,8 @@ describe PublicBody, " when loading CSV files" do
notes.size.should == 4
notes.should == [
"line 2: creating new authority 'North West Fake Authority' (locale: en):\n\t{\"name\":\"North West Fake Authority\",\"request_email\":\"north_west_foi@localhost\",\"home_page\":\"http://northwest.org\"}",
- "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t{\"tag_string\":\"scottish\",\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\"}",
- "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t{\"tag_string\":\"fake aTag\",\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\"}",
+ "line 3: creating new authority 'Scottish Fake Authority' (locale: en):\n\t{\"name\":\"Scottish Fake Authority\",\"request_email\":\"scottish_foi@localhost\",\"home_page\":\"http://scottish.org\",\"tag_string\":\"scottish\"}",
+ "line 4: creating new authority 'Fake Authority of Northern Ireland' (locale: en):\n\t{\"name\":\"Fake Authority of Northern Ireland\",\"request_email\":\"ni_foi@localhost\",\"tag_string\":\"fake aTag\"}",
"Notes: Some bodies are in database, but not in CSV file:\n Department for Humpadinking\n Geraldine Quango\nYou may want to delete them manually.\n"
]
diff --git a/spec/models/request_mailer_spec.rb b/spec/models/request_mailer_spec.rb
index fbe22c220..ef4ed8074 100644
--- a/spec/models/request_mailer_spec.rb
+++ b/spec/models/request_mailer_spec.rb
@@ -1,7 +1,7 @@
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe RequestMailer, " when receiving incoming mail" do
- fixtures :info_requests, :incoming_messages, :raw_emails, :users, :public_bodies, :public_body_translations
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
diff --git a/spec/models/track_thing_spec.rb b/spec/models/track_thing_spec.rb
index 1a0324a78..4922a96c7 100644
--- a/spec/models/track_thing_spec.rb
+++ b/spec/models/track_thing_spec.rb
@@ -1,7 +1,7 @@
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe TrackThing, "when tracking changes" do
- fixtures :track_things, :users
+ fixtures :users, :info_requests, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@track_thing = track_things(:track_fancy_dog_search)
diff --git a/spec/models/user_spec.rb b/spec/models/user_spec.rb
index 751a61060..e0a6c649e 100644
--- a/spec/models/user_spec.rb
+++ b/spec/models/user_spec.rb
@@ -152,10 +152,10 @@ end
describe User, "when reindexing referencing models" do
before do
- @request_event = mock_model(InfoRequestEvent, :xapian_mark_needs_index => true)
- @request = mock_model(InfoRequest, :info_request_events => [@request_event])
- @comment_event = mock_model(InfoRequestEvent, :xapian_mark_needs_index => true)
- @comment = mock_model(Comment, :info_request_events => [@comment_event])
+ @request_event = safe_mock_model(InfoRequestEvent, :xapian_mark_needs_index => true)
+ @request = safe_mock_model(InfoRequest, :info_request_events => [@request_event])
+ @comment_event = safe_mock_model(InfoRequestEvent, :xapian_mark_needs_index => true)
+ @comment = safe_mock_model(Comment, :info_request_events => [@comment_event])
@user = User.new(:comments => [@comment], :info_requests => [@request])
end
@@ -193,7 +193,7 @@ describe User, "when reindexing referencing models" do
end
describe User, "when checking abilities" do
- fixtures :users
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@user = users(:bob_smith_user)
@@ -283,7 +283,7 @@ describe User, "when setting a profile photo" do
end
describe User, "when unconfirmed" do
- fixtures :users
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before do
@user = users(:unconfirmed_user)
@@ -295,7 +295,7 @@ describe User, "when unconfirmed" do
end
describe User, "when emails have bounced" do
- fixtures :users
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should record bounces" do
User.record_bounce_for_email("bob@localhost", "The reason we think the email bounced (e.g. a bounce message)")
diff --git a/spec/models/xapian_spec.rb b/spec/models/xapian_spec.rb
index 0c6fa6bb6..ec11c944b 100644
--- a/spec/models/xapian_spec.rb
+++ b/spec/models/xapian_spec.rb
@@ -1,9 +1,10 @@
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
describe User, " when indexing users with Xapian" do
- fixtures :users
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
it "should search by name" do
+ parse_all_incoming_messages
rebuild_xapian_index
# def InfoRequest.full_search(models, query, order, ascending, collapse, per_page, page)
xapian_object = InfoRequest.full_search([User], "Silly", 'created_at', true, nil, 100, 1)
@@ -12,10 +13,10 @@ describe User, " when indexing users with Xapian" do
end
it "should search by 'about me' text" do
+ rebuild_xapian_index
user = users(:bob_smith_user)
- rebuild_xapian_index
- # def InfoRequest.full_search(models, query, order, ascending, collapse, per_page, page)
+ # def InfoRequest.full_search(models, query, order, ascending, collapse, per_page, page)
xapian_object = InfoRequest.full_search([User], "stuff", 'created_at', true, nil, 100, 1)
xapian_object.results.size.should == 1
xapian_object.results[0][:model].should == user
@@ -34,7 +35,7 @@ describe User, " when indexing users with Xapian" do
end
describe PublicBody, " when indexing public bodies with Xapian" do
- fixtures :public_bodies, :public_body_translations, :incoming_messages, :outgoing_messages, :raw_emails, :comments, :info_requests
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -72,7 +73,7 @@ describe PublicBody, " when indexing public bodies with Xapian" do
end
describe PublicBody, " when indexing requests by body they are to" do
- fixtures :public_bodies, :public_body_translations, :info_request_events, :info_requests, :raw_emails, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
@@ -132,7 +133,7 @@ describe PublicBody, " when indexing requests by body they are to" do
end
describe User, " when indexing requests by user they are from" do
- fixtures :users, :info_request_events, :info_requests, :incoming_messages, :outgoing_messages, :raw_emails, :comments
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -219,7 +220,7 @@ describe User, " when indexing requests by user they are from" do
end
describe User, " when indexing comments by user they are by" do
- fixtures :users, :info_request_events, :info_requests, :comments, :incoming_messages, :outgoing_messages, :raw_emails, :comments
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -256,7 +257,7 @@ describe User, " when indexing comments by user they are by" do
end
describe InfoRequest, " when indexing requests by their title" do
- fixtures :info_request_events, :info_requests, :incoming_messages, :raw_emails, :comments
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -287,7 +288,7 @@ describe InfoRequest, " when indexing requests by their title" do
end
describe InfoRequest, " when indexing requests by tag" do
- fixtures :info_request_events, :info_requests, :incoming_messages, :raw_emails, :comments
+ fixtures :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -309,7 +310,7 @@ describe InfoRequest, " when indexing requests by tag" do
end
describe PublicBody, " when indexing authorities by tag" do
- fixtures :public_bodies, :public_body_translations, :incoming_messages, :outgoing_messages, :raw_emails, :comments
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
before(:each) do
load_raw_emails_data(raw_emails)
end
@@ -333,6 +334,66 @@ describe PublicBody, " when indexing authorities by tag" do
end
end
+describe PublicBody, " when only indexing selected things on a rebuild" do
+ fixtures :public_bodies, :public_body_translations, :public_body_versions, :users, :info_requests, :raw_emails, :incoming_messages, :outgoing_messages, :comments, :info_request_events, :track_things
+ before(:each) do
+ load_raw_emails_data(raw_emails)
+ end
+
+ it "should only index what we ask it to" do
+ rebuild_xapian_index
+ body = public_bodies(:geraldine_public_body)
+ body.tag_string = 'mice:3'
+ body.name = 'frobzn'
+ body.save!
+ # only reindex 'variety' term
+ dropfirst = true
+ terms = "V"
+ values = false
+ texts = false
+ rebuild_xapian_index(terms, values, texts, dropfirst)
+ xapian_object = InfoRequest.full_search([PublicBody], "tag:mice", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 0
+ xapian_object = InfoRequest.full_search([PublicBody], "frobzn", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 0
+ xapian_object = InfoRequest.full_search([PublicBody], "variety:authority", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 2
+ # only reindex 'tag' and text
+ dropfirst = true
+ terms = "U"
+ values = false
+ texts = true
+ rebuild_xapian_index(terms, values, texts, dropfirst)
+ xapian_object = InfoRequest.full_search([PublicBody], "tag:mice", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 1
+ xapian_object = InfoRequest.full_search([PublicBody], "frobzn", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 1
+ xapian_object = InfoRequest.full_search([PublicBody], "variety:authority", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 0
+ # only reindex 'variety' term, but keeping the existing data in-place
+ dropfirst = false
+ terms = "V"
+ texts = false
+ rebuild_xapian_index(terms, values, texts, dropfirst)
+ xapian_object = InfoRequest.full_search([PublicBody], "tag:mice", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 1
+ xapian_object = InfoRequest.full_search([PublicBody], "frobzn", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 1
+ xapian_object = InfoRequest.full_search([PublicBody], "variety:authority", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 2
+ # only reindex 'variety' term, blowing away existing data
+ dropfirst = true
+ rebuild_xapian_index(terms, values, texts, dropfirst)
+ xapian_object = InfoRequest.full_search([PublicBody], "tag:mice", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 0
+ xapian_object = InfoRequest.full_search([PublicBody], "frobzn", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 0
+ xapian_object = InfoRequest.full_search([PublicBody], "variety:authority", 'created_at', true, nil, 100, 1)
+ xapian_object.results.size.should == 2
+ end
+end
+
+
diff --git a/spec/script/handle-mail-replies_spec.rb b/spec/script/handle-mail-replies_spec.rb
index eae0b516b..8ed83b31f 100644
--- a/spec/script/handle-mail-replies_spec.rb
+++ b/spec/script/handle-mail-replies_spec.rb
@@ -54,5 +54,15 @@ describe "When filtering" do
r = mail_reply_test("track-response-messageclass-oof.email")
r.status.should == 2
end
+
+ it "should detect an Outlook(?)-style out-of-office" do
+ r = mail_reply_test("track-response-outlook-oof.email")
+ r.status.should == 2
+ end
+
+ it "should detect an ABCMail-style out-of-office" do
+ r = mail_reply_test("track-response-abcmail-oof.email")
+ r.status.should == 2
+ end
end
diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb
index ffe48c731..5c5cd9a7f 100644
--- a/spec/spec_helper.rb
+++ b/spec/spec_helper.rb
@@ -1,7 +1,7 @@
# This file is copied to ~/spec when you run 'ruby script/generate rspec'
# from the project root directory.
ENV["RAILS_ENV"] ||= 'test'
-require File.expand_path(File.join(File.dirname(__FILE__),'..','config','environment'))
+require File.expand_path(File.join('..', '..', 'config', 'environment'), __FILE__)
require 'spec/autorun'
require 'spec/rails'
@@ -17,16 +17,13 @@ config['REPLY_LATE_AFTER_DAYS'] = 20
# Uncomment the next line to use webrat's matchers
#require 'webrat/integrations/rspec-rails'
-# Requires supporting files with custom matchers and macros, etc,
-# in ./support/ and its subdirectories.
-Dir[File.expand_path(File.join(File.dirname(__FILE__),'support','**','*.rb'))].each {|f| require f}
-
Spec::Runner.configure do |config|
# If you're not using ActiveRecord you should remove these
# lines, delete config/database.yml and disable :active_record
# in your config/boot.rb
- config.fixture_path = RAILS_ROOT + '/spec/fixtures/'
+ # fixture_path must end in a separator
+ config.fixture_path = File.join(Rails.root, 'spec', 'fixtures') + File::SEPARATOR
# == Fixtures
#
@@ -80,12 +77,21 @@ def load_file_fixture(file_name)
return content
end
-def rebuild_xapian_index
- # XXX could for speed call ActsAsXapian.rebuild_index directly, but would
- # need model name list, and would need to fix acts_as_xapian so can call writes
- # and reads mixed up (it asserts where it thinks it can't do this)
- rebuild_name = File.dirname(__FILE__) + '/../script/rebuild-xapian-index'
- Kernel.system(rebuild_name) or raise "failed to launch #{rebuild_name}, error bitcode #{$?}, exit status: #{$?.exitstatus}"
+def rebuild_xapian_index(terms = true, values = true, texts = true, dropfirst = true)
+ parse_all_incoming_messages
+ if dropfirst
+ begin
+ ActsAsXapian.readable_init
+ FileUtils.rm_r(ActsAsXapian.db_path)
+ rescue RuntimeError
+ end
+ ActsAsXapian.writable_init
+ end
+ verbose = false
+ # safe_rebuild=true, which involves forking to avoid memory leaks, doesn't work well with rspec.
+ # unsafe is significantly faster, and we can afford possible memory leaks while testing.
+ safe_rebuild = false
+ ActsAsXapian.rebuild_index(["PublicBody", "User", "InfoRequestEvent"].map{|m| m.constantize}, verbose, terms, values, texts, safe_rebuild)
end
def update_xapian_index
@@ -114,7 +120,7 @@ def validate_as_body(html)
end
def basic_auth_login(request, username = nil, password = nil)
- username = MySociety::Config.get('ADMIN_USERNAME') if username.nil?
+ username = MySociety::Config.get('ADMIN_USERNAME') if username.nil?
password = MySociety::Config.get('ADMIN_PASSWORD') if password.nil?
request.env["HTTP_AUTHORIZATION"] = "Basic " + Base64::encode64("#{username}:#{password}")
end
@@ -147,6 +153,14 @@ if $tempfilecount.nil?
end
end
+# to_ary differs in Ruby 1.8 and 1.9
+# @see http://yehudakatz.com/2010/01/02/the-craziest-fing-bug-ive-ever-seen/
+def safe_mock_model(model, args = {})
+ mock = mock_model(model, args)
+ mock.should_receive(:to_ary).any_number_of_times
+ mock
+end
+
def load_raw_emails_data(raw_emails)
raw_email = raw_emails(:useless_raw_email)
begin
@@ -155,3 +169,7 @@ def load_raw_emails_data(raw_emails)
end
raw_email.data = load_file_fixture("useless_raw_email.email")
end
+
+def parse_all_incoming_messages
+ IncomingMessage.find(:all).each{|x| x.parse_raw_email!}
+end
diff --git a/spec/views/public_body/show.rhtml_spec.rb b/spec/views/public_body/show.rhtml_spec.rb
index cd81888eb..a37d8be0d 100644
--- a/spec/views/public_body/show.rhtml_spec.rb
+++ b/spec/views/public_body/show.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe "when viewing a body" do
before do
diff --git a/spec/views/request/_after_actions.rhtml_spec.rb b/spec/views/request/_after_actions.rhtml_spec.rb
index c73f35d33..6a56e7a71 100644
--- a/spec/views/request/_after_actions.rhtml_spec.rb
+++ b/spec/views/request/_after_actions.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe 'when displaying actions that can be taken with regard to a request' do
diff --git a/spec/views/request/_describe_state.rhtml_spec.rb b/spec/views/request/_describe_state.rhtml_spec.rb
index 9fb776db3..ccf653b1b 100644
--- a/spec/views/request/_describe_state.rhtml_spec.rb
+++ b/spec/views/request/_describe_state.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe 'when showing the form for describing the state of a request' do
diff --git a/spec/views/request/list.rhtml_spec.rb b/spec/views/request/list.rhtml_spec.rb
index 60a28eec5..1f86ec641 100644
--- a/spec/views/request/list.rhtml_spec.rb
+++ b/spec/views/request/list.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe "when listing recent requests" do
diff --git a/spec/views/request/show.rhtml_spec.rb b/spec/views/request/show.rhtml_spec.rb
index ca4663afc..adb244f47 100644
--- a/spec/views/request/show.rhtml_spec.rb
+++ b/spec/views/request/show.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe 'when viewing an information request' do
diff --git a/spec/views/request_game/play.rhtml_spec.rb b/spec/views/request_game/play.rhtml_spec.rb
index e90861e34..24fb6d75d 100644
--- a/spec/views/request_game/play.rhtml_spec.rb
+++ b/spec/views/request_game/play.rhtml_spec.rb
@@ -1,4 +1,4 @@
-require File.dirname(__FILE__) + '/../../spec_helper'
+require File.expand_path(File.join('..', '..', '..', 'spec_helper'), __FILE__)
describe 'when viewing the request game' do