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

#include "components/omnibox/browser/omnibox_metrics_provider.h"

#include <memory>
#include <string>

#include "base/memory/scoped_refptr.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/scoped_feature_list.h"
#include "base/test/task_environment.h"
#include "components/omnibox/browser/autocomplete_match.h"
#include "components/omnibox/browser/autocomplete_match_type.h"
#include "components/omnibox/browser/autocomplete_provider.h"
#include "components/omnibox/browser/autocomplete_result.h"
#include "components/omnibox/browser/fake_autocomplete_provider.h"
#include "components/omnibox/browser/match_compare.h"
#include "components/omnibox/browser/omnibox_field_trial.h"
#include "components/omnibox/browser/omnibox_log.h"
#include "components/omnibox/browser/omnibox_popup_selection.h"
#include "components/omnibox/common/omnibox_features.h"
#include "components/ukm/test_ukm_recorder.h"
#include "services/metrics/public/cpp/ukm_builders.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/metrics_proto/omnibox_event.pb.h"
#include "third_party/metrics_proto/omnibox_scoring_signals.pb.h"
#include "ui/base/window_open_disposition.h"

using ScoringSignals = ::metrics::OmniboxEventProto::Suggestion::ScoringSignals;
using OmniboxScoringSignals = ::metrics::OmniboxScoringSignals;

struct SessionData {
  bool zero_prefix_suggestions_shown_in_session = false;
  bool zero_prefix_search_suggestions_shown_in_session = false;
  bool zero_prefix_url_suggestions_shown_in_session = false;
  bool typed_search_suggestions_shown_in_session = false;
  bool typed_url_suggestions_shown_in_session = false;
  bool contextual_search_suggestions_shown_in_session = false;
  bool lens_action_shown_in_session = false;
};

const SessionData kTypedSearchShown = {false, false, false, true, false};
const SessionData kTypedUrlShown = {false, false, false, false, true};
const SessionData kTypedSearchAndUrlShown = {false, false, false, true, true};

const SessionData kZeroPrefixSearchShown = {true, true, false, false, false};
const SessionData kZeroPrefixUrlShown = {true, false, true, false, false};
const SessionData kZeroPrefixSearchAndUrlShown = {true, true, true, false,
                                                  false};

class OmniboxMetricsProviderTest : public testing::Test {
 public:
  OmniboxMetricsProviderTest() = default;
  ~OmniboxMetricsProviderTest() override = default;

  void SetUp() override {
    autocomplete_provider_ =
        new FakeAutocompleteProvider(AutocompleteProvider::TYPE_SEARCH);
    metrics_provider_ = std::make_unique<OmniboxMetricsProvider>();
  }

  void TearDown() override { metrics_provider_.reset(); }

  OmniboxLog BuildOmniboxLog(const AutocompleteResult& result,
                             size_t selected_index,
                             SessionData session_data,
                             bool contextual_search_selected = false,
                             bool lens_action_selected = false) {
    return OmniboxLog(
        /*text=*/u"my text", /*just_deleted_text=*/false,
        /*input_type=*/metrics::OmniboxInputType::URL,
        /*in_keyword_mode=*/false,
        /*entry_method=*/
        metrics::OmniboxEventProto_KeywordModeEntryMethod_INVALID,
        /*is_popup_open=*/false,
        /*selection=*/OmniboxPopupSelection(selected_index),
        /*disposition=*/WindowOpenDisposition::CURRENT_TAB,
        /*is_paste_and_go=*/false,
        /*tab_id=*/SessionID::NewUnique(),
        /*current_page_classification=*/
        metrics::OmniboxEventProto_PageClassification_NTP_REALBOX,
        /*elapsed_time_since_user_first_modified_omnibox=*/base::TimeDelta(),
        /*completed_length=*/0,
        /*elapsed_time_since_last_change_to_default_match=*/base::TimeDelta(),
        /*result=*/result, /*destination_url=*/GURL("https://www.example.com/"),
        /*is_incognito=*/false,
        /*zero_prefix_suggestions_shown_in_session=*/
        session_data.zero_prefix_suggestions_shown_in_session,
        /*zero_prefix_search_suggestions_shown_in_session=*/
        session_data.zero_prefix_search_suggestions_shown_in_session,
        /*zero_prefix_url_suggestions_shown_in_session=*/
        session_data.zero_prefix_url_suggestions_shown_in_session,
        /*typed_search_suggestions_shown_in_session=*/
        session_data.typed_search_suggestions_shown_in_session,
        /*typed_url_suggestions_shown_in_session=*/
        session_data.typed_url_suggestions_shown_in_session,
        /*contextual_search_suggestions_selected_in_session=*/
        contextual_search_selected,
        /*contextual_search_suggestions_shown_in_session=*/
        session_data.contextual_search_suggestions_shown_in_session,
        /*lens_action_selected_in_session=*/
        lens_action_selected,
        /*lens_action_shown_in_session=*/
        session_data.lens_action_shown_in_session);
  }

