зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1435161
- mochitest for PaymentResponse.retry(). r=baku
1. Add testcase testRetryAfterComplete to test the behavior of retry() after complete(). 2. Add testcase testRetryAfterRetry to test the multiple retry()s in the same round. 3. Add testcase testRetryWithEmptyErrors to test the retry() called with an empty PaymentValidationErrors. 4. Add testcase testRetry to test the normal flow of retry(). 5. Add testcase testRetryAbortByUser to test the retry() aborted by user.
This commit is contained in:
Родитель
357f9deb02
Коммит
f4764c9019
|
@ -0,0 +1,182 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
"use strict";
|
||||
|
||||
const { XPCOMUtils } = ChromeUtils.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
const paymentSrv = Cc["@mozilla.org/dom/payments/payment-request-service;1"].getService(Ci.nsIPaymentRequestService);
|
||||
|
||||
function emitTestFail(message) {
|
||||
sendAsyncMessage("test-fail", message);
|
||||
}
|
||||
function emitTestPass(message) {
|
||||
sendAsyncMessage("test-pass", message);
|
||||
}
|
||||
|
||||
const billingAddress = Cc["@mozilla.org/dom/payments/payment-address;1"].
|
||||
createInstance(Ci.nsIPaymentAddress);
|
||||
const addressLine = Cc["@mozilla.org/array;1"].createInstance(Ci.nsIMutableArray);
|
||||
const address = Cc["@mozilla.org/supports-string;1"].createInstance(Ci.nsISupportsString);
|
||||
address.data = "Easton Ave";
|
||||
addressLine.appendElement(address);
|
||||
billingAddress.init("USA", // country
|
||||
addressLine, // address line
|
||||
"CA", // region
|
||||
"San Bruno", // city
|
||||
"", // dependent locality
|
||||
"94066", // postal code
|
||||
"123456", // sorting code
|
||||
"", // organization
|
||||
"Bill A. Pacheco", // recipient
|
||||
"+14344413879"); // phone
|
||||
|
||||
function acceptPayment(requestId, mode) {
|
||||
const basiccardResponseData = Cc["@mozilla.org/dom/payments/basiccard-response-data;1"].
|
||||
createInstance(Ci.nsIBasicCardResponseData);
|
||||
const showResponse = Cc["@mozilla.org/dom/payments/payment-show-action-response;1"].
|
||||
createInstance(Ci.nsIPaymentShowActionResponse);
|
||||
basiccardResponseData.initData("Bill A. Pacheco", // cardholderName
|
||||
"4916855166538720", // cardNumber
|
||||
"01", // expiryMonth
|
||||
"2024", // expiryYear
|
||||
"180", // cardSecurityCode
|
||||
billingAddress); // billingAddress
|
||||
if (mode === "show") {
|
||||
showResponse.init(requestId,
|
||||
Ci.nsIPaymentActionResponse.PAYMENT_ACCEPTED,
|
||||
"basic-card", // payment method
|
||||
basiccardResponseData,// payment method data
|
||||
"Bill A. Pacheco", // payer name
|
||||
"", // payer email
|
||||
""); // payer phone
|
||||
}
|
||||
if (mode == "retry") {
|
||||
showResponse.init(requestId,
|
||||
Ci.nsIPaymentActionResponse.PAYMENT_ACCEPTED,
|
||||
"basic-card", // payment method
|
||||
basiccardResponseData,// payment method data
|
||||
"Bill A. Pacheco", // payer name
|
||||
"bpacheco@test.org", // payer email
|
||||
"+123456789"); // payer phone
|
||||
}
|
||||
paymentSrv.respondPayment(showResponse.QueryInterface(Ci.nsIPaymentActionResponse));
|
||||
}
|
||||
|
||||
function rejectPayment(requestId) {
|
||||
const responseData = Cc["@mozilla.org/dom/payments/general-response-data;1"].
|
||||
createInstance(Ci.nsIGeneralResponseData);
|
||||
responseData.initData({});
|
||||
const showResponse = Cc["@mozilla.org/dom/payments/payment-show-action-response;1"].
|
||||
createInstance(Ci.nsIPaymentShowActionResponse);
|
||||
showResponse.init(requestId,
|
||||
Ci.nsIPaymentActionResponse.PAYMENT_REJECTED,
|
||||
"", // payment method
|
||||
responseData, // payment method data
|
||||
"", // payer name
|
||||
"", // payer email
|
||||
""); // payer phone
|
||||
paymentSrv.respondPayment(showResponse.QueryInterface(Ci.nsIPaymentActionResponse));
|
||||
}
|
||||
|
||||
function checkAddressErrors(testName, errors) {
|
||||
if (!errors) {
|
||||
emitTestFail(`${testName}: Expect non-null shippingAddressErrors, but got null.`);
|
||||
return;
|
||||
}
|
||||
for (const [key, msg] of Object.entries(errors)) {
|
||||
const expected = `${key} error`;
|
||||
if (msg !== expected) {
|
||||
emitTestFail(
|
||||
`${testName}: Expected '${expected}' on shippingAddressErrors.${key}, but got '${msg}'.`
|
||||
);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function checkPayerErrors(testName, errors) {
|
||||
if (!errors) {
|
||||
emitTestFail(`${testName}: Expect non-null payerErrors, but got null.`);
|
||||
return;
|
||||
}
|
||||
for (const [key, msg] of Object.entries(errors)) {
|
||||
const expected = `${key} error`;
|
||||
if (msg !== expected) {
|
||||
emitTestFail(`${testName}: Expected '${expected}' on payerErrors.${key}, but got '${msg}'.`);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function checkPaymentMethodErrors(testName, errors) {
|
||||
if (!errors) {
|
||||
emitTestFail(`${testName} :Expect non-null payerMethodErrors, but got null.`);
|
||||
return;
|
||||
}
|
||||
for (const [key, msg] of Object.entries(errors)) {
|
||||
const expected = `method ${key} error`;
|
||||
if (msg !== expected) {
|
||||
emitTestFail(
|
||||
`${testName}: Expected '${expected}' on paymentMethodErrors.${key}, but got '${msg}'.`
|
||||
);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const DummyUIService = {
|
||||
testName: "",
|
||||
rejectRetry: false,
|
||||
showPayment(requestId) {
|
||||
acceptPayment(requestId, "show");
|
||||
},
|
||||
abortPaymen(requestId) {
|
||||
respondRequestId = requestId
|
||||
},
|
||||
completePayment(requestId) {
|
||||
let completeResponse = Cc["@mozilla.org/dom/payments/payment-complete-action-response;1"].
|
||||
createInstance(Ci.nsIPaymentCompleteActionResponse);
|
||||
completeResponse.init(requestId, Ci.nsIPaymentActionResponse.COMPLETE_SUCCEEDED);
|
||||
paymentSrv.respondPayment(completeResponse.QueryInterface(Ci.nsIPaymentActionResponse));
|
||||
},
|
||||
updatePayment(requestId) {
|
||||
const payment = paymentSrv.getPaymentRequestById(requestId);
|
||||
if (payment.paymentDetails.error !== "error") {
|
||||
emitTestFail("Expect 'error' on details.error, but got '" +
|
||||
payment.paymentDetails.error + "'");
|
||||
}
|
||||
checkAddressErrors(this.testName, payment.paymentDetails.shippingAddressErrors)
|
||||
checkPayerErrors(this.testName, payment.paymentDetails.payer);
|
||||
checkPaymentMethodErrors(this.testName, payment.paymentDetails.paymentMethod);
|
||||
if (this.rejectRetry) {
|
||||
rejectPayment(requestId);
|
||||
} else {
|
||||
acceptPayment(requestId, "retry");
|
||||
}
|
||||
},
|
||||
closePayment: (requestId) => {respondRequestId = requestId},
|
||||
QueryInterface: ChromeUtils.generateQI([Ci.nsIPaymentUIService]),
|
||||
};
|
||||
|
||||
paymentSrv.setTestingUIService(DummyUIService.QueryInterface(Ci.nsIPaymentUIService));
|
||||
|
||||
addMessageListener("start-test", function(testName) {
|
||||
DummyUIService.testName = testName;
|
||||
sendAsyncMessage("start-test-complete");
|
||||
});
|
||||
|
||||
addMessageListener("finish-test", function() {
|
||||
DummyUIService.testName = "";
|
||||
sendAsyncMessage("finish-test-complete");
|
||||
});
|
||||
|
||||
addMessageListener("reject-retry", function() {
|
||||
DummyUIService.rejectRetry = true;
|
||||
sendAsyncMessage("reject-retry-complete");
|
||||
});
|
||||
|
||||
addMessageListener("teardown", function() {
|
||||
paymentSrv.setTestingUIService(null);
|
||||
sendAsyncMessage('teardown-complete');
|
||||
});
|
|
@ -14,6 +14,7 @@ support-files =
|
|||
GeneralChromeScript.js
|
||||
PMIValidationChromeScript.js
|
||||
RequestShippingChromeScript.js
|
||||
RetryPaymentChromeScript.js
|
||||
ShippingOptionsChromeScript.js
|
||||
ShowPaymentChromeScript.js
|
||||
UpdateErrorsChromeScript.js
|
||||
|
@ -33,6 +34,7 @@ skip-if = (verify && debug)
|
|||
[test_pmi_validation.html]
|
||||
skip-if = (verify && debug)
|
||||
[test_requestShipping.html]
|
||||
[test_retryPayment.html]
|
||||
[test_shippingOptions.html]
|
||||
[test_showPayment.html]
|
||||
[test_update_errors.html]
|
||||
|
|
|
@ -0,0 +1,354 @@
|
|||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=1435161
|
||||
-->
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Test for retry PaymentRequest</title>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<script type="application/javascript" src="DefaultData.js"></script>
|
||||
<script type="application/javascript">
|
||||
|
||||
"use strict";
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
|
||||
const gUrl = SimpleTest.getTestFileURL('RetryPaymentChromeScript.js');
|
||||
const gScript = SpecialPowers.loadChromeScript(gUrl);
|
||||
|
||||
function testFailHandler(message) {
|
||||
ok(false, message);
|
||||
}
|
||||
function testPassHandler(message) {
|
||||
ok(true, message);
|
||||
}
|
||||
gScript.addMessageListener("test-fail", testFailHandler);
|
||||
gScript.addMessageListener("test-pass", testPassHandler);
|
||||
|
||||
async function requestChromeAction(action, params) {
|
||||
gScript.sendAsyncMessage(action, params);
|
||||
await new Promise(resolve => {
|
||||
gScript.addMessageListener(`${action}-complete`, function completeListener() {
|
||||
gScript.removeMessageListener(`${action}-complete`, completeListener);
|
||||
resolve();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
const validationErrors = {
|
||||
error: "error",
|
||||
shippingAddress: {
|
||||
addressLine: "addressLine error",
|
||||
city: "city error",
|
||||
country: "country error",
|
||||
dependentLocality: "dependentLocality error",
|
||||
organization: "organization error",
|
||||
phone: "phone error",
|
||||
postalCode: "postalCode error",
|
||||
recipient: "recipient error",
|
||||
region: "region error",
|
||||
regionCode: "regionCode error",
|
||||
sortingCode: "sortingCode error",
|
||||
},
|
||||
payer: {
|
||||
name: "name error",
|
||||
email: "email error",
|
||||
phone: "phone error",
|
||||
},
|
||||
paymentMethod: {
|
||||
account: "method account error",
|
||||
password: "method password error",
|
||||
},
|
||||
};
|
||||
|
||||
const options = {
|
||||
requestPayerName: true,
|
||||
requestPayerEmail: true,
|
||||
reqeustPayerPhone: true,
|
||||
requestShipping: true,
|
||||
shippingType: "shipping"
|
||||
};
|
||||
|
||||
function checkShowResponse(testName, payResponse) {
|
||||
const { payerName, payerEmail, payerPhone } = payResponse.toJSON();
|
||||
is(
|
||||
payerName,
|
||||
"Bill A. Pacheco",
|
||||
`${testName}: Expected 'Bill A. Pacheco' on payerName, but got '${payerName}' after show PaymentRequest`
|
||||
);
|
||||
is(
|
||||
payerEmail,
|
||||
"",
|
||||
`${testName}: Expected '' on payerEmail, but got '${payerEmail}' after show PaymentRequest`
|
||||
);
|
||||
is(
|
||||
payerPhone,
|
||||
"",
|
||||
`${testName}: Expected '' on payerPhone, but got '${payerPhone}' after show PaymentRequest`
|
||||
);
|
||||
}
|
||||
|
||||
function checkRetryResponse(testName, payResponse) {
|
||||
const { payerName, payerEmail, payerPhone } = payResponse.toJSON();
|
||||
is(
|
||||
payerName,
|
||||
"Bill A. Pacheco",
|
||||
`${testName}: Expected 'Bill A. Pacheco' on payerName, but got '${payerName}' after retry PaymentRequest`
|
||||
);
|
||||
is(
|
||||
payerEmail,
|
||||
"bpacheco@test.org",
|
||||
`${testName} : Expected 'bpacheco@test.org' on payerEmail, but got '${payerEmail}' after retry PaymentRequest`
|
||||
);
|
||||
is(
|
||||
payerPhone,
|
||||
"+123456789",
|
||||
`${testName} : Expected '+123456789' on payerPhone, but got '${payerPhone}' after retry PaymentRequest`
|
||||
);
|
||||
}
|
||||
|
||||
function unexpectedErrMsg(testName, errName, timing) {
|
||||
return `${testName}: Unexpected error(${errName}) when ${timing} the PaymentRequest.`;
|
||||
}
|
||||
|
||||
function expectedErrMsg(testName, expectedErr, errName, timing) {
|
||||
return `${testName}: Expected '${expectedErr}' when ${timing} PaymentResponse, but got '${errName}'.`;
|
||||
}
|
||||
|
||||
async function testRetryAfterComplete() {
|
||||
const testName = "testRetryAfterComplete";
|
||||
await requestChromeAction("start-test", testName);
|
||||
const payRequest = new PaymentRequest(defaultMethods, defaultDetails, options);
|
||||
ok(payRequest, testName + ": failed to create PaymentRequest.");
|
||||
if (!payRequest) {
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
const handler = SpecialPowers.getDOMWindowUtils(window).setHandlingUserInput(true);
|
||||
let payResponse;
|
||||
try {
|
||||
payResponse = await payRequest.show();
|
||||
await checkShowResponse(testName, payResponse);
|
||||
handler.destruct();
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.Name, "showing"));
|
||||
await requestChromeAction("finish-test");
|
||||
handler.destruct();
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await payResponse.complete("success");
|
||||
} catch(err) {
|
||||
let errName = err.Name;
|
||||
ok(false, unexpectedErrMsg(testName, err.Name, "completing"));
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await payResponse.retry(validationErrors);
|
||||
ok(false, `${testName}: Unexpected success when retry the PaymentResponse.`);
|
||||
return;
|
||||
} catch(err) {
|
||||
is(err.name,
|
||||
"InvalidStateError",
|
||||
expectedErrMsg(testName, "InvalidStateError", err.name, "retrying"));
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
await requestChromeAction("finish-test");
|
||||
}
|
||||
|
||||
async function testRetryAfterRetry() {
|
||||
const testName = "testRetryAfterRetry";
|
||||
await requestChromeAction("start-test", testName);
|
||||
const payRequest = new PaymentRequest(defaultMethods, defaultDetails, options);
|
||||
ok(payRequest, testName + ": failed to create PaymentRequest.");
|
||||
if (!payRequest) {
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
const handler = SpecialPowers.getDOMWindowUtils(window).setHandlingUserInput(true);
|
||||
let payResponse;
|
||||
try {
|
||||
payResponse = await payRequest.show();
|
||||
await checkShowResponse(testName, payResponse);
|
||||
handler.destruct();
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "showing"));
|
||||
await requestChromeAction("finish-test");
|
||||
handler.destruct();
|
||||
return;
|
||||
}
|
||||
let retryPromise;
|
||||
try {
|
||||
retryPromise = payResponse.retry(validationErrors);
|
||||
await payResponse.retry(validationErrors);
|
||||
ok(false, `${testName}: Unexpected success when retry the PaymentResponse.`);
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
} catch(err) {
|
||||
is(err.name,
|
||||
"InvalidStateError",
|
||||
expectedErrMsg(testName, "InvalidStateError", err.name, "retrying"));
|
||||
}
|
||||
try {
|
||||
await retryPromise;
|
||||
await payResponse.complete("success");
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "completing"));
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
await requestChromeAction("finish-test");
|
||||
}
|
||||
|
||||
async function testRetryWithEmptyErrors() {
|
||||
const testName = "testRetryWithEmptyErrors";
|
||||
await requestChromeAction("start-test", testName);
|
||||
const payRequest = new PaymentRequest(defaultMethods, defaultDetails, options);
|
||||
ok(payRequest, testName + ": failed to create PaymentRequest.");
|
||||
if (!payRequest) {
|
||||
requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
const handler = SpecialPowers.getDOMWindowUtils(window).setHandlingUserInput(true);
|
||||
let payResponse;
|
||||
try {
|
||||
payResponse = await payRequest.show();
|
||||
await checkShowResponse(testName, payResponse);
|
||||
handler.destruct();
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "showing"));
|
||||
await requestChromeAction("finish-test");
|
||||
handler.destruct();
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await payResponse.retry();
|
||||
ok(false, `${testName}: Unexpected success when retry the PaymentResponse.`);
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
} catch(err) {
|
||||
is(err.name,
|
||||
"AbortError",
|
||||
expectedErrMsg(testName, "AbortError", err.name, "retrying"));
|
||||
}
|
||||
try {
|
||||
await payResponse.complete("success");
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "completing"));
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
await requestChromeAction("finish-test");
|
||||
}
|
||||
|
||||
async function testRetry() {
|
||||
const testName = "testRetry";
|
||||
await requestChromeAction("start-test", testName);
|
||||
const payRequest = new PaymentRequest(defaultMethods, defaultDetails, options);
|
||||
ok(payRequest, testName + ": failed to create PaymentRequest.");
|
||||
if (!payRequest) {
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
const handler = SpecialPowers.getDOMWindowUtils(window).setHandlingUserInput(true);
|
||||
let payResponse;
|
||||
try {
|
||||
payResponse = await payRequest.show();
|
||||
await checkShowResponse(testName, payResponse);
|
||||
handler.destruct();
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "showing"));
|
||||
await requestChromeAction("finish-test");
|
||||
handler.destruct();
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await payResponse.retry(validationErrors);
|
||||
await checkRetryResponse(testName, payResponse);
|
||||
await payResponse.complete("success");
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "retrying"));
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
await requestChromeAction("finish-test");
|
||||
}
|
||||
|
||||
async function testRetryAbortByUser() {
|
||||
const testName = "testRetryAbortByUser";
|
||||
await requestChromeAction("reject-retry");
|
||||
const payRequest = new PaymentRequest(defaultMethods, defaultDetails, options);
|
||||
ok(payRequest, testName + ": failed to create PaymentRequest.");
|
||||
if (!payRequest) {
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
const handler = SpecialPowers.getDOMWindowUtils(window).setHandlingUserInput(true);
|
||||
let payResponse;
|
||||
try {
|
||||
payResponse = await payRequest.show();
|
||||
await checkShowResponse(testName, payResponse);
|
||||
handler.destruct();
|
||||
} catch(err) {
|
||||
ok(false, unexpectedErrMsg(testName, err.name, "showing"));
|
||||
handler.destruct();
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
await payResponse.retry(validationErrors);
|
||||
ok(false, `${testName}: Unexpected success when retry the PaymentResponse.`);
|
||||
await requestChromeAction("finish-test");
|
||||
return;
|
||||
} catch(err) {
|
||||
is(err.name,
|
||||
"AbortError",
|
||||
expectedErrMsg(testName, "AbortError", err.name, "retrying"));
|
||||
}
|
||||
await requestChromeAction("finish-test");
|
||||
}
|
||||
|
||||
function teardown() {
|
||||
return new Promise((resolve, reject) => {
|
||||
gScript.addMessageListener("teardown-complete", function teardownCompleteHandler() {
|
||||
gScript.removeMessageListener("teardown-complete", teardownCompleteHandler);
|
||||
gScript.removeMessageListener("test-fail", testFailHandler);
|
||||
gScript.removeMessageListener("test-pass", testPassHandler);
|
||||
gScript.destroy();
|
||||
SimpleTest.finish();
|
||||
resolve();
|
||||
});
|
||||
gScript.sendAsyncMessage("teardown");
|
||||
});
|
||||
}
|
||||
|
||||
async function runTests() {
|
||||
try {
|
||||
await testRetryAfterComplete()
|
||||
await testRetryAfterRetry()
|
||||
await testRetryWithEmptyErrors()
|
||||
await testRetry()
|
||||
await testRetryAbortByUser()
|
||||
await teardown()
|
||||
} catch(e) {
|
||||
ok(false, "Unexpected error: " + e.name);
|
||||
SimpleTest.finish();
|
||||
}
|
||||
}
|
||||
|
||||
window.addEventListener('load', function() {
|
||||
SpecialPowers.pushPrefEnv({
|
||||
'set': [
|
||||
['dom.payments.request.enabled', true],
|
||||
]
|
||||
}, runTests);
|
||||
});
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1435161">Mozilla Bug 1435161</a>
|
||||
</body>
|
||||
</html>
|
Загрузка…
Ссылка в новой задаче