// Copyright 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <vector>

#include "chrome/browser/android/signin/signin_manager_android.h"

#include "base/android/jni_android.h"
#include "base/android/jni_array.h"
#include "base/android/jni_string.h"
#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/memory/ref_counted.h"
#include "base/message_loop/message_loop_proxy.h"
#include "base/prefs/pref_service.h"
#include "chrome/browser/bookmarks/bookmark_model_factory.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/browsing_data/browsing_data_helper.h"
#include "chrome/browser/browsing_data/browsing_data_remover.h"
#include "chrome/browser/profiles/profile_manager.h"
#include "chrome/browser/signin/account_tracker_service_factory.h"
#include "chrome/browser/signin/android_profile_oauth2_token_service.h"
#include "chrome/browser/signin/profile_oauth2_token_service_factory.h"
#include "chrome/browser/signin/signin_manager_factory.h"
#include "chrome/common/pref_names.h"
#include "components/bookmarks/browser/bookmark_model.h"
#include "components/signin/core/browser/account_tracker_service.h"
#include "components/signin/core/browser/profile_oauth2_token_service.h"
#include "components/signin/core/browser/signin_manager.h"
#include "components/signin/core/browser/signin_metrics.h"
#include "components/signin/core/common/profile_management_switches.h"
#include "google_apis/gaia/gaia_constants.h"
#include "jni/SigninManager_jni.h"

#if defined(ENABLE_CONFIGURATION_POLICY)
#include "chrome/browser/policy/cloud/user_cloud_policy_manager_factory.h"
#include "chrome/browser/policy/cloud/user_policy_signin_service_factory.h"
#include "chrome/browser/policy/cloud/user_policy_signin_service_mobile.h"
#include "components/policy/core/browser/browser_policy_connector.h"
#include "components/policy/core/common/cloud/cloud_policy_core.h"
#include "components/policy/core/common/cloud/cloud_policy_store.h"
#include "components/policy/core/common/cloud/user_cloud_policy_manager.h"
#include "google_apis/gaia/gaia_auth_util.h"
#include "net/url_request/url_request_context_getter.h"
#endif

using bookmarks::BookmarkModel;

namespace {

// A BrowsingDataRemover::Observer that clears all Profile data and then
// invokes a callback and deletes itself.
class ProfileDataRemover : public BrowsingDataRemover::Observer {
 public:
  ProfileDataRemover(Profile* profile, const base::Closure& callback)
      : callback_(callback),
        origin_loop_(base::MessageLoopProxy::current()),
        remover_(BrowsingDataRemover::CreateForUnboundedRange(profile)) {
    remover_->AddObserver(this);
    remover_->Remove(BrowsingDataRemover::REMOVE_ALL, BrowsingDataHelper::ALL);
  }

  ~ProfileDataRemover() override {}

  void OnBrowsingDataRemoverDone() override {
    remover_->RemoveObserver(this);
    origin_loop_->PostTask(FROM_HERE, callback_);
    origin_loop_->DeleteSoon(FROM_HERE, this);
  }

 private:
  base::Closure callback_;
  scoped_refptr<base::MessageLoopProxy> origin_loop_;
  BrowsingDataRemover* remover_;

  DISALLOW_COPY_AND_ASSIGN(ProfileDataRemover);
};

}  // namespace

SigninManagerAndroid::SigninManagerAndroid(JNIEnv* env, jobject obj)
    : profile_(NULL),
      weak_factory_(this) {
  java_signin_manager_.Reset(env, obj);
  profile_ = ProfileManager::GetActiveUserProfile();
  DCHECK(profile_);
  pref_change_registrar_.Init(profile_->GetPrefs());
  pref_change_registrar_.Add(
      prefs::kSigninAllowed,
      base::Bind(&SigninManagerAndroid::OnSigninAllowedPrefChanged,
                 base::Unretained(this)));
}

SigninManagerAndroid::~SigninManagerAndroid() {}

