3

我正在为 jvm 和 js 创建一个 kotlin mutliplatform 项目。我的 build.gradle.kts 看起来像这样:

plugins {
    id ("org.jetbrains.kotlin.multiplatform")
}

repositories {
    mavenCentral()
}

kotlin {
    jvm() {
        compilations["main"].kotlinOptions{
            jvmTarget = "1.8"
        }
    }
    js() {
        compilations["main"].kotlinOptions{
            outputFile = "${buildDir}/nodejs/common.js"
            moduleKind = "commonjs"
            sourceMap = true
            verbose = true
        }
    }

    sourceSets {
        val commonMain by getting {
            dependencies {
                implementation (kotlin("stdlib"))
                implementation (kotlin("stdlib-common"))
            }
        }
        val commonTest by getting {
            dependencies {
                implementation (kotlin("test-common"))
                implementation (kotlin("test-annotations-common"))
            }
        }
        jvm().compilations["main"].defaultSourceSet  {
            dependencies {
                implementation (kotlin("stdlib-jdk8"))
            }
        }
        jvm().compilations["test"].defaultSourceSet  {
            dependencies {
                implementation (kotlin("test"))
                implementation (kotlin("test-junit"))
            }
        }
        js().compilations["main"].defaultSourceSet {
            dependencies {
                implementation (kotlin("stdlib-js"))
            }

        }
        js().compilations["test"].defaultSourceSet  {
            dependencies {
                implementation (kotlin("test-js"))
            }
        }
    }
}

当我构建项目时,会创建一个 common.js,其内容如下所示:

(function (_, Kotlin) {
    'use strict';
    var Kind_CLASS = Kotlin.Kind.CLASS;
    var ArrayList_init = Kotlin.kotlin.collections.ArrayList_init_287e2$;
    var emptyList = Kotlin.kotlin.collections.emptyList_287e2$;
    var NotImplementedError_init = Kotlin.kotlin.NotImplementedError;
    function commonSharedCode(platform) {
        return 'Common: Hi! ' + platform.greetingMethod + '(' + platform.name + ') AND NOW IN BEAUTIFUL ' + platform.beautifulPlatform();
    }
    function Platform(greetingMethod, name) {
        this.greetingMethod = greetingMethod;
        this.name = name;
    }
    Platform.prototype.beautifulPlatform = function () {
        return '***' + this.name + '***';
    };
    // ... //
    return _;
}(module.exports, require('kotlin')));

现在我在项目外部创建了一个简单的 javascript 文件并尝试使用创建的代码(就像您在教程中看到的那样 - 他们创建了一个使用 mutliplatform 项目作为依赖项的应用程序)。这似乎是不可能的,因为创建的代码没有导出任何功能等。我希望能够做类似的事情

const common = require('common');

function myTest () {
    console.log(common.Platform('Hello', 'World'));
}

您是否知道如何构建项目以完成这些事情?

4

1 回答 1

1

您是否尝试过实际运行上述代码?如果是,会发生什么?这个问题有些模棱两可,所以很难确定真正的问题是什么。

无论如何,让我以一种快速而肮脏的方式分享我设法做的事情。也许这个概念证明会解除你的障碍。

  1. 我在我的 Kotlin/JS 项目中创建了这样的 Kotlin 文件:
class TestLibraryClass {
    @JsName("appendNumberToString")
    fun appendNumberToString(string: String, number: Int) =
        "Appending: $string - $number"

    fun functionWithoutJsNameAnnotation(someStr: String)
            = someStr
}
  1. 我构建了项目,并在build/distributions/project-name.js.

  2. 我在具有 JS 控制台的 Web 浏览器中打开了任何网页,并project-name.js像这样粘贴了文件的代码 - 这相当于您尝试使用require

importedKotlinLib = ...pasted the code here...
[hit enter]
  1. 我创建了一个实例TestLibraryClass
testLibraryClassInstance = new importedKotlinLib.TestLibraryClass()
  1. 我能够调用这两个函数,第一个具有自定义名称以避免名称损坏,第二个具有损坏名称:

JS 控制台转储

我在这里了解了名称修改(以及如何解决它)。请注意,类名TestLibraryClass没有错位。我测试了顶级函数的名称是否被破坏。


关于大局 - 如果官方支持准备用 Kotlin 编写的 JS 库 - 我在这里并不完全清楚。一旦我发现,我会很乐意更新这个答案。我也在考虑将 Kotlin/JS 整合到我公司的项目中。

于 2020-02-22T12:00:33.910 回答