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

#include "ui/accessibility/ax_language_detection.h"

#include <stddef.h>
#include <stdint.h>

#include <memory>

#include "base/command_line.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/scoped_feature_list.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/accessibility/accessibility_features.h"
#include "ui/accessibility/accessibility_switches.h"
#include "ui/accessibility/ax_enums.mojom.h"
#include "ui/accessibility/ax_node.h"
#include "ui/accessibility/ax_tree.h"

namespace ui {

const std::string kTextEnglish =
    "This is text created using Google Translate, it is unlikely to be "
    "idiomatic in the given target language. This text is only used to "
    "test language detection";

const std::string kTextFrench =
    "Ce texte a été créé avec Google Translate, il est peu probable qu'il "
    "soit idiomatique dans la langue cible indiquée Ce texte est "
    "uniquement utilisé pour tester la détection de la langue.";

const std::string kTextGerman =
    "Dies ist ein mit Google Translate erstellter Text. Es ist "
    "unwahrscheinlich, dass er in der angegebenen Zielsprache idiomatisch "
    "ist. Dieser Text wird nur zum Testen der Spracherkennung verwendet.";

const std::string kTextSpanish =
    "Este es un texto creado usando Google Translate, es poco probable que sea "
    "idiomático en el idioma de destino dado. Este texto solo se usa para "
    "probar la detección de idioma.";

// This test fixture is a friend of classes in ax_language_detection.h in order
// to enable testing of internals.
//
// When used with TEST_F, the test body is a subclass of this fixture, so we
// need to re-expose any members through this fixture in order for them to
// be accessible from within the test body.
class AXLanguageDetectionTestFixture : public testing::Test {
 public:
  AXLanguageDetectionTestFixture() = default;
  ~AXLanguageDetectionTestFixture() override = default;

  AXLanguageDetectionTestFixture(const AXLanguageDetectionTestFixture&) =
      delete;
  AXLanguageDetectionTestFixture& operator=(
      const AXLanguageDetectionTestFixture&) = delete;

 protected:
  bool IsStaticLanguageDetectionEnabled() {
    return AXLanguageDetectionManager::IsStaticLanguageDetectionEnabled();
  }

  bool IsDynamicLanguageDetectionEnabled() {
    return AXLanguageDetectionManager::IsDynamicLanguageDetectionEnabled();
  }

  AXLanguageDetectionObserver* getObserver(AXTree& tree) {
    return tree.language_detection_manager->language_detection_observer_.get();
  }

  int get_score(AXTree& tree, const std::string& lang) {
    return tree.language_detection_manager->lang_info_stats_.GetScore(lang);
  }

  // Accessors for testing metric data.
  void disable_metric_clearing(AXTree& tree) {
    tree.language_detection_manager->lang_info_stats_.disable_metric_clearing_ =
        true;
  }

  int count_detection_attempted(AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_
        .count_detection_attempted_;
  }

  int count_detection_results(AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_
        .count_detection_results_;
  }

  int count_labelled(AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_.count_labelled_;
  }

  int count_labelled_with_top_result(AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_
        .count_labelled_with_top_result_;
  }

  int count_overridden(AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_.count_overridden_;
  }

  const absl::flat_hash_set<std::string>& unique_top_lang_detected(
      AXTree& tree) const {
    return tree.language_detection_manager->lang_info_stats_
        .unique_top_lang_detected_;
  }
};

class AXLanguageDetectionTestStaticContent
    : public AXLanguageDetectionTestFixture {
 public:
  AXLanguageDetectionTestStaticContent() = default;
  ~AXLanguageDetectionTestStaticContent() override = default;

  AXLanguageDetectionTestStaticContent(
      const AXLanguageDetectionTestStaticContent&) = delete;
  AXLanguageDetectionTestStaticContent& operator=(
      const AXLanguageDetectionTestStaticContent&) = delete;

  void SetUp() override {
    AXLanguageDetectionTestFixture::SetUp();

    base::CommandLine::ForCurrentProcess()->AppendSwitch(
        ::switches::kEnableExperimentalAccessibilityLanguageDetection);
  }
};

class AXLanguageDetectionTestDynamicContent
    : public AXLanguageDetectionTestStaticContent {
 public:
  AXLanguageDetectionTestDynamicContent() = default;
  ~AXLanguageDetectionTestDynamicContent() override = default;

  AXLanguageDetectionTestDynamicContent(
      const AXLanguageDetectionTestDynamicContent&) = delete;
  AXLanguageDetectionTestDynamicContent& operator=(
      const AXLanguageDetectionTestDynamicContent&) = delete;

  void SetUp() override {
    AXLanguageDetectionTestStaticContent::SetUp();

    base::CommandLine::ForCurrentProcess()->AppendSwitch(
        ::switches::kEnableExperimentalAccessibilityLanguageDetectionDynamic);
  }
};

TEST_F(AXLanguageDetectionTestFixture, StaticContentFeatureFlag) {
  // TODO(crbug.com/41417304): Remove this test once this feature is stable
  EXPECT_FALSE(
      ::switches::IsExperimentalAccessibilityLanguageDetectionEnabled());
  EXPECT_FALSE(IsStaticLanguageDetectionEnabled());

  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);

  EXPECT_TRUE(
      ::switches::IsExperimentalAccessibilityLanguageDetectionEnabled());
  EXPECT_TRUE(IsStaticLanguageDetectionEnabled());
}

TEST_F(AXLanguageDetectionTestFixture, DynamicContentFeatureFlag) {
  // TODO(crbug.com/41417304): Remove this test once this feature is stable
  EXPECT_FALSE(
      ::switches::IsExperimentalAccessibilityLanguageDetectionDynamicEnabled());
  EXPECT_FALSE(IsDynamicLanguageDetectionEnabled());

  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetectionDynamic);

  EXPECT_TRUE(
      ::switches::IsExperimentalAccessibilityLanguageDetectionDynamicEnabled());
  EXPECT_TRUE(IsDynamicLanguageDetectionEnabled());
}

