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

#include "chrome/browser/android/omnibox/omnibox_prerender.h"

#include "base/android/jni_string.h"
#include "base/check.h"
#include "base/notreached.h"
#include "chrome/browser/android/tab_android.h"
#include "chrome/browser/predictors/autocomplete_action_predictor.h"
#include "chrome/browser/predictors/autocomplete_action_predictor_factory.h"
#include "chrome/browser/predictors/loading_predictor.h"
#include "chrome/browser/predictors/loading_predictor_factory.h"
#include "chrome/browser/preloading/autocomplete_dictionary_preload_service.h"
#include "chrome/browser/preloading/autocomplete_dictionary_preload_service_factory.h"
#include "chrome/browser/preloading/prefetch/search_prefetch/search_prefetch_service.h"
#include "chrome/browser/preloading/prefetch/search_prefetch/search_prefetch_service_factory.h"
#include "chrome/browser/preloading/prerender/prerender_manager.h"
#include "chrome/browser/preloading/prerender/prerender_utils.h"
#include "chrome/browser/preloading/search_preload/search_preload_service.h"
#include "chrome/browser/preloading/search_preload/search_preload_service_factory.h"
#include "chrome/browser/profiles/profile.h"
#include "components/omnibox/browser/autocomplete_match.h"
#include "components/omnibox/browser/autocomplete_result.h"
#include "components/omnibox/browser/base_search_provider.h"
#include "content/public/browser/web_contents.h"
#include "url/gurl.h"

// Must come after all headers that specialize FromJniType() / ToJniType().
#include "chrome/browser/ui/android/omnibox/jni_headers/OmniboxPrerender_jni.h"

using base::android::JavaParamRef;
using predictors::AutocompleteActionPredictor;
using predictors::AutocompleteActionPredictorFactory;

OmniboxPrerender::OmniboxPrerender(JNIEnv* env,
                                   const jni_zero::JavaRef<jobject>& obj)
    : weak_java_omnibox_(env, obj) {}

OmniboxPrerender::~OmniboxPrerender() = default;

jlong JNI_OmniboxPrerender_Init(JNIEnv* env,
                                const jni_zero::JavaParamRef<jobject>& obj) {
  OmniboxPrerender* omnibox = new OmniboxPrerender(env, obj);
  return reinterpret_cast<intptr_t>(omnibox);
}

void OmniboxPrerender::Clear(JNIEnv* env,
                             Profile* profile) {
  DCHECK(profile);
  if (!profile)
    return;
  AutocompleteActionPredictor* action_predictor =
      AutocompleteActionPredictorFactory::GetForProfile(profile);
  action_predictor->UpdateDatabaseFromTransitionalMatches(GURL());
}

void OmniboxPrerender::InitializeForProfile(JNIEnv* env,
                                            Profile* profile) {
  // Initialize the AutocompleteActionPredictor for this profile.
  // It needs to register for notifications as part of its initialization.
  AutocompleteActionPredictorFactory::GetForProfile(profile);
}

void OmniboxPrerender::PrerenderMaybe(
    JNIEnv* env,
    const JavaParamRef<jstring>& j_url,
    const JavaParamRef<jstring>& j_current_url,
    jlong jsource_match,
    Profile* profile,
    const JavaParamRef<jobject>& j_tab) {
  AutocompleteResult* autocomplete_result =
      reinterpret_cast<AutocompleteResult*>(jsource_match);
  std::u16string url_string =
      base::android::ConvertJavaStringToUTF16(env, j_url);
  std::u16string current_url_string =
      base::android::ConvertJavaStringToUTF16(env, j_current_url);
  content::WebContents* web_contents =
      TabAndroid::GetNativeTab(env, j_tab)->web_contents();
  // TODO(apiccion) Use a delegate for communicating with web_contents.
  // This can happen in OmniboxTests since the results are generated
  // in Java only.
  if (!autocomplete_result)
    return;
  if (!profile)
    return;

  if (auto* dictionary_preload_service =
          AutocompleteDictionaryPreloadServiceFactory::GetForProfile(profile)) {
    dictionary_preload_service->MaybePreload(*autocomplete_result);
  }

  // TODO(crbug.com/40830195): Consider how to co-work with preconnect.
  if (SearchPrefetchService* search_prefetch_service =
          SearchPrefetchServiceFactory::GetForProfile(profile)) {
    search_prefetch_service->OnResultChanged(web_contents,
                                             *autocomplete_result);
  }

  if (SearchPreloadService* search_preload_service =
          SearchPreloadServiceFactory::GetForProfile(profile)) {
    search_preload_service->OnAutocompleteResultChanged(web_contents,
                                                        *autocomplete_result);
  }

  auto* default_match = autocomplete_result->default_match();
  if (!default_match)
    return;

  AutocompleteActionPredictor* action_predictor =
      AutocompleteActionPredictorFactory::GetForProfile(profile);
  if (!action_predictor)
    return;

  action_predictor->
      RegisterTransitionalMatches(url_string, *autocomplete_result);
  AutocompleteActionPredictor::Action recommended_action =
      action_predictor->RecommendAction(url_string, *default_match,
                                        web_contents);

  GURL current_url = GURL(current_url_string);
  // Ask for prerendering if the destination URL is different than the
  // current URL.
  if (default_match->destination_url == current_url)
    return;

  switch (recommended_action) {
    case AutocompleteActionPredictor::ACTION_PRERENDER:
      DoPrerender(*default_match, profile, web_contents);
      break;
    case AutocompleteActionPredictor::ACTION_PRECONNECT:
      DoPreconnect(*default_match, profile);
      break;
    case AutocompleteActionPredictor::ACTION_NONE:
      break;
    default:
      NOTREACHED();
  }
}

void OmniboxPrerender::DoPrerender(const AutocompleteMatch& match,
                                   Profile* profile,
                                   content::WebContents* web_contents) {
  DCHECK(profile);
  if (!profile)
    return;
  DCHECK(web_contents);
  if (!web_contents)
    return;

  // AutocompleteActionPredictor does not perform prerendering for search
  // AutocompleteMatches. See `AutocompleteActionPredictor::RecommendAction` for
  // more information.
  // SearchPrefetchService is responsible for handling search
  // AutocompleteMatches and preloading search result pages when needed.
  DCHECK(!AutocompleteMatch::IsSearchType(match.type));
  predictors::AutocompleteActionPredictorFactory::GetForProfile(profile)
      ->StartPrerendering(match.destination_url, *web_contents);
}

void OmniboxPrerender::DoPreconnect(const AutocompleteMatch& match,
                                    Profile* profile) {
  auto* loading_predictor =
      predictors::LoadingPredictorFactory::GetForProfile(profile);
  if (loading_predictor) {
    loading_predictor->PrepareForPageLoad(
        /*initiator_origin=*/std::nullopt, match.destination_url,
        predictors::HintOrigin::OMNIBOX,
        predictors::AutocompleteActionPredictor::IsPreconnectable(match));
  }
}
