diff options
10 files changed, 107 insertions, 31 deletions
diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AarImport.java b/src/main/java/com/google/devtools/build/lib/rules/android/AarImport.java index d021892d8f..46f391878e 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AarImport.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AarImport.java @@ -108,7 +108,7 @@ public class AarImport implements RuleConfiguredTargetFactory { ruleContext, dataContext, manifest, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), neverlink); MergedAndroidAssets mergedAssets = AndroidAssets.forAarImport(assets) diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidBinary.java b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidBinary.java index dc4b78d317..90c9c6f303 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidBinary.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidBinary.java @@ -225,7 +225,7 @@ public abstract class AndroidBinary implements RuleConfiguredTargetFactory { .getPrerequisite("feature_after", Mode.TARGET, ApkInfo.PROVIDER) .getApk() : null, - DataBinding.contextFrom(ruleContext)) + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())) .generateRClass(dataContext, aaptVersion); } else { applicationManifest = @@ -246,7 +246,7 @@ public abstract class AndroidBinary implements RuleConfiguredTargetFactory { applicationManifest.packBinaryWithDataAndResources( ruleContext, dataContext, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), ruleContext.getImplicitOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_APK), resourceDeps, ruleContext.getImplicitOutputArtifact(AndroidRuleClasses.ANDROID_R_TXT), diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidConfiguration.java b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidConfiguration.java index 00134a7ca2..752b8cf1b1 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidConfiguration.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidConfiguration.java @@ -52,6 +52,7 @@ import javax.annotation.Nullable; @Immutable public class AndroidConfiguration extends BuildConfiguration.Fragment implements AndroidConfigurationApi { + /** * Converter for {@link * com.google.devtools.build.lib.rules.android.AndroidConfiguration.ConfigurationDistinguisher} @@ -729,6 +730,19 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment public boolean compressJavaResources; @Option( + name = "experimental_android_databinding_v2", + defaultValue = "false", + documentationCategory = OptionDocumentationCategory.OUTPUT_PARAMETERS, + effectTags = { + OptionEffectTag.AFFECTS_OUTPUTS, + OptionEffectTag.LOADING_AND_ANALYSIS, + OptionEffectTag.LOSES_INCREMENTAL_STATE, + }, + metadataTags = OptionMetadataTag.EXPERIMENTAL, + help = "Use android databinding v2") + public boolean dataBindingV2; + + @Option( name = "experimental_android_library_exports_manifest_default", defaultValue = "false", documentationCategory = OptionDocumentationCategory.UNDOCUMENTED, @@ -922,6 +936,7 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment private final boolean decoupleDataProcessing; private final boolean checkForMigrationTag; private final boolean oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest; + private final boolean dataBindingV2; AndroidConfiguration(Options options) throws InvalidConfigurationException { this.sdk = options.sdk; @@ -963,6 +978,7 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment this.checkForMigrationTag = options.checkForMigrationTag; this.oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest = options.oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest; + this.dataBindingV2 = options.dataBindingV2; if (incrementalDexingShardsAfterProguard < 0) { throw new InvalidConfigurationException( @@ -1015,7 +1031,8 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment AndroidRobolectricTestDeprecationLevel robolectricTestDeprecationLevel, boolean decoupleDataProcessing, boolean checkForMigrationTag, - boolean oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest) { + boolean oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest, + boolean dataBindingV2) { this.sdk = sdk; this.cpu = cpu; this.useIncrementalNativeLibs = useIncrementalNativeLibs; @@ -1052,6 +1069,7 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment this.checkForMigrationTag = checkForMigrationTag; this.oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest = oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest; + this.dataBindingV2 = dataBindingV2; } public String getCpu() { @@ -1211,6 +1229,10 @@ public class AndroidConfiguration extends BuildConfiguration.Fragment return oneVersionEnforcementUseTransitiveJarsForBinaryUnderTest; } + public boolean useDataBindingV2() { + return dataBindingV2; + } + @Override public String getOutputDirectoryName() { return configurationDistinguisher.suffix; diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLibrary.java b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLibrary.java index 8ed119b670..963ac63576 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLibrary.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLibrary.java @@ -169,7 +169,7 @@ public abstract class AndroidLibrary implements RuleConfiguredTargetFactory { ruleContext, dataContext, manifest, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), isNeverLink); MergedAndroidAssets assets = @@ -196,7 +196,7 @@ public abstract class AndroidLibrary implements RuleConfiguredTargetFactory { ruleContext.getImplicitOutputArtifact( AndroidRuleClasses.ANDROID_PROCESSED_MANIFEST), ruleContext.getImplicitOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_ZIP), - DataBinding.contextFrom(ruleContext)); + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); } if (ruleContext.hasErrors()) { return null; @@ -206,7 +206,7 @@ public abstract class AndroidLibrary implements RuleConfiguredTargetFactory { resourceApk = ResourceApk.processFromTransitiveLibraryData( dataContext, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), resourceDeps, assetDeps, StampedAndroidManifest.createEmpty(ruleContext, /* exported = */ false)); diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLocalTestBase.java b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLocalTestBase.java index 55fe52f37a..6e6743ce0e 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLocalTestBase.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidLocalTestBase.java @@ -101,7 +101,7 @@ public abstract class AndroidLocalTestBase implements RuleConfiguredTargetFactor buildResourceApk( dataContext, androidSemantics, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), AndroidManifest.fromAttributes(ruleContext, dataContext), AndroidResources.from(ruleContext, "resource_files"), AndroidAssets.from(ruleContext), @@ -122,7 +122,7 @@ public abstract class AndroidLocalTestBase implements RuleConfiguredTargetFactor applicationManifest.packBinaryWithDataAndResources( ruleContext, dataContext, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), ruleContext.getImplicitOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_APK), resourceDependencies, ruleContext.getImplicitOutputArtifact(AndroidRuleClasses.ANDROID_R_TXT), diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidSkylarkData.java b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidSkylarkData.java index 8d48497115..02f9808292 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/AndroidSkylarkData.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/AndroidSkylarkData.java @@ -175,7 +175,10 @@ public abstract class AndroidSkylarkData ctx, manifest.asStampedManifest(), ResourceDependencies.fromProviders(deps, neverlink), - DataBinding.contextFrom(enableDataBinding, ctx.getActionConstructionContext()), + DataBinding.contextFrom( + enableDataBinding, + ctx.getActionConstructionContext(), + ctx.getAndroidConfig()), aaptVersion); JavaInfo javaInfo = getJavaInfoForRClassJar(validated.getClassJar()); @@ -581,7 +584,10 @@ public abstract class AndroidSkylarkData crunchPng, /* featureOf = */ null, /* featureAfter = */ null, - DataBinding.contextFrom(dataBindingEnabled, ctx.getActionConstructionContext())) + DataBinding.contextFrom( + dataBindingEnabled, + ctx.getActionConstructionContext(), + ctx.getAndroidConfig())) .generateRClass(ctx, settings.aaptVersion); return AndroidBinaryDataInfo.of( diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/ApplicationManifest.java b/src/main/java/com/google/devtools/build/lib/rules/android/ApplicationManifest.java index 94e99ac53d..b0b08102d9 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/ApplicationManifest.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/ApplicationManifest.java @@ -420,7 +420,10 @@ public final class ApplicationManifest { .setSourceJarOut(resourceContainer.getJavaSourceJar()); } ResourceContainer processed = - builder.build(dataContext, resourceContainer, DataBinding.contextFrom(ruleContext)); + builder.build( + dataContext, + resourceContainer, + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); ResourceContainer finalContainer = new RClassGeneratorActionBuilder() @@ -496,7 +499,10 @@ public final class ApplicationManifest { .setStaticLibraryOut(merged.getStaticLibrary()) .build(dataContext, merged); - return ResourceApk.of(processed, resourceDeps, DataBinding.contextFrom(ruleContext)); + return ResourceApk.of( + processed, + resourceDeps, + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); } /* Creates an incremental apk from assets and data. */ @@ -550,12 +556,19 @@ public final class ApplicationManifest { .getFragment(AndroidConfiguration.class) .throwOnResourceConflict()) .setPackageUnderTest(null) - .build(dataContext, resourceContainer, DataBinding.contextFrom(ruleContext)); + .build( + dataContext, + resourceContainer, + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); // Intentionally skip building an R class JAR - incremental binaries handle this separately. return ResourceApk.of( - processed, resourceDeps, proguardCfg, null, DataBinding.contextFrom(ruleContext)); + processed, + resourceDeps, + proguardCfg, + null, + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); } /** Packages up the manifest with resource and assets from the rule and dependent resources. */ @@ -636,7 +649,10 @@ public final class ApplicationManifest { .setRTxtOut(resourceContainer.getRTxt()) .setSymbols(resourceContainer.getSymbols()) .setSourceJarOut(resourceContainer.getJavaSourceJar()) - .build(dataContext, resourceContainer, DataBinding.contextFrom(ruleContext)); + .build( + dataContext, + resourceContainer, + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())); ResourceContainer finalContainer = new RClassGeneratorActionBuilder() diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/DataBinding.java b/src/main/java/com/google/devtools/build/lib/rules/android/DataBinding.java index 9564643e8e..a5c4c33624 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/DataBinding.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/DataBinding.java @@ -148,11 +148,11 @@ public final class DataBinding { } } - private static final class EnabledDataBindingContext implements DataBindingContext { + private static final class EnabledDataBindingV1Context implements DataBindingContext { private final ActionConstructionContext actionConstructionContext; - private EnabledDataBindingContext(ActionConstructionContext actionConstructionContext) { + private EnabledDataBindingV1Context(ActionConstructionContext actionConstructionContext) { this.actionConstructionContext = actionConstructionContext; } @@ -269,7 +269,7 @@ public final class DataBinding { if (o == null || getClass() != o.getClass()) { return false; } - EnabledDataBindingContext that = (EnabledDataBindingContext) o; + EnabledDataBindingV1Context that = (EnabledDataBindingV1Context) o; return Objects.equals(actionConstructionContext, that.actionConstructionContext); } @@ -284,28 +284,52 @@ public final class DataBinding { } } + private static class EnabledDataBindingV2Context implements DataBindingContext { + + private final ActionConstructionContext actionContext; + + private EnabledDataBindingV2Context(ActionConstructionContext actionContext) { + this.actionContext = actionContext; + throw new UnsupportedOperationException("V2 not implemented yet."); + } + // TODO(b/112038432): Enable databinding v2. + } + private static final DataBindingContext DISABLED_CONTEXT = new DataBindingContext() {}; /** Supplies a databinding context from a rulecontext. */ - public static DataBindingContext contextFrom(RuleContext ruleContext) { + public static DataBindingContext contextFrom( + RuleContext ruleContext, AndroidConfiguration androidConfig) { if (isEnabled(ruleContext)) { - return asEnabledDataBindingContextFrom(ruleContext); + if (androidConfig.useDataBindingV2()) { + return asEnabledDataBindingV2ContextFrom(ruleContext); + } + return asEnabledDataBindingV1ContextFrom(ruleContext); } return asDisabledDataBindingContext(); } /** Supplies a databinding context from an action context. */ - public static DataBindingContext contextFrom(boolean enabled, ActionConstructionContext context) { + public static DataBindingContext contextFrom( + boolean enabled, ActionConstructionContext context, AndroidConfiguration androidConfig) { if (enabled) { - return asEnabledDataBindingContextFrom(context); + if (androidConfig.useDataBindingV2()) { + return asEnabledDataBindingV2ContextFrom(context); + } + return asEnabledDataBindingV1ContextFrom(context); } return asDisabledDataBindingContext(); } /** Supplies an enabled DataBindingContext from the action context. */ - public static DataBindingContext asEnabledDataBindingContextFrom( + private static DataBindingContext asEnabledDataBindingV1ContextFrom( + ActionConstructionContext actionContext) { + return new EnabledDataBindingV1Context(actionContext); + } + + private static DataBindingContext asEnabledDataBindingV2ContextFrom( ActionConstructionContext actionContext) { - return new EnabledDataBindingContext(actionContext); + return new EnabledDataBindingV2Context(actionContext); } /** Supplies a disabled (no-op) DataBindingContext. */ diff --git a/src/main/java/com/google/devtools/build/lib/rules/android/ProcessedAndroidData.java b/src/main/java/com/google/devtools/build/lib/rules/android/ProcessedAndroidData.java index d0bd385c0f..90a55e2d48 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/android/ProcessedAndroidData.java +++ b/src/main/java/com/google/devtools/build/lib/rules/android/ProcessedAndroidData.java @@ -124,7 +124,7 @@ public class ProcessedAndroidData { return buildActionForBinary( dataContext, - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), ruleContext, builder, manifest, diff --git a/src/test/java/com/google/devtools/build/lib/rules/android/AndroidResourcesTest.java b/src/test/java/com/google/devtools/build/lib/rules/android/AndroidResourcesTest.java index d1f9db8166..d60f365b71 100644 --- a/src/test/java/com/google/devtools/build/lib/rules/android/AndroidResourcesTest.java +++ b/src/test/java/com/google/devtools/build/lib/rules/android/AndroidResourcesTest.java @@ -145,13 +145,14 @@ public class AndroidResourcesTest extends ResourceTestBase { ImmutableList<Artifact> unfilteredResources, ImmutableList<Artifact> filteredResources) throws Exception { RuleContext ruleContext = getRuleContext(); + final AndroidDataContext dataContext = AndroidDataContext.forNative(ruleContext); ValidatedAndroidResources unfiltered = new AndroidResources(unfilteredResources, getResourceRoots(unfilteredResources)) .process( ruleContext, - AndroidDataContext.forNative(ruleContext), + dataContext, getManifest(), - DataBinding.contextFrom(ruleContext), + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()), /* neverlink = */ false); Optional<? extends AndroidResources> maybeFiltered = assertFilter(unfiltered, filteredResources, /* isDependency = */ true); @@ -227,7 +228,11 @@ public class AndroidResourcesTest extends ResourceTestBase { RuleContext ruleContext = getRuleContext(); ParsedAndroidResources parsed = - assertParse(ruleContext, DataBinding.asEnabledDataBindingContextFrom(ruleContext)); + assertParse( + ruleContext, + DataBinding.contextFrom( + ruleContext, + ruleContext.getConfiguration().getFragment(AndroidConfiguration.class))); // Since we are not using aapt2, there should be no compiled symbols assertThat(parsed.getCompiledSymbols()).isNull(); @@ -498,7 +503,7 @@ public class AndroidResourcesTest extends ResourceTestBase { false, null, null, - DataBinding.contextFrom(ruleContext)) + DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig())) .generateRClass(dataContext, AndroidAaptVersion.AUTO); assertThat(resourceApk.getResourceProguardConfig()).isNotNull(); @@ -510,7 +515,10 @@ public class AndroidResourcesTest extends ResourceTestBase { * for further validation. */ private ParsedAndroidResources assertParse(RuleContext ruleContext) throws Exception { - return assertParse(ruleContext, DataBinding.contextFrom(ruleContext)); + return assertParse( + ruleContext, + DataBinding.contextFrom( + ruleContext, ruleContext.getConfiguration().getFragment(AndroidConfiguration.class))); } private ParsedAndroidResources assertParse( |