/*global wc_geolocation_params */ jQuery( function( $ ) { /** * Contains the current geo hash (or false if the hash * is not set/cannot be determined). * * @type {boolean|string} */ var geo_hash = false; /** * Obtains the current geo hash from the `woocommerce_geo_hash` cookie, if set. * * @returns {boolean} */ function get_geo_hash() { var geo_hash_cookie = Cookies.get( 'woocommerce_geo_hash' ); if ( 'string' === typeof geo_hash_cookie && geo_hash_cookie.length ) { geo_hash = geo_hash_cookie; return true; } return false; } /** * If we have an active geo hash value but it does not match the `?v=` query var in * current page URL, that indicates that we need to refresh the page. * * @returns {boolean} */ function needs_refresh() { return geo_hash && ( new URLSearchParams( window.location.search ) ).get( 'v' ) !== geo_hash; } /** * Appends (or replaces) the geo hash used for links on the current page. */ var $append_hashes = function() { if ( ! geo_hash ) { return; } $( 'a[href^="' + wc_geolocation_params.home_url + '"]:not(a[href*="v="]), a[href^="/"]:not(a[href*="v="])' ).each( function() { var $this = $( this ), href = $this.attr( 'href' ), href_parts = href.split( '#' ); href = href_parts[0]; if ( href.indexOf( '?' ) > 0 ) { href = href + '&v=' + geo_hash; } else { href = href + '?v=' + geo_hash; } if ( typeof href_parts[1] !== 'undefined' && href_parts[1] !== null ) { href = href + '#' + href_parts[1]; } $this.attr( 'href', href ); }); }; var $geolocate_customer = { url: wc_geolocation_params.wc_ajax_url.toString().replace( '%%endpoint%%', 'get_customer_location' ), type: 'GET', success: function( response ) { if ( response.success && response.data.hash && response.data.hash !== geo_hash ) { $geolocation_redirect( response.data.hash ); } } }; /** * Once we have a new hash, we redirect so a new version of the current page * (with correct pricing for the current region, etc) is displayed. * * @param {string} hash */ var $geolocation_redirect = function( hash ) { // Updates our (cookie-based) cache of the hash value. Expires in 1 hour. Cookies.set( 'woocommerce_geo_hash', hash, { expires: 1 / 24 } ); const urlQuery = new URL( window.location ).searchParams; const existingHash = urlQuery.get( 'v' ); // If the current URL does not contain the expected hash, redirect. if ( existingHash !== hash ) { urlQuery.set( 'v', hash ); window.location.search = '?' + urlQuery.toString(); } }; /** * Updates any forms on the page so they use the current geo hash. */ function update_forms() { if ( ! geo_hash ) { return; } $( 'form' ).each( function () { var $this = $( this ); var method = $this.attr( 'method' ); var hasField = $this.find( 'input[name="v"]' ).length > 0; if ( method && 'get' === method.toLowerCase() && ! hasField ) { $this.append( '' ); } else { var href = $this.attr( 'action' ); if ( href ) { if ( href.indexOf( '?' ) > 0 ) { $this.attr( 'action', href + '&v=' + geo_hash ); } else { $this.attr( 'action', href + '?v=' + geo_hash ); } } } }); } // Get the current geo hash. If it doesn't exist, or if it doesn't match the current // page URL, perform a geolocation request. if ( ! get_geo_hash() || needs_refresh() ) { $.ajax( $geolocate_customer ); } // Page updates. update_forms(); $append_hashes(); $( document.body ).on( 'added_to_cart', function() { $append_hashes(); }); // Enable user to trigger manual append hashes on AJAX operations $( document.body ).on( 'woocommerce_append_geo_hashes', function() { $append_hashes(); }); });