From d464155e334998bc2b770a441e7a45c65aa00c30 Mon Sep 17 00:00:00 2001 From: Giorgio Garofalo Date: Thu, 1 Aug 2024 15:19:16 +0200 Subject: [PATCH] Set up locales --- .../quarkdown/document/locale/JVMLocale.kt | 18 +++++++ .../document/locale/JVMLocaleLoader.kt | 14 +++++ .../quarkdown/document/locale/Locale.kt | 29 ++++++++++ .../quarkdown/document/locale/LocaleLoader.kt | 18 +++++++ .../kotlin/eu/iamgio/quarkdown/MiscTest.kt | 54 +++++++++++++++++++ 5 files changed, 133 insertions(+) create mode 100644 core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocale.kt create mode 100644 core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocaleLoader.kt create mode 100644 core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/Locale.kt create mode 100644 core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/LocaleLoader.kt create mode 100644 core/src/test/kotlin/eu/iamgio/quarkdown/MiscTest.kt diff --git a/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocale.kt b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocale.kt new file mode 100644 index 00000000..2b78da1f --- /dev/null +++ b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocale.kt @@ -0,0 +1,18 @@ +package eu.iamgio.quarkdown.document.locale + +/** + * [Locale] implementation using [java.util.Locale]. + */ +internal class JVMLocale(private val jvmLocale: java.util.Locale) : Locale { + override val code: String + get() = jvmLocale.language + + override val countryCode: String? + get() = jvmLocale.country.takeIf { it.isNotBlank() } + + override val localizedName: String + get() = jvmLocale.getDisplayLanguage(jvmLocale) + + override val localizedCountryName: String? + get() = jvmLocale.getDisplayCountry(jvmLocale).takeIf { it.isNotBlank() } +} diff --git a/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocaleLoader.kt b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocaleLoader.kt new file mode 100644 index 00000000..a04ca626 --- /dev/null +++ b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/JVMLocaleLoader.kt @@ -0,0 +1,14 @@ +package eu.iamgio.quarkdown.document.locale + +/** + * Loader of [JVMLocale]s. + */ +internal object JVMLocaleLoader : LocaleLoader { + override val all: Iterable + get() = java.util.Locale.getAvailableLocales().map(::JVMLocale) + + override fun fromTag(tag: String): Locale? = + java.util.Locale.forLanguageTag(tag) + ?.let(::JVMLocale) + ?.takeIf { it.code.isNotBlank() } +} diff --git a/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/Locale.kt b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/Locale.kt new file mode 100644 index 00000000..5cb412ee --- /dev/null +++ b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/Locale.kt @@ -0,0 +1,29 @@ +package eu.iamgio.quarkdown.document.locale + +/** + * Represents a locale, which defines the document language. + */ +interface Locale { + /** + * Language code of the locale. + * For instance, `en` for English and `it` for Italian. + */ + val code: String + + /** + * Country code of the locale. + */ + val countryCode: String? + + /** + * Name of the locale, possibly in the locale's language itself. + * For instance, `English` for English and `italiano` for Italian. + */ + val localizedName: String + + /** + * Name of the country of the locale, possibly in the locale's language itself. + * For instance, `United States` for `en-US` and `Italia` for `it`. + */ + val localizedCountryName: String? +} diff --git a/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/LocaleLoader.kt b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/LocaleLoader.kt new file mode 100644 index 00000000..7481f5a4 --- /dev/null +++ b/core/src/main/kotlin/eu/iamgio/quarkdown/document/locale/LocaleLoader.kt @@ -0,0 +1,18 @@ +package eu.iamgio.quarkdown.document.locale + +/** + * Loader of [Locale]s. + */ +interface LocaleLoader { + /** + * All available locales. + */ + val all: Iterable + + /** + * @param tag language code of the locale and optionally the country code, separated by a hyphen. + * Example: `en`, `en-US`, `it`, `fr-CA` + * @return [Locale] with the given tag, or `null` if not found + */ + fun fromTag(tag: String): Locale? +} diff --git a/core/src/test/kotlin/eu/iamgio/quarkdown/MiscTest.kt b/core/src/test/kotlin/eu/iamgio/quarkdown/MiscTest.kt new file mode 100644 index 00000000..c081cb6a --- /dev/null +++ b/core/src/test/kotlin/eu/iamgio/quarkdown/MiscTest.kt @@ -0,0 +1,54 @@ +package eu.iamgio.quarkdown + +import eu.iamgio.quarkdown.document.locale.JVMLocaleLoader +import org.junit.Assert.assertEquals +import org.junit.Assert.assertTrue +import kotlin.test.Test +import kotlin.test.assertNotNull +import kotlin.test.assertNull + +/** + * Tests for miscellaneous classes. + */ +class MiscTest { + @Test + fun locale() { + val retriever = JVMLocaleLoader + + with(retriever.fromTag("en")) { + assertNotNull(this) + assertEquals("en", code) + assertEquals("English", localizedName) + assertNull(countryCode) + assertNull(localizedCountryName) + } + + with(retriever.fromTag("it")) { + assertNotNull(this) + assertEquals("it", code) + assertEquals("italiano", localizedName) + assertNull(countryCode) + assertNull(localizedCountryName) + } + + with(retriever.fromTag("en-US")) { + assertNotNull(this) + assertEquals("en", code) + assertEquals("English", localizedName) + assertEquals("US", countryCode) + assertEquals("United States", localizedCountryName) + } + + with(retriever.fromTag("fr-CA")) { + assertNotNull(this) + assertEquals("fr", code) + assertEquals("français", localizedName) + assertEquals("CA", countryCode) + assertEquals("Canada", localizedCountryName) + } + + assertNull(retriever.fromTag("nonexistent")) + + assertTrue(retriever.all.iterator().hasNext()) + } +}