有时候导入一个新库

compile'com.libertybrowser:affiliatetrigger:2.0.1'

后会gradle构建的时候发生这种错误:

Process 'command '/home/meizu/android/sdk/build-tools/25.0.1/aapt'' finished with non-zero exit value 1

网上说是库依赖有冲突,但实际看具体的出错地方是因为manifest节点中没有appComponentFactory,

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven

gradle修改maven gradle修改dependence后没有重新依赖_android_02

原因就是新导入的依赖中依赖的appcompat-v7的版本是28:

gradle修改maven gradle修改dependence后没有重新依赖_gradle_03

这个版本已经没有这个属性了,所以需要把这个高版本的依赖去掉。

我们知道gradle依赖,会向上查找是否有最新的版本,如果同一个依赖库有多个版本,那就会默认使用最高的版本,所以 在依赖的时候通过exclude来去掉appcompat-v7包:

compile('com.libertybrowser:affiliatetrigger:2.0.1'){
   exclude module: 'appcompat-v7'
}

gradle修改maven gradle修改dependence后没有重新依赖_java_04

 顺便说下,这里使用了一个查看gradle依赖的插件,在我们设置中,选择plugin,然后查找gradle View插件,安装

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven_05

安装成功后,在AS的工具栏中点击View , Tool Windows, Gradle View 就能出现如下界面:

gradle修改maven gradle修改dependence后没有重新依赖_依赖冲突_06

第一个是依赖库的列表,第二个就是依赖的传递的结构,我们点开第二个:

 

gradle修改maven gradle修改dependence后没有重新依赖_依赖冲突_07

里面出现了很多节点,主要点开compile节点,这里面会显示所有这个module的依赖关系,这样就可以排查是否同一个库被依赖了多个版本,或者同一个库的同一个版本被依赖了多次(如果是这样的话就需要去掉其中一个,否则编译会有问题)

 

紧接着上面,上面说道把appcomat-v7剔除掉后,执行gradle后也没有问题了,本以为这样就行了,结果在执行编译的时候报了这么个错误:

Return code 1 for dex process

详细看下android errors的错误信息:

AGPBI: {"kind":"error","text":"1 error; aborting","sources":[{}]}
 :Browser:transformClassesWithDexForDebug FAILED
 FAILURE: Build failed with an exception.
 * What went wrong:
 Execution failed for task ':Browser:transformClassesWithDexForDebug'.
 > com.android.build.api.transform.TransformException: java.lang.RuntimeException: java.lang.RuntimeException: com.android.ide.common.process.ProcessException: java.util.concurrent.ExecutionException: com.android.ide.common.process.ProcessException: Return code 1 for dex process

gradle修改maven gradle修改dependence后没有重新依赖_android_08

真是一头雾水啊,网上有说是重复的依赖导致的 ,于是我把这个新库中所以依赖的第三方库都去掉了,还是会报一样的错误。

待解决:

后续:

上面信息是AS 3.2.1上报出来的,感觉信息不是很全面,我记得之前也是构建有问题,然后换成2.3版本能显示出更多的信息,这次我也是用AS 2.3版本来编译,然后同样的错误,但是多了一些信息在gradle console下:

