From 590a9a2c59832bb2eaa8faaf03ad2fdae2849265 Mon Sep 17 00:00:00 2001 From: mattab Date: Fri, 8 Jul 2016 14:51:44 +1200 Subject: [PATCH] Reset the list of items in the cart, after tracking an ecommerce conversion But do not reset the list of itms in the cart after tracking an ecommerce cart update. fixes #10252 --- js/piwik.js | 12 ++++++++++-- piwik.js | 2 +- tests/javascript/index.php | 11 +++++++++-- 3 files changed, 20 insertions(+), 5 deletions(-) diff --git a/js/piwik.js b/js/piwik.js index bed97aa65f8..3422a71afc4 100644 --- a/js/piwik.js +++ b/js/piwik.js @@ -3970,9 +3970,10 @@ if (typeof window.Piwik !== 'object') { lastEcommerceOrderTs, now = new Date(), items = [], - sku; + sku, + isEcommerceOrder = String(orderId).length; - if (String(orderId).length) { + if (isEcommerceOrder) { request += '&ec_id=' + encodeWrapper(orderId); // Record date of order in the visitor cookie lastEcommerceOrderTs = Math.round(now.getTime() / 1000); @@ -4028,6 +4029,10 @@ if (typeof window.Piwik !== 'object') { } request = getRequest(request, configCustomData, 'ecommerce', lastEcommerceOrderTs); sendRequest(request, configTrackerPause); + + if (isEcommerceOrder) { + ecommerceItems = {}; + } } function logEcommerceOrder(orderId, grandTotal, subTotal, tax, shipping, discount) { @@ -6320,6 +6325,7 @@ if (typeof window.Piwik !== 'object') { * Adds an item (product) that is in the current Cart or in the Ecommerce order. * This function is called for every item (product) in the Cart or the Order. * The only required parameter is sku. + * The items are deleted from this JavaScript object when the Ecommerce order is tracked via the method trackEcommerceOrder. * * @param string sku (required) Item's SKU Code. This is the unique identifier for the product. * @param string name (optional) Item's name @@ -6338,6 +6344,7 @@ if (typeof window.Piwik !== 'object') { * If the Ecommerce order contains items (products), you must call first the addEcommerceItem() for each item in the order. * All revenues (grandTotal, subTotal, tax, shipping, discount) will be individually summed and reported in Piwik reports. * Parameters orderId and grandTotal are required. For others, you can set to false if you don't need to specify them. + * After calling this method, items added to the cart will be deleted. * * @param string|int orderId (required) Unique Order ID. * This will be used to count this order only once in the event the order page is reloaded several times. @@ -6356,6 +6363,7 @@ if (typeof window.Piwik !== 'object') { * Tracks a Cart Update (add item, remove item, update item). * On every Cart update, you must call addEcommerceItem() for each item (product) in the cart, including the items that haven't been updated since the last cart update. * Then you can call this function with the Cart grandTotal (typically the sum of all items' prices) + * Calling this method does not remove from this JavaScript object the items that were added to the cart via addEcommerceItem * * @param float grandTotal (required) Items (products) amount in the Cart */ diff --git a/piwik.js b/piwik.js index 4e2285c843c..3bf3250eac9 100644 --- a/piwik.js +++ b/piwik.js @@ -44,7 +44,7 @@ if(bh.length){cB[1]=bh}return cB}if(bh.length){cA=bh}else{if("0"===bx()){cA=""}e }function aj(){var cz=aT;aT=false;var cx=["id","ses","cvar","ref"];var cy,cA;for(cy=0;cycW){cN.visitCount++;cN.lastVisitTs=cN.currentVisitTs}if(!a1||!cF.length){for(cT in bS){if(Object.prototype.hasOwnProperty.call(bS,cT)){cF=M(cX,bS[cT]); if(cF.length){break}}}for(cT in ba){if(Object.prototype.hasOwnProperty.call(ba,cT)){cx=M(cX,ba[cT]);if(cx.length){break}}}}c0=c(aV);cI=cS.length?c(cS):"";if(c0.length&&!ay(c0)&&(!a1||!cI.length||ay(cI))){cS=aV}if(cS.length||cF.length){cE=cH;cR=[cF,cx,cE,bu(cS.slice(0,cB))];ct(cO,JSON2.stringify(cR),cm,aX,cg)}}cz+="&idsite="+by+"&rec=1&r="+String(Math.random()).slice(2,8)+"&h="+cy.getHours()+"&m="+cy.getMinutes()+"&s="+cy.getSeconds()+"&url="+n(bu(cX))+(aV.length?"&urlref="+n(bu(aV)):"")+((a4&&a4.length)?"&uid="+n(a4):"")+"&_id="+cN.uuid+"&_idts="+cN.createTs+"&_idvc="+cN.visitCount+"&_idn="+cN.newVisitor+(cF.length?"&_rcn="+n(cF):"")+(cx.length?"&_rck="+n(cx):"")+"&_refts="+cE+"&_viewts="+cN.lastVisitTs+(String(cN.lastEcommerceOrderTs).length?"&_ects="+cN.lastEcommerceOrderTs:"")+(String(cS).length?"&_ref="+n(bu(cS.slice(0,cB))):"")+(cK?"&cs="+n(cK):"")+"&send_image=0";for(cT in co){if(Object.prototype.hasOwnProperty.call(co,cT)){cz+="&"+cT+"="+co[cT]}}var cZ=[];if(cU){for(cT in cU){if(Object.prototype.hasOwnProperty.call(cU,cT)&&/^dimension\d+$/.test(cT)){var cD=cT.replace("dimension",""); cZ.push(parseInt(cD,10));cZ.push(String(cD));cz+="&"+cT+"="+cU[cT];delete cU[cT]}}}if(cU&&t(cU)){cU=null}for(cT in aU){if(Object.prototype.hasOwnProperty.call(aU,cT)){var cJ=(-1===cZ.indexOf(cT));if(cJ){cz+="&dimension"+cT+"="+aU[cT]}}}if(cU){cz+="&data="+n(JSON2.stringify(cU))}else{if(Y){cz+="&data="+n(JSON2.stringify(Y))}}function cG(c1,c2){var c3=JSON2.stringify(c1);if(c3.length>2){return"&"+c2+"="+n(c3)}return""}var cY=cw(bo);var cP=cw(bN);cz+=cG(cY,"cvar");cz+=cG(cP,"e_cvar");if(at){cz+=cG(at,"_cvar");for(cT in cQ){if(Object.prototype.hasOwnProperty.call(cQ,cT)){if(at[cT][0]===""||at[cT][1]===""){delete at[cT]}}}if(bj){ct(cL,JSON2.stringify(at),bQ,aX,cg)}}if(aE){if(bO){cz+=">_ms="+bO}else{if(g&&g.timing&&g.timing.requestStart&&g.timing.responseEnd){cz+=">_ms="+(g.timing.responseEnd-g.timing.requestStart)}}}cN.lastEcommerceOrderTs=A(cA)&&String(cA).length?cA:cN.lastEcommerceOrderTs;ao(cN);bF();cz+=R(cV);if(ci.length){cz+="&"+ci}if(s(bD)){cz=bD(cz)}return cz}bk=function aI(){var cx=new Date(); -if(ch+aH<=cx.getTime()){var cy=bT("ping=1",null,"ping");a9(cy,bc);return true}return false};function aY(cA,cz,cE,cB,cx,cH){var cC="idgoal=0",cD,cy=new Date(),cF=[],cG;if(String(cA).length){cC+="&ec_id="+n(cA);cD=Math.round(cy.getTime()/1000)}cC+="&revenue="+cz;if(String(cE).length){cC+="&ec_st="+cE}if(String(cB).length){cC+="&ec_tx="+cB}if(String(cx).length){cC+="&ec_sh="+cx}if(String(cH).length){cC+="&ec_dt="+cH}if(cj){for(cG in cj){if(Object.prototype.hasOwnProperty.call(cj,cG)){if(!A(cj[cG][1])){cj[cG][1]=""}if(!A(cj[cG][2])){cj[cG][2]=""}if(!A(cj[cG][3])||String(cj[cG][3]).length===0){cj[cG][3]=0}if(!A(cj[cG][4])||String(cj[cG][4]).length===0){cj[cG][4]=1}cF.push(cj[cG])}}cC+="&ec_items="+n(JSON2.stringify(cF))}cC=bT(cC,Y,"ecommerce",cD);a9(cC,bc)}function br(cx,cB,cA,cz,cy,cC){if(String(cx).length&&A(cB)){aY(cx,cB,cA,cz,cy,cC)}}function aZ(cx){if(A(cx)){aY("",cx,"","","","")}}function bs(cy,cA,cz){var cx=bT("action_name="+n(X(cy||aR)),cA,"log");a9(cx,bc,cz)}function aC(cz,cy){var cA,cx="(^| )(piwik[_-]"+cy; +if(ch+aH<=cx.getTime()){var cy=bT("ping=1",null,"ping");a9(cy,bc);return true}return false};function aY(cA,cz,cF,cB,cx,cI){var cD="idgoal=0",cE,cy=new Date(),cG=[],cH,cC=String(cA).length;if(cC){cD+="&ec_id="+n(cA);cE=Math.round(cy.getTime()/1000)}cD+="&revenue="+cz;if(String(cF).length){cD+="&ec_st="+cF}if(String(cB).length){cD+="&ec_tx="+cB}if(String(cx).length){cD+="&ec_sh="+cx}if(String(cI).length){cD+="&ec_dt="+cI}if(cj){for(cH in cj){if(Object.prototype.hasOwnProperty.call(cj,cH)){if(!A(cj[cH][1])){cj[cH][1]=""}if(!A(cj[cH][2])){cj[cH][2]=""}if(!A(cj[cH][3])||String(cj[cH][3]).length===0){cj[cH][3]=0}if(!A(cj[cH][4])||String(cj[cH][4]).length===0){cj[cH][4]=1}cG.push(cj[cH])}}cD+="&ec_items="+n(JSON2.stringify(cG))}cD=bT(cD,Y,"ecommerce",cE);a9(cD,bc);if(cC){cj={}}}function br(cx,cB,cA,cz,cy,cC){if(String(cx).length&&A(cB)){aY(cx,cB,cA,cz,cy,cC)}}function aZ(cx){if(A(cx)){aY("",cx,"","","","")}}function bs(cy,cA,cz){var cx=bT("action_name="+n(X(cy||aR)),cA,"log");a9(cx,bc,cz)}function aC(cz,cy){var cA,cx="(^| )(piwik[_-]"+cy; if(cz){for(cA=0;cA([0-9]+)\<\/span\>/.exec(results))[1], "36", "count tracking events" ); // firing callback ok( trackLinkCallbackFired, "trackLink() callback fired" ); @@ -3428,6 +3432,9 @@ function getLastInteractionType() { return lastInteractionType; } // Cart update ok( /idgoal=0&revenue=555.55&ec_items=%5B%5B%22SKU%20PRODUCT%22%2C%22random%22%2C%22random%20PRODUCT%20CATEGORY%22%2C11.1111%2C2%5D%2C%5B%22SKU%20ONLY%20SKU%22%2C%22%22%2C%22%22%2C0%2C1%5D%2C%5B%22SKU%20ONLY%20NAME%22%2C%22PRODUCT%20NAME%202%22%2C%22%22%2C0%2C1%5D%2C%5B%22SKU%20NO%20PRICE%20NO%20QUANTITY%22%2C%22PRODUCT%20NAME%203%22%2C%22CATEGORY%22%2C0%2C1%5D%2C%5B%22SKU%20ONLY%22%2C%22%22%2C%22%22%2C0%2C1%5D%5D/.test( results ), "logEcommerceCartUpdate() with items" ); + // Ecommerce order recorded twice, but each order empties the cart/list of items, so this order is empty of items + ok( /idgoal=0&ec_id=ORDER%20WITHOUT%20ANY%20ITEM&revenue=777&ec_st=444&ec_tx=222&ec_sh=111&ec_dt=1&ec_items=%5B%5D/.test( results ), "logEcommerceOrder() called twice, second time has no item" ); + // parameters inserted by plugin hooks ok( /testlog/.test( results ), "plugin hook log" ); ok( /testlink/.test( results ), "plugin hook link" );