  AutocompleteMatch BuildMatch(AutocompleteMatch::Type type) {
    return AutocompleteMatch(autocomplete_provider_.get(), /*relevance=*/0,
                             /*deletable=*/false, type);
  }

  void RecordMetrics(const OmniboxLog& log) {
    metrics_provider_->RecordMetrics(log);
  }

  void RecordContextualSearchPrecisionRecallUsage(const OmniboxLog& log) {
    metrics_provider_->RecordContextualSearchPrecisionRecallUsage(log);
  }

  void RecordLogAndVerifyScoringSignals(
      const OmniboxLog& log,
      OmniboxScoringSignals& expected_scoring_signals) {
    // Clear the event cache so we start with a clean slate.
    metrics_provider_->omnibox_events_cache.clear_omnibox_event();

    metrics_provider_->RecordOmniboxEvent(log);

    EXPECT_EQ(metrics_provider_->omnibox_events_cache.omnibox_event_size(), 1);
    const metrics::OmniboxEventProto& omnibox_event =
        metrics_provider_->omnibox_events_cache.omnibox_event(0);

    for (int i = 0; i < omnibox_event.suggestion_size(); i++) {
      const metrics::OmniboxEventProto::Suggestion& suggestion =
          omnibox_event.suggestion(i);
      // Scoring signals should not be logged when in incognito/off-the-record
      // mode, regardless of result type.
      if (log.is_incognito) {
        EXPECT_FALSE(suggestion.has_scoring_signals());
        continue;
      }

      // When not in incognito, scoring signals should only be logged for the
      // proper suggestion types. Check that the signals are logged correctly
      // for URL types and Search types, while not being logged for any others.
      if (suggestion.has_result_type()) {
        EXPECT_TRUE(suggestion.has_scoring_signals());

        if (suggestion.result_type() ==
            metrics::
                OmniboxEventProto_Suggestion_ResultType_SEARCH_WHAT_YOU_TYPED) {
          EXPECT_EQ(suggestion.scoring_signals().search_suggest_relevance(),
                    expected_scoring_signals.search_suggest_relevance());
          EXPECT_EQ(suggestion.scoring_signals().is_search_suggest_entity(),
                    expected_scoring_signals.is_search_suggest_entity());
        } else {
          EXPECT_EQ(
              suggestion.scoring_signals()
                  .first_bookmark_title_match_position(),
              expected_scoring_signals.first_bookmark_title_match_position());
          EXPECT_EQ(suggestion.scoring_signals().allowed_to_be_default_match(),
                    expected_scoring_signals.allowed_to_be_default_match());
          EXPECT_EQ(suggestion.scoring_signals().length_of_url(),
                    expected_scoring_signals.length_of_url());
        }
      } else {
        EXPECT_FALSE(suggestion.has_scoring_signals());
      }
    }

    // Clear the event cache.
    metrics_provider_->omnibox_events_cache.clear_omnibox_event();
  }

 protected:
  base::test::TaskEnvironment task_environment_;
  scoped_refptr<FakeAutocompleteProvider> autocomplete_provider_;
  std::unique_ptr<OmniboxMetricsProvider> metrics_provider_;
};