AGPBI: {"kind":"error","text":"Error converting bytecode to dex:\nCause: Dex cannot parse version 52 byte code.\nThis is caused by library dependencies that have been compiled using Java 8 or above.\nIf you are using the \u0027java\u0027 gradle plugin in a library submodule add \ntargetCompatibility \u003d \u00271.7\u0027\nsourceCompatibility \u003d \u00271.7\u0027\nto that submodule\u0027s build.gradle file.","sources":[{}],"original":"UNEXPECTED TOP-LEVEL EXCEPTION:\njava.lang.RuntimeException: Exception parsing classes\n\tat com.android.dx.command.dexer.Main.processClass(Main.java:775)\n\tat com.android.dx.command.dexer.Main.processFileBytes(Main.java:741)\n\tat com.android.dx.command.dexer.Main.access$1200(Main.java:88)\n\tat com.android.dx.command.dexer.Main$FileBytesConsumer.processFileBytes(Main.java:1683)\n\tat com.android.dx.cf.direct.ClassPathOpener.processArchive(ClassPathOpener.java:284)\n\tat com.android.dx.cf.direct.ClassPathOpener.processOne(ClassPathOpener.java:166)\n\tat com.android.dx.cf.direct.ClassPathOpener.process(ClassPathOpener.java:144)\n\tat com.android.dx.command.dexer.Main.processOne(Main.java:695)\n\tat com.android.dx.command.dexer.Main.processAllFiles(Main.java:592)\n\tat com.android.dx.command.dexer.Main.runMultiDex(Main.java:376)\n\tat com.android.dx.command.dexer.Main.run(Main.java:290)\n\tat com.android.builder.internal.compiler.DexWrapper.run(DexWrapper.java:54)\n\tat com.android.builder.core.DexByteCodeConverter.lambda$dexInProcess$0(DexByteCodeConverter.java:173)\n\tat java.util.concurrent.FutureTask.run(FutureTask.java:266)\n\tat java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)\n\tat java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)\n\tat java.lang.Thread.run(Thread.java:748)\nCaused by: com.android.dx.cf.iface.ParseException: bad class file magic (cafebabe) or version (0034.0000)\n\tat com.android.dx.cf.direct.DirectClassFile.parse0(DirectClassFile.java:476)\n\tat com.android.dx.cf.direct.DirectClassFile.parse(DirectClassFile.java:406)\n\tat com.android.dx.cf.direct.DirectClassFile.parseToInterfacesIfNecessary(DirectClassFile.java:388)\n\tat com.android.dx.cf.direct.DirectClassFile.getMagic(DirectClassFile.java:251)\n\tat com.android.dx.command.dexer.Main.parseClass(Main.java:787)\n\tat com.android.dx.command.dexer.Main.access$1600(Main.java:88)\n\tat com.android.dx.command.dexer.Main$ClassParserTask.call(Main.java:1722)\n\tat com.android.dx.command.dexer.Main.processClass(Main.java:773)\n\t... 16 more\n","tool":"Dex"}


(这里实在要吐槽一下,为什么AS3.0后gradle console这个面板没有了,很明显在这里面给出的信息是比较全面的也比较准确的,容易让人找到问题。也许是我不会用3.2版本吧,有哪位大神知道显示详细信息的地方还望不吝赐教)

(后续,哈哈,果然是自己蠢!!!,原来输出日志的详细面板在这里:

在我们平常build构建的日志的窗口中,左边其实有这么一个按钮,点开就能看到详细的日志,只不过平时没怎么注意,然后这个面板的颜色又太按了,很难让人发现啊。。。。

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven_09

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven_10

 

点开之后果然和2.3版本的build console输出是一致的了。。。) 

按照上面的提示,上网搜了一遍,说是要在build.gradle的android节点内添加:

compileOptions {    sourceCompatibility JavaVersion.VERSION_1_8
    targetCompatibility JavaVersion.VERSION_1_8
}

结果在sync的时候出现了:

gradle修改maven gradle修改dependence后没有重新依赖_java_11

Error:Jack is required to support java 8 language features. Either enable Jack or remove sourceCompatibility JavaVersion.VERSION_1_8.

这个错误。因为我项目的gradle的版本用的还是2.3,所以要在defaultConfig节点下增加:

jackOptions {
             enabled true
         }

加入之后又同步一下。期待能通过啊~~~

gradle修改maven gradle修改dependence后没有重新依赖_依赖冲突_12

sync正常了,然后执行编译。。。。

果不其然,又失败了。。。。

Cause: com.android.jack.api.v01.CompilationException
ERROR: AppIndexingService.java:150-151: Lambda coming from jar file need their interfaces on the classpath to be compiled, unknown interfaces are com.google.android.gms.tasks.OnCompleteListener

gradle修改maven gradle修改dependence后没有重新依赖_java_13

 