TEST_F(AXLanguageDetectionTestFixture, FeatureFlag) {
  // TODO(crbug.com/41417304): Remove this test once this feature is stable
  EXPECT_FALSE(IsStaticLanguageDetectionEnabled());
  EXPECT_FALSE(IsDynamicLanguageDetectionEnabled());

  base::test::ScopedFeatureList scoped_feature_list;
  scoped_feature_list.InitWithFeatures(
      {features::kEnableAccessibilityLanguageDetection}, {});

  EXPECT_TRUE(IsStaticLanguageDetectionEnabled());
  EXPECT_TRUE(IsDynamicLanguageDetectionEnabled());
}

TEST(AXLanguageDetectionTest, LangAttrInheritanceFeatureFlagOff) {
  // Test lang attribute inheritance when feature flag is off.
  //
  // Lang attribute inheritance is handled by GetLanguage.
  //
  // Tree:
  //        1
  //      2   3
  //    4
  //  5
  //
  //  1 - English lang attribute
  //  2 - French lang attribute
  //
  //  Expected:
  //    3 - inherit English from 1
  //    4 - inherit French from 2
  //    5 - inherit Frnech from 4/2
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(5);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "en");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kGenericContainer;
    node2.child_ids.resize(1);
    node2.child_ids[0] = 4;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
  }

  {
    AXNodeData& node4 = initial_state.nodes[3];
    node4.id = 4;
    node4.role = ax::mojom::Role::kStaticText;
    node4.child_ids.resize(1);
    node4.child_ids[0] = 5;
  }

  {
    AXNodeData& node5 = initial_state.nodes[4];
    node5.id = 5;
    node5.role = ax::mojom::Role::kInlineTextBox;
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  {
    AXNode* node1 = tree.GetFromId(1);
    EXPECT_EQ(node1->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node1->GetLanguage(), "en");
  }

  {
    AXNode* node2 = tree.GetFromId(2);
    EXPECT_EQ(node2->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node2->GetLanguage(), "fr");
  }

  {
    AXNode* node3 = tree.GetFromId(3);
    EXPECT_EQ(node3->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node3->GetLanguage(), "en");
  }

  {
    AXNode* node4 = tree.GetFromId(4);
    EXPECT_EQ(node4->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node4->GetLanguage(), "fr");
  }

  {
    AXNode* node5 = tree.GetFromId(5);
    EXPECT_EQ(node5->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node5->GetLanguage(), "fr");
  }
}

TEST(AXLanguageDetectionTest, LangAttrInheritanceFeatureFlagOn) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);

  // Test lang attribute inheritance in the absence of any detected language.
  //
  // Lang attribute inheritance is handled by the Label step.
  //
  // Tree:
  //        1
  //      2   3
  //    4
  //  5
  //
  //  1 - English lang attribute
  //  2 - French lang attribute
  //
  //  Expected:
  //    3 - inherit English from 1
  //    4 - inherit French from 2
  //    5 - inherit Frnech from 4/2

  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(5);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "en");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kGenericContainer;
    node2.child_ids.resize(1);
    node2.child_ids[0] = 4;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
  }

  {
    AXNodeData& node4 = initial_state.nodes[3];
    node4.id = 4;
    node4.role = ax::mojom::Role::kStaticText;
    node4.child_ids.resize(1);
    node4.child_ids[0] = 5;
  }

  {
    AXNodeData& node5 = initial_state.nodes[4];
    node5.id = 5;
    node5.role = ax::mojom::Role::kInlineTextBox;
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  {
    AXNode* node1 = tree.GetFromId(1);
    // No detection for non text nodes.
    EXPECT_EQ(node1->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node1->GetLanguage(), "en");
  }

  {
    AXNode* node2 = tree.GetFromId(2);
    EXPECT_EQ(node2->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node2->GetLanguage(), "fr");
  }

  {
    AXNode* node3 = tree.GetFromId(3);
    // Inherited languages are not stored in lang info.
    EXPECT_EQ(node3->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node3->GetLanguage(), "en");
  }

  {
    AXNode* node4 = tree.GetFromId(4);
    // Inherited languages are not stored in lang info.
    EXPECT_EQ(node4->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node4->GetLanguage(), "fr");
  }

  {
    AXNode* node5 = tree.GetFromId(5);
    // Inherited languages are not stored in lang info.
    EXPECT_EQ(node5->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node5->GetLanguage(), "fr");
  }
}

// Tests that AXNode::GetLanguage() terminates when there is no lang attribute.
TEST_F(AXLanguageDetectionTestStaticContent, GetLanguageBoringTree) {
  // This test checks the behaviour of Detect, Label, and GetLanguage on a
  // 'boring' tree.
  //
  // The tree built here contains no lang attributes, nor does it contain any
  // text to perform detection on.
  //
  // Tree:
  //      1
  //    2   3
  //  4
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(4);
  initial_state.nodes[0].id = 1;
  initial_state.nodes[0].child_ids.resize(2);
  initial_state.nodes[0].child_ids[0] = 2;
  initial_state.nodes[0].child_ids[1] = 3;
  initial_state.nodes[1].id = 2;
  initial_state.nodes[1].child_ids.resize(1);
  initial_state.nodes[1].child_ids[0] = 4;
  initial_state.nodes[2].id = 3;
  initial_state.nodes[3].id = 4;

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Check that tree parenting conforms to expected shape.
  AXNode* node1 = tree.GetFromId(1);
  EXPECT_EQ(node1->parent(), nullptr);

  AXNode* node2 = tree.GetFromId(2);
  ASSERT_EQ(node2->parent(), node1);
  EXPECT_EQ(node2->parent()->parent(), nullptr);

  AXNode* node3 = tree.GetFromId(3);
  ASSERT_EQ(node3->parent(), node1);
  EXPECT_EQ(node3->parent()->parent(), nullptr);

  AXNode* node4 = tree.GetFromId(4);
  ASSERT_EQ(node4->parent(), node2);
  ASSERT_EQ(node4->parent()->parent(), node1);
  EXPECT_EQ(node4->parent()->parent()->parent(), nullptr);

  EXPECT_EQ(node1->GetLanguage(), "");
  EXPECT_EQ(node2->GetLanguage(), "");
  EXPECT_EQ(node3->GetLanguage(), "");
  EXPECT_EQ(node4->GetLanguage(), "");
}

