Skip to content

Commit 1083d1d

Browse files
committed
qdoc: Fix double entries for shared comment node in detailed description
If multiple API functions are documented directly under a namespace and the functions share a QDoc comment block, duplicate entries for them were generated in the detailed description - once with the correct documentation, and a second time with empty docs. This happened because Sections::stdRefPageSwitch() was indiscriminantly called for both `Summary` and `Details` sections, and that function did not check whether the node being distributed is sharing a comment (for `Details`). Extract the recurring piece of code that tests for shared comment nodes as a static helper method, and use it in all call sites doing node distribution to various sections. This makes the output for namespace reference pages more uniform with ones for classes and QML types. Add a validatedqdocoutputfiles test case with expected output. Pick-to: 6.8 Fixes: QTBUG-120186 Change-Id: If9f2d4c006c19958a4948cd3dfd395d215b6c97f Reviewed-by: Paul Wicking <[email protected]>
1 parent 4d59b4c commit 1083d1d

File tree

8 files changed

+139
-38
lines changed

8 files changed

+139
-38
lines changed

src/qdoc/qdoc/src/qdoc/sections.cpp

Lines changed: 27 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -517,16 +517,30 @@ void Sections::reduce(QList<Section> &v)
517517
section.reduce();
518518
}
519519

520+
/*!
521+
\internal
522+
523+
Returns the node to test when distributing \a node based on
524+
Node::nodeType().
525+
526+
It returns either \a node itself, or if \a node is a shared comment
527+
node, the first node in its collective.
528+
*/
529+
static Node *nodeToTestForDistribution(Node *node)
530+
{
531+
if (node && node->isSharedCommentNode() && node->hasDoc()) {
532+
if (auto *scn = static_cast<SharedCommentNode *>(node); scn->collective().size())
533+
return scn->collective().first(); // TODO: warn about mixed node types in collective?
534+
}
535+
return node;
536+
}
537+
520538
/*!
521539
This is a private helper function for buildStdRefPageSections().
522540
*/
523-
void Sections::stdRefPageSwitch(SectionVector &v, Node *n, Node *t)
541+
void Sections::stdRefPageSwitch(SectionVector &v, Node *n)
524542
{
525-
// t is the reference node to be tested, n is the node to be distributed.
526-
// t differs from n only for shared comment nodes.
527-
if (!t)
528-
t = n;
529-
543+
auto *t = nodeToTestForDistribution(n);
530544
switch (t->nodeType()) {
531545
case Node::Namespace:
532546
v[StdNamespaces].insert(n);
@@ -559,14 +573,6 @@ void Sections::stdRefPageSwitch(SectionVector &v, Node *n, Node *t)
559573
}
560574
}
561575
return;
562-
case Node::SharedComment: {
563-
auto *scn = static_cast<SharedCommentNode *>(t);
564-
if (!scn->doc().isEmpty() && scn->collective().size())
565-
stdRefPageSwitch(
566-
v, scn,
567-
scn->collective().first()); // TODO: warn about mixed node types in collective?
568-
}
569-
return;
570576
default:
571577
return;
572578
}
@@ -601,7 +607,8 @@ void Sections::buildStdRefPageSections()
601607
Node *n = *it;
602608
if (documentAll || n->hasDoc()) {
603609
stdRefPageSwitch(stdSummarySections(), n);
604-
stdRefPageSwitch(stdDetailsSections(), n);
610+
if (!n->isSharingComment())
611+
stdRefPageSwitch(stdDetailsSections(), n);
605612
}
606613
}
607614
if (!m_aggregate->relatedByProxy().isEmpty()) {
@@ -720,16 +727,7 @@ void Sections::distributeNodeInDetailsVector(SectionVector &dv, Node *n)
720727
if (n->isSharingComment())
721728
return;
722729

723-
// t is the reference node to be tested - typically it's this node (n), but for
724-
// shared comment nodes we need to distribute based on the nodes in its collective.
725-
Node *t = n;
726-
727-
if (n->isSharedCommentNode() && n->hasDoc()) {
728-
auto *scn = static_cast<SharedCommentNode *>(n);
729-
if (scn->collective().size())
730-
t = scn->collective().first(); // TODO: warn about mixed node types in collective?
731-
}
732-
730+
auto *t = nodeToTestForDistribution(n);
733731
if (t->isFunction()) {
734732
auto *fn = static_cast<FunctionNode *>(t);
735733
if (fn->isRelatedNonmember()) {
@@ -765,18 +763,10 @@ void Sections::distributeQmlNodeInDetailsVector(SectionVector &dv, Node *n)
765763
if (n->isSharingComment())
766764
return;
767765

768-
// t is the reference node to be tested - typically it's this node (n), but for
769-
// shared comment nodes we need to distribute based on the nodes in its collective.
770-
Node *t = n;
771-
772-
if (n->isSharedCommentNode() && n->hasDoc()) {
773-
if (n->isPropertyGroup()) {
774-
dv[QmlProperties].insert(n);
775-
return;
776-
}
777-
auto *scn = static_cast<SharedCommentNode *>(n);
778-
if (scn->collective().size())
779-
t = scn->collective().first(); // TODO: warn about mixed node types in collective?
766+
auto *t = nodeToTestForDistribution(n);
767+
if (t != n && n->isPropertyGroup()) {
768+
dv[QmlProperties].insert(n);
769+
return;
780770
}
781771

782772
if (t->isQmlProperty()) {

src/qdoc/qdoc/src/qdoc/sections.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ class Sections
181181
[[nodiscard]] Aggregate *aggregate() const { return m_aggregate; }
182182

183183
private:
184-
void stdRefPageSwitch(SectionVector &v, Node *n, Node *t = nullptr);
184+
void stdRefPageSwitch(SectionVector &v, Node *n);
185185
void distributeNodeInSummaryVector(SectionVector &sv, Node *n);
186186
void distributeNodeInDetailsVector(SectionVector &dv, Node *n);
187187
void distributeQmlNodeInDetailsVector(SectionVector &dv, Node *n);
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="utf-8">
5+
<!-- test.cpp -->
6+
<title>SharedCommentsInNamespace</title>
7+
</head>
8+
<body>
9+
<div class="sidebar">
10+
<div class="toc">
11+
<h3 id="toc">Contents</h3>
12+
<ul>
13+
<li class="level1"><a href="#details">Detailed Description</a></li>
14+
</ul>
15+
</div>
16+
<div class="sidebar-content" id="sidebar-content"></div></div>
17+
<h2 id="namespaces">Namespaces</h2>
18+
<div class="table"><table class="annotated">
19+
<tr class="odd topAlign"><td class="tblName" translate="no"><p><a href="test.html">Test</a></p></td></tr>
20+
</table></div>
21+
<!-- $$$Mod-description -->
22+
<div class="descr" id="details">
23+
</div>
24+
<!-- @@@Mod -->
25+
</body>
26+
</html>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<!DOCTYPE QDOCINDEX>
3+
<INDEX url="" title="SharedCommentsInNamespace Reference Documentation" version="" project="SharedCommentsInNamespace">
4+
<namespace name="" status="active" access="public" module="sharedcommentsinnamespace">
5+
<namespace name="Test" href="test.html" status="active" access="public" location="test.h" documented="true" module="Mod">
6+
<function name="bar" fullname="Test::bar" href="test.html#bar" status="active" access="public" location="test.h" documented="true" meta="plain" type="void" signature="void bar()"/>
7+
<function name="foo" fullname="Test::foo" href="test.html#foo" status="active" access="public" location="test.h" documented="true" meta="plain" type="void" signature="void foo()"/>
8+
</namespace>
9+
<module name="Mod" href="mod-module.html" status="active" documented="true" seen="true" title=""/>
10+
</namespace>
11+
</INDEX>
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="utf-8">
5+
<!-- test.cpp -->
6+
<title>Test Namespace | SharedCommentsInNamespace</title>
7+
</head>
8+
<body>
9+
<div class="sidebar">
10+
<div class="toc">
11+
<h3 id="toc">Contents</h3>
12+
<ul>
13+
<li class="level1"><a href="#functions">Functions</a></li>
14+
<li class="level1"><a href="#details">Detailed Description</a></li>
15+
</ul>
16+
</div>
17+
<div class="sidebar-content" id="sidebar-content"></div></div>
18+
<h1 class="title" translate="no">Test Namespace</h1>
19+
<div class="table"><table class="alignedsummary requisites" translate="no">
20+
<tr><td class="memItemLeft rightAlign topAlign"> Header:</td><td class="memItemRight bottomAlign"> <code translate="no">#include &lt;Test&gt;</code></td></tr>
21+
</table></div>
22+
<h2 id="functions">Functions</h2>
23+
<div class="table"><table class="alignedsummary" translate="no">
24+
<tr><td class="memItemLeft rightAlign topAlign"> </td><td class="memItemRight bottomAlign"><b></b></td></tr>
25+
<tr><td class="memItemLeft rightAlign topAlign"> void </td><td class="memItemRight bottomAlign"><b><a href="test.html#bar" translate="no">bar</a></b>()</td></tr>
26+
<tr><td class="memItemLeft rightAlign topAlign"> void </td><td class="memItemRight bottomAlign"><b><a href="test.html#foo" translate="no">foo</a></b>()</td></tr>
27+
</table></div>
28+
<!-- $$$Test-description -->
29+
<div class="descr">
30+
<h2 id="details">Detailed Description</h2>
31+
</div>
32+
<!-- @@@Test -->
33+
<div class="func">
34+
<h2>Function Documentation</h2>
35+
<!-- $$$ -->
36+
<div class="fngroup">
37+
<h3 class="fn fngroupitem" translate="no" id="bar"><span class="type">void</span> Test::<span class="name">bar</span>()</h3><h3 class="fn fngroupitem" translate="no" id="foo"><span class="type">void</span> Test::<span class="name">foo</span>()</h3></div>
38+
<p>Two functions sharing a doc comment.</p>
39+
<!-- @@@ -->
40+
</div>
41+
</body>
42+
</html>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
project = SharedCommentsInNamespace
2+
3+
{sourcedirs,headerdirs} = ./src
4+
5+
locationinfo = false
6+
warninglimit = 0
7+
warninglimit.enabled = true
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// Copyright (C) 2024 The Qt Company Ltd.
2+
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0
3+
4+
#include "test.h"
5+
6+
/*! \module Mod */
7+
/*! \namespace Test
8+
\inmodule Mod
9+
*/
10+
namespace Test {
11+
/*!
12+
\fn void foo()
13+
\fn void bar()
14+
15+
Two functions sharing a doc comment.
16+
*/
17+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// Copyright (C) 2024 The Qt Company Ltd.
2+
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0
3+
#pragma once
4+
5+
namespace Test {
6+
void foo(){}
7+
void bar(){}
8+
}

0 commit comments

Comments
 (0)