blob: 96a0923419937b581db65e3aeeb63518bb2aa75b [file] [log] [blame]
// Copyright 2014 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package com.flutter.gradle
import kotlin.math.max
object VersionUtils {
/**
* Compares semantic versions ignoring labels.
*
* If the versions are equal (ignoring labels), returns one of the two strings arbitrarily. If
* minor or patch are omitted (non-conformant to semantic versioning), they are considered zero.
* If the provided versions in both are equal, the longest version string is returned. For
* example, "2.8.0" vs "2.8" will always consider "2.8.0" to be the most recent version. For
* another example, "8.7-rc-2" vs "8.7.2" will always consider "8.7.2" to be the most recent
* version.
*/
@JvmStatic
fun mostRecentSemanticVersion(
version1: String,
version2: String
): String {
val v1Parts = version1.split(".", "-")
val v2Parts = version2.split(".", "-")
val maxSize = max(v1Parts.size, v2Parts.size)
for (i in 0 until maxSize) {
val v1Part: String = v1Parts.getOrNull(i) ?: "0"
val v2Part: String = v2Parts.getOrNull(i) ?: "0"
val v1Num: Int? = v1Part.toIntOrNull()
val v2Num: Int? = v2Part.toIntOrNull()
when {
v1Num != null && v2Num != null -> { // Both are numbers
if (v1Num != v2Num) {
return if (v1Num > v2Num) version1 else version2
}
}
v1Num != null && v2Num == null ->
return version1 // v1 is a number, v2 is not, so v1 is newer.
v1Num == null && v2Num != null ->
return version2 // v1 is not a number, v2 is, so v2 is newer.
else -> { // Both are not numbers (pre-release identifiers)
if (v1Part != v2Part) {
return if (comparePreReleaseIdentifiers(v1Part, v2Part)) version1 else version2
}
}
}
}
// If versions are equal, return the longest version string
return if (version1.length >= version2.length) version1 else version2
}
/** Compares only non digits and returns true if v1Part is than v2Part. */
private fun comparePreReleaseIdentifiers(
v1Part: String,
v2Part: String
): Boolean {
val digits = Regex("\\d")
val v1PreRelease = v1Part.replace(digits, "")
val v2PreRelease = v2Part.replace(digits, "")
return v1PreRelease < v2PreRelease
}
}