/**
* Aelia Currency Switcher, Prices by Country, Tax Display by Country
* --
* Integration with the "cart" and "checkout" blocks provided by WooCommerce Blocks.
*
* THIS CODE IS PROVIDED AS A PROOF OF CONCEPT. Please make sure to read all the documentation,
* below, before using it.
*
* GPL DISCLAIMER
* THE USE OF THIS CODE IS AS YOUR OWN RISK.
* This code is provided free of charge and comes without any warranty, implied or explicit, to the extent permitted
* by applicable law. Except when otherwise stated in writing the copyright holders and/or other parties provide the
* program "as is" without warranty of any kind, either expressed or implied, including, but not limited to, the implied
* warranties of merchantability and fitness for a particular purpose. The entire risk as to the quality and performance
* of the program is with you. Should the program prove defective, you assume the cost of all necessary servicing, repair
* or correction.
*
* Need a consultation, or assistance to customise this code? Find us on Codeable: https://aelia.co/hire_us
*
* BACKGROUND
* On a "plain" WooCommerce setup, changing fields like billing and shipping country on the
* cart and checkout page triggers a call to the site to refresh the cart contents. The Aelia
* plugins intercept this call, check which country was selected and set customer's country and
* currency accordingly.
*
* For some reason, the WooCommerce Blocks plugin follows a different approach. Rather than the
* standard call used by WooCommerce, that plugin uses a custom REST API to update the shipping
* details. The Aelia plugins are not aware of that call, therefore they can't "see" that the
* address changed.
*
* Unfortunately, the WooCommerce Blocks plugin is still quite rigid and doesn't offer events
* that can be intercepted to detect the change. Due to that, a more "rustic" approach is needed,
* to listen for the specific REST calls it makes.
*
* CAVEATS
* - This code listens for the "shipping country" change. When this code was written (29 May 2020),
* the WooCommerce Blocks plugin didn't seem to trigger any event when the BILLING country.
* - This code doesn't check if the Aelia plugins are supposed to use the shipping country or the
* billing country. Since the WooCommerce Blocks plugin only triggers a call on "shipping address change",
* this code takes such country and uses it to set customer's country.
*
* IMPLEMENTATION
* For this code snippet to work, you will probably have to wrap it into a mini-plugin. You can
* do that as follows:
*
* 1. Create a file called your-plugin-name file in the new subfolder.
* 2. Add a plugin header to the file: https://developer.wordpress.org/plugins/plugin-basics/header-requirements/.
* You can just set it to "Plugin Name: YOUR PLUGIN NAME".
* 3. Add your custom code below the plugin header.
* 4. Save the file.
* 5. Create a folder called wp-content/plugins/your-plugin-name on your site (e.g. via FTP).
* 6. Enter the new folder.
* 7. Upload the file you just created.
* 8. Go to WordPress > Plugins to enable the custom plugin.
*
* By doing this, the custom code will be loaded together with the other plugin. That will be much earlier than
* file "functions.php", and it will ensure that the custom code will be loaded soon enough.
*/
add_filter('woocommerce_rest_is_request_to_rest_api', function($is_request_to_rest_api) {
if($is_request_to_rest_api) {
// Extract the path to the REST API
$rest_api_path = parse_url(esc_url_raw(wp_unslash($_SERVER['REQUEST_URI'])), PHP_URL_PATH);
// Check if the path matches the "update shipping" call made by the WooCommerce Blocks plugin
if(substr_compare($rest_api_path, '/wc/store/cart/update-shipping', -strlen('/wc/store/cart/update-shipping')) === 0) {
// Extract and decode the posted data
// @see WC_API_Server::get_raw_data()
$raw_body = file_get_contents('php://input');
$body = json_decode($raw_body, true);
// If a country was posted, simulate a "country selection". This will allow
// the Aelia plugins to pick it up automatically
if(!empty($body['country'])) {
$_POST['aelia_customer_country'] = $body['country'];
}
}
}
return $is_request_to_rest_api;
}, 1, 3);
Comments