| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 package org.chromium.chrome.browser.payments; | 5 package org.chromium.chrome.browser.payments; |
| 6 | 6 |
| 7 import android.app.Activity; | 7 import android.app.Activity; |
| 8 import android.graphics.Bitmap; | 8 import android.graphics.Bitmap; |
| 9 import android.os.Handler; | 9 import android.os.Handler; |
| 10 import android.support.v4.util.ArrayMap; | 10 import android.support.v4.util.ArrayMap; |
| (...skipping 201 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 212 */ | 212 */ |
| 213 private PaymentItem mRawTotal; | 213 private PaymentItem mRawTotal; |
| 214 | 214 |
| 215 /** | 215 /** |
| 216 * The raw items in the shopping cart, as they were received from the websit
e. This data is | 216 * The raw items in the shopping cart, as they were received from the websit
e. This data is |
| 217 * passed to the payment app. | 217 * passed to the payment app. |
| 218 */ | 218 */ |
| 219 private List<PaymentItem> mRawLineItems; | 219 private List<PaymentItem> mRawLineItems; |
| 220 | 220 |
| 221 /** | 221 /** |
| 222 * A mapping from method names to modified totals. Used to display modified
totals for each |
| 223 * payment instrument. |
| 224 */ |
| 225 private Map<String, PaymentItem> mModifiedTotals; |
| 226 |
| 227 /** |
| 222 * The UI model of the shopping cart, including the total. Each item include
s a label and a | 228 * The UI model of the shopping cart, including the total. Each item include
s a label and a |
| 223 * price string. This data is passed to the UI. | 229 * price string. This data is passed to the UI. |
| 224 */ | 230 */ |
| 225 private ShoppingCart mUiShoppingCart; | 231 private ShoppingCart mUiShoppingCart; |
| 226 | 232 |
| 227 /** | 233 /** |
| 228 * The UI model for the shipping options. Includes the label and sublabel fo
r each shipping | 234 * The UI model for the shipping options. Includes the label and sublabel fo
r each shipping |
| 229 * option. Also keeps track of the selected shipping option. This data is pa
ssed to the UI. | 235 * option. Also keeps track of the selected shipping option. This data is pa
ssed to the UI. |
| 230 */ | 236 */ |
| 231 private SectionInformation mUiShippingOptions; | 237 private SectionInformation mUiShippingOptions; |
| 232 | 238 |
| 233 private Map<String, PaymentMethodData> mMethodData; | 239 private Map<String, PaymentMethodData> mMethodData; |
| 234 private SectionInformation mShippingAddressesSection; | 240 private SectionInformation mShippingAddressesSection; |
| 235 private SectionInformation mContactSection; | 241 private SectionInformation mContactSection; |
| 236 private List<PaymentApp> mPendingApps; | 242 private List<PaymentApp> mPendingApps; |
| 237 private List<PaymentInstrument> mPendingInstruments; | 243 private List<PaymentInstrument> mPendingInstruments; |
| 238 private List<PaymentInstrument> mPendingAutofillInstruments; | 244 private List<PaymentInstrument> mPendingAutofillInstruments; |
| 239 private SectionInformation mPaymentMethodsSection; | 245 private SectionInformation mPaymentMethodsSection; |
| 240 private PaymentRequestUI mUI; | 246 private PaymentRequestUI mUI; |
| 241 private Callback<PaymentInformation> mPaymentInformationCallback; | 247 private Callback<PaymentInformation> mPaymentInformationCallback; |
| 242 private boolean mPaymentAppRunning; | 248 private boolean mPaymentAppRunning; |
| 243 private boolean mMerchantSupportsAutofillPaymentInstruments; | 249 private boolean mMerchantSupportsAutofillPaymentInstruments; |
| 244 private ContactEditor mContactEditor; | 250 private ContactEditor mContactEditor; |
| 245 private boolean mHasRecordedAbortReason; | 251 private boolean mHasRecordedAbortReason; |
| 246 private boolean mQueriedCanMakeActivePayment; | 252 private boolean mQueriedCanMakeActivePayment; |
| 253 private CurrencyStringFormatter mFormatter; |
| 247 | 254 |
| 248 /** True if any of the requested payment methods are supported. */ | 255 /** True if any of the requested payment methods are supported. */ |
| 249 private boolean mArePaymentMethodsSupported; | 256 private boolean mArePaymentMethodsSupported; |
| 250 | 257 |
| 251 /** The helper to create and fill the response to send to the merchant. */ | 258 /** The helper to create and fill the response to send to the merchant. */ |
| 252 private PaymentResponseHelper mPaymentResponseHelper; | 259 private PaymentResponseHelper mPaymentResponseHelper; |
| 253 | 260 |
| 254 /** | 261 /** |
| 255 * Builds the PaymentRequest service implementation. | 262 * Builds the PaymentRequest service implementation. |
| 256 * | 263 * |
| (...skipping 332 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 589 */ | 596 */ |
| 590 private boolean parseAndValidateDetailsOrDisconnectFromClient(PaymentDetails
details) { | 597 private boolean parseAndValidateDetailsOrDisconnectFromClient(PaymentDetails
details) { |
| 591 if (!PaymentValidator.validatePaymentDetails(details)) { | 598 if (!PaymentValidator.validatePaymentDetails(details)) { |
| 592 disconnectFromClientWithDebugMessage("Invalid payment details"); | 599 disconnectFromClientWithDebugMessage("Invalid payment details"); |
| 593 recordAbortReasonHistogram( | 600 recordAbortReasonHistogram( |
| 594 PaymentRequestMetrics.ABORT_REASON_INVALID_DATA_FROM_RENDERE
R); | 601 PaymentRequestMetrics.ABORT_REASON_INVALID_DATA_FROM_RENDERE
R); |
| 595 return false; | 602 return false; |
| 596 } | 603 } |
| 597 | 604 |
| 598 String totalCurrency = details.total.amount.currency; | 605 String totalCurrency = details.total.amount.currency; |
| 599 CurrencyStringFormatter formatter = | 606 if (mFormatter == null) { |
| 600 new CurrencyStringFormatter(totalCurrency, Locale.getDefault()); | 607 mFormatter = new CurrencyStringFormatter(totalCurrency, Locale.getDe
fault()); |
| 608 } |
| 601 | 609 |
| 602 // Total is never pending. | 610 // Total is never pending. |
| 603 LineItem uiTotal = new LineItem( | 611 LineItem uiTotal = new LineItem( |
| 604 details.total.label, formatter.getFormattedCurrencyCode(), | 612 details.total.label, mFormatter.getFormattedCurrencyCode(), |
| 605 formatter.format(details.total.amount.value), /* isPending */ fa
lse); | 613 mFormatter.format(details.total.amount.value), /* isPending */ f
alse); |
| 606 | 614 |
| 607 List<LineItem> uiLineItems = getLineItems(details.displayItems, totalCur
rency, formatter); | 615 List<LineItem> uiLineItems = getLineItems(details.displayItems, totalCur
rency, mFormatter); |
| 608 | 616 |
| 609 mUiShoppingCart = new ShoppingCart(uiTotal, uiLineItems); | 617 mUiShoppingCart = new ShoppingCart(uiTotal, uiLineItems); |
| 610 mRawTotal = details.total; | 618 mRawTotal = details.total; |
| 611 mRawLineItems = Collections.unmodifiableList(Arrays.asList(details.displ
ayItems)); | 619 mRawLineItems = Collections.unmodifiableList(Arrays.asList(details.displ
ayItems)); |
| 612 | 620 |
| 613 mUiShippingOptions = getShippingOptions(details.shippingOptions, totalCu
rrency, formatter); | 621 mUiShippingOptions = getShippingOptions(details.shippingOptions, totalCu
rrency, mFormatter); |
| 622 |
| 623 for (int i = 0; i < details.modifiers.length; i++) { |
| 624 PaymentItem total = details.modifiers[i].total; |
| 625 String[] methods = details.modifiers[i].methodData.supportedMethods; |
| 626 if (total != null) { |
| 627 for (int j = 0; j < methods.length; j++) { |
| 628 if (mModifiedTotals == null) mModifiedTotals = new ArrayMap<
>(); |
| 629 mModifiedTotals.put(methods[j], total); |
| 630 } |
| 631 } |
| 632 } |
| 633 |
| 634 updateInstrumentModifiedTotals(); |
| 614 | 635 |
| 615 return true; | 636 return true; |
| 616 } | 637 } |
| 617 | 638 |
| 639 /** Updates the modified totals for payment instruments. */ |
| 640 private void updateInstrumentModifiedTotals() { |
| 641 if (!ChromeFeatureList.isEnabled(ChromeFeatureList.WEB_PAYMENTS_MODIFIER
S)) return; |
| 642 if (mModifiedTotals == null) return; |
| 643 if (mPaymentMethodsSection == null) return; |
| 644 |
| 645 for (int i = 0; i < mPaymentMethodsSection.getSize(); i++) { |
| 646 PaymentOption option = mPaymentMethodsSection.getItem(i); |
| 647 assert option instanceof PaymentInstrument; |
| 648 PaymentInstrument instrument = (PaymentInstrument) option; |
| 649 PaymentItem modifiedTotal = mModifiedTotals.get(instrument.getInstru
mentMethodName()); |
| 650 instrument.setModifiedTotal( |
| 651 modifiedTotal == null ? null : mFormatter.format(modifiedTot
al.amount.value)); |
| 652 } |
| 653 } |
| 654 |
| 618 /** | 655 /** |
| 619 * Returns true if all fields in the payment item are non-null and non-empty
. | 656 * Returns true if all fields in the payment item are non-null and non-empty
. |
| 620 * | 657 * |
| 621 * @param item The payment item to examine. | 658 * @param item The payment item to examine. |
| 622 * @return True if all fields are present and non-empty. | 659 * @return True if all fields are present and non-empty. |
| 623 */ | 660 */ |
| 624 private static boolean hasAllPaymentItemFields(PaymentItem item) { | 661 private static boolean hasAllPaymentItemFields(PaymentItem item) { |
| 625 // "label", "currency", and "value" should be non-empty. | 662 // "label", "currency", and "value" should be non-empty. |
| 626 return item != null && !TextUtils.isEmpty(item.label) && item.amount !=
null | 663 return item != null && !TextUtils.isEmpty(item.label) && item.amount !=
null |
| 627 && !TextUtils.isEmpty(item.amount.currency) | 664 && !TextUtils.isEmpty(item.amount.currency) |
| (...skipping 492 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1120 | 1157 |
| 1121 ActivePaymentQuery query = sCanMakeActivePaymentQueries.get(mOrigin); | 1158 ActivePaymentQuery query = sCanMakeActivePaymentQueries.get(mOrigin); |
| 1122 if (query != null) query.setResponse(selection == 0); | 1159 if (query != null) query.setResponse(selection == 0); |
| 1123 | 1160 |
| 1124 // The list of payment instruments is ready to display. | 1161 // The list of payment instruments is ready to display. |
| 1125 mPaymentMethodsSection = new SectionInformation(PaymentRequestUI.TYPE_PA
YMENT_METHODS, | 1162 mPaymentMethodsSection = new SectionInformation(PaymentRequestUI.TYPE_PA
YMENT_METHODS, |
| 1126 selection, mPendingInstruments); | 1163 selection, mPendingInstruments); |
| 1127 | 1164 |
| 1128 mPendingInstruments.clear(); | 1165 mPendingInstruments.clear(); |
| 1129 | 1166 |
| 1167 updateInstrumentModifiedTotals(); |
| 1168 |
| 1130 // UI has requested the full list of payment instruments. Provide it now
. | 1169 // UI has requested the full list of payment instruments. Provide it now
. |
| 1131 if (mPaymentInformationCallback != null) providePaymentInformation(); | 1170 if (mPaymentInformationCallback != null) providePaymentInformation(); |
| 1132 } | 1171 } |
| 1133 | 1172 |
| 1134 /** | 1173 /** |
| 1135 * If no payment methods are supported, disconnect from the client and retur
n true. | 1174 * If no payment methods are supported, disconnect from the client and retur
n true. |
| 1136 * | 1175 * |
| 1137 * @return True if no payment methods are supported | 1176 * @return True if no payment methods are supported |
| 1138 */ | 1177 */ |
| 1139 private boolean disconnectIfNoPaymentMethodsSupported() { | 1178 private boolean disconnectIfNoPaymentMethodsSupported() { |
| (...skipping 183 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1323 "PaymentRequest.CheckoutFunnel.Aborted", abortReason, | 1362 "PaymentRequest.CheckoutFunnel.Aborted", abortReason, |
| 1324 PaymentRequestMetrics.ABORT_REASON_MAX); | 1363 PaymentRequestMetrics.ABORT_REASON_MAX); |
| 1325 | 1364 |
| 1326 if (abortReason == PaymentRequestMetrics.ABORT_REASON_ABORTED_BY_USER) { | 1365 if (abortReason == PaymentRequestMetrics.ABORT_REASON_ABORTED_BY_USER) { |
| 1327 mJourneyLogger.recordJourneyStatsHistograms("UserAborted"); | 1366 mJourneyLogger.recordJourneyStatsHistograms("UserAborted"); |
| 1328 } else { | 1367 } else { |
| 1329 mJourneyLogger.recordJourneyStatsHistograms("OtherAborted"); | 1368 mJourneyLogger.recordJourneyStatsHistograms("OtherAborted"); |
| 1330 } | 1369 } |
| 1331 } | 1370 } |
| 1332 } | 1371 } |
| OLD | NEW |