这个答案将演示项目中的实现、api和编译之间的区别。
假设我有一个有三个Gradle模块的项目:
app (Android应用程序)
myandroidlibrary(一个Android库)
myjavalibrary(一个Java库)
应用程序有myandroidlibrary作为依赖项。Myandroidlibrary有myjavlibrary作为依赖项。
myjavlibrary有一个MySecret类
public class MySecret {
public static String getSecret() {
return "Money";
}
}
myandroidlibrary中有MyAndroidComponent类,用于操作MySecret类的值。
public class MyAndroidComponent {
private static String component = MySecret.getSecret();
public static String getComponent() {
return "My component: " + component;
}
}
最后,app只对myandroidlibrary的值感兴趣
TextView tvHelloWorld = findViewById(R.id.tv_hello_world);
tvHelloWorld.setText(MyAndroidComponent.getComponent());
现在,让我们谈谈依赖关系……
应用需要消耗:myandroidlibrary,所以在应用构建中。Gradle使用实现。
(注意:你也可以使用api/compile。但请稍等片刻。)
dependencies {
implementation project(':myandroidlibrary')
}
你认为myandroidlibrary构建了什么?Gradle应该是什么样子?我们应该使用哪个作用域?
我们有三个选择:
dependencies {
// Option #1
implementation project(':myjavalibrary')
// Option #2
compile project(':myjavalibrary')
// Option #3
api project(':myjavalibrary')
}
它们之间的区别是什么,我应该用什么?
编译或Api(选项#2或#3)
如果你使用的是编译器或者api。我们的Android应用现在可以访问myandroidcomponent依赖,这是一个MySecret类。
TextView textView = findViewById(R.id.text_view);
textView.setText(MyAndroidComponent.getComponent());
// You can access MySecret
textView.setText(MySecret.getSecret());
实现(选项#1)
如果您正在使用实现配置,MySecret将不会公开。
TextView textView = findViewById(R.id.text_view);
textView.setText(MyAndroidComponent.getComponent());
// You can NOT access MySecret
textView.setText(MySecret.getSecret()); // Won't even compile
那么,应该选择哪种配置呢?那要看你的要求了。
如果你想公开依赖关系,请使用api或compile。
如果你不想公开依赖关系(隐藏你的内部模块),那么使用实现。
注意:
这只是Gradle配置的一个要点,参见表49.1。Java库插件-用于声明依赖关系的配置,以获得更详细的解释。
这个答案的示例项目可以在https://github.com/aldoKelvianto/ImplementationVsCompile上找到