TEST_F(OmniboxMetricsProviderTest, RecordMetrics_SingleURL) {
  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches(
        {BuildMatch(AutocompleteMatch::Type::URL_WHAT_YOU_TYPED)});
    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/kTypedUrlShown);
    log.ukm_source_id = ukm::NoURLSourceId();
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);

    // Verify the UKM event.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kUrl));
  }

  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches(
        {BuildMatch(AutocompleteMatch::Type::URL_WHAT_YOU_TYPED)});
    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/kZeroPrefixUrlShown);
    log.text = u"";
    log.ukm_source_id = ukm::NoURLSourceId();
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kUrl, /*expected_count=*/1);

    // Verify the UKM event.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kUrl));
  }
}

TEST_F(OmniboxMetricsProviderTest, RecordMetrics_SingleSearch) {
  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});
    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/kTypedSearchShown);
    log.ukm_source_id = ukm::NoURLSourceId();
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);

    // Verify the UKM event.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kSearch));
  }

  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});
    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/kZeroPrefixSearchShown);
    log.ukm_source_id = ukm::NoURLSourceId();
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kSearch, /*expected_count=*/1);

    // Verify the UKM event.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kSearch));
  }
}

TEST_F(OmniboxMetricsProviderTest, RecordContextualSearchPrecisionRecallUsage) {
  // Contextual search suggestion shown, but not selected.
  {
    base::HistogramTester histogram_tester;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});

    SessionData session_data = kZeroPrefixSearchShown;
    session_data.contextual_search_suggestions_shown_in_session = true;

    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/session_data,
                                     /*contextual_search_selected=*/false,
                                     /*lens_action_selected=*/false);
    RecordContextualSearchPrecisionRecallUsage(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Precision", /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Precision", false,
        /*expected_count=*/1);

    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Recall",
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Recall", true,
        /*expected_count=*/1);

    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Usage",
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Usage", false,
        /*expected_count=*/1);
  }

  // Contextual search suggestion shown and selected.
  {
    base::HistogramTester histogram_tester;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});

    SessionData session_data = kZeroPrefixSearchShown;
    session_data.contextual_search_suggestions_shown_in_session = true;

    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/session_data,
                                     /*contextual_search_selected=*/true,
                                     /*lens_action_selected=*/false);
    RecordContextualSearchPrecisionRecallUsage(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Precision", /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Precision", true,
        /*expected_count=*/1);

    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Recall",
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Recall", true,
        /*expected_count=*/1);

    histogram_tester.ExpectTotalCount(
        "Omnibox.ContextualSearchSuggestion.Usage",
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.ContextualSearchSuggestion.Usage", true, /*expected_count=*/1);
  }

  // Google Lens action shown, but not selected.
  {
    base::HistogramTester histogram_tester;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});

    SessionData session_data = kZeroPrefixSearchShown;
    session_data.lens_action_shown_in_session = true;

    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/session_data,
                                     /*contextual_search_selected=*/false,
                                     /*lens_action_selected=*/false);
    RecordContextualSearchPrecisionRecallUsage(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Precision", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Precision", false,
                                       /*expected_count=*/1);

    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Recall", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Recall", true,
                                       /*expected_count=*/1);

    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Usage", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Usage", false,
                                       /*expected_count=*/1);
  }

  // Google Lens action shown and selected.
  {
    base::HistogramTester histogram_tester;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST)});

    SessionData session_data = kZeroPrefixSearchShown;
    session_data.lens_action_shown_in_session = true;

    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/0,
                                     /*session_data=*/session_data,
                                     /*contextual_search_selected=*/false,
                                     /*lens_action_selected=*/true);
    RecordContextualSearchPrecisionRecallUsage(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Precision", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Precision", true,
                                       /*expected_count=*/1);

    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Recall", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Recall", true,
                                       /*expected_count=*/1);

    histogram_tester.ExpectTotalCount("Omnibox.LensAction.Usage", 1);
    histogram_tester.ExpectBucketCount("Omnibox.LensAction.Usage", true,
                                       /*expected_count=*/1);
  }
}

