fknives / Android-Tutorial-Test-ShowCase

Mock project showcasing testing on Android. It is used as a CodeKata.
Apache License 2.0
7 stars 2 forks source link

Sharing SourceSets via adding it in Gradle is no longer supported #106

Closed fknives closed 2 years ago

fknives commented 2 years ago

Is your feature request related to a problem? Please describe. Since Chipmunk and AGP 7.2 the SourceSet sharing leveraged in the repo is no longer recommended / supported by the IDE.

Describe the solution you'd like Alternative is to use separate test modules and shared test modules.

Additional context https://issuetracker.google.com/issues/232007221 https://issuetracker.google.com/issues/232420188

fknives commented 2 years ago

I am a bit undecided on this issue, cause the suggested solution brings in a couple of almost empty duplicate classes, but resolves the IDE issue.

Specially because Robolectric still suggest the sharedSourceSet solution: link, they also have an open issue with the pattern no longer being supported by Studio

shared directory's current limitation The current limitation with srcDir is basically the IDE. Running testDebugUnitTest and connectedAndroidTest will run all the Shared code properly, but you cannot run the test class separately. This can be mitigated by commenting out the line of sharing the sourceCode to keep only for UnitTests or AndroidTests. So while inconvenient during creating the test it can be worked around then the test can be run automatically. Example:

// build.gradle (:app)
android {
    // ...
    sourceSets {
        androidTest {
            java.srcDirs += "src/sharedTest/java"
            assets.srcDirs += files("$projectDir/schemas".toString())
        }
        test {
//            java.srcDirs += "src/sharedTest/java"
            java.srcDirs += "src/robolectricTest/java"
//            resources.srcDirs += files("$projectDir/schemas".toString())
        }
    }
    // ...

Current Recommendation by Google/JetBrains The current recommendation from Google is simply to extract any code you want to share between test and androidTest into a separate android module with the following dependency graph:

:app-shared-test -implements-> :app
:app -testImplements-> :app-shared-test
:app -androidTestImplements-> :app-shared-test

Which works fine for utility classes, resources, mocks fakes, but you cannot share actual Test classes. That's because those Test classes won't be recognized to be run with the test tasks. To resolve that you would need to create a Test class in both :app:test and :app:androidTest which then extend that shared test class. I think this is cumbersome quite a bit, creating classes like in both androidTest and unitTest source sets:

@RunWith(AndroidJUnit4::class)
class MainActivityInstrumentedTest : MainActivityInstrumentedSharedTest()