mirror of
https://github.com/wp-graphql/wp-graphql-woocommerce.git
synced 2026-08-14 12:53:44 +02:00
* feat: add authenticated download URLs for headless frontends - Add downloadNonce and downloadUrl fields to DownloadableItem type using the existing Protected Router session transfer pattern - Add preAuthDownloadUrl field (toggleable via settings) that generates tokenized download URLs for direct file access without cookie auth - Add download_url nonce handling to Protected_Router - Add enable_pre_auth_download_urls and download_url_nonce_param settings - Add GraphQLE2E helpers for checkout and account shortcode pages - Rewrite ProtectedRouterCest to test redirect flow without JS-dependent page content assertions, add account and payment method URL tests - Add DownloadableItemAuthCest with 5 e2e tests covering both options * fix: test suite stability and code coverage collection - Add WC_Unit_Tests_Bootstrap stub to wpunit bootstrap to bypass wc_get_product_visibility_term_ids static cache between suites - Add setWooGraphQLSetting helper to GraphQLE2E for safe individual field updates to woographql_settings option with proper defaults - Update all functional tests to use setWooGraphQLSetting instead of replacing the entire woographql_settings option - Fix createRelated factory to use explicit shared category instead of relying on default Uncategorized category - Add download_url to ProtectedRouterTest nonce names assertion - Remove debug logs from ProductQueriesTest and ProductsQueriesTest - Fix CI workflow to run suites separately and aggregate coverage via phpcov merge - Wire c3.php into WordPress index.php for remote coverage collection - Update .coveralls.yml service_name to github-actions - Clean up Xdebug 2 settings in Dockerfile * chore: Linter compliances met * fix: ensure tests/_output is writable for c3.php coverage collection * devops: .env.docker removed from setup * devops: split CI into separate jobs per suite with retry and coverage aggregation * devops: add +Coverage indicator to CI job names * devops: add --fail-fast to first run, fix retry to mark job as passing on retry success
147 lines
3.8 KiB
PHP
147 lines
3.8 KiB
PHP
<?php
|
|
/**
|
|
* WPGraphQL test case
|
|
*
|
|
* For testing WPGraphQL responses.
|
|
*
|
|
* @since 0.8.0
|
|
* @package Tests\WPGraphQL\TestCase
|
|
*/
|
|
namespace Tests\WPGraphQL\WooCommerce\TestCase;
|
|
|
|
use Automattic\WooCommerce\Internal\ProductDownloads\ApprovedDirectories\Register as Download_Directories;
|
|
|
|
class WooGraphQLTestCase extends \Tests\WPGraphQL\TestCase\WPGraphQLTestCase {
|
|
/**
|
|
* Holds the User ID of an user with the "shop_manager" role.
|
|
* For use through the tests for purpose of testing user access levels.
|
|
*
|
|
* @var integer
|
|
*/
|
|
protected $shop_manager;
|
|
|
|
/**
|
|
* Holds the User ID of an user with the "customer/subscriber" role.
|
|
* For use through the tests for purpose of testing user access levels.
|
|
*
|
|
* @var integer
|
|
*/
|
|
protected $customer;
|
|
|
|
/**
|
|
* Creates users and loads factories.
|
|
*/
|
|
public function setUp(): void {
|
|
parent::setUp();
|
|
|
|
// Flush the object cache to prevent stale WooCommerce product
|
|
// data from leaking between tests (e.g. related product lookups,
|
|
// featured product queries, product meta cache groups).
|
|
wp_cache_flush();
|
|
|
|
|
|
// Load factories.
|
|
$factories = [
|
|
'Product',
|
|
'ProductVariation',
|
|
'Cart',
|
|
'Coupon',
|
|
'Customer',
|
|
'ShippingZone',
|
|
'TaxClass',
|
|
'TaxRate',
|
|
'Order',
|
|
'Refund',
|
|
'PaymentToken',
|
|
];
|
|
|
|
foreach ( $factories as $factory ) {
|
|
$factory_name = strtolower( preg_replace( '/\B([A-Z])/', '_$1', $factory ) );
|
|
$factory_class = '\\Tests\\WPGraphQL\\WooCommerce\\Factory\\' . $factory . 'Factory';
|
|
$this->factory->{$factory_name} = new $factory_class( $this->factory );
|
|
}
|
|
|
|
$this->factory->shipping_zone->createLegacyFlatRate();
|
|
|
|
// Create test users.
|
|
$this->shop_manager = $this->factory->user->create( [ 'role' => 'shop_manager' ] );
|
|
$this->customer = $this->factory->customer->create();
|
|
|
|
// For these tests, we are not concerned with Approved Download Directory functionality.
|
|
wc_get_container()->get( Download_Directories::class )->set_mode( Download_Directories::MODE_DISABLED );
|
|
|
|
// Clear cached schema.
|
|
$this->clearSchema();
|
|
}
|
|
|
|
public function tearDown(): void {
|
|
global $wpdb;
|
|
|
|
\WC()->cart->empty_cart( true );
|
|
$this->factory->product->deleteAttributes();
|
|
|
|
// Clean WooCommerce lookup tables that are not covered by
|
|
// WPBrowser's transaction rollback, preventing stale data
|
|
// from leaking into subsequent test queries.
|
|
$wpdb->query( "DELETE FROM {$wpdb->prefix}wc_product_meta_lookup" );
|
|
$wpdb->query( "DELETE FROM {$wpdb->prefix}wc_product_attributes_lookup" );
|
|
|
|
// then
|
|
parent::tearDown();
|
|
}
|
|
|
|
/**
|
|
* Logs in as a "shop manager"
|
|
*/
|
|
protected function loginAsShopManager() {
|
|
$this->loginAs( $this->shop_manager );
|
|
}
|
|
|
|
/**
|
|
* Logs in as a "customer"
|
|
*/
|
|
protected function loginAsCustomer() {
|
|
$this->loginAs( $this->customer );
|
|
}
|
|
|
|
/**
|
|
* Logs in as a specific user
|
|
*/
|
|
protected function loginAs( $customer_id = 0 ) {
|
|
wp_set_current_user( $customer_id );
|
|
\WC()->customer = new \WC_Customer( get_current_user_id(), true );
|
|
\WC()->session->init();
|
|
}
|
|
|
|
/**
|
|
* Logs out current user.
|
|
*/
|
|
protected function logout() {
|
|
wp_set_current_user( 0 );
|
|
}
|
|
|
|
/**
|
|
* The death of `! empty( $v ) ? apply_filters( $v ) : null;`
|
|
*
|
|
* @param array|mixed $possible Variable whose existence has to be verified, or
|
|
* an array containing the variable followed by a decorated value to be returned.
|
|
* @param mixed $default Default value to be returned if $possible doesn't exist.
|
|
*
|
|
* @return mixed
|
|
*/
|
|
protected function maybe( $possible, $custom_default = null ) {
|
|
if ( null === $custom_default ) {
|
|
$default = static::IS_NULL;
|
|
} else {
|
|
$default = $custom_default;
|
|
}
|
|
|
|
if ( is_array( $possible ) && 2 === count( $possible ) ) {
|
|
list( $possible, $decorated ) = $possible;
|
|
} else {
|
|
$decorated = $possible;
|
|
}
|
|
return ! empty( $possible ) ? $decorated : $default;
|
|
}
|
|
}
|