Commit dfa7dca5c38 for woocommerce

commit dfa7dca5c38639df58d2f5f20e8007d836a0259a
Author: Vlad Olaru <vlad.olaru@automattic.com>
Date:   Wed May 27 18:25:08 2026 +0300

    Fix DefaultCustomerAddress autoload race during 10.7→10.8 in-place upgrade (#65337)

    * fix(settings): pre-load DefaultCustomerAddress enum to dodge upgrade-time autoload race

    Context: WC 10.8.0 added the Automattic\WooCommerce\Enums\DefaultCustomerAddress
    enum and referenced its constants from class-wc-settings-general.php for the
    "Default customer location" setting.

    Problem: PR #64091 (10.8.0) landed the enum reference in a file reachable from
    the AssetDataRegistry chain that update.php's iframe footer triggers via
    admin_print_footer_scripts. On a same-request in-place upgrade from 10.7.x,
    the Jetpack autoloader's in-memory Version_Loader::$classmap is the snapshot
    captured at request start (pre-upgrade) and therefore does not contain the new
    enum class. When the post-swap class-wc-settings-general.php loads fresh from
    disk and evaluates DefaultCustomerAddress::BASE, PHP autoloads via the stale
    classmap, gets a miss (no PSR-4 fallback for the WC namespace in the shipped
    jetpack_autoload_psr4.php — that file isn't generated), and fatals with
    "Class Automattic\WooCommerce\Enums\DefaultCustomerAddress not found" at
    line 237 of class-wc-settings-general.php. Site stays up, db migrates to
    10.8.0-2, next request works — but admins get a fatal-error email from WP.

    Solution: bypass the autoloader for this one class by require_once'ing its
    file at the top of class-wc-settings-general.php. The class is final and
    dependency-free, so the include is idempotent and safe. The enum is still
    the canonical definition; the eight other includes/ files that reference it
    keep using the enum constants because they are loaded during WC's normal
    boot (their class definitions get pinned to the pre-upgrade version in PHP's
    class table, so the post-swap file content never executes).

    This is a narrow hotfix for the specific reported file. The underlying race
    applies structurally to any new class added in version N+1 that's referenced
    from files reachable during the update.php iframe footer; that bug class is
    tracked in #54657 and is best fixed by hooking AssetDataRegistry's enqueue
    earlier so the settings page loads BEFORE the file swap completes (a draft
    PR #65005 explored this approach).

    Refs #54657

    * fix(settings): guard DefaultCustomerAddress preload with class_exists()

    Wraps the require_once added in the prior commit with a class_exists(..., false)
    guard. Matches the defensive pattern in class-wc-gateway-paypal.php (PR #62789)
    and keeps this safe under opcache.preload or any other mechanism that may have
    already defined the class before the file is included. The require_once on its
    own is already idempotent via PHP's realpath tracking — confirmed empirically
    on the docker stack for both 10.7→fix-build and 10.8.0→fix-build in-place
    upgrades — but the guard makes the intent explicit and stays consistent with
    the rest of the codebase.

    No functional change for the realistic in-place upgrade paths.

    Refs #65337

diff --git a/plugins/woocommerce/changelog/fix-defaultcustomeraddress-autoload-race b/plugins/woocommerce/changelog/fix-defaultcustomeraddress-autoload-race
new file mode 100644
index 00000000000..507b980eff8
--- /dev/null
+++ b/plugins/woocommerce/changelog/fix-defaultcustomeraddress-autoload-race
@@ -0,0 +1,4 @@
+Significance: patch
+Type: fix
+
+Fix a fatal error during in-place upgrade to 10.8.0 caused by the new DefaultCustomerAddress enum being referenced from class-wc-settings-general.php before the in-process autoloader classmap is refreshed.
diff --git a/plugins/woocommerce/includes/admin/settings/class-wc-settings-general.php b/plugins/woocommerce/includes/admin/settings/class-wc-settings-general.php
index 674d4990af4..a903d0b2d61 100644
--- a/plugins/woocommerce/includes/admin/settings/class-wc-settings-general.php
+++ b/plugins/woocommerce/includes/admin/settings/class-wc-settings-general.php
@@ -11,6 +11,25 @@ use Automattic\WooCommerce\Internal\AddressProvider\AddressProviderController;

 defined( 'ABSPATH' ) || exit;

+/*
+ * Pre-load the enum file because the in-process Jetpack autoloader classmap is
+ * captured at request start by the pre-upgrade plugin version, so during a same-
+ * request in-place upgrade it will not contain new src/Enums/* classes added in
+ * the new version. Without this, the DefaultCustomerAddress::* references below
+ * would trigger an autoloader miss and a "Class not found" fatal during the
+ * upgrade-completion iframe of /wp-admin/update.php.
+ *
+ * The class_exists() guard (with autoload disabled) matches the defensive
+ * pattern used elsewhere in includes/, e.g. class-wc-gateway-paypal.php, and
+ * keeps this safe under opcache.preload or any other mechanism that may have
+ * already defined the class before the file is included.
+ *
+ * The architectural fix lives in https://github.com/woocommerce/woocommerce/issues/54657.
+ */
+if ( ! class_exists( '\Automattic\WooCommerce\Enums\DefaultCustomerAddress', false ) ) {
+	require_once dirname( WC_PLUGIN_FILE ) . '/src/Enums/DefaultCustomerAddress.php';
+}
+
 if ( class_exists( 'WC_Settings_General', false ) ) {
 	return new WC_Settings_General();
 }