【问题标题】:Travis CI & CodeCov AndroidTravis CI & CodeCov Android
【发布时间】:2017-05-12 15:56:29
【问题描述】:

我正在尝试使用 Travis CI 并让它通过测试来查看 codecov 上的结果。

.travis.yml:

language: android
sudo: required
jdk: oraclejdk8

before_cache:
 - rm -f $HOME/.gradle/caches/modules-2/modules-2.lock
 - rm -fr $HOME/.gradle/caches/*/plugin-resolution/

cache:
 directories:
 - $HOME/.gradle/caches/
 - $HOME/.gradle/wrapper/

env:
 global:
 - ANDROID_API=25
 - EMULATOR_API=21
 - ANDROID_BUILD_TOOLS=25.0.0
 - ADB_INSTALL_TIMEOUT=5 # minutes

android:
 components:
 - tools
 - platform-tools
 - build-tools-$ANDROID_BUILD_TOOLS
 - android-$ANDROID_API
 - android-$EMULATOR_API_LEVEL
 - extra-google-m2repository
 - extra-android-m2repository # for design library
 - addon-google_apis-google-19 # google play services
 - sys-img-armeabi-v7a-addon-google_apis-google-$ANDROID_API_LEVEL
 - sys-img-armeabi-v7a-addon-google_apis-google-$EMULATOR_API_LEVEL

licenses:
 - android-sdk-preview-license-.+
 - android-sdk-license-.+
 - google-gdk-license-.+

before_install:
- mkdir "$ANDROID_HOME/licenses" || true
- echo -e "\n8933bad161af4178b1185d1a37fbf41ea5269c55" > "$ANDROID_HOME/licenses/android-sdk-license"
- echo -e "\n84831b9409646a918e30573bab4c9c91346d8abd" > "$ANDROID_HOME/licenses/android-sdk-preview-license"
- chmod +x gradlew
#- ./gradlew dependencies || true # DON'T ADD unless you are getting "Install missing components using SDK manager"
#Source: https://medium.com/@oldergod/constraint-layout-and-circleci-travis-d50342696d2



script:
  - ./gradlew build jacocoTestReport assembleAndroidTest
  - echo no | android create avd --force -n test -t android-21 --abi armeabi-v7a
  - emulator -avd test -no-skin -no-audio -no-window &
  - android-wait-for-emulator
  - adb shell setprop dalvik.vm.dexopt-flags v=n,o=v
  - ./gradlew connectedCheck

after_success:
- bash <(curl -s https://codecov.io/bash)

build.gradle:

// Top-level build file where you can add configuration options common to all sub-projects/modules.

buildscript {
    repositories {
        jcenter()
    }
    dependencies {
        classpath 'com.android.tools.build:gradle:2.2.2'
        classpath 'com.dicedmelon.gradle:jacoco-android:0.1.1'
        // NOTE: Do not place your application dependencies here; they belong
        // in the individual module build.gradle files
    }
}

allprojects {
    repositories {
        jcenter()
    }
}

task clean(type: Delete) {
    delete rootProject.buildDir
}

build.gradle(app):

apply plugin: 'com.android.application'
apply plugin: 'jacoco-android'

android {
    compileSdkVersion 24
    buildToolsVersion "24.0.3"
    defaultConfig {
        applicationId "<ID>"
        minSdkVersion 15
        targetSdkVersion 24
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
        vectorDrawables.useSupportLibrary = true
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
        debug {
            testCoverageEnabled true
        }
    }
    testOptions {
        unitTests.returnDefaultValues = true
    }
    lintOptions {
        abortOnError false
    }
    productFlavors {
        free {}
        paid {}
    }


    packagingOptions {
        exclude 'META-INF/DEPENDENCIES'
        exclude 'META-INF/NOTICE'
        exclude 'META-INF/LICENSE'
        exclude 'META-INF/LICENSE.txt'
        exclude 'META-INF/NOTICE.txt'
    }
}

dependencies {
    compile files('libs/httpclient-4.5.1.jar')
    compile fileTree(include: ['*.jar'], dir: 'libs')
    androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
        exclude group: 'com.android.support', module: 'support-annotations'
    })
    compile 'com.android.support:appcompat-v7:24.2.1'
    compile 'com.android.support:support-v4:24.2.1'
    compile 'com.android.support:design:24.2.1'
    compile 'com.android.support:support-vector-drawable:24.2.1'
    testCompile 'junit:junit:4.12'
    compile files('libs/themoviedbapi-4.3.jar')
    compile files('libs/api-common-2.0.jar')
    compile files('libs/commons-codec-1.9.jar')
    compile files('libs/commons-lang3-3.4.jar')
    compile files('libs/httpcore-4.4.3.jar')
    compile files('libs/jackson-annotations-2.7.1.jar')
    compile files('libs/jackson-core-2.7.1.jar')
    compile files('libs/jackson-databind-2.7.1.jar')
    compile files('libs/slf4j-api-1.7.16.jar')
}

我们正在尝试运行的测试是仪器化测试。 Travis 日志的输出如下所示:

com.example.fabian.tinf15b4_lsmf.SeeMovieDetailsTest > seeMovieDetails[test(AVD) - 5.0.2] [31mFAILED [0m
    java.lang.NoSuchMethodError: No virtual method releaseConnection()V in class Lorg/apache/http/client/methods/HttpRequestBase; or its super classes (declaration of 'org.apache.http.client.methods.HttpRequestBase' appears in /system/framework/ext.jar)

    at org.yamj.api.common.http.DigestedResponseReader.processRequest(DigestedResponseReader.java:119)

Tests on test(AVD) - 5.0.2 failed: Instrumentation run failed due to 'java.lang.NoSuchMethodError'
:app:connectedFreeDebugAndroidTest FAILED

还有自动生成的测试,它只是简单地将两个数字相加并检查结果,但特拉维斯甚至没有通过它。

谁能帮忙解决这个烂摊子?

【问题讨论】:

  • 我没有使用 HttpClient,但在下面添加了一些可能对您有帮助的相关答案。

标签: android testing continuous-integration code-coverage travis-ci


【解决方案1】:

阅读this related question 关于HTTPClient - NoSuchMethodError for .releaseConnection

HttpRequestBase#releaseConnection() 方法定义添加在 4.2 version.

可能你有罐子地狱。如果编译器没有编译错误 可以在运行时加载该类的另一个版本。真正的原因 取决于您的构建工具。如果您使用的是 maven/gradle,则可以 是一些传递依赖。

所以实际上HttpRequestBase#releaseConnection() 方法只是代理 调用AbstractExecutionAwareRequest#reset()。和 AbstractExecutionAwareRequest#reset() 只是取消方法执行。 可能不是你需要的。

执行和释放httpClient资源的正确方法是 关闭httpResponse,表示可以在httpClient的释放Thread 内部线程池。

private static String makeRequest(HttpUriRequest httpRequest) throws IOException {
        CloseableHttpResponse httpResponse = httpClient.execute(httpRequest);
        try {
            HttpEntity httpEntity = httpResponse.getEntity();
            StringWriter writer = new StringWriter();
            IOUtils.copy(httpEntity.getContent(), writer, "UTF-8");
            return writer.toString();
        } finally {
            httpResponse.close();
        }
    }

quickstart 你会看到 .releaseConnection() 不再使用(已弃用), 而是关闭响应对象以确保连接 关闭。

尝试不同的httpclienthttpcore版本(来自here):

您的 jar 文件似乎包含旧/新版本 基本的HttpContext。如果存在直接冲突,您将收到 类NotFoundException。类加载器通常是关于这个的混蛋 之类的事情。在这种情况下,类存在,但是,没有 另一个库的方法(我相信它是 httpclient 调用上下文)是针对编译的。

对于 API 23+,您还可以在 /app/build.gradle 中添加 the removed apache library like this

android {
compileSdkVersion 24
buildToolsVersion "24.0.3"
    useLibrary 'org.apache.http.legacy'
    ...
}

Android 6.0 版本删除了对 Apache HTTP 客户端的支持。如果 您的应用正在使用此客户端并针对 Android 2.3(API 级别 9)或 更高,请改用 HttpURLConnection 类。这个API更多 高效...

this articlethis sample 似乎有助于为 Android 和 Travis-ci 配置 Codecov:

生成仪器测试代码覆盖率报告需要 对构建脚本的微小改动。

android {
  buildTypes {
    debug {
      testCoverageEnabled true
    }
  }
}

为避免覆盖率报告忽略我们的测试,我们需要 配置以下设置:

android {
  testOptions {
    unitTests.all {
      jacoco {
        includeNoLocationClasses = true
      }
    }
  }
}

接下来,我们需要配置报表输出:

 jacocoAndroidUnitTestReport {
  csv.enabled false
  html.enabled true
  xml.enabled true
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-04-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-01-04
    相关资源
    最近更新 更多