Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(36)

Side by Side Diff: components/payments/content/payment_request_state.cc

Issue 2742813004: [Payments] Refactor into PaymentRequestState and Spec (Closed)
Patch Set: deps fix Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2016 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 "components/payments/content/payment_request_state.h"
6
7 #include "components/autofill/core/browser/autofill_data_util.h"
8 #include "components/autofill/core/browser/autofill_profile.h"
9 #include "components/autofill/core/browser/credit_card.h"
10 #include "components/payments/content/payment_request_spec.h"
11 #include "components/payments/core/autofill_payment_instrument.h"
12
13 namespace payments {
14
15 namespace {
16 // Identifier for the basic card payment method in the PaymentMethodData.
17 static const char* const kBasicCardMethodName = "basic-card";
18 } // namespace
19
20 PaymentRequestState::PaymentRequestState(PaymentRequestSpec* spec,
21 Delegate* delegate)
22 : is_ready_to_pay_(false),
23 spec_(spec),
24 delegate_(delegate),
25 selected_shipping_profile_(nullptr),
26 selected_contact_profile_(nullptr),
27 selected_credit_card_(nullptr),
28 selected_shipping_option_(nullptr) {
29 UpdateSelectedShippingOption();
30 }
31
32 void PaymentRequestState::AddObserver(Observer* observer) {
33 CHECK(observer);
34 observers_.AddObserver(observer);
35 }
36 PaymentRequestState::~PaymentRequestState() {}
37
38 void PaymentRequestState::RemoveObserver(Observer* observer) {
39 observers_.RemoveObserver(observer);
40 }
41
42 void PaymentRequestState::OnInstrumentDetailsReady(
43 const std::string& method_name,
44 const std::string& stringified_details) {
45 // TODO(mathp): Fill other fields in the PaymentResponsePtr object.
46 mojom::PaymentResponsePtr payment_response = mojom::PaymentResponse::New();
47
48 payment_response->method_name = method_name;
49 payment_response->stringified_details = stringified_details;
50 delegate_->OnPaymentResponseAvailable(std::move(payment_response));
51 }
52
53 void PaymentRequestState::GeneratePaymentResponse() {
54 // TODO(mathp): PaymentRequest should know about the currently selected
55 // instrument, and not |selected_credit_card_| which is too specific.
56 // TODO(mathp): The method_name should reflect what the merchant asked, and
57 // not necessarily basic-card.
58 selected_payment_instrument_.reset(new AutofillPaymentInstrument(
59 kBasicCardMethodName, *selected_credit_card_,
60 delegate_->GetBillingProfiles(), delegate_->GetApplicationLocale()));
61 // Fetch the instrument details, will call back into
62 // PaymentRequest::OnInstrumentsDetailsReady.
63 selected_payment_instrument_->InvokePaymentApp(this);
64 }
65
66 void PaymentRequestState::SetSelectedShippingProfile(
67 autofill::AutofillProfile* profile) {
68 selected_shipping_profile_ = profile;
69 UpdateIsReadyToPayAndNotifyObservers();
70 }
71
72 void PaymentRequestState::SetSelectedContactProfile(
73 autofill::AutofillProfile* profile) {
74 selected_contact_profile_ = profile;
75 UpdateIsReadyToPayAndNotifyObservers();
76 }
77
78 void PaymentRequestState::SetSelectedCreditCard(autofill::CreditCard* card) {
79 selected_credit_card_ = card;
80 UpdateIsReadyToPayAndNotifyObservers();
81 }
82
83 void PaymentRequestState::SetInitialSelections(
84 autofill::AutofillProfile* shipping,
85 autofill::AutofillProfile* contact,
86 autofill::CreditCard* card) {
87 // Setting directly instead of using their setters to avoid recomputing the
88 // "ready to pay" state.
89 selected_shipping_profile_ = shipping;
90 selected_contact_profile_ = contact;
91 selected_credit_card_ = card;
92 UpdateIsReadyToPayAndNotifyObservers();
93 }
94
95 void PaymentRequestState::UpdateIsReadyToPayAndNotifyObservers() {
96 is_ready_to_pay_ =
97 ArePaymentDetailsSatisfied() && ArePaymentOptionsSatisfied();
98 NotifyOnSelectedInformationChanged();
99 }
100
101 void PaymentRequestState::NotifyOnSelectedInformationChanged() {
102 for (auto& observer : observers_)
103 observer.OnSelectedInformationChanged();
104 }
105
106 bool PaymentRequestState::ArePaymentDetailsSatisfied() {
107 // TODO(mathp): A masked card may not satisfy IsValid().
108 if (selected_credit_card_ == nullptr || !selected_credit_card_->IsValid())
109 return false;
110
111 const std::string basic_card_payment_type =
112 autofill::data_util::GetPaymentRequestData(selected_credit_card_->type())
113 .basic_card_payment_type;
114 return !spec_->supported_card_networks().empty() &&
115 std::find(spec_->supported_card_networks().begin(),
116 spec_->supported_card_networks().end(),
117 basic_card_payment_type) !=
118 spec_->supported_card_networks().end();
119 }
120
121 bool PaymentRequestState::ArePaymentOptionsSatisfied() {
122 // TODO(mathp): Have a measure of shipping address completeness.
123 if (spec_->request_shipping() && selected_shipping_profile_ == nullptr)
124 return false;
125
126 // TODO(mathp): Make an encompassing class to validate contact info.
127 const std::string& app_locale = delegate_->GetApplicationLocale();
128 if (spec_->request_payer_name() &&
129 (selected_contact_profile_ == nullptr ||
130 selected_contact_profile_
131 ->GetInfo(autofill::AutofillType(autofill::NAME_FULL), app_locale)
132 .empty())) {
133 return false;
134 }
135 if (spec_->request_payer_email() &&
136 (selected_contact_profile_ == nullptr ||
137 selected_contact_profile_
138 ->GetInfo(autofill::AutofillType(autofill::EMAIL_ADDRESS),
139 app_locale)
140 .empty())) {
141 return false;
142 }
143 if (spec_->request_payer_phone() &&
144 (selected_contact_profile_ == nullptr ||
145 selected_contact_profile_
146 ->GetInfo(autofill::AutofillType(autofill::PHONE_HOME_WHOLE_NUMBER),
147 app_locale)
148 .empty())) {
149 return false;
150 }
151
152 return true;
153 }
154
155 void PaymentRequestState::UpdateSelectedShippingOption() {
156 selected_shipping_option_ = nullptr;
157
158 // As per the spec, the selected shipping option should initially be the last
159 // one in the array that has its selected field set to true.
160 auto selected_shipping_option_it = std::find_if(
161 spec_->details()->shipping_options.rbegin(),
162 spec_->details()->shipping_options.rend(),
163 [](const payments::mojom::PaymentShippingOptionPtr& element) {
164 return element->selected;
165 });
166 if (selected_shipping_option_it !=
167 spec_->details()->shipping_options.rend()) {
168 selected_shipping_option_ = selected_shipping_option_it->get();
169 }
170 }
171
172 } // namespace payments
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698