blob: 4604e137002dad5bdf539ab6484f153eef0683df [file] [log] [blame]
Danyao Wang25f72dc2019-10-18 05:11:321// Copyright 2019 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
5#include "base/macros.h"
Danyao Wang25f72dc2019-10-18 05:11:326#include "base/test/metrics/histogram_tester.h"
Sahel Sharify6bfc6192020-02-21 20:33:357#include "chrome/test/payments/payment_request_platform_browsertest_base.h"
Danyao Wang25f72dc2019-10-18 05:11:328#include "components/payments/core/journey_logger.h"
Sahel Sharifydab66602020-01-30 20:35:309#include "components/ukm/test_ukm_recorder.h"
Peter Kasting919ce652020-05-07 10:22:3610#include "content/public/test/browser_test.h"
Sahel Sharifydab66602020-01-30 20:35:3011#include "services/metrics/public/cpp/ukm_builders.h"
Danyao Wang25f72dc2019-10-18 05:11:3212
13namespace payments {
Danyao Wang25f72dc2019-10-18 05:11:3214
Sahel Sharify6bfc6192020-02-21 20:33:3515class JourneyLoggerTest : public PaymentRequestPlatformBrowserTestBase {
Danyao Wang25f72dc2019-10-18 05:11:3216 public:
Sahel Sharify6bfc6192020-02-21 20:33:3517 JourneyLoggerTest() : gpay_server_(net::EmbeddedTestServer::TYPE_HTTPS) {}
Danyao Wang25f72dc2019-10-18 05:11:3218
Sahel Sharify6bfc6192020-02-21 20:33:3519 ~JourneyLoggerTest() override = default;
Danyao Wang25f72dc2019-10-18 05:11:3220
Sahel Sharifydab66602020-01-30 20:35:3021 void PreRunTestOnMainThread() override {
Sahel Sharify6bfc6192020-02-21 20:33:3522 PaymentRequestPlatformBrowserTestBase::PreRunTestOnMainThread();
Sahel Sharifydab66602020-01-30 20:35:3023 test_ukm_recorder_ = std::make_unique<ukm::TestAutoSetUkmRecorder>();
24 }
25
Danyao Wang25f72dc2019-10-18 05:11:3226 void SetUpOnMainThread() override {
Sahel Sharify6bfc6192020-02-21 20:33:3527 PaymentRequestPlatformBrowserTestBase::SetUpOnMainThread();
Sahel Sharify54f5e862020-03-26 20:02:4128 main_frame_url_ = https_server()->GetURL("/journey_logger_test.html");
29 ASSERT_TRUE(
30 content::NavigateToURL(GetActiveWebContents(), main_frame_url_));
31 }
32
33 void SetUpForGpay() {
Danyao Wang25f72dc2019-10-18 05:11:3234 gpay_server_.ServeFilesFromSourceDirectory(
35 "components/test/data/payments/google.com/");
36 ASSERT_TRUE(gpay_server_.Start());
37
38 // Set up test manifest downloader that knows how to fake origin.
Sahel Sharify6bfc6192020-02-21 20:33:3539 const std::string method_name = "google.com";
40 SetDownloaderAndIgnorePortInOriginComparisonForTesting(
41 {{method_name, &gpay_server_}});
Danyao Wang25f72dc2019-10-18 05:11:3242
Sahel Sharify54f5e862020-03-26 20:02:4143 gpay_scope_url_ = gpay_server_.GetURL("google.com", "/");
Danyao Wang25f72dc2019-10-18 05:11:3244 }
45
Sahel Sharifydab66602020-01-30 20:35:3046 const GURL& main_frame_url() const { return main_frame_url_; }
Sahel Sharify54f5e862020-03-26 20:02:4147 const GURL& gpay_scope_url() const { return gpay_scope_url_; }
Sahel Sharifydab66602020-01-30 20:35:3048
49 ukm::TestAutoSetUkmRecorder* test_ukm_recorder() {
50 return test_ukm_recorder_.get();
51 }
52
Danyao Wang25f72dc2019-10-18 05:11:3253 private:
Danyao Wang25f72dc2019-10-18 05:11:3254 net::EmbeddedTestServer gpay_server_;
Sahel Sharifydab66602020-01-30 20:35:3055 GURL main_frame_url_;
Sahel Sharify54f5e862020-03-26 20:02:4156 GURL gpay_scope_url_;
Sahel Sharifydab66602020-01-30 20:35:3057 std::unique_ptr<ukm::TestAutoSetUkmRecorder> test_ukm_recorder_;
Danyao Wang25f72dc2019-10-18 05:11:3258
59 DISALLOW_COPY_AND_ASSIGN(JourneyLoggerTest);
60};
61
62IN_PROC_BROWSER_TEST_F(JourneyLoggerTest, NoPaymentMethodSupported) {
63 base::HistogramTester histogram_tester;
Sahel Sharify9306fe92020-08-18 20:04:5864 GURL merchant_url = https_server()->GetURL("/payment_handler.html");
65 ASSERT_TRUE(content::NavigateToURL(GetActiveWebContents(), merchant_url));
Danyao Wang25f72dc2019-10-18 05:11:3266
Sahel Sharify9306fe92020-08-18 20:04:5867 // Launch the payment request without installing the payment app.
68 ResetEventWaiterForSingleEvent(TestEvent::kNotSupportedError);
69 EXPECT_EQ("success", content::EvalJs(GetActiveWebContents(),
70 "launchWithoutWaitForResponse()"));
Danyao Wang25f72dc2019-10-18 05:11:3271 WaitForObservedEvent();
72
Danyao Wang25f72dc2019-10-18 05:11:3273 std::vector<base::Bucket> buckets =
74 histogram_tester.GetAllSamples("PaymentRequest.Events");
75 ASSERT_EQ(1U, buckets.size());
76 EXPECT_FALSE(buckets[0].min &
77 JourneyLogger::EVENT_AVAILABLE_METHOD_BASIC_CARD);
78 EXPECT_FALSE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_GOOGLE);
79 EXPECT_FALSE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_OTHER);
Sahel Sharify9306fe92020-08-18 20:04:5880
81 // Verify recorded checkout steps.
82 histogram_tester.ExpectBucketCount(
83 "PaymentRequest.CheckoutFunnel",
84 JourneyLogger::CheckoutFunnelStep::kInitiated, 1U);
85 histogram_tester.ExpectBucketCount(
86 "PaymentRequest.CheckoutFunnel",
87 JourneyLogger::CheckoutFunnelStep::kShowCalled, 1U);
88 histogram_tester.ExpectBucketCount(
89 "PaymentRequest.CheckoutFunnel",
90 JourneyLogger::CheckoutFunnelStep::kPaymentRequestTriggered, 0U);
91 histogram_tester.ExpectBucketCount(
92 "PaymentRequest.CheckoutFunnel",
93 JourneyLogger::CheckoutFunnelStep::kPaymentHandlerInvoked, 0U);
94 histogram_tester.ExpectBucketCount(
95 "PaymentRequest.CheckoutFunnel",
96 JourneyLogger::CheckoutFunnelStep::kCompleted, 0U);
Danyao Wang25f72dc2019-10-18 05:11:3297}
98
99IN_PROC_BROWSER_TEST_F(JourneyLoggerTest, BasicCardOnly) {
Sahel Sharify6bfc6192020-02-21 20:33:35100 CreateAndAddCreditCardForProfile(CreateAndAddAutofillProfile());
Danyao Wang25f72dc2019-10-18 05:11:32101 base::HistogramTester histogram_tester;
102
Sahel Sharifyfd677ff2020-07-08 19:01:52103 ResetEventWaiterForSingleEvent(TestEvent::kAppListReady);
Danyao Wang25f72dc2019-10-18 05:11:32104 EXPECT_TRUE(content::ExecJs(GetActiveWebContents(), "testBasicCard()"));
105 WaitForObservedEvent();
106
107 EXPECT_EQ(true, content::EvalJs(GetActiveWebContents(), "abort()"));
108
109 std::vector<base::Bucket> buckets =
110 histogram_tester.GetAllSamples("PaymentRequest.Events");
111 ASSERT_EQ(1U, buckets.size());
112 EXPECT_TRUE(buckets[0].min &
113 JourneyLogger::EVENT_AVAILABLE_METHOD_BASIC_CARD);
114 EXPECT_FALSE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_GOOGLE);
115 EXPECT_FALSE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_OTHER);
116}
117
118IN_PROC_BROWSER_TEST_F(JourneyLoggerTest, GooglePaymentApp) {
119 base::HistogramTester histogram_tester;
Sahel Sharify54f5e862020-03-26 20:02:41120 SetUpForGpay();
Danyao Wang25f72dc2019-10-18 05:11:32121
122 EXPECT_EQ("{\"apiVersion\":1}",
123 content::EvalJs(GetActiveWebContents(), "testGPay()"));
124
125 std::vector<base::Bucket> buckets =
126 histogram_tester.GetAllSamples("PaymentRequest.Events");
127 ASSERT_EQ(1U, buckets.size());
128 EXPECT_FALSE(buckets[0].min &
129 JourneyLogger::EVENT_AVAILABLE_METHOD_BASIC_CARD);
130 EXPECT_TRUE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_GOOGLE);
131 EXPECT_FALSE(buckets[0].min & JourneyLogger::EVENT_AVAILABLE_METHOD_OTHER);
Sahel Sharify9306fe92020-08-18 20:04:58132
133 // Verify recorded checkout steps.
134 histogram_tester.ExpectBucketCount(
135 "PaymentRequest.CheckoutFunnel",
136 JourneyLogger::CheckoutFunnelStep::kInitiated, 1U);
137 histogram_tester.ExpectBucketCount(
138 "PaymentRequest.CheckoutFunnel",
139 JourneyLogger::CheckoutFunnelStep::kShowCalled, 1U);
140 histogram_tester.ExpectBucketCount(
141 "PaymentRequest.CheckoutFunnel",
142 JourneyLogger::CheckoutFunnelStep::kPaymentRequestTriggered, 1U);
143 histogram_tester.ExpectBucketCount(
144 "PaymentRequest.CheckoutFunnel",
145 JourneyLogger::CheckoutFunnelStep::kPaymentHandlerInvoked, 1U);
146 histogram_tester.ExpectBucketCount(
147 "PaymentRequest.CheckoutFunnel",
148 JourneyLogger::CheckoutFunnelStep::kCompleted, 1U);
Danyao Wang25f72dc2019-10-18 05:11:32149}
150
Sahel Sharifydab66602020-01-30 20:35:30151// Make sure the UKM was logged correctly.
152IN_PROC_BROWSER_TEST_F(JourneyLoggerTest, UKMTransactionAmountRecorded) {
Sahel Sharify54f5e862020-03-26 20:02:41153 SetUpForGpay();
Sahel Sharifydab66602020-01-30 20:35:30154 EXPECT_EQ("{\"apiVersion\":1}",
155 content::EvalJs(GetActiveWebContents(), "testGPay()"));
156
157 auto entries = test_ukm_recorder()->GetEntriesByName(
158 ukm::builders::PaymentRequest_TransactionAmount::kEntryName);
159 size_t num_entries = entries.size();
160 EXPECT_EQ(2u, num_entries);
161 for (size_t i = 0; i < num_entries; i++) {
162 test_ukm_recorder()->ExpectEntrySourceHasUrl(entries[i], main_frame_url());
163 EXPECT_EQ(2U, entries[i]->metrics.size());
164 test_ukm_recorder()->ExpectEntryMetric(
165 entries[i],
166 ukm::builders::PaymentRequest_TransactionAmount::kCompletionStatusName,
167 i != 0 /* completed */);
168 test_ukm_recorder()->ExpectEntryMetric(
169 entries[i],
170 ukm::builders::PaymentRequest_TransactionAmount::kCategoryName,
171 static_cast<int64_t>(
172 JourneyLogger::TransactionSize::kRegularTransaction));
173 }
174}
175
Sahel Sharify54f5e862020-03-26 20:02:41176IN_PROC_BROWSER_TEST_F(JourneyLoggerTest,
177 UKMCheckoutEventsRecordedForAppOrigin) {
178 GURL merchant_url = https_server()->GetURL("/payment_handler.html");
179 ASSERT_TRUE(content::NavigateToURL(GetActiveWebContents(), merchant_url));
180 EXPECT_EQ("success", content::EvalJs(GetActiveWebContents(), "install()"));
181
182 ResetEventWaiterForSingleEvent(TestEvent::kPaymentCompleted);
183 EXPECT_EQ("success", content::EvalJs(GetActiveWebContents(), "launch()"));
184 WaitForObservedEvent();
185
186 // UKM for merchant's website origin.
187 auto entries = test_ukm_recorder()->GetEntriesByName(
188 ukm::builders::PaymentRequest_CheckoutEvents::kEntryName);
189 size_t num_entries = entries.size();
190 EXPECT_EQ(1u, num_entries);
191 test_ukm_recorder()->ExpectEntrySourceHasUrl(entries[0], merchant_url);
192
193 // UKM for payment app's scope.
194 entries = test_ukm_recorder()->GetEntriesByName(
195 ukm::builders::PaymentApp_CheckoutEvents::kEntryName);
196 num_entries = entries.size();
197 EXPECT_EQ(1u, num_entries);
198 test_ukm_recorder()->ExpectEntrySourceHasUrl(entries[0],
199 https_server()->GetURL("/"));
200}
201
202IN_PROC_BROWSER_TEST_F(
203 JourneyLoggerTest,
204 UKMCheckoutEventsNotRecordedForAppOriginWhenNoWindowShown) {
205 SetUpForGpay();
206
207 EXPECT_EQ("{\"apiVersion\":1}",
208 content::EvalJs(GetActiveWebContents(), "testGPay()"));
209
210 // UKM for merchant's website origin.
211 auto entries = test_ukm_recorder()->GetEntriesByName(
212 ukm::builders::PaymentRequest_CheckoutEvents::kEntryName);
213 size_t num_entries = entries.size();
214 EXPECT_EQ(1u, num_entries);
215 test_ukm_recorder()->ExpectEntrySourceHasUrl(entries[0], main_frame_url());
216
217 // No UKM for payment app's scope since the app's origin is not shown inside
218 // the PH modal window.
219 entries = test_ukm_recorder()->GetEntriesByName(
220 ukm::builders::PaymentApp_CheckoutEvents::kEntryName);
221 num_entries = entries.size();
222 EXPECT_EQ(0u, num_entries);
223}
224
225IN_PROC_BROWSER_TEST_F(
226 JourneyLoggerTest,
227 UKMCheckoutEventsNotRecordedForAppOriginWhenNoAppInvoked) {
228 CreateAndAddCreditCardForProfile(CreateAndAddAutofillProfile());
229
Sahel Sharifyfd677ff2020-07-08 19:01:52230 ResetEventWaiterForSingleEvent(TestEvent::kAppListReady);
Sahel Sharify54f5e862020-03-26 20:02:41231 EXPECT_TRUE(content::ExecJs(GetActiveWebContents(), "testBasicCard()"));
232 WaitForObservedEvent();
233
234 EXPECT_EQ(true, content::EvalJs(GetActiveWebContents(), "abort()"));
235
236 // UKM for merchant's website origin.
237 auto entries = test_ukm_recorder()->GetEntriesByName(
238 ukm::builders::PaymentRequest_CheckoutEvents::kEntryName);
239 size_t num_entries = entries.size();
240 EXPECT_EQ(1u, num_entries);
241 test_ukm_recorder()->ExpectEntrySourceHasUrl(entries[0], main_frame_url());
242
243 // No UKM for payment app's scope since the request got aborted before
244 // invoking a payment app.
245 entries = test_ukm_recorder()->GetEntriesByName(
246 ukm::builders::PaymentApp_CheckoutEvents::kEntryName);
247 num_entries = entries.size();
248 EXPECT_EQ(0u, num_entries);
249}
250
Danyao Wang25f72dc2019-10-18 05:11:32251} // namespace payments