govuk_content_models 6.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +17 -0
- data/.ruby-version +1 -0
- data/.travis.yml +14 -0
- data/CONTRIBUTING.md +22 -0
- data/Gemfile +4 -0
- data/LICENSE +20 -0
- data/README.md +5 -0
- data/Rakefile +46 -0
- data/app/models/action.rb +60 -0
- data/app/models/answer_edition.rb +13 -0
- data/app/models/artefact.rb +341 -0
- data/app/models/artefact_action.rb +27 -0
- data/app/models/artefact_external_link.rb +15 -0
- data/app/models/business_support/business_size.rb +14 -0
- data/app/models/business_support/business_type.rb +14 -0
- data/app/models/business_support/location.rb +14 -0
- data/app/models/business_support/purpose.rb +14 -0
- data/app/models/business_support/sector.rb +14 -0
- data/app/models/business_support/stage.rb +14 -0
- data/app/models/business_support/support_type.rb +14 -0
- data/app/models/business_support_edition.rb +69 -0
- data/app/models/campaign_edition.rb +72 -0
- data/app/models/completed_transaction_edition.rb +14 -0
- data/app/models/curated_list.rb +32 -0
- data/app/models/edition.rb +286 -0
- data/app/models/expectant.rb +21 -0
- data/app/models/expectation.rb +12 -0
- data/app/models/guide_edition.rb +19 -0
- data/app/models/help_page_edition.rb +13 -0
- data/app/models/licence_edition.rb +35 -0
- data/app/models/local_authority.rb +58 -0
- data/app/models/local_interaction.rb +20 -0
- data/app/models/local_service.rb +49 -0
- data/app/models/local_transaction_edition.rb +49 -0
- data/app/models/overview_dashboard.rb +25 -0
- data/app/models/part.rb +28 -0
- data/app/models/parted.rb +32 -0
- data/app/models/place_edition.rb +20 -0
- data/app/models/programme_edition.rb +26 -0
- data/app/models/simple_smart_answer_edition.rb +66 -0
- data/app/models/simple_smart_answer_edition/node.rb +40 -0
- data/app/models/simple_smart_answer_edition/node/option.rb +31 -0
- data/app/models/tag.rb +88 -0
- data/app/models/transaction_edition.rb +28 -0
- data/app/models/travel_advice_edition.rb +177 -0
- data/app/models/user.rb +54 -0
- data/app/models/video_edition.rb +24 -0
- data/app/models/workflow.rb +217 -0
- data/app/models/workflow_actor.rb +141 -0
- data/app/traits/attachable.rb +60 -0
- data/app/traits/govspeak_smart_quotes_fixer.rb +19 -0
- data/app/traits/taggable.rb +113 -0
- data/app/validators/safe_html.rb +33 -0
- data/app/validators/slug_validator.rb +53 -0
- data/config/mongoid.yml +5 -0
- data/govuk_content_models.gemspec +42 -0
- data/jenkins.sh +7 -0
- data/lib/fact_check_address.rb +36 -0
- data/lib/govuk_content_models.rb +12 -0
- data/lib/govuk_content_models/require_all.rb +14 -0
- data/lib/govuk_content_models/test_helpers/factories.rb +213 -0
- data/lib/govuk_content_models/test_helpers/local_services.rb +24 -0
- data/lib/govuk_content_models/version.rb +4 -0
- data/test/fixtures/contactotron_api_response.json +1 -0
- data/test/fixtures/uploads/image.jpg +0 -0
- data/test/models/artefact_action_test.rb +123 -0
- data/test/models/artefact_external_link_test.rb +32 -0
- data/test/models/artefact_tag_test.rb +52 -0
- data/test/models/artefact_test.rb +583 -0
- data/test/models/business_support/business_size_test.rb +25 -0
- data/test/models/business_support/business_type_test.rb +25 -0
- data/test/models/business_support/location_test.rb +25 -0
- data/test/models/business_support/purpose_test.rb +29 -0
- data/test/models/business_support/sector_test.rb +25 -0
- data/test/models/business_support/stage_test.rb +25 -0
- data/test/models/business_support/support_type_test.rb +25 -0
- data/test/models/business_support_edition_test.rb +186 -0
- data/test/models/campaign_edition_test.rb +90 -0
- data/test/models/curated_list_test.rb +32 -0
- data/test/models/edition_test.rb +826 -0
- data/test/models/fact_check_address_test.rb +36 -0
- data/test/models/help_page_edition_test.rb +38 -0
- data/test/models/licence_edition_test.rb +104 -0
- data/test/models/local_authority_test.rb +113 -0
- data/test/models/local_service_test.rb +199 -0
- data/test/models/local_transaction_edition_test.rb +78 -0
- data/test/models/overview_dashboard_test.rb +47 -0
- data/test/models/simple_smart_answer_edition_test.rb +169 -0
- data/test/models/simple_smart_answer_node_test.rb +134 -0
- data/test/models/simple_smart_answer_option_test.rb +90 -0
- data/test/models/tag_test.rb +92 -0
- data/test/models/time_zone_test.rb +48 -0
- data/test/models/transaction_edition_test.rb +20 -0
- data/test/models/travel_advice_edition_test.rb +480 -0
- data/test/models/user_test.rb +114 -0
- data/test/models/video_edition_test.rb +64 -0
- data/test/models/workflow_actor_test.rb +61 -0
- data/test/models/workflow_test.rb +307 -0
- data/test/test_helper.rb +47 -0
- data/test/traits/attachable_test.rb +143 -0
- data/test/traits/taggable_test.rb +114 -0
- data/test/validators/safe_html_validator_test.rb +86 -0
- data/test/validators/slug_validator_test.rb +42 -0
- metadata +511 -0
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
require "test_helper"
|
|
2
|
+
|
|
3
|
+
class UserTest < ActiveSupport::TestCase
|
|
4
|
+
def setup
|
|
5
|
+
@artefact = FactoryGirl.create(:artefact)
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
test "should convert to string using name by preference" do
|
|
9
|
+
user = User.new(name: "Bob", email: "user@example.com")
|
|
10
|
+
assert_equal "Bob", user.to_s
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
test "should convert to string using email if name if missing" do
|
|
14
|
+
user = User.new(email: "user@example.com")
|
|
15
|
+
assert_equal "user@example.com", user.to_s
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
test "should convert to empty string if name and email are missing" do
|
|
19
|
+
user = User.new
|
|
20
|
+
assert_equal "", user.to_s
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
test "should create new user with oauth params" do
|
|
24
|
+
auth_hash = {
|
|
25
|
+
"uid" => "1234abcd",
|
|
26
|
+
"info" => {
|
|
27
|
+
"uid" => "1234abcd",
|
|
28
|
+
"email" => "user@example.com",
|
|
29
|
+
"name" => "Luther Blisset"
|
|
30
|
+
},
|
|
31
|
+
"extra" => {
|
|
32
|
+
"user" => {
|
|
33
|
+
"permissions" => ["signin"]
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
user = User.find_for_gds_oauth(auth_hash).reload
|
|
38
|
+
assert_equal "1234abcd", user.uid
|
|
39
|
+
assert_equal "user@example.com", user.email
|
|
40
|
+
assert_equal "Luther Blisset", user.name
|
|
41
|
+
assert_equal(["signin"], user.permissions)
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
test "should find and update the user with oauth params" do
|
|
45
|
+
attributes = {uid: "1234abcd", name: "Old", email: "old@m.com",
|
|
46
|
+
permissions: ["everything"]}
|
|
47
|
+
User.create!(attributes, without_protection: true)
|
|
48
|
+
auth_hash = {
|
|
49
|
+
"uid" => "1234abcd",
|
|
50
|
+
"info" => {
|
|
51
|
+
"email" => "new@m.com",
|
|
52
|
+
"name" => "New"
|
|
53
|
+
},
|
|
54
|
+
"extra" => {
|
|
55
|
+
"user" => {
|
|
56
|
+
"permissions" => []
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
user = User.find_for_gds_oauth(auth_hash).reload
|
|
61
|
+
assert_equal "1234abcd", user.uid
|
|
62
|
+
assert_equal "new@m.com", user.email
|
|
63
|
+
assert_equal "New", user.name
|
|
64
|
+
assert_equal([], user.permissions)
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
test "should create insecure gravatar URL" do
|
|
68
|
+
user = User.new(email: "User@example.com")
|
|
69
|
+
expected = "http://www.gravatar.com/avatar/b58996c504c5638798eb6b511e6f49af"
|
|
70
|
+
assert_equal expected, user.gravatar_url
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
test "should create secure gravatar URL" do
|
|
74
|
+
user = User.new(email: "user@example.com")
|
|
75
|
+
expected = "https://secure.gravatar.com/avatar/b58996c504c5638798eb6b511e6f49af"
|
|
76
|
+
assert_equal expected, user.gravatar_url(ssl: true)
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
test "should add escaped s parameter if supplied" do
|
|
80
|
+
user = User.new(email: "user@example.com")
|
|
81
|
+
expected = "http://www.gravatar.com/avatar/b58996c504c5638798eb6b511e6f49af?s=foo+bar"
|
|
82
|
+
assert_equal expected, user.gravatar_url(s: "foo bar")
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
test "creating a transaction with the initial details creates a valid transaction" do
|
|
86
|
+
user = User.create(:name => "bob")
|
|
87
|
+
trans = user.create_edition(:transaction, title: "test", slug: "test", panopticon_id: @artefact.id)
|
|
88
|
+
assert trans.valid?
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
test "user can't okay a publication they've sent for review" do
|
|
92
|
+
user = User.create(:name => "bob")
|
|
93
|
+
|
|
94
|
+
trans = user.create_edition(:transaction, title: "test answer", slug: "test", panopticon_id: @artefact.id)
|
|
95
|
+
user.request_review(trans, {comment: "Hello"})
|
|
96
|
+
assert ! user.approve_review(trans, {comment: "Hello"})
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
test "Edition becomes assigned to user when user is assigned an edition" do
|
|
100
|
+
boss_user = User.create(:name => "Mat")
|
|
101
|
+
worker_user = User.create(:name => "Grunt")
|
|
102
|
+
|
|
103
|
+
publication = boss_user.create_edition(:answer, title: "test answer", slug: "test", panopticon_id: @artefact.id)
|
|
104
|
+
boss_user.assign(publication, worker_user)
|
|
105
|
+
publication.save
|
|
106
|
+
publication.reload
|
|
107
|
+
|
|
108
|
+
assert_equal(worker_user, publication.assigned_to)
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
test "should default to a collection called 'users'" do
|
|
112
|
+
assert_equal "users", User.collection_name
|
|
113
|
+
end
|
|
114
|
+
end
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
require "test_helper"
|
|
2
|
+
|
|
3
|
+
class VideoEditionTest < ActiveSupport::TestCase
|
|
4
|
+
setup do
|
|
5
|
+
@artefact = FactoryGirl.create(:artefact)
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
should "have correct extra fields" do
|
|
9
|
+
v = FactoryGirl.build(:video_edition, panopticon_id: @artefact.id)
|
|
10
|
+
v.video_url = "http://www.youtube.com/watch?v=qySFp3qnVmM"
|
|
11
|
+
v.video_summary = "Coke smoothie"
|
|
12
|
+
v.body = "Description of video"
|
|
13
|
+
v.caption_file_id = 'file-to-an-asset-of-the-caption-file'
|
|
14
|
+
v.safely.save!
|
|
15
|
+
|
|
16
|
+
v = VideoEdition.first
|
|
17
|
+
assert_equal "http://www.youtube.com/watch?v=qySFp3qnVmM", v.video_url
|
|
18
|
+
assert_equal "Coke smoothie", v.video_summary
|
|
19
|
+
assert_equal "Description of video", v.body
|
|
20
|
+
assert_equal 'file-to-an-asset-of-the-caption-file', v.caption_file_id
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
should "give a friendly (legacy supporting) description of its format" do
|
|
24
|
+
video = VideoEdition.new
|
|
25
|
+
assert_equal "Video", video.format
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
context "whole_body" do
|
|
29
|
+
should "combine the video_summary, video_url and body" do
|
|
30
|
+
v = FactoryGirl.build(:video_edition,
|
|
31
|
+
:panopticon_id => @artefact.id,
|
|
32
|
+
:video_summary => "Coke smoothie",
|
|
33
|
+
:video_url => "http://www.youtube.com/watch?v=qySFp3qnVmM",
|
|
34
|
+
:body => "Make a smoothie from a whole can of coke")
|
|
35
|
+
expected = ["Coke smoothie", "http://www.youtube.com/watch?v=qySFp3qnVmM", "Make a smoothie from a whole can of coke"].join("\n\n")
|
|
36
|
+
assert_equal expected, v.whole_body
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
should "cope with a field being nil" do
|
|
40
|
+
v = FactoryGirl.build(:video_edition,
|
|
41
|
+
:panopticon_id => @artefact.id,
|
|
42
|
+
:video_summary => nil,
|
|
43
|
+
:video_url => "http://www.youtube.com/watch?v=qySFp3qnVmM",
|
|
44
|
+
:body => "Make a smoothie from a whole can of coke")
|
|
45
|
+
expected = ["", "http://www.youtube.com/watch?v=qySFp3qnVmM", "Make a smoothie from a whole can of coke"].join("\n\n")
|
|
46
|
+
assert_equal expected, v.whole_body
|
|
47
|
+
end
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
should "clone extra fields when cloning edition" do
|
|
51
|
+
video = FactoryGirl.create(:video_edition,
|
|
52
|
+
:panopticon_id => @artefact.id,
|
|
53
|
+
:state => "published",
|
|
54
|
+
:video_url => "http://www.youtube.com/watch?v=qySFp3qnVmM",
|
|
55
|
+
:video_summary => "Coke smoothie",
|
|
56
|
+
:body => "Description of video")
|
|
57
|
+
|
|
58
|
+
new_video = video.build_clone
|
|
59
|
+
|
|
60
|
+
assert_equal video.video_url, new_video.video_url
|
|
61
|
+
assert_equal video.video_summary, new_video.video_summary
|
|
62
|
+
assert_equal video.body, new_video.body
|
|
63
|
+
end
|
|
64
|
+
end
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
require_relative "../test_helper"
|
|
2
|
+
|
|
3
|
+
class WorkflowActorTest < ActiveSupport::TestCase
|
|
4
|
+
|
|
5
|
+
context "creating a new version of an edition" do
|
|
6
|
+
setup do
|
|
7
|
+
@user = User.new
|
|
8
|
+
@user.stubs(:record_action)
|
|
9
|
+
@edition = stub("AnswerEdition", :published? => true, :build_clone => :new_version)
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
should "return false if the edition is not published" do
|
|
13
|
+
@edition.stubs(:published?).returns(false)
|
|
14
|
+
@edition.expects(:build_clone).never
|
|
15
|
+
@user.expects(:record_action).never
|
|
16
|
+
assert_equal false, @user.new_version(@edition)
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
should "build a clone" do
|
|
20
|
+
@edition.expects(:build_clone).with(nil).returns(:new_verison)
|
|
21
|
+
@user.new_version(@edition)
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
should "record the action" do
|
|
25
|
+
@user.expects(:record_action).with(:new_version, Action::NEW_VERSION)
|
|
26
|
+
@user.new_version(@edition)
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
should "return the new edition" do
|
|
30
|
+
assert_equal :new_version, @user.new_version(@edition)
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
context "creating an edition of a different type" do
|
|
34
|
+
should "build a clone of a new type" do
|
|
35
|
+
@edition.expects(:build_clone).with(GuideEdition).returns(:new_verison)
|
|
36
|
+
@user.new_version(@edition, "GuideEdition")
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
should "record the action" do
|
|
40
|
+
@user.expects(:record_action).with(:new_version, Action::NEW_VERSION)
|
|
41
|
+
@user.new_version(@edition)
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
context "when building the edition fails" do
|
|
46
|
+
setup do
|
|
47
|
+
@edition.stubs(:build_clone).returns(nil)
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
should "not record the action" do
|
|
51
|
+
@user.expects(:record_action).never
|
|
52
|
+
@user.new_version(@edition)
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
should "return false" do
|
|
56
|
+
assert_equal false, @user.new_version(@edition)
|
|
57
|
+
end
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
end
|
|
@@ -0,0 +1,307 @@
|
|
|
1
|
+
require "test_helper"
|
|
2
|
+
|
|
3
|
+
class WorkflowTest < ActiveSupport::TestCase
|
|
4
|
+
def setup
|
|
5
|
+
@artefact = FactoryGirl.create(:artefact)
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
def template_users
|
|
9
|
+
user = User.create(name: "Bob")
|
|
10
|
+
other_user = User.create(name: "James")
|
|
11
|
+
return user, other_user
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def template_programme
|
|
15
|
+
p = ProgrammeEdition.new(slug:"childcare", title:"Children", panopticon_id: @artefact.id)
|
|
16
|
+
p.start_work
|
|
17
|
+
p.save
|
|
18
|
+
p
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def template_guide
|
|
22
|
+
edition = FactoryGirl.create(:guide_edition, slug: "childcare", title: "One", panopticon_id: @artefact.id)
|
|
23
|
+
edition.start_work
|
|
24
|
+
edition.save
|
|
25
|
+
edition
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def publisher_and_guide
|
|
29
|
+
user = User.create(name: "Ben")
|
|
30
|
+
other_user = User.create(name: "James")
|
|
31
|
+
|
|
32
|
+
guide = user.create_edition(:guide, panopticon_id: @artefact.id, overview: "My Overview", title: "My Title", slug: "my-title", alternative_title: "My Other Title")
|
|
33
|
+
edition = guide
|
|
34
|
+
user.start_work(edition)
|
|
35
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
36
|
+
other_user.approve_review(edition, {comment: "I've reviewed it"})
|
|
37
|
+
user.send_fact_check(edition,{comment: "Review this guide please.", email_addresses: "test@test.com"})
|
|
38
|
+
user.receive_fact_check(edition, {comment: "No changes needed, this is all correct"})
|
|
39
|
+
other_user.approve_fact_check(edition, {comment: "Looks good to me"})
|
|
40
|
+
user.publish(edition, {comment: "PUBLISHED!"})
|
|
41
|
+
return user, guide
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def template_user_and_published_transaction
|
|
45
|
+
user = User.create(name: "Ben")
|
|
46
|
+
other_user = User.create(name: "James")
|
|
47
|
+
expectation = Expectation.create text:"Credit card required"
|
|
48
|
+
|
|
49
|
+
transaction = user.create_edition(:transaction, title: "My title", slug: "my-title", panopticon_id: @artefact.id)
|
|
50
|
+
transaction.expectation_ids = [expectation.id]
|
|
51
|
+
transaction.save
|
|
52
|
+
|
|
53
|
+
transaction.start_work
|
|
54
|
+
transaction.save
|
|
55
|
+
user.request_review(transaction, {comment: "Review this guide please."})
|
|
56
|
+
transaction.save
|
|
57
|
+
other_user.approve_review(transaction, {comment: "I've reviewed it"})
|
|
58
|
+
transaction.save
|
|
59
|
+
user.publish(transaction, {comment: "Let's go"})
|
|
60
|
+
transaction.save
|
|
61
|
+
return user, transaction
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
test "permits the creation of new editions" do
|
|
65
|
+
user, transaction = template_user_and_published_transaction
|
|
66
|
+
assert transaction.persisted?
|
|
67
|
+
assert transaction.published?
|
|
68
|
+
|
|
69
|
+
reloaded_transaction = TransactionEdition.find(transaction.id)
|
|
70
|
+
new_edition = user.new_version(reloaded_transaction)
|
|
71
|
+
|
|
72
|
+
assert new_edition.save
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
test "should allow creation of new editions from GuideEdition to AnswerEdition" do
|
|
76
|
+
user, guide = publisher_and_guide
|
|
77
|
+
new_edition = user.new_version(guide, AnswerEdition)
|
|
78
|
+
|
|
79
|
+
assert_equal "AnswerEdition", new_edition._type
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
test "a new answer is lined up" do
|
|
83
|
+
g = AnswerEdition.new(slug: "childcare", panopticon_id: @artefact.id, title: "My new answer")
|
|
84
|
+
assert g.lined_up?
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
test "starting work on an answer removes it from lined up" do
|
|
88
|
+
g = AnswerEdition.new(slug: "childcare", panopticon_id: @artefact.id, title: "My new answer")
|
|
89
|
+
g.save!
|
|
90
|
+
user = User.create(name: "Ben")
|
|
91
|
+
user.start_work(g)
|
|
92
|
+
assert_equal false, g.lined_up?
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
test "a new guide has lined_up but isn't published" do
|
|
96
|
+
g = FactoryGirl.create(:guide_edition, panopticon_id: @artefact.id)
|
|
97
|
+
assert g.lined_up?
|
|
98
|
+
refute g.published?
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
test "when work started a new guide has draft but isn't published" do
|
|
102
|
+
g = FactoryGirl.create(:guide_edition, panopticon_id: @artefact.id)
|
|
103
|
+
g.start_work
|
|
104
|
+
assert g.draft?
|
|
105
|
+
refute g.published?
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
test "a guide should be marked as having reviewables if requested for review" do
|
|
109
|
+
guide = template_guide
|
|
110
|
+
user = User.create(name:"Ben")
|
|
111
|
+
refute guide.in_review?
|
|
112
|
+
user.request_review(guide, {comment: "Review this guide please."})
|
|
113
|
+
assert guide.in_review?
|
|
114
|
+
end
|
|
115
|
+
|
|
116
|
+
test "guide workflow" do
|
|
117
|
+
user = User.create(name: "Ben")
|
|
118
|
+
other_user = User.create(name: "James")
|
|
119
|
+
|
|
120
|
+
guide = user.create_edition(:guide, title: "My Title", slug: "my-title", panopticon_id: @artefact.id)
|
|
121
|
+
edition = guide
|
|
122
|
+
user.start_work(edition)
|
|
123
|
+
assert edition.can_request_review?
|
|
124
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
125
|
+
refute edition.can_request_review?
|
|
126
|
+
assert edition.can_request_amendments?
|
|
127
|
+
other_user.request_amendments(edition, {comment: "I've reviewed it"})
|
|
128
|
+
refute edition.can_request_amendments?
|
|
129
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
130
|
+
assert edition.can_approve_review?
|
|
131
|
+
other_user.approve_review(edition, {comment: "Looks good to me"})
|
|
132
|
+
assert edition.can_publish?
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
test "when fact check has been initiated it can be skipped" do
|
|
136
|
+
user = User.create(name: "Ben")
|
|
137
|
+
other_user = User.create(name: "James")
|
|
138
|
+
|
|
139
|
+
edition = user.create_edition(:guide, panopticon_id: @artefact.id, overview: "My Overview", title: "My Title", slug: "my-title", alternative_title: "My Other Title")
|
|
140
|
+
|
|
141
|
+
user.start_work(edition)
|
|
142
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
143
|
+
other_user.approve_review(edition, {comment: "I've reviewed it"})
|
|
144
|
+
user.send_fact_check(edition,{comment: "Review this guide please.", email_addresses: "test@test.com"})
|
|
145
|
+
|
|
146
|
+
assert other_user.skip_fact_check(edition, {comment: 'Fact check not received in time'})
|
|
147
|
+
edition.reload
|
|
148
|
+
assert edition.can_publish?
|
|
149
|
+
assert edition.actions.detect { |e| e.request_type == 'skip_fact_check' }
|
|
150
|
+
end
|
|
151
|
+
|
|
152
|
+
# until we improve the validation to produce few or no false positives
|
|
153
|
+
test "when processing fact check, it is not validated" do
|
|
154
|
+
user = User.create(name: "Ben")
|
|
155
|
+
other_user = User.create(name: "James")
|
|
156
|
+
|
|
157
|
+
guide = user.create_edition(:guide, panopticon_id: FactoryGirl.create(:artefact).id, overview: "My Overview", title: "My Title", slug: "my-title", alternative_title: "My Other Title")
|
|
158
|
+
edition = guide
|
|
159
|
+
user.start_work(edition)
|
|
160
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
161
|
+
other_user.approve_review(edition, {comment: "I've reviewed it"})
|
|
162
|
+
user.send_fact_check(edition,{comment: "Review this guide please.", email_addresses: "test@test.com"})
|
|
163
|
+
user.receive_fact_check(edition, {comment: "Text.<l>content that the SafeHtml validator would catch</l>"})
|
|
164
|
+
|
|
165
|
+
assert_equal "Text.<l>content that the SafeHtml validator would catch</l>", edition.actions.last.comment
|
|
166
|
+
end
|
|
167
|
+
|
|
168
|
+
test "check counting reviews" do
|
|
169
|
+
user = User.create(name: "Ben")
|
|
170
|
+
other_user = User.create(name: "James")
|
|
171
|
+
|
|
172
|
+
guide = user.create_edition(:guide, title: "My Title", slug: "my-title", panopticon_id: @artefact.id)
|
|
173
|
+
edition = guide
|
|
174
|
+
|
|
175
|
+
assert_equal 0, guide.rejected_count
|
|
176
|
+
|
|
177
|
+
user.start_work(edition)
|
|
178
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
179
|
+
other_user.request_amendments(edition, {comment: "I've reviewed it"})
|
|
180
|
+
|
|
181
|
+
assert_equal 1, guide.rejected_count
|
|
182
|
+
|
|
183
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
184
|
+
other_user.approve_review(edition, {comment: "Looks good to me"})
|
|
185
|
+
|
|
186
|
+
assert_equal 1, guide.rejected_count
|
|
187
|
+
end
|
|
188
|
+
|
|
189
|
+
test "user should not be able to review a guide they requested review for" do
|
|
190
|
+
user = User.create(name: "Ben")
|
|
191
|
+
|
|
192
|
+
guide = user.create_edition(:guide, title: "My Title", slug: "my-title", panopticon_id: @artefact.id)
|
|
193
|
+
edition = guide
|
|
194
|
+
user.start_work(edition)
|
|
195
|
+
assert edition.can_request_review?
|
|
196
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
197
|
+
refute user.request_amendments(edition, {comment: "Well Done, but work harder"})
|
|
198
|
+
end
|
|
199
|
+
|
|
200
|
+
test "user should not be able to okay a guide they requested review for" do
|
|
201
|
+
user = User.create(name: "Ben")
|
|
202
|
+
|
|
203
|
+
guide = user.create_edition(:guide, title: "My Title", slug: "my-title", panopticon_id: @artefact.id)
|
|
204
|
+
edition = guide
|
|
205
|
+
user.start_work(edition)
|
|
206
|
+
assert edition.can_request_review?
|
|
207
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
208
|
+
refute user.approve_review(edition, "")
|
|
209
|
+
end
|
|
210
|
+
|
|
211
|
+
test "a new programme has drafts but isn't published" do
|
|
212
|
+
p = template_programme
|
|
213
|
+
assert p.draft?
|
|
214
|
+
refute p.published?
|
|
215
|
+
end
|
|
216
|
+
|
|
217
|
+
test "a programme should be marked as having reviewables if requested for review" do
|
|
218
|
+
programme = template_programme
|
|
219
|
+
user, other_user = template_users
|
|
220
|
+
|
|
221
|
+
refute programme.in_review?
|
|
222
|
+
user.request_review(programme, {comment: "Review this programme please."})
|
|
223
|
+
assert programme.in_review?, "A review was not requested for this programme."
|
|
224
|
+
end
|
|
225
|
+
|
|
226
|
+
test "programme workflow" do
|
|
227
|
+
user, other_user = template_users
|
|
228
|
+
|
|
229
|
+
edition = user.create_edition(:programme, panopticon_id: @artefact.id, title: "My title", slug: "my-slug")
|
|
230
|
+
user.start_work(edition)
|
|
231
|
+
assert edition.can_request_review?
|
|
232
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
233
|
+
refute edition.can_request_review?
|
|
234
|
+
assert edition.can_request_amendments?
|
|
235
|
+
other_user.request_amendments(edition, {comment: "I've reviewed it"})
|
|
236
|
+
refute edition.can_request_amendments?
|
|
237
|
+
user.request_review(edition,{comment: "Review this guide please."})
|
|
238
|
+
assert edition.can_approve_review?
|
|
239
|
+
other_user.approve_review(edition, {comment: "Looks good to me"})
|
|
240
|
+
assert edition.can_publish?
|
|
241
|
+
end
|
|
242
|
+
|
|
243
|
+
test "user should not be able to okay a programme they requested review for" do
|
|
244
|
+
user, other_user = template_users
|
|
245
|
+
|
|
246
|
+
edition = user.create_edition(:programme, panopticon_id: @artefact.id, title: "My title", slug: "my-slug")
|
|
247
|
+
user.start_work(edition)
|
|
248
|
+
assert edition.can_request_review?
|
|
249
|
+
user.request_review(edition,{comment: "Review this programme please."})
|
|
250
|
+
refute user.approve_review(edition, "")
|
|
251
|
+
end
|
|
252
|
+
|
|
253
|
+
test "you can only create a new edition from a published edition" do
|
|
254
|
+
user, other_user = template_users
|
|
255
|
+
edition = user.create_edition(:programme, panopticon_id: @artefact.id, title: "My title", slug: "my-slug")
|
|
256
|
+
refute edition.published?
|
|
257
|
+
refute user.new_version(edition)
|
|
258
|
+
end
|
|
259
|
+
|
|
260
|
+
test "a new edition of an answer creates a diff when published" do
|
|
261
|
+
without_metadata_denormalisation(AnswerEdition) do
|
|
262
|
+
edition_one = AnswerEdition.new(title: "Chucking wood", slug: "woodchuck", panopticon_id: @artefact.id)
|
|
263
|
+
edition_one.body = "A woodchuck would chuck all the wood he could chuck if a woodchuck could chuck wood."
|
|
264
|
+
edition_one.state = :ready
|
|
265
|
+
edition_one.save!
|
|
266
|
+
|
|
267
|
+
user = User.create name: "Michael"
|
|
268
|
+
user.publish edition_one, comment: "First edition"
|
|
269
|
+
|
|
270
|
+
edition_two = edition_one.build_clone
|
|
271
|
+
edition_two.body = "A woodchuck would chuck all the wood he could chuck if a woodchuck could chuck wood.\nAlthough no more than 361 cubic centimetres per day."
|
|
272
|
+
edition_two.state = :ready
|
|
273
|
+
edition_two.save!
|
|
274
|
+
|
|
275
|
+
user.publish edition_two, comment: "Second edition"
|
|
276
|
+
|
|
277
|
+
publish_action = edition_two.actions.where(request_type: "publish").last
|
|
278
|
+
|
|
279
|
+
assert_equal "A woodchuck would chuck all the wood he could chuck if a woodchuck could chuck wood.{+\"\\nAlthough no more than 361 cubic centimetres per day.\"}", publish_action.diff
|
|
280
|
+
end
|
|
281
|
+
end
|
|
282
|
+
|
|
283
|
+
test "handles inconsistent newlines" do
|
|
284
|
+
# Differ tries to be smart when calculating changes, by searching for a matching line
|
|
285
|
+
# later in the texts. When we have predominantly Windows-style new lines (\r\n) with
|
|
286
|
+
# a few Unix-style new lines (\n), a Unix-style new line later in one document will be
|
|
287
|
+
# matched to a Unix-style new line in the other, causing large swathes of spurious diff.
|
|
288
|
+
|
|
289
|
+
edition_one = AnswerEdition.new(title: "Chucking wood", slug: "woodchuck", panopticon_id: @artefact.id)
|
|
290
|
+
edition_one.body = "badger\n\nmushroom\r\n\r\nsnake\n\nend"
|
|
291
|
+
|
|
292
|
+
edition_two = AnswerEdition.new(title: "Chucking wood", slug: "woodchuck", panopticon_id: @artefact.id)
|
|
293
|
+
edition_two.body = "badger\r\n\r\nmushroom\r\n\r\nsnake\n\nend"
|
|
294
|
+
edition_two.stubs(:published_edition).returns(edition_one)
|
|
295
|
+
|
|
296
|
+
# Test that the diff output is simply the (normalised) string, with no diff markers
|
|
297
|
+
assert_equal "badger\n\nmushroom\n\nsnake\n\nend", edition_two.edition_changes.to_s
|
|
298
|
+
end
|
|
299
|
+
|
|
300
|
+
test "an edition can be moved into archive state" do
|
|
301
|
+
user, other_user = template_users
|
|
302
|
+
|
|
303
|
+
edition = user.create_edition(:programme, panopticon_id: @artefact.id, title: "My title", slug: "my-slug")
|
|
304
|
+
user.take_action!(edition, "archive")
|
|
305
|
+
assert_equal "archived", edition.state
|
|
306
|
+
end
|
|
307
|
+
end
|