Skip to content

Commit a23583b

Browse files
[XWI-127] Add "as parent" badge to referencing wiki pages (#23849)
Co-authored-by: Jan Sandbrink <j.sandbrink@openproject.com>
1 parent 3c89e53 commit a23583b

14 files changed

Lines changed: 315 additions & 22 deletions

File tree

modules/wikis/app/components/wikis/collapsible_page_links_component.html.erb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,8 +36,8 @@ See COPYRIGHT and LICENSE files for more details.
3636
end
3737
end
3838

39-
page_links.each do |page_link|
40-
box.with_row { render(Wikis::PageLinkComponent.new(page_link)) }
39+
page_links.each do |view_model|
40+
box.with_row { render(Wikis::PageLinkComponent.new(view_model.page_info_result, source: view_model.source)) }
4141
end
4242
end
4343
%>

modules/wikis/app/components/wikis/page_link_component.html.erb

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,11 +37,22 @@ See COPYRIGHT and LICENSE files for more details.
3737
%>
3838

3939
<%=
40-
render(Primer::Alpha::StackItem.new(grow: true, classes: "ellipsis")) do
41-
if error?
42-
render(Primer::Beta::Text.new(color: :muted)) { page_title }
43-
else
44-
render(Primer::Beta::Link.new(href: page_href, scheme: :primary, data: { allow_external_link: true })) { page_title }
40+
render(Primer::Alpha::StackItem.new(grow: true)) do
41+
render(Primer::Alpha::Stack.new(direction: :horizontal, gap: :condensed, align: :center)) do
42+
concat(
43+
render(Primer::Beta::Truncate.new) do |truncate|
44+
truncate.with_item(priority: true) do
45+
if error?
46+
render(Primer::Beta::Text.new(color: :muted)) { page_title }
47+
else
48+
render(Primer::Beta::Link.new(href: page_href, scheme: :primary, data: { allow_external_link: true })) { page_title }
49+
end
50+
end
51+
end
52+
)
53+
if badge_label.present?
54+
concat(render(Primer::Beta::Label.new(scheme: :secondary, test_selector: "wiki-page-link-source-badge")) { badge_label })
55+
end
4556
end
4657
end
4758
%>

modules/wikis/app/components/wikis/page_link_component.rb

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,15 +35,20 @@ class PageLinkComponent < ApplicationComponent
3535

3636
alias_method :page_info_result, :model
3737

38-
attr_reader :actions
38+
attr_reader :actions, :source
3939

40-
def initialize(model = nil, actions: [], page_link: nil, **)
40+
def initialize(model = nil, actions: [], page_link: nil, source: nil, **)
4141
@actions = actions
4242
@page_link = page_link
43+
@source = source
4344

4445
super(model, **)
4546
end
4647

48+
def badge_label
49+
I18n.t("wikis.page_links.source.parent") if source == :parent
50+
end
51+
4752
def page_title
4853
page_info_result.either(
4954
->(pi) { pi.title },
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
module Wikis
32+
# View model for a single row in a CollapsiblePageLinksComponent.
33+
# Mapping source -> badge label and styling is the component's concern.
34+
PageLinkViewModel = Data.define(:page_info_result, :source) do
35+
def self.from_page_reference_result(result)
36+
new(page_info_result: result.fmap(&:page_info), source: result.fmap(&:source).value_or(nil))
37+
end
38+
39+
def self.from_page_info_result(result)
40+
new(page_info_result: result, source: nil)
41+
end
42+
end
43+
end

modules/wikis/app/components/wikis/work_package_wikis_tab_component.rb

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,10 +48,12 @@ def show_inline_and_references_section?
4848

4949
def inline_page_links
5050
@inline_page_links ||= page_link_service.inline_page_link_infos_for(linkable: work_package)
51+
.map { PageLinkViewModel.from_page_info_result(it) }
5152
end
5253

5354
def referencing_wiki_pages
54-
@referencing_wiki_pages ||= page_link_service.referencing_wiki_page_infos_for(linkable: work_package)
55+
@referencing_wiki_pages ||= page_link_service.referencing_wiki_page_references_for(linkable: work_package)
56+
.map { PageLinkViewModel.from_page_reference_result(it) }
5557
end
5658

5759
private
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
# frozen_string_literal: true
2+
3+
#-- copyright
4+
# OpenProject is an open source project management software.
5+
# Copyright (C) the OpenProject GmbH
6+
#
7+
# This program is free software; you can redistribute it and/or
8+
# modify it under the terms of the GNU General Public License version 3.
9+
#
10+
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows:
11+
# Copyright (C) 2006-2013 Jean-Philippe Lang
12+
# Copyright (C) 2010-2013 the ChiliProject Team
13+
#
14+
# This program is free software; you can redistribute it and/or
15+
# modify it under the terms of the GNU General Public License
16+
# as published by the Free Software Foundation; either version 2
17+
# of the License, or (at your option) any later version.
18+
#
19+
# This program is distributed in the hope that it will be useful,
20+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
21+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22+
# GNU General Public License for more details.
23+
#
24+
# You should have received a copy of the GNU General Public License
25+
# along with this program; if not, write to the Free Software
26+
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
27+
#
28+
# See COPYRIGHT and LICENSE files for more details.
29+
#++
30+
31+
module Wikis::Adapters::Results
32+
# Pairs a PageInfo with how it relates to a given linkable.
33+
# source: :parent — page has a linkable as a parent link
34+
# source: :mention — page mentions the linkable in its content
35+
PageReference = Data.define(:page_info, :source)
36+
end

modules/wikis/app/services/wikis/adapters/providers/internal/queries/referencing_pages.rb

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,10 @@ def call(input_data:, auth_strategy:)
4040
.merge(ReverseInlinePageLink.all)
4141
.where(linkable: input_data.linkable)
4242
.order(created_at: :desc)
43-
.map { page_info(identifier: it.identifier, auth_strategy:) }
43+
.map do |link|
44+
page_info(identifier: link.identifier, auth_strategy:)
45+
.fmap { Wikis::Adapters::Results::PageReference.new(page_info: it, source: :mention) }
46+
end
4447
)
4548
end
4649
end

modules/wikis/app/services/wikis/adapters/providers/xwiki/queries/referencing_pages.rb

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,15 +47,25 @@ def call(input_data:, auth_strategy:)
4747
authenticated(auth_strategy) do |http|
4848
fetch_reference_ids(http, input_data).bind do |reference_ids|
4949
fetch_mention_ids(http, input_data).bind do |mention_ids|
50-
ids = (reference_ids + mention_ids).uniq
51-
success(ids.map { canonical_page_info(identifier: it, auth_strategy:) })
50+
mention_only_ids = mention_ids - reference_ids
51+
success(
52+
canonical_pages(reference_ids, source: :parent, auth_strategy:) +
53+
canonical_pages(mention_only_ids, source: :mention, auth_strategy:)
54+
)
5255
end
5356
end
5457
end
5558
end
5659

5760
private
5861

62+
def canonical_pages(ids, source:, auth_strategy:)
63+
ids.map do |id|
64+
canonical_page_info(identifier: id, auth_strategy:)
65+
.fmap { Wikis::Adapters::Results::PageReference.new(page_info: it, source:) }
66+
end
67+
end
68+
5969
def fetch_reference_ids(http, input_data)
6070
fetch_page_ids(http, rest_url("openproject/links/workPackages/#{input_data.linkable.id}"),
6171
params: { number: MAXIMUM_RESULTS, withInstance: instance_id })

modules/wikis/app/services/wikis/page_link_service.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ def count(linkable)
3737

3838
relation_page_links +
3939
inline_page_link_infos_for(linkable:).size +
40-
referencing_wiki_page_infos_for(linkable:).size
40+
referencing_wiki_page_references_for(linkable:).size
4141
end
4242

4343
def relation_page_links_for(provider:, linkable:)
@@ -59,7 +59,7 @@ def inline_page_link_infos_for(linkable:)
5959
.map { page_info(provider: it.provider, identifier: it.identifier) }
6060
end
6161

62-
def referencing_wiki_page_infos_for(linkable:)
62+
def referencing_wiki_page_references_for(linkable:)
6363
referenced_in = []
6464

6565
Adapters::Input::ReferencingPages.build(linkable:).bind do |input|

modules/wikis/config/locales/en.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,8 @@ en:
184184
page_access_forbidden: You do not have permission to access this wiki page
185185
page_not_found: Linked wiki page no longer available
186186
unexpected: An unexpected error occurred
187+
source:
188+
parent: As parent
187189
provider_types:
188190
xwiki:
189191
name: XWiki

0 commit comments

Comments
 (0)