TEST_F(OmniboxMetricsProviderTest, RecordMetrics_MultipleSearch) {
  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches(
        {BuildMatch(AutocompleteMatch::Type::URL_WHAT_YOU_TYPED),
         BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST),
         BuildMatch(AutocompleteMatch::Type::URL_WHAT_YOU_TYPED)});
    OmniboxLog log = BuildOmniboxLog(result, /*selected_index=*/1,
                                     /*session_data=*/kTypedSearchAndUrlShown);
    log.ukm_source_id = ukm::NoURLSourceId();
    log.elapsed_time_since_user_focused_omnibox = base::Milliseconds(10);
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.TypedSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);

    // Verify the UKM event and the full set of metrics.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kPageClassificationName,
        static_cast<uint64_t>(
            metrics::OmniboxEventProto_PageClassification_NTP_REALBOX));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kProviderTypeName,
        static_cast<uint64_t>(metrics::OmniboxEventProto_ProviderType_SEARCH));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeName,
        static_cast<uint64_t>(
            metrics::OmniboxEventProto_Suggestion::SEARCH_SUGGEST));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kSearch));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kSelectedIndexName, 1ul);
    // With exponential bucketing scheme with a standard spacing of 2.0, 10
    // falls into the 8-16 bucket as the boundaries of the buckets increase
    // exponentially, e.g., 1, 2, 4, 8, 16, etc.
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTimeSinceLastFocusMsName,
        8ul);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTypedLengthName, 7ul);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTypingDurationMsName,
        0ul);
    ukm_recorder.ExpectEntryMetric(
        entry,
        ukm::builders::Omnibox_SuggestionUsed::kZeroPrefixSearchShownName,
        false);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kZeroPrefixUrlShownName,
        false);
  }
  {
    base::HistogramTester histogram_tester;
    ukm::TestAutoSetUkmRecorder ukm_recorder;

    AutocompleteResult result;
    result.AppendMatches({BuildMatch(AutocompleteMatch::Type::HISTORY_URL),
                          BuildMatch(AutocompleteMatch::Type::SEARCH_SUGGEST),
                          BuildMatch(AutocompleteMatch::Type::HISTORY_URL)});
    OmniboxLog log =
        BuildOmniboxLog(result, /*selected_index=*/1,
                        /*session_data=*/kZeroPrefixSearchAndUrlShown);
    log.text = u"";
    log.ukm_source_id = ukm::NoURLSourceId();
    log.elapsed_time_since_user_focused_omnibox = base::Milliseconds(10);
    RecordMetrics(log);

    // Verify the UMA histograms.
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionUsed.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kSearch,
        /*expected_count=*/1);

    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ClientSummarizedResultType.ByPageContext.NTP_"
        "REALBOX",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);
    histogram_tester.ExpectBucketCount(
        "Omnibox.SuggestionShown.ZeroSuggest.ClientSummarizedResultType."
        "ByPageContext.NTP_REALBOX",
        ClientSummarizedResultType::kUrl,
        /*expected_count=*/1);

    // Verify the UKM event and the full set of metrics.
    const char* entry_name = ukm::builders::Omnibox_SuggestionUsed::kEntryName;
    EXPECT_EQ(ukm_recorder.GetEntriesByName(entry_name).size(), 1ul);
    auto* entry = ukm_recorder.GetEntriesByName(entry_name)[0].get();
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kPageClassificationName,
        static_cast<uint64_t>(
            metrics::OmniboxEventProto_PageClassification_NTP_REALBOX));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kProviderTypeName,
        static_cast<uint64_t>(metrics::OmniboxEventProto_ProviderType_SEARCH));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeName,
        static_cast<uint64_t>(
            metrics::OmniboxEventProto_Suggestion::SEARCH_SUGGEST));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kResultTypeGroupName,
        static_cast<uint64_t>(ClientSummarizedResultType::kSearch));
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kSelectedIndexName, 1ul);
    // With exponential bucketing scheme with a standard spacing of 2.0, 10
    // falls into the 8-16 bucket as the boundaries of the buckets increase
    // exponentially, e.g., 1, 2, 4, 8, 16, etc.
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTimeSinceLastFocusMsName,
        8ul);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTypedLengthName, 0ul);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kTypingDurationMsName,
        0ul);
    ukm_recorder.ExpectEntryMetric(
        entry,
        ukm::builders::Omnibox_SuggestionUsed::kZeroPrefixSearchShownName,
        true);
    ukm_recorder.ExpectEntryMetric(
        entry, ukm::builders::Omnibox_SuggestionUsed::kZeroPrefixUrlShownName,
        true);
  }
}

