Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/215.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android FragmentScenario必须在FragmentInteractionListener上实现_Android_Android Testing_Instrumented Test - Fatal编程技术网

Android FragmentScenario必须在FragmentInteractionListener上实现

Android FragmentScenario必须在FragmentInteractionListener上实现,android,android-testing,instrumented-test,Android,Android Testing,Instrumented Test,我目前正在尝试使用本教程中建议的androidTest、mokito和espresso来测试android导航: 但我系统地得到了以下错误: E/MonitoringInstr:线程[main,5,main]遇到异常。将线程状态转储到输出,并锁定峡湾。 java.lang.RuntimeException:androidx.fragment.app.testing.FragmentScenario$EmptyFragmentActivity@fa3e8be必须实现OnFragmentIntera

我目前正在尝试使用本教程中建议的androidTest、mokito和espresso来测试android导航: 但我系统地得到了以下错误: E/MonitoringInstr:线程[main,5,main]遇到异常。将线程状态转储到输出,并锁定峡湾。 java.lang.RuntimeException:androidx.fragment.app.testing.FragmentScenario$EmptyFragmentActivity@fa3e8be必须实现OnFragmentInteractionListener

以下是测试类:

package developer.android.com.enlightme

import androidx.fragment.app.testing.launchFragmentInContainer
import androidx.navigation.NavController
import androidx.navigation.Navigation
import androidx.test.espresso.Espresso.onView
import androidx.test.espresso.action.ViewActions
import androidx.test.espresso.matcher.ViewMatchers
import androidx.test.espresso.matcher.ViewMatchers.withId
import androidx.test.filters.MediumTest
import androidx.test.runner.AndroidJUnit4
import org.junit.Assert.*
import org.junit.Test
import org.junit.runner.RunWith
import org.mockito.Mockito.*


@MediumTest
@RunWith(AndroidJUnit4::class)
class MainFragmentTest{
    @Test
    fun createDebateTransition(){
        // Create a mock NavController
        val mockNavController = mock(NavController::class.java)
        // Create a graphical FragmentScenario for the TitleScreen
        var mainScenario = launchFragmentInContainer<MainFragment>()
        // Set the NavController property on the fragment
        mainScenario.onFragment { fragment ->  Navigation.setViewNavController(fragment.requireView(), mockNavController)
        }
        // Verify that performing a click "créer" prompt the correct Navigation action
        onView(ViewMatchers.withId(R.id.nav_button_creer)).perform(ViewActions.click())
        verify(mockNavController).navigate(R.id.action_mainFragment_to_create1Fragment)
    }
  }
}
以及模块graddle文件:

apply plugin: 'com.android.application'

apply plugin: 'kotlin-android'
apply plugin: 'maven'
apply plugin: 'kotlin-android-extensions'
apply plugin: "androidx.navigation.safeargs"
apply plugin: "kotlinx-serialization"

android {
    compileSdkVersion 28
    dataBinding {
        enabled = true
    }
    defaultConfig {
        applicationId "developer.android.com.enlightme"
        minSdkVersion 18
        targetSdkVersion 28
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
        vectorDrawables.useSupportLibrary = true
        android.defaultConfig.vectorDrawables.useSupportLibrary = true
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }
    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }
    buildToolsVersion = '28.0.3'
    kotlinOptions {
        jvmTarget = JavaVersion.VERSION_1_8.toString()
    }
}

dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
    implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
    implementation 'androidx.appcompat:appcompat:1.2.0-alpha01'
    implementation 'androidx.core:core-ktx:1.2.0-rc01'
    implementation 'androidx.constraintlayout:constraintlayout:2.0.0-beta4'
    implementation 'androidx.legacy:legacy-support-v4:1.0.0'

    //ViewModel
    implementation 'androidx.lifecycle:lifecycle-extensions:2.2.0-rc03'
    //MaterialIO
    implementation 'com.google.android.material:material:1.2.0-alpha03'

    // Navigation

    // Java
    implementation "androidx.navigation:navigation-fragment:$navigationVersion"
    implementation "androidx.navigation:navigation-ui:$navigationVersion"

    // Kotlin
    implementation "androidx.navigation:navigation-fragment-ktx:$navigationVersion"
    implementation "androidx.navigation:navigation-ui-ktx:$navigationVersion"

    //P2P with Nearby
    implementation "com.google.android.gms:play-services-nearby:17.0.0"

    //Serialization
    implementation "org.jetbrains.kotlinx:kotlinx-serialization-runtime:0.13.0" // JVM dependency

    //Testing
    // Required -- JUnit 4 framework
    testImplementation 'junit:junit:4.13-rc-2'
    // Optional -- Robolectric environment
    testImplementation 'androidx.test:core:1.2.0'
    // Optional -- Mockito framework
    //testImplementation 'org.mockito:mockito-core:1.10.19'
    //androidTestImplementation "org.mockito:mockito-core:${var}"
    //espresso
    androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.0'
    androidTestImplementation 'androidx.test:runner:1.1.0'
    androidTestImplementation 'androidx.test:rules:1.1.0'
    //androidTestImplementation "org.jetbrains.kotlinx:kotlinx-coroutines-test:$coroutinesVersion"
    debugImplementation "androidx.fragment:fragment-testing:$fragmentVersion"
    androidTestImplementation "org.mockito:mockito-core:${var}"
    androidTestImplementation "com.google.dexmaker:dexmaker:1.2"
    androidTestImplementation "com.google.dexmaker:dexmaker-mockito:1.2"


}
ext {
    espressoVersion = '3.3.0-alpha03'
    coroutinesVersion = '1.2.1'
    fragmentVersion = '1.1.0'
    var = '1.10.19'
    var1 = '1.3.60'
    kotlin_version = '1.3.60'
}// Top-level build file where you can add configuration options common to all sub-projects/modules.

buildscript {
    ext {
    kotlin_version = '1.3.40'
        navigationVersion = '2.2.0-rc04'
    }
    repositories {
        google()
        jcenter()
    }
    dependencies {
        classpath 'com.android.tools.build:gradle:3.5.3'
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
        classpath "org.jetbrains.kotlin:kotlin-serialization:$kotlin_version"
        // NOTE: Do not place your application dependencies here; they belong
        // in the individual module build.gradle files
        //navigation
        def nav_version = "2.1.0-alpha05"
        classpath "androidx.navigation:navigation-safe-args-gradle-plugin:$nav_version"
    }
}

allprojects {
    repositories {
        google()
        jcenter()
    }
}

task clean(type: Delete) {
    delete rootProject.buildDir
}
以及项目梯度文件:

apply plugin: 'com.android.application'

apply plugin: 'kotlin-android'
apply plugin: 'maven'
apply plugin: 'kotlin-android-extensions'
apply plugin: "androidx.navigation.safeargs"
apply plugin: "kotlinx-serialization"

android {
    compileSdkVersion 28
    dataBinding {
        enabled = true
    }
    defaultConfig {
        applicationId "developer.android.com.enlightme"
        minSdkVersion 18
        targetSdkVersion 28
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
        vectorDrawables.useSupportLibrary = true
        android.defaultConfig.vectorDrawables.useSupportLibrary = true
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }
    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }
    buildToolsVersion = '28.0.3'
    kotlinOptions {
        jvmTarget = JavaVersion.VERSION_1_8.toString()
    }
}

dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
    implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
    implementation 'androidx.appcompat:appcompat:1.2.0-alpha01'
    implementation 'androidx.core:core-ktx:1.2.0-rc01'
    implementation 'androidx.constraintlayout:constraintlayout:2.0.0-beta4'
    implementation 'androidx.legacy:legacy-support-v4:1.0.0'

    //ViewModel
    implementation 'androidx.lifecycle:lifecycle-extensions:2.2.0-rc03'
    //MaterialIO
    implementation 'com.google.android.material:material:1.2.0-alpha03'

    // Navigation

    // Java
    implementation "androidx.navigation:navigation-fragment:$navigationVersion"
    implementation "androidx.navigation:navigation-ui:$navigationVersion"

    // Kotlin
    implementation "androidx.navigation:navigation-fragment-ktx:$navigationVersion"
    implementation "androidx.navigation:navigation-ui-ktx:$navigationVersion"

    //P2P with Nearby
    implementation "com.google.android.gms:play-services-nearby:17.0.0"

    //Serialization
    implementation "org.jetbrains.kotlinx:kotlinx-serialization-runtime:0.13.0" // JVM dependency

    //Testing
    // Required -- JUnit 4 framework
    testImplementation 'junit:junit:4.13-rc-2'
    // Optional -- Robolectric environment
    testImplementation 'androidx.test:core:1.2.0'
    // Optional -- Mockito framework
    //testImplementation 'org.mockito:mockito-core:1.10.19'
    //androidTestImplementation "org.mockito:mockito-core:${var}"
    //espresso
    androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.0'
    androidTestImplementation 'androidx.test:runner:1.1.0'
    androidTestImplementation 'androidx.test:rules:1.1.0'
    //androidTestImplementation "org.jetbrains.kotlinx:kotlinx-coroutines-test:$coroutinesVersion"
    debugImplementation "androidx.fragment:fragment-testing:$fragmentVersion"
    androidTestImplementation "org.mockito:mockito-core:${var}"
    androidTestImplementation "com.google.dexmaker:dexmaker:1.2"
    androidTestImplementation "com.google.dexmaker:dexmaker-mockito:1.2"


}
ext {
    espressoVersion = '3.3.0-alpha03'
    coroutinesVersion = '1.2.1'
    fragmentVersion = '1.1.0'
    var = '1.10.19'
    var1 = '1.3.60'
    kotlin_version = '1.3.60'
}// Top-level build file where you can add configuration options common to all sub-projects/modules.

buildscript {
    ext {
    kotlin_version = '1.3.40'
        navigationVersion = '2.2.0-rc04'
    }
    repositories {
        google()
        jcenter()
    }
    dependencies {
        classpath 'com.android.tools.build:gradle:3.5.3'
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
        classpath "org.jetbrains.kotlin:kotlin-serialization:$kotlin_version"
        // NOTE: Do not place your application dependencies here; they belong
        // in the individual module build.gradle files
        //navigation
        def nav_version = "2.1.0-alpha05"
        classpath "androidx.navigation:navigation-safe-args-gradle-plugin:$nav_version"
    }
}

allprojects {
    repositories {
        google()
        jcenter()
    }
}

task clean(type: Delete) {
    delete rootProject.buildDir
}
我正在使用Android studio 3.5.3

所以基本上,当我在手机上运行应用程序时,一切都很好,包括导航。问题源于仪器化测试本身。据我所知,FragmentScenario并没有实现OnFragmentInteractionListener。当然,我不能改变零碎的场景类,我不知道这件事应该如何处理。我是否使用了错误的工具来测试片段交互


谢谢大家!

FragmentScenario获取您的片段并在容器中启动它,使用默认的空活动作为主机。它不会启动您的活动。目标是单独测试片段

当然,空主机活动不会实现OnFragmentInteractionListener,因为它是您创建的接口。在onAttach回调中,您强制主机活动实现此接口,并告诉它以其他方式抛出异常。这就是你在测试中遇到的错误

您可以删除onAttach方法中的else部分,错误将消失。但是您的侦听器将为null,并且依赖它的一些功能将无法正常工作


也许你也可以考虑改变这个体系结构。您可以考虑使用共享视图模型吗?这比与听众互动容易。如果您不想更改当前状态,可能您可以继续进行集成测试,而不是单独的片段测试

目前,我发现的唯一解决办法是完全避免类与OnFragmentInteractionListener接口。。。这是有限的。谢谢(有点晚了,抱歉…)你的见解。我最好改变我的架构:)