diff --git a/backend/src/main/java/io/papermc/hangar/model/api/project/version/Version.java b/backend/src/main/java/io/papermc/hangar/model/api/project/version/Version.java index 80795db82..a40e9ceec 100644 --- a/backend/src/main/java/io/papermc/hangar/model/api/project/version/Version.java +++ b/backend/src/main/java/io/papermc/hangar/model/api/project/version/Version.java @@ -6,6 +6,7 @@ import io.papermc.hangar.model.common.projects.Visibility; import java.time.OffsetDateTime; import java.util.EnumMap; +import java.util.List; import java.util.Map; import java.util.Set; import org.jdbi.v3.core.enums.EnumByOrdinal; @@ -16,7 +17,7 @@ public class Version extends VersionCompact { private final Map> pluginDependencies = new EnumMap<>(Platform.class); private final Map> platformDependencies = new EnumMap<>(Platform.class); - private final Map platformDependenciesFormatted = new EnumMap<>(Platform.class); + private final Map> platformDependenciesFormatted = new EnumMap<>(Platform.class); public Version(final OffsetDateTime createdAt, @ColumnName("version_string") final String name, final Visibility visibility, final String description, @Nested("vs") final VersionStats stats, final String author, @EnumByOrdinal final ReviewState reviewState, @Nested("pc") final ProjectChannel channel, final PinnedStatus pinnedStatus) { super(createdAt, name, visibility, description, stats, author, reviewState, channel, pinnedStatus); @@ -30,7 +31,7 @@ public Map> getPlatformDependencies() { return this.platformDependencies; } - public Map getPlatformDependenciesFormatted() { + public Map> getPlatformDependenciesFormatted() { return this.platformDependenciesFormatted; } diff --git a/backend/src/main/java/io/papermc/hangar/model/internal/projects/HangarProject.java b/backend/src/main/java/io/papermc/hangar/model/internal/projects/HangarProject.java index f797c5ddf..684bc019a 100644 --- a/backend/src/main/java/io/papermc/hangar/model/internal/projects/HangarProject.java +++ b/backend/src/main/java/io/papermc/hangar/model/internal/projects/HangarProject.java @@ -125,7 +125,7 @@ public static class PinnedVersion { private final Type type; private final String name; private final ProjectChannel channel; - private final Map platformDependenciesFormatted; + private final Map> platformDependenciesFormatted; private final Map downloads; public PinnedVersion(final long versionId, final Type type, final String name, @Nested("pc") final ProjectChannel channel) { @@ -149,7 +149,7 @@ public String getName() { return this.name; } - public Map getPlatformDependenciesFormatted() { + public Map> getPlatformDependenciesFormatted() { return this.platformDependenciesFormatted; } diff --git a/backend/src/main/java/io/papermc/hangar/service/internal/versions/VersionDependencyService.java b/backend/src/main/java/io/papermc/hangar/service/internal/versions/VersionDependencyService.java index cb012dc1c..341ea19a6 100644 --- a/backend/src/main/java/io/papermc/hangar/service/internal/versions/VersionDependencyService.java +++ b/backend/src/main/java/io/papermc/hangar/service/internal/versions/VersionDependencyService.java @@ -73,11 +73,12 @@ public DownloadsAndDependencies addDownloadsAndDependencies(final String project public DownloadsAndDependencies addDownloadsAndDependencies(final String user, final String project, final String versionName, final long versionId) { //TODO All of this is dumb and needs to be redone into as little queries as possible final Map> platformDependencies = this.versionsApiDAO.getPlatformDependencies(versionId); - final Map platformDependenciesFormatted = new EnumMap<>(Platform.class); + final Map> platformDependenciesFormatted = new EnumMap<>(Platform.class); platformDependencies.entrySet().parallelStream().forEach(entry -> { - final List fullVersionsForPlatform = this.platformService.getFullVersionsForPlatform(entry.getKey()); - final String formattedVersionRange = VersionFormatter.formatVersionRange(new ArrayList<>(entry.getValue()), fullVersionsForPlatform); - platformDependenciesFormatted.put(entry.getKey(), formattedVersionRange); + final Platform platform = entry.getKey(); + final List fullVersionsForPlatform = this.platformService.getFullVersionsForPlatform(platform); + final List formattedVersionRange = VersionFormatter.formatVersionRange(new ArrayList<>(entry.getValue()), fullVersionsForPlatform); + platformDependenciesFormatted.put(platform, formattedVersionRange); }); final Map> pluginDependencies = this.versionsApiDAO.getPluginDependencies(versionId).stream() @@ -89,7 +90,7 @@ public DownloadsAndDependencies addDownloadsAndDependencies(final String user, f public record DownloadsAndDependencies(Map> pluginDependencies, Map> platformDependencies, - Map platformDependenciesFormatted, + Map> platformDependenciesFormatted, Map downloads ) { public T applyTo(final T version) { diff --git a/backend/src/main/java/io/papermc/hangar/util/VersionFormatter.java b/backend/src/main/java/io/papermc/hangar/util/VersionFormatter.java index c1dd4047e..56fc4cfaa 100644 --- a/backend/src/main/java/io/papermc/hangar/util/VersionFormatter.java +++ b/backend/src/main/java/io/papermc/hangar/util/VersionFormatter.java @@ -1,5 +1,6 @@ package io.papermc.hangar.util; +import java.util.ArrayList; import java.util.List; public final class VersionFormatter { @@ -12,14 +13,14 @@ private VersionFormatter() { * * @param versions list of versions to stringify * @param allVersions sorted list of all valid versions - * @return formatted version range string + * @return formatted version range strings from oldest to newest * @throws IllegalArgumentException if versions contains a string not included in allVersions */ - public static String formatVersionRange(final List versions, final List allVersions) { + public static List formatVersionRange(final List versions, final List allVersions) { if (versions.isEmpty()) { - return ""; + return List.of(""); } else if (versions.size() == 1) { - return versions.get(0); + return List.of(versions.getFirst()); } versions.sort((version1, version2) -> { @@ -33,8 +34,8 @@ public static String formatVersionRange(final List versions, final List< return index1 - index2; }); - final StringBuilder builder = new StringBuilder(); - String fromVersion = versions.get(0); + final List formattedVersions = new ArrayList<>(); + String fromVersion = versions.getFirst(); String lastVersion = fromVersion; int lastVersionIndex = allVersions.indexOf(fromVersion); for (int i = 1; i < versions.size(); i++) { @@ -43,12 +44,11 @@ public static String formatVersionRange(final List versions, final List< if (versionIndex != lastVersionIndex + 1) { // Append last version/range if a new range starts if (!lastVersion.equals(fromVersion)) { - builder.append(fromVersion).append('-').append(lastVersion); + formattedVersions.add(fromVersion + '-' + lastVersion); } else { - builder.append(fromVersion); + formattedVersions.add(fromVersion); } - builder.append(", "); fromVersion = version; } @@ -57,10 +57,15 @@ public static String formatVersionRange(final List versions, final List< } // Append last version or range - builder.append(fromVersion); if (!fromVersion.equals(lastVersion)) { - builder.append('-').append(lastVersion); + formattedVersions.add(fromVersion + '-' + lastVersion); + } else { + formattedVersions.add(fromVersion); } - return builder.toString(); + return formattedVersions; + } + + public static String formatVersionRangeString(final List versions, final List allVersions) { + return String.join(", ", formatVersionRange(versions, allVersions)); } } diff --git a/backend/src/test/java/io/papermc/hangar/util/FormattedVersionsTest.java b/backend/src/test/java/io/papermc/hangar/util/FormattedVersionsTest.java index a7918becc..05b0c10d5 100644 --- a/backend/src/test/java/io/papermc/hangar/util/FormattedVersionsTest.java +++ b/backend/src/test/java/io/papermc/hangar/util/FormattedVersionsTest.java @@ -19,6 +19,6 @@ void testFormattedVersions() { } private void testFormatVersionNumbers(final String expected, final String... versions) { - Assertions.assertEquals(expected, VersionFormatter.formatVersionRange(new ArrayList<>(List.of(versions)), this.versions)); + Assertions.assertEquals(expected, VersionFormatter.formatVersionRangeString(new ArrayList<>(List.of(versions)), this.versions)); } } diff --git a/frontend/src/components/projects/DownloadButton.vue b/frontend/src/components/projects/DownloadButton.vue index 4e11a8c27..65ce7b876 100644 --- a/frontend/src/components/projects/DownloadButton.vue +++ b/frontend/src/components/projects/DownloadButton.vue @@ -64,6 +64,11 @@ function trackDownload(platform: string, version: { id?: number; versionId?: num const id = version.id || version.versionId; useInternalApi(`versions/version/${id}/${platform}/track`); } + +function formatVersionRange(versions: string[]): string { + // In download buttons, only show the latest version/version range + the remaining amount + return versions.length > 1 ? i18n.t("version.page.shortVersions", [versions.at(-1), versions.length - 1]) : versions[0]; +}