Android打包设置Debug与Release环境切换(build.gradle buildTypes properties env)

4,231 阅读5分钟

场景

App里包含Api的Url,web网址,变量,这些值在开发环境(线下)和正式环境(线上)是不同的,因为项目需要我打三个包,一个是开发环境,就是咱们调试debug,第二个是sandbox包,这个其实就是beta版本,给测试用户安装使用,反馈问题的版本,第三个包是release包,这个版本放的Api的Url,web网址,变量都是需要访问正式服务器的.

准备

我一开始的实现方式是把所有变量写到一个接口里,写一个正式一个沙盒,设置页面做一个隐藏的按钮点击十下后切换模式.

1.常量接口文件

2.切换模式

之后的项目就这么一直使用,但是项目老大说最好apk包里不要包含sandbox的url,变量.于是去网上查解决方案.

网上解决方案

大致分为两种.

1.第一种是在build.gradle文件中找到buildTypes,填写需要的变量

上面这段代码粘贴于网络,

个人感觉一个key要写两个地方不太好吧,像我要打三个包key就要复制三遍,还有一点每次修改都是重新build一下,鸡肋.

2.第二种是Properties保存易变常量,此方案是java的方式,个人感觉不太适合android.看一下实现.

上面这段代码粘贴于网络,

会有乱码问题,需要设置解决, properties文件会保存在assets目录,这样大家都不用反编译都看到重要的变量了.不好.

最佳实现

想起之前项目src下的debug目录不会被打包到apk里,再结合第一种方案,想到一个结合版本.下面看实现步骤.

第一步.

创建一个接口AppConstant.java

/**
 * 应用常量
 *
 * @author Wyjson
 * @version 1
 * @date 2019-10-28 14:39
 */
public interface AppConstant {

    /**
     * 通用api
     */
    String API_URL = "https://dev-api.url.com";

    /**
     * 用户api
     */
    String API_USER_URL = "https://dev-user-api.url.com";

    /**
     * web app url
     */
    String WEB_APP_URL = "https://dev.url.com";

    /**
     * 商城
     */
    String SHOP_URL = WEB_APP_URL + "/shop";
    /**
     * 订单详细
     */
    String ORDER_DETAIL_URL = WEB_APP_URL + "/orders/%s";
    /**
     * 收藏
     */
    String FAVOUR_URL = WEB_APP_URL + "/favours";}

解释一下为什么要AppConstant.java,之前我在写laravel的时候需要.env文件来切换服务器和本地开发环境,他的设计就是统一一个config.php文件去调用.env里的不同变量.项目在去调用这个config.php文件.比如有一天不用这个解决方案了,你只需要修改AppConstant里的值,项目其他地方是不用任何修改的.

第二步.

创建一个抽象类AppConfig.java

public abstract class AppConfig {

    /**
     * 通用api
     */
    public abstract String getApiUrl();

    /**
     * 用户api
     */
    public abstract String getApiUserUrl();

    /**
     * web app url
     */
    public abstract String getWebAppUrl();

}

第三步.

创建一个ReleaseAppConfig.java继承AppConfig.java

/**
 * 应用线上配置
 *
 * @author Wyjson
 * @version 1
 * @date 2019-10-28 15:21
 */
public class ReleaseAppConfig extends AppConfig {
    @Override
    public String getApiUrl() {
        return "https://api.url.com";
    }

    @Override
    public String getApiUserUrl() {
        return "https://user-api.url.com";
    }

    @Override
    public String getWebAppUrl() {
        return "https://url.com";
    }
}

这里填写release线上版本的变量.

第四步.

创建一个DebugAppConfig.java继承AppConfig.java

DebugAppConfig.java创建目录是/src/debug/java/你的应用包名/DebugAppConfig.java

这样在打正式包就不会把debug的信息打到apk里了.

/**
 * 应用开发配置
 *
 * @author Wyjson
 * @version 1
 * @date 2019-10-28 15:24
 */
public class DebugAppConfig extends AppConfig {