void SigninManagerAndroid::CheckPolicyBeforeSignIn(JNIEnv* env,
                                                   jobject obj,
                                                   jstring username) {
#if defined(ENABLE_CONFIGURATION_POLICY)
  username_ = base::android::ConvertJavaStringToUTF8(env, username);
  policy::UserPolicySigninService* service =
      policy::UserPolicySigninServiceFactory::GetForProfile(profile_);
  service->RegisterForPolicy(
      base::android::ConvertJavaStringToUTF8(env, username),
      base::Bind(&SigninManagerAndroid::OnPolicyRegisterDone,
                 weak_factory_.GetWeakPtr()));
#else
  // This shouldn't be called when ShouldLoadPolicyForUser() is false.
  NOTREACHED();
  base::android::ScopedJavaLocalRef<jstring> domain;
  Java_SigninManager_onPolicyCheckedBeforeSignIn(env,
                                                 java_signin_manager_.obj(),
                                                 domain.obj());
#endif
}

void SigninManagerAndroid::FetchPolicyBeforeSignIn(JNIEnv* env, jobject obj) {
#if defined(ENABLE_CONFIGURATION_POLICY)
  if (!dm_token_.empty()) {
    policy::UserPolicySigninService* service =
        policy::UserPolicySigninServiceFactory::GetForProfile(profile_);
    service->FetchPolicyForSignedInUser(
        username_,
        dm_token_,
        client_id_,
        profile_->GetRequestContext(),
        base::Bind(&SigninManagerAndroid::OnPolicyFetchDone,
                   weak_factory_.GetWeakPtr()));
    dm_token_.clear();
    client_id_.clear();
    return;
  }
#endif
  // This shouldn't be called when ShouldLoadPolicyForUser() is false, or when
  // CheckPolicyBeforeSignIn() failed.
  NOTREACHED();
  Java_SigninManager_onPolicyFetchedBeforeSignIn(env,
                                                 java_signin_manager_.obj());
}

void SigninManagerAndroid::OnSignInCompleted(JNIEnv* env,
                                             jobject obj,
                                             jstring username,
                                             jobjectArray accountIds,
                                             jobjectArray accountNames) {
  DVLOG(1) << "SigninManagerAndroid::OnSignInCompleted";
  // Seed the account tracker with id/email information if provided.
  if (accountIds && accountNames) {
    std::vector<std::string> gaia_ids;
    std::vector<std::string> emails;
    base::android::AppendJavaStringArrayToStringVector(env, accountIds,
                                                       &gaia_ids);
    base::android::AppendJavaStringArrayToStringVector(env, accountNames,
                                                       &emails);
    DCHECK_EQ(emails.size(), gaia_ids.size());
    DVLOG(1) << "SigninManagerAndroid::OnSignInCompleted: seeding "
             << emails.size() << " accounts";

    AccountTrackerService* tracker =
        AccountTrackerServiceFactory::GetForProfile(profile_);
    for (size_t i = 0; i < emails.size(); ++i) {
      DVLOG(1) << "SigninManagerAndroid::OnSignInCompleted: seeding"
               << " gaia_id=" << gaia_ids[i]
               << " email=" << emails[i];
      if (!gaia_ids[i].empty() && !emails[i].empty())
        tracker->SeedAccountInfo(gaia_ids[i], emails[i]);
    }
  } else {
    DVLOG(1) << "SigninManagerAndroid::OnSignInCompleted: missing ids/email"
             << " ids=" << (void*) accountIds
             << " emails=" << (void*) accountNames;
  }

  SigninManagerFactory::GetForProfile(profile_)->OnExternalSigninCompleted(
      base::android::ConvertJavaStringToUTF8(env, username));
}

void SigninManagerAndroid::SignOut(JNIEnv* env, jobject obj) {
  SigninManagerFactory::GetForProfile(profile_)->SignOut(
      signin_metrics::USER_CLICKED_SIGNOUT_SETTINGS);
}

base::android::ScopedJavaLocalRef<jstring>
SigninManagerAndroid::GetManagementDomain(JNIEnv* env, jobject obj) {
  base::android::ScopedJavaLocalRef<jstring> domain;

#if defined(ENABLE_CONFIGURATION_POLICY)
  policy::UserCloudPolicyManager* manager =
      policy::UserCloudPolicyManagerFactory::GetForBrowserContext(profile_);
  policy::CloudPolicyStore* store = manager->core()->store();

  if (store && store->is_managed() && store->policy()->has_username()) {
    domain.Reset(
        base::android::ConvertUTF8ToJavaString(
            env, gaia::ExtractDomainName(store->policy()->username())));
  }
#endif

  return domain;
}

