// Copyright 2018 The Bazel Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//    http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.devtools.build.lib.rules.android;

import com.google.common.collect.ImmutableMap;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.analysis.RuleContext;
import com.google.devtools.build.lib.packages.RuleClass.ConfiguredTargetFactory.RuleErrorException;
import com.google.devtools.build.lib.packages.RuleErrorConsumer;
import com.google.devtools.build.lib.rules.android.AndroidConfiguration.AndroidAaptVersion;
import com.google.devtools.build.lib.rules.android.databinding.DataBinding;
import com.google.devtools.build.lib.rules.android.databinding.DataBindingContext;
import com.google.devtools.build.lib.rules.java.ProguardHelper;
import com.google.devtools.build.lib.syntax.Type;
import java.util.List;
import java.util.Map;
import javax.annotation.Nullable;

/**
 * Processed Android data (assets, resources, and manifest) returned from resource processing.
 *
 * <p>In libraries, data is parsed, merged, and then validated. For top-level targets like
 * android_binary, however, most of these steps happen in a single monolithic action. The only thing
 * the monolithic action doesn't do is generate an R.class file for the resources. When combined
 * with such a file, this object should contain the same data as the results of the individual
 * actions.
 *
 * <p>In general, the individual actions should be used, as they are decoupled and designed to allow
 * parallelized processing of a dependency tree of android_library targets. The monolithic action
 * should only be used as part of building the data into a final APK that can become part of a
 * produce android_binary or other top-level APK.
 */
public class ProcessedAndroidData {
  private final ParsedAndroidResources resources;
  private final MergedAndroidAssets assets;
  private final ProcessedAndroidManifest manifest;
  private final Artifact rTxt;
  private final Artifact sourceJar;
  private final Artifact apk;
  @Nullable private final Artifact dataBindingInfoZip;
  private final ResourceDependencies resourceDeps;
  private final Artifact resourceProguardConfig;
  @Nullable private final Artifact mainDexProguardConfig;