TEST_F(OmniboxMetricsProviderTest, RecordMetrics_InvalidUkmSourceId) {
  base::HistogramTester histogram_tester;
  ukm::TestAutoSetUkmRecorder ukm_recorder;
  AutocompleteResult result;
  result.AppendMatches(
      {BuildMatch(AutocompleteMatch::Type::URL_WHAT_YOU_TYPED)});
  OmniboxLog log =
      BuildOmniboxLog(result, /*selected_index=*/0, /*session_data=*/{});
  RecordMetrics(log);

  // Verify the UMA histogram.
  histogram_tester.ExpectBucketCount(
      "Omnibox.SuggestionUsed.ClientSummarizedResultType",
      ClientSummarizedResultType::kUrl, 1);

  // Verify the UKM event was not logged due to invalid ukm source id.
  EXPECT_EQ(
      ukm_recorder
          .GetEntriesByName(ukm::builders::Omnibox_SuggestionUsed::kEntryName)
          .size(),
      0ul);
}

// TODO(b/261895038): This test is flaky on android.  Currently scoring signals
// logging is only enabled on desktop, so disable for mobile.
#if !(BUILDFLAG(IS_IOS) || BUILDFLAG(IS_ANDROID))
TEST_F(OmniboxMetricsProviderTest, LogScoringSignals) {
  // Enable feature flag to log scoring signals.
  OmniboxFieldTrial::ScopedMLConfigForTesting scoped_ml_config;
  scoped_ml_config.GetMLConfig().log_url_scoring_signals = true;

  // Populate a set of scoring signals with some test values. This will be used
  // to ensure the scoring signals are being propagated correctly.
  OmniboxScoringSignals expected_url_scoring_signals;
  expected_url_scoring_signals.set_first_bookmark_title_match_position(3);
  expected_url_scoring_signals.set_allowed_to_be_default_match(true);
  expected_url_scoring_signals.set_length_of_url(20);

  OmniboxScoringSignals expected_search_scoring_signals;
  expected_search_scoring_signals.set_search_suggest_relevance(1000);
  expected_search_scoring_signals.set_is_search_suggest_entity(true);

  // Create matches and populate the scoring signals. Signals should only be
  // logged for non-search suggestions.
  ACMatches matches = {
      BuildMatch(AutocompleteMatchType::Type::BOOKMARK_TITLE),
      BuildMatch(AutocompleteMatchType::Type::SEARCH_WHAT_YOU_TYPED)};
  for (auto& match : matches) {
    match.scoring_signals = AutocompleteMatch::IsSearchHistoryType(match.type)
                                ? expected_search_scoring_signals
                                : expected_url_scoring_signals;
  }
  AutocompleteResult result;
  result.AppendMatches(matches);

  // Create the log and call simulate logging.
  OmniboxLog log =
      BuildOmniboxLog(result, /*selected_index=*/1, /*session_data=*/{});
  RecordLogAndVerifyScoringSignals(log, *matches[0].scoring_signals);

  // Now, "turn on" incognito mode, scoring signals should not be logged.
  log.is_incognito = true;
  RecordLogAndVerifyScoringSignals(log, *matches[0].scoring_signals);
}
#endif  // !(BUILDFLAG(IS_IOS) || BUILDFLAG(IS_ANDROID))
