Clear Product After 10 Minutes

Description

#1. Install Code

#1.1. You can use this code to Code Injection > Footer

<!-- 07.26c22v1 Clear Product After 10 Minutes -->
<script>
window.CartAutoClearConfig = {
  minutes: 0.1,
  clearOnNewSession: true,
  resetTimerOnCartChange: true,
  debug: true
};
</script>
<script>
(function () {
  'use strict';

  if (window.top !== window.self) return;

  var cfg = window.CartAutoClearConfig;
  if (!cfg) return;

  var TS_KEY = 'ssCacTs';
  var QTY_KEY = 'ssCacQty';
  var SESSION_KEY = 'ssCacSession';
  var PENDING_KEY = 'ssCacPending';
  var timerId = null;
  var evalDebounce = null;
  var clearing = false;

  function log() {
    if (!cfg.debug) return;
    var a = Array.prototype.slice.call(arguments);
    a.unshift('[CAC]');
    console.log.apply(console, a);
  }

  function isEditMode() {
    return document.body && document.body.classList.contains('sqs-edit-mode-active');
  }

  function isCartPage() {
    return (document.body && document.body.id === 'cart') || !!document.getElementById('sqs-cart-root');
  }

  function isCheckout() {
    return /checkout/i.test(location.pathname);
  }

  function windowMs() {
    return (Number(cfg.minutes) || 10) * 60000;
  }

  function parseCartFromDoc(doc) {
    var s = doc.querySelector('#sqs-cart-root script[type="application/json"]');
    if (!s) return null;
    try { return JSON.parse(s.textContent); } catch (e) { return null; }
  }

  async function getCart() {
    if (isCartPage()) {
      var local = parseCartFromDoc(document);
      if (local) return local;
    }
    try {
      var res = await fetch('/cart', { credentials: 'same-origin' });
      var text = await res.text();
      var doc = new DOMParser().parseFromString(text, 'text/html');
      return parseCartFromDoc(doc);
    } catch (e) {
      return null;
    }
  }

  function entryIds(cart) {
    if (!cart || !cart.cart || !Array.isArray(cart.cart.items)) return [];
    return cart.cart.items.map(function (i) { return i.id; }).filter(Boolean);
  }

  function totalQty(cart) {
    if (!cart || !cart.cart || !Array.isArray(cart.cart.items)) return 0;
    return cart.cart.items.reduce(function (n, i) { return n + (Number(i.quantity) || 0); }, 0);
  }

  function updateBadges() {
    document.querySelectorAll('.sqs-cart-quantity').forEach(function (el) { el.textContent = '0'; });
  }

  function clearState() {
    localStorage.removeItem(TS_KEY);
    localStorage.removeItem(QTY_KEY);
  }

  function runClear(doc, resolve) {
    var tries = 0;
    var sawButtons = false;
    var iv = setInterval(function () {
      tries++;
      var btns, rows;
      try {
        btns = doc.querySelectorAll('.cart-row-remove, [data-test="remove-item"]');
        rows = doc.querySelectorAll('[data-testid="cart-table-row"], .cart-row');
      } catch (e) {
        clearInterval(iv);
        resolve(false);
        return;
      }

      if (btns.length) {
        sawButtons = true;
        btns[0].click();
        return;
      }

      if (sawButtons && rows.length === 0) {
        clearInterval(iv);
        resolve(true);
        return;
      }

      if (!sawButtons) {
        var c = parseCartFromDoc(doc);
        if (c && entryIds(c).length === 0) {
          clearInterval(iv);
          resolve(true);
          return;
        }
      }

      if (tries > 90) {
        clearInterval(iv);
        resolve(sawButtons && btns.length === 0);
      }
    }, 350);
  }

  function clearViaIframe() {
    return new Promise(function (resolve) {
      var iframe = document.createElement('iframe');
      iframe.setAttribute('aria-hidden', 'true');
      iframe.style.cssText = 'position:absolute;width:0;height:0;border:0;left:-9999px;top:-9999px;opacity:0;';
      iframe.src = '/cart';

      var settled = false;
      function finish(ok) {
        if (settled) return;
        settled = true;
        clearTimeout(hardStop);
        try { iframe.remove(); } catch (e) {}
        resolve(ok);
      }

      var hardStop = setTimeout(function () { finish(false); }, 35000);

      iframe.onload = function () {
        var doc;
        try {
          doc = iframe.contentDocument || iframe.contentWindow.document;
        } catch (e) {
          finish(false);
          return;
        }
        if (!doc) { finish(false); return; }
        runClear(doc, finish);
      };

      document.body.appendChild(iframe);
    });
  }

  async function clearCart(reason) {
    if (clearing) return;
    clearing = true;
    log('clear triggered:', reason);

    var cart = await getCart();
    if (!entryIds(cart).length) {
      clearState();
      localStorage.removeItem(PENDING_KEY);
      clearing = false;
      return;
    }

    if (isCartPage()) {
      runClear(document, function (ok) {
        if (ok) {
          clearState();
          localStorage.removeItem(PENDING_KEY);
          updateBadges();
          log('cleared on cart page');
        }
        clearing = false;
      });
      return;
    }

    var ok = await clearViaIframe();
    if (ok) {
      clearState();
      localStorage.removeItem(PENDING_KEY);
      updateBadges();
      log('cleared via iframe');
    } else {
      localStorage.setItem(PENDING_KEY, '1');
      log('iframe clear failed, deferred to cart page');
    }
    clearing = false;
  }

  function schedule(remaining) {
    if (timerId) clearTimeout(timerId);
    timerId = setTimeout(function () { clearCart('timer'); }, Math.max(0, remaining));
    log('scheduled clear in', Math.round(remaining / 1000), 's');
  }

  async function evaluate() {
    if (isCheckout() || isEditMode()) return;

    var cart = await getCart();
    var ids = entryIds(cart);
    var qty = totalQty(cart);

    if (!ids.length) {
      clearState();
      return;
    }

    if (cfg.clearOnNewSession && !sessionStorage.getItem(SESSION_KEY)) {
      sessionStorage.setItem(SESSION_KEY, '1');
      clearCart('new-session');
      return;
    }
    if (!sessionStorage.getItem(SESSION_KEY)) sessionStorage.setItem(SESSION_KEY, '1');

    var ts = Number(localStorage.getItem(TS_KEY)) || 0;
    var lastQty = Number(localStorage.getItem(QTY_KEY));

    if (!ts || (cfg.resetTimerOnCartChange && qty !== lastQty)) {
      ts = Date.now();
    }
    localStorage.setItem(TS_KEY, String(ts));
    localStorage.setItem(QTY_KEY, String(qty));

    var remaining = windowMs() - (Date.now() - ts);
    if (remaining <= 0) {
      clearCart('expired');
      return;
    }
    schedule(remaining);
  }

  function queueEvaluate() {
    if (evalDebounce) clearTimeout(evalDebounce);
    evalDebounce = setTimeout(evaluate, 400);
  }

  function watchBadge() {
    var box = document.querySelector('.icon-cart-quantity') || document.body;
    var obs = new MutationObserver(queueEvaluate);
    obs.observe(box, { childList: true, subtree: true, characterData: true });
  }

  function handlePending(done) {
    if (isCartPage() && localStorage.getItem(PENDING_KEY)) {
      runClear(document, function () {
        localStorage.removeItem(PENDING_KEY);
        clearState();
        updateBadges();
        if (done) done();
      });
      return true;
    }
    return false;
  }

  function init() {
    if (isEditMode()) return;
    if (document.documentElement.dataset.cacDone === '1') {
      if (!handlePending()) evaluate();
      return;
    }
    document.documentElement.dataset.cacDone = '1';
    watchBadge();
    if (!handlePending(evaluate)) evaluate();
  }

  window.addEventListener('load', init);
  window.addEventListener('mercury:load', init);
})();
</script>

07.26c22v1 Clear Product After 10 Minutes

#1.2. Update Minutes here

  • 0.1 = 10 seconds
  • if you want to set 10 minutes, just change 0.1 to 10
minutes: 0.1,

07.26c22v1 Clear Product After 10 Minutes

#2. Customize

nothing now

Buy me a coffee