// Copyright 2018 Google LLC
//
// 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.

import org.gradle.util.ConfigureUtil;

// A map of library to the dependencies that need to be added for it.
def firebaseDependenciesMap = [
  'app' : ['com.google.firebase:firebase-analytics'],
  'app_check' : ['com.google.firebase:firebase-appcheck',
                 'com.google.firebase:firebase-appcheck-debug',
                 'com.google.firebase:firebase-appcheck-playintegrity'],
  'play_services' : ['com.google.android.gms:play-services-base:18.7.2'],
  'analytics' : ['com.google.firebase:firebase-analytics'],
  'auth' : ['com.google.firebase:firebase-auth'],
  'database' : ['com.google.firebase:firebase-database'],
  'firestore' : ['com.google.firebase:firebase-firestore'],
  'functions' : ['com.google.firebase:firebase-functions'],
  'installations' : ['com.google.firebase:firebase-installations'],
  // Messaging has an additional local dependency to include.
  'messaging' : ['com.google.firebase:firebase-messaging',
                 'firebase_cpp_sdk.messaging:messaging_java',
                 'androidx.core:core:1.6.0-alpha03',
                 'com.google.flatbuffers:flatbuffers-java:1.12.0'],
  'performance' : ['com.google.firebase:firebase-perf'],
  'remote_config' : ['com.google.firebase:firebase-config'],
  'storage' : ['com.google.firebase:firebase-storage'],
  'testlab' : [],
  'ump' : ['com.google.android.ump:user-messaging-platform:3.2.0']
]

// A map of library to the gradle resources that they depend upon.
def firebaseResourceDependenciesMap = [
  'app' : [':app:app_resources',
           ':app:google_api_resources'],
  'app_check' : [':app_check:app_check_resources'],
  'auth' : [':auth:auth_resources'],
  'database' : [':database:database_resources'],
  'firestore' : [':firestore:firestore_resources'],
  'remote_config' : [':remote_config:remote_config_resources'],
  'storage' : [':storage:storage_resources'],
  'ump' : [':ump:ump_resources']
]

def setResourceDependencies(String subproject) {
  preDebugBuild.dependsOn gradle.includedBuild('firebase_cpp_sdk').task(
      "$subproject:generateDexJarDebug")
  preReleaseBuild.dependsOn gradle.includedBuild('firebase_cpp_sdk').task(
      "$subproject:generateDexJarRelease")
}

// Handles adding the Firebase C++ dependencies as properties.
class Dependencies {
  HashSet<String> libSet = new HashSet<String>()

  def getApp() {
    libSet.add('app')
    libSet.add('play_services')
  }
  def getAppWithoutPlayServices() {
    libSet.add('app')
  }
  def getAnalytics() {
    libSet.add('analytics')
  }
  def getAppCheck() {
    libSet.add('app_check')
  }
  def getAuth() {
    libSet.add('auth')
  }
  def getDatabase() {
    libSet.add('database')
  }
  def getFirestore() {
    libSet.add('firestore')
  }
  def getFunctions() {
    libSet.add('functions')
  }
  def getInstallations() {
    libSet.add('installations')
  }
  def getMessaging() {
    libSet.add('messaging')
  }
  def getPerformance() {
    libSet.add('performance')
  }
  def getRemoteConfig() {
    libSet.add('remote_config')
  }
  def getStorage() {
    libSet.add('storage')
  }
  def getUmp() {
    libSet.add('ump')
  }
}

// Extension to handle which Firebase C++ dependencies are being added to the
// gradle project.
// They are added via: firebaseCpp.dependencies "auth", "analytics", ...
class FirebaseCppExtension {
  Dependencies dependencies = new Dependencies()

  void dependencies(Closure c) {
    ConfigureUtil.configure(c, dependencies)
  }
  void dependencies(Action<? super Dependencies> action) {
    action.execute(dependencies)
  }
}

project.extensions.create('firebaseCpp', FirebaseCppExtension)

apply from: "${gradle.firebase_cpp_sdk_dir}/android_build_files/generate_proguard.gradle"

def generateAndAddProguard(String lib) {
  // Set the property on the project, so it is easier to use
  project.ext.firebase_cpp_sdk_dir = "${gradle.firebase_cpp_sdk_dir}"

  // Generate the proguard file for the library, and add it to the project
  generateProguardFileWithCallback(lib, new Action<File>() {
      public void execute(File proguardFile) {
        project.android.buildTypes.debug.proguardFile proguardFile
        project.android.buildTypes.release.proguardFile proguardFile
      }
  })
}

project.afterEvaluate {
  if (!firebaseCpp.dependencies.libSet.isEmpty()) {
    // App is required, so add it if it wasn't included.
    if (!firebaseCpp.dependencies.libSet.contains('app')) {
      firebaseCpp.dependencies.libSet.add('app')
      firebaseCpp.dependencies.libSet.add('play_services')
    }

    // Add the bill-of-materials
    project.dependencies {
      implementation platform('com.google.firebase:firebase-bom:34.2.0')
    }
    for (String lib : firebaseCpp.dependencies.libSet) {
      // Generate and include the proguard file
      generateAndAddProguard(lib)

      // Add the dependencies for the library
      for (String dep : firebaseDependenciesMap.get(lib)) {
        project.dependencies {
          implementation "$dep"
        }
      }
      if (firebaseResourceDependenciesMap.containsKey(lib)) {
        for (String resDep : firebaseResourceDependenciesMap.get(lib)) {
          setResourceDependencies(resDep)
        }
      }
    }
  }

}
