Skip to content

Commit

Permalink
Use breadcrumbs based on organisation if no parent
Browse files Browse the repository at this point in the history
Use breadcrumbs based on ancestors, if the document has a linked parent.
Otherwise use breadcrumbs based on the first normal
(non-world) organisation the page is linked to.
If there are no linked organisations use taxon based breadcrumbs,
or if taxons are also not linked to,
the default breadcrumbs pointing to the homepage.
  • Loading branch information
unoduetre committed Sep 27, 2024
1 parent f8d8c29 commit 69a27bc
Show file tree
Hide file tree
Showing 10 changed files with 268 additions and 1 deletion.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
## Unreleased

* Update accessibility criteria in component docs ([PR #4242](https://github.com/alphagov/govuk_publishing_components/pull/4242))
* Use the first organisation to generate breadcrumbs, if no parent linked ([PR #4270](https://github.com/alphagov/govuk_publishing_components/pull/4270))

## 43.5.0

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,12 @@ body: |
This is a complex component that calls other components. For more accurate
preview with real data, see the [contextual navigation preview][preview].
There are 3 main variants of the component:
There are 4 main variants of the component:
- Step by step, which uses the [step by step header][header]
- Parent breadcrumb, which uses the `parent` link of the page with the [breadcrumbs component][breadcrumbs]
- Taxon breadcrumb, which uses the `taxons` link of the page with the [breadcrumbs component][breadcrumbs]
- Organisation breadcrumb, which uses the `organisations` link of the page with the [breadcrumbs component][breadcrumbs]
It must always used [together with the contextual sidebar][sidebar] and [footer].
Expand Down
1 change: 1 addition & 0 deletions lib/govuk_publishing_components.rb
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
require "govuk_publishing_components/presenters/page_with_step_by_step_navigation"
require "govuk_publishing_components/presenters/public_layout_helper"
require "govuk_publishing_components/presenters/content_breadcrumbs_based_on_ancestors"
require "govuk_publishing_components/presenters/content_breadcrumbs_based_on_organisations"
require "govuk_publishing_components/presenters/content_breadcrumbs_based_on_taxons"
require "govuk_publishing_components/presenters/checkboxes_helper"
require "govuk_publishing_components/presenters/select_helper"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,11 @@ def options(navigation)
step_by_step: false,
breadcrumbs: navigation.breadcrumbs,
}
elsif navigation.content_is_a_corporate_information_page? && navigation.content_has_related_organisations?
{
step_by_step: false,
breadcrumbs: navigation.organisation_breadcrumbs,
}
elsif navigation.use_taxon_breadcrumbs?
{
step_by_step: false,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
module GovukPublishingComponents
module Presenters
# @private
class ContentBreadcrumbsBasedOnOrganisations
def self.call(content_item)
new(content_item).breadcrumbs
end

def initialize(content_item)
@content_item = ContentItem.new(content_item)
end

def breadcrumbs
[
{ title: "Home", url: "/" },
*organisation_breadcrumbs_items,
]
end

private

attr_reader :content_item

def organisation_breadcrumbs_items
first_related_organisation = ContentItem.new(content_item.related_organisations.first)
return [] unless first_related_organisation.present?

[{
title: first_related_organisation.title,
url: first_related_organisation.base_path,
}]
end
end
end
end
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,10 @@ def taxon_breadcrumbs
@taxon_breadcrumbs ||= ContentBreadcrumbsBasedOnTaxons.call(content_item)
end

def organisation_breadcrumbs
@organisation_breadcrumbs ||= ContentBreadcrumbsBasedOnOrganisations.call(content_item)
end

def breadcrumbs
breadcrumbs_based_on_ancestors
end
Expand Down Expand Up @@ -72,6 +76,10 @@ def content_has_curated_related_items?
content_item.dig("links", "ordered_related_items").present? && content_item.dig("links", "parent").present?
end

def content_has_related_organisations?
ContentItem.new(content_item).related_organisations.present?
end

def content_is_tagged_to_a_live_taxon?
content_item.dig("links", "taxons").to_a.any? { |taxon| taxon["phase"] == "live" }
end
Expand All @@ -80,6 +88,10 @@ def content_is_a_specialist_document?
content_item["schema_name"] == "specialist_document"
end

def content_is_a_corporate_information_page?
content_item["schema_name"] == "corporate_information_page"
end

def content_is_a_html_publication?
content_item["document_type"] == "html_publication"
end
Expand Down
15 changes: 15 additions & 0 deletions spec/components/contextual_breadcrumbs_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,21 @@ def set_live_taxons(content_item)
assert_select ".gem-c-breadcrumbs.gem-c-breadcrumbs--inverse"
end

it "renders parent-based breadcrumbs if the content item is a corporate information page with a parent" do
content_item = example_document_for("corporate_information_page", "corporate_information_page_complaints")
render_component(content_item:)
assert_select "a", text: "Home"
assert_select "a", text: "Department of Health"
assert_select "a", text: "About us"
end

it "renders organisation breadcrumbs if the content item is a corporate information page with no parent but with a linked organisation" do
content_item = example_document_for("corporate_information_page", "best-practice-about-page")
render_component(content_item:)
assert_select "a", text: "Home"
assert_select "a", text: "Intellectual Property Office"
end

it "renders no taxon breadcrumbs if they are not live" do
content_item = example_document_for("guide", "guide")
content_item = remove_mainstream_browse(content_item)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
require "spec_helper"

RSpec.describe GovukPublishingComponents::Presenters::BreadcrumbSelector do
subject do
described_class.new(
content_item,
request,
prioritise_taxon_breadcrumbs,
disable_ga4,
)
end
let(:example) { ["guide", "guide"] }
let(:content_item) { GovukSchemas::Example.find(example.first, example_name: example.second) }
let(:path) { content_item["base_path"] }
let(:query_parameters) { {} }
let(:request) { instance_double("ActionDispatch::Request", path:, query_parameters:) }
let(:prioritise_taxon_breadcrumbs) { false }
let(:disable_ga4) { false }

describe "#initialize" do
it "does not raise exception" do
expect { subject }.not_to raise_error
end
end

describe "#breadcrumbs" do
context "when content item is corporate information page with parent" do
let(:example) { ["corporate_information_page", "corporate_information_page_complaints"] }

it "returns breadcrumbs based on ancestors" do
expect(subject.breadcrumbs).to eq([
{ title: "Home", url: "/" },
{ title: "Department of Health", url: "/government/organisations/department-of-health" },
{ title: "About us", url: "/government/organisations/department-of-health/about" },
])
end
end

context "when content item is corporate information page without parent but with organisation" do
let(:example) { ["corporate_information_page", "best-practice-about-page"] }

it "returns breadcrumbs based on organisation" do
expect(subject.breadcrumbs).to eq([
{ title: "Home", url: "/" },
{ title: "Intellectual Property Office", url: "/government/organisations/intellectual-property-office" },
])
end
end

context "when content item is corporate information page without parent, organisations but with taxon" do
let(:content_item) do
item = GovukSchemas::Example.find(
"corporate_information_page",
example_name: "best-practice-about-page",
)
item = item.deep_dup
item.dig("links", "organisations").clear
item["links"]["taxons"] = [{
"base_path" => "/corporate-information",
"title" => "Corporate information",
"phase" => "live",
}]
item
end

it "returns breadcrumbs based on taxons" do
expect(subject.breadcrumbs).to eq([
{ title: "Home", url: "/", is_page_parent: false },
{ title: "Corporate information", url: "/corporate-information", is_page_parent: true },
])
end
end

context "when content item is corporate information page without parent, organisations and taxons" do
let(:content_item) do
item = GovukSchemas::Example.find(
"corporate_information_page",
example_name: "best-practice-about-page",
)
item = item.deep_dup
item.dig("links", "organisations").clear
item
end

it "returns default breadcrumbs" do
expect(subject.breadcrumbs).to eq([
{ title: "Home", url: "/" },
])
end
end
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
require "spec_helper"

RSpec.describe GovukPublishingComponents::Presenters::ContentBreadcrumbsBasedOnOrganisations do
subject { described_class.new(content_item) }
let(:content_item) { GovukSchemas::Example.find("document_collection", example_name: "document_collection") }

describe "#initialize" do
it "does not raise exception" do
expect { subject }.not_to raise_error
end
end

describe "#breadcrumbs" do
it "returns breadcrumbs based on organisation" do
expect(subject.breadcrumbs).to eq([
{ title: "Home", url: "/" },
{
title: "Driver and Vehicle Standards Agency",
url: "/government/organisations/driver-and-vehicle-standards-agency",
},
])
end
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
require "spec_helper"

RSpec.describe GovukPublishingComponents::Presenters::ContextualNavigation do
subject { described_class.new(content_item, request) }
let(:content_item) { GovukSchemas::Example.find("guide", example_name: "guide") }
let(:path) { content_item["base_path"] }
let(:query_parameters) { {} }
let(:request) { instance_double("ActionDispatch::Request", path:, query_parameters:) }

describe "#initialize" do
it "does not raise exception" do
expect { subject }.not_to raise_error
end
end

describe "#organisation_breadcrumbs" do
it "calls ContentBreadcrumbsBasedOnOrganisation" do
called_class = GovukPublishingComponents::Presenters::ContentBreadcrumbsBasedOnOrganisations
expect(called_class).to receive(:call)
.with(content_item)
.and_return([])
subject.organisation_breadcrumbs
end
end

describe "#content_has_related_organisations?" do
context "when content item is linked to no organisations" do
let(:content_item) do
GovukSchemas::Example.find(
"homepage",
example_name: "homepage_with_popular_links_on_govuk",
)
end

it "returns false" do
expect(subject.content_has_related_organisations?).to be(false)
end
end

context "when content item is only linked to world organisations" do
let(:content_item) do
GovukSchemas::Example.find(
"worldwide_corporate_information_page",
example_name: "worldwide_corporate_information_page",
)
end

it "returns false" do
expect(subject.content_has_related_organisations?).to be(false)
end
end

context "when content item is linked to at least 1 normal organisation" do
let(:content_item) { GovukSchemas::Example.find("document_collection", example_name: "document_collection") }

it "returns true" do
expect(subject.content_has_related_organisations?).to be(true)
end
end
end

describe "#content_is_a_corporate_information_page?" do
context "when content item is corporate information page" do
let(:content_item) do
GovukSchemas::Example.find("corporate_information_page", example_name: "corporate_information_page")
end

it "returns true" do
expect(subject.content_is_a_corporate_information_page?).to be(true)
end
end

context "when content item is not corporate information page" do
let(:content_item) { GovukSchemas::Example.find("guide", example_name: "guide") }

it "returns false" do
expect(subject.content_is_a_corporate_information_page?).to be(false)
end
end
end
end

0 comments on commit 69a27bc

Please sign in to comment.