TEST_F(AXLanguageDetectionTestStaticContent, Basic) {
  // Tree:
  //        1
  //      2   3
  //    4
  //  5
  //
  //  1 - German lang attribute,  no text
  //  2 - French lang attribute,  no text
  //  3 - no attribute,           French text
  //  4 - no attribute,           English text
  //  5 - no attribute,           no text
  //
  //  Expected:
  //    3 - French detected
  //    4 - English detected
  //    5 - inherit English from 4
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(5);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "de");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kGenericContainer;
    node2.child_ids.resize(1);
    node2.child_ids[0] = 4;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
  }

  {
    AXNodeData& node4 = initial_state.nodes[3];
    node4.id = 4;
    node4.child_ids.resize(1);
    node4.child_ids[0] = 5;
    node4.role = ax::mojom::Role::kStaticText;
    node4.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  {
    AXNodeData& node5 = initial_state.nodes[4];
    node5.id = 5;
    node5.role = ax::mojom::Role::kInlineTextBox;
    node5.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  {
    AXNode* node1 = tree.GetFromId(1);
    // node1 is not a text node, so no lang info should be attached.
    EXPECT_EQ(node1->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node1->GetLanguage(), "de");
  }

  {
    AXNode* node2 = tree.GetFromId(2);
    // node2 is not a text node, so no lang info should be attached.
    EXPECT_EQ(node2->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node2->GetLanguage(), "fr");
  }

  {
    AXNode* node3 = tree.GetFromId(3);
    EXPECT_TRUE(node3->IsText());
    EXPECT_NE(node3->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node3->GetLanguage(), "fr");
  }

  {
    AXNode* node4 = tree.GetFromId(4);
    EXPECT_TRUE(node4->IsText());
    EXPECT_NE(node4->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node4->GetLanguage(), "en");
  }

  {
    AXNode* node5 = tree.GetFromId(5);
    EXPECT_TRUE(node5->IsText());
    // Inherited languages are not stored in lang info.
    EXPECT_EQ(node5->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node5->GetLanguage(), "en");
  }
}

TEST_F(AXLanguageDetectionTestStaticContent, MetricCollection) {
  // Tree:
  //        1
  //    2 3 4 5 6
  //
  //  1 - German lang attribute,  no text
  //  2 - no attribute,           German text
  //  3 - no attribute,           French text
  //  4 - no attribute,           English text
  //  5 - no attribute,           Spanish text
  //  6 - no attribute,           text too short to get detection results.
  //
  //  Expected:
  //    2 - German detected
  //    3 - French detected
  //    4 - English detected
  //    5 - Spanish detected
  //    6 - too short for results
  //
  //    only 3 of these languages can be labelled due to heuristics.
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(6);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(5);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.child_ids[2] = 4;
    node1.child_ids[3] = 5;
    node1.child_ids[4] = 6;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "de");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
  }

  {
    AXNodeData& node4 = initial_state.nodes[3];
    node4.id = 4;
    node4.role = ax::mojom::Role::kStaticText;
    node4.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  {
    AXNodeData& node5 = initial_state.nodes[4];
    node5.id = 5;
    node5.role = ax::mojom::Role::kStaticText;
    node5.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextSpanish);
  }

  {
    AXNodeData& node6 = initial_state.nodes[5];
    node6.id = 6;
    node6.role = ax::mojom::Role::kStaticText;
    node6.AddStringAttribute(ax::mojom::StringAttribute::kName,
                             "too short for detection.");
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Specifically disable clearing of metrics.
  disable_metric_clearing(tree);
  // Our histogram for testing.
  base::HistogramTester histograms;

  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // All 4 of our languages should have been detected for one node each, scoring
  // a maximum 3 points.
  EXPECT_EQ(3, get_score(tree, "de"));
  EXPECT_EQ(3, get_score(tree, "en"));
  EXPECT_EQ(3, get_score(tree, "fr"));
  EXPECT_EQ(3, get_score(tree, "es"));

  // 5 nodes (2, 3, 4, 5, 6) should have had detection attempted.
  EXPECT_EQ(5, count_detection_attempted(tree));
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.CountDetectionAttempted", 5, 1);

  // 4 nodes (2, 3, 4, 5) should have had detection results.
  EXPECT_EQ(4, count_detection_results(tree));
  // 5 nodes attempted, 4 got results = 4*100/5 = 80%
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageLanguageDetected", 80, 1);

  // 3 nodes (any of 2, 3, 4, 5) should have been labelled.
  EXPECT_EQ(3, count_labelled(tree));
  histograms.ExpectUniqueSample("Accessibility.LanguageDetection.CountLabelled",
                                3, 1);

  // 3 nodes (any of 2, 3, 4, 5) should have been given top label.
  EXPECT_EQ(3, count_labelled_with_top_result(tree));
  // 3 nodes labelled, all of them given top result = 100%.
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageLabelledWithTop", 100, 1);

  // 3 nodes (3, 4, 5) should have been labelled to disagree with node1 author
  // provided language.
  EXPECT_EQ(3, count_overridden(tree));
  // 3 nodes labelled, all 3 disagree with node1 = 100%.
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageOverridden", 100, 1);

  // There should be 4 unique languages (de, en, fr, es).
  {
    const auto& top_lang = unique_top_lang_detected(tree);
    const absl::flat_hash_set<std::string> expected_top_lang = {"de", "en",
                                                                "es", "fr"};
    EXPECT_EQ(top_lang, expected_top_lang);
  }
  histograms.ExpectUniqueSample("Accessibility.LanguageDetection.LangsPerPage",
                                4, 1);
}

