Commit 02bc8a2803d for woocommerce

commit 02bc8a2803d8da8028022f84d938d1f40a56d70e
Author: Adrian Moldovan <3854374+adimoldovan@users.noreply.github.com>
Date:   Thu Jul 9 20:33:54 2026 +0300

    php tests: create REST auth user once per class in v4 API unit tests (#66432)

diff --git a/plugins/woocommerce/changelog/testops-214-share-rest-auth-user-v4-tests b/plugins/woocommerce/changelog/testops-214-share-rest-auth-user-v4-tests
new file mode 100644
index 00000000000..ea5c8365a4e
--- /dev/null
+++ b/plugins/woocommerce/changelog/testops-214-share-rest-auth-user-v4-tests
@@ -0,0 +1,3 @@
+Significance: patch
+Type: dev
+Comment: Share the REST auth user across tests in v4 API unit test classes instead of recreating it per test.
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Customers/class-wc-rest-customers-v4-controller-tests.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Customers/class-wc-rest-customers-v4-controller-tests.php
index 725702fe080..8adf64de9a3 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Customers/class-wc-rest-customers-v4-controller-tests.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Customers/class-wc-rest-customers-v4-controller-tests.php
@@ -30,11 +30,11 @@ class WC_REST_Customers_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	private $endpoint;

 	/**
-	 * User ID.
+	 * Shared admin user ID used for REST authentication across the class.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * Customer schema instance.
@@ -78,6 +78,15 @@ class WC_REST_Customers_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		);
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -95,12 +104,7 @@ class WC_REST_Customers_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		$this->endpoint = new CustomersController();
 		$this->endpoint->init( $this->customer_schema, $collection_query, $update_utils );

-		$this->user_id = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 	}

 	/**
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OfflinePaymentMethods/class-wc-rest-offline-payment-methods-v4-controller-tests.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OfflinePaymentMethods/class-wc-rest-offline-payment-methods-v4-controller-tests.php
index 470f6d8b960..43c5105dfc4 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OfflinePaymentMethods/class-wc-rest-offline-payment-methods-v4-controller-tests.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OfflinePaymentMethods/class-wc-rest-offline-payment-methods-v4-controller-tests.php
@@ -24,11 +24,11 @@ class WC_REST_Offline_Payment_Methods_V4_Controller_Tests extends WC_REST_Unit_T
 	protected $endpoint;

 	/**
-	 * Test user ID.
+	 * Shared admin user ID for REST authentication.
 	 *
 	 * @var int
 	 */
-	protected $user;
+	protected static $user;

 	/**
 	 * Payments instance.
@@ -68,6 +68,15 @@ class WC_REST_Offline_Payment_Methods_V4_Controller_Tests extends WC_REST_Unit_T
 		}
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -88,12 +97,7 @@ class WC_REST_Offline_Payment_Methods_V4_Controller_Tests extends WC_REST_Unit_T
 		// Manually register ONLY our controller's routes to avoid triggering global REST API init.
 		$this->endpoint->register_routes();

-		$this->user = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user );
+		wp_set_current_user( self::$user );
 	}

 	/**
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OrderNotes/class-wc-rest-order-notes-v4-controller-tests.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OrderNotes/class-wc-rest-order-notes-v4-controller-tests.php
index a06f730ebf3..17f176ace33 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OrderNotes/class-wc-rest-order-notes-v4-controller-tests.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/OrderNotes/class-wc-rest-order-notes-v4-controller-tests.php
@@ -20,11 +20,11 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	private $endpoint;

 	/**
-	 * User ID.
+	 * Shared admin user ID for REST auth.
 	 *
 	 * @var int
 	 */
-	private $user;
+	protected static $user;

 	/**
 	 * Runs after each test.
@@ -60,6 +60,15 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		);
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -76,12 +85,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		$this->endpoint = new OrderNotesController();
 		$this->endpoint->init( $order_note_schema, $collection_query );

-		$this->user = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user );
+		wp_set_current_user( self::$user );
 	}

 	/**
@@ -98,7 +102,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_get_items() {
 		// Create an order.
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		// Add some order notes.
 		$order->add_order_note( 'Test note 1', false, false );
@@ -120,8 +124,8 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_get_items_with_order_filter() {
 		// Create two orders.
-		$order1 = OrderHelper::create_order( $this->user );
-		$order2 = OrderHelper::create_order( $this->user );
+		$order1 = OrderHelper::create_order( self::$user );
+		$order2 = OrderHelper::create_order( self::$user );

 		// Add notes to both orders.
 		$order1->add_order_note( 'Order 1 note', false, false );
@@ -146,7 +150,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test getting order notes with type filter.
 	 */
 	public function test_get_items_with_type_filter() {
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		// Add different types of notes.
 		$order->add_order_note( 'Internal note', false, false );
@@ -195,7 +199,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test creating an order note.
 	 */
 	public function test_create_item() {
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/order-notes' );
 		$request->set_body_params(
@@ -219,7 +223,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test creating a customer order note.
 	 */
 	public function test_create_is_customer_note() {
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/order-notes' );
 		$request->set_body_params(
@@ -261,7 +265,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test creating order note without required fields.
 	 */
 	public function test_create_item_missing_fields() {
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/order-notes' );
 		$request->set_body_params(
@@ -280,7 +284,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test getting a single order note.
 	 */
 	public function test_get_item() {
-		$order   = OrderHelper::create_order( $this->user );
+		$order   = OrderHelper::create_order( self::$user );
 		$note_id = $order->add_order_note( 'Test single note', false, false );

 		$response = $this->server->dispatch( new WP_REST_Request( 'GET', '/wc/v4/order-notes/' . $note_id ) );
@@ -306,7 +310,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test deleting an order note.
 	 */
 	public function test_delete_item() {
-		$order   = OrderHelper::create_order( $this->user );
+		$order   = OrderHelper::create_order( self::$user );
 		$note_id = $order->add_order_note( 'Note to delete', false, false );

 		$request = new WP_REST_Request( 'DELETE', '/wc/v4/order-notes/' . $note_id );
@@ -358,7 +362,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_get_items_without_permission() {
 		wp_set_current_user( 0 );
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/order-notes' );
 		$request->set_query_params( array( 'order_id' => $order->get_id() ) );
@@ -372,7 +376,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_create_item_without_permission() {
 		wp_set_current_user( 0 );
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/order-notes' );
 		$request->set_body_params(
@@ -391,7 +395,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 * Test that order note content is sanitized to prevent XSS.
 	 */
 	public function test_create_item_sanitizes_note_content() {
-		$order = OrderHelper::create_order( $this->user );
+		$order = OrderHelper::create_order( self::$user );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/order-notes' );
 		$request->set_body_params(
@@ -415,7 +419,7 @@ class WC_REST_Order_Notes_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_delete_item_without_permission() {
 		wp_set_current_user( 0 );
-		$order   = OrderHelper::create_order( $this->user );
+		$order   = OrderHelper::create_order( self::$user );
 		$note_id = $order->add_order_note( 'Note to delete', false, false );

 		$request = new WP_REST_Request( 'DELETE', '/wc/v4/order-notes/' . $note_id );
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-can-be-refunded-test.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-can-be-refunded-test.php
index d11d69251cc..c69de1e0b7f 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-can-be-refunded-test.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-can-be-refunded-test.php
@@ -9,11 +9,11 @@ use Automattic\WooCommerce\Enums\OrderStatus;
 class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {

 	/**
-	 * User ID for an admin user.
+	 * Shared admin user ID, used for REST authentication across the class.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * Enable the REST API v4 feature.
@@ -46,6 +46,15 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 		return $features;
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Set up test fixtures.
 	 */
@@ -53,8 +62,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 		self::enable_rest_api_v4_feature();
 		parent::setUp();

-		$this->user_id = $this->factory->user->create( array( 'role' => 'administrator' ) );
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 	}

 	/**
@@ -87,7 +95,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 */
 	private function create_order_with_product( string $status = 'completed' ): WC_Order {
 		$product = WC_Helper_Product::create_simple_product( true, array( 'regular_price' => '10.00' ) );
-		$order   = WC_Helper_Order::create_order( $this->user_id, $product );
+		$order   = WC_Helper_Order::create_order( self::$user_id, $product );
 		$order->set_status( $status );
 		$order->save();
 		$order->calculate_totals( true );
@@ -141,7 +149,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 		$product_a = WC_Helper_Product::create_simple_product( true, array( 'regular_price' => '10.00' ) );
 		$product_b = WC_Helper_Product::create_simple_product( true, array( 'regular_price' => '20.00' ) );

-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$item_a = new WC_Order_Item_Product();
 		$item_a->set_props(
@@ -275,7 +283,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Line item with product_id 0 has can_be_refunded false.
 	 */
 	public function test_line_item_without_product_not_refundable(): void {
-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$item = new WC_Order_Item_Product();
 		$item->set_props(
@@ -350,7 +358,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Shipping line with remaining amount has can_be_refunded true.
 	 */
 	public function test_shipping_line_can_be_refunded(): void {
-		$order = WC_Helper_Order::create_order_with_fees_and_shipping( $this->user_id );
+		$order = WC_Helper_Order::create_order_with_fees_and_shipping( self::$user_id );
 		$order->set_status( 'completed' );
 		$order->save();
 		$order->calculate_totals( true );
@@ -365,7 +373,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Fee line with remaining amount has can_be_refunded true.
 	 */
 	public function test_fee_line_can_be_refunded(): void {
-		$order = WC_Helper_Order::create_order_with_fees_and_shipping( $this->user_id );
+		$order = WC_Helper_Order::create_order_with_fees_and_shipping( self::$user_id );
 		$order->set_status( 'completed' );
 		$order->save();
 		$order->calculate_totals( true );
@@ -380,7 +388,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Fully refunded shipping line has can_be_refunded false.
 	 */
 	public function test_fully_refunded_shipping_line(): void {
-		$order = WC_Helper_Order::create_order_with_fees_and_shipping( $this->user_id );
+		$order = WC_Helper_Order::create_order_with_fees_and_shipping( self::$user_id );
 		$order->set_status( 'completed' );
 		$order->save();
 		$order->calculate_totals( true );
@@ -410,7 +418,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Fully refunded fee line has can_be_refunded false.
 	 */
 	public function test_fully_refunded_fee_line(): void {
-		$order = WC_Helper_Order::create_order_with_fees_and_shipping( $this->user_id );
+		$order = WC_Helper_Order::create_order_with_fees_and_shipping( self::$user_id );
 		$order->set_status( 'completed' );
 		$order->save();
 		$order->calculate_totals( true );
@@ -440,7 +448,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Fully refunded shipping line with tax has can_be_refunded false.
 	 */
 	public function test_fully_refunded_shipping_line_with_tax(): void {
-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$shipping_item = new WC_Order_Item_Shipping();
 		$shipping_item->set_props(
@@ -487,7 +495,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * @testdox Fully refunded fee line with tax has can_be_refunded false.
 	 */
 	public function test_fully_refunded_fee_line_with_tax(): void {
-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$fee_item = new WC_Order_Item_Fee();
 		$fee_item->set_props(
@@ -538,7 +546,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * so OrderSchema::can_be_refunded must compare against tax-inclusive line totals.
 	 */
 	public function test_partially_refunded_shipping_line_with_tax(): void {
-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$shipping_item = new WC_Order_Item_Shipping();
 		$shipping_item->set_props(
@@ -587,7 +595,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 * Regression test for WOOPLUG-6819.
 	 */
 	public function test_partially_refunded_fee_line_with_tax(): void {
-		$order = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$fee_item = new WC_Order_Item_Fee();
 		$fee_item->set_props(
@@ -638,7 +646,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_zero_priced_item_follows_quantity_logic(): void {
 		$product = WC_Helper_Product::create_simple_product( true, array( 'regular_price' => '0.00' ) );
-		$order   = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order   = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$item = new WC_Order_Item_Product();
 		$item->set_props(
@@ -672,7 +680,7 @@ class WC_REST_Orders_V4_Can_Be_Refunded_Test extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_negative_fee_line_can_be_refunded(): void {
 		$product = WC_Helper_Product::create_simple_product( true, array( 'regular_price' => '50.00' ) );
-		$order   = wc_create_order( array( 'customer_id' => $this->user_id ) );
+		$order   = wc_create_order( array( 'customer_id' => self::$user_id ) );

 		$item = new WC_Order_Item_Product();
 		$item->set_props(
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-controller-tests.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-controller-tests.php
index 4b90c5db7db..c1d0da7d501 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-controller-tests.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Orders/class-wc-rest-orders-v4-controller-tests.php
@@ -29,11 +29,11 @@ class WC_REST_Orders_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 	private $endpoint;

 	/**
-	 * User ID.
+	 * Shared admin user ID for REST auth.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * Order schema instance.
@@ -76,6 +76,15 @@ class WC_REST_Orders_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		);
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -103,12 +112,7 @@ class WC_REST_Orders_V4_Controller_Tests extends WC_REST_Unit_Test_Case {
 		$this->endpoint = new OrdersController();
 		$this->endpoint->init( $this->order_schema, $collection_query, $update_utils, $action_controller );

-		$this->user_id = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 	}

 	/**
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Settings/class-wc-rest-general-settings-v4-controller-test.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Settings/class-wc-rest-general-settings-v4-controller-test.php
index aae1ce1e76a..e9336dfbe26 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Settings/class-wc-rest-general-settings-v4-controller-test.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/Settings/class-wc-rest-general-settings-v4-controller-test.php
@@ -17,11 +17,11 @@ declare(strict_types=1);
 class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case {

 	/**
-	 * User ID.
+	 * Shared shop_manager user used for REST auth.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * @var callable
@@ -32,6 +32,15 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 */
 	private $prev_default_country;

+	/**
+	 * Create the shared shop manager user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'shop_manager' ) );
+	}
+
 	/**
 	 * Setup.
 	 */
@@ -48,13 +57,6 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case

 		// This is to reset the country after the test.
 		$this->prev_default_country = get_option( 'woocommerce_default_country' );
-
-		// Create a user with permissions.
-		$this->user_id = $this->factory->user->create(
-			array(
-				'role' => 'shop_manager',
-			)
-		);
 	}

 	/**
@@ -86,7 +88,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * Test getting general settings.
 	 */
 	public function test_get_item() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/general' );
 		$response = $this->server->dispatch( $request );
 		$data     = $response->get_data();
@@ -107,7 +109,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * Test updating general settings with new values format.
 	 */
 	public function test_update_item() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -145,7 +147,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * Test updating general settings with backward compatibility (old format).
 	 */
 	public function test_update_item_backward_compatibility() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -195,7 +197,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 		$initial_value = 'initial_value';
 		update_option( 'woocommerce_share_key_display', $initial_value );

-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -227,7 +229,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * State codes in WooCommerce include the country prefix (e.g., "DE-BY" for Bavaria).
 	 */
 	public function test_update_country_with_state() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -252,7 +254,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * Test updating country with invalid state code returns error.
 	 */
 	public function test_update_country_with_invalid_state() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -275,7 +277,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 	 * Test updating country without state (country only).
 	 */
 	public function test_update_country_only() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -310,7 +312,7 @@ class WC_REST_General_Settings_V4_Controller_Test extends WC_REST_Unit_Test_Case
 		update_option( 'woocommerce_price_num_decimals', 2 );
 		update_option( 'woocommerce_share_key_display', 'no' ); // Initial value, should not be updated.

-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/general' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
diff --git a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/ShippingZones/class-wc-rest-shipping-zones-v4-controller-tests.php b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/ShippingZones/class-wc-rest-shipping-zones-v4-controller-tests.php
index ab0d91e3cd5..f1d778c546b 100644
--- a/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/ShippingZones/class-wc-rest-shipping-zones-v4-controller-tests.php
+++ b/plugins/woocommerce/tests/php/includes/rest-api/Controllers/Version4/ShippingZones/class-wc-rest-shipping-zones-v4-controller-tests.php
@@ -24,11 +24,11 @@ class WC_REST_Shipping_Zones_V4_Controller_Tests extends WC_REST_Unit_Test_Case
 	protected $endpoint;

 	/**
-	 * Test user ID.
+	 * Admin user ID, shared across all tests in the class for REST authentication.
 	 *
 	 * @var int
 	 */
-	protected $user;
+	protected static $user;

 	/**
 	 * Created shipping zones for cleanup.
@@ -63,6 +63,22 @@ class WC_REST_Shipping_Zones_V4_Controller_Tests extends WC_REST_Unit_Test_Case
 		);
 	}

+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * The user is read-only (used only for REST authentication), so it is safe to
+	 * share across every test method instead of recreating it per test.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user = $factory->user->create(
+			array(
+				'role' => 'administrator',
+			)
+		);
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -71,12 +87,7 @@ class WC_REST_Shipping_Zones_V4_Controller_Tests extends WC_REST_Unit_Test_Case
 		parent::setUp();
 		$this->endpoint = new ShippingZonesController();
 		$this->endpoint->init( new ShippingZoneSchema(), new ShippingZoneService() );
-		$this->user = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user );
+		wp_set_current_user( self::$user );
 		$this->zones = array();
 	}

diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ControllerTest.php
index fe984e82ddf..b4d98afe3ba 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ControllerTest.php
@@ -33,18 +33,18 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	private static $original_fulfillments_flag;

 	/**
-	 * Admin user for tests
+	 * Admin user for tests, shared across all tests in the class for REST authentication.
 	 *
 	 * @var int
 	 */
-	private int $admin_user_id;
+	private static int $admin_user_id;

 	/**
-	 * Customer user for tests
+	 * Customer user for tests, shared across all tests in the class.
 	 *
 	 * @var int
 	 */
-	private int $customer_user_id;
+	private static int $customer_user_id;

 	/**
 	 * Test order
@@ -85,28 +85,35 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	}

 	/**
-	 * Setup test environment
+	 * Create the shared users once for the whole class.
+	 *
+	 * @param object $factory Factory object.
 	 */
-	public function setUp(): void {
-		parent::setUp();
-
-		$this->controller = new FulfillmentsController();
-		$this->controller->init( new FulfillmentSchema(), new OrderFulfillmentsRestController() );
-		$this->controller->register_routes();
-
-		$this->admin_user_id = $this->factory->user->create(
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$admin_user_id = $factory->user->create(
 			array(
 				'role' => 'administrator',
 			)
 		);

-		$this->customer_user_id = $this->factory->user->create(
+		self::$customer_user_id = $factory->user->create(
 			array(
 				'role' => 'customer',
 			)
 		);
+	}

-		$this->test_order       = WC_Helper_Order::create_order( $this->customer_user_id );
+	/**
+	 * Setup test environment
+	 */
+	public function setUp(): void {
+		parent::setUp();
+
+		$this->controller = new FulfillmentsController();
+		$this->controller->init( new FulfillmentSchema(), new OrderFulfillmentsRestController() );
+		$this->controller->register_routes();
+
+		$this->test_order       = WC_Helper_Order::create_order( self::$customer_user_id );
 		$this->test_fulfillment = FulfillmentsHelper::create_fulfillment(
 			array(
 				'entity_id' => $this->test_order->get_id(),
@@ -118,10 +125,6 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Teardown test environment
 	 */
 	public function tearDown(): void {
-		// Delete the created users.
-		wp_delete_user( $this->admin_user_id );
-		wp_delete_user( $this->customer_user_id );
-
 		// Delete the created orders and their fulfillments.
 		WC_Helper_Order::delete_order( $this->test_order->get_id() );
 		global $wpdb;
@@ -145,7 +148,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test get_fulfillments endpoint
 	 */
 	public function test_get_fulfillments_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', $this->test_order->get_id() );
@@ -159,7 +162,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test get_fulfillments without order_id
 	 */
 	public function test_get_fulfillments_missing_order_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );

@@ -174,7 +177,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test get_fulfillments with invalid order_id
 	 */
 	public function test_get_fulfillments_invalid_order_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', 99999 );
@@ -187,7 +190,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test create_fulfillment endpoint
 	 */
 	public function test_create_fulfillment_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/fulfillments' );
 		$request->set_header( 'Content-Type', 'application/json' );
@@ -202,7 +205,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test create_fulfillment without entity_id
 	 */
 	public function test_create_fulfillment_missing_entity_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );
 		$test_data = $this->get_test_fulfillment_data();
 		unset( $test_data['entity_id'] );

@@ -220,7 +223,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test create_fulfillment with invalid entity_type
 	 */
 	public function test_create_fulfillment_invalid_entity_type() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/fulfillments' );
 		$request->set_header( 'Content-Type', 'application/json' );
@@ -236,7 +239,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test get_fulfillment endpoint
 	 */
 	public function test_get_fulfillment_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/' . $this->test_fulfillment->get_id() );

@@ -252,7 +255,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * see the raw 'Y-m-d H:i:s' form.
 	 */
 	public function test_get_fulfillment_formats_date_fulfilled_meta_as_iso8601() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$this->test_fulfillment->set_date_fulfilled( '2025-01-15T10:30:00Z' );
 		$this->test_fulfillment->save();
@@ -276,7 +279,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test get_fulfillment with invalid ID
 	 */
 	public function test_get_fulfillment_invalid_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/99999' );

@@ -290,7 +293,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test update_fulfillment endpoint
 	 */
 	public function test_update_fulfillment_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'PUT', '/wc/v4/fulfillments/' . $this->test_fulfillment->get_id() );
 		$request->set_header( 'Content-Type', 'application/json' );
@@ -304,7 +307,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test update_fulfillment with invalid ID
 	 */
 	public function test_update_fulfillment_invalid_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'PUT', '/wc/v4/fulfillments/99999' );
 		$request->set_header( 'Content-Type', 'application/json' );
@@ -320,7 +323,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test delete_fulfillment endpoint
 	 */
 	public function test_delete_fulfillment_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$fulfillment = FulfillmentsHelper::create_fulfillment(
 			array( 'entity_id' => $this->test_order->get_id() )
@@ -340,7 +343,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test delete_fulfillment with invalid ID
 	 */
 	public function test_delete_fulfillment_invalid_id() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'DELETE', '/wc/v4/fulfillments/99999' );

@@ -354,7 +357,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - admin user
 	 */
 	public function test_permission_check_admin() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', $this->test_order->get_id() );
@@ -367,7 +370,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - customer reading their own order
 	 */
 	public function test_permission_check_customer_own_order() {
-		wp_set_current_user( $this->customer_user_id );
+		wp_set_current_user( self::$customer_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', $this->test_order->get_id() );
@@ -380,7 +383,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - customer trying to create fulfillment
 	 */
 	public function test_permission_check_customer_create() {
-		wp_set_current_user( $this->customer_user_id );
+		wp_set_current_user( self::$customer_user_id );

 		$request = new WP_REST_Request( 'POST', '/wc/v4/fulfillments' );
 		$request->set_header( 'Content-Type', 'application/json' );
@@ -435,7 +438,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 */
 	public function test_permission_check_customer_other_order() {
 		$other_order = WC_Helper_Order::create_order();
-		wp_set_current_user( $this->customer_user_id );
+		wp_set_current_user( self::$customer_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', $other_order->get_id() );
@@ -448,7 +451,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test schema validation for get fulfillments
 	 */
 	public function test_get_fulfillments_schema() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request  = new WP_REST_Request( 'OPTIONS', '/wc/v4/fulfillments' );
 		$response = rest_get_server()->dispatch( $request );
@@ -471,7 +474,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test schema validation for create fulfillment
 	 */
 	public function test_create_fulfillment_schema() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request  = new WP_REST_Request( 'OPTIONS', '/wc/v4/fulfillments' );
 		$response = rest_get_server()->dispatch( $request );
@@ -495,7 +498,7 @@ class ControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test error response format
 	 */
 	public function test_error_response_format() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments' );
 		$request->set_param( 'order_id', 0 );
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ProvidersTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ProvidersTest.php
index fb3ebdb6f6a..33198ca57e6 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ProvidersTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Fulfillments/ProvidersTest.php
@@ -29,25 +29,25 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	private static $original_fulfillments_flag;

 	/**
-	 * Admin user for tests
+	 * Admin user for tests, shared across all tests in the class for REST authentication.
 	 *
 	 * @var int
 	 */
-	private int $admin_user_id;
+	private static int $admin_user_id;

 	/**
-	 * Shop manager user for tests
+	 * Shop manager user for tests, shared across all tests in the class.
 	 *
 	 * @var int
 	 */
-	private int $shop_manager_user_id;
+	private static int $shop_manager_user_id;

 	/**
-	 * Customer user for tests
+	 * Customer user for tests, shared across all tests in the class.
 	 *
 	 * @var int
 	 */
-	private int $customer_user_id;
+	private static int $customer_user_id;

 	/**
 	 * Set up the test environment.
@@ -74,28 +74,24 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	}

 	/**
-	 * Setup test environment
+	 * Create the shared users once for the whole class.
+	 *
+	 * @param object $factory Factory object.
 	 */
-	public function setUp(): void {
-		parent::setUp();
-
-		$this->controller = new FulfillmentsController();
-		$this->controller->init( new FulfillmentSchema(), new OrderFulfillmentsRestController() );
-		$this->controller->register_routes();
-
-		$this->admin_user_id = $this->factory->user->create(
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$admin_user_id = $factory->user->create(
 			array(
 				'role' => 'administrator',
 			)
 		);

-		$this->shop_manager_user_id = $this->factory->user->create(
+		self::$shop_manager_user_id = $factory->user->create(
 			array(
 				'role' => 'shop_manager',
 			)
 		);

-		$this->customer_user_id = $this->factory->user->create(
+		self::$customer_user_id = $factory->user->create(
 			array(
 				'role' => 'customer',
 			)
@@ -103,15 +99,14 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	}

 	/**
-	 * Teardown test environment
+	 * Setup test environment
 	 */
-	public function tearDown(): void {
-		// Delete the created users.
-		wp_delete_user( $this->admin_user_id );
-		wp_delete_user( $this->shop_manager_user_id );
-		wp_delete_user( $this->customer_user_id );
+	public function setUp(): void {
+		parent::setUp();

-		parent::tearDown();
+		$this->controller = new FulfillmentsController();
+		$this->controller->init( new FulfillmentSchema(), new OrderFulfillmentsRestController() );
+		$this->controller->register_routes();
 	}

 	/**
@@ -127,7 +122,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test get_providers endpoint success
 	 */
 	public function test_get_providers_success() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

@@ -139,7 +134,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test get_providers contains expected providers
 	 */
 	public function test_get_providers_contains_expected_providers() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		// Add a test provider using the filter.
 		$test_provider = function () {
@@ -164,7 +159,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - admin user
 	 */
 	public function test_permission_check_admin() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

@@ -176,7 +171,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - shop manager user
 	 */
 	public function test_permission_check_shop_manager() {
-		wp_set_current_user( $this->shop_manager_user_id );
+		wp_set_current_user( self::$shop_manager_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

@@ -188,7 +183,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test permission check - customer user
 	 */
 	public function test_permission_check_customer() {
-		wp_set_current_user( $this->customer_user_id );
+		wp_set_current_user( self::$customer_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

@@ -215,7 +210,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 		// Disable the fulfillments feature.
 		update_option( 'woocommerce_feature_fulfillments_enabled', 'no' );

-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

@@ -233,7 +228,7 @@ class ProvidersTest extends WC_REST_Unit_Test_Case {
 	 * Test response format validation
 	 */
 	public function test_response_format_validation() {
-		wp_set_current_user( $this->admin_user_id );
+		wp_set_current_user( self::$admin_user_id );

 		$request = new WP_REST_Request( 'GET', '/wc/v4/fulfillments/providers' );

diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsAddToCartTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsAddToCartTest.php
index af452be7224..68435a2897e 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsAddToCartTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsAddToCartTest.php
@@ -15,6 +15,22 @@ use WP_REST_Request;
  */
 class ProductsAddToCartTest extends WC_REST_Unit_Test_Case {

+	/**
+	 * The shared admin user used for REST authentication across all tests in this class.
+	 *
+	 * @var int
+	 */
+	protected static $user;
+
+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user = $factory->user->create( array( 'role' => 'administrator' ) );
+	}
+
 	/**
 	 * Setup our test server, endpoints, and user info.
 	 */
@@ -29,12 +45,7 @@ class ProductsAddToCartTest extends WC_REST_Unit_Test_Case {
 		);
 		parent::setUp();
 		$this->endpoint = new ProductsController();
-		$this->user     = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user );
+		wp_set_current_user( self::$user );
 	}

 	/**
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsControllerTest.php
index 1b8fd86ed73..5f96d785d87 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Products/ProductsControllerTest.php
@@ -65,11 +65,25 @@ class ProductsControllerTest extends WC_REST_Unit_Test_Case {
 	protected static $products = array();

 	/**
-	 * Create products for tests.
+	 * Admin user ID, shared across all tests in the class for REST authentication.
 	 *
+	 * @var int
+	 */
+	protected static $user;
+
+	/**
+	 * Create the shared admin user and products once for the whole class.
+	 *
+	 * @param object $factory Factory object.
 	 * @return void
 	 */
-	public static function wpSetUpBeforeClass() {
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user = $factory->user->create(
+			array(
+				'role' => 'administrator',
+			)
+		);
+
 		self::$products[] = WC_Helper_Product::create_simple_product(
 			true,
 			array(
@@ -132,12 +146,7 @@ class ProductsControllerTest extends WC_REST_Unit_Test_Case {
 		$this->enable_rest_api_v4_feature();
 		parent::setUp();
 		$this->endpoint = new ProductsController();
-		$this->user     = $this->factory->user->create(
-			array(
-				'role' => 'administrator',
-			)
-		);
-		wp_set_current_user( $this->user );
+		wp_set_current_user( self::$user );

 		// Reset tax settings to ensure consistent product pricing.
 		// Some tests (like OrderHelper::create_complex_wp_post_order) modify tax settings globally,
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Email/EmailSettingsControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Email/EmailSettingsControllerTest.php
index 04a4c29d638..c645fb08055 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Email/EmailSettingsControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Email/EmailSettingsControllerTest.php
@@ -20,11 +20,11 @@ use WP_REST_Request;
 class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {

 	/**
-	 * User ID.
+	 * Shared shop_manager user for REST auth.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * @var callable
@@ -38,6 +38,15 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 */
 	private $prev_options = array();

+	/**
+	 * Create the shared shop manager user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'shop_manager' ) );
+	}
+
 	/**
 	 * Setup.
 	 */
@@ -65,13 +74,6 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 		foreach ( $option_ids as $id ) {
 			$this->prev_options[ $id ] = get_option( $id, null );
 		}
-
-		// Create a user with permissions.
-		$this->user_id = $this->factory->user->create(
-			array(
-				'role' => 'shop_manager',
-			)
-		);
 	}

 	/**
@@ -109,7 +111,7 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Reply-to fields should be present, but design fields should not be present.
 	 */
 	public function test_get_item() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/email' );
 		$response = $this->server->dispatch( $request );
 		$data     = $response->get_data();
@@ -164,7 +166,7 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 		// Disable block email editor feature.
 		update_option( 'woocommerce_feature_block_email_editor_enabled', 'no' );

-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/email' );
 		$response = $this->server->dispatch( $request );
 		$data     = $response->get_data();
@@ -232,7 +234,7 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test updating email settings.
 	 */
 	public function test_update_item() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/email' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -264,7 +266,7 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * When reply-to is enabled, the name is required.
 	 */
 	public function test_update_item_with_invalid_reply_to_name() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/email' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -289,7 +291,7 @@ class EmailSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * When reply-to is enabled, the name is required.
 	 */
 	public function test_update_item_with_invalid_reply_to_address() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/email' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Emails/EmailsSettingsControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Emails/EmailsSettingsControllerTest.php
index d3e0e6d1834..acf6c7bb58a 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Emails/EmailsSettingsControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Emails/EmailsSettingsControllerTest.php
@@ -41,11 +41,11 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	private $email;

 	/**
-	 * User ID with shop_manager permissions.
+	 * Shared shop_manager user ID used for REST auth across the class.
 	 *
 	 * @var int
 	 */
-	private $user_id;
+	protected static $user_id;

 	/**
 	 * Feature filter callback.
@@ -68,6 +68,15 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 */
 	private $registry;

+	/**
+	 * Create the shared shop manager user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$user_id = $factory->user->create( array( 'role' => 'shop_manager' ) );
+	}
+
 	/**
 	 * Setup.
 	 */
@@ -105,13 +114,6 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 		$option_key                        = 'woocommerce_' . self::SAMPLE_EMAIL_ID . '_settings';
 		$this->prev_options[ $option_key ] = get_option( $option_key, null );

-		// Create a user with permissions.
-		$this->user_id = $this->factory->user->create(
-			array(
-				'role' => 'shop_manager',
-			)
-		);
-
 		// Initialize WC_Emails to ensure emails are registered.
 		WC_Emails::instance()->init();
 		$this->email = WC_Emails::instance()->emails['WC_Email_Customer_Completed_Order'];
@@ -157,7 +159,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test that get_items returns properly formatted response.
 	 */
 	public function test_get_items_returns_properly_formatted_response() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/emails' );
 		$response = $this->server->dispatch( $request );
 		$data     = $response->get_data();
@@ -175,7 +177,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test that get_item returns properly formatted response.
 	 */
 	public function test_get_single_item_returns_properly_formatted_response() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
 		$response = $this->server->dispatch( $request );
 		$data     = $response->get_data();
@@ -196,7 +198,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test that get_items can filter by post_id.
 	 */
 	public function test_get_items_can_filter_by_post_id() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		// First, get an email and its post_id.
 		$request      = new WP_REST_Request( 'GET', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
@@ -226,7 +228,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test that filtering by nonexistent post_id returns empty array.
 	 */
 	public function test_get_items_with_nonexistent_post_id_returns_empty() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'GET', '/wc/v4/settings/emails' );
 		$request->set_param( 'post_id', 999999 );
 		$response = $this->server->dispatch( $request );
@@ -241,7 +243,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test successfully updating email settings.
 	 */
 	public function test_update_item_successfully_updates_settings() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -275,7 +277,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test updating with invalid email ID returns 404.
 	 */
 	public function test_update_item_with_invalid_email_id_returns_404() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/invalid_email_id' );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body( wp_json_encode( array( 'values' => array( 'subject' => 'Test' ) ) ) );
@@ -289,7 +291,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test updating with empty body returns 400.
 	 */
 	public function test_update_item_with_empty_body_returns_400() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body( wp_json_encode( array() ) );
@@ -303,7 +305,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test checkbox field sanitization.
 	 */
 	public function test_sanitize_checkbox_field() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		// Test boolean true.
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
@@ -331,7 +333,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test text field sanitization.
 	 */
 	public function test_sanitize_text_field() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
@@ -358,7 +360,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test unwrapping personalization tags on GET.
 	 */
 	public function test_unwrap_personalization_tags_on_get() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		// Store wrapped subject directly in database.
 		$wrapped_subject                  = 'Hello <!--[woocommerce/customer-first-name]-->';
@@ -378,7 +380,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test wrapping personalization tags on UPDATE.
 	 */
 	public function test_wrap_personalization_tags_on_update() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$unwrapped_subject = 'Hello [woocommerce/customer-first-name]';

@@ -406,7 +408,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test personalization tags support multiple prefixes.
 	 */
 	public function test_personalization_tags_support_multiple_prefixes() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$subject_with_multiple_prefixes = 'Hello [woocommerce/customer-first-name] [custom-plugin/test-field]';

 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
@@ -445,7 +447,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test that personalization tags are not double-wrapped.
 	 */
 	public function test_personalization_tags_no_double_wrapping() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$already_wrapped_subject = 'Hello <!--[woocommerce/customer-first-name]-->';

@@ -475,7 +477,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test mixed wrapped and unwrapped tags.
 	 */
 	public function test_personalization_tags_mixed_wrapped_unwrapped() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$mixed_subject = 'Hello <!--[woocommerce/customer-first-name]--> and [woocommerce/order-number]';

@@ -503,7 +505,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test personalization tags are case insensitive.
 	 */
 	public function test_personalization_tags_case_insensitive() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$uppercase_subject = 'Hello [WooCommerce/customer-first-name]';

@@ -531,7 +533,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test personalization tags with attributes.
 	 */
 	public function test_personalization_tags_with_attributes() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$subject_with_attributes = 'Hello [woocommerce/customer-first-name default="Guest"]';

@@ -566,7 +568,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test preheader field also supports personalization tags.
 	 */
 	public function test_personalization_tags_preheader_field_support() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );

 		$preheader_with_tag = 'Check your order [woocommerce/order-number]';

@@ -628,7 +630,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test GET with shop_manager permission succeeds.
 	 */
 	public function test_get_items_with_shop_manager_permission() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request  = new WP_REST_Request( 'GET', '/wc/v4/settings/emails' );
 		$response = $this->server->dispatch( $request );

@@ -639,7 +641,7 @@ class EmailsSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	 * Test UPDATE with shop_manager permission succeeds.
 	 */
 	public function test_update_item_with_shop_manager_permission() {
-		wp_set_current_user( $this->user_id );
+		wp_set_current_user( self::$user_id );
 		$request = new WP_REST_Request( 'PUT', '/wc/v4/settings/emails/' . self::SAMPLE_EMAIL_ID );
 		$request->set_header( 'Content-Type', 'application/json' );
 		$request->set_body(
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/OfflinePaymentMethods/OfflinePaymentMethodsControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/OfflinePaymentMethods/OfflinePaymentMethodsControllerTest.php
index cf49be5d45f..c7496782a20 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/OfflinePaymentMethods/OfflinePaymentMethodsControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/OfflinePaymentMethods/OfflinePaymentMethodsControllerTest.php
@@ -36,9 +36,20 @@ class OfflinePaymentMethodsControllerTest extends WC_REST_Unit_Test_Case {
 	/**
 	 * The ID of the store admin user.
 	 *
+	 * Shared across the class for REST authentication; created once in wpSetUpBeforeClass().
+	 *
 	 * @var int
 	 */
-	protected $store_admin_id;
+	protected static $store_admin_id;
+
+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$store_admin_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}

 	/**
 	 * Set up test.
@@ -46,8 +57,7 @@ class OfflinePaymentMethodsControllerTest extends WC_REST_Unit_Test_Case {
 	public function setUp(): void {
 		parent::setUp();

-		$this->store_admin_id = $this->factory->user->create( array( 'role' => 'administrator' ) );
-		wp_set_current_user( $this->store_admin_id );
+		wp_set_current_user( self::$store_admin_id );

 		$this->mock_payments_service = $this->getMockBuilder( Payments::class )
 			->disableOriginalConstructor()
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/PaymentGateways/PaymentGatewaysSettingsControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/PaymentGateways/PaymentGatewaysSettingsControllerTest.php
index b1ea340a787..c8d2873e259 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/PaymentGateways/PaymentGatewaysSettingsControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/PaymentGateways/PaymentGatewaysSettingsControllerTest.php
@@ -30,11 +30,20 @@ class PaymentGatewaysSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	protected Controller $sut;

 	/**
-	 * The ID of the store admin user.
+	 * Shared admin user used for REST authentication across all tests in the class.
 	 *
 	 * @var int
 	 */
-	protected $store_admin_id;
+	protected static $store_admin_id;
+
+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$store_admin_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}

 	/**
 	 * Set up test.
@@ -42,8 +51,7 @@ class PaymentGatewaysSettingsControllerTest extends WC_REST_Unit_Test_Case {
 	public function setUp(): void {
 		parent::setUp();

-		$this->store_admin_id = $this->factory->user->create( array( 'role' => 'administrator' ) );
-		wp_set_current_user( $this->store_admin_id );
+		wp_set_current_user( self::$store_admin_id );

 		// Inject the mock gateway directly — avoids filter pollution and a second init() call.
 		WC()->payment_gateways()->payment_gateways[] = new WCGatewayMockPassword();
diff --git a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Tax/TaxControllerTest.php b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Tax/TaxControllerTest.php
index 2f18e3f5aed..c3b001a398f 100644
--- a/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Tax/TaxControllerTest.php
+++ b/plugins/woocommerce/tests/php/src/Internal/RestApi/Routes/V4/Settings/Tax/TaxControllerTest.php
@@ -27,11 +27,20 @@ class TaxControllerTest extends WC_REST_Unit_Test_Case {
 	protected $sut;

 	/**
-	 * The ID of the store admin user.
+	 * The ID of the store admin user, shared across all tests in the class for REST authentication.
 	 *
 	 * @var int
 	 */
-	protected $store_admin_id;
+	protected static $store_admin_id;
+
+	/**
+	 * Create the shared admin user once for the whole class.
+	 *
+	 * @param object $factory Factory object.
+	 */
+	public static function wpSetUpBeforeClass( $factory ) {
+		self::$store_admin_id = $factory->user->create( array( 'role' => 'administrator' ) );
+	}

 	/**
 	 * Set up test.
@@ -39,8 +48,7 @@ class TaxControllerTest extends WC_REST_Unit_Test_Case {
 	public function setUp(): void {
 		parent::setUp();

-		$this->store_admin_id = $this->factory->user->create( array( 'role' => 'administrator' ) );
-		wp_set_current_user( $this->store_admin_id );
+		wp_set_current_user( self::$store_admin_id );

 		$schema    = new TaxSettingsSchema();
 		$this->sut = new Controller();
@@ -48,14 +56,6 @@ class TaxControllerTest extends WC_REST_Unit_Test_Case {
 		$this->sut->register_routes();
 	}

-	/**
-	 * Tear down test.
-	 */
-	public function tearDown(): void {
-		wp_delete_user( $this->store_admin_id );
-		parent::tearDown();
-	}
-
 	/**
 	 * Test getting tax settings by a user without the needed capabilities.
 	 */