Skip to content

Commit 47216a8

Browse files
committed
Expand javadoc links to include packages
Update javadoc links to include package references when relevant. The packages are used to populate `javadoc-location-*` attributes that the Asciidoctor javadoc extension can use. See gh-41614
1 parent 317d943 commit 47216a8

File tree

9 files changed

+249
-173
lines changed

9 files changed

+249
-173
lines changed

buildSrc/src/main/java/org/springframework/boot/build/antora/AntoraAsciidocAttributes.java

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -175,10 +175,21 @@ private void addUrlJava(Map<String, String> attributes) {
175175
private void addUrlLibraryLinkAttributes(Map<String, String> attributes) {
176176
this.libraries.forEach((library) -> {
177177
String prefix = "url-" + library.getLinkRootName() + "-";
178-
library.getLinks().forEach((name, link) -> attributes.put(prefix + name, link));
178+
library.getLinks().forEach((name, link) -> {
179+
String linkName = prefix + name;
180+
attributes.put(linkName, link.url(library));
181+
link.packages()
182+
.stream()
183+
.map(this::packageAttributeName)
184+
.forEach((packageAttributeName) -> attributes.put(packageAttributeName, "{" + linkName + "}"));
185+
});
179186
});
180187
}
181188

189+
private String packageAttributeName(String packageName) {
190+
return "javadoc-location-" + packageName.replace('.', '-');
191+
}
192+
182193
private void addPropertyAttributes(Map<String, String> attributes) {
183194
Properties properties = new Properties() {
184195

buildSrc/src/main/java/org/springframework/boot/build/bom/BomExtension.java

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@
6161
import org.springframework.boot.build.bom.Library.Exclusion;
6262
import org.springframework.boot.build.bom.Library.Group;
6363
import org.springframework.boot.build.bom.Library.LibraryVersion;
64+
import org.springframework.boot.build.bom.Library.Link;
6465
import org.springframework.boot.build.bom.Library.Module;
6566
import org.springframework.boot.build.bom.Library.ProhibitedVersion;
6667
import org.springframework.boot.build.bom.Library.VersionAlignment;
@@ -255,7 +256,7 @@ public static class LibraryHandler {
255256

256257
private String linkRootName;
257258

258-
private final Map<String, Function<LibraryVersion, String>> links = new HashMap<>();
259+
private final Map<String, Link> links = new HashMap<>();
259260

260261
@Inject
261262
public LibraryHandler(Project project, String version) {
@@ -458,7 +459,7 @@ public void managedBy(String managedBy) {
458459

459460
public static class LinksHandler {
460461

461-
private final Map<String, Function<LibraryVersion, String>> links = new HashMap<>();
462+
private final Map<String, Link> links = new HashMap<>();
462463

463464
public void site(String linkTemplate) {
464465
site(asFactory(linkTemplate));
@@ -488,10 +489,18 @@ public void javadoc(String linkTemplate) {
488489
javadoc(asFactory(linkTemplate));
489490
}
490491

492+
public void javadoc(String linkTemplate, String... packages) {
493+
javadoc(asFactory(linkTemplate), packages);
494+
}
495+
491496
public void javadoc(Function<LibraryVersion, String> linkFactory) {
492497
add("javadoc", linkFactory);
493498
}
494499

500+
public void javadoc(Function<LibraryVersion, String> linkFactory, String... packages) {
501+
add("javadoc", linkFactory, packages);
502+
}
503+
495504
public void releaseNotes(String linkTemplate) {
496505
releaseNotes(asFactory(linkTemplate));
497506
}
@@ -505,7 +514,11 @@ public void add(String name, String linkTemplate) {
505514
}
506515

507516
public void add(String name, Function<LibraryVersion, String> linkFactory) {
508-
this.links.put(name, linkFactory);
517+
add(name, linkFactory, null);
518+
}
519+
520+
public void add(String name, Function<LibraryVersion, String> linkFactory, String[] packages) {
521+
this.links.put(name, new Link(linkFactory, (packages != null) ? List.of(packages) : null));
509522
}
510523

511524
private Function<LibraryVersion, String> asFactory(String linkTemplate) {

buildSrc/src/main/java/org/springframework/boot/build/bom/CheckLinks.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ void releaseNotes() {
6262
library.getLinks().forEach((name, link) -> {
6363
URI uri;
6464
try {
65-
uri = new URI(link);
65+
uri = new URI(link.url(library));
6666
ResponseEntity<String> response = restTemplate.exchange(uri, HttpMethod.HEAD, null, String.class);
6767
System.out.printf("[%3d] %s - %s (%s)%n", response.getStatusCode().value(), library.getName(), name,
6868
uri);

buildSrc/src/main/java/org/springframework/boot/build/bom/Library.java

Lines changed: 47 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,9 @@
2727
import java.util.Set;
2828
import java.util.TreeMap;
2929
import java.util.function.Function;
30+
import java.util.regex.Matcher;
31+
import java.util.regex.Pattern;
32+
import java.util.stream.Stream;
3033

3134
import org.apache.maven.artifact.versioning.DefaultArtifactVersion;
3235
import org.apache.maven.artifact.versioning.VersionRange;
@@ -65,7 +68,7 @@ public class Library {
6568

6669
private final String linkRootName;
6770

68-
private final Map<String, Function<LibraryVersion, String>> links;
71+
private final Map<String, Link> links;
6972

7073
/**
7174
* Create a new {@code Library} with the given {@code name}, {@code version}, and
@@ -86,7 +89,7 @@ public class Library {
8689
*/
8790
public Library(String name, String calendarName, LibraryVersion version, List<Group> groups,
8891
List<ProhibitedVersion> prohibitedVersions, boolean considerSnapshots, VersionAlignment versionAlignment,
89-
String alignsWithBom, String linkRootName, Map<String, Function<LibraryVersion, String>> links) {
92+
String alignsWithBom, String linkRootName, Map<String, Link> links) {
9093
this.name = name;
9194
this.calendarName = (calendarName != null) ? calendarName : name;
9295
this.version = version;
@@ -98,7 +101,7 @@ public Library(String name, String calendarName, LibraryVersion version, List<Gr
98101
this.versionAlignment = versionAlignment;
99102
this.alignsWithBom = alignsWithBom;
100103
this.linkRootName = (linkRootName != null) ? linkRootName : generateLinkRootName(name);
101-
this.links = Collections.unmodifiableMap(links);
104+
this.links = Collections.unmodifiableMap(new TreeMap<>(links));
102105
}
103106

104107
private static String generateLinkRootName(String name) {
@@ -145,14 +148,17 @@ public String getAlignsWithBom() {
145148
return this.alignsWithBom;
146149
}
147150

148-
public Map<String, String> getLinks() {
149-
return getLinks(this.version);
151+
public Map<String, Link> getLinks() {
152+
return this.links;
150153
}
151154

152-
public Map<String, String> getLinks(LibraryVersion version) {
153-
Map<String, String> links = new TreeMap<>();
154-
this.links.forEach((name, linkFactory) -> links.put(name, linkFactory.apply(version)));
155-
return Collections.unmodifiableMap(links);
155+
public String getLinkUrl(String name) {
156+
Link link = getLink(name);
157+
return (link != null) ? link.url(this) : null;
158+
}
159+
160+
public Link getLink(String name) {
161+
return this.links.get(name);
156162
}
157163

158164
/**
@@ -518,4 +524,36 @@ public String toString() {
518524

519525
}
520526

527+
public static record Link(Function<LibraryVersion, String> factory, List<String> packages) {
528+
529+
private static final Pattern PACKAGE_EXPAND = Pattern.compile("^(.*)\\[(.*)\\]$");
530+
531+
public Link {
532+
packages = (packages != null) ? List.copyOf(expandPackages(packages)) : Collections.emptyList();
533+
}
534+
535+
private static List<String> expandPackages(List<String> packages) {
536+
return packages.stream().flatMap(Link::expandPackage).toList();
537+
}
538+
539+
private static Stream<String> expandPackage(String packageName) {
540+
Matcher matcher = PACKAGE_EXPAND.matcher(packageName);
541+
if (!matcher.matches()) {
542+
return Stream.of(packageName);
543+
}
544+
String root = matcher.group(1);
545+
String[] suffixes = matcher.group(2).split("\\|");
546+
return Stream.of(suffixes).map((suffix) -> root + suffix);
547+
}
548+
549+
public String url(Library library) {
550+
return url(library.getVersion());
551+
}
552+
553+
public String url(LibraryVersion libraryVersion) {
554+
return factory().apply(libraryVersion);
555+
}
556+
557+
}
558+
521559
}

buildSrc/src/main/java/org/springframework/boot/build/bom/bomr/MoveToSnapshots.java

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -80,11 +80,12 @@ private String description(Upgrade upgrade) {
8080

8181
@Override
8282
protected String issueBody(Upgrade upgrade, Issue existingUpgrade) {
83-
String releaseNotes = upgrade.getLibrary().getLinks().get("releaseNotes");
83+
Library library = upgrade.getLibrary();
84+
String releaseNotesLink = library.getLinkUrl("releaseNotes");
8485
List<String> lines = new ArrayList<>();
8586
String description = description(upgrade);
86-
if (releaseNotes != null) {
87-
lines.add("Upgrade to [%s](%s).".formatted(description, releaseNotes));
87+
if (releaseNotesLink != null) {
88+
lines.add("Upgrade to [%s](%s).".formatted(description, releaseNotesLink));
8889
}
8990
lines.add("Upgrade to %s.".formatted(description));
9091
if (existingUpgrade != null) {

buildSrc/src/main/java/org/springframework/boot/build/bom/bomr/UpgradeBom.java

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828

2929
import org.springframework.boot.build.bom.BomExtension;
3030
import org.springframework.boot.build.bom.Library.LibraryVersion;
31+
import org.springframework.boot.build.bom.Library.Link;
3132
import org.springframework.boot.build.bom.bomr.github.Issue;
3233
import org.springframework.boot.build.properties.BuildProperties;
3334

@@ -75,13 +76,12 @@ protected String commitMessage(Upgrade upgrade, int issueNumber) {
7576

7677
@Override
7778
protected String issueBody(Upgrade upgrade, Issue existingUpgrade) {
78-
String releaseNotes = upgrade.getLibrary()
79-
.getLinks(new LibraryVersion(upgrade.getVersion()))
80-
.get("releaseNotes");
79+
LibraryVersion upgradeVersion = new LibraryVersion(upgrade.getVersion());
80+
String releaseNotesLink = getReleaseNotesLink(upgrade, upgradeVersion);
8181
List<String> lines = new ArrayList<>();
82-
String description = upgrade.getLibrary().getName() + " " + upgrade.getVersion();
83-
if (releaseNotes != null) {
84-
lines.add("Upgrade to [%s](%s).".formatted(description, releaseNotes));
82+
String description = upgrade.getLibrary().getName() + " " + upgradeVersion;
83+
if (releaseNotesLink != null) {
84+
lines.add("Upgrade to [%s](%s).".formatted(description, releaseNotesLink));
8585
}
8686
else {
8787
lines.add("Upgrade to %s.".formatted(description));
@@ -92,4 +92,9 @@ protected String issueBody(Upgrade upgrade, Issue existingUpgrade) {
9292
return String.join("\\r\\n\\r\\n", lines);
9393
}
9494

95+
private String getReleaseNotesLink(Upgrade upgrade, LibraryVersion upgradeVersion) {
96+
Link releaseNotesLink = upgrade.getLibrary().getLink("releaseNotes");
97+
return releaseNotesLink.url(upgradeVersion);
98+
}
99+
95100
}

buildSrc/src/test/java/org/springframework/boot/build/antora/AntoraAsciidocAttributesTests.java

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,13 +21,13 @@
2121
import java.util.LinkedHashMap;
2222
import java.util.List;
2323
import java.util.Map;
24-
import java.util.function.Function;
2524

2625
import org.junit.jupiter.api.Test;
2726

2827
import org.springframework.boot.build.bom.Library;
2928
import org.springframework.boot.build.bom.Library.Group;
3029
import org.springframework.boot.build.bom.Library.LibraryVersion;
30+
import org.springframework.boot.build.bom.Library.Link;
3131
import org.springframework.boot.build.bom.Library.ProhibitedVersion;
3232
import org.springframework.boot.build.bom.Library.VersionAlignment;
3333
import org.springframework.boot.build.bom.bomr.version.DependencyVersion;
@@ -187,14 +187,20 @@ void artifactReleaseTypeWhenCommercialSnapshot() {
187187

188188
@Test
189189
void urlLinksFromLibrary() {
190-
Map<String, Function<LibraryVersion, String>> links = new LinkedHashMap<>();
191-
links.put("site", (version) -> "https://example.com/site/" + version);
192-
links.put("docs", (version) -> "https://example.com/docs/" + version);
190+
Map<String, Link> links = new LinkedHashMap<>();
191+
links.put("site", new Link((version) -> "https://example.com/site/" + version, null));
192+
links.put("docs", new Link((version) -> "https://example.com/docs/" + version, null));
193+
links.put("javadoc", new Link((version) -> "https://example.com/api/" + version,
194+
List.of("org.springframework.[core|util]")));
193195
Library library = mockLibrary(links);
194196
AntoraAsciidocAttributes attributes = new AntoraAsciidocAttributes("1.2.3.1-SNAPSHOT", false,
195197
BuildType.OPEN_SOURCE, List.of(library), mockDependencyVersions(), null);
196198
assertThat(attributes.get()).containsEntry("url-spring-framework-site", "https://example.com/site/1.2.3")
197-
.containsEntry("url-spring-framework-docs", "https://example.com/docs/1.2.3");
199+
.containsEntry("url-spring-framework-docs", "https://example.com/docs/1.2.3")
200+
.containsEntry("url-spring-framework-javadoc", "https://example.com/api/1.2.3");
201+
assertThat(attributes.get())
202+
.containsEntry("javadoc-location-org-springframework-core", "{url-spring-framework-javadoc}")
203+
.containsEntry("javadoc-location-org-springframework-util", "{url-spring-framework-javadoc}");
198204
}
199205

200206
@Test
@@ -209,7 +215,7 @@ null, mockDependencyVersions(), null)
209215
assertThat(keys.indexOf("include-java")).isLessThan(keys.indexOf("code-spring-boot-latest"));
210216
}
211217

212-
private Library mockLibrary(Map<String, Function<LibraryVersion, String>> links) {
218+
private Library mockLibrary(Map<String, Link> links) {
213219
String name = "Spring Framework";
214220
String calendarName = null;
215221
LibraryVersion version = new LibraryVersion(DependencyVersion.parse("1.2.3"));

buildSrc/src/test/java/org/springframework/boot/build/bom/LibraryTests.java

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,12 @@
1919
import java.util.Collections;
2020
import java.util.List;
2121
import java.util.Map;
22-
import java.util.function.Function;
2322

2423
import org.junit.jupiter.api.Test;
2524

2625
import org.springframework.boot.build.bom.Library.Group;
2726
import org.springframework.boot.build.bom.Library.LibraryVersion;
27+
import org.springframework.boot.build.bom.Library.Link;
2828
import org.springframework.boot.build.bom.Library.ProhibitedVersion;
2929
import org.springframework.boot.build.bom.Library.VersionAlignment;
3030
import org.springframework.boot.build.bom.bomr.version.DependencyVersion;
@@ -49,7 +49,7 @@ void getLinkRootNameWhenNoneSpecified() {
4949
VersionAlignment versionAlignment = null;
5050
String alignsWithBom = null;
5151
String linkRootName = null;
52-
Map<String, Function<LibraryVersion, String>> links = Collections.emptyMap();
52+
Map<String, Link> links = Collections.emptyMap();
5353
Library library = new Library(name, calendarName, version, groups, prohibitedVersion, considerSnapshots,
5454
versionAlignment, alignsWithBom, linkRootName, links);
5555
assertThat(library.getLinkRootName()).isEqualTo("spring-framework");
@@ -66,7 +66,7 @@ void getLinkRootNameWhenSpecified() {
6666
VersionAlignment versionAlignment = null;
6767
String alignsWithBom = null;
6868
String linkRootName = "spring-data";
69-
Map<String, Function<LibraryVersion, String>> links = Collections.emptyMap();
69+
Map<String, Link> links = Collections.emptyMap();
7070
Library library = new Library(name, calendarName, version, groups, prohibitedVersion, considerSnapshots,
7171
versionAlignment, alignsWithBom, linkRootName, links);
7272
assertThat(library.getLinkRootName()).isEqualTo("spring-data");

0 commit comments

Comments
 (0)