    @Override
    public String getApiUrl() {
        return "https://dev-api.url.com";    
    }

    @Override
    public String getApiUserUrl() {
        return "https://dev-user-api.url.com";    
    }

    @Override
    public String getWebAppUrl() {
        return "https://dev.url.com";    
    }
}

第五步.

用到第一种解决方案,在App的build.gradle文件中找到buildTypes,添加

buildTypes {
        debug {
            buildConfigField 'com.wyjson.releasebuildconfig.constant.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.DebugAppConfig()'
            minifyEnabled false
            zipAlignEnabled true
            shrinkResources false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
        release {
            buildConfigField 'com.wyjson.releasebuildconfig.constant.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.constant.ReleaseAppConfig()'
            minifyEnabled true
            zipAlignEnabled true
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }

想必大家都看到了,

在debug里添加

buildConfigField 'com.wyjson.releasebuildconfig.constant.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.DebugAppConfig()'

在release里添加

buildConfigField 'com.wyjson.releasebuildconfig.constant.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.constant.ReleaseAppConfig()'

build一下,你会发现BuildConfig文件已经帮你生成好了

第六步.

修改第一步创建的AppConstant.java文件

/**
 * 应用常量
 *
 * @author Wyjson
 * @version 1
 * @date 2019-10-28 14:39
 */
public interface AppConstant {

    /**
     * 通用api
     */
    String API_URL = BuildConfig.AppConfig.getApiUrl();

    /**
     * 用户api
     */
    String API_USER_URL = BuildConfig.AppConfig.getApiUserUrl();

    /**
     * web app url
     */
    String WEB_APP_URL = BuildConfig.AppConfig.getWebAppUrl();
    /**
     * 商城
     */
    String SHOP_URL = WEB_APP_URL + "/shop";
    /**
     * 订单详细
     */
    String ORDER_DETAIL_URL = WEB_APP_URL + "/orders/%s";
    /**
     * 收藏
     */
    String FAVOUR_URL = WEB_APP_URL + "/favours";}

大功告成,至此就可以去项目里调用AppConstant文件啦.看着步骤多,其实有几步都是一起操作的.我是为了拆分的详细一点,以后使用直接复制粘贴就Ok啦.

下面分享一下更多配置文件的使用

多配置文件

上文说到,我的需求是要打三个包,还有sandbox包,也就是beta版本.这个版本是我们新功能上线前先去给测试用户安装的包.和debug步骤一样,

创建一个SandboxAppConfig.java继承ReleaseAppConfig.java

SandboxAppConfig.java创建目录是/src/sandbox/java/你的应用包名/SandboxAppConfig.java

/**
 * 应用Beta配置
 *
 * @author Wyjson
 * @version 1
 * @date 2019-10-28 15:24
 */
public class SandboxAppConfig extends ReleaseAppConfig {
    @Override
    public String getApiUrl() {
        return "https://sandbox-api.url.com";
    }

    @Override
    public String getApiUserUrl() {
        return "https://sandbox-user-api.url.com";
    }

    @Override
    public String getWebAppUrl() {
        return "https://sandbox.url.com";
    }
}

在App的build.gradle文件中找到buildTypes,添加

buildTypes {
        sandbox {
            buildConfigField 'com.wyjson.releasebuildconfig.constant.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.SandboxAppConfig()'
            minifyEnabled true
            zipAlignEnabled true
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }

在sandbox里添加

buildConfigField 'com.wyjson.releasebuildconfig.AppConfig', 'AppConfig', 'new com.wyjson.releasebuildconfig.SandboxAppConfig()'

操作完成上面的步骤你会发现找不到ReleaseAppConfig.java,需要在App的build.gradle文件中找到android{},添加

sourceSets {
        main {
            java.srcDirs = [                    'src/main/java',                    'src/sandbox/java'            ]
        }
    }

ide识别出是java代码,就Ok啦.

效果

帮助

如果在使用中遇到问题或者想看到详细的代码可以去github

github.com/wangyao5018…

转载请写明出处.juejin.im/post/684490…