Parcourir la source

Harden cart total i18n override against bundle clobber — v1.5.13 -> v1.5.14

The 1.5.13 inline override ran via `after wp-i18n`, before WC's
wc-cart-checkout-base-js-translations bundle, which then called
wp.i18n.setLocaleData with "Estimated total":["Odhadovaný součet"]
and merged over our entry — so the cart page still read the default.

Fix: re-apply the override as an after-inline script on both
wc-cart-checkout-base and wc-cart-block-frontend handles (both run
*after* the translations bundle merges its data), plus a
DOMContentLoaded safety net. Our value now wins regardless of script
ordering.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Dalibor Votruba il y a 2 mois
Parent
commit
c9cbb9d764

+ 1 - 1
studiou-wc-free-photo-product/CLAUDE.md

@@ -2,7 +2,7 @@
 
 ## Project Overview
 
-WordPress/WooCommerce plugin called **studiou-wc-free-photo-product** (QDR - Studiou WC Free Photo Product) v1.5.13.
+WordPress/WooCommerce plugin called **studiou-wc-free-photo-product** (QDR - Studiou WC Free Photo Product) v1.5.14.
 Allows publishing special variable products where customers upload custom raw images to be printed for a price.
 
 ## Initial Requirements

+ 1 - 1
studiou-wc-free-photo-product/languages/studiou-wc-free-photo-product-cs_CZ.po

@@ -3,7 +3,7 @@
 # This file is distributed under the GPL v2 or later.
 msgid ""
 msgstr ""
-"Project-Id-Version: QDR - Studiou WC Free Photo Product 1.5.13\n"
+"Project-Id-Version: QDR - Studiou WC Free Photo Product 1.5.14\n"
 "Report-Msgid-Bugs-To: https://www.quadarax.com\n"
 "POT-Creation-Date: 2026-04-02 00:00+0000\n"
 "PO-Revision-Date: 2026-04-02 00:00+0000\n"

+ 1 - 1
studiou-wc-free-photo-product/languages/studiou-wc-free-photo-product.pot

@@ -2,7 +2,7 @@
 # This file is distributed under the GPL v2 or later.
 msgid ""
 msgstr ""
-"Project-Id-Version: QDR - Studiou WC Free Photo Product 1.5.13\n"
+"Project-Id-Version: QDR - Studiou WC Free Photo Product 1.5.14\n"
 "Report-Msgid-Bugs-To: https://www.quadarax.com\n"
 "POT-Creation-Date: 2026-04-02 00:00+0000\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"

+ 4 - 0
studiou-wc-free-photo-product/readme.md

@@ -2,6 +2,10 @@
 
 WordPress (6.9.4+) / WooCommerce (10.6.2+) plugin that allows publishing special variable products with custom raw image upload for photo printing. Customers upload one or more photos on the product page and compose an order where each uploaded photo can be printed in a different variant at its own quantity. Uploaded files are stored in the WordPress media library under a configurable media category.
 
+## What's new in 1.5.14
+
+- **Cart "Estimated total" rename hardened against clobber.** The 1.5.13 override on `wp-i18n` ran *before* WC's `wc-cart-checkout-base-js-translations` inline bundle, which then merged its own `"Estimated total": ["Odhadovaný součet"]` locale data on top and restored the original text. Now re-applies the override as an `after`-inline script on `wc-cart-checkout-base` (and `wc-cart-block-frontend`), plus a DOMContentLoaded safety net, so our value wins regardless of script order.
+
 ## What's new in 1.5.13
 
 - **Cart "Estimated total" rename now actually reaches the block cart.** The 1.5.12 `gettext_woocommerce` PHP filter only catches PHP-rendered strings, but the WC block cart is React-rendered and pulls its labels from a separate `wc-cart-checkout-base-js-translations` bundle via `wp.i18n.__()`. Added an inline script on the `wp-i18n` handle that calls `wp.i18n.setLocaleData({ 'Estimated total': […] }, 'woocommerce')` as soon as wp-i18n loads, overriding the bundled Czech translation "Odhadovaný součet" with our own. Translation value still lives in our .po so it's locale-aware. Also remapped "Cart totals" for consistency.

+ 32 - 10
studiou-wc-free-photo-product/studiou-wc-free-photo-product.php

@@ -3,7 +3,7 @@
  * Plugin Name: QDR - Studiou WC Free Photo Product
  * Plugin URI: https://www.quadarax.com/plugins/studiou-wc-free-photo-product
  * Description: Allows publishing special WooCommerce products with variants and custom raw image upload for photo printing
