govuk_content_models 29.1.1 → 29.1.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 50dc520a74843e9a3ccd9b5a0427b966711f30b5
4
- data.tar.gz: 8ba0639769f9c134d133ff996e9d2d41d4d0ed77
3
+ metadata.gz: ab1abf4484762f870e3d8e538b706e5cd426a66d
4
+ data.tar.gz: b6545c3d24622aaf2b7d912bec0612063dc7efad
5
5
  SHA512:
6
- metadata.gz: 1360728473419a672030754f02164c27f17fb790ef0acf0a1abcac89bb659680e778c6c32ecd894d5e219c65a774fe33e322d499dafd337b39e5b08b96d51ca5
7
- data.tar.gz: 7651c6ef9eef44d07dabe3ebe997179f1aa20b89d6e26b5d785a89d66e0343c1c22b8f2d699f4d57fd62740fad031cdd60c5f9f2aa7d4dccdb5184ada39f3c7c
6
+ metadata.gz: 7e6a87f32f108d5ad7fde9fbcd35a962ff99f15cc93fddb9bc72fb02e8ef3b10f7a803eb6d30c2be0da930b434a125e6313188a13509fc43041a2de2ca965be1
7
+ data.tar.gz: d264ff8d7bdca85773d58504fcd3e2e4dbafc09df865638bad3386e0715bea87e779ce8e227eca83c8b93443fd2f8d17262699afcc1ad2267b07ac8f9e237d87
data/CHANGELOG.md CHANGED
@@ -1,5 +1,9 @@
1
1
  # CHANGELOG
2
2
 
3
+ ## 29.1.2
4
+
5
+ - Bugfix: revert removal of specialist publisher code since it breaks Panopticon integration
6
+
3
7
  ## 29.1.1
4
8
 
5
9
  - Bugfix: update question options slugs when their labels are updated
@@ -37,6 +37,7 @@ class Artefact
37
37
  field "publication_id", type: String
38
38
  field "description", type: String
39
39
  field "state", type: String, default: "draft"
40
+ field "specialist_body", type: String
40
41
  field "language", type: String, default: "en"
41
42
  field "need_extended_font", type: Boolean, default: false
42
43
  field "latest_change_note", type: String
@@ -74,6 +75,17 @@ class Artefact
74
75
  "smartanswers" => ["smart-answer"],
75
76
  "custom-application" => ["custom-application"], # In this case the owning_app is overriden. eg calendars, licencefinder
76
77
  "travel-advice-publisher" => ["travel-advice"],
78
+ "specialist-publisher" => ["aaib_report",
79
+ "cma_case",
80
+ "countryside_stewardship_grant",
81
+ "drug_safety_update",
82
+ "european_structural_investment_fund",
83
+ "international_development_fund",
84
+ "maib_report",
85
+ "manual",
86
+ "medical_safety_alert",
87
+ "raib_report",
88
+ "vehicle_recalls_and_faults_alert"],
77
89
  "finder-api" => ["finder",
78
90
  "finder_email_signup"],