网络搜索搜~~~

无奈之下,升级下gradle版本吧,有人说gradle版本升级到3.2.1后,就不需要指定jackOptions,好吧,尝试下看看。

dependencies {    classpath 'com.android.tools.build:gradle:3.2.1'    // NOTE: Do not place your application dependencies here; they belong
    // in the individual module build.gradle files
}


继续同步,然后提示gradle-wrapper也要升级,

Minimum supported Gradle version is 4.6. Current version is 2.14.1.

Please fix the project's Gradle settings.
Fix Gradle wrapper and re-import project
Gradle settings
 

原来的老版本是

distributionUrl=https\://services.gradle.org/distributions/gradle-2.14.1-all.zip

升吧,升完之后提示:

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven_14

还好这次能定位到准确的位置,把这个注释掉就好了,然后继续同步一下。Could not find method jackOptions() for arguments 

gradle修改maven gradle修改dependence后没有重新依赖_gradle_15

于是可以把上面那个jack可选项去掉了。再继续同步。

另外一个坑又出现了。

gradle修改maven gradle修改dependence后没有重新依赖_gradle修改maven_16

我的工程有主module和一个扫一扫module。

Could not resolve all files for configuration ':ScannerSDK:androidApis'.
 Failed to transform file 'android.jar' to match attributes {artifactType=android-mockable-jar, returnDefaultValues=false} using transform MockableJarTransform

完全搞不懂这个什么意思,网上也搜不到相关的信息,难道是我引入module的方式有问题吗(之前傻傻的怀疑是不是module的命名有什么问题:不能大写?懵逼,,,?带着这个怀疑,我自己又新建一个名字类似(也就是命名规则)的module,然后同步,结果是正常的。这就奇怪了,然后后面就打算看下两个module到底有什么区别,去分别看了下两个module的build.gradle文件,唯一的区别可能就是compileSdkVersion的不同了,我的主工程和新建的module用的是26版本,而扫一扫的module用的是25,于是把它改成一致的,神奇的事情发生了,居然同步成功了。。。。

gradle修改maven gradle修改dependence后没有重新依赖_android_17

大喘一口气了,继续编译。

 

gradle修改maven gradle修改dependence后没有重新依赖_依赖冲突_18

出现主module引用的扫一扫module的库的类文件找不到,我可没改动过引用关系,升级了gradle之后居然原来的引用关系不存在了。哎,没办法,只得从扫一扫中将该module目录下的lib里面的jar库也拷贝到主module一份看看。结果编译运行成功了。不知道两个module中引入了同一个库会不会在运行的时候有什么问题。。

对了,在我的主module引入扫一扫module是这样的:

compile(project(':ScannerSDK')) {    transitive = false}

也就是不进行依赖的传递,gradle2.3上是可以获取到扫一扫module下的jar类的,gradle3.2上就不能了,不知是什么原因了。

 

 后记:

就为了引入一个库,结果花费了2天的时间来搞这个,真是五味杂陈,自己对gradle构建还是认识不够啊。

-------------------------------------------------------优美分割线--------------------------------------------------------------

ps:gradle三种依赖仓库地址的配置的区别:

【gradle】 buildScript块、allprojects块、根级别三种所属的repositories区别

在Android Studio的Project的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.3.0'
        classpath 'com.novoda:bintray-release:0.4.0'

        // NOTE: Do not place your application dependencies here; they belong
        // in the individual module build.gradle files
    }
}

allprojects {
    repositories {
        jcenter()
        maven {url 'https://dl.bintray.com/calvinning/maven'}
    }
}

那么buildscript中的repositories和allprojects的repositories的作用和区别是什么呢? 
答: 
1、 buildscript里是gradle脚本执行所需依赖,分别是对应的maven库和插件 
2、 allprojects里是项目本身需要的依赖,比如我现在要依赖我自己maven库的toastutils库,那么我应该将maven {url ‘https://dl.bintray.com/calvinning/maven‘}写在这里,而不是buildscript中,不然找不到。