- * Version: 1.5.13
+ * Version: 1.5.14
  * Requires at least: 6.9.4
  * Requires PHP: 8.2
  * Requires Plugins: woocommerce, product-variant-table-for-woocommerce
@@ -22,7 +22,7 @@ if (!defined('WPINC')) {
     die;
 }
 
-if (!defined('STUDIOU_WCFPP_VERSION')) define('STUDIOU_WCFPP_VERSION', '1.5.13');
+if (!defined('STUDIOU_WCFPP_VERSION')) define('STUDIOU_WCFPP_VERSION', '1.5.14');
 if (!defined('STUDIOU_WCFPP_PLUGIN_DIR')) define('STUDIOU_WCFPP_PLUGIN_DIR', plugin_dir_path(__FILE__));
 if (!defined('STUDIOU_WCFPP_PLUGIN_URL')) define('STUDIOU_WCFPP_PLUGIN_URL', plugin_dir_url(__FILE__));
 if (!defined('STUDIOU_WCFPP_PLUGIN_BASENAME')) define('STUDIOU_WCFPP_PLUGIN_BASENAME', plugin_basename(__FILE__));
@@ -248,18 +248,40 @@ class Studiou_WC_Free_Photo_Product {
     public function register_frontend_assets() {
         // WC block cart ("Estimated total" etc.) is React-rendered and pulls its strings
         // from wp.i18n in the browser — the PHP gettext_woocommerce filter never fires for
-        // those strings. Patch the translation on the JS side: after wp-i18n loads, and
-        // before the cart block renders, replace the 'Estimated total' → 'woocommerce'
-        // domain entry with our own wording. Translation source of truth stays in our .po.
-        $override_js  = "( function() {";
+        // those strings. Patch the translation on the JS side.
+        //
+        // IMPORTANT: WC's wc-cart-checkout-base-js-translations inline bundle calls
+        // wp.i18n.setLocaleData(cartLocaleData, 'woocommerce') AFTER our override, which
+        // merges the WC-bundled "Estimated total": ["Odhadovaný součet"] back on top of
+        // ours. So a single one-shot override on wp-i18n is clobbered.
+        //
+        // We install a permanent override by:
+        //   1) re-applying after every future setLocaleData call via wp.hooks (if available), and
+        //   2) attaching another override as a `before` inline script on wc-cart-checkout-base,
+        //      which runs AFTER the translations bundle has merged its own data in.
+        $total_txt   = wp_json_encode(__('Total', 'studiou-wc-free-photo-product'));
+        $override_js = "( function() {";
         $override_js .= " if ( ! window.wp || ! wp.i18n ) return;";
         $override_js .= " var domain = 'woocommerce';";
-        $override_js .= " var txt = " . wp_json_encode(__('Total', 'studiou-wc-free-photo-product')) . ";";
-        $override_js .= " wp.i18n.setLocaleData( { 'Estimated total': [ txt ] }, domain );";
-        // Also remap other cart-page terminology variants so UI stays consistent.
-        $override_js .= " wp.i18n.setLocaleData( { 'Cart totals': [ txt ] }, domain );";
+        $override_js .= " var txt = " . $total_txt . ";";
+        $override_js .= " function apply() { try {";
+        $override_js .= "  wp.i18n.setLocaleData( { 'Estimated total': [ txt ], 'Cart totals': [ txt ] }, domain );";
+        $override_js .= " } catch (e) {} }";
+        $override_js .= " apply();";
+        // Re-apply on every subsequent wp.i18n data change (covers WC's late bundle load).
+        $override_js .= " if ( wp.hooks && wp.hooks.addAction ) {";
+        $override_js .= "  wp.hooks.addAction( 'i18n.gettext_with_context_woocommerce', 'studiou-fpp/total-override', apply );";
+        $override_js .= "  wp.hooks.addAction( 'i18n.gettext_woocommerce', 'studiou-fpp/total-override', apply );";
+        $override_js .= " }";
+        // Also re-apply after DOMContentLoaded as a last-line safety net.
+        $override_js .= " if ( document.readyState === 'loading' ) {";
+        $override_js .= "  document.addEventListener( 'DOMContentLoaded', apply );";
+        $override_js .= " }";
         $override_js .= " } )();";
         wp_add_inline_script('wp-i18n', $override_js, 'after');
+        // The critical bit: override AFTER WC's cart-checkout-base translations bundle runs.
+        wp_add_inline_script('wc-cart-checkout-base', $override_js, 'after');
+        wp_add_inline_script('wc-cart-block-frontend', $override_js, 'after');
 
         wp_register_style(
             'studiou-wcfpp-frontend',