summaryrefslogtreecommitdiff
path: root/common/src/commonMain/kotlin/net/taler/lib/common
diff options
context:
space:
mode:
Diffstat (limited to 'common/src/commonMain/kotlin/net/taler/lib/common')
-rw-r--r--common/src/commonMain/kotlin/net/taler/lib/common/Amount.kt41
-rw-r--r--common/src/commonMain/kotlin/net/taler/lib/common/TalerUri.kt6
-rw-r--r--common/src/commonMain/kotlin/net/taler/lib/common/Time.kt41
-rw-r--r--common/src/commonMain/kotlin/net/taler/lib/common/Version.kt10
4 files changed, 51 insertions, 47 deletions
diff --git a/common/src/commonMain/kotlin/net/taler/lib/common/Amount.kt b/common/src/commonMain/kotlin/net/taler/lib/common/Amount.kt
index 213abb3..7635f8c 100644
--- a/common/src/commonMain/kotlin/net/taler/lib/common/Amount.kt
+++ b/common/src/commonMain/kotlin/net/taler/lib/common/Amount.kt
@@ -16,20 +16,20 @@
package net.taler.lib.common
-import kotlinx.serialization.Decoder
-import kotlinx.serialization.Encoder
import kotlinx.serialization.KSerializer
import kotlinx.serialization.Serializable
import kotlinx.serialization.Serializer
+import kotlinx.serialization.encoding.Decoder
+import kotlinx.serialization.encoding.Encoder
import kotlin.math.floor
import kotlin.math.pow
import kotlin.math.roundToInt
-class AmountParserException(msg: String? = null, cause: Throwable? = null) : Exception(msg, cause)
-class AmountOverflowException(msg: String? = null, cause: Throwable? = null) : Exception(msg, cause)
+public class AmountParserException(msg: String? = null, cause: Throwable? = null) : Exception(msg, cause)
+public class AmountOverflowException(msg: String? = null, cause: Throwable? = null) : Exception(msg, cause)
@Serializable(with = KotlinXAmountSerializer::class)
-data class Amount(
+public data class Amount(
/**
* name of the currency using either a three-character ISO 4217 currency code,
* or a regional currency identifier starting with a "*" followed by at most 10 characters.
@@ -53,26 +53,26 @@ data class Amount(
val fraction: Int
) : Comparable<Amount> {
- companion object {
+ public companion object {
private const val FRACTIONAL_BASE: Int = 100000000 // 1e8
private val REGEX_CURRENCY = Regex("""^[-_*A-Za-z0-9]{1,12}$""")
- val MAX_VALUE = 2.0.pow(52).toLong()
+ public val MAX_VALUE: Long = 2.0.pow(52).toLong()
private const val MAX_FRACTION_LENGTH = 8
- const val MAX_FRACTION = 99_999_999
+ public const val MAX_FRACTION: Int = 99_999_999
- fun zero(currency: String): Amount {
+ public fun zero(currency: String): Amount {
return Amount(checkCurrency(currency), 0, 0)
}
- fun fromJSONString(str: String): Amount {
+ public fun fromJSONString(str: String): Amount {
val split = str.split(":")
if (split.size != 2) throw AmountParserException("Invalid Amount Format")
return fromString(split[0], split[1])
}
- fun fromString(currency: String, str: String): Amount {
+ public fun fromString(currency: String, str: String): Amount {
// value
val valueSplit = str.split(".")
val value = checkValue(valueSplit[0].toLongOrNull())
@@ -89,8 +89,8 @@ data class Amount(
return Amount(checkCurrency(currency), value, fraction)
}
- fun min(currency: String): Amount = Amount(currency, 0, 1)
- fun max(currency: String): Amount = Amount(currency, MAX_VALUE, MAX_FRACTION)
+ public fun min(currency: String): Amount = Amount(currency, 0, 1)
+ public fun max(currency: String): Amount = Amount(currency, MAX_VALUE, MAX_FRACTION)
internal fun checkCurrency(currency: String): String {
@@ -113,7 +113,7 @@ data class Amount(
}
- val amountStr: String
+ public val amountStr: String
get() = if (fraction == 0) "$value" else {
var f = fraction
var fractionStr = ""
@@ -124,7 +124,7 @@ data class Amount(
"$value.$fractionStr"
}
- operator fun plus(other: Amount): Amount {
+ public operator fun plus(other: Amount): Amount {
check(currency == other.currency) { "Can only subtract from same currency" }
val resultValue = value + other.value + floor((fraction + other.fraction).toDouble() / FRACTIONAL_BASE).toLong()
if (resultValue > MAX_VALUE)
@@ -133,7 +133,7 @@ data class Amount(
return Amount(currency, resultValue, resultFraction)
}
- operator fun times(factor: Int): Amount {
+ public operator fun times(factor: Int): Amount {
// TODO consider replacing with a faster implementation
if (factor == 0) return zero(currency)
var result = this
@@ -141,7 +141,7 @@ data class Amount(
return result
}
- operator fun minus(other: Amount): Amount {
+ public operator fun minus(other: Amount): Amount {
check(currency == other.currency) { "Can only subtract from same currency" }
var resultValue = value
var resultFraction = fraction
@@ -159,11 +159,11 @@ data class Amount(
return Amount(currency, resultValue, resultFraction)
}
- fun isZero(): Boolean {
+ public fun isZero(): Boolean {
return value == 0L && fraction == 0
}
- fun toJSONString(): String {
+ public fun toJSONString(): String {
return "$currency:$amountStr"
}
@@ -186,8 +186,9 @@ data class Amount(
}
+@Suppress("EXPERIMENTAL_API_USAGE")
@Serializer(forClass = Amount::class)
-object KotlinXAmountSerializer: KSerializer<Amount> {
+internal object KotlinXAmountSerializer : KSerializer<Amount> {
override fun serialize(encoder: Encoder, value: Amount) {
encoder.encodeString(value.toJSONString())
}
diff --git a/common/src/commonMain/kotlin/net/taler/lib/common/TalerUri.kt b/common/src/commonMain/kotlin/net/taler/lib/common/TalerUri.kt
index 8255dc0..724820e 100644
--- a/common/src/commonMain/kotlin/net/taler/lib/common/TalerUri.kt
+++ b/common/src/commonMain/kotlin/net/taler/lib/common/TalerUri.kt
@@ -16,7 +16,7 @@
package net.taler.lib.common
-object TalerUri {
+public object TalerUri {
private const val SCHEME = "taler://"
private const val SCHEME_INSECURE = "taler+http://"
@@ -25,7 +25,7 @@ object TalerUri {
private const val AUTHORITY_REFUND = "refund"
private const val AUTHORITY_TIP = "tip"
- data class WithdrawUriResult(
+ public data class WithdrawUriResult(
val bankIntegrationApiBaseUrl: String,
val withdrawalOperationId: String
)
@@ -33,7 +33,7 @@ object TalerUri {
/**
* Parses a withdraw URI and returns a bank status URL or null if the URI was invalid.
*/
- fun parseWithdrawUri(uri: String): WithdrawUriResult? {
+ public fun parseWithdrawUri(uri: String): WithdrawUriResult? {
val (resultScheme, prefix) = when {
uri.startsWith(SCHEME, ignoreCase = true) -> {
Pair("https://", "${SCHEME}${AUTHORITY_WITHDRAW}/")
diff --git a/common/src/commonMain/kotlin/net/taler/lib/common/Time.kt b/common/src/commonMain/kotlin/net/taler/lib/common/Time.kt
index 0e5e07c..704a91a 100644
--- a/common/src/commonMain/kotlin/net/taler/lib/common/Time.kt
+++ b/common/src/commonMain/kotlin/net/taler/lib/common/Time.kt
@@ -24,38 +24,40 @@ import kotlinx.serialization.json.JsonElement
import kotlinx.serialization.json.JsonPrimitive
import kotlinx.serialization.json.JsonTransformingSerializer
import kotlinx.serialization.json.contentOrNull
+import kotlinx.serialization.json.jsonPrimitive
import kotlinx.serialization.json.longOrNull
import net.taler.lib.common.Duration.Companion.FOREVER
import kotlin.math.max
@Serializable
-data class Timestamp(
+public data class Timestamp(
@SerialName("t_ms")
@Serializable(NeverSerializer::class)
val ms: Long
) : Comparable<Timestamp> {
- companion object {
- const val NEVER: Long = -1
- fun now(): Timestamp = Timestamp(DateTime.nowUnixLong())
+ public companion object {
+ private const val NEVER: Long = -1
+ public fun now(): Timestamp = Timestamp(DateTime.nowUnixLong())
+ public fun never(): Timestamp = Timestamp(NEVER)
}
/**
* Returns a copy of this [Timestamp] rounded to seconds.
*/
- fun truncateSeconds(): Timestamp {
+ public fun truncateSeconds(): Timestamp {
if (ms == NEVER) return Timestamp(ms)
return Timestamp((ms / 1000L) * 1000L)
}
- operator fun minus(other: Timestamp): Duration = when {
+ public operator fun minus(other: Timestamp): Duration = when {
ms == NEVER -> Duration(FOREVER)
other.ms == NEVER -> throw Error("Invalid argument for timestamp comparision")
ms < other.ms -> Duration(0)
else -> Duration(ms - other.ms)
}
- operator fun minus(other: Duration): Timestamp = when {
+ public operator fun minus(other: Duration): Timestamp = when {
ms == NEVER -> this
other.ms == FOREVER -> Timestamp(0)
else -> Timestamp(max(0, ms - other.ms))
@@ -74,7 +76,7 @@ data class Timestamp(
}
@Serializable
-data class Duration(
+public data class Duration(
/**
* Duration in milliseconds.
*/
@@ -82,24 +84,25 @@ data class Duration(
@Serializable(ForeverSerializer::class)
val ms: Long
) {
- companion object {
- const val FOREVER: Long = -1
+ public companion object {
+ internal const val FOREVER: Long = -1
+ public fun forever(): Duration = Duration(FOREVER)
}
}
-abstract class MinusOneSerializer(private val keyword: String) :
- JsonTransformingSerializer<Long>(Long.serializer(), keyword) {
+internal abstract class MinusOneSerializer(private val keyword: String) :
+ JsonTransformingSerializer<Long>(Long.serializer()) {
- override fun readTransform(element: JsonElement): JsonElement {
- return if (element.contentOrNull == keyword) return JsonPrimitive(-1)
- else super.readTransform(element)
+ override fun transformDeserialize(element: JsonElement): JsonElement {
+ return if (element.jsonPrimitive.contentOrNull == keyword) return JsonPrimitive(-1)
+ else super.transformDeserialize(element)
}
- override fun writeTransform(element: JsonElement): JsonElement {
- return if (element.longOrNull == -1L) return JsonPrimitive(keyword)
+ override fun transformSerialize(element: JsonElement): JsonElement {
+ return if (element.jsonPrimitive.longOrNull == -1L) return JsonPrimitive(keyword)
else element
}
}
-object NeverSerializer : MinusOneSerializer("never")
-object ForeverSerializer : MinusOneSerializer("forever")
+internal object NeverSerializer : MinusOneSerializer("never")
+internal object ForeverSerializer : MinusOneSerializer("forever")
diff --git a/common/src/commonMain/kotlin/net/taler/lib/common/Version.kt b/common/src/commonMain/kotlin/net/taler/lib/common/Version.kt
index d3f0ad2..c4dc53d 100644
--- a/common/src/commonMain/kotlin/net/taler/lib/common/Version.kt
+++ b/common/src/commonMain/kotlin/net/taler/lib/common/Version.kt
@@ -22,13 +22,13 @@ import kotlin.math.sign
* Semantic versioning, but libtool-style.
* See https://www.gnu.org/software/libtool/manual/html_node/Libtool-versioning.html
*/
-data class Version(
+public data class Version(
val current: Int,
val revision: Int,
val age: Int
) {
- companion object {
- fun parse(v: String): Version? {
+ public companion object {
+ public fun parse(v: String): Version? {
val elements = v.split(":")
if (elements.size != 3) return null
val (currentStr, revisionStr, ageStr) = elements
@@ -45,7 +45,7 @@ data class Version(
*
* Returns a [VersionMatchResult] or null if the given version was null.
*/
- fun compare(other: Version?): VersionMatchResult? {
+ public fun compare(other: Version?): VersionMatchResult? {
if (other == null) return null
val compatible = current - age <= other.current &&
current >= other.current - other.age
@@ -56,7 +56,7 @@ data class Version(
/**
* Result of comparing two libtool versions.
*/
- data class VersionMatchResult(
+ public data class VersionMatchResult(
/**
* Is the first version compatible with the second?
*/