feat: Add product images support with WP Media Library integration
- Add WP Media Library integration for product and variation images - Support images array (URLs) conversion to attachment IDs - Add images array to API responses (Admin & Customer SPA) - Implement drag-and-drop sortable images in Admin product form - Add image gallery thumbnails in Customer SPA product page - Initialize WooCommerce session for guest cart operations - Fix product variations and attributes display in Customer SPA - Add variation image field in Admin SPA Changes: - includes/Api/ProductsController.php: Handle images array, add to responses - includes/Frontend/ShopController.php: Add images array for customer SPA - includes/Frontend/CartController.php: Initialize WC session for guests - admin-spa/src/lib/wp-media.ts: Add openWPMediaGallery function - admin-spa/src/routes/Products/partials/tabs/GeneralTab.tsx: WP Media + sortable images - admin-spa/src/routes/Products/partials/tabs/VariationsTab.tsx: Add variation image field - customer-spa/src/pages/Product/index.tsx: Add gallery thumbnails display
This commit is contained in:
373
includes/Api/Controllers/CartController.php
Normal file
373
includes/Api/Controllers/CartController.php
Normal file
@@ -0,0 +1,373 @@
|
||||
<?php
|
||||
namespace WooNooW\Api\Controllers;
|
||||
|
||||
use WP_REST_Controller;
|
||||
use WP_REST_Response;
|
||||
use WP_Error;
|
||||
|
||||
/**
|
||||
* Cart Controller
|
||||
* Handles cart operations via REST API
|
||||
*/
|
||||
class CartController extends WP_REST_Controller {
|
||||
|
||||
/**
|
||||
* Register routes
|
||||
*/
|
||||
public function register_routes() {
|
||||
$namespace = 'woonoow/v1';
|
||||
|
||||
// Get cart
|
||||
register_rest_route($namespace, '/cart', [
|
||||
'methods' => 'GET',
|
||||
'callback' => [$this, 'get_cart'],
|
||||
'permission_callback' => '__return_true',
|
||||
]);
|
||||
|
||||
// Add to cart
|
||||
register_rest_route($namespace, '/cart/add', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'add_to_cart'],
|
||||
'permission_callback' => '__return_true',
|
||||
'args' => [
|
||||
'product_id' => [
|
||||
'required' => true,
|
||||
'type' => 'integer',
|
||||
'sanitize_callback' => 'absint',
|
||||
],
|
||||
'quantity' => [
|
||||
'required' => false,
|
||||
'type' => 'integer',
|
||||
'default' => 1,
|
||||
'sanitize_callback' => 'absint',
|
||||
],
|
||||
'variation_id' => [
|
||||
'required' => false,
|
||||
'type' => 'integer',
|
||||
'sanitize_callback' => 'absint',
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
// Update cart item
|
||||
register_rest_route($namespace, '/cart/update', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'update_cart_item'],
|
||||
'permission_callback' => '__return_true',
|
||||
'args' => [
|
||||
'cart_item_key' => [
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
],
|
||||
'quantity' => [
|
||||
'required' => true,
|
||||
'type' => 'integer',
|
||||
'sanitize_callback' => 'absint',
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
// Remove from cart
|
||||
register_rest_route($namespace, '/cart/remove', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'remove_from_cart'],
|
||||
'permission_callback' => '__return_true',
|
||||
'args' => [
|
||||
'cart_item_key' => [
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
// Clear cart
|
||||
register_rest_route($namespace, '/cart/clear', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'clear_cart'],
|
||||
'permission_callback' => '__return_true',
|
||||
]);
|
||||
|
||||
// Apply coupon
|
||||
register_rest_route($namespace, '/cart/apply-coupon', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'apply_coupon'],
|
||||
'permission_callback' => '__return_true',
|
||||
'args' => [
|
||||
'coupon_code' => [
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
'sanitize_callback' => 'sanitize_text_field',
|
||||
],
|
||||
],
|
||||
]);
|
||||
|
||||
// Remove coupon
|
||||
register_rest_route($namespace, '/cart/remove-coupon', [
|
||||
'methods' => 'POST',
|
||||
'callback' => [$this, 'remove_coupon'],
|
||||
'permission_callback' => '__return_true',
|
||||
'args' => [
|
||||
'coupon_code' => [
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
'sanitize_callback' => 'sanitize_text_field',
|
||||
],
|
||||
],
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get cart contents
|
||||
*/
|
||||
public function get_cart($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$cart = WC()->cart;
|
||||
|
||||
return new WP_REST_Response([
|
||||
'items' => $this->format_cart_items($cart->get_cart()),
|
||||
'totals' => [
|
||||
'subtotal' => $cart->get_subtotal(),
|
||||
'subtotal_tax' => $cart->get_subtotal_tax(),
|
||||
'discount_total' => $cart->get_discount_total(),
|
||||
'discount_tax' => $cart->get_discount_tax(),
|
||||
'shipping_total' => $cart->get_shipping_total(),
|
||||
'shipping_tax' => $cart->get_shipping_tax(),
|
||||
'fee_total' => $cart->get_fee_total(),
|
||||
'fee_tax' => $cart->get_fee_tax(),
|
||||
'total' => $cart->get_total(''),
|
||||
'total_tax' => $cart->get_total_tax(),
|
||||
],
|
||||
'coupons' => $cart->get_applied_coupons(),
|
||||
'needs_shipping' => $cart->needs_shipping(),
|
||||
'needs_payment' => $cart->needs_payment(),
|
||||
'item_count' => $cart->get_cart_contents_count(),
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add product to cart
|
||||
*/
|
||||
public function add_to_cart($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$product_id = $request->get_param('product_id');
|
||||
$quantity = $request->get_param('quantity') ?: 1;
|
||||
$variation_id = $request->get_param('variation_id') ?: 0;
|
||||
|
||||
// Validate product
|
||||
$product = wc_get_product($product_id);
|
||||
if (!$product) {
|
||||
return new WP_Error('invalid_product', 'Product not found', ['status' => 404]);
|
||||
}
|
||||
|
||||
// Check stock
|
||||
if (!$product->is_in_stock()) {
|
||||
return new WP_Error('out_of_stock', 'Product is out of stock', ['status' => 400]);
|
||||
}
|
||||
|
||||
// Add to cart
|
||||
$cart_item_key = WC()->cart->add_to_cart($product_id, $quantity, $variation_id);
|
||||
|
||||
if (!$cart_item_key) {
|
||||
return new WP_Error('add_to_cart_failed', 'Failed to add product to cart', ['status' => 400]);
|
||||
}
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'cart_item_key' => $cart_item_key,
|
||||
'message' => sprintf('%s has been added to your cart.', $product->get_name()),
|
||||
'cart' => $this->get_cart($request)->data,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update cart item quantity
|
||||
*/
|
||||
public function update_cart_item($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$cart_item_key = $request->get_param('cart_item_key');
|
||||
$quantity = $request->get_param('quantity');
|
||||
|
||||
// Validate cart item
|
||||
$cart = WC()->cart->get_cart();
|
||||
if (!isset($cart[$cart_item_key])) {
|
||||
return new WP_Error('invalid_cart_item', 'Cart item not found', ['status' => 404]);
|
||||
}
|
||||
|
||||
// Update quantity
|
||||
$updated = WC()->cart->set_quantity($cart_item_key, $quantity);
|
||||
|
||||
if (!$updated) {
|
||||
return new WP_Error('update_failed', 'Failed to update cart item', ['status' => 400]);
|
||||
}
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'message' => 'Cart updated successfully',
|
||||
'cart' => $this->get_cart($request)->data,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove item from cart
|
||||
*/
|
||||
public function remove_from_cart($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$cart_item_key = $request->get_param('cart_item_key');
|
||||
|
||||
// Validate cart item
|
||||
$cart = WC()->cart->get_cart();
|
||||
if (!isset($cart[$cart_item_key])) {
|
||||
return new WP_Error('invalid_cart_item', 'Cart item not found', ['status' => 404]);
|
||||
}
|
||||
|
||||
// Remove item
|
||||
$removed = WC()->cart->remove_cart_item($cart_item_key);
|
||||
|
||||
if (!$removed) {
|
||||
return new WP_Error('remove_failed', 'Failed to remove cart item', ['status' => 400]);
|
||||
}
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'message' => 'Item removed from cart',
|
||||
'cart' => $this->get_cart($request)->data,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear cart
|
||||
*/
|
||||
public function clear_cart($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
WC()->cart->empty_cart();
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'message' => 'Cart cleared successfully',
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Apply coupon
|
||||
*/
|
||||
public function apply_coupon($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$coupon_code = $request->get_param('coupon_code');
|
||||
|
||||
// Apply coupon
|
||||
$applied = WC()->cart->apply_coupon($coupon_code);
|
||||
|
||||
if (!$applied) {
|
||||
return new WP_Error('coupon_failed', 'Failed to apply coupon', ['status' => 400]);
|
||||
}
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'message' => 'Coupon applied successfully',
|
||||
'cart' => $this->get_cart($request)->data,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove coupon
|
||||
*/
|
||||
public function remove_coupon($request) {
|
||||
if (!function_exists('WC')) {
|
||||
return new WP_Error('woocommerce_not_active', 'WooCommerce is not active', ['status' => 500]);
|
||||
}
|
||||
|
||||
// Ensure cart is initialized
|
||||
if (is_null(WC()->cart)) {
|
||||
wc_load_cart();
|
||||
}
|
||||
|
||||
$coupon_code = $request->get_param('coupon_code');
|
||||
|
||||
// Remove coupon
|
||||
$removed = WC()->cart->remove_coupon($coupon_code);
|
||||
|
||||
if (!$removed) {
|
||||
return new WP_Error('coupon_remove_failed', 'Failed to remove coupon', ['status' => 400]);
|
||||
}
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'message' => 'Coupon removed successfully',
|
||||
'cart' => $this->get_cart($request)->data,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Format cart items for response
|
||||
*/
|
||||
private function format_cart_items($cart_items) {
|
||||
$formatted = [];
|
||||
|
||||
foreach ($cart_items as $cart_item_key => $cart_item) {
|
||||
$product = $cart_item['data'];
|
||||
|
||||
$formatted[] = [
|
||||
'key' => $cart_item_key,
|
||||
'product_id' => $cart_item['product_id'],
|
||||
'variation_id' => $cart_item['variation_id'],
|
||||
'quantity' => $cart_item['quantity'],
|
||||
'name' => $product->get_name(),
|
||||
'price' => $product->get_price(),
|
||||
'subtotal' => $cart_item['line_subtotal'],
|
||||
'total' => $cart_item['line_total'],
|
||||
'image' => wp_get_attachment_image_url($product->get_image_id(), 'thumbnail'),
|
||||
'permalink' => $product->get_permalink(),
|
||||
];
|
||||
}
|
||||
|
||||
return $formatted;
|
||||
}
|
||||
}
|
||||
317
includes/Api/Controllers/SettingsController.php
Normal file
317
includes/Api/Controllers/SettingsController.php
Normal file
@@ -0,0 +1,317 @@
|
||||
<?php
|
||||
namespace WooNooW\Api\Controllers;
|
||||
|
||||
use WP_REST_Controller;
|
||||
use WP_REST_Server;
|
||||
use WP_REST_Request;
|
||||
use WP_REST_Response;
|
||||
use WP_Error;
|
||||
|
||||
/**
|
||||
* Settings Controller
|
||||
* Handles Customer SPA settings via REST API
|
||||
*/
|
||||
class SettingsController extends WP_REST_Controller {
|
||||
|
||||
/**
|
||||
* Namespace
|
||||
*/
|
||||
protected $namespace = 'woonoow/v1';
|
||||
|
||||
/**
|
||||
* Rest base
|
||||
*/
|
||||
protected $rest_base = 'settings';
|
||||
|
||||
/**
|
||||
* Register routes
|
||||
*/
|
||||
public function register_routes() {
|
||||
// Get/Update Customer SPA settings
|
||||
register_rest_route($this->namespace, '/' . $this->rest_base . '/customer-spa', [
|
||||
[
|
||||
'methods' => WP_REST_Server::READABLE,
|
||||
'callback' => [$this, 'get_customer_spa_settings'],
|
||||
'permission_callback' => [$this, 'get_settings_permissions_check'],
|
||||
],
|
||||
[
|
||||
'methods' => WP_REST_Server::CREATABLE,
|
||||
'callback' => [$this, 'update_customer_spa_settings'],
|
||||
'permission_callback' => [$this, 'update_settings_permissions_check'],
|
||||
'args' => $this->get_customer_spa_schema(),
|
||||
],
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get Customer SPA settings
|
||||
*/
|
||||
public function get_customer_spa_settings(WP_REST_Request $request) {
|
||||
$settings = $this->get_default_settings();
|
||||
$saved_settings = get_option('woonoow_customer_spa_settings', []);
|
||||
|
||||
// Merge with saved settings
|
||||
if (!empty($saved_settings)) {
|
||||
$settings = array_replace_recursive($settings, $saved_settings);
|
||||
}
|
||||
|
||||
// Add enabled flag
|
||||
$settings['enabled'] = get_option('woonoow_customer_spa_enabled', false);
|
||||
|
||||
return new WP_REST_Response($settings, 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update Customer SPA settings
|
||||
*/
|
||||
public function update_customer_spa_settings(WP_REST_Request $request) {
|
||||
$params = $request->get_json_params();
|
||||
|
||||
// Extract enabled flag
|
||||
if (isset($params['enabled'])) {
|
||||
update_option('woonoow_customer_spa_enabled', (bool) $params['enabled']);
|
||||
unset($params['enabled']);
|
||||
}
|
||||
|
||||
// Get current settings
|
||||
$current_settings = get_option('woonoow_customer_spa_settings', $this->get_default_settings());
|
||||
|
||||
// Merge with new settings
|
||||
$new_settings = array_replace_recursive($current_settings, $params);
|
||||
|
||||
// Validate settings
|
||||
$validated = $this->validate_settings($new_settings);
|
||||
if (is_wp_error($validated)) {
|
||||
return $validated;
|
||||
}
|
||||
|
||||
// Save settings
|
||||
update_option('woonoow_customer_spa_settings', $new_settings);
|
||||
|
||||
// Return updated settings
|
||||
$new_settings['enabled'] = get_option('woonoow_customer_spa_enabled', false);
|
||||
|
||||
return new WP_REST_Response([
|
||||
'success' => true,
|
||||
'data' => $new_settings,
|
||||
], 200);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get default settings
|
||||
*/
|
||||
private function get_default_settings() {
|
||||
return [
|
||||
'mode' => 'disabled',
|
||||
'checkoutPages' => [
|
||||
'checkout' => true,
|
||||
'thankyou' => true,
|
||||
'account' => true,
|
||||
'cart' => false,
|
||||
],
|
||||
'layout' => 'modern',
|
||||
'branding' => [
|
||||
'logo' => '',
|
||||
'favicon' => '',
|
||||
'siteName' => get_bloginfo('name'),
|
||||
],
|
||||
'colors' => [
|
||||
'primary' => '#3B82F6',
|
||||
'secondary' => '#8B5CF6',
|
||||
'accent' => '#10B981',
|
||||
'background' => '#FFFFFF',
|
||||
'text' => '#1F2937',
|
||||
],
|
||||
'typography' => [
|
||||
'preset' => 'professional',
|
||||
'customFonts' => null,
|
||||
],
|
||||
'menus' => [
|
||||
'primary' => 0,
|
||||
'footer' => 0,
|
||||
],
|
||||
'homepage' => [
|
||||
'sections' => [
|
||||
[
|
||||
'id' => 'hero-1',
|
||||
'type' => 'hero',
|
||||
'enabled' => true,
|
||||
'order' => 0,
|
||||
'config' => [],
|
||||
],
|
||||
[
|
||||
'id' => 'featured-1',
|
||||
'type' => 'featured',
|
||||
'enabled' => true,
|
||||
'order' => 1,
|
||||
'config' => [],
|
||||
],
|
||||
[
|
||||
'id' => 'categories-1',
|
||||
'type' => 'categories',
|
||||
'enabled' => true,
|
||||
'order' => 2,
|
||||
'config' => [],
|
||||
],
|
||||
],
|
||||
],
|
||||
'product' => [
|
||||
'layout' => 'standard',
|
||||
'showRelatedProducts' => true,
|
||||
'showReviews' => true,
|
||||
],
|
||||
'checkout' => [
|
||||
'style' => 'onepage',
|
||||
'enableGuestCheckout' => true,
|
||||
'showTrustBadges' => true,
|
||||
'showOrderSummary' => 'sidebar',
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate settings
|
||||
*/
|
||||
private function validate_settings($settings) {
|
||||
// Validate mode
|
||||
if (isset($settings['mode']) && !in_array($settings['mode'], ['disabled', 'full', 'checkout_only'])) {
|
||||
return new WP_Error(
|
||||
'invalid_mode',
|
||||
__('Invalid mode. Must be disabled, full, or checkout_only.', 'woonoow'),
|
||||
['status' => 400]
|
||||
);
|
||||
}
|
||||
|
||||
// Validate layout
|
||||
if (isset($settings['layout']) && !in_array($settings['layout'], ['classic', 'modern', 'boutique', 'launch'])) {
|
||||
return new WP_Error(
|
||||
'invalid_layout',
|
||||
__('Invalid layout. Must be classic, modern, boutique, or launch.', 'woonoow'),
|
||||
['status' => 400]
|
||||
);
|
||||
}
|
||||
|
||||
// Validate colors (hex format)
|
||||
if (isset($settings['colors'])) {
|
||||
foreach ($settings['colors'] as $key => $color) {
|
||||
if (!preg_match('/^#[a-fA-F0-9]{6}$/', $color)) {
|
||||
return new WP_Error(
|
||||
'invalid_color',
|
||||
sprintf(__('Invalid color format for %s. Must be hex format (#RRGGBB).', 'woonoow'), $key),
|
||||
['status' => 400]
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Validate typography preset
|
||||
if (isset($settings['typography']['preset'])) {
|
||||
$valid_presets = ['professional', 'modern', 'elegant', 'tech', 'custom'];
|
||||
if (!in_array($settings['typography']['preset'], $valid_presets)) {
|
||||
return new WP_Error(
|
||||
'invalid_typography',
|
||||
__('Invalid typography preset.', 'woonoow'),
|
||||
['status' => 400]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get Customer SPA settings schema
|
||||
*/
|
||||
private function get_customer_spa_schema() {
|
||||
return [
|
||||
'mode' => [
|
||||
'type' => 'string',
|
||||
'enum' => ['disabled', 'full', 'checkout_only'],
|
||||
'description' => __('Customer SPA mode', 'woonoow'),
|
||||
],
|
||||
'checkoutPages' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'checkout' => ['type' => 'boolean'],
|
||||
'thankyou' => ['type' => 'boolean'],
|
||||
'account' => ['type' => 'boolean'],
|
||||
'cart' => ['type' => 'boolean'],
|
||||
],
|
||||
],
|
||||
'layout' => [
|
||||
'type' => 'string',
|
||||
'enum' => ['classic', 'modern', 'boutique', 'launch'],
|
||||
'description' => __('Master layout', 'woonoow'),
|
||||
],
|
||||
'branding' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'logo' => ['type' => 'string'],
|
||||
'favicon' => ['type' => 'string'],
|
||||
'siteName' => ['type' => 'string'],
|
||||
],
|
||||
],
|
||||
'colors' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'primary' => ['type' => 'string', 'pattern' => '^#[a-fA-F0-9]{6}$'],
|
||||
'secondary' => ['type' => 'string', 'pattern' => '^#[a-fA-F0-9]{6}$'],
|
||||
'accent' => ['type' => 'string', 'pattern' => '^#[a-fA-F0-9]{6}$'],
|
||||
'background' => ['type' => 'string', 'pattern' => '^#[a-fA-F0-9]{6}$'],
|
||||
'text' => ['type' => 'string', 'pattern' => '^#[a-fA-F0-9]{6}$'],
|
||||
],
|
||||
],
|
||||
'typography' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'preset' => ['type' => 'string', 'enum' => ['professional', 'modern', 'elegant', 'tech', 'custom']],
|
||||
'customFonts' => ['type' => ['object', 'null']],
|
||||
],
|
||||
],
|
||||
'menus' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'primary' => ['type' => 'integer'],
|
||||
'footer' => ['type' => 'integer'],
|
||||
],
|
||||
],
|
||||
'homepage' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'sections' => ['type' => 'array'],
|
||||
],
|
||||
],
|
||||
'product' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'layout' => ['type' => 'string'],
|
||||
'showRelatedProducts' => ['type' => 'boolean'],
|
||||
'showReviews' => ['type' => 'boolean'],
|
||||
],
|
||||
],
|
||||
'checkout' => [
|
||||
'type' => 'object',
|
||||
'properties' => [
|
||||
'style' => ['type' => 'string'],
|
||||
'enableGuestCheckout' => ['type' => 'boolean'],
|
||||
'showTrustBadges' => ['type' => 'boolean'],
|
||||
'showOrderSummary' => ['type' => 'string'],
|
||||
],
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* Check permissions for getting settings
|
||||
*/
|
||||
public function get_settings_permissions_check() {
|
||||
return current_user_can('manage_woocommerce');
|
||||
}
|
||||
|
||||
/**
|
||||
* Check permissions for updating settings
|
||||
*/
|
||||
public function update_settings_permissions_check() {
|
||||
return current_user_can('manage_woocommerce');
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user