From 16427b0aea03d09e6c3ef41b41f0144fe8b741ff Mon Sep 17 00:00:00 2001 From: Jason Frey Date: Thu, 9 Jul 2020 10:34:04 -0400 Subject: [PATCH] Add support for canonical URLs Fixes #844 --- lib/miq/ref_page.rb | 1 + lib/miq/ref_versions.rb | 7 ++++++- site/_includes/head.html | 4 ++-- site/_plugins/canonical_url.rb | 20 ++++++++++++++++++++ test/lib/miq/ref_versions_test.rb | 13 +++++++++++++ 5 files changed, 42 insertions(+), 3 deletions(-) create mode 100644 site/_plugins/canonical_url.rb diff --git a/lib/miq/ref_page.rb b/lib/miq/ref_page.rb index a06a1bac3..d1175fb6b 100644 --- a/lib/miq/ref_page.rb +++ b/lib/miq/ref_page.rb @@ -31,6 +31,7 @@ def initialize(site, base, dir, name) data['branch'] = @branch || data['doc_branch'] data['legacy'] = @legacy data['branch_paths'] = RefVersions.instance.paths_for(@source) + data['canonical_url'] = RefVersions.instance.canonical_path_for(@source) end # Only render with liquid if markdown file diff --git a/lib/miq/ref_versions.rb b/lib/miq/ref_versions.rb index 3cab359c2..33ab8c2ce 100644 --- a/lib/miq/ref_versions.rb +++ b/lib/miq/ref_versions.rb @@ -21,7 +21,12 @@ def paths_for(path) def canonical_path_for(path) recent_path = self[path].first - path_version(recent_path) == "latest" ? recent_path : nil + + # TODO: This case should not happen, but some docs do not conform to versioned docs (e.g. /api/) + # Remove this when all docs conform. + recent_path ||= path.to_s.sub(%r{/docs/reference/(?:\w+)/}, "/docs/reference/latest/") + + recent_path end private diff --git a/site/_includes/head.html b/site/_includes/head.html index 72592e244..309132509 100644 --- a/site/_includes/head.html +++ b/site/_includes/head.html @@ -7,9 +7,9 @@ {{ site.title | escape }}{% if page.title %} - {{ page.title | escape }}{% endif %} - + {% css main %} - + diff --git a/site/_plugins/canonical_url.rb b/site/_plugins/canonical_url.rb new file mode 100644 index 000000000..92c528f12 --- /dev/null +++ b/site/_plugins/canonical_url.rb @@ -0,0 +1,20 @@ +# Jekyll::Page#url is memoized on first call, but this causes issues with the +# paginator. As such, we get the URL and then remove the memoization. +def extract_page_url(page) + had_url = page.instance_variable_defined?(:@url) + page.url.tap do + page.instance_variable_set(:@url, nil) unless had_url + end +end + +Jekyll::Hooks.register :pages, :post_init do |page| + page.data['canonical_url'] ||= extract_page_url(page) +end + +Jekyll::Hooks.register :posts, :post_init do |post| + post.data['canonical_url'] ||= extract_page_url(post) +end + +Jekyll::Hooks.register :documents, :post_init do |doc| + doc.data['canonical_url'] ||= extract_page_url(doc) +end diff --git a/test/lib/miq/ref_versions_test.rb b/test/lib/miq/ref_versions_test.rb index edd77710e..219d8dfc0 100644 --- a/test/lib/miq/ref_versions_test.rb +++ b/test/lib/miq/ref_versions_test.rb @@ -26,4 +26,17 @@ def test_paths_for_with_ref_doc assert_equal "latest", paths.keys.first assert_equal "euwe", paths.keys.last end + + def test_canonical_path_for_with_ref_doc + path = Miq::RefVersions.instance.canonical_path_for("/docs/reference/latest/installing_on_google_compute_engine/index.html") + assert_equal "/docs/reference/latest/installing_on_google_compute_engine/index.html", path + + path = Miq::RefVersions.instance.canonical_path_for("/docs/reference/jansa/installing_on_google_compute_engine/index.html") + assert_equal "/docs/reference/latest/installing_on_google_compute_engine/index.html", path + end + + def test_canonical_path_for_with_legacy_ref_doc + path = Miq::RefVersions.instance.canonical_path_for("/docs/reference/ivanchuk/doc-Installing_on_Google_Compute_Engine/miq/index.html") + assert_equal "/docs/reference/latest/installing_on_google_compute_engine/index.html", path + end end