no_state_prefetch_processor_impl_unittest.cc 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. // Copyright 2020 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "components/no_state_prefetch/browser/no_state_prefetch_processor_impl.h"
  5. #include "base/memory/raw_ptr.h"
  6. #include "base/run_loop.h"
  7. #include "base/test/bind.h"
  8. #include "components/no_state_prefetch/browser/no_state_prefetch_link_manager.h"
  9. #include "components/no_state_prefetch/browser/no_state_prefetch_processor_impl_delegate.h"
  10. #include "content/public/test/test_browser_context.h"
  11. #include "content/public/test/test_renderer_host.h"
  12. #include "mojo/public/cpp/system/functions.h"
  13. #include "third_party/blink/public/common/features.h"
  14. namespace prerender {
  15. class MockNoStatePrefetchLinkManager final : public NoStatePrefetchLinkManager {
  16. public:
  17. MockNoStatePrefetchLinkManager()
  18. : NoStatePrefetchLinkManager(/*manager=*/nullptr) {}
  19. absl::optional<int> OnStartLinkTrigger(
  20. int launcher_render_process_id,
  21. int launcher_render_view_id,
  22. blink::mojom::PrerenderAttributesPtr attributes,
  23. const url::Origin& initiator_origin) override {
  24. DCHECK(!is_start_called_);
  25. is_start_called_ = true;
  26. return link_trigger_id_;
  27. }
  28. void OnCancelLinkTrigger(int link_trigger_id) override {
  29. DCHECK_EQ(link_trigger_id_, link_trigger_id);
  30. DCHECK(!is_cancel_called_);
  31. is_cancel_called_ = true;
  32. }
  33. void OnAbandonLinkTrigger(int link_trigger_id) override {
  34. DCHECK_EQ(link_trigger_id_, link_trigger_id);
  35. DCHECK(!is_abandon_called_);
  36. is_abandon_called_ = true;
  37. }
  38. bool is_start_called() const { return is_start_called_; }
  39. bool is_cancel_called() const { return is_cancel_called_; }
  40. bool is_abandon_called() const { return is_abandon_called_; }
  41. private:
  42. const int link_trigger_id_ = 100;
  43. bool is_start_called_ = false;
  44. bool is_cancel_called_ = false;
  45. bool is_abandon_called_ = false;
  46. };
  47. class MockNoStatePrefetchProcessorImplDelegate final
  48. : public NoStatePrefetchProcessorImplDelegate {
  49. public:
  50. explicit MockNoStatePrefetchProcessorImplDelegate(
  51. MockNoStatePrefetchLinkManager* link_manager)
  52. : link_manager_(link_manager) {}
  53. NoStatePrefetchLinkManager* GetNoStatePrefetchLinkManager(
  54. content::BrowserContext* browser_context) override {
  55. return link_manager_;
  56. }
  57. private:
  58. raw_ptr<MockNoStatePrefetchLinkManager> link_manager_;
  59. };
  60. class NoStatePrefetchProcessorImplTest
  61. : public content::RenderViewHostTestHarness {};
  62. TEST_F(NoStatePrefetchProcessorImplTest, StartCancelAbandon) {
  63. auto link_manager = std::make_unique<MockNoStatePrefetchLinkManager>();
  64. mojo::Remote<blink::mojom::NoStatePrefetchProcessor> remote;
  65. NoStatePrefetchProcessorImpl::Create(
  66. main_rfh(), remote.BindNewPipeAndPassReceiver(),
  67. std::make_unique<MockNoStatePrefetchProcessorImplDelegate>(
  68. link_manager.get()));
  69. auto attributes = blink::mojom::PrerenderAttributes::New();
  70. attributes->url = GURL("https://example.com/prefetch");
  71. attributes->referrer = blink::mojom::Referrer::New();
  72. // Start() call should be propagated to the link manager.
  73. EXPECT_FALSE(link_manager->is_start_called());
  74. remote->Start(std::move(attributes));
  75. remote.FlushForTesting();
  76. EXPECT_TRUE(link_manager->is_start_called());
  77. // Cancel() call should be propagated to the link manager.
  78. EXPECT_FALSE(link_manager->is_cancel_called());
  79. remote->Cancel();
  80. remote.FlushForTesting();
  81. EXPECT_TRUE(link_manager->is_cancel_called());
  82. // Connection lost should abandon the link manager.
  83. EXPECT_FALSE(link_manager->is_abandon_called());
  84. remote.reset();
  85. // FlushForTesting() is no longer available. Instead, use base::RunLoop.
  86. base::RunLoop().RunUntilIdle();
  87. EXPECT_TRUE(link_manager->is_abandon_called());
  88. }
  89. TEST_F(NoStatePrefetchProcessorImplTest, StartAbandon) {
  90. auto link_manager = std::make_unique<MockNoStatePrefetchLinkManager>();
  91. mojo::Remote<blink::mojom::NoStatePrefetchProcessor> remote;
  92. NoStatePrefetchProcessorImpl::Create(
  93. main_rfh(), remote.BindNewPipeAndPassReceiver(),
  94. std::make_unique<MockNoStatePrefetchProcessorImplDelegate>(
  95. link_manager.get()));
  96. auto attributes = blink::mojom::PrerenderAttributes::New();
  97. attributes->url = GURL("https://example.com/prefetch");
  98. attributes->referrer = blink::mojom::Referrer::New();
  99. // Start() call should be propagated to the link manager.
  100. EXPECT_FALSE(link_manager->is_start_called());
  101. remote->Start(std::move(attributes));
  102. remote.FlushForTesting();
  103. EXPECT_TRUE(link_manager->is_start_called());
  104. // Connection lost should abandon the link manager.
  105. EXPECT_FALSE(link_manager->is_abandon_called());
  106. remote.reset();
  107. // FlushForTesting() is no longer available. Instead, use base::RunLoop.
  108. base::RunLoop().RunUntilIdle();
  109. EXPECT_TRUE(link_manager->is_abandon_called());
  110. }
  111. TEST_F(NoStatePrefetchProcessorImplTest, StartTwice) {
  112. auto link_manager = std::make_unique<MockNoStatePrefetchLinkManager>();
  113. mojo::Remote<blink::mojom::NoStatePrefetchProcessor> remote;
  114. NoStatePrefetchProcessorImpl::Create(
  115. main_rfh(), remote.BindNewPipeAndPassReceiver(),
  116. std::make_unique<MockNoStatePrefetchProcessorImplDelegate>(
  117. link_manager.get()));
  118. // Set up the error handler for bad mojo messages.
  119. std::string bad_message_error;
  120. mojo::SetDefaultProcessErrorHandler(
  121. base::BindLambdaForTesting([&](const std::string& error) {
  122. EXPECT_TRUE(bad_message_error.empty());
  123. bad_message_error = error;
  124. }));
  125. auto attributes1 = blink::mojom::PrerenderAttributes::New();
  126. attributes1->url = GURL("https://example.com/prefetch");
  127. attributes1->referrer = blink::mojom::Referrer::New();
  128. // Start() call should be propagated to the link manager.
  129. EXPECT_FALSE(link_manager->is_start_called());
  130. remote->Start(std::move(attributes1));
  131. remote.FlushForTesting();
  132. EXPECT_TRUE(link_manager->is_start_called());
  133. auto attributes2 = blink::mojom::PrerenderAttributes::New();
  134. attributes2->url = GURL("https://example.com/prefetch");
  135. attributes2->referrer = blink::mojom::Referrer::New();
  136. // Call Start() again. This should be reported as a bad mojo message.
  137. ASSERT_TRUE(bad_message_error.empty());
  138. remote->Start(std::move(attributes2));
  139. remote.FlushForTesting();
  140. EXPECT_EQ(bad_message_error, "NSPPI_START_TWICE");
  141. }
  142. TEST_F(NoStatePrefetchProcessorImplTest, Cancel) {
  143. auto link_manager = std::make_unique<MockNoStatePrefetchLinkManager>();
  144. mojo::Remote<blink::mojom::NoStatePrefetchProcessor> remote;
  145. NoStatePrefetchProcessorImpl::Create(
  146. main_rfh(), remote.BindNewPipeAndPassReceiver(),
  147. std::make_unique<MockNoStatePrefetchProcessorImplDelegate>(
  148. link_manager.get()));
  149. // Call Cancel() before Start().
  150. EXPECT_FALSE(link_manager->is_cancel_called());
  151. remote->Cancel();
  152. remote.FlushForTesting();
  153. // The cancellation should not be propagated to the link manager.
  154. EXPECT_FALSE(link_manager->is_cancel_called());
  155. }
  156. TEST_F(NoStatePrefetchProcessorImplTest, Abandon) {
  157. auto link_manager = std::make_unique<MockNoStatePrefetchLinkManager>();
  158. mojo::Remote<blink::mojom::NoStatePrefetchProcessor> remote;
  159. NoStatePrefetchProcessorImpl::Create(
  160. main_rfh(), remote.BindNewPipeAndPassReceiver(),
  161. std::make_unique<MockNoStatePrefetchProcessorImplDelegate>(
  162. link_manager.get()));
  163. // Disconnect before Start().
  164. EXPECT_FALSE(link_manager->is_abandon_called());
  165. remote.reset();
  166. // FlushForTesting() is no longer available. Instead, use base::RunLoop.
  167. base::RunLoop().RunUntilIdle();
  168. // The disconnection should not be propagated to the link manager.
  169. EXPECT_FALSE(link_manager->is_abandon_called());
  170. }
  171. } // namespace prerender