| package io.bazel.kotlin.builder.tasks.js |
| |
| import io.bazel.kotlin.builder.toolchain.CompilationException |
| import io.bazel.kotlin.builder.toolchain.KotlinToolchain |
| import io.bazel.kotlin.builder.utils.CompilationTaskContext |
| import io.bazel.kotlin.builder.utils.addAll |
| import io.bazel.kotlin.builder.utils.jars.JarCreator |
| import io.bazel.kotlin.builder.utils.jars.SourceJarCreator |
| import io.bazel.kotlin.builder.utils.resolveTwinVerified |
| import io.bazel.kotlin.builder.utils.verifiedPath |
| import io.bazel.kotlin.model.JsCompilationTask |
| import java.io.FileOutputStream |
| import java.nio.file.Files |
| import java.nio.file.Path |
| import java.nio.file.Paths |
| import javax.inject.Inject |
| import javax.inject.Singleton |
| |
| @Singleton |
| class Kotlin2JsTaskExecutor @Inject constructor( |
| private val invoker: KotlinToolchain.K2JSCompilerInvoker |
| ) { |
| fun execute(context: CompilationTaskContext, task: JsCompilationTask) { |
| context.print(Paths.get(task.inputs.kotlinSourcesList[0]).toRealPath().toAbsolutePath().toString()) |
| task.compile(context) |
| |
| val jsPath = Paths.get(task.outputs.js) |
| val jsMetaFile = jsPath.resolveTwinVerified(".meta.js") |
| val jsDirectory = jsPath.parent.resolve(jsPath.toFile().nameWithoutExtension) |
| task.createJar(jsDirectory, listOf(jsPath, jsPath.resolveTwinVerified(".js.map"), jsMetaFile)) |
| // this mutates the jsPath file , so do it after creating the jar. |
| appendMetaToPrimary(jsPath, jsMetaFile) |
| task.createSourceJar() |
| } |
| |
| private fun JsCompilationTask.compile(context: CompilationTaskContext) { |
| val args = mutableListOf<String>().also { |
| it.addAll(passThroughFlagsList) |
| it.addAll("-libraries", inputs.librariesList.joinToString(":")) |
| it.addAll("-output", outputs.js) |
| it.addAll(inputs.kotlinSourcesList) |
| } |
| context.whenTracing { printLines("js compile args", args) } |
| context.executeCompilerTask(args, invoker::compile) |
| } |
| |
| private fun JsCompilationTask.createSourceJar() { |
| try { |
| SourceJarCreator(Paths.get(outputs.srcjar), false).also { creator -> |
| creator.addSources(inputs.kotlinSourcesList.map { Paths.get(it) }.stream()) |
| }.execute() |
| } catch (ex: Throwable) { |
| throw CompilationException("could not create source jar", ex) |
| } |
| } |
| |
| /** |
| * Append the meta file to the JS file. This is an accepted pattern, and it allows us to not have to export the |
| * meta.js file with the js. |
| */ |
| private fun appendMetaToPrimary(jsPath: Path, jsMetaFile: Path) { |
| try { |
| FileOutputStream(jsPath.toFile(), true).use { Files.copy(jsMetaFile, it) } |
| } catch (ex: Throwable) { |
| throw CompilationException("could not normalize js file", ex) |
| } |
| } |
| |
| private fun JsCompilationTask.createJar(jsDirectoryPath: Path, rootEntries: List<Path>) { |
| try { |
| val outputJarPath = Paths.get(outputs.jar) |
| |
| JarCreator(outputJarPath).also { creator -> |
| creator.addDirectory(jsDirectoryPath) |
| creator.addRootEntries(rootEntries.map { it.toString() }) |
| creator.execute() |
| } |
| } catch (ex: Throwable) { |
| throw CompilationException("error creating js jar", ex) |
| } |
| } |
| } |