Android Studio 3.0 Canary 1:引用Kotlin类的Kotlin测试或Java测试失败

UPDATE

这个问题已经提交到这里: https : //youtrack.jetbrains.com/issue/KT-17951

更新2

这个bug已经在Android Studio 3.0 Canary 3中修复了

原始帖子

我刚刚开始玩Android Studio 3.0,我从一开始就启用了kotlin支持。 我在我的项目中写了一个非常简单的Kotlin类:

data class Wallet(val coins: Int) { fun add(value: Int): Wallet = Wallet(coins + value) fun substract(value: Int): Wallet = if (coins > value) Wallet(coins + value) else throw InsufficientFundsException() } 

现在我想测试这个类,首先我在Kotlin上写了一个本地运行的unittest(测试目录):

 class WalletTestKotlin { @Throws(Exception::class) @Test fun add() { Assert.assertEquals(22, Wallet(20).add(2).coins.toLong()) Assert.assertNotEquals(5, Wallet(2).add(13).coins.toLong()) } } 

它编译和运行,但与错误消息:

未找到类:“com.agentknopf.hachi.repository.model.WalletTestKotlin”空测试套件。

我因此重新编写了Java测试:

 public class WalletTest { @Throws(exceptionClasses = Exception.class) @Test public void add() { Assert.assertEquals(22, new Wallet(20).add(2).getCoins()); Assert.assertNotEquals(5, new Wallet(2).add(13).getCoins()); } } 

然而那个测试失败了 – 这次Kotlin类“钱包”无法找到:

java.lang.NoClassDefFoundError:com / example / repository / model / Wallet

我想知道我是否缺少一些东西…运行一个Java Test,它不是指Kotlin类,而是Java类只能成功完成。

我的项目build.gradle文件是默认的一个:

 // Top-level build file where you can add configuration options common to all sub-projects/modules. buildscript { ext.kotlin_version = '1.1.2-4' repositories { maven { url 'https://maven.google.com' } jcenter() } dependencies { classpath 'com.android.tools.build:gradle:3.0.0-alpha1' classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version" // NOTE: Do not place your application dependencies here; they belong // in the individual module build.gradle files } } allprojects { repositories { jcenter() maven { url 'https://maven.google.com' } mavenCentral() } } task clean(type: Delete) { delete rootProject.buildDir } 

我的模块特定的build.gradle的依赖关系:

 dependencies { compile fileTree(dir: 'libs', include: ['*.jar']) //Kotlin support compile "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version" //Testing libraries androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { exclude group: 'com.android.support', module: 'support-annotations' }) testCompile 'junit:junit:4.12' testCompile "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version" testCompile "org.jetbrains.kotlin:kotlin-test-junit:$kotlin_version" } 

解决方法(现在):

把这个放到你的(应用程序级)build.gradle中:

 task copyTestClasses(type: Copy) { from "build/tmp/kotlin-classes/debugUnitTest" into "build/intermediates/classes/debug" } 

然后在底部“启动之前”修改测试JUnit运行/调试配置,在其中有'Gradle-aware make',另一部分,选择gradle task ,选择它所在的项目build.gradle文件,然后键入copyTestClasses 。 点击这里查看不同测试框架的屏幕截图 ,但管道工作方式相同。

您可能需要根据您的构建类型更改/添加更多目录管道。 你发现那些奇怪的地方的方式是通过粗暴搜索相关的.class文件的项目树。

注意:Android Studio 3.3 Canary已经解决了问题

感谢@kat让我朝着正确的方向展示。 首先 – 对于OP中提到的问题已经提出了一个错误 。

我的设置如下所示:Kotlin测试与Java测试位于同一目录中。 为了同时使用这两个用例:

  • 参考Java测试中的kotlin类
  • 请参阅kotlin测试中的kotlin类

首先删除您可能拥有的任何其他测试运行配置。 然后在我的应用程序级build.gradle中添加了这两个gradle构建任务:

 android { ... task copyTestClasses(type: Copy) { from "build/tmp/kotlin-classes/debugUnitTest" into "build/intermediates/classes/debug" } task copySdkClasses(type: Copy) { from "build/tmp/kotlin-classes/debug" into "build/intermediates/classes/debug" } } 

然后我通过运行>编辑配置打开运行配置菜单。 在左边我删除了顶级的Android JUnit配置。 然后我点击了Defaults> Android JUnit然后编辑配置如下:

  • 测试种类=全包
  • 表单模式=无
  • 重复=一次
  • 包=我的基础包如com.yourname
  • 在单个模块中搜索tests =
  • 我离开了中间部分(VM选项等)
  • 在“启动之前”部分,通过单击加号图标添加两个条目:
  • 运行gradle任务:选择您的应用程序模块的build.gradle,然后在任务中输入名称copyTestClasses,然后单击确定
  • 像以前一样添加第二个运行gradle任务,但这次是作为任务名称输入copySdkClasses,然后单击确定
  • 点击配置上的应用,然后运行测试

这就是它最终的样子: 在这里输入图像描述

@AgentKnopf恰到好处,但是您需要像这样每个新的测试案例添加任务

在这里输入图像描述

 dependencies { compile fileTree(include: ['*.jar'], dir: 'libs') androidTestCompile("com.android.support.test.espresso:espresso-core:$espresso_version", { exclude group: 'com.android.support', module: 'support-annotations' }) testCompile "junit:junit:$junit_version" // kotlin compile "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version" ............... } // add 2 task in run config to make kotlin test working // for junit task copyTestClasses(type: Copy) { from "build/tmp/kotlin-classes/debugUnitTest" into "build/intermediates/classes/debug" } // for instrumented test task copySdkClasses(type: Copy) { from "build/tmp/kotlin-classes/debug" into "build/intermediates/classes/debug" } afterEvaluate { compileDebugUnitTestSources.dependsOn copyTestClasses compileReleaseUnitTestSources.dependsOn copyTestClasses compileDebugAndroidTestSources.dependsOn copySdkClasses } 

为你自动添加任务

这个Bug在Android Studio 3.0 Canary 3中修复