You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Gradle Release构建替换主srcDir遇重复类报错求助

解决Android Release构建中替换源码目录导致的重复类问题

我之前也踩过一模一样的坑!核心问题其实是你没彻底替换掉原来的主源码目录——默认情况下Android Gradle插件会把src/main/java加入所有变体的源码集,如果你只是追加处理后的目录而不移除原目录,就会同时包含两份相同的类文件,自然报重复类错误。

下面是我验证过的解决方案,分两步走:

1. 先定义可靠的源码预处理任务

首先把预处理逻辑封装成独立的Copy任务,明确输入输出路径,这样Gradle能正确做增量构建,避免重复执行:

task processReleaseSources(type: Copy) {
    // 输入:原main源码目录
    from "src/main/java"
    // 输出:处理后的代码放在build目录下的generated文件夹(避免和其他目录冲突)
    into "$buildDir/generated/sources/processed/release/java"
    
    // 这里替换成你的正则处理逻辑
    filter { line ->
        line.replaceAll(/旧的正则匹配规则/, "新的替换内容")
    }
    
    // 只处理Java文件,有Kotlin的话可以再加一行include "**/*.kt"
    include "**/*.java"
}

2. 给Release变体单独替换源码集

接下来找到Release变体,把它的源码集里的原src/main/java去掉,换成预处理后的目录,同时确保编译任务依赖预处理任务:

android {
    // 常规配置:compileSdk、defaultConfig、buildTypes等
    compileSdk 34
    defaultConfig {
        applicationId "com.your.app"
        minSdk 24
        targetSdk 34
        versionCode 1
        versionName "1.0"
    }

    buildTypes {
        release {
            minifyEnabled true
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
        debug {
            // Debug构建保持原源码目录不变
        }
    }

    // 遍历所有变体,只修改Release的源码集
    applicationVariants.all { variant ->
        if (variant.name.equalsIgnoreCase("release")) {
            variant.sourceSets.each { sourceSet ->
                // 移除原main java目录
                sourceSet.java.srcDirs = sourceSet.java.srcDirs - file("src/main/java")
                // 添加预处理后的目录
                sourceSet.java.srcDirs += processReleaseSources.outputs.files
            }
            // 确保编译Release代码前先执行预处理任务
            variant.javaCompileProvider.get().dependsOn(processReleaseSources)
        }
    }
}

关键注意点

  • 如果用Kotlin开发,记得同时处理sourceSet.kotlin.srcDirs,逻辑和Java目录一致;
  • 输出路径一定要放在build目录下,避免把生成的代码提交到版本库;
  • 用variant.javaCompileProvider.get()而非直接引用compileReleaseJavaWithJavac,是为了兼容不同Gradle版本的API变化;
  • 增量构建:因为明确了from和into,Gradle会自动检测原文件变化,只有源码修改时才会重新执行预处理任务。

这样配置后,Release构建就只会使用预处理后的代码,Debug构建还是用原源码,也不会出现重复类的问题了。

内容的提问来源于stack exchange,提问作者Nobby_Nobody

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.22 09:28:32