使用 Gradle 在 Kotlin 服务器和客户端项目之间共享代码

Shared code between Kotlin server and client projects using Gradle

我想使用单独的 shared 项目在服务器 (JVM) 和客户端 (JS) 之间共享一些代码。我看过 solution using Maven, but I'm not sure how to convert this to a Gradle project. Also, there aren't any examples of shared projects in the official guide。那么,具有这种设置的最小 build.gradle 会是什么样子呢?

使用来自另一个 Kotlin 项目的依赖项构建 Kotlin2JS 项目似乎需要以任何方式复制源代码。一种方法是将 Kotlin 项目源代码目录添加到 Kotlin2JS 项目源代码集目录中。

这可以在 project 范围内使用以下行来完成:

sourceSets {  
    main.kotlin.srcDirs += project(':shared').sourceSets.main.kotlin.srcDirs
}

请查看整个项目结构:

root/
  shared/
    src/main/kotlin
    build.gradle
  client/
    src/main/kotlin
  server/
    src/main/kotlin
  build.gradle
  settings.gradle

settings.gradle中:

include 'shared', 'server', 'client'

build.gradle中:

group 'com.example.multiproject'
version '1.0-SNAPSHOT'

buildscript {
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.0.0-beta-4589"
    }
}

subprojects {
    repositories {
        mavenCentral()
    }
}

project(':client') {
    evaluationDependsOn(':shared')

    apply plugin: 'kotlin2js'
    compileKotlin2Js.kotlinOptions.sourceMap = true
    compileKotlin2Js.kotlinOptions.outputFile = "${projectDir}/web/js/app.js"
    compileKotlin2Js.kotlinOptions.suppressWarnings = true
    compileKotlin2Js.kotlinOptions.verbose = true

    sourceSets {
        main.kotlin.srcDirs += project(':shared').sourceSets.main.kotlin.srcDirs
    }
    dependencies {
        compile 'org.jetbrains.kotlin:kotlin-js-library:1.0.0-beta-4589'
    }
}

project(':server') {
    apply plugin: 'kotlin'
    dependencies {
        compile 'org.jetbrains.kotlin:kotlin-stdlib:1.0.0-beta-4589'
        compile project(':shared')
    }
}

请注意,shared 项目应包含其自己的 build.gradle

为了完整起见,这是我几乎同时使用 hotkey:

创建的设置

主要settings.gradleinclude 'shared', 'client', 'server'

主要build.gradle:

buildscript {
  ext {
    kotlinVer = '1.0.0-beta-4589'
  }
  repositories {
    mavenCentral()
    maven {
      url 'http://oss.sonatype.org/content/repositories/snapshots'
    }
  }
  dependencies {
    classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlinVer"
  }
}

allprojects {
  apply plugin: 'idea'
  group = 'some.company'
  version = '0.0.1'

  ext {
    kotlinVer = '1.0.0-beta-4589'
    // Lib versions go there.
  }
  repositories {
    mavenLocal()
    mavenCentral()
    maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }
    maven { url "https://oss.sonatype.org/content/repositories/releases/" }
  }
}

project('shared') {
  apply plugin: 'kotlin'
}

project('server') {
  apply plugin: 'kotlin'
  apply plugin: 'application'

  mainClassName = 'some.company.Main'
  dependencies {
    compile project(':shared')
  }
}

project('client') {
  apply plugin: 'kotlin2js'
  dependencies {
    compile project(':shared')
  }
}

客户build.gradle

apply plugin: 'kotlin2js'

compileKotlin2Js {
  kotlinOptions.outputFile = "server/src/main/resources/static/js/app.js"
  kotlinOptions.sourceMap = true
}

sourceSets {
  main.kotlin.srcDirs += '../shared/src/main/kotlin'
  // hotkey's solution:
  // main.kotlin.srcDirs += project(':shared').sourceSets.main.kotlin.srcDirs
}

dependencies {
  compile "org.jetbrains.kotlin:kotlin-js-library:$kotlinVer"
}

服务器build.gradle:

apply plugin: 'kotlin'

sourceCompatibility = 1.7
targetCompatibility = 1.7

dependencies {
  // Libs go there.
  compile "org.jetbrains.kotlin:kotlin-stdlib:$kotlinVer"
  testCompile "org.jetbrains.kotlin:kotlin-test-junit:$kotlinVer"
}

共享项目的 build.gradle 仅包含 apply plugin: 'kotlin' 而且,好吧,我不确定使用共享库是否简单(或者在许多情况下是必需的),所以我想它甚至可以保留空。

gradle client:build 在服务器的静态资源文件夹中生成 JavaScript 文件。 gradle idea 生成具有正确链接的依赖项和源文件夹的 IntelliJ 项目(只要使用默认名称 - src/main/kotlin 等;请参阅官方 Kotlin Gradle 自定义源目录手册)。