Связывание с JVM asm-определенными классами из Kotlin с использованием Gradle
У меня есть следующие настройки для приложения Android:
├── build.gradle
└── src
└── main
├── AndroidManifest.xml
├── asm
│ └── SomeJVMClass.j
├── kotlin
│ └── activity.kt
└── res
└── values
└── strings.xml
Исходный файл в src/main/asm/SomeJVMClass.j
это сборка JVM формата Кракатау (почти такая же, как у Jasmin). Я хотел бы использовать класс, который он определяет из моего основного источника Kotlin activity.kt
,
Прежде чем я попытаюсь автоматизировать это с помощью Gradle, просто соберите файл вручную в build
не помогает Вот что я попробовал:
- Сделать
gradle build
получить скелетbuild
каталог (это, конечно, не удается, компилятор Kotlin не находитSomeJVMClass
) Я запускаю Krakatau вручную, чтобы поместить его файлы классов в
build/intermediates/classes/{debug,release}
:$ for flavor in debug release; do ~/prog/jvm/krakatau/assemble.py -out build/intermediates/classes/$flavor -r src/main/asm ;done Processing file src/main/asm/SomeJVMClass.j, 1/1 remaining Class written to build/intermediates/classes/debug/com/example/JVMServer/SomeJVMClass.class Processing file src/main/asm/SomeJVMClass.j, 1/1 remaining Class written to build/intermediates/classes/release/com/example/JVMServer/SomeJVMClass.class
Re беги
grade build
с надеждой, что теперь Котлин найдет.class
файлы; но без улучшения вообще
:compileDebugKotlin e: /home/cactus/prog/android/kotlin-asm/src/main/kotlin/activity.kt (3,20): Unresolved reference: JVMServer e: /home/cactus/prog/android/kotlin-asm/src/main/kotlin/activity.kt: (12,14): Unresolved reference: SomeJVMClass
Итак, первый вопрос, очевидно, куда я помещу .class
файлы, чтобы компилятор Kotlin мог их найти. И второй, дополнительный вопрос, как мне автоматизировать это так, чтобы один gradle build
Команда запустит ассемблер Krakatau перед запуском компилятора Kotlin.
Для справки, вот мои исходные файлы:
src/main/asm/SomeJVMClass.j
:
.class public com/example/JVMServer/SomeJVMClass
.super java/lang/Object
.method public static foo: ()Ljava/lang/String;
.code stack 2 locals 0
ldc "JVM bytecode works"
areturn
.end code
.end method
.end class
src/main/kotlin/activity.kt
:
package com.example.JVMClient
import com.example.JVMServer.SomeJVMClass
import android.app.Activity
import android.os.Bundle
class MainActivity: Activity() {
protected override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setTitle(SomeJVMClass.foo())
}
}
1 ответ
Редактировать: оказывается, этот подход не работает для Android-Gradle
Это больше относится к Gradle, чем Kotlin, вы можете сказать, Gradle включить .class
файлы во время компиляции, добавив оператор compile files("build/intermediates/classes/debug")
к вашим зависимостям.
Это поместит файлы.class в путь к классам, где Kotlin сможет их найти.