' . esc_html__('Akkedli Connector', 'akkedli-connector') . ' ' . esc_html__('requires WooCommerce to be installed and active.', 'akkedli-connector') . '

'; } // Declare WooCommerce HPOS compatibility add_action('before_woocommerce_init', function () { if (class_exists('\Automattic\WooCommerce\Utilities\FeaturesUtil')) { \Automattic\WooCommerce\Utilities\FeaturesUtil::declare_compatibility('custom_order_tables', __FILE__, true); \Automattic\WooCommerce\Utilities\FeaturesUtil::declare_compatibility('orders_cache', __FILE__, true); } }); /** * Main Plugin Class */ class Akkedli_Connector { private static $instance = null; public static function get_instance() { if (null === self::$instance) { self::$instance = new self(); } return self::$instance; } public function __construct() { $this->includes(); $this->init_hooks(); } private function includes() { require_once AKKEDLI_PLUGIN_PATH . 'includes/class-akkedli-settings.php'; require_once AKKEDLI_PLUGIN_PATH . 'includes/class-akkedli-order-handler.php'; require_once AKKEDLI_PLUGIN_PATH . 'includes/class-akkedli-api-handler.php'; } private function init_hooks() { add_action('admin_menu', array($this, 'add_admin_menu')); add_action('admin_enqueue_scripts', array($this, 'enqueue_admin_styles')); // Register custom order status add_action('init', array($this, 'register_custom_order_status')); add_filter('wc_order_statuses', array($this, 'add_custom_order_status')); add_filter('woocommerce_reports_order_statuses', array($this, 'include_status_in_reports')); // One-Click Setup: Handle auto_connect handshake add_action('admin_init', array($this, 'handle_auto_connect')); // Initialize handlers add_action('init', array($this, 'init')); } /** * Handle One-Click Auto Connect from Akkedli Dashboard * URL format: /wp-admin/admin.php?page=akkedli-connector&action=auto_connect&api_key=xxx&webhook_url=xxx&return_url=xxx */ public function handle_auto_connect() { // Check if this is an auto_connect request if (!isset($_GET['action']) || sanitize_text_field(wp_unslash($_GET['action'])) !== 'auto_connect') { return; } // Security: Must be on our settings page if (!isset($_GET['page']) || sanitize_text_field(wp_unslash($_GET['page'])) !== 'akkedli-connector') { return; } // Security: User must be logged in and have admin permissions if (!is_user_logged_in() || !current_user_can('manage_woocommerce')) { wp_die( esc_html__('You must be logged in as an administrator to connect Akkedli.', 'akkedli-connector'), esc_html__('Permission Denied', 'akkedli-connector'), array('response' => 403) ); } // CRITICAL: Verify nonce to prevent CSRF attacks $nonce = isset($_GET['_akkedli_nonce']) ? sanitize_text_field(wp_unslash($_GET['_akkedli_nonce'])) : ''; if (empty($nonce) || !wp_verify_nonce($nonce, 'akkedli_auto_connect')) { wp_die( esc_html__('Security check failed. Please try connecting again from the Akkedli Dashboard.', 'akkedli-connector'), esc_html__('Security Error', 'akkedli-connector'), array('response' => 403) ); } // Get and validate parameters $api_key = isset($_GET['api_key']) ? sanitize_text_field(wp_unslash($_GET['api_key'])) : ''; $webhook_url = isset($_GET['webhook_url']) ? esc_url_raw(wp_unslash($_GET['webhook_url'])) : ''; $return_url = isset($_GET['return_url']) ? esc_url_raw(wp_unslash($_GET['return_url'])) : ''; // Validate required fields if (empty($api_key) || empty($webhook_url)) { wp_safe_redirect(admin_url('admin.php?page=akkedli-connector&error=missing_params')); exit; } // Save settings update_option('akkedli_api_key', sanitize_text_field($api_key)); update_option('akkedli_webhook_url', esc_url_raw($webhook_url)); update_option('akkedli_api_key_validated', 1); update_option('akkedli_connected_at', current_time('mysql')); update_option('akkedli_store_domain', home_url()); // Prepare success redirect if (!empty($return_url)) { // Redirect back to Akkedli Dashboard with success status $redirect_url = add_query_arg(array( 'status' => 'success', 'domain' => rawurlencode(home_url()), 'store_name' => rawurlencode(get_bloginfo('name')), ), $return_url); wp_redirect(esc_url_raw($redirect_url)); // phpcs:ignore WordPress.Security.SafeRedirect.wp_redirect_wp_redirect -- Redirecting to external Akkedli Dashboard URL. exit; } // If no return URL, stay on settings page with success message wp_safe_redirect(admin_url('admin.php?page=akkedli-connector&connected=1')); exit; } public function init() { new Akkedli_Settings(); new Akkedli_Order_Handler(); new Akkedli_API_Handler(); } /** * Register custom order status: Confirmed by Akkedli */ public function register_custom_order_status() { register_post_status('wc-akkedli-confirmed', array( 'label' => _x('Confirmed by Akkedli', 'Order status', 'akkedli-connector'), 'public' => true, 'exclude_from_search' => false, 'show_in_admin_all_list' => true, 'show_in_admin_status_list' => true, /* translators: %s: number of orders with this status */ 'label_count' => _n_noop( 'Confirmed by Akkedli (%s)', 'Confirmed by Akkedli (%s)', 'akkedli-connector' ) )); } /** * Add custom status to WooCommerce order statuses */ public function add_custom_order_status($order_statuses) { $new_statuses = array(); foreach ($order_statuses as $key => $status) { $new_statuses[$key] = $status; // Add our status after 'processing' if ('wc-processing' === $key) { $new_statuses['wc-akkedli-confirmed'] = _x('Confirmed by Akkedli', 'Order status', 'akkedli-connector'); } } return $new_statuses; } /** * Include custom status in reports */ public function include_status_in_reports($statuses) { $statuses[] = 'akkedli-confirmed'; return $statuses; } /** * Add admin menu */ public function add_admin_menu() { // Akkedli Logo icon (SVG) $icon = 'data:image/svg+xml;base64,' . base64_encode(' '); add_menu_page( 'Akkedli', 'Akkedli', 'manage_woocommerce', 'akkedli-connector', array($this, 'render_settings_page'), $icon, 56 ); } /** * Render settings page */ public function render_settings_page() { include AKKEDLI_PLUGIN_PATH . 'templates/admin-settings.php'; } /** * Enqueue admin styles */ public function enqueue_admin_styles($hook) { if (strpos($hook, 'akkedli') === false) { return; } wp_enqueue_style( 'akkedli-admin-style', AKKEDLI_PLUGIN_URL . 'assets/css/admin.css', array(), AKKEDLI_VERSION ); // Custom status color (inline) wp_add_inline_style('akkedli-admin-style', ' .order-status.status-akkedli-confirmed, mark.order-status.status-akkedli-confirmed { background: #dcfce7 !important; color: #15803d !important; } '); } } // Initialize plugin add_action('plugins_loaded', function () { Akkedli_Connector::get_instance(); }); // Activation hook register_activation_hook(__FILE__, function () { flush_rewrite_rules(); }); // Deactivation hook register_deactivation_hook(__FILE__, function () { flush_rewrite_rules(); });