TEST_F(AXLanguageDetectionTestStaticContent, DetectOnly) {
  // This tests a Detect step without any matching Label step.
  //
  // Tree:
  //        1
  //      2   3
  //    4
  //  5
  //
  //  1 - German lang attribute, no text
  //  2 - French lang attribute,  no text
  //  3 - no attribute,           French text
  //  4 - no attribute,           English text
  //  5 - no attribute,           no text
  //
  //  Expected:
  //    3 - French detected, never labelled, so still inherits German from 1
  //    4 - English detected, never labelled, so still inherits French from 2
  //    5 - English inherited from 4, still inherits French from 4
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(5);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "de");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kGenericContainer;
    node2.child_ids.resize(1);
    node2.child_ids[0] = 4;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
  }

  {
    AXNodeData& node4 = initial_state.nodes[3];
    node4.id = 4;
    node4.child_ids.resize(1);
    node4.child_ids[0] = 5;
    node4.role = ax::mojom::Role::kStaticText;
    node4.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  {
    AXNodeData& node5 = initial_state.nodes[4];
    node5.id = 5;
    node5.role = ax::mojom::Role::kInlineTextBox;
    node5.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  // Purposefully not calling Label so we can test Detect in isolation.

  {
    AXNode* node1 = tree.GetFromId(1);
    // node1 is not a text node, so no lang info should be attached.
    EXPECT_EQ(node1->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node1->GetLanguage(), "de");
  }

  {
    AXNode* node2 = tree.GetFromId(2);
    // node2 is not a text node, so no lang info should be attached.
    EXPECT_EQ(node2->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node2->GetLanguage(), "fr");
  }

  {
    AXNode* node3 = tree.GetFromId(3);
    EXPECT_TRUE(node3->IsText());
    ASSERT_NE(node3->GetLanguageInfo(), nullptr);
    ASSERT_GT(node3->GetLanguageInfo()->detected_languages.size(), (unsigned)0);
    ASSERT_EQ(node3->GetLanguageInfo()->detected_languages[0], "fr");
    EXPECT_TRUE(node3->GetLanguageInfo()->language.empty());
    EXPECT_EQ(node3->GetLanguage(), "de");
  }

  {
    AXNode* node4 = tree.GetFromId(4);
    EXPECT_TRUE(node4->IsText());
    ASSERT_NE(node4->GetLanguageInfo(), nullptr);
    ASSERT_GT(node4->GetLanguageInfo()->detected_languages.size(), (unsigned)0);
    ASSERT_EQ(node4->GetLanguageInfo()->detected_languages[0], "en");
    EXPECT_TRUE(node4->GetLanguageInfo()->language.empty());
    EXPECT_EQ(node4->GetLanguage(), "fr");
  }

  {
    AXNode* node5 = tree.GetFromId(5);
    EXPECT_TRUE(node5->IsText());
    // Inherited languages are not stored in lang info.
    ASSERT_EQ(node5->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node5->GetLanguage(), "fr");
  }
}

TEST_F(AXLanguageDetectionTestStaticContent, kLanguageUntouched) {
  // This test is to ensure that the kLanguage string attribute is not updated
  // during language detection and labelling, even when it disagrees with the
  // detected language.

  // Built tree:
  //        1
  //      2   3
  //
  //  1 - German lang attribute,  no text
  //  2 - English lang attribute, French text
  //  3 - French lang attribute,  English text
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(3);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "de");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "en");
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  {
    AXNode* node1 = tree.GetFromId(1);
    ASSERT_EQ(node1->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node1->GetLanguage(), "de");
  }

  {
    // French should be detected, original English attr should be untouched.
    AXNode* node2 = tree.GetFromId(2);
    ASSERT_NE(node2->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node2->GetLanguageInfo()->language, "fr");
    EXPECT_EQ(node2->GetStringAttribute(ax::mojom::StringAttribute::kLanguage),
              "en");
    EXPECT_EQ(node2->GetLanguage(), "fr");
  }

  {
    // English should be detected, original French attr should be untouched.
    AXNode* node3 = tree.GetFromId(3);
    ASSERT_NE(node3->GetLanguageInfo(), nullptr);
    EXPECT_EQ(node3->GetLanguageInfo()->language, "en");
    EXPECT_EQ(node3->GetStringAttribute(ax::mojom::StringAttribute::kLanguage),
              "fr");
    EXPECT_EQ(node3->GetLanguage(), "en");
  }
}

// Test RegisterLanguageDetectionObserver correctly respects the command line
// flags.
TEST_F(AXLanguageDetectionTestFixture, ObserverRegistrationObeysFlag) {
  // Enable only the flag controlling static language detection.
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);

  // Construct empty tree and check initialisation.
  AXTree tree;
  ASSERT_NE(tree.language_detection_manager, nullptr);
  ASSERT_EQ(getObserver(tree), nullptr);

  // Try registration without enabling Dynamic feature flag, should be a no-op.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();

  ASSERT_EQ(getObserver(tree), nullptr);

  // Now enable the dynamic feature flag.
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetectionDynamic);

  // Try registration again, this should construct and register observer as flag
  // is now enabled.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();

  // Check our observer was constructed.
  ASSERT_NE(getObserver(tree), nullptr);

  // Check our observer was registered in our tree.
  ASSERT_TRUE(tree.HasObserver(getObserver(tree)));
}

// Test RegisterLanguageDetectionObserver correctly respects the feature flag.
TEST_F(AXLanguageDetectionTestFixture, ObserverRegistrationObeysFeatureFlag) {
  // Construct empty tree and check initialisation.
  AXTree tree;
  ASSERT_NE(tree.language_detection_manager, nullptr);
  ASSERT_EQ(getObserver(tree), nullptr);

  // Try registration without enabling Dynamic feature flag, should be a no-op.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();

  ASSERT_EQ(getObserver(tree), nullptr);

  // Enable general feature flag which gates both Static and Dynamic features.
  base::test::ScopedFeatureList scoped_feature_list;
  scoped_feature_list.InitWithFeatures(
      {features::kEnableAccessibilityLanguageDetection}, {});

  // Try registration again, this should now construct and register an observer.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();

  // Check our observer was constructed.
  ASSERT_NE(getObserver(tree), nullptr);

  // Check our observer was registered in our tree.
  ASSERT_TRUE(tree.HasObserver(getObserver(tree)));
}