void SigninManagerAndroid::WipeProfileData(JNIEnv* env, jobject obj) {
  // The ProfileDataRemover deletes itself once done.
  new ProfileDataRemover(
      profile_,
      base::Bind(&SigninManagerAndroid::OnBrowsingDataRemoverDone,
                 weak_factory_.GetWeakPtr()));
}

#if defined(ENABLE_CONFIGURATION_POLICY)

void SigninManagerAndroid::OnPolicyRegisterDone(
    const std::string& dm_token,
    const std::string& client_id) {
  dm_token_ = dm_token;
  client_id_ = client_id;

  JNIEnv* env = base::android::AttachCurrentThread();
  base::android::ScopedJavaLocalRef<jstring> domain;
  if (!dm_token_.empty()) {
    DCHECK(!username_.empty());
    domain.Reset(
        base::android::ConvertUTF8ToJavaString(
            env, gaia::ExtractDomainName(username_)));
  } else {
    username_.clear();
  }

  Java_SigninManager_onPolicyCheckedBeforeSignIn(env,
                                                 java_signin_manager_.obj(),
                                                 domain.obj());
}

void SigninManagerAndroid::OnPolicyFetchDone(bool success) {
  Java_SigninManager_onPolicyFetchedBeforeSignIn(
      base::android::AttachCurrentThread(),
      java_signin_manager_.obj());
}

#endif

void SigninManagerAndroid::OnBrowsingDataRemoverDone() {
  BookmarkModel* model = BookmarkModelFactory::GetForProfile(profile_);
  model->RemoveAllUserBookmarks();

  // All the Profile data has been wiped. Clear the last signed in username as
  // well, so that the next signin doesn't trigger the acount change dialog.
  ClearLastSignedInUser();

  Java_SigninManager_onProfileDataWiped(base::android::AttachCurrentThread(),
                                        java_signin_manager_.obj());
}

void SigninManagerAndroid::ClearLastSignedInUser(JNIEnv* env, jobject obj) {
  ClearLastSignedInUser();
}

void SigninManagerAndroid::ClearLastSignedInUser() {
  profile_->GetPrefs()->ClearPref(prefs::kGoogleServicesLastUsername);
}

void SigninManagerAndroid::MergeSessionCompleted(
    const std::string& account_id,
    const GoogleServiceAuthError& error) {
  merge_session_helper_->RemoveObserver(this);
  merge_session_helper_.reset();
}

void SigninManagerAndroid::LogInSignedInUser(JNIEnv* env, jobject obj) {
  SigninManagerBase* signin_manager =
      SigninManagerFactory::GetForProfile(profile_);
    // Just fire the events and let the Account Reconcilor handles everything.
    AndroidProfileOAuth2TokenService* token_service =
        ProfileOAuth2TokenServiceFactory::GetPlatformSpecificForProfile(
            profile_);
    const std::string& primary_acct =
        signin_manager->GetAuthenticatedAccountId();
    token_service->ValidateAccounts(primary_acct, true);
}

jboolean SigninManagerAndroid::IsSigninAllowedByPolicy(JNIEnv* env,
                                                       jobject obj) {
  return SigninManagerFactory::GetForProfile(profile_)->IsSigninAllowed();
}

jboolean SigninManagerAndroid::IsSignedInOnNative(JNIEnv* env, jobject obj) {
  return SigninManagerFactory::GetForProfile(profile_)->IsAuthenticated();
}

void SigninManagerAndroid::OnSigninAllowedPrefChanged() {
  Java_SigninManager_onSigninAllowedByPolicyChanged(
      base::android::AttachCurrentThread(), java_signin_manager_.obj(),
      SigninManagerFactory::GetForProfile(profile_)->IsSigninAllowed());
}

static jlong Init(JNIEnv* env, jobject obj) {
  SigninManagerAndroid* signin_manager_android =
      new SigninManagerAndroid(env, obj);
  return reinterpret_cast<intptr_t>(signin_manager_android);
}

static jboolean ShouldLoadPolicyForUser(JNIEnv* env,
                                        jobject obj,
                                        jstring j_username) {
#if defined(ENABLE_CONFIGURATION_POLICY)
  std::string username =
      base::android::ConvertJavaStringToUTF8(env, j_username);
  return !policy::BrowserPolicyConnector::IsNonEnterpriseUser(username);
#else
  return false;
#endif
}

// static
bool SigninManagerAndroid::Register(JNIEnv* env) {
  return RegisterNativesImpl(env);
}
