我正在Kotlin开发Android库。我保留了一些类的访问修饰符作为internal
。内部类仅在Kotlin的库模块中可见。如果我在应用程序中实现了这个库,那么它就根本看不见了。
但是,当从Java代码访问该库时,问题就来了。如果我创建了.java
文件并键入库的internal
类的名称,那么IDE就是建议名称,并且它被解析和编译而没有任何错误。
例如
库模块:
internal class LibClass {
// Fields and Methods
}
在DemoApp模块中实现上述库后:
应用程序模块
Kotlin:fun stuff() {
val lib = LibClass() // Error.. Not resolving
}
Java:public void stuff() {
LibClass lib = new LibClass() // Successfully resolving and compiling
}
这就是问题所在。如何从Java中保护该类?
谢谢!
我看到您有一个带有内部修饰符的类,它不能在kotlin类中实例化,但可以在Java文件中实例化。如果它是一个独立的类,您可以将其构造函数设为私有的,并允许使用静态方法(Companion对象(进行实例化。
不是完美的解决方案,但我发现了两个破解的解决方案
用空格或特殊符号对internal class
和@JvmName
的每个公共方法进行注释,从而在Java中产生语法错误
例如
internal class LibClass {
@JvmName(" ") // Blank Space will generate error in Java
fun foo() {}
@JvmName(" $#") // These characters will cause error in Java
fun bar() {}
}
由于上面的解决方案不适合管理大型项目,或者看起来不是很好的实践,下面的解决方案可能会有所帮助。
用@JvmSynthetic
注释该internal class
的每个公共方法,通过这些方法Java无法访问公共方法
例如
internal class LibClass {
@JvmSynthetic
fun foo() {}
@JvmSynthetic
fun bar() {}
}
注:
本文对此进行了详细解释。
如果您想隐藏类的可见性,而不是每个函数或字段,可以在类的顶部使用@file:JvmSynthetic
。
例如
@file:JvmSynthetic
package com.example.app
internal class LibClass {
var count: Int = 0
internal fun exampleFun() {
}
}