TEST_F(AXLanguageDetectionTestDynamicContent, Basic) {
  // Tree:
  //   1
  //   2
  //
  // 1 - kStaticText - English text.
  // 2 - kInlineTextBox - English text.
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(2);

  // TODO(chrishall): Create more realistic kStaticText with multiple
  // kInlineTextBox(es) children. Look at the real-world behaviour of
  // kStaticText, kInlineText and kLineBreak around empty divs and empty lines
  // within paragraphs of text.

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kStaticText;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
    node1.child_ids.resize(1);
    node1.child_ids[0] = 2;
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kInlineTextBox;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Manually run initial language detection and labelling.
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Quickly verify "before" state
  {
    AXNode* node1 = tree.GetFromId(1);
    ASSERT_NE(node1, nullptr);
    ASSERT_NE(node1->GetLanguageInfo(), nullptr);
    ASSERT_EQ(node1->GetLanguage(), "en");

    AXNode* node2 = tree.GetFromId(2);
    ASSERT_NE(node2, nullptr);
    // Inherited language not stored in lang info.
    ASSERT_EQ(node2->GetLanguageInfo(), nullptr);
    // Should still inherit language from parent.
    ASSERT_EQ(node2->GetLanguage(), "en");
  }

  // Manually register observer.
  AXLanguageDetectionObserver observer(&tree);

  // Observer constructor is responsible for attaching itself to tree.
  ASSERT_TRUE(tree.HasObserver(&observer));

  // Dynamic update
  //
  // New tree:
  //     1
  //     2
  //
  // 1 - Text changed to German.
  // 2 - Text changed to German.
  AXTreeUpdate update_state;
  update_state.root_id = 1;
  update_state.nodes.resize(2);

  // Change text to German.
  {
    AXNodeData& node1 = update_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kStaticText;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
    node1.child_ids.resize(1);
    node1.child_ids[0] = 2;
  }

  {
    AXNodeData& node2 = update_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kInlineTextBox;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
  }

  // Perform update.
  ASSERT_TRUE(tree.Unserialize(update_state));

  // Check language detection was re-run on new content.
  {
    AXNode* node1 = tree.GetFromId(1);
    ASSERT_NE(node1, nullptr);
    ASSERT_NE(node1->GetLanguageInfo(), nullptr);
    ASSERT_EQ(node1->GetLanguage(), "de");
  }

  {
    AXNode* node2 = tree.GetFromId(2);
    ASSERT_NE(node2, nullptr);
    // Inherited language not stored in lang info.
    ASSERT_EQ(node2->GetLanguageInfo(), nullptr);
    // Should inherit new language from parent.
    ASSERT_EQ(node2->GetLanguage(), "de");
  }
}

TEST_F(AXLanguageDetectionTestDynamicContent, MetricCollection) {
  // Tree:
  //   1
  //  2 3
  //
  // 1 - kGenericContainer, French lang attribute.
  // 2 - kStaticText - English text.
  // 3 - kSTaticText - German text.
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(3);

  // TODO(chrishall): Create more realistic kStaticText with multiple
  // kInlineTextBox(es) children. Look at the real-world behaviour of
  // kStaticText, kInlineText and kLineBreak around empty divs and empty lines
  // within paragraphs of text.

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(2);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  {
    AXNodeData& node3 = initial_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Manually run initial language detection and labelling.
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Quickly verify "before" metrics were cleared.
  EXPECT_EQ(0, count_detection_attempted(tree));

  // Specifically disable clearing of metrics for dynamic only.
  disable_metric_clearing(tree);
  // Our histogram for testing.
  base::HistogramTester histograms;

  // Manually register observer.
  AXLanguageDetectionObserver observer(&tree);

  // Observer constructor is responsible for attaching itself to tree.
  ASSERT_TRUE(tree.HasObserver(&observer));

  // Dynamic update
  //
  // New tree:
  //     1
  //   2 3 4
  //
  // 1 - no change.
  // 2 - Text changed to French.
  // 3 - no change.
  // 4 - new kStaticText node, Spanish text.
  AXTreeUpdate update_state;
  update_state.root_id = 1;
  update_state.nodes.resize(3);

  // Change text to German.
  {
    AXNodeData& node1 = update_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(3);
    node1.child_ids[0] = 2;
    node1.child_ids[1] = 3;
    node1.child_ids[2] = 4;
    node1.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr");
  }

  {
    AXNodeData& node2 = update_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
  }

  {
    AXNodeData& node4 = update_state.nodes[2];
    node4.id = 4;
    node4.role = ax::mojom::Role::kStaticText;
    node4.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextSpanish);
  }

  // Perform update.
  ASSERT_TRUE(tree.Unserialize(update_state));

  // Check "after" metrics.
  // note that the metrics were cleared after static work had finished, so these
  // metrics only reflect the dynamic work.

  // All 4 of our languages should have been detected for one node each, scoring
  // a maximum 3 points.
  EXPECT_EQ(3, get_score(tree, "de"));
  EXPECT_EQ(3, get_score(tree, "en"));
  EXPECT_EQ(3, get_score(tree, "fr"));
  EXPECT_EQ(3, get_score(tree, "es"));

  // 2 nodes (2, 4) should have had detection attempted.
  EXPECT_EQ(2, count_detection_attempted(tree));
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.CountDetectionAttempted", 2, 1);

  // 2 nodes (2, 4) should have had detection results
  EXPECT_EQ(2, count_detection_results(tree));
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageLanguageDetected", 100, 1);

  // 2 nodes (2, 4) should have been labelled
  EXPECT_EQ(2, count_labelled(tree));
  histograms.ExpectUniqueSample("Accessibility.LanguageDetection.CountLabelled",
                                2, 1);

  // 2 nodes (2, 4) should have been given top label
  EXPECT_EQ(2, count_labelled_with_top_result(tree));
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageLabelledWithTop", 100, 1);

  // 1 nodes (4) should have been labelled to disagree with node1 author
  // provided language.
  EXPECT_EQ(1, count_overridden(tree));
  // 2 nodes were labelled, 1 disagreed with node1 = 50%.
  histograms.ExpectUniqueSample(
      "Accessibility.LanguageDetection.PercentageOverridden", 50, 1);

  // There should be 2 unique languages (fr, es).
  {
    auto top_lang = unique_top_lang_detected(tree);
    const absl::flat_hash_set<std::string> expected_top_lang = {"es", "fr"};
    EXPECT_EQ(top_lang, expected_top_lang);
  }
  // There should be a single (unique, 1) value for '2' unique languages.
  histograms.ExpectUniqueSample("Accessibility.LanguageDetection.LangsPerPage",
                                2, 1);
}

