diff --git a/buildSrc/src/main/kotlin/zoneInfosResourcesGenerator.kt b/buildSrc/src/main/kotlin/zoneInfosResourcesGenerator.kt index 01cd8885e..692e6e38f 100644 --- a/buildSrc/src/main/kotlin/zoneInfosResourcesGenerator.kt +++ b/buildSrc/src/main/kotlin/zoneInfosResourcesGenerator.kt @@ -1,3 +1,4 @@ +import org.gradle.api.file.Directory import java.io.File /* @@ -51,7 +52,7 @@ private fun loadTzBinaries( } } -fun generateZoneInfosResources(zoneInfoDir: File, outputDir: File, version: String) { +fun generateZoneInfosResources(zoneInfoDir: File, outputDir: Directory, version: String) { val header = buildString { appendLine() append("/* AUTOGENERATED FROM ZONE INFO DATABASE v.$version */") @@ -70,7 +71,7 @@ fun generateZoneInfosResources(zoneInfoDir: File, outputDir: File, version: Stri loadedZones.forEachIndexed { id, tzData -> val tzDataName = "tzData$id" val data = generateByteArrayProperty(tzData, header, tzDataName) - File(outputDir, "$tzDataName.kt").writeText(data) + outputDir.file("$tzDataName.kt").asFile.writeText(data) tzData.fullTzNames.forEach { name -> zoneDataByNameBody.appendLine(" \"$name\" -> $tzDataName") getTimeZonesBody.appendLine(" \"$name\",") @@ -97,5 +98,5 @@ fun generateZoneInfosResources(zoneInfoDir: File, outputDir: File, version: Stri append("}") } - File(outputDir, "tzData.kt").writeText(content) + outputDir.file("tzData.kt").asFile.writeText(content) } \ No newline at end of file diff --git a/core/build.gradle.kts b/core/build.gradle.kts index 39ecca39f..fbbf851e8 100644 --- a/core/build.gradle.kts +++ b/core/build.gradle.kts @@ -1,13 +1,13 @@ import kotlinx.team.infra.mavenPublicationsPom -import org.jetbrains.kotlin.gradle.tasks.KotlinCompile -import java.net.URL -import javax.xml.parsers.DocumentBuilderFactory -import java.io.ByteArrayOutputStream -import java.io.PrintWriter import org.jetbrains.kotlin.gradle.ExperimentalKotlinGradlePluginApi +import org.jetbrains.kotlin.gradle.ExperimentalWasmDsl import org.jetbrains.kotlin.gradle.dsl.JsModuleKind -import org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet +import org.jetbrains.kotlin.gradle.tasks.KotlinCompile import org.jetbrains.kotlin.konan.target.Family +import java.io.ByteArrayOutputStream +import java.io.PrintWriter +import java.net.URL +import javax.xml.parsers.DocumentBuilderFactory plugins { kotlin("multiplatform") @@ -22,10 +22,6 @@ mavenPublicationsPom { description.set("Kotlin Datetime Library") } -base { - archivesBaseName = "kotlinx-datetime" // doesn't work -} - val mainJavaToolchainVersion: String by project val modularJavaToolchainVersion: String by project val serializationVersion: String by project @@ -112,6 +108,7 @@ kotlin { } } + @OptIn(ExperimentalWasmDsl::class) wasmJs { nodejs { testTask { @@ -122,6 +119,7 @@ kotlin { } } + @OptIn(ExperimentalWasmDsl::class) wasmWasi { nodejs() } @@ -295,7 +293,7 @@ tasks { // Workaround for https://youtrack.jetbrains.com/issue/KT-58303: // the `clean` task can't delete the expanded.lock file on Windows as it's still held by Gradle, failing the build val clean by existing(Delete::class) { - setDelete(fileTree(buildDir) { + setDelete(fileTree(layout.buildDirectory) { exclude("tmp/.cache/expanded/expanded.lock") }) } @@ -322,7 +320,7 @@ val downloadWindowsZonesMapping by tasks.registering { val output = "$projectDir/windows/src/internal/WindowsZoneNames.kt" outputs.file(output) doLast { - val initialFileContents = try { File(output).readBytes() } catch(e: Throwable) { ByteArray(0) } + val initialFileContents = try { File(output).readBytes() } catch(_: Throwable) { ByteArray(0) } val documentBuilderFactory = DocumentBuilderFactory.newInstance() // otherwise, parsing fails since it can't find the dtd documentBuilderFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false) diff --git a/core/common/src/format/DateTimeComponents.kt b/core/common/src/format/DateTimeComponents.kt index 5bba7ac2b..5d95bade5 100644 --- a/core/common/src/format/DateTimeComponents.kt +++ b/core/common/src/format/DateTimeComponents.kt @@ -538,7 +538,7 @@ public class DateTimeComponents internal constructor(internal val contents: Date truncatedDate.year = requireParsedField(truncatedDate.year, "year") % 10_000 val totalSeconds = try { val secDelta = safeMultiply((year!! / 10_000).toLong(), SECONDS_PER_10000_YEARS) - val epochDays = truncatedDate.toLocalDate().toEpochDays().toLong() + val epochDays = truncatedDate.toLocalDate().toEpochDays() safeAdd(secDelta, epochDays * SECONDS_PER_DAY + time.toSecondOfDay() - offset.totalSeconds) } catch (e: ArithmeticException) { throw DateTimeFormatException("The parsed date is outside the range representable by Instant", e) @@ -654,10 +654,8 @@ internal class DateTimeComponentsFormat(override val actualFormat: CachedFormatS override fun timeZoneId() = actualBuilder.add(BasicFormatStructure(TimeZoneIdDirective())) - @Suppress("NO_ELSE_IN_WHEN") - override fun dateTimeComponents(format: DateTimeFormat) = when (format) { - is DateTimeComponentsFormat -> actualBuilder.add(format.actualFormat) - } + override fun dateTimeComponents(format: DateTimeFormat) = + format.withForceCast { format: DateTimeComponentsFormat -> actualBuilder.add(format.actualFormat) } override fun createEmpty(): Builder = Builder(AppendableFormatStructure()) } diff --git a/core/common/src/format/DateTimeFormat.kt b/core/common/src/format/DateTimeFormat.kt index 501c0416b..ec46d3e0f 100644 --- a/core/common/src/format/DateTimeFormat.kt +++ b/core/common/src/format/DateTimeFormat.kt @@ -116,7 +116,7 @@ internal sealed class AbstractDateTimeFormat> : DateTimeForma open fun valueFromIntermediateOrNull(intermediate: U): T? = try { valueFromIntermediate(intermediate) - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { null } diff --git a/core/common/src/format/DateTimeFormatBuilder.kt b/core/common/src/format/DateTimeFormatBuilder.kt index d77021f59..955908b75 100644 --- a/core/common/src/format/DateTimeFormatBuilder.kt +++ b/core/common/src/format/DateTimeFormatBuilder.kt @@ -362,9 +362,8 @@ internal fun DateTimeFormatBuilder.WithTime.secondFractionInternal( maxLength: Int, grouping: List ) { - @Suppress("NO_ELSE_IN_WHEN") - when (this) { - is AbstractWithTimeBuilder -> addFormatStructureForTime( + withForceCast { value: AbstractWithTimeBuilder -> + value.addFormatStructureForTime( BasicFormatStructure(FractionalSecondDirective(minLength, maxLength, grouping)) ) } diff --git a/core/common/src/format/LocalDateFormat.kt b/core/common/src/format/LocalDateFormat.kt index c472ea19e..838aa1b2b 100644 --- a/core/common/src/format/LocalDateFormat.kt +++ b/core/common/src/format/LocalDateFormat.kt @@ -280,10 +280,8 @@ internal interface AbstractWithDateBuilder : AbstractWithYearMonthBuilder, DateT override fun dayOfYear(padding: Padding) = addFormatStructureForDate(BasicFormatStructure(DayOfYearDirective(padding))) - @Suppress("NO_ELSE_IN_WHEN") - override fun date(format: DateTimeFormat) = when (format) { - is LocalDateFormat -> addFormatStructureForDate(format.actualFormat) - } + override fun date(format: DateTimeFormat) = + format.withForceCast { format: LocalDateFormat -> addFormatStructureForDate(format.actualFormat) } } // these are constants so that the formats are not recreated every time they are used diff --git a/core/common/src/format/LocalDateTimeFormat.kt b/core/common/src/format/LocalDateTimeFormat.kt index 8e97ea607..4586f88ae 100644 --- a/core/common/src/format/LocalDateTimeFormat.kt +++ b/core/common/src/format/LocalDateTimeFormat.kt @@ -8,6 +8,7 @@ package kotlinx.datetime.format import kotlinx.datetime.* import kotlinx.datetime.internal.format.* import kotlinx.datetime.internal.format.parser.Copyable +import kotlinx.datetime.internal.withForceCast internal interface DateTimeFieldContainer : DateFieldContainer, TimeFieldContainer @@ -67,10 +68,8 @@ internal interface AbstractWithDateTimeBuilder: addFormatStructureForDateTime(structure) } - @Suppress("NO_ELSE_IN_WHEN") - override fun dateTime(format: DateTimeFormat) = when (format) { - is LocalDateTimeFormat -> addFormatStructureForDateTime(format.actualFormat) - } + override fun dateTime(format: DateTimeFormat) = + format.withForceCast { format: LocalDateTimeFormat -> addFormatStructureForDateTime(format.actualFormat) } } // these are constants so that the formats are not recreated every time they are used diff --git a/core/common/src/format/LocalTimeFormat.kt b/core/common/src/format/LocalTimeFormat.kt index d1854e124..c5a6f64f6 100644 --- a/core/common/src/format/LocalTimeFormat.kt +++ b/core/common/src/format/LocalTimeFormat.kt @@ -10,6 +10,7 @@ import kotlinx.datetime.DateTimeFormatException import kotlinx.datetime.internal.DecimalFraction import kotlinx.datetime.internal.format.* import kotlinx.datetime.internal.format.parser.Copyable +import kotlinx.datetime.internal.withForceCast /** * The AM/PM marker that indicates whether the hour in range `1..12` is before or after noon. @@ -122,10 +123,8 @@ internal interface AbstractWithTimeBuilder : DateTimeFormatBuilder.WithTime { override fun secondFraction(minLength: Int, maxLength: Int) = addFormatStructureForTime(BasicFormatStructure(FractionalSecondDirective(minLength, maxLength))) - @Suppress("NO_ELSE_IN_WHEN") - override fun time(format: DateTimeFormat) = when (format) { - is LocalTimeFormat -> addFormatStructureForTime(format.actualFormat) - } + override fun time(format: DateTimeFormat) = + format.withForceCast { format: LocalTimeFormat -> addFormatStructureForTime(format.actualFormat) } } private class HourDirective(private val padding: Padding) : diff --git a/core/common/src/format/Unicode.kt b/core/common/src/format/Unicode.kt index 97404a77c..908ac6418 100644 --- a/core/common/src/format/Unicode.kt +++ b/core/common/src/format/Unicode.kt @@ -5,8 +5,6 @@ package kotlinx.datetime.format -import kotlin.native.concurrent.* - /** * Marks declarations in the datetime library that use format strings to define datetime formats. * @@ -241,8 +239,7 @@ internal sealed interface UnicodeFormat { data class StringLiteral(val literal: String) : UnicodeFormat { override fun toString(): String = if (literal == "'") "''" else if (literal.any { it.isLetter() }) "'$literal'" - else if (literal.isEmpty()) "" - else literal + else literal.ifEmpty { "" } } sealed class Directive : UnicodeFormat { @@ -257,8 +254,8 @@ internal sealed interface UnicodeFormat { sealed class YearMonthBased : DateBased() { abstract fun addToFormat(builder: DateTimeFormatBuilder.WithYearMonth) override fun addToFormat(builder: DateTimeFormatBuilder.WithDate) { - val downcastedBuilder: DateTimeFormatBuilder.WithYearMonth = builder - addToFormat(downcastedBuilder) + val downcastBuilder: DateTimeFormatBuilder.WithYearMonth = builder + addToFormat(downcastBuilder) } class Era(override val formatLength: Int) : YearMonthBased() { diff --git a/core/common/src/format/UtcOffsetFormat.kt b/core/common/src/format/UtcOffsetFormat.kt index e8bc47779..cf425b261 100644 --- a/core/common/src/format/UtcOffsetFormat.kt +++ b/core/common/src/format/UtcOffsetFormat.kt @@ -8,6 +8,7 @@ package kotlinx.datetime.format import kotlinx.datetime.* import kotlinx.datetime.internal.format.* import kotlinx.datetime.internal.format.parser.Copyable +import kotlinx.datetime.internal.withForceCast import kotlin.math.* internal interface UtcOffsetFieldContainer { @@ -34,10 +35,8 @@ internal interface AbstractWithOffsetBuilder : DateTimeFormatBuilder.WithUtcOffs override fun offsetSecondsOfMinute(padding: Padding) = addFormatStructureForOffset(BasicFormatStructure(UtcOffsetSecondOfMinuteDirective(padding))) - @Suppress("NO_ELSE_IN_WHEN") - override fun offset(format: DateTimeFormat) = when (format) { - is UtcOffsetFormat -> addFormatStructureForOffset(format.actualFormat) - } + override fun offset(format: DateTimeFormat) = + format.withForceCast { format: UtcOffsetFormat -> addFormatStructureForOffset(format.actualFormat) } } internal class UtcOffsetFormat(override val actualFormat: CachedFormatStructure) : diff --git a/core/common/src/format/YearMonthFormat.kt b/core/common/src/format/YearMonthFormat.kt index a8a0a7d65..bde684ddf 100644 --- a/core/common/src/format/YearMonthFormat.kt +++ b/core/common/src/format/YearMonthFormat.kt @@ -193,9 +193,8 @@ private const val YEAR_OF_ERA_COMMENT = * additional comment and explain that the behavior was not preserved exactly. */ internal fun DateTimeFormatBuilder.WithYearMonth.yearOfEra(padding: Padding) { - @Suppress("NO_ELSE_IN_WHEN") - when (this) { - is AbstractWithYearMonthBuilder -> addFormatStructureForYearMonth( + withForceCast { value: AbstractWithYearMonthBuilder -> + value.addFormatStructureForYearMonth( BasicFormatStructure(YearDirective(padding, isYearOfEra = true)) ) } @@ -208,9 +207,8 @@ internal fun DateTimeFormatBuilder.WithYearMonth.yearOfEra(padding: Padding) { * additional comment and explain that the behavior was not preserved exactly. */ internal fun DateTimeFormatBuilder.WithYearMonth.yearOfEraTwoDigits(baseYear: Int) { - @Suppress("NO_ELSE_IN_WHEN") - when (this) { - is AbstractWithYearMonthBuilder -> addFormatStructureForYearMonth( + withForceCast { value: AbstractWithYearMonthBuilder -> + value.addFormatStructureForYearMonth( BasicFormatStructure(ReducedYearDirective(baseYear, isYearOfEra = true)) ) } @@ -284,10 +282,8 @@ internal interface AbstractWithYearMonthBuilder : DateTimeFormatBuilder.WithYear override fun monthName(names: MonthNames) = addFormatStructureForYearMonth(BasicFormatStructure(MonthNameDirective(names))) - @Suppress("NO_ELSE_IN_WHEN") - override fun yearMonth(format: DateTimeFormat) = when (format) { - is YearMonthFormat -> addFormatStructureForYearMonth(format.actualFormat) - } + override fun yearMonth(format: DateTimeFormat) = + format.withForceCast { format: YearMonthFormat -> addFormatStructureForYearMonth(format.actualFormat) } } private val emptyIncompleteYearMonth = IncompleteYearMonth() diff --git a/core/common/src/internal/util.kt b/core/common/src/internal/util.kt index 2bdbb1ba3..2e76a71a5 100644 --- a/core/common/src/internal/util.kt +++ b/core/common/src/internal/util.kt @@ -36,10 +36,16 @@ private fun removeLeadingZerosFromLongYearForm(input: String, minStringLengthAft } internal fun removeLeadingZerosFromLongYearFormLocalDate(input: String) = - removeLeadingZerosFromLongYearForm(input.toString(), 6) // 6 = "-01-02".length + removeLeadingZerosFromLongYearForm(input, 6) // 6 = "-01-02".length internal fun removeLeadingZerosFromLongYearFormLocalDateTime(input: String) = - removeLeadingZerosFromLongYearForm(input.toString(), 12) // 12 = "-01-02T23:59".length + removeLeadingZerosFromLongYearForm(input, 12) // 12 = "-01-02T23:59".length internal fun removeLeadingZerosFromLongYearFormYearMonth(input: String) = - removeLeadingZerosFromLongYearForm(input.toString(), 3) // 3 = "-01".length + removeLeadingZerosFromLongYearForm(input, 3) // 3 = "-01".length + +internal inline fun S.withForceCast(block: (T) -> R): R = when { + this is T -> block(this) + else -> error("Expected ${T::class} but found ${this::class}. " + + "Please report this to the kotlinx-datetime issue tracker.") +} diff --git a/core/common/test/ClockTimeSourceTest.kt b/core/common/test/ClockTimeSourceTest.kt index 920f5b7c9..a74bbf975 100644 --- a/core/common/test/ClockTimeSourceTest.kt +++ b/core/common/test/ClockTimeSourceTest.kt @@ -46,7 +46,7 @@ class ClockTimeSourceTest { assertEquals(1.days, mark.elapsedNow()) clock.instant -= 2.days - assertEquals(-1.days, mark.elapsedNow()) + assertEquals((-1).days, mark.elapsedNow()) clock.instant = Instant.MAX assertEquals(Duration.INFINITE, mark.elapsedNow()) diff --git a/core/common/test/DeprecatedClockTimeSourceTest.kt b/core/common/test/DeprecatedClockTimeSourceTest.kt index 85a453ee5..f6a9a95f3 100644 --- a/core/common/test/DeprecatedClockTimeSourceTest.kt +++ b/core/common/test/DeprecatedClockTimeSourceTest.kt @@ -43,7 +43,7 @@ class DeprecatedClockTimeSourceTest { assertEquals(1.days, mark.elapsedNow()) clock.instant -= 2.days - assertEquals(-1.days, mark.elapsedNow()) + assertEquals((-1).days, mark.elapsedNow()) clock.instant = Instant.fromEpochSeconds(Long.MAX_VALUE) assertEquals(Duration.INFINITE, mark.elapsedNow()) diff --git a/core/common/test/InstantTest.kt b/core/common/test/InstantTest.kt index 082c2f30e..b2905a97b 100644 --- a/core/common/test/InstantTest.kt +++ b/core/common/test/InstantTest.kt @@ -6,20 +6,17 @@ package kotlinx.datetime.test import kotlinx.datetime.* -import kotlinx.datetime.format.* -import kotlinx.datetime.internal.* -import kotlin.random.* +import kotlinx.datetime.internal.NANOS_PER_ONE +import kotlin.random.Random import kotlin.test.* import kotlin.time.* +import kotlin.time.Clock import kotlin.time.Duration.Companion.days import kotlin.time.Duration.Companion.hours import kotlin.time.Duration.Companion.milliseconds import kotlin.time.Duration.Companion.nanoseconds import kotlin.time.Duration.Companion.seconds -import kotlin.time.Clock import kotlin.time.Instant -import kotlin.time.isDistantFuture -import kotlin.time.isDistantPast class InstantTest { diff --git a/core/common/test/LocalDateTimeTest.kt b/core/common/test/LocalDateTimeTest.kt index fcb44200c..5339c16ca 100644 --- a/core/common/test/LocalDateTimeTest.kt +++ b/core/common/test/LocalDateTimeTest.kt @@ -6,6 +6,7 @@ package kotlinx.datetime.test import kotlinx.datetime.* +import kotlinx.datetime.LocalDateTime import kotlin.time.Clock import kotlin.time.Instant import kotlin.test.* @@ -20,14 +21,14 @@ class LocalDateTimeTest { @Test fun localDateTimeParsing() { fun checkParsedComponents(value: String, year: Int, month: Int, day: Int, hour: Int, minute: Int, second: Int, nanosecond: Int, dayOfWeek: Int? = null, dayOfYear: Int? = null) { - checkComponents(value.toLocalDateTime(), year, month, day, hour, minute, second, nanosecond, dayOfWeek, dayOfYear) + checkComponents(LocalDateTime.parse(value), year, month, day, hour, minute, second, nanosecond, dayOfWeek, dayOfYear) } checkParsedComponents("2019-10-01T18:43:15.100500", 2019, 10, 1, 18, 43, 15, 100500000, 2, 274) checkParsedComponents("2019-10-01T18:43:15", 2019, 10, 1, 18, 43, 15, 0, 2, 274) checkParsedComponents("2019-10-01T18:12", 2019, 10, 1, 18, 12, 0, 0, 2, 274) assertFailsWith { LocalDateTime.parse("x") } - assertFailsWith { "+1000000000-03-26T04:00:00".toLocalDateTime() } + assertFailsWith { LocalDateTime.parse("+1000000000-03-26T04:00:00") } for (i in 1..30) { checkComponents(LocalDateTime.parse("+${"0".repeat(i)}2024-01-01T23:59"), 2024, 1, 1, 23, 59) @@ -46,8 +47,8 @@ class LocalDateTimeTest { @Test fun localDtToInstantConversion() { - val ldt1 = "2019-10-01T18:43:15.100500".toLocalDateTime() - val ldt2 = "2019-10-01T19:50:00.500600".toLocalDateTime() + val ldt1 = LocalDateTime.parse("2019-10-01T18:43:15.100500") + val ldt2 = LocalDateTime.parse("2019-10-01T19:50:00.500600") val diff = with(TimeZone.UTC) { ldt2.toInstant() - ldt1.toInstant() } assertEquals(with(Duration) { 1.hours + 7.minutes - 15.seconds + 400100.microseconds }, diff) @@ -57,8 +58,8 @@ class LocalDateTimeTest { @Test fun localDtToInstantConversionRespectsTimezones() { - val ldt1 = "2011-03-26T04:00:00".toLocalDateTime() - val ldt2 = "2011-03-27T04:00:00".toLocalDateTime() + val ldt1 = LocalDateTime.parse("2011-03-26T04:00:00") + val ldt2 = LocalDateTime.parse("2011-03-27T04:00:00") val diff = with(TimeZone.of("Europe/Moscow")) { ldt2.toInstant() - ldt1.toInstant() } assertEquals(23.hours, diff) } diff --git a/core/common/test/LocalTimeTest.kt b/core/common/test/LocalTimeTest.kt index 09f0f5f6e..b9fd18e25 100644 --- a/core/common/test/LocalTimeTest.kt +++ b/core/common/test/LocalTimeTest.kt @@ -6,6 +6,8 @@ package kotlinx.datetime.test import kotlinx.datetime.* +import kotlinx.datetime.LocalDateTime +import kotlinx.datetime.LocalTime import kotlinx.datetime.internal.* import kotlin.math.* import kotlin.random.* @@ -16,14 +18,14 @@ class LocalTimeTest { @Test fun localTimeParsing() { fun checkParsedComponents(value: String, hour: Int, minute: Int, second: Int, nanosecond: Int) { - checkComponents(value.toLocalTime(), hour, minute, second, nanosecond) + checkComponents(LocalTime.parse(value), hour, minute, second, nanosecond) } checkParsedComponents("18:43:15.100500", 18, 43, 15, 100500000) checkParsedComponents("18:43:15", 18, 43, 15, 0) checkParsedComponents("18:12", 18, 12, 0, 0) assertFailsWith { LocalTime.parse("x") } - assertFailsWith { "+10000000004:00:00".toLocalDateTime() } + assertFailsWith { LocalDateTime.parse("+10000000004:00:00") } /* Based on the ThreeTenBp project. * Copyright (c) 2007-present, Stephen Colebourne & Michael Nascimento Santos diff --git a/core/common/test/assertions.kt b/core/common/test/assertions.kt index c86b27382..74ca0f4a6 100644 --- a/core/common/test/assertions.kt +++ b/core/common/test/assertions.kt @@ -9,8 +9,6 @@ import kotlinx.datetime.DateTimeFormatException import kotlin.test.assertFailsWith import kotlin.test.fail -@Suppress("INVISIBLE_REFERENCE", "INVISIBLE_MEMBER") -@kotlin.internal.InlineOnly inline fun assertArithmeticFails(message: String? = null, f: () -> T) { assertFailsWith(message) { val result = f() @@ -18,8 +16,6 @@ inline fun assertArithmeticFails(message: String? = null, f: () -> T) { } } -@Suppress("INVISIBLE_REFERENCE", "INVISIBLE_MEMBER") -@kotlin.internal.InlineOnly inline fun assertInvalidFormat(message: String? = null, f: () -> T) { assertFailsWith(message) { val result = f() @@ -27,8 +23,6 @@ inline fun assertInvalidFormat(message: String? = null, f: () -> T) { } } -@Suppress("INVISIBLE_REFERENCE", "INVISIBLE_MEMBER") -@kotlin.internal.InlineOnly inline fun assertIllegalArgument(message: String? = null, f: () -> T) { assertFailsWith(message) { val result = f() diff --git a/core/common/test/format/YearMonthFormatTest.kt b/core/common/test/format/YearMonthFormatTest.kt index dc8b1df28..b4f6e9c6b 100644 --- a/core/common/test/format/YearMonthFormatTest.kt +++ b/core/common/test/format/YearMonthFormatTest.kt @@ -25,6 +25,7 @@ class YearMonthFormatTest { put(YearMonth(-123456, 5), ("-123456-05" to setOf())) } test(yearMonths, YearMonth.Formats.ISO) + @OptIn(FormatStringsInDatetimeFormats::class) test(yearMonths, YearMonth.Format { byUnicodePattern("yyyy-MM") }) } @@ -43,6 +44,7 @@ class YearMonthFormatTest { put(YearMonth(-123456, 5), ("-12345605" to setOf())) } test(yearMonths, YearMonth.Format { year(); monthNumber() }) + @OptIn(FormatStringsInDatetimeFormats::class) test(yearMonths, YearMonth.Format { byUnicodePattern("yyyyMM") }) } diff --git a/core/common/test/samples/DateTimeUnitSamples.kt b/core/common/test/samples/DateTimeUnitSamples.kt index bea41aa58..caac56834 100644 --- a/core/common/test/samples/DateTimeUnitSamples.kt +++ b/core/common/test/samples/DateTimeUnitSamples.kt @@ -21,7 +21,7 @@ class DateTimeUnitSamples { @Test fun multiplication() { - // Obtaining a measurement unit that's several times larger than another one + // Getting a measurement unit that's several times larger than another one val twoWeeks = DateTimeUnit.WEEK * 2 check(twoWeeks.days == 14) } diff --git a/core/common/test/samples/DayOfWeekSamples.kt b/core/common/test/samples/DayOfWeekSamples.kt index 4c491fcc1..73320fbf5 100644 --- a/core/common/test/samples/DayOfWeekSamples.kt +++ b/core/common/test/samples/DayOfWeekSamples.kt @@ -23,7 +23,6 @@ class DayOfWeekSamples { DayOfWeek.FRIDAY -> check(today.dayOfWeek.isoDayNumber == 5) DayOfWeek.SATURDAY -> check(today.dayOfWeek.isoDayNumber == 6) DayOfWeek.SUNDAY -> check(today.dayOfWeek.isoDayNumber == 7) - else -> TODO("A new day was added to the week?") } } @@ -46,7 +45,7 @@ class DayOfWeekSamples { try { DayOfWeek(0) fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // Expected } } diff --git a/core/common/test/samples/InstantSamples.kt b/core/common/test/samples/InstantSamples.kt index cbb574354..3d3ce3e2a 100644 --- a/core/common/test/samples/InstantSamples.kt +++ b/core/common/test/samples/InstantSamples.kt @@ -19,7 +19,7 @@ class InstantSamples { @Test fun epochSeconds() { - // Getting the number of whole seconds that passed since the Unix epoch + // Getting the number of whole seconds that'd passed since the Unix epoch val instant1 = Instant.fromEpochSeconds(999_999, nanosecondAdjustment = 123_456_789) check(instant1.epochSeconds == 999_999L) val instant2 = Instant.fromEpochSeconds(1_000_000, nanosecondAdjustment = 100_123_456_789) @@ -30,7 +30,7 @@ class InstantSamples { @Test fun nanosecondsOfSecond() { - // Getting the number of nanoseconds that passed since the start of the second + // Getting the number of nanoseconds that'd passed since the start of the second val instant1 = Instant.fromEpochSeconds(999_999, nanosecondAdjustment = 123_456_789) check(instant1.nanosecondsOfSecond == 123_456_789) val instant2 = Instant.fromEpochSeconds(1_000_000, nanosecondAdjustment = 100_123_456_789) @@ -81,7 +81,7 @@ class InstantSamples { repeat(100) { val instant1 = randomInstant() val instant2 = randomInstant() - // in the UTC time zone, earlier instants are represented as earlier datetimes + // in the UTC time zone, earlier instants are represented as earlier datetime values check((instant1 < instant2) == (instant1.toLocalDateTime(TimeZone.UTC) < instant2.toLocalDateTime(TimeZone.UTC))) } diff --git a/core/common/test/samples/LocalTimeSamples.kt b/core/common/test/samples/LocalTimeSamples.kt index 3bbb19e89..ae3482089 100644 --- a/core/common/test/samples/LocalTimeSamples.kt +++ b/core/common/test/samples/LocalTimeSamples.kt @@ -162,7 +162,7 @@ class LocalTimeSamples { @Test fun toSecondOfDay() { - // Obtaining the number of seconds a clock has to advance since 00:00 to reach the given time + // Getting the number of seconds a clock has to advance since 00:00 to reach the given time check(LocalTime(0, 0, 0, 0).toSecondOfDay() == 0) check(LocalTime(0, 0, 0, 1).toSecondOfDay() == 0) check(LocalTime(0, 0, 1, 0).toSecondOfDay() == 1) @@ -174,7 +174,7 @@ class LocalTimeSamples { @Test fun toMillisecondOfDay() { - // Obtaining the number of milliseconds a clock has to advance since 00:00 to reach the given time + // Getting the number of milliseconds a clock has to advance since 00:00 to reach the given time check(LocalTime(0, 0, 0, 0).toMillisecondOfDay() == 0) check(LocalTime(0, 0, 0, 1).toMillisecondOfDay() == 0) check(LocalTime(0, 0, 1, 0).toMillisecondOfDay() == 1000) @@ -186,7 +186,7 @@ class LocalTimeSamples { @Test fun toNanosecondOfDay() { - // Obtaining the number of nanoseconds a clock has to advance since 00:00 to reach the given time + // Getting the number of nanoseconds a clock has to advance since 00:00 to reach the given time check(LocalTime(0, 0, 0, 0).toNanosecondOfDay() == 0L) check(LocalTime(0, 0, 0, 1).toNanosecondOfDay() == 1L) check(LocalTime(0, 0, 1, 0).toNanosecondOfDay() == 1_000_000_000L) diff --git a/core/common/test/samples/MonthSamples.kt b/core/common/test/samples/MonthSamples.kt index a2ab2edd1..4b2c9e0d3 100644 --- a/core/common/test/samples/MonthSamples.kt +++ b/core/common/test/samples/MonthSamples.kt @@ -28,7 +28,6 @@ class MonthSamples { Month.OCTOBER -> check(today.month.number == 10) Month.NOVEMBER -> check(today.month.number == 11) Month.DECEMBER -> check(today.month.number == 12) - else -> TODO("A new month was added to the calendar?") } } @@ -51,7 +50,7 @@ class MonthSamples { try { Month(0) fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // Expected } } diff --git a/core/common/test/samples/TimeZoneSamples.kt b/core/common/test/samples/TimeZoneSamples.kt index a777f4d98..b5fd164ca 100644 --- a/core/common/test/samples/TimeZoneSamples.kt +++ b/core/common/test/samples/TimeZoneSamples.kt @@ -51,7 +51,7 @@ class TimeZoneSamples { @Test fun currentSystemDefault() { - // Obtaining the current system default time zone and using it for formatting + // Getting the current system default time zone and using it for formatting // a fixed-width format for log entries val logTimeFormat = DateTimeComponents.Format { date(LocalDate.Formats.ISO) @@ -134,7 +134,7 @@ class TimeZoneSamples { */ @Test fun offsetAt() { - // Obtaining the offset of a time zone at a specific instant + // Getting the offset of a time zone at a specific instant val zone = TimeZone.of("America/New_York") val instant = Instant.parse("2023-06-02T12:30:00Z") val offset = zone.offsetAt(instant) @@ -164,7 +164,7 @@ class TimeZoneSamples { */ @Test fun offsetIn() { - // Obtaining the offset of a time zone at a specific instant + // Getting the offset of a time zone at a specific instant val zone = TimeZone.of("America/New_York") val instant = Instant.parse("2023-06-02T12:30:00Z") val offset = instant.offsetIn(zone) @@ -244,7 +244,7 @@ class TimeZoneSamples { @Test fun offset() { - // Obtaining the offset of a fixed-offset time zone + // Getting the offset of a fixed-offset time zone val zone = TimeZone.of("UTC+01:30") as FixedOffsetTimeZone check(zone.id == "UTC+01:30") check(zone.offset == UtcOffset(hours = 1, minutes = 30)) diff --git a/core/common/test/samples/UtcOffsetSamples.kt b/core/common/test/samples/UtcOffsetSamples.kt index ec651c71d..118051d68 100644 --- a/core/common/test/samples/UtcOffsetSamples.kt +++ b/core/common/test/samples/UtcOffsetSamples.kt @@ -88,13 +88,13 @@ class UtcOffsetSamples { try { UtcOffset(hours = 1, minutes = 60) fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // Since `hours` is non-zero, `minutes` must be in the range of 0..59 } try { UtcOffset(hours = -1, minutes = 30) fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // Since `hours` is negative, `minutes` must also be negative } } diff --git a/core/common/test/samples/YearMonthSamples.kt b/core/common/test/samples/YearMonthSamples.kt index bffa246fc..0e8384bbf 100644 --- a/core/common/test/samples/YearMonthSamples.kt +++ b/core/common/test/samples/YearMonthSamples.kt @@ -157,7 +157,7 @@ class YearMonthSamples { val endMonth = YearMonth(2024, Month.APRIL) val differenceInMonths = startMonth.until(endMonth, DateTimeUnit.MONTH) check(differenceInMonths == 15L) - // one whole year + january, february, and march + // one whole year and january, february, and march } @Test diff --git a/core/common/test/samples/format/DateTimeComponentsSamples.kt b/core/common/test/samples/format/DateTimeComponentsSamples.kt index dee5bff32..5b4a91253 100644 --- a/core/common/test/samples/format/DateTimeComponentsSamples.kt +++ b/core/common/test/samples/format/DateTimeComponentsSamples.kt @@ -178,7 +178,7 @@ class DateTimeComponentsSamples { check(parsedDate.year == 2023) check(parsedDate.dayOfYear == 44) check(parsedDate.month == null) - check(parsedDate.dayOfMonth == null) + check(parsedDate.day == null) check(parsedDate.dayOfWeek == null) } @@ -311,7 +311,7 @@ class DateTimeComponentsSamples { @Test fun toUtcOffset() { - // Obtaining a UTC offset from the parsed data + // Getting a UTC offset from the parsed data val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val offset = parsed.toUtcOffset() @@ -320,7 +320,7 @@ class DateTimeComponentsSamples { @Test fun toYearMonth() { - // Obtaining a YearMonth from the parsed data + // Getting a YearMonth from the parsed data val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val yearMonth = parsed.toYearMonth() @@ -329,7 +329,7 @@ class DateTimeComponentsSamples { @Test fun toLocalDate() { - // Obtaining a LocalDate from the parsed data + // Getting a LocalDate from the parsed data val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val localDate = parsed.toLocalDate() @@ -338,7 +338,7 @@ class DateTimeComponentsSamples { @Test fun toLocalTime() { - // Obtaining a LocalTime from the parsed data + // Getting a LocalTime from the parsed data val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val localTime = parsed.toLocalTime() @@ -347,7 +347,7 @@ class DateTimeComponentsSamples { @Test fun toLocalDateTime() { - // Obtaining a LocalDateTime from the parsed data + // Getting a LocalDateTime from the parsed data val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val localDateTime = parsed.toLocalDateTime() @@ -356,7 +356,7 @@ class DateTimeComponentsSamples { @Test fun toInstantUsingOffset() { - // Obtaining an Instant from the parsed data using the given UTC offset + // Getting an Instant from the parsed data using the given UTC offset val rfc1123Input = "Sun, 06 Nov 1994 08:49:37 +0300" val parsed = DateTimeComponents.Formats.RFC_1123.parse(rfc1123Input) val instant = parsed.toInstantUsingOffset() @@ -383,7 +383,7 @@ class DateTimeComponentsSamples { setOffset(UtcOffset(3, 30)) } check(formattedCompoundData == "2023-01-02 03:46:58.531 +03:30:00") - // It can also be used to format partial data that is missing some components + // It can also be used to format partial data missing some components val partialFormat = DateTimeComponents.Format { year(); char('-'); monthNumber() } @@ -410,7 +410,7 @@ class DateTimeComponentsSamples { check(parsedCompoundData.toLocalDate() == LocalDate(2023, 1, 2)) check(parsedCompoundData.toUtcOffset() == UtcOffset(3, 30)) check(parsedCompoundData.toInstantUsingOffset() == Instant.parse("2023-01-02T03:46:58.531+03:30")) - // It can also be used to parse partial data that is missing some components + // It can also be used to parse partial data missing some components val partialFormat = DateTimeComponents.Format { year(); char('-'); monthNumber() } @@ -420,7 +420,7 @@ class DateTimeComponentsSamples { try { parsedPartialData.toLocalDate() fail("Expected an exception") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // expected: the day is missing, so LocalDate cannot be constructed } } diff --git a/core/common/test/samples/format/DateTimeFormatBuilderSamples.kt b/core/common/test/samples/format/DateTimeFormatBuilderSamples.kt index a8190acd5..614e2fda2 100644 --- a/core/common/test/samples/format/DateTimeFormatBuilderSamples.kt +++ b/core/common/test/samples/format/DateTimeFormatBuilderSamples.kt @@ -82,7 +82,7 @@ class DateTimeFormatBuilderSamples { try { LocalDate.Format { optional { year() }} fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // Since `year` has no optional component, it is an error to put it inside `optional`. // Use `alternativeParsing` for parsing-only optional components. } diff --git a/core/common/test/samples/format/DateTimeFormatSamples.kt b/core/common/test/samples/format/DateTimeFormatSamples.kt index 1a91c7a25..34136a09b 100644 --- a/core/common/test/samples/format/DateTimeFormatSamples.kt +++ b/core/common/test/samples/format/DateTimeFormatSamples.kt @@ -19,7 +19,7 @@ class DateTimeFormatSamples { @Test fun formatTo() { - // Appending a formatted date to an `Appendable` (e.g. a `StringBuilder`) + // Appending a formatted date to an `Appendable` (e.g., a `StringBuilder`) val sb = StringBuilder() sb.append("Today is ") LocalDate.Formats.ISO.formatTo(sb, LocalDate(2024, 4, 5)) @@ -28,18 +28,18 @@ class DateTimeFormatSamples { @Test fun parse() { - // Parsing a string that is expected to be in the given format + // Parsing a string expected to be in the given format check(LocalDate.Formats.ISO.parse("2021-02-07") == LocalDate(2021, 2, 7)) try { LocalDate.Formats.ISO.parse("2021-02-07T") fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // the input string is not in the expected format } try { LocalDate.Formats.ISO.parse("2021-02-40") fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // the input string is in the expected format, but the value is invalid } // to parse strings that have valid formats but invalid values, use `DateTimeComponents`: @@ -108,7 +108,7 @@ class DateTimeFormatSamples { try { LocalDate.parse("02/7 0457", format) fail("Expected IllegalArgumentException") - } catch (e: IllegalArgumentException) { + } catch (_: IllegalArgumentException) { // parsing without padding is not allowed, and the day-of-month was not padded } } diff --git a/core/common/test/samples/format/UnicodeSamples.kt b/core/common/test/samples/format/UnicodeSamples.kt index ad9438e0e..e12df4479 100644 --- a/core/common/test/samples/format/UnicodeSamples.kt +++ b/core/common/test/samples/format/UnicodeSamples.kt @@ -12,7 +12,7 @@ import kotlin.test.* class UnicodeSamples { @Test fun byUnicodePattern() { - // Using the Unicode pattern to define a custom format and obtain the corresponding Kotlin code + // Using the Unicode pattern to define a custom format and get the corresponding Kotlin code val customFormat = LocalDate.Format { @OptIn(FormatStringsInDatetimeFormats::class) byUnicodePattern("MM/dd uuuu") diff --git a/core/common/test/samples/format/YearMonthFormatSamples.kt b/core/common/test/samples/format/YearMonthFormatSamples.kt index 710aaf3bc..47e497381 100644 --- a/core/common/test/samples/format/YearMonthFormatSamples.kt +++ b/core/common/test/samples/format/YearMonthFormatSamples.kt @@ -6,12 +6,10 @@ package kotlinx.datetime.test.samples.format import kotlinx.datetime.LocalDate -import kotlinx.datetime.LocalDateTime import kotlinx.datetime.YearMonth import kotlinx.datetime.format.DayOfWeekNames import kotlinx.datetime.format.MonthNames import kotlinx.datetime.format.Padding -import kotlinx.datetime.format.alternativeParsing import kotlinx.datetime.format.char import kotlin.test.Test @@ -20,7 +18,7 @@ class YearMonthFormatSamples { fun year() { // Using the year number in a custom format val format = LocalDate.Format { - year(); char(' '); monthNumber(); char('/'); dayOfMonth() + year(); char(' '); monthNumber(); char('/'); day() } check(format.format(LocalDate(2021, 1, 13)) == "2021 01/13") check(format.format(LocalDate(13, 1, 13)) == "0013 01/13") @@ -32,7 +30,7 @@ class YearMonthFormatSamples { fun yearTwoDigits() { // Using two-digit years in a custom format val format = LocalDate.Format { - yearTwoDigits(baseYear = 1960); char(' '); monthNumber(); char('/'); dayOfMonth() + yearTwoDigits(baseYear = 1960); char(' '); monthNumber(); char('/'); day() } check(format.format(LocalDate(1960, 1, 13)) == "60 01/13") check(format.format(LocalDate(2000, 1, 13)) == "00 01/13") @@ -46,12 +44,12 @@ class YearMonthFormatSamples { fun monthNumber() { // Using month number with various paddings in a custom format val zeroPaddedMonths = LocalDate.Format { - monthNumber(); char('/'); dayOfMonth(); char('/'); year() + monthNumber(); char('/'); day(); char('/'); year() } check(zeroPaddedMonths.format(LocalDate(2021, 1, 13)) == "01/13/2021") check(zeroPaddedMonths.format(LocalDate(2021, 12, 13)) == "12/13/2021") val spacePaddedMonths = LocalDate.Format { - monthNumber(padding = Padding.SPACE); char('/'); dayOfMonth(); char('/'); year() + monthNumber(padding = Padding.SPACE); char('/'); day(); char('/'); year() } check(spacePaddedMonths.format(LocalDate(2021, 1, 13)) == " 1/13/2021") check(spacePaddedMonths.format(LocalDate(2021, 12, 13)) == "12/13/2021") @@ -61,7 +59,7 @@ class YearMonthFormatSamples { fun monthName() { // Using strings for month names in a custom format val format = LocalDate.Format { - monthName(MonthNames.ENGLISH_FULL); char(' '); dayOfMonth(); char('/'); year() + monthName(MonthNames.ENGLISH_FULL); char(' '); day(); char('/'); year() } check(format.format(LocalDate(2021, 1, 13)) == "January 13/2021") check(format.format(LocalDate(2021, 12, 13)) == "December 13/2021") @@ -75,7 +73,7 @@ class YearMonthFormatSamples { chars(", ") dayOfWeek(DayOfWeekNames.ENGLISH_ABBREVIATED) char(' ') - dayOfMonth() + day() } check(format.format(LocalDate(2021, 1, 13)) == "2021-01, Wed 13") } @@ -87,7 +85,7 @@ class YearMonthFormatSamples { val format = LocalDate.Format { monthName(MonthNames.ENGLISH_ABBREVIATED) // "Jan", "Feb", ... char(' ') - dayOfMonth() + day() chars(", ") year() } @@ -131,7 +129,7 @@ class YearMonthFormatSamples { val format = LocalDate.Format { monthName(MonthNames.ENGLISH_FULL) char(' ') - dayOfMonth() + day() chars(", ") year() } @@ -144,7 +142,7 @@ class YearMonthFormatSamples { val format = LocalDate.Format { monthName(MonthNames.ENGLISH_ABBREVIATED) char(' ') - dayOfMonth() + day() chars(", ") year() } diff --git a/core/commonKotlin/src/UtcOffset.kt b/core/commonKotlin/src/UtcOffset.kt index e947e88fd..83c67262d 100644 --- a/core/commonKotlin/src/UtcOffset.kt +++ b/core/commonKotlin/src/UtcOffset.kt @@ -97,8 +97,7 @@ public actual class UtcOffset private constructor(public actual val totalSeconds @ThreadLocal private var utcOffsetCache: MutableMap = mutableMapOf() -@Suppress("ACTUAL_FUNCTION_WITH_DEFAULT_ARGUMENTS") -public actual fun UtcOffset(hours: Int? = null, minutes: Int? = null, seconds: Int? = null): UtcOffset = +public actual fun UtcOffset(hours: Int?, minutes: Int?, seconds: Int?): UtcOffset = when { hours != null -> UtcOffset.ofHoursMinutesSeconds(hours, minutes ?: 0, seconds ?: 0) diff --git a/core/commonKotlin/test/ThreeTenBpLocalDateTimeTest.kt b/core/commonKotlin/test/ThreeTenBpLocalDateTimeTest.kt index d1b7e0971..627221cb3 100644 --- a/core/commonKotlin/test/ThreeTenBpLocalDateTimeTest.kt +++ b/core/commonKotlin/test/ThreeTenBpLocalDateTimeTest.kt @@ -8,6 +8,7 @@ package kotlinx.datetime.test import kotlinx.datetime.* +import kotlinx.datetime.LocalDateTime import kotlin.test.* class ThreeTenBpLocalDateTimeTest { @@ -91,8 +92,8 @@ class ThreeTenBpLocalDateTimeTest { Pair(Pair("2012-06-15T12:30:40.500", "2012-06-16T12:30:41.501"), Pair(DateTimeUnit.SECOND, 86400L + 1))) for ((values, interval) in data) { val (v1, v2) = values - val dt1 = v1.toLocalDateTime() - val dt2 = v2.toLocalDateTime() + val dt1 = LocalDateTime.parse(v1) + val dt2 = LocalDateTime.parse(v2) val (unit, length) = interval assertEquals(length, dt1.until(dt2, unit)) assertEquals(-length, dt2.until(dt1, unit)) diff --git a/core/wasmJs/src/PlatformSpecifics.kt b/core/wasmJs/src/PlatformSpecifics.kt index 459c2a81d..e93b6a27b 100644 --- a/core/wasmJs/src/PlatformSpecifics.kt +++ b/core/wasmJs/src/PlatformSpecifics.kt @@ -7,13 +7,13 @@ package kotlinx.datetime.internal import kotlinx.datetime.internal.JSJoda.ZoneRulesProvider import kotlin.js.unsafeCast -private fun getZones(rulesProvider: JsAny): JsAny = js("rulesProvider.getTzdbData().zones") -private fun getLinks(rulesProvider: JsAny): JsAny = js("rulesProvider.getTzdbData().links") +private fun getZones(rulesProvider: ZoneRulesProvider): JsAny = js("rulesProvider.getTzdbData().zones") +private fun getLinks(rulesProvider: ZoneRulesProvider): JsAny = js("rulesProvider.getTzdbData().links") internal actual fun readTzdb(): Pair, List>? = try { jsTry { - val zones = getZones(ZoneRulesProvider as JsAny) - val links = getLinks(ZoneRulesProvider as JsAny) + val zones = getZones(ZoneRulesProvider) + val links = getLinks(ZoneRulesProvider) zones.unsafeCast>().toList() to links.unsafeCast>().toList() } } catch (_: Throwable) { @@ -21,7 +21,7 @@ internal actual fun readTzdb(): Pair, List>? = try { } private fun JsArray.toList(): List = buildList { - for (i in 0 until toList@length) { + for (i in 0 until this@toList.length) { add(this@toList[i].toString()) } } diff --git a/core/windows/src/internal/TzdbInRegistry.kt b/core/windows/src/internal/TzdbInRegistry.kt index 104c00225..4e3d22373 100644 --- a/core/windows/src/internal/TzdbInRegistry.kt +++ b/core/windows/src/internal/TzdbInRegistry.kt @@ -137,7 +137,7 @@ private fun processTimeZonesInRegistry(onTimeZone: (String, PerYearZoneRulesData val tziRecord = zoneInfoBuffer.readZoneRules(tzHKey, "TZI") val historicData = try { dynamicDstHkeyBuffer.readHistoricDataFromRegistry(tzHKey, dwordBuffer, zoneInfoBuffer) - } catch (e: IllegalStateException) { + } catch (_: IllegalStateException) { emptyList() } onTimeZone(windowsTzNameBuffer.toKString(), tziRecord, historicData) @@ -236,7 +236,7 @@ private class RegistryTimeZoneInfoBuffer private constructor( fun allocate(scope: MemScope, cbData: DWORDVar): RegistryTimeZoneInfoBuffer = RegistryTimeZoneInfoBuffer(scope.allocArray(SIZE_BYTES), cbData) - private val SIZE_BYTES = 44 + private const val SIZE_BYTES = 44 } @OptIn(ExperimentalNativeApi::class) diff --git a/core/windows/test/TimeZoneRulesCompleteTest.kt b/core/windows/test/TimeZoneRulesCompleteTest.kt index 12d4c7964..2868085a8 100644 --- a/core/windows/test/TimeZoneRulesCompleteTest.kt +++ b/core/windows/test/TimeZoneRulesCompleteTest.kt @@ -9,7 +9,9 @@ package kotlinx.datetime.test import kotlinx.cinterop.* import kotlinx.cinterop.ptr import kotlinx.datetime.* +import kotlinx.datetime.LocalDateTime import kotlinx.datetime.internal.* +import kotlinx.datetime.number import platform.windows.* import kotlin.test.* import kotlin.time.Duration.Companion.hours @@ -186,8 +188,8 @@ private fun LocalDateTime.toSystemTime(outputBuffer: CPointer) { require(year in 1601..30827) outputBuffer.pointed.apply { wYear = year.convert() - wMonth = monthNumber.convert() - wDay = dayOfMonth.convert() + wMonth = month.number.convert() + wDay = day.convert() wDayOfWeek = (dayOfWeek.isoDayNumber % 7).convert() wHour = hour.convert() wMinute = minute.convert() @@ -199,8 +201,8 @@ private fun LocalDateTime.toSystemTime(outputBuffer: CPointer) { private fun SYSTEMTIME.toLocalDateTime(): LocalDateTime = LocalDateTime( year = wYear.convert(), - monthNumber = wMonth.convert(), - dayOfMonth = wDay.convert(), + month = wMonth.convert(), + day = wDay.convert(), hour = wHour.convert(), minute = wMinute.convert(), second = wSecond.convert(), diff --git a/integration-testing/js-without-timezones/build.gradle.kts b/integration-testing/js-without-timezones/build.gradle.kts index 794313fed..9a3c15a3f 100644 --- a/integration-testing/js-without-timezones/build.gradle.kts +++ b/integration-testing/js-without-timezones/build.gradle.kts @@ -22,7 +22,7 @@ kotlin { sourceSets.all { val suffixIndex = name.indexOfLast { it.isUpperCase() } val targetName = name.substring(0, suffixIndex) - val suffix = name.substring(suffixIndex).toLowerCase(Locale.ROOT).takeIf { it != "main" } + val suffix = name.substring(suffixIndex).lowercase(Locale.ROOT).takeIf { it != "main" } kotlin.srcDir("$targetName/${suffix ?: "src"}") resources.srcDir("$targetName/${suffix?.let { it + "Resources" } ?: "resources"}") } diff --git a/integration-testing/serialization/build.gradle.kts b/integration-testing/serialization/build.gradle.kts index 0633c9ed1..2ace2e460 100644 --- a/integration-testing/serialization/build.gradle.kts +++ b/integration-testing/serialization/build.gradle.kts @@ -1,3 +1,4 @@ +import org.jetbrains.kotlin.gradle.ExperimentalWasmDsl import org.jetbrains.kotlin.gradle.dsl.JsModuleKind import java.util.Locale @@ -61,12 +62,13 @@ kotlin { } } - + @OptIn(ExperimentalWasmDsl::class) wasmJs { nodejs { } } + @OptIn(ExperimentalWasmDsl::class) wasmWasi { nodejs { } @@ -75,7 +77,7 @@ kotlin { sourceSets.all { val suffixIndex = name.indexOfLast { it.isUpperCase() } val targetName = name.substring(0, suffixIndex) - val suffix = name.substring(suffixIndex).toLowerCase(Locale.ROOT).takeIf { it != "main" } + val suffix = name.substring(suffixIndex).lowercase(Locale.ROOT).takeIf { it != "main" } kotlin.srcDir("$targetName/${suffix ?: "src"}") resources.srcDir("$targetName/${suffix?.let { it + "Resources" } ?: "resources"}") } diff --git a/integration-testing/serialization/common/test/DateTimePeriodSerializationTest.kt b/integration-testing/serialization/common/test/DateTimePeriodSerializationTest.kt index 9bd58dc96..25b9a2c8d 100644 --- a/integration-testing/serialization/common/test/DateTimePeriodSerializationTest.kt +++ b/integration-testing/serialization/common/test/DateTimePeriodSerializationTest.kt @@ -13,6 +13,8 @@ import kotlin.test.* class DateTimePeriodSerializationTest { + private val jsonIgnoringUnknownKeys = Json { ignoreUnknownKeys = true } + private fun datePeriodIso8601Serialization( datePeriodSerializer: KSerializer, dateTimePeriodSerializer: KSerializer @@ -33,7 +35,7 @@ class DateTimePeriodSerializationTest { } // time-based keys should not be considered unknown here assertFailsWith { - Json { ignoreUnknownKeys = true }.decodeFromString(datePeriodSerializer, "\"P3DT1H\"") + jsonIgnoringUnknownKeys.decodeFromString(datePeriodSerializer, "\"P3DT1H\"") } // presence of time-based keys should not be a problem if the values are 0 Json.decodeFromString(datePeriodSerializer, "\"P3DT0H\"") @@ -59,7 +61,7 @@ class DateTimePeriodSerializationTest { } // time-based keys should not be considered unknown here assertFailsWith { - Json { ignoreUnknownKeys = true }.decodeFromString(datePeriodSerializer, "{\"hours\":3}") + jsonIgnoringUnknownKeys.decodeFromString(datePeriodSerializer, "{\"hours\":3}") } // presence of time-based keys should not be a problem if the values are 0 Json.decodeFromString(datePeriodSerializer, "{\"hours\":0}") diff --git a/timezones/full/build.gradle.kts b/timezones/full/build.gradle.kts index a22e986fc..77adfc9e2 100644 --- a/timezones/full/build.gradle.kts +++ b/timezones/full/build.gradle.kts @@ -24,7 +24,7 @@ node { val tzdbVersion: String by rootProject.properties version = "$tzdbVersion-spi.$version" -val convertedKtFilesDir = File(project.buildDir, "convertedTimesZones-full/src/internal/tzData") +val convertedKtFilesDir = project.layout.buildDirectory.dir("convertedTimesZones-full/src/internal/tzData") val tzdbDirectory = File(project.projectDir, "tzdb") val timeTzdbInstall by tasks.creating(NpmTask::class) { @@ -51,7 +51,7 @@ val generateZoneInfo by tasks.registering { inputs.dir(tzdbDirectory) outputs.dir(convertedKtFilesDir) doLast { - generateZoneInfosResources(tzdbDirectory, convertedKtFilesDir, tzdbVersion) + generateZoneInfosResources(tzdbDirectory, convertedKtFilesDir.get(), tzdbVersion) } } @@ -73,7 +73,7 @@ kotlin { sourceSets { commonMain { dependencies { - compileOnly(project(":kotlinx-datetime")) + api(project(":kotlinx-datetime")) kotlin.srcDir(generateZoneInfo) } }