  /** Processes Android data (assets, resources, and manifest) for android_binary targets. */
  public static ProcessedAndroidData processBinaryDataFrom(
      AndroidDataContext dataContext,
      RuleErrorConsumer errorConsumer,
      StampedAndroidManifest manifest,
      boolean conditionalKeepRules,
      Map<String, String> manifestValues,
      AndroidAaptVersion aaptVersion,
      AndroidResources resources,
      AndroidAssets assets,
      ResourceDependencies resourceDeps,
      AssetDependencies assetDeps,
      ResourceFilterFactory resourceFilterFactory,
      List<String> noCompressExtensions,
      boolean crunchPng,
      @Nullable Artifact featureOf,
      @Nullable Artifact featureAfter,
      DataBindingContext dataBindingContext)
      throws RuleErrorException, InterruptedException {
    if (conditionalKeepRules && aaptVersion != AndroidAaptVersion.AAPT2) {
      throw errorConsumer.throwWithRuleError(
          "resource cycle shrinking can only be enabled for builds with aapt2");
    }

    AndroidResourcesProcessorBuilder builder =
        builderForNonIncrementalTopLevelTarget(dataContext, manifest, manifestValues, aaptVersion)
            .setUseCompiledResourcesForMerge(aaptVersion == AndroidAaptVersion.AAPT2)
            .setManifestOut(
                dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_PROCESSED_MANIFEST))
            .setMergedResourcesOut(
                dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_ZIP))
            .setMainDexProguardOut(
                AndroidBinary.createMainDexProguardSpec(
                    dataContext.getLabel(), dataContext.getActionConstructionContext()))
            .conditionalKeepRules(conditionalKeepRules)
            .setFeatureOf(featureOf)
            .setFeatureAfter(featureAfter);
    dataBindingContext.supplyLayoutInfo(builder::setDataBindingInfoZip);
    return buildActionForBinary(
        dataContext,
        dataBindingContext,
        errorConsumer,
        builder,
        manifest,
        resources,
        assets,
        resourceDeps,
        assetDeps,
        resourceFilterFactory,
        noCompressExtensions,
        crunchPng);
  }

  public static ProcessedAndroidData processIncrementalBinaryDataFrom(
      RuleContext ruleContext,
      AndroidDataContext dataContext,
      StampedAndroidManifest manifest,
      Artifact apkOut,
      Artifact mergedResourcesOut,
      String proguardPrefix,
      Map<String, String> manifestValues)
      throws RuleErrorException {

    AndroidResourcesProcessorBuilder builder =
        builderForTopLevelTarget(dataContext, manifest, proguardPrefix, manifestValues)
            .targetAaptVersion(AndroidAaptVersion.chooseTargetAaptVersion(ruleContext))
            .setApkOut(apkOut)
            .setMergedResourcesOut(mergedResourcesOut);

    return buildActionForBinary(
        dataContext,
        DataBinding.contextFrom(ruleContext, dataContext.getAndroidConfig()),
        ruleContext,
        builder,
        manifest,
        AndroidResources.from(ruleContext, "resource_files"),
        AndroidAssets.from(ruleContext),
        ResourceDependencies.fromRuleDeps(ruleContext, /* neverlink = */ false),
        AssetDependencies.fromRuleDeps(ruleContext, /* neverlink = */ false),
        ResourceFilterFactory.fromRuleContextAndAttrs(ruleContext),
        ruleContext.getExpander().withDataLocations().tokenized("nocompress_extensions"),
        ruleContext.attributes().get("crunch_png", Type.BOOLEAN));
  }

  private static ProcessedAndroidData buildActionForBinary(
      AndroidDataContext dataContext,
      DataBindingContext dataBindingContext,
      RuleErrorConsumer errorConsumer,
      AndroidResourcesProcessorBuilder builder,
      StampedAndroidManifest manifest,
      AndroidResources resources,
      AndroidAssets assets,
      ResourceDependencies resourceDeps,
      AssetDependencies assetDeps,
      ResourceFilterFactory resourceFilterFactory,
      List<String> noCompressExtensions,
      boolean crunchPng)
      throws RuleErrorException {

    ResourceFilter resourceFilter =
        resourceFilterFactory.getResourceFilter(errorConsumer, resourceDeps, resources);

    // Filter unwanted resources out
    resources = resources.filterLocalResources(errorConsumer, resourceFilter);
    resourceDeps = resourceDeps.filter(errorConsumer, resourceFilter);

    return builder
        .setResourceFilterFactory(resourceFilterFactory)
        .setUncompressedExtensions(noCompressExtensions)
        .setCrunchPng(crunchPng)
        .withResourceDependencies(resourceDeps)
        .withAssetDependencies(assetDeps)
        .build(dataContext, resources, assets, manifest, dataBindingContext);
  }

  /** Processes Android data (assets, resources, and manifest) for android_local_test targets. */
  public static ProcessedAndroidData processLocalTestDataFrom(
      AndroidDataContext dataContext,
      DataBindingContext dataBindingContext,
      StampedAndroidManifest manifest,
      Map<String, String> manifestValues,
      AndroidAaptVersion aaptVersion,
      AndroidResources resources,
      AndroidAssets assets,
      ResourceDependencies resourceDeps,
      AssetDependencies assetDeps,
      List<String> noCompressExtensions)
      throws InterruptedException {

    return builderForNonIncrementalTopLevelTarget(
            dataContext, manifest, manifestValues, aaptVersion)
        .setUseCompiledResourcesForMerge(
            aaptVersion == AndroidAaptVersion.AAPT2
                && dataContext.getAndroidConfig().skipParsingAction())
        .setManifestOut(
            dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_PROCESSED_MANIFEST))
        .setMergedResourcesOut(
            dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_ZIP))
        .setCrunchPng(false)
        .withResourceDependencies(resourceDeps)
        .withAssetDependencies(assetDeps)
        .setUncompressedExtensions(noCompressExtensions)
        .build(dataContext, resources, assets, manifest, dataBindingContext);
  }

  /** Processes Android data (assets, resources, and manifest) for android_test targets. */
  public static ProcessedAndroidData processTestDataFrom(
      AndroidDataContext dataContext,
      DataBindingContext dataBindingContext,
      StampedAndroidManifest manifest,
      String packageUnderTest,
      boolean hasLocalResourceFiles,
      AndroidAaptVersion aaptVersion,
      AndroidResources resources,
      ResourceDependencies resourceDeps,
      AndroidAssets assets,
      AssetDependencies assetDeps)
      throws InterruptedException {

    AndroidResourcesProcessorBuilder builder =
        builderForNonIncrementalTopLevelTarget(
                dataContext, manifest, ImmutableMap.of(), aaptVersion)
            .setMergedResourcesOut(
                dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_ZIP))
            .setMainDexProguardOut(
                AndroidBinary.createMainDexProguardSpec(
                    dataContext.getLabel(), dataContext.getActionConstructionContext()))
            .setPackageUnderTest(packageUnderTest)
            .setIsTestWithResources(hasLocalResourceFiles)
            .withResourceDependencies(resourceDeps)
            .withAssetDependencies(assetDeps);

    return builder.build(dataContext, resources, assets, manifest, dataBindingContext);
  }

  /**
   * Common {@link AndroidResourcesProcessorBuilder} builder for non-incremental top-level targets.
   *
   * <p>The builder will be populated with commonly-used settings and outputs.
   */
  private static AndroidResourcesProcessorBuilder builderForNonIncrementalTopLevelTarget(
      AndroidDataContext dataContext,
      StampedAndroidManifest manifest,
      Map<String, String> manifestValues,
      AndroidAaptVersion aaptVersion)
      throws InterruptedException {

    return builderForTopLevelTarget(dataContext, manifest, "", manifestValues)
        .targetAaptVersion(aaptVersion)

        // Outputs
        .setApkOut(dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_APK))
        .setRTxtOut(dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_R_TXT))
        .setSourceJarOut(
            dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_JAVA_SOURCE_JAR))
        .setSymbols(dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_MERGED_SYMBOLS));
  }

  /**
   * Common {@link AndroidResourcesProcessorBuilder} builder for top-level targets.
   *
   * <p>The builder will be populated with commonly-used settings and outputs.
   */
  private static AndroidResourcesProcessorBuilder builderForTopLevelTarget(
      AndroidDataContext dataContext,
      StampedAndroidManifest manifest,
      String proguardPrefix,
      Map<String, String> manifestValues) {
    return new AndroidResourcesProcessorBuilder()
        // Settings
        .setDebug(dataContext.useDebug())
        .setJavaPackage(manifest.getPackage())
        .setApplicationId(manifestValues.get("applicationId"))
        .setVersionCode(manifestValues.get("versionCode"))
        .setVersionName(manifestValues.get("versionName"))
        .setThrowOnResourceConflict(dataContext.getAndroidConfig().throwOnResourceConflict())

        // Output
        .setProguardOut(
            ProguardHelper.getProguardConfigArtifact(
                dataContext.getLabel(),
                dataContext.getActionConstructionContext(),
                proguardPrefix));
  }

  static ProcessedAndroidData of(
      ParsedAndroidResources resources,
      MergedAndroidAssets assets,
      ProcessedAndroidManifest manifest,
      Artifact rTxt,
      Artifact sourceJar,
      Artifact apk,
      @Nullable Artifact dataBindingInfoZip,
      ResourceDependencies resourceDeps,
      Artifact resourceProguardConfig,
      @Nullable Artifact mainDexProguardConfig) {
    return new ProcessedAndroidData(
        resources,
        assets,
        manifest,
        rTxt,
        sourceJar,
        apk,
        dataBindingInfoZip,
        resourceDeps,
        resourceProguardConfig,
        mainDexProguardConfig);
  }

  private ProcessedAndroidData(
      ParsedAndroidResources resources,
      MergedAndroidAssets assets,
      ProcessedAndroidManifest manifest,
      Artifact rTxt,
      Artifact sourceJar,
      Artifact apk,
      @Nullable Artifact dataBindingInfoZip,
      ResourceDependencies resourceDeps,
      Artifact resourceProguardConfig,
      @Nullable Artifact mainDexProguardConfig) {
    this.resources = resources;
    this.assets = assets;
    this.manifest = manifest;
    this.rTxt = rTxt;
    this.sourceJar = sourceJar;
    this.apk = apk;
    this.dataBindingInfoZip = dataBindingInfoZip;
    this.resourceDeps = resourceDeps;
    this.resourceProguardConfig = resourceProguardConfig;
    this.mainDexProguardConfig = mainDexProguardConfig;
  }

  /**
   * Gets the fully processed data from this class.
   *
   * <p>Registers an action to run R class generation, the last step needed in resource processing.
   * Returns the fully processed data, including validated resources, wrapped in a ResourceApk.
   */
  public ResourceApk generateRClass(AndroidDataContext dataContext, AndroidAaptVersion aaptVersion)
      throws InterruptedException {
    return new RClassGeneratorActionBuilder()
        .targetAaptVersion(aaptVersion)
        .withDependencies(resourceDeps)
        .setClassJarOut(
            dataContext.createOutputArtifact(AndroidRuleClasses.ANDROID_RESOURCES_CLASS_JAR))
        .build(dataContext, this);
  }

  /**
   * Returns fully processed resources. The R class generator action will not be registered.
   *
   * @param rClassJar an artifact containing the resource class jar for these resources. An action
   *     to generate it must be registered elsewhere.
   */
  ResourceApk withValidatedResources(Artifact rClassJar) {
    // When assets and resources are processed together, they are both merged into the same zip
    Artifact mergedResources = assets.getMergedAssets();

    // Since parts of both merging and validation were already done in combined resource processing,
    // we need to build containers for both here.
    MergedAndroidResources merged =
        MergedAndroidResources.of(
            resources, mergedResources, rClassJar, dataBindingInfoZip, resourceDeps, manifest);

    // Combined resource processing does not produce aapt2 artifacts; they're nulled out
    ValidatedAndroidResources validated =
        ValidatedAndroidResources.of(merged, rTxt, sourceJar, apk, null, null, null);
    return ResourceApk.of(validated, assets, resourceProguardConfig, mainDexProguardConfig);
  }

  public MergedAndroidAssets getAssets() {
    return assets;
  }

  public ProcessedAndroidManifest getManifest() {
    return manifest;
  }

  public Artifact getRTxt() {
    return rTxt;
  }
}