TEST_F(AXLanguageDetectionTestDynamicContent, MultipleUpdates) {
  // This test runs language detection a total of 3 times, once for the initial
  // 'static' content, and then twice for 'dynamic' updates.

  // Tree:
  //        1
  //        2
  //
  //  1 - GenericContainer
  //  2 - English text
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(2);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(1);
    node1.child_ids[0] = 2;
  }

  {
    AXNodeData& node2 = initial_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextEnglish);
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Run initial language detection and labelling.
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Quickly verify "before" state
  {
    AXNode* node1 = tree.GetFromId(1);
    ASSERT_NE(node1, nullptr);
    ASSERT_EQ(node1->GetLanguage(), "");

    AXNode* node2 = tree.GetFromId(2);
    ASSERT_NE(node2, nullptr);
    ASSERT_EQ(node2->GetLanguage(), "en");
  }

  // Register dynamic content observer.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();
  ASSERT_NE(getObserver(tree), nullptr);
  ASSERT_TRUE(tree.HasObserver(getObserver(tree)));

  // First update
  {
    // Dynamic update
    //
    // New tree layout will be:
    //        1
    //      2   3
    //
    //  1 - GenericContainer, unchanged
    //  2 - changed to German text
    //  3 - new child, French text
    AXTreeUpdate update_state;
    update_state.root_id = 1;
    update_state.nodes.resize(3);

    // Update node1 to include new child node3.
    {
      AXNodeData& node1 = update_state.nodes[0];
      node1.id = 1;
      node1.role = ax::mojom::Role::kGenericContainer;
      node1.child_ids.resize(2);
      node1.child_ids[0] = 2;
      node1.child_ids[1] = 3;
    }

    // Change node2 text to German
    {
      AXNodeData& node2 = update_state.nodes[1];
      node2.id = 2;
      node2.role = ax::mojom::Role::kStaticText;
      node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
    }

    // Add new node3 with French text.
    {
      AXNodeData& node3 = update_state.nodes[2];
      node3.id = 3;
      node3.role = ax::mojom::Role::kStaticText;
      node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
    }

    // Perform update.
    ASSERT_TRUE(tree.Unserialize(update_state));

    {
      AXNode* node1 = tree.GetFromId(1);
      ASSERT_NE(node1, nullptr);
      ASSERT_EQ(node1->GetLanguage(), "");
    }

    {
      // Detection should have been re-run on node2, detecting German.
      AXNode* node2 = tree.GetFromId(2);
      ASSERT_NE(node2, nullptr);
      ASSERT_EQ(node2->GetLanguage(), "de");
    }

    {
      // New node3 should have detected French.
      AXNode* node3 = tree.GetFromId(3);
      ASSERT_NE(node3, nullptr);
      ASSERT_EQ(node3->GetLanguage(), "fr");
    }
  }

  // Second update
  {
    // Dynamic update
    //
    // New tree layout will be:
    //        1
    //      2   x
    //
    //  1 - GenericContainer, unchanged
    //  2 - changed to French text
    //  3 - deleted
    AXTreeUpdate update_state;
    update_state.root_id = 1;
    update_state.nodes.resize(2);

    // Update node1 to delete child node3.
    {
      AXNodeData& node1 = update_state.nodes[0];
      node1.id = 1;
      node1.role = ax::mojom::Role::kGenericContainer;
      node1.child_ids.resize(1);
      node1.child_ids[0] = 2;
    }

    // Change node2 text to French
    {
      AXNodeData& node2 = update_state.nodes[1];
      node2.id = 2;
      node2.role = ax::mojom::Role::kStaticText;
      node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextFrench);
    }

    // Perform update.
    ASSERT_TRUE(tree.Unserialize(update_state));

    {
      AXNode* node1 = tree.GetFromId(1);
      ASSERT_NE(node1, nullptr);
      ASSERT_EQ(node1->GetLanguage(), "");
    }

    {
      // Detection should have been re-run on node2, detecting French.
      AXNode* node2 = tree.GetFromId(2);
      ASSERT_NE(node2, nullptr);
      ASSERT_EQ(node2->GetLanguage(), "fr");
    }

    {
      // Node3 should be no more.
      AXNode* node3 = tree.GetFromId(3);
      ASSERT_EQ(node3, nullptr);
    }
  }

  // Third update.
  {
    // Dynamic update
    //
    // New tree layout will be:
    //        1
    //      2   3
    //
    //  1 - GenericContainer, unchanged
    //  2 - French text, unchanged
    //  3 - new node, German text
    AXTreeUpdate update_state;
    update_state.root_id = 1;
    update_state.nodes.resize(2);

    // Update node1 to include new child node3.
    {
      AXNodeData& node1 = update_state.nodes[0];
      node1.id = 1;
      node1.role = ax::mojom::Role::kGenericContainer;
      node1.child_ids.resize(2);
      node1.child_ids[0] = 2;
      node1.child_ids[1] = 3;
    }

    // Add new node3 with German text.
    {
      AXNodeData& node3 = update_state.nodes[1];
      node3.id = 3;
      node3.role = ax::mojom::Role::kStaticText;
      node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
    }

    // Perform update.
    ASSERT_TRUE(tree.Unserialize(update_state));

    {
      AXNode* node1 = tree.GetFromId(1);
      ASSERT_NE(node1, nullptr);
      ASSERT_EQ(node1->GetLanguage(), "");
    }

    {
      AXNode* node2 = tree.GetFromId(2);
      ASSERT_NE(node2, nullptr);
      ASSERT_EQ(node2->GetLanguage(), "fr");
    }

    {
      AXNode* node3 = tree.GetFromId(3);
      ASSERT_NE(node3, nullptr);
      ASSERT_EQ(node3->GetLanguage(), "de");
    }
  }
}

