Internationalization 如何使用kotlin js支持i18n

Internationalization 如何使用kotlin js支持i18n,internationalization,kotlin-js,Internationalization,Kotlin Js,我目前正在尝试将i18n支持添加到kotlin js项目中(无响应) 添加了资源包文件(strings.properties、strings\u en.properties) 试图通过ResourceBundle.getBundle获取它们我相信ResourceBundle是JVM特有的,对于Kotlin/JS,我认为,您可以尝试任何JS i18n库。此外,您可以找到一些Kotlin多平台解决方案,例如,流体的使用非常有趣,但不适合我的使用。我们正在使用transifex,所以我需要一种从js

我目前正在尝试将i18n支持添加到kotlin js项目中(无响应)

  • 添加了资源包文件(strings.properties、strings\u en.properties)

  • 试图通过ResourceBundle.getBundle获取它们我相信ResourceBundle是JVM特有的,对于Kotlin/JS,我认为,您可以尝试任何JS i18n库。此外,您可以找到一些Kotlin多平台解决方案,例如,流体的使用非常有趣,但不适合我的使用。我们正在使用transifex,所以我需要一种从json或属性文件获取我们自己的DEF的方法。目前我正在尝试javasrcipt方法。更新
    return document.create.div {
            span("mid-title") {
                +i18n here (ResourceBundle.getBundle()?)
            }....
    
     fun loadJSON(callback: (response: String) -> Unit) {
        val xobj = XMLHttpRequest()
        xobj.overrideMimeType("application/json")
        xobj.open("GET", "test.json", true)
        xobj.onreadystatechange = {
    
            if (xobj.readyState.toInt() == 4 && xobj.status.toInt() == 200) {
                // Required use of an anonymous callback
                // as .open() will NOT return a value but simply returns undefined in asynchronous mode
                callback(xobj.responseText);
            }
        }
        xobj.send(null)
    }
    
    class LanguageSupport(private val folder: String = "", private val lang: String) {
        private lateinit var currentLang: Json
    
        private val languageMutableStateFlow = MutableStateFlow<LanguageSupportState>(
            LanguageSupportState.LanguageInit
        )
        val languageStateFlow: StateFlow<LanguageSupportState> = languageMutableStateFlow
    
        init {
            loadJSON()
        }
    
        fun get(key: String): String {
            val value = currentLang[key]
            check(value != null) {
                throw Exception("key not found to load language definition")
            }
            return if (value is String) {
                value
            } else {
                throw Exception("value of key is not a string")
            }
        }
    
        fun get(key: String, vararg placeholders: String): String {
            val value = currentLang[key]
            check(value != null) {
                throw Exception("key not found to load language definition")
            }
            return if (value is String) {
                var finalValue: String = value
                for (item in placeholders) {
                    finalValue = finalValue.replaceFirst(PLACEHOLDER, item)
                }
                finalValue
            } else {
                throw Exception("value of key is not a string")
            }
        }
    
        private fun loadJSON() {
            val xobj = XMLHttpRequest()
            xobj.overrideMimeType("application/json")
            xobj.open("GET", "${folder}test_${lang}.json", true)
            xobj.onreadystatechange = {
    
                if (xobj.readyState.toInt() == 4 && xobj.status.toInt() == 200) {
                    // Required use of an anonymous callback
                    // as .open() will NOT return a value but simply returns undefined in asynchronous mode
                    currentLang = JSON.parse(xobj.responseText)
                    languageMutableStateFlow.value = LanguageSupportState.LanguageLoaded
                }
            }
            xobj.send(null)
        }
    
        companion object {
            const val PLACEHOLDER = "%s"
        }
    }
    
    sealed class LanguageSupportState {
        object LanguageLoaded : LanguageSupportState()
        object LanguageError : LanguageSupportState()
        object LanguageInit : LanguageSupportState()
    }
    
    single { (folder: String, language: String) ->
            LanguageSupport(
                folder = folder,
                lang = language,
            )
        }