cherry pick changes and fixes from annotation-processing-branch
diff --git a/.bazelproject b/.bazelproject
index 7828fba..529a61b 100644
--- a/.bazelproject
+++ b/.bazelproject
@@ -17,7 +17,7 @@
.
targets:
- //kotlin/workers:worker_for_ide
+ //kotlin/workers:for_ide
//kotlin/workers:unittests
test_sources:
diff --git a/kotlin/workers/BUILD b/kotlin/workers/BUILD
index 622afeb..b57623f 100644
--- a/kotlin/workers/BUILD
+++ b/kotlin/workers/BUILD
@@ -27,13 +27,14 @@
runtime_deps = [
"@com_github_jetbrains_kotlin//:kotlin-stdlib",
"@com_github_jetbrains_kotlin//:kotlin-stdlib-jdk7",
- "@com_github_jetbrains_kotlin//:kotlin-stdlib-jdk8"
+ "@com_github_jetbrains_kotlin//:kotlin-stdlib-jdk8",
+ "@com_github_jetbrains_kotlin//:kotlin-reflect"
]
)
java_binary(
name = "compiler_jvm",
- main_class = "io.bazel.ruleskotlin.workers.compilers.jvm.KotlinJvmBuilder",
+ main_class = "io.bazel.ruleskotlin.workers.KotlinJvmBuilder",
visibility = ["//visibility:public"],
runtime_deps = [":worker_lib"]
)
diff --git a/kotlin/workers/bootstrap.bzl b/kotlin/workers/bootstrap.bzl
index dbdc866..70fccd5 100644
--- a/kotlin/workers/bootstrap.bzl
+++ b/kotlin/workers/bootstrap.bzl
@@ -72,7 +72,7 @@
"@com_github_jetbrains_kotlin//:kotlinc",
"@local_jdk//:jdk",
dep_label
- ] + deps,
+ ],
srcs = srcs,
outs = [jar_name],
cmd = _gen_cmd(dep_label, " ".join(args)),
@@ -83,5 +83,6 @@
jars = [jar_name],
exports = exports,
runtime_deps = (depset(runtime_deps) + exports + deps).to_list(),
- visibility = ["//visibility:private"]
+ visibility = ["//visibility:private"],
+ tags = ["no-ide"]
)
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/CommandLineProgram.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/CommandLineProgram.kt
index 5fb40fe..60638bd 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/CommandLineProgram.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/CommandLineProgram.kt
@@ -15,14 +15,12 @@
*/
package io.bazel.ruleskotlin.workers
-
/**
* Interface for command line programs.
*
* This is the same thing as a main function, except not static.
*/
interface CommandLineProgram {
-
/**
* Runs blocking program start to finish.
*
@@ -35,4 +33,43 @@
* @return program exit code, i.e. 0 for success, non-zero for failure
*/
fun apply(args: List<String>): Int
-}
+
+ abstract class Base(
+ protected val flags: FlagNameMap = emptyMap()
+ ): CommandLineProgram {
+ private val mandatoryFlags: List<Flag> = flags.values.filter { it is Flag.Mandatory }
+
+ private fun createContext(args: List<String>): Context {
+ val tally = mutableMapOf<Flag, String>()
+
+ if (args.size % 2 != 0) {
+ throw RuntimeException("args should be k,v pairs")
+ }
+
+ for (i in 0 until args.size / 2) {
+ val flag = args[i * 2]
+ val value = args[i * 2 + 1]
+ val field = flags[flag] ?: throw RuntimeException("unrecognised arg: " + flag)
+ tally[field] = value
+ }
+
+ mandatoryFlags.forEach { require(tally.containsKey(it)) { "missing mandatory flag ${it.globalFlag}" } }
+ return Context(tally)
+ }
+
+ abstract fun toolchain(ctx: Context): KotlinToolchain
+ abstract fun actions(toolchain: KotlinToolchain, ctx: Context): List<BuildAction>
+
+ override fun apply(args: List<String>): Int {
+ val ctx = createContext(args)
+ val toolchain = toolchain(ctx)
+ var exitCode = 0
+ for (action in actions(toolchain,ctx)) {
+ exitCode = action(ctx)
+ if (exitCode != 0)
+ break
+ }
+ return exitCode
+ }
+ }
+}
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/CompileResult.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/CompileResult.kt
index 6ac5a57..52c30b4 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/CompileResult.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/CompileResult.kt
@@ -34,7 +34,8 @@
error().ifPresent { e -> throw RuntimeException(message, e) }
}
- class Meta(id: String) : io.bazel.ruleskotlin.workers.Meta<CompileResult>(id) {
+ class Meta(id: String) : io.bazel.ruleskotlin.workers.Meta<CompileResult> {
+ override val id: String = id
fun run(ctx: Context, op: (Context) -> Int): CompileResult {
var result: CompileResult
@@ -49,7 +50,7 @@
fun runAndBind(ctx: Context, op: (Context) -> Int): CompileResult {
val res = run(ctx, op)
- bind(ctx, res)
+ set(ctx,res)
return res
}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Context.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Context.kt
index 1a42331..18b1d93 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Context.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Context.kt
@@ -17,55 +17,20 @@
package io.bazel.ruleskotlin.workers
-import java.util.*
import java.util.stream.Stream
-class Context private constructor(args: List<String>) {
- private val args = EnumMap<Flags, String>(Flags::class.java)
- private val meta = HashMap<Meta<*>, Any>()
+class Context internal constructor(
+ private val flags: Map<Flag, String>
+) {
+ private val meta = mutableMapOf<Meta<*>, Any>()
- init {
- if (args.size % 2 != 0) {
- throw RuntimeException("args should be k,v pairs")
- }
-
- for (i in 0 until args.size / 2) {
- val flag = args[i * 2]
- val value = args[i * 2 + 1]
- val field = ALL_FIELDS_MAP[flag] ?: throw RuntimeException("unrecognised arg: " + flag)
- this.args[field] = value
- }
-
- MANDATORY_FIELDS.asSequence()
- .filterNot { this.args.containsKey(it) }
- .forEach { throw RuntimeException("mandatory arg missing: " + it.globalFlag) }
- }
-
- fun of(vararg fields: Flags): EnumMap<Flags, String> {
- val result = EnumMap<Flags, String>(Flags::class.java)
- for (field in fields) {
- val value = args[field]
- if (value != null) {
- result[field] = value
- }
- }
- return result
- }
+ fun copyOfFlags(vararg fields: Flag): Map<Flag, String> = fields.mapNotNull { f -> flags[f]?.let { f to it } }.toMap()
fun apply(vararg consumers: (Context) -> Unit) {
Stream.of(*consumers).forEach { it(this) }
}
- internal operator fun get(field: Flags): String? = args[field]
- internal operator fun <T : Any> get(key: Meta<T>): T? = meta[key] as T?
+ internal operator fun get(flag: Flag): String? = flags[flag]
+ operator fun <T : Any> get(key: Meta<T>): T? = meta[key] as T?
internal fun <T : Any> putIfAbsent(key: Meta<T>, value: T): T? = meta.putIfAbsent(key, value as Any) as T?
-
- companion object {
- private val ALL_FIELDS_MAP = Flags.values().map { it.globalFlag to Flags.valueOf(it.name) }.toMap()
- private val MANDATORY_FIELDS = Flags.values().filter { x -> x.mandatory }
-
- fun from(args: List<String>): Context {
- return Context(args)
- }
- }
}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flag.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flag.kt
new file mode 100644
index 0000000..e00301e
--- /dev/null
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flag.kt
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2018 The Bazel Authors. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package io.bazel.ruleskotlin.workers
+
+import kotlin.reflect.KClass
+import kotlin.reflect.full.declaredMemberProperties
+
+sealed class Flag(val globalFlag: String, val kotlinFlag: String? = null) {
+ open operator fun get(context: Context): String? = context[this]
+
+ class Optional(globalFlag: String, kotlinFlag: String? = null) : Flag(globalFlag, kotlinFlag)
+
+ class Mandatory(globalFlag: String, kotlinFlag: String? = null) : Flag(globalFlag, kotlinFlag) {
+ override fun get(context: Context): String = requireNotNull(super.get(context)) { "mandatory flag $globalFlag not present" }
+ }
+}
+
+/**
+ * all of the static flag properties declared in a class.
+ */
+// works for objects only.
+private fun <T : Any> KClass<T>.allFlags(): Sequence<Flag> {
+ val obj = requireNotNull(this.objectInstance) { "only collects flag instances from classes with an object instance" }
+ return declaredMemberProperties.asSequence().mapNotNull {
+ it.get(obj).takeIf(Flag::class::isInstance).let { it as Flag }
+ }
+}
+
+typealias FlagNameMap = Map<String, Flag>
+
+/**
+ * Map from flag name to flag collected from the static properteis declared in a class.
+ */
+fun <T : Any> KClass<T>.flagsByName(): FlagNameMap = allFlags().associateBy { it.globalFlag }
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flags.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flags.kt
deleted file mode 100644
index fe20049..0000000
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Flags.kt
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2018 The Bazel Authors. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package io.bazel.ruleskotlin.workers
-
-
-enum class Flags(val globalFlag: String, val kotlinFlag: String?, internal val mandatory: Boolean) {
- // flags that line up with the java builder.
- LABEL(JavaBuilderFlags.TARGET_LABEL.flag, null, true),
- OUTPUT_CLASSJAR(JavaBuilderFlags.OUTPUT.flag, null, true),
- SOURCES(JavaBuilderFlags.SOURCES.flag, null, true),
- CLASSPATH(JavaBuilderFlags.CLASSPATH.flag, "-cp", true),
-
- // flags that could be aligned with the java builder.
- OUTPUT_JDEPS("--output_jdeps", null, true),
- COMPILER_OUTPUT_BASE("--compiler_output_base", null, true),
-
- // flags for kotlin.
- KOTLIN_API_VERSION("--kotlin_api_version", "-api-version", false),
- KOTLIN_LANGUAGE_VERSION("--kotlin_language_version", "-language-version", false),
- KOTLIN_JVM_TARGET("--kotlin_jvm_target", "-jvm-target", false);
-
- operator fun get(context: Context): String? = context[this]
-}
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinJvmBuilder.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinJvmBuilder.kt
new file mode 100644
index 0000000..a2a4b6a
--- /dev/null
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinJvmBuilder.kt
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2018 The Bazel Authors. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package io.bazel.ruleskotlin.workers
+
+
+import io.bazel.ruleskotlin.workers.compilers.jvm.actions.*
+import io.bazel.ruleskotlin.workers.model.Flags
+import java.io.IOException
+
+/**
+ * Bazel Kotlin Compiler worker.
+ */
+object KotlinJvmBuilder : CommandLineProgram.Base(
+ flags = Flags::class.flagsByName()
+) {
+ private val toolchain: KotlinToolchain = try {
+ KotlinToolchain()
+ } catch (e: IOException) {
+ throw RuntimeException("could not initialize toolchain", e)
+ }
+
+ private val compileActions: List<BuildAction> = listOf(
+ Initialize(toolchain),
+ KotlinMainCompile(toolchain),
+ JavaMainCompile(toolchain),
+ ProcessCompileResult(toolchain),
+ CreateOutputJar(toolchain),
+ GenerateJdepsFile(toolchain)
+ )
+
+ override fun toolchain(ctx: Context): KotlinToolchain = toolchain
+ override fun actions(toolchain: KotlinToolchain, ctx: Context): List<BuildAction> = compileActions
+
+ @JvmStatic
+ fun main(args: Array<String>) {
+ val kotlinCompilerBazelWorker = BazelWorker(
+ this,
+ System.err,
+ "KotlinCompile"
+ )
+ System.exit(kotlinCompilerBazelWorker.apply(args.toList()))
+ }
+}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinToolchain.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinToolchain.kt
index 6e7a2c8..622c46d 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinToolchain.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/KotlinToolchain.kt
@@ -19,6 +19,7 @@
import io.bazel.ruleskotlin.workers.utils.verifiedRelativeFiles
import org.jetbrains.kotlin.preloading.ClassPreloadingUtils
import org.jetbrains.kotlin.preloading.Preloader
+import java.io.File
import java.io.PrintStream
import java.nio.file.Path
import java.nio.file.Paths
@@ -37,9 +38,10 @@
val JDEPS_PATH = JAVA_HOME.resolveVerified("bin", "jdeps").toString()
val KOTLIN_LIB_DIR: Path = KOTLIN_HOME.resolveVerified("lib").toPath()
- private val kotlinPreloadJars = KOTLIN_LIB_DIR.verifiedRelativeFiles(
- Paths.get("kotlin-compiler.jar")
- )
+ private val kotlinPreloadJars = mutableListOf<File>().let {
+ it.addAll(KOTLIN_LIB_DIR.verifiedRelativeFiles(Paths.get("kotlin-compiler.jar")))
+ it.toList()
+ }
val KOTLIN_STD_LIBS = arrayOf(
"kotlin-stdlib.jar",
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Meta.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Meta.kt
index a0aca11..1b48198 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/Meta.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/Meta.kt
@@ -15,17 +15,18 @@
*/
package io.bazel.ruleskotlin.workers
-open class Meta<T: Any>(
- private val id: String,
- private val defaultValue: T? = null
-) {
- constructor(id: String) : this(id, null)
+interface Meta<T : Any> {
+ val id: String
+ get() = this.javaClass.simpleName
+
+ val defaultValue: T?
+ get() = null
/**
* Gets a mandatory value.
*/
fun mustGet(ctx: Context): T =
- ctx[this] ?: checkNotNull(defaultValue) { "mandatory meta parameter missing in context and does not have a default value" }
+ ctx[this] ?: checkNotNull(defaultValue) { "mandatory meta parameter missing in context and does not have a default value" }
/**
* Gets an optional value, if it has not been bound the default value is used.
@@ -39,5 +40,25 @@
}
}
- fun bind(ctx: Context, value: T) { check(ctx.putIfAbsent(this, value) == null) { "attempting to change bound meta variable: $id " } }
+ operator fun set(ctx: Context, value: T) {
+ check(ctx.putIfAbsent(this, value) == null) { "attempting to change bound meta variable: $id " }
+ }
+
+ companion object {
+ operator fun <T : Any> invoke(id: String): Meta<T> = object : Meta<T> {
+ override val id: String = id
+ override val defaultValue: T? = null
+ }
+ }
+}
+
+interface MandatoryMeta<T: Any>: Meta<T> {
+ override fun get(ctx: Context): T = checkNotNull(super.get(ctx)) { "ctx missing mandatory meta ${this.id}" }
+
+ companion object {
+ operator fun <T : Any> invoke(id: String): Meta<T> = object : MandatoryMeta<T> {
+ override val id: String = id
+ override val defaultValue: T? = null
+ }
+ }
}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/KotlinJvmBuilder.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/KotlinJvmBuilder.kt
deleted file mode 100644
index 571bdd1..0000000
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/KotlinJvmBuilder.kt
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2018 The Bazel Authors. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package io.bazel.ruleskotlin.workers.compilers.jvm
-
-
-import io.bazel.ruleskotlin.workers.*
-import io.bazel.ruleskotlin.workers.compilers.jvm.actions.*
-
-import java.io.IOException
-
-/**
- * Bazel Kotlin Compiler worker.
- */
-class KotlinJvmBuilder private constructor() : CommandLineProgram {
- private val compileActions: Array<BuildAction>
-
- init {
- val toolchain: KotlinToolchain
- try {
- toolchain = KotlinToolchain()
- } catch (e: IOException) {
- throw RuntimeException("could not initialize toolchain", e)
- }
-
- compileActions = arrayOf(
- Initialize(toolchain),
- KotlinMainCompile(toolchain),
- JavaMainCompile(toolchain),
- ProcessCompileResult(toolchain),
- CreateOutputJar(toolchain),
- GenerateJdepsFile(toolchain)
- )
- }
-
- override fun apply(args: List<String>): Int {
- val ctx = Context.from(args)
- var exitCode = 0
- for (action in compileActions) {
- exitCode = action(ctx)
- if (exitCode != 0)
- break
- }
- return exitCode
- }
-
- companion object {
- @JvmStatic
- fun main(args: Array<String>) {
- val kotlinBuilder = KotlinJvmBuilder()
- val kotlinCompilerBazelWorker = BazelWorker(
- kotlinBuilder,
- System.err,
- "KotlinCompile"
- )
- System.exit(kotlinCompilerBazelWorker.apply(args.toList()))
- }
- }
-}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/Metas.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/Metas.kt
deleted file mode 100644
index 6b56242..0000000
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/Metas.kt
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2018 The Bazel Authors. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package io.bazel.ruleskotlin.workers.compilers.jvm
-
-import io.bazel.ruleskotlin.workers.CompileResult
-import io.bazel.ruleskotlin.workers.Meta
-
-import java.nio.file.Path
-
-/**
- * Meta is a key to some compilation state,.
- */
-object Metas {
- // mandatory: the package part of the label.
- val PKG = Meta<String>("package")
- // mandatory: The target part of the label.
- val TARGET = Meta<String>("target")
- // mandatory: the class staging directory.
- val CLASSES_DIRECTORY = Meta<Path>("class_directory")
- // mandatory: If this is non empty then it is a mixed mode operation.
- val JAVA_SOURCES = Meta<List<String>>("java_sources")
- // mandatory:
- val ALL_SOURCES = Meta<List<String>>("all_sources")
- // mandatory:
- val KOTLINC_RESULT = CompileResult.Meta("kotlin_compile_result")
- // optional: when not a mixed mode operation.
- val JAVAC_RESULT = CompileResult.Meta("javac_compile_result")
-}
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/CreateOutputJar.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/CreateOutputJar.kt
index 38545fa..be2732d 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/CreateOutputJar.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/CreateOutputJar.kt
@@ -18,9 +18,9 @@
import io.bazel.ruleskotlin.workers.BuildAction
import io.bazel.ruleskotlin.workers.Context
-import io.bazel.ruleskotlin.workers.Flags
import io.bazel.ruleskotlin.workers.KotlinToolchain
-import io.bazel.ruleskotlin.workers.compilers.jvm.Metas
+import io.bazel.ruleskotlin.workers.model.CompileDirectories
+import io.bazel.ruleskotlin.workers.model.Flags
import io.bazel.ruleskotlin.workers.utils.executeAndAwaitSuccess
/**
@@ -32,7 +32,7 @@
executeAndAwaitSuccess(10,
toolchain.JAR_TOOL_PATH,
"cf", checkNotNull(Flags.OUTPUT_CLASSJAR[ctx]),
- "-C", Metas.CLASSES_DIRECTORY.mustGet(ctx).toString(),
+ "-C", CompileDirectories[ctx].classes,
"."
)
} catch (e: Exception) {
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/GenerateJdepsFile.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/GenerateJdepsFile.kt
index 120e38d..ca13558 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/GenerateJdepsFile.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/GenerateJdepsFile.kt
@@ -18,9 +18,12 @@
import com.google.devtools.build.lib.view.proto.Deps
import io.bazel.ruleskotlin.workers.BuildAction
import io.bazel.ruleskotlin.workers.Context
-import io.bazel.ruleskotlin.workers.Flags.*
import io.bazel.ruleskotlin.workers.KotlinToolchain
import io.bazel.ruleskotlin.workers.compilers.jvm.utils.JdepsParser
+import io.bazel.ruleskotlin.workers.model.Flags.CLASSPATH
+import io.bazel.ruleskotlin.workers.model.Flags.LABEL
+import io.bazel.ruleskotlin.workers.model.Flags.OUTPUT_CLASSJAR
+import io.bazel.ruleskotlin.workers.model.Flags.OUTPUT_JDEPS
import io.bazel.ruleskotlin.workers.utils.executeAndWaitOutput
import io.bazel.ruleskotlin.workers.utils.rootCause
import java.io.FileOutputStream
@@ -32,10 +35,11 @@
private val isKotlinImplicit = JdepsParser.pathSuffixMatchingPredicate(toolchain.KOTLIN_LIB_DIR, *toolchain.KOTLIN_STD_LIBS)
override fun invoke(ctx: Context): Int {
- val classJar = checkNotNull(OUTPUT_CLASSJAR[ctx])
- val classPath = checkNotNull(CLASSPATH[ctx])
- val output = checkNotNull(OUTPUT_JDEPS[ctx])
- val label = checkNotNull(LABEL[ctx])
+ val classJar = OUTPUT_CLASSJAR[ctx]
+ val classPath = CLASSPATH[ctx]
+ val output = OUTPUT_JDEPS[ctx]
+ val label = LABEL[ctx]
+
val jdepsContent: Deps.Dependencies
try {
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/Initialize.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/Initialize.kt
index 6a3f3b9..31a8a9d 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/Initialize.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/Initialize.kt
@@ -16,17 +16,14 @@
package io.bazel.ruleskotlin.workers.compilers.jvm.actions
-import io.bazel.ruleskotlin.workers.*
-import io.bazel.ruleskotlin.workers.compilers.jvm.Metas
-
-import io.bazel.ruleskotlin.workers.utils.purgeDirectory
-
-import java.io.IOException
+import io.bazel.ruleskotlin.workers.BuildAction
+import io.bazel.ruleskotlin.workers.Context
+import io.bazel.ruleskotlin.workers.KotlinToolchain
+import io.bazel.ruleskotlin.workers.model.CompileDirectories
+import io.bazel.ruleskotlin.workers.model.Flags
+import io.bazel.ruleskotlin.workers.model.Metas
import java.nio.file.Files
-import java.nio.file.Path
import java.nio.file.Paths
-import java.util.ArrayList
-import java.util.Collections
/**
* Should be the first step, does mandatory pre-processing.
@@ -42,8 +39,8 @@
}
private fun bindSources(ctx: Context) {
- val javaSources = ArrayList<String>()
- val allSources = ArrayList<String>()
+ val javaSources = mutableListOf<String>()
+ val allSources = mutableListOf<String>()
for (src in requireNotNull(Flags.SOURCES[ctx]).split(":")) {
when {
src.endsWith(".java") -> {
@@ -54,35 +51,14 @@
else -> throw RuntimeException("unrecognised file type: $src")
}
}
- Metas.JAVA_SOURCES.bind(ctx, Collections.unmodifiableList(javaSources))
- Metas.ALL_SOURCES.bind(ctx, Collections.unmodifiableList(allSources))
+ Metas.JAVA_SOURCES[ctx] = javaSources.toList()
+ Metas.ALL_SOURCES[ctx] = allSources.toList()
}
private fun initializeAndBindBindDirectories(ctx: Context) {
- val outputBase: Path
-
- try {
- outputBase = Files.createDirectories(Paths.get(checkNotNull(Flags.COMPILER_OUTPUT_BASE[ctx])))
- } catch (e: IOException) {
- throw RuntimeException("could not create compiler output base", e)
+ Files.createDirectories(Paths.get(Flags.COMPILER_OUTPUT_BASE[ctx])).let {
+ CompileDirectories[ctx] = CompileDirectories(it)
}
-
- try {
- outputBase.purgeDirectory()
- } catch (e: IOException) {
- throw RuntimeException("could not purge output directory", e)
- }
-
- createAndBindComponentDirectory(ctx, outputBase, Metas.CLASSES_DIRECTORY, "_classes")
- }
-
- private fun createAndBindComponentDirectory(ctx: Context, outputBase: Path, key: Meta<Path>, component: String) {
- try {
- key.bind(ctx, Files.createDirectories(outputBase.resolve(component)))
- } catch (e: IOException) {
- throw RuntimeException("could not create subdirectory for component " + component, e)
- }
-
}
/**
@@ -92,7 +68,7 @@
val label = requireNotNull(Flags.LABEL[ctx])
val parts = label.split(":")
require(parts.size == 2) { "the label $label is invalid" }
- Metas.PKG.bind(ctx, parts[0])
- Metas.TARGET.bind(ctx, parts[1])
+ Metas.PKG[ctx] = parts[0]
+ Metas.TARGET[ctx] = parts[1]
}
}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/JavaMainCompile.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/JavaMainCompile.kt
index 3ae306b..3295c57 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/JavaMainCompile.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/JavaMainCompile.kt
@@ -15,26 +15,28 @@
*/
package io.bazel.ruleskotlin.workers.compilers.jvm.actions
-import io.bazel.ruleskotlin.workers.BuildAction
-import io.bazel.ruleskotlin.workers.Context
-import io.bazel.ruleskotlin.workers.Flags
-import io.bazel.ruleskotlin.workers.KotlinToolchain
-import io.bazel.ruleskotlin.workers.compilers.jvm.Metas
+import io.bazel.ruleskotlin.workers.*
+import io.bazel.ruleskotlin.workers.model.Metas
+import io.bazel.ruleskotlin.workers.model.CompileDirectories
+import io.bazel.ruleskotlin.workers.model.Flags
import io.bazel.ruleskotlin.workers.utils.executeAndAwait
/**
* Simple java compile action that invokes javac directly and simply.
*/
class JavaMainCompile(toolchain: KotlinToolchain) : BuildAction("compile java classes", toolchain) {
+ companion object {
+ val Result = CompileResult.Meta("javac_compile_result")
+ }
override fun invoke(ctx: Context): Int {
val javaSources = Metas.JAVA_SOURCES.mustGet(ctx)
- val classpath = checkNotNull(Flags.CLASSPATH[ctx])
+ val classpath = Flags.CLASSPATH[ctx]
if (!javaSources.isEmpty()) {
- val classesDirectory = Metas.CLASSES_DIRECTORY.mustGet(ctx).toString()
+ val classesDirectory = CompileDirectories[ctx].classes
val args = mutableListOf(toolchain.JAVAC_PATH, "-cp", "$classesDirectory/:$classpath", "-d", classesDirectory).also { it.addAll(javaSources) }
- Metas.JAVAC_RESULT.runAndBind(ctx) { executeAndAwait(30, args) }
+ Result.runAndBind(ctx) { executeAndAwait(30, args) }
}
return 0
}
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/KotlinMainCompile.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/KotlinMainCompile.kt
index bf5b1ab..0be74ba 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/KotlinMainCompile.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/KotlinMainCompile.kt
@@ -15,13 +15,13 @@
*/
package io.bazel.ruleskotlin.workers.compilers.jvm.actions
+
import io.bazel.ruleskotlin.workers.*
-import io.bazel.ruleskotlin.workers.compilers.jvm.Metas
+import io.bazel.ruleskotlin.workers.model.Metas
import io.bazel.ruleskotlin.workers.compilers.jvm.utils.KotlinCompilerOutputProcessor
-
-
-import java.util.ArrayList
-import java.util.Collections
+import io.bazel.ruleskotlin.workers.model.CompileDirectories
+import io.bazel.ruleskotlin.workers.model.Flags
+import java.util.*
/**
* Either compiles to a jar directly or when performing mixed-mode-compilation compiles to a temp directory first.
@@ -44,21 +44,29 @@
Flags.KOTLIN_LANGUAGE_VERSION,
Flags.KOTLIN_JVM_TARGET)
- /**
- * Evaluate the compilation context and add Metadata to the ctx if needed.
- *
- * @return The args to pass to the kotlin compile class.
- */
- private fun setupCompileContext(ctx: Context): Array<String> {
- val args = ArrayList<String>()
- Collections.addAll(args, "-d", Metas.CLASSES_DIRECTORY.mustGet(ctx).toString())
- ctx.of(*COMPILE_MAPPED_FLAGS).forEach { field, arg ->
- args.add(field.kotlinFlag!!); args.add(arg)
+ val Result = CompileResult.Meta("kotlin_compile_result")
+ }
- }
- args.addAll(Metas.ALL_SOURCES.mustGet(ctx))
- return args.toTypedArray()
+ /**
+ * Evaluate the compilation context and add Metadata to the ctx if needed.
+ *
+ * @return The args to pass to the kotlin compile class.
+ */
+ private fun setupCompileContext(ctx: Context): Array<String> {
+ val args = mutableListOf<String>()
+ val compileDirectories = CompileDirectories[ctx]
+
+ ctx.copyOfFlags(*COMPILE_MAPPED_FLAGS).forEach { field, arg ->
+ args.add(field.kotlinFlag!!); args.add(arg)
}
+
+ Collections.addAll(args, "-kotlin-home", KotlinToolchain.KOTLIN_HOME.toString())
+ Collections.addAll(args, "-d", compileDirectories.classes)
+
+
+ args.addAll(Metas.ALL_SOURCES.mustGet(ctx))
+ println(args.joinToString(" "))
+ return args.toTypedArray()
}
override fun invoke(ctx: Context): Int {
@@ -77,10 +85,10 @@
// 3 is the script execution error
// give javac a chance to process the java sources.
- Metas.KOTLINC_RESULT.bind(ctx, CompileResult.deferred(exitCode) { _ ->
+ Result[ctx] = CompileResult.deferred(exitCode) { _ ->
outputProcessor.process()
exitCode
- })
+ }
return 0
} else {
outputProcessor.process()
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/ProcessCompileResult.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/ProcessCompileResult.kt
index 01fbf3b..5165880 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/ProcessCompileResult.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/compilers/jvm/actions/ProcessCompileResult.kt
@@ -19,7 +19,6 @@
import io.bazel.ruleskotlin.workers.BuildAction
import io.bazel.ruleskotlin.workers.Context
import io.bazel.ruleskotlin.workers.KotlinToolchain
-import io.bazel.ruleskotlin.workers.compilers.jvm.Metas
/**
@@ -29,8 +28,8 @@
*/
class ProcessCompileResult(toolchain: KotlinToolchain) : BuildAction("render class compile output", toolchain) {
override fun invoke(ctx: Context): Int {
- val kotlincResult = Metas.KOTLINC_RESULT.mustGet(ctx)
- val javacResult = Metas.JAVAC_RESULT[ctx]
+ val kotlincResult = KotlinMainCompile.Result.mustGet(ctx)
+ val javacResult = JavaMainCompile.Result[ctx]
return if (javacResult == null) {
kotlincResult.render(ctx)
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/CompileDirectories.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/CompileDirectories.kt
new file mode 100644
index 0000000..c547f87
--- /dev/null
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/CompileDirectories.kt
@@ -0,0 +1,31 @@
+/*
+ * Copyright 2018 The Bazel Authors. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package io.bazel.ruleskotlin.workers.model
+
+import io.bazel.ruleskotlin.workers.MandatoryMeta
+import java.nio.file.Files
+import java.nio.file.Path
+
+/**
+ * Temporary output directories used durng compilation.
+ */
+class CompileDirectories(private val outputBase: Path) {
+ val classes by lazy { dir("_classes") }
+
+ private fun dir(component: String) = Files.createDirectories(outputBase.resolve(component)).toString()
+
+ companion object: MandatoryMeta<CompileDirectories>
+}
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Flags.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Flags.kt
new file mode 100644
index 0000000..de2a9f1
--- /dev/null
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Flags.kt
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2018 The Bazel Authors. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package io.bazel.ruleskotlin.workers.model
+
+import io.bazel.ruleskotlin.workers.Flag
+
+/**
+ * The flags supported by the worker.
+ */
+object Flags {
+ val LABEL = Flag.Mandatory(JavaBuilderFlags.TARGET_LABEL.flag)
+ val OUTPUT_CLASSJAR = Flag.Mandatory(JavaBuilderFlags.OUTPUT.flag)
+ val SOURCES = Flag.Mandatory(JavaBuilderFlags.SOURCES.flag)
+ val CLASSPATH = Flag.Mandatory(JavaBuilderFlags.CLASSPATH.flag, "-cp")
+
+ val OUTPUT_JDEPS = Flag.Mandatory("--output_jdeps")
+ val COMPILER_OUTPUT_BASE = Flag.Mandatory("--compiler_output_base")
+
+ val KOTLIN_API_VERSION = Flag.Optional("--kotlin_api_version", "-api-version")
+ val KOTLIN_LANGUAGE_VERSION = Flag.Optional("--kotlin_language_version", "-language-version")
+ val KOTLIN_JVM_TARGET = Flag.Optional("--kotlin_jvm_target", "-jvm-target")
+}
\ No newline at end of file
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/JavaBuilderFlags.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/JavaBuilderFlags.kt
similarity index 92%
rename from kotlin/workers/src/io/bazel/ruleskotlin/workers/JavaBuilderFlags.kt
rename to kotlin/workers/src/io/bazel/ruleskotlin/workers/model/JavaBuilderFlags.kt
index 3287a27..54cfebf 100644
--- a/kotlin/workers/src/io/bazel/ruleskotlin/workers/JavaBuilderFlags.kt
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/JavaBuilderFlags.kt
@@ -13,12 +13,12 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-package io.bazel.ruleskotlin.workers
+package io.bazel.ruleskotlin.workers.model
/**
- * Flags used by the java builder.
+ * Declares the flags used by the java builder.
*/
-enum class JavaBuilderFlags(val flag: String) {
+internal enum class JavaBuilderFlags(val flag: String) {
TARGET_LABEL("--target_label"),
CLASSPATH("--classpath"),
JAVAC_OPTS("--javacopts"),
diff --git a/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Metas.kt b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Metas.kt
new file mode 100644
index 0000000..0951c39
--- /dev/null
+++ b/kotlin/workers/src/io/bazel/ruleskotlin/workers/model/Metas.kt
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2018 The Bazel Authors. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package io.bazel.ruleskotlin.workers.model
+
+import io.bazel.ruleskotlin.workers.MandatoryMeta
+import io.bazel.ruleskotlin.workers.Meta
+
+/**
+ * Listin of Meta keys that don't make sense as companion objects.
+ */
+object Metas {
+ // mandatory: the package part of the label.
+ val PKG = Meta<String>("package")
+ // mandatory: The target part of the label.
+ val TARGET = Meta<String>("target")
+
+ // mandatory: If this is non empty then it is a mixed mode operation.
+ val JAVA_SOURCES = MandatoryMeta<List<String>>("java_sources")
+
+ // mandatory:
+ val ALL_SOURCES = MandatoryMeta<List<String>>("all_sources")
+}
\ No newline at end of file
diff --git a/tests/smoke/BUILD b/tests/smoke/BUILD
index 99a28d7..5233b03 100644
--- a/tests/smoke/BUILD
+++ b/tests/smoke/BUILD
@@ -78,7 +78,8 @@
name = "propagation_ct_consumer_fail_on_runtime",
main_class = "testing.CompileTimeDependent",
srcs = ["propagation/CompileTimeDependent.java"],
- deps = [":propagation_test_runtime_lib"]
+ deps = [":propagation_test_runtime_lib"],
+ tags = ["manual"]
)
java_binary(