TEST_F(AXLanguageDetectionTestDynamicContent, NewRoot) {
  // Artificial test change which changes the root node.

  // Tree:
  //        1
  //
  //  1 - GenericContainer
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(1);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Run initial language detection and labelling.
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Register dynamic content observer.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();
  ASSERT_NE(getObserver(tree), nullptr);
  ASSERT_TRUE(tree.HasObserver(getObserver(tree)));

  // New Tree:
  //       2
  // 2 - new root, German text

  AXTreeUpdate update_state;
  update_state.root_id = 2;
  update_state.nodes.resize(1);

  {
    AXNodeData& node2 = update_state.nodes[0];
    node2.id = 2;
    node2.role = ax::mojom::Role::kStaticText;
    node2.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
  }

  // Perform update.
  ASSERT_TRUE(tree.Unserialize(update_state));

  {
    AXNode* node2 = tree.GetFromId(2);
    ASSERT_NE(node2, nullptr);
    ASSERT_EQ(node2->GetLanguage(), "de");
  }
}

TEST_F(AXLanguageDetectionTestDynamicContent, ChainOfNewNodes) {
  // Artificial test which adds two new nodes in a 'chain', simultaneously
  // adding a child of the root and a grandchild of the root.

  // Tree:
  //        1
  //
  //  1 - GenericContainer
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(1);

  {
    AXNodeData& node1 = initial_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
  }

  AXTree tree(initial_state);
  ASSERT_NE(tree.language_detection_manager, nullptr);

  // Run initial language detection and labelling.
  tree.language_detection_manager->DetectLanguages();
  tree.language_detection_manager->LabelLanguages();

  // Register dynamic content observer.
  tree.language_detection_manager->RegisterLanguageDetectionObserver();
  ASSERT_NE(getObserver(tree), nullptr);
  ASSERT_TRUE(tree.HasObserver(getObserver(tree)));

  // New Tree:
  //       1
  //       2
  //       3
  // 1 - generic container
  // 2 - generic container
  // 3 - German text

  AXTreeUpdate update_state;
  update_state.root_id = 1;
  update_state.nodes.resize(3);

  {
    AXNodeData& node1 = update_state.nodes[0];
    node1.id = 1;
    node1.role = ax::mojom::Role::kGenericContainer;
    node1.child_ids.resize(1);
    node1.child_ids[0] = 2;
  }

  {
    AXNodeData& node2 = update_state.nodes[1];
    node2.id = 2;
    node2.role = ax::mojom::Role::kGenericContainer;
    node2.child_ids.resize(1);
    node2.child_ids[0] = 3;
  }

  {
    AXNodeData& node3 = update_state.nodes[2];
    node3.id = 3;
    node3.role = ax::mojom::Role::kStaticText;
    node3.AddStringAttribute(ax::mojom::StringAttribute::kName, kTextGerman);
  }

  // Perform update.
  ASSERT_TRUE(tree.Unserialize(update_state));

  {
    AXNode* node3 = tree.GetFromId(3);
    ASSERT_NE(node3, nullptr);
    ASSERT_EQ(node3->GetLanguage(), "de");
  }
}

TEST(AXLanguageDetectionTest, AXLanguageInfoStatsBasic) {
  AXLanguageInfoStats stats;

  {
    std::vector<std::string> detected_languages;
    detected_languages.push_back("en");
    detected_languages.push_back("fr");
    detected_languages.push_back("ja");
    stats.Add(detected_languages);
  }

  ASSERT_EQ(stats.GetScore("en"), 3);
  ASSERT_EQ(stats.GetScore("fr"), 2);
  ASSERT_EQ(stats.GetScore("ja"), 1);

  EXPECT_TRUE(stats.CheckLanguageWithinTop("en"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("fr"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("ja"));

  {
    std::vector<std::string> detected_languages;
    detected_languages.push_back("en");
    detected_languages.push_back("de");
    detected_languages.push_back("fr");
    stats.Add(detected_languages);
  }

  ASSERT_EQ(stats.GetScore("en"), 6);
  ASSERT_EQ(stats.GetScore("fr"), 3);
  ASSERT_EQ(stats.GetScore("de"), 2);
  ASSERT_EQ(stats.GetScore("ja"), 1);

  EXPECT_TRUE(stats.CheckLanguageWithinTop("en"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("fr"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("de"));

  EXPECT_FALSE(stats.CheckLanguageWithinTop("ja"));

  {
    std::vector<std::string> detected_languages;
    detected_languages.push_back("fr");
    stats.Add(detected_languages);
  }

  ASSERT_EQ(stats.GetScore("en"), 6);
  ASSERT_EQ(stats.GetScore("fr"), 6);
  ASSERT_EQ(stats.GetScore("de"), 2);
  ASSERT_EQ(stats.GetScore("ja"), 1);

  EXPECT_TRUE(stats.CheckLanguageWithinTop("en"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("fr"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("de"));

  EXPECT_FALSE(stats.CheckLanguageWithinTop("ja"));

  {
    std::vector<std::string> detected_languages;
    detected_languages.push_back("ja");
    detected_languages.push_back("qq");
    detected_languages.push_back("zz");
    stats.Add(detected_languages);
  }

  ASSERT_EQ(stats.GetScore("en"), 6);
  ASSERT_EQ(stats.GetScore("fr"), 6);
  ASSERT_EQ(stats.GetScore("ja"), 4);
  ASSERT_EQ(stats.GetScore("de"), 2);
  ASSERT_EQ(stats.GetScore("qq"), 2);
  ASSERT_EQ(stats.GetScore("zz"), 1);

  EXPECT_TRUE(stats.CheckLanguageWithinTop("en"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("fr"));
  EXPECT_TRUE(stats.CheckLanguageWithinTop("ja"));

  EXPECT_FALSE(stats.CheckLanguageWithinTop("de"));
  EXPECT_FALSE(stats.CheckLanguageWithinTop("qq"));
  EXPECT_FALSE(stats.CheckLanguageWithinTop("zz"));
}

TEST(AXLanguageDetectionTest, ShortLanguageDetectorLabeledTest) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(2);
  initial_state.nodes[0].id = 1;
  initial_state.nodes[0].child_ids = {2};
  initial_state.nodes[1].id = 2;
  initial_state.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kName,
                                            "Hello");
  initial_state.nodes[1].AddStringAttribute(
      ax::mojom::StringAttribute::kLanguage, "en");
  AXTree tree(initial_state);

  AXNode* item = tree.GetFromId(2);
  std::vector<AXLanguageSpan> annotation;
  ASSERT_NE(tree.language_detection_manager, nullptr);
  // Empty output.
  annotation =
      tree.language_detection_manager->GetLanguageAnnotationForStringAttribute(
          *item, ax::mojom::StringAttribute::kMathContent);
  ASSERT_EQ(0, (int)annotation.size());
  // Returns single AXLanguageSpan.
  annotation =
      tree.language_detection_manager->GetLanguageAnnotationForStringAttribute(
          *item, ax::mojom::StringAttribute::kName);
  ASSERT_EQ(1, (int)annotation.size());
  AXLanguageSpan* lang_span = &annotation[0];
  ASSERT_EQ("en", lang_span->language);
  std::string name =
      item->GetStringAttribute(ax::mojom::StringAttribute::kName);
  ASSERT_EQ("Hello",
            name.substr(lang_span->start_index,
                        lang_span->end_index - lang_span->start_index));
}

TEST(AXLanguageDetectionTest, ShortLanguageDetectorCharacterTest) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(2);
  initial_state.nodes[0].id = 1;
  initial_state.nodes[0].child_ids = {2};
  initial_state.nodes[1].id = 2;
  initial_state.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kName,
                                            "δ");
  AXTree tree(initial_state);

  AXNode* item = tree.GetFromId(2);
  std::vector<AXLanguageSpan> annotation;
  ASSERT_NE(tree.language_detection_manager, nullptr);
  // Returns single LanguageSpan.
  annotation =
      tree.language_detection_manager->GetLanguageAnnotationForStringAttribute(
          *item, ax::mojom::StringAttribute::kName);
  ASSERT_EQ(1, (int)annotation.size());
  AXLanguageSpan* lang_span = &annotation[0];
  ASSERT_EQ("el", lang_span->language);
  std::string name =
      item->GetStringAttribute(ax::mojom::StringAttribute::kName);
  ASSERT_EQ("δ", name.substr(lang_span->start_index,
                             lang_span->end_index - lang_span->start_index));
}

TEST(AXLanguageDetectionTest, ShortLanguageDetectorMultipleLanguagesTest) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(2);
  initial_state.nodes[0].id = 1;
  initial_state.nodes[0].child_ids = {2};
  initial_state.nodes[1].id = 2;
  initial_state.nodes[1].AddStringAttribute(
      ax::mojom::StringAttribute::kName,
      "This text should be read in English. 차에 한하여 중임할 수. Followed "
      "by English.");
  AXTree tree(initial_state);

  AXNode* item = tree.GetFromId(2);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  std::vector<AXLanguageSpan> annotation =
      tree.language_detection_manager->GetLanguageAnnotationForStringAttribute(
          *item, ax::mojom::StringAttribute::kName);
  ASSERT_EQ(3, (int)annotation.size());
  std::string name =
      item->GetStringAttribute(ax::mojom::StringAttribute::kName);
  AXLanguageSpan* lang_span = &annotation[0];
  ASSERT_EQ("This text should be read in English. ",
            name.substr(lang_span->start_index,
                        lang_span->end_index - lang_span->start_index));
  lang_span = &annotation[1];
  ASSERT_EQ("차에 한하여 중임할 수. ",
            name.substr(lang_span->start_index,
                        lang_span->end_index - lang_span->start_index));
  lang_span = &annotation[2];
  ASSERT_EQ("Followed by English.",
            name.substr(lang_span->start_index,
                        lang_span->end_index - lang_span->start_index));
}

// Assert that GetLanguageAnnotationForStringAttribute works for attributes
// other than kName.
TEST(AXLanguageDetectionTest, DetectLanguagesForRoleTest) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      ::switches::kEnableExperimentalAccessibilityLanguageDetection);
  AXTreeUpdate initial_state;
  initial_state.root_id = 1;
  initial_state.nodes.resize(1);
  initial_state.nodes[0].id = 1;
  initial_state.nodes[0].AddStringAttribute(ax::mojom::StringAttribute::kValue,
                                            "どうぞよろしくお願いします.");
  AXTree tree(initial_state);

  AXNode* item = tree.GetFromId(1);
  ASSERT_NE(tree.language_detection_manager, nullptr);
  std::vector<AXLanguageSpan> annotation =
      tree.language_detection_manager->GetLanguageAnnotationForStringAttribute(
          *item, ax::mojom::StringAttribute::kValue);
  ASSERT_EQ(1, (int)annotation.size());
  std::string value =
      item->GetStringAttribute(ax::mojom::StringAttribute::kValue);
  AXLanguageSpan* lang_span = &annotation[0];
  ASSERT_EQ("どうぞよろしくお願いします.",
            value.substr(lang_span->start_index,
                         lang_span->end_index - lang_span->start_index));
}

}  // namespace ui