79
91
  "whitehall" => ["announcement",
@@ -0,0 +1,13 @@
1
+ module PrerenderedEntity
2
+ def create_or_update_by_slug!(attributes)
3
+ find_or_initialize_by(
4
+ slug: attributes.fetch(:slug)
5
+ ).tap do |doc|
6
+ doc.update_attributes!(attributes)
7
+ end
8
+ end
9
+
10
+ def find_by_slug(slug)
11
+ where(slug: slug).first
12
+ end
13
+ end
@@ -0,0 +1,17 @@
1
+ require "prerendered_entity"
2
+
3
+ class RenderedManual
4
+ include Mongoid::Document
5
+ include Mongoid::Timestamps
6
+ extend PrerenderedEntity
7
+
8
+ field :manual_id, type: String
9
+ field :slug, type: String
10
+ field :title, type: String
11
+ field :summary, type: String
12
+ field :section_groups, type: Array
13
+
14
+ index "slug", unique: true
15
+
16
+ validates_uniqueness_of :slug
17
+ end
@@ -0,0 +1,19 @@
1
+ require "prerendered_entity"
2
+
3
+ class RenderedSpecialistDocument
4
+ include Mongoid::Document
5
+ include Mongoid::Timestamps
6
+ extend PrerenderedEntity
7
+
8
+ field :slug, type: String
9
+ field :title, type: String
10
+ field :summary, type: String
11
+ field :body, type: String
12
+ field :published_at, type: DateTime
13
+
14
+ field :details, type: Hash
15
+
16
+ index "slug", unique: true
17
+
18
+ validates :slug, uniqueness: true
19
+ end
@@ -7,6 +7,8 @@ class SlugValidator < ActiveModel::EachValidator
7
7
  HelpPageValidator,
8
8
  FinderEmailSignupValidator,
9
9
  GovernmentPageValidator,
10
+ ManualPageValidator,
11
+ SpecialistDocumentPageValidator,
10
12
  BrowsePageValidator,
11
13
  DetailedGuideValidator,
12
14
  DefaultValidator
@@ -115,6 +117,63 @@ protected
115
117
  end
116
118
  end
117
119
 
120
+ class ManualPageValidator < InstanceValidator
121
+ def applicable?
122
+ of_kind?('manual')
123
+ end
124
+
125
+ def validate!
126
+ validate_number_of_parts!
127
+ validate_guidance_prefix!
128
+ validate_parts_as_slugs!
129
+ end
130
+
131
+ private
132
+ def validate_number_of_parts!
133
+ unless [2, 3].include?(url_parts.size)
134
+ record.errors[attribute] << 'must contains two or three path parts'
135
+ end
136
+ end
137
+
138
+ def validate_guidance_prefix!
139
+ unless starts_with?('guidance/')
140
+ record.errors[attribute] << 'must have a guidance/ prefix'
141
+ end
142
+ end
143
+
144
+ def validate_parts_as_slugs!
145
+ unless url_parts.all? { |url_part| valid_slug?(url_part) }
146
+ record.errors[attribute] << 'must be usable in a URL'
147
+ end
148
+ end
149
+ end
150
+
151
+ class SpecialistDocumentPageValidator < InstanceValidator
152
+ def applicable?
153
+ of_kind?(acceptable_formats)
154
+ end
155
+
156
+ def validate!
157
+ unless url_parts.size == 2
158
+ record.errors[attribute] << "must be of form <finder-slug>/<specialist-document-slug>"
159
+ end
160
+ unless url_parts.all? { |url_part| valid_slug?(url_part) }
161
+ record.errors[attribute] << "must be usable in a URL"
162
+ end
163
+ end
164
+
165
+ private
166
+ def acceptable_formats
167
+ Artefact::FORMATS_BY_DEFAULT_OWNING_APP["specialist-publisher"] - unacceptable_formats
168
+ end
169
+
170
+ def unacceptable_formats
171
+ [
172
+ "manual",
173
+ ]
174
+ end
175
+ end
176
+
118
177
  class BrowsePageValidator < InstanceValidator
119
178
  def applicable?
120
179
  of_kind?('specialist_sector')
@@ -252,6 +252,25 @@ FactoryGirl.define do
252
252
  end
253
253
  end
254
254
 
255
+ factory :rendered_specialist_document do
256
+ sequence(:slug) {|n| "test-rendered-specialist-document-#{n}" }
257
+ sequence(:title) {|n| "Test Rendered Specialist Document #{n}" }
258
+ summary "My summary"
259
+ body "<p>My body</p>"
260
+ details({
261
+ "opened_date" => "2013-04-20",
262
+ "market_sector" => "some-market-sector",
263
+ "case_type" => "a-case-type",
264
+ "case_state" => "open",
265
+ })
266
+ end
267
+
268
+ factory :rendered_manual do
269
+ sequence(:slug) {|n| "test-rendered-manual-#{n}" }
270
+ sequence(:title) {|n| "Test Rendered Manual #{n}" }
271
+ summary "My summary"
272
+ end
273
+
255
274
  factory :simple_smart_answer_edition, :parent => :edition, :class => "SimpleSmartAnswerEdition" do
256
275
  title "Simple smart answer"
257
276
  body "Introduction to the smart answer"
@@ -1,4 +1,4 @@
1
1
  module GovukContentModels
2
2
  # Changing this causes Jenkins to tag and release the gem into the wild
3
- VERSION = "29.1.1"
3
+ VERSION = "29.1.2"
4
4
  end
@@ -0,0 +1,16 @@
1
+ module SpecialistDocumentFixtures
2
+ def basic_specialist_document_fields
3
+ {
4
+ slug: 'cma-cases/merger-investigation-2014',
5
+ title: "Merger Investigation 2014",
6
+ summary: "This is the summary of stuff going on in the Merger Investigation 2014",
7
+ state: "published",
8
+ body: "A body",
9
+ opened_date: '2012-04-21',
10
+ document_id: 'a-document-id',
11
+ market_sector: 'oil-and-gas',
12
+ case_type: 'some-case-type',
13
+ case_state: 'open'
14
+ }
15
+ end
16
+ end
@@ -424,6 +424,15 @@ class ArtefactTest < ActiveSupport::TestCase
424
424
  assert artefact.any_editions_published?
425
425
  end
426
426
 
427
+ test "should have a specialist_body field present for markdown content" do
428
+ artefact = Artefact.create!(slug: "parent", name: "Harry Potter", kind: "guide", owning_app: "x")
429
+ refute_includes artefact.attributes, "specialist_body"
430
+
431
+ artefact.specialist_body = "Something wicked this way comes"
432
+ assert_includes artefact.attributes, "specialist_body"
433
+ assert_equal "Something wicked this way comes", artefact.specialist_body
434
+ end
435
+
427
436
  test "should have 'video' as a supported FORMAT" do
428
437
  assert_includes Artefact::FORMATS, "video"
429
438
  end
@@ -0,0 +1,46 @@
1
+ # include in a test class and define a #model_class instance method
2
+
3
+ module PrerenderedEntityTests
4
+ def test_duplicate_slug_not_allowed
5
+ model_class.create(slug: "my-slug")
6
+ second = model_class.create(slug: "my-slug")
7
+
8
+ refute second.valid?
9
+ assert_equal 1, model_class.count
10
+ end
11
+
12
+ def test_has_no_govspeak_fields
13
+ refute model_class.const_defined?(:GOVSPEAK_FIELDS)
14
+ end
15
+
16
+ def test_create_or_update_by_slug
17
+ slug = "a-slug"
18
+ original_body = "Original body"
19
+
20
+ version1_attrs= {
21
+ slug: slug,
22
+ body: original_body,
23
+ }
24
+
25
+ created = model_class.create_or_update_by_slug!(version1_attrs)
26
+
27
+ assert created.is_a?(model_class)
28
+ assert created.persisted?
29
+
30
+ version2_attrs = version1_attrs.merge(
31
+ body: "Updated body",
32
+ )
33
+
34
+ version2 = model_class.create_or_update_by_slug!(version2_attrs)
35
+
36
+ assert version2.persisted?
37
+ assert_equal "Updated body", version2.body
38
+ end
39
+
40
+ def test_find_by_slug
41
+ created = model_class.create!(slug: "find-by-this-slug")
42
+ found = model_class.find_by_slug("find-by-this-slug")
43
+
44
+ assert_equal created, found
45
+ end
46
+ end
@@ -0,0 +1,10 @@
1
+ require "test_helper"
2
+ require_relative "prerendered_entity_tests"
3
+
4
+ class RenderedManualTest < ActiveSupport::TestCase
5
+ include PrerenderedEntityTests
6
+
7
+ def model_class
8
+ RenderedManual
9
+ end
10
+ end
@@ -0,0 +1,12 @@
1
+ require "test_helper"
2
+ require "fixtures/specialist_document_fixtures"
3
+ require "models/prerendered_entity_tests"
4
+
5
+ class RenderedSpecialistDocumentTest < ActiveSupport::TestCase
6
+ include SpecialistDocumentFixtures
7
+ include PrerenderedEntityTests
8
+
9
+ def model_class
10
+ RenderedSpecialistDocument
11
+ end
12
+ end
@@ -76,6 +76,16 @@ class SlugTest < ActiveSupport::TestCase
76
76
  end
77
77
  end
78
78
 
79
+ context "Specialist documents" do
80
+ should "all url nested one level deep" do
81
+ assert document_with_slug("some-finder/my-specialist-document", kind: "cma_case").valid?;
82
+ end
83
+
84
+ should "not allow deeper nesting" do
85
+ refute document_with_slug("some-finder/my-specialist-document/not-allowed", kind: "cma_case").valid?
86
+ end
87
+ end
88
+
79
89
  context "Specialist sector browse pages" do
80
90
  should "allow a single path part" do
81
91
  assert document_with_slug("oil-and-gas", kind: "specialist_sector").valid?
@@ -108,4 +118,20 @@ class SlugTest < ActiveSupport::TestCase
108
118
  end
109
119
  #TODO: disallow this once guidance migration has been complete
110
120
  end
121
+
122
+ context "Manual pages" do
123
+ should "allow slugs starting guidance/" do
124
+ refute document_with_slug("manuals/a-manual", kind: "manual").valid?
125
+ assert document_with_slug("guidance/a-manual", kind: "manual").valid?
126
+ end
127
+
128
+ should "allow two or three path parts" do
129
+ refute document_with_slug("guidance", kind: "manual").valid?
130
+ assert document_with_slug("guidance/a-manual", kind: "manual").valid?
131
+ end
132
+
133
+ should "not allow invalid path segments" do
134
+ refute document_with_slug("guidance/bad.manual.slug", kind: "manual").valid?
135
+ end
136
+ end
111
137
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: govuk_content_models
3
3
  version: !ruby/object:Gem::Version
4
- version: 29.1.1
4
+ version: 29.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Paul Battley
@@ -307,7 +307,10 @@ files:
307
307
  - app/models/part.rb
308
308
  - app/models/parted.rb
309
309
  - app/models/place_edition.rb
310
+ - app/models/prerendered_entity.rb
310
311
  - app/models/programme_edition.rb
312
+ - app/models/rendered_manual.rb
313
+ - app/models/rendered_specialist_document.rb
311
314
  - app/models/simple_smart_answer_edition.rb
312
315
  - app/models/simple_smart_answer_edition/node.rb
313
316
  - app/models/simple_smart_answer_edition/node/option.rb
@@ -357,6 +360,7 @@ files:
357
360
  - lib/govuk_content_models/version.rb
358
361
  - lib/mongoid/monkey_patches.rb
359
362
  - test/fixtures/contactotron_api_response.json
363
+ - test/fixtures/specialist_document_fixtures.rb
360
364
  - test/fixtures/uploads/image.jpg
361
365
  - test/models/action_test.rb
362
366
  - test/models/artefact_action_test.rb
@@ -384,6 +388,9 @@ files:
384
388
  - test/models/local_transaction_edition_test.rb
385
389
  - test/models/overview_dashboard_test.rb
386
390
  - test/models/parted_test.rb
391
+ - test/models/prerendered_entity_tests.rb
392
+ - test/models/rendered_manual_test.rb
393
+ - test/models/rendered_specialist_document_test.rb
387
394
  - test/models/simple_smart_answer_edition_test.rb
388
395
  - test/models/simple_smart_answer_node_test.rb
389
396
  - test/models/simple_smart_answer_option_test.rb
@@ -429,6 +436,7 @@ specification_version: 4
429
436
  summary: Shared models for Panopticon and Publisher, as a Rails Engine
430
437
  test_files:
431
438
  - test/fixtures/contactotron_api_response.json
439
+ - test/fixtures/specialist_document_fixtures.rb
432
440
  - test/fixtures/uploads/image.jpg
433
441
  - test/models/action_test.rb
434
442
  - test/models/artefact_action_test.rb
@@ -456,6 +464,9 @@ test_files:
456
464
  - test/models/local_transaction_edition_test.rb
457
465
  - test/models/overview_dashboard_test.rb
458
466
  - test/models/parted_test.rb
467
+ - test/models/prerendered_entity_tests.rb
468
+ - test/models/rendered_manual_test.rb
469
+ - test/models/rendered_specialist_document_test.rb
459
470
  - test/models/simple_smart_answer_edition_test.rb
460
471
  - test/models/simple_smart_answer_node_test.rb
461
472
  - test/models/simple_smart_answer_option_test.rb