Comments (14)
Hey.
Are you calling setFinalizeAfter() on the last checkout page before entering your upsell gauntlet?
That will ensure the order is captured even if the browser is closed during the upsell.
from responsive_checkout.
Thank you for your instantaneous response!
Yes I am calling it ...Here's what I am doing
if (checkoutResult && checkoutResult.redirectToUrl) {
jQuery.cookie('UltraCartShoppingCartID', checkoutResult.cart.cartId, { expires: 7, path: '/' });
localStorage['redirectToUrl'] = checkoutResult.redirectToUrl;
finalizeAfter();
window.location.href = after_checkout_page;
##########################
function finalizeAfter() {
var finalizeCart = null;
var restUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart' : '/rest/cart';
if (!finalizeCart) {
jQuery.ajax({
url: restUrl,
headers: {'X-UC-Merchant-Id': merchantId,
"cache-control": "no-cache"},
dataType: 'json',
async: true
}).done(function (cart) {
finalizeCart = cart;
});
}
var restUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart/setFinalizeAfter' :'/rest/cart/setFinalizeAfter';
jQuery.ajax({
url: restUrl+"?minutes=20",
type: 'POST', // Notice
headers: { 'X-UC-Merchant-Id': merchantId, "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(finalizeCart),
dataType: 'json'
}).done(function (data, textStatus, jqXHR) {
var txt = jqXHR.status == 204
? "Server returned 204 'No Content', so the setFinalizeAfter was successful"
: "Error. setFinalizeAfter failed with this: " + textStatus;
var pre = jQuery('<pre>');
pre.text(txt);
jQuery('#finalizeResults').html('').append(pre);
});
}
I see that the var finalizeCart = null;
which is wrong I guess and how can I set the cart into that method? Please do let me know!
from responsive_checkout.
Hey. The big change you need is to nest the second rest call inside the first since they're both async. The second is probably firing before the first returns, so the finalizeCart is null. I've done away with finalizeCart entirely. It's not needed. Here's the untested code I've written:
function finalizeAfter() {
var restUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart' : '/rest/cart';
jQuery.ajax({
url: restUrl,
headers: {'X-UC-Merchant-Id': merchantId,
"cache-control": "no-cache"},
dataType: 'json',
async: true
}).done(function (cart) {
// beware the need for ?minutes or &minutes depending on proxy usage.
var finalizeUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart/setFinalizeAfter&minutes=20' : '/rest/cart/setFinalizeAfter?minutes=20'
jQuery.ajax({
url: finalizeUrl,
type: 'POST', // Notice
headers: { 'X-UC-Merchant-Id': merchantId, "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(cart),
dataType: 'json'
}).done(function (data, textStatus, jqXHR) {
var txt = jqXHR.status == 204
? "Server returned 204 'No Content', so the setFinalizeAfter was successful"
: "Error. setFinalizeAfter failed with this: " + textStatus;
var pre = jQuery('<pre>');
pre.text(txt);
jQuery('#finalizeResults').html('').append(pre);
});
});
}
from responsive_checkout.
Perry,
Thank you for your response. It doesn't even enter into the first done
call i..e here
}).done(function (cart) {
// NOT AT ALL ENTERING HERE
//Tried with console.log("test");
// beware the need for ?minutes or &minutes depending on proxy usage.
var finalizeUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart/setFinalizeAfter&minutes=20' : '/rest/cart/setFinalizeAfter?minutes=20'
Please do let me know. Once again, thank you very much for your time!
from responsive_checkout.
where's this page at? I'll need to see it and play with it to advise further.
from responsive_checkout.
Here's the page:
http://personallifemedia.com/uc1_test/test.html
from responsive_checkout.
@perrytew Did you get a chance to play around? :)
Please do help me!
from responsive_checkout.
Not yet. Between Black Friday and Christmas, the schedule can be somewhat
demanding.
I’ll have a look now.
from responsive_checkout.
Thanks a LOT! :)
from responsive_checkout.
Well, you've got the old code in there. I'll tell you again, your finalizeAfter has a race condition in it. You cannot call "get cart" and then "finalize after" right afterwards. Your finalizeCart is null. I saw this in the firebug network panel.
Look at my example above and try to implement it. You mention that it didn't work. Still, try to implement it, and then let's look at what the issue is there. If you're struggling with that, set the async: true => async: false in your first call within finalizeAfter (line 133). That's not best practice, but it should make the procedure work until you can get your feet.
Also, you might wish to call validate before you do finalizeAfter just to make sure everything is kosher before heading to the upsell. If you're not calling checkout, call validate, else a simple "missing field" is going to make everything fail silently behind the scenes.
Thanks,
Perry
from responsive_checkout.
Thank you very much for time, Perry!
Yup, after making async: false
it entered into the first call and now its not getting into the second call
}).done(function (data, textStatus, jqXHR) {
console.log("status2");
var txt = jqXHR.status == 204
? "Server returned 204 'No Content', so the setFinalizeAfter was successful"
: "Error. setFinalizeAfter failed with this: " + textStatus;
var pre = jQuery('<pre>');
pre.text(txt);
console.log(txt);
jQuery('#finalizeResults').html('').append(pre);
from responsive_checkout.
@perrytew When you get a could you please look into it? Also when a "upsell" has been configured inside "ultracart" and we add a "product" via responsive checkout ....does it break the in-built upsell funnel? Please do let me know. Once again, thank you very much for your time!
from responsive_checkout.
Strange. I updated this issue Friday night. Oh well. Here's the code again. I rewrote your order js file to make use of callbacks to avoid the race conditions. If you look at your code, you're calling finalizeOrder right before you set location.href. That finalize call will never complete before the page changes to the next page.
I haven't tested the code myself, so you'll want to examine it thoroughly. But the concepts are there, and I have a good editor. :)
var $j = jQuery.noConflict();
var merchantId = 'CPTX';
var i_am_using_a_proxy = true;
var pathToProxy = '/uc1_test/rest_proxy.php'; // relative or absolute. it doesn't matter.
// function createCart() {
// jQuery.ajax({
// url: '/rest_proxy.php?_url=/rest/cart',
// headers: {'X-UC-Merchant-Id': 'CPTX',
// "cache-control": "no-cache"},
// dataType: 'json'
// }).done(function (cart) {
// jQuery('#createCartResults').html('<pre>' + JSON.stringify(cart, null, ' ') + '</pre>');
// });
// }
// function addItems(product_code, upsell) {
// var items = [];
// items.push({'itemId': product_code, 'quantity': 1});
// var cart = {
// 'merchantId': 'CPTX',
// 'cartId': '', // will be populated by call
// 'items': items,
// 'upsell': upsell
// };
// jQuery.ajax({
// url: '/rest_proxy.php?_url=/rest/cart',
// type: 'PUT', // Notice
// headers: { "cache-control": "no-cache" },
// contentType: 'application/json; charset=UTF-8',
// data: JSON.stringify(cart),
// dataType: 'json'
// }).done(function (updatedCart) {
// // delete the last item and update the cart before displaying the results.
// //updatedCart.items.pop();
// jQuery.ajax({
// url: '/rest_proxy.php?_url=/rest/cart',
// type: 'PUT', // Notice, PUT == update
// headers: { "cache-control": "no-cache" },
// contentType: 'application/json; charset=UTF-8',
// data: JSON.stringify(updatedCart),
// dataType: 'json'
// }).done(function (cartWithTwoItems) {
// // can't use the following line because the cart (with items) will contain javascript strings the jQuery().html() will try to interpret.
// //jQuery('#addItemsResults').html('<pre>' + JSON.stringify(updatedCart, null, ' ') + '</pre>');
// var txt = JSON.stringify(cartWithTwoItems, null, ' ');
// var pre = jQuery('<pre>');
// pre.text(txt);
// jQuery('#addItemsResults').html('').append(pre);
// });
// });
// }
function checkout(product_code) {
var cart = {
'merchantId': merchantId,
'cartId': '',
"billToFirstName": $j("#shippingfirstname").val(),
"billToLastName": $j("#shippinglastname").val(),
"billToAddress1": $j("#shippingaddress1").val(),
"billToAddress2": "",
"billToCity": $j("#shippingcity").val(),
"billToState": $j("#shippingstate").val(),
"billToPostalCode": $j("#shippingzip").val(),
"billToCountry": $j("#shippingcountry").val(),
"email": $j("#email").val(),
"emailConfirm": $j("#email").val(),
"paymentMethod": $j("input[name='paymentMethod']:checked").val(),
"creditCardType": $j("#creditcardtype").val(),
"creditCardNumber": $j("#CC_num").val(),
"creditCardExpirationMonth": $j("#creditcardexpmonth").val(),
"creditCardExpirationYear": $j("#creditcardexpyear").val(),
"creditCardVerificationNumber": $j("#CC_cvv").val(),
'items': [
{'itemId': product_code, 'quantity': 1}
]
// if this is not a digital product, you're going to need shipping fields too...
};
// validate doesn't return back the cart, which we'll need to pass to finalize. So do a quick update here first
// to get a cart variable and a cart id assigned by the server.
updateCart(cart, function(cart){
validate(cart, finalizeAfter);
});
}
// a global variable will make this much easier...
var nextPage = 'upsell-page1.html';
function updateCart(cart, callback){
jQuery.ajax({
url: i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart' : '/rest/cart',
type: 'POST', // Notice
headers: { "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(cart),
dataType: 'json'
}).done(function (cart) {
callback(cart);
});
}
function validate(cart, callback){
jQuery.ajax({
url: i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart/validate' : '/rest/cart/validate',
type: 'POST', // Notice
headers: { "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(cart),
dataType: 'json'
}).done(function (errors) {
if(errors){
display_cart_errors(errors);
} else {
callback(cart);
}
});
}
function finalizeAfter(cart){
jQuery.ajax({
url: i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart/setFinalizeAfter&minutes=20' :'/rest/cart/setFinalizeAfter?minutes=20',
type: 'POST', // Notice
headers: { 'X-UC-Merchant-Id': merchantId, "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(finalizeCart),
dataType: 'json'
}).done(function (data, textStatus, jqXHR) {
if(jqXHR.status == 204){
location.href = nextPage;
}
});
}
function displayCart(cart) {
if (cart) {
var html = 'Cart: (' + cart.items.length + ') items, Total: $' + cart.total;
jQuery('#cart-summary').html(html);
}
}
function addToCart(itemId, next_page) {
var restUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart' :'/rest/cart';
// var restUrl = '/rest_proxy.php?_url=/rest/cart'; // you shouldn't change this.
if (itemId) {
if (!myCart) {
// this shouldn't happen, since loadCart should return back a valid cart. this code is here just in case.
myCart = {'merchantId': "CPTX", 'cartId': null}; // passing null will create a new cart for us.
}
if (!myCart.items) {
myCart['items'] = [];
}
myCart.items.push({itemId: itemId, quantity: 1});
jQuery.ajax({
url: restUrl,
type: 'POST', // Notice
headers: { "cache-control": "no-cache" },
contentType: 'application/json; charset=UTF-8',
data: JSON.stringify(myCart),
dataType: 'json'
}).done(function (cart) {
if(next_page != "")
window.location.href = next_page;
//displayCart(cart)
});
}
}
function loadCart() {
var restUrl = i_am_using_a_proxy ? pathToProxy + '?_url=/rest/cart' : '/rest/cart';
jQuery.ajax({
url: restUrl,
type: 'GET', // Notice
headers: { "cache-control": "no-cache", "X-UC-Merchant-Id": merchantId },
dataType: 'json'
}).done(function (cart) {
if (cart && cart.cartId) {
window.myCart = cart;
jQuery.cookie('UltraCartShoppingCartID', cart.cartId, { expires: 7, path: '/' });
displayCart(cart);
}
});
}
function display_cart_errors(errors)
{
error_list_html = '';
if (errors.length != 0) {
for(var i = 0; i < errors.length; i ++)
{
error_list_html += '<li>' + errors[i] + '</li>';
}
$j('.errors ol').html(error_list_html);
$j('.errors').show(250);
window.setTimeout(scroll_to_errors, 500);
}else{
$j('.errors').hide();
}
}
function scroll_to_errors()
{
$j('html,body').animate({scrollTop: $j('.errors h4').offset().top -20}, 1500);
}
from responsive_checkout.
Thanks Perry for your time and this can be closed! Once again thanks a lot!
from responsive_checkout.
Related Issues (20)
- Checkout Registration HOT 2
- Microsoft Edge HOT 3
- Turn Off Billing City / Zip Validation HOT 1
- CC Hosted Fields Iframes - Loads slow in some systems HOT 13
- Custom Receipt Page HOT 7
- Testing Credit Card Failed Attempt Limit Feature HOT 2
- Missing Hosted Fields (CC Number and CVV) HOT 10
- Order ID / Authorize Transaction ID Passed Back to Cart HOT 3
- Payment Declined but Receipt is generated in Ultracart HOT 2
- Using the new rest_proxy.php script with legacy catalog-structured merchant accounts HOT 3
- responsive_checkout HOT 13
- item.html
- I cant run commands giving error HOT 10
- Checkout is not working HOT 8
- upsell custom page setFinalizeAfter HOT 1
- How do I get the value of the credit card type HOT 3
- Load additional states/provinces when the country changes
- International Orders Outside US, Canada, Australia or Manual State/Province Method Needed HOT 2
- Delete Coupons Function
- credit card field values are missing HOT 3
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from responsive_checkout.