diff --git a/includes/class-menu.php b/includes/class-menu.php index 61467adb403e867df8d00d913365ead5f6e1ee91..54e1ccd5ec5bb091d63c52d27feb0a5ea67d1f7a 100644 --- a/includes/class-menu.php +++ b/includes/class-menu.php @@ -6,11 +6,13 @@ use WPCT_ABSTRACT\Menu as BaseMenu; class Menu extends BaseMenu { - static protected $settings_class = '\WPCT_ERP_FORMS\Settings'; + protected static $settings_class = '\WPCT_ERP_FORMS\Settings'; protected function render_page($echo = true) { - $output = parent::render_page(false); - echo apply_filters('wpct_erp_forms_menu_page_content', $output); + printf( + '<div class="wrap" id="wpct-erp-forms">%s</div>', + esc_html__('Loading', 'wpct-erp-forms') + ); } } diff --git a/includes/class-rest-controller.php b/includes/class-rest-controller.php index 3517c953d843830fe51ccf2c22e1767e320e4997..7e29bbff58676ebb64a3a32ff2de68bfbb3d05e5 100644 --- a/includes/class-rest-controller.php +++ b/includes/class-rest-controller.php @@ -10,17 +10,13 @@ class REST_Controller private $namespace = 'wpct'; private $version = 1; - private static $settings = ['wpct-erp-forms_general', 'wpct-erp-forms_api']; + private static $settings = ['general', 'rest-api', 'rpc-api']; private static function error($code, $message, $status) { - return new WP_Error( - $code, - __($message, 'wpct-erp-forms'), - [ - 'status' => $status, - ], - ); + return new WP_Error($code, __($message, 'wpct-erp-forms'), [ + 'status' => $status, + ]); } public function __construct() @@ -32,36 +28,44 @@ class REST_Controller private function init() { - register_rest_route("{$this->namespace}/v{$this->version}", '/erp-forms/forms', [ - 'methods' => WP_REST_Server::READABLE, - 'callback' => function () { - return $this->forms(); - }, - 'permission_callback' => function () { - return $this->permission_callback(); - } - ]); - - register_rest_route("{$this->namespace}/v{$this->version}", '/erp-forms/settings', [ + register_rest_route( + "{$this->namespace}/v{$this->version}", + '/erp-forms/forms', [ 'methods' => WP_REST_Server::READABLE, 'callback' => function () { - return $this->get_settings(); + return $this->forms(); }, 'permission_callback' => function () { return $this->permission_callback(); - } - ], - [ - 'methods' => WP_REST_Server::CREATABLE, - 'callback' => function () { - return $this->set_settings(); }, - 'permission_callback' => function () { - return $this->permission_callback(); - } ] - ]); + ); + + register_rest_route( + "{$this->namespace}/v{$this->version}", + '/erp-forms/settings/', + [ + [ + 'methods' => WP_REST_Server::READABLE, + 'callback' => function () { + return $this->get_settings(); + }, + 'permission_callback' => function () { + return $this->permission_callback(); + }, + ], + [ + 'methods' => WP_REST_Server::CREATABLE, + 'callback' => function () { + return $this->set_settings(); + }, + 'permission_callback' => function () { + return $this->permission_callback(); + }, + ], + ] + ); } private function forms() @@ -77,9 +81,12 @@ class REST_Controller private function get_settings() { - $settings = []; - foreach (self::$settings as $setting_name) { - $settings[$setting_name] = Settings::get_setting($setting_name); + $settings = []; + foreach (self::$settings as $setting) { + $settings[$setting] = Settings::get_setting( + 'wpct-erp-forms', + $setting + ); } return $settings; } @@ -87,25 +94,34 @@ class REST_Controller private function set_settings() { $data = (array) json_decode(file_get_contents('php://input'), true); - $response = []; - foreach (self::$settings as $setting_name) { - if (!isset($data[$setting_name])) continue; - $from = Settings::get_setting($setting_name); - $to = $data[$setting_name]; - foreach (array_keys($from) as $key) { - $to[$key] = isset($to[$key]) ? $to[$key] : $from[$key]; - } - update_option($setting_name, $to); - $response[$setting_name] = $to; - } - - return $response; + $response = []; + foreach (self::$settings as $setting) { + if (!isset($data[$setting])) { + continue; + } + + $from = Settings::get_setting('wpct-erp-forms', $setting); + $to = $data[$setting]; + foreach (array_keys($from) as $key) { + $to[$key] = isset($to[$key]) ? $to[$key] : $from[$key]; + } + update_option('wpct-erp-forms_' . $setting, $to); + $response[$setting] = $to; + } + + return $response; } private function permission_callback() { + // $nonce = $_REQUEST['_wpctnonce']; if (!current_user_can('manage_options')) { - return self::error('rest_unauthorized', 'You can\'t manage wp options', 403); + // if (!wp_verify_nonce($nonce, 'wpct-erp-forms')) { + return self::error( + 'rest_unauthorized', + 'You can\'t manage wp options', + 403 + ); } return true; diff --git a/includes/class-settings.php b/includes/class-settings.php index 7b401afb6154ab6fe603f6574b8ea9343fb0bd8f..554d81735019dcece1215b9427a2ef36fb9c5141 100644 --- a/includes/class-settings.php +++ b/includes/class-settings.php @@ -2,17 +2,56 @@ namespace WPCT_ERP_FORMS; +use Exception; use WPCT_ABSTRACT\Settings as BaseSettings; class Settings extends BaseSettings { + public function __construct($group_name) + { + parent::__construct($group_name); + + add_action( + 'load-settings_page_wpct-erp-forms', + function () { + echo '<style>.wpct-erp-forms_general__backends table tr { display: flex; flex-direction: column; }</style>'; + }, + 10, + 0 + ); + } + + public static function get_backends() + { + $setting = Settings::get_setting('wpct-erp-forms', 'general'); + return array_map(function ($backend) { + return $backend['name']; + }, $setting['backends']); + } + public static function get_forms() { global $wpdb; - if (apply_filters('wpct_is_plugin_active', false, 'contact-form-7/wp-contact-form-7.php')) { - return $wpdb->get_results("SELECT id, post_title title FROM {$wpdb->prefix}posts WHERE post_type = 'wpcf7_contact_form' AND post_status = 'publish'"); - } elseif (apply_filters('wpct_is_plugin_active', false, 'gravityforms/gravityforms.php')) { - return $wpdb->get_results("SELECT id, title FROM {$wpdb->prefix}gf_form WHERE is_active = 1 AND is_trash = 0"); + if ( + apply_filters( + 'wpct_is_plugin_active', + false, + 'contact-form-7/wp-contact-form-7.php' + ) + ) { + return $wpdb->get_results( + "SELECT id, post_title title FROM {$wpdb->prefix}posts WHERE post_type = 'wpcf7_contact_form' AND post_status = 'publish'" + ); + } elseif ( + apply_filters( + 'wpct_is_plugin_active', + false, + 'gravityforms/gravityforms.php' + ) + ) { + return $wpdb->get_results( + "SELECT id, title FROM {$wpdb->prefix}gf_form WHERE is_active = 1 AND is_trash = 0" + ); } } @@ -25,18 +64,42 @@ class Settings extends BaseSettings 'notification_receiver' => [ 'type' => 'string', ], - 'base_url' => [ - 'type' => 'string', - ], - 'api_key' => [ - 'type' => 'string', + 'backends' => [ + 'type' => 'array', + 'items' => [ + 'type' => 'object', + 'properties' => [ + 'name' => ['type' => 'string'], + 'base_url' => ['type' => 'string'], + 'headers' => [ + 'type' => 'array', + 'items' => [ + 'type' => 'object', + 'properties' => [ + 'name' => ['type' => 'string'], + 'value' => ['type' => 'string'], + ], + ], + ], + ], + ], ], ], [ 'notification_receiver' => 'admin@' . $host, - 'base_url' => 'https://erp.' . $host, - 'api_key' => '', - ], + 'backends' => [ + [ + 'name' => 'ERP', + 'base_url' => 'https://erp.' . $host, + 'headers' => [ + [ + 'name' => 'Auhtorization', + 'value' => 'Bearer <erp-backend-token>', + ], + ], + ], + ], + ] ); $this->register_setting( @@ -47,21 +110,23 @@ class Settings extends BaseSettings 'items' => [ 'type' => 'object', 'properties' => [ + 'backend' => ['type' => 'string'], 'form_id' => ['type' => 'string'], 'endpoint' => ['type' => 'string'], 'ref' => ['type' => 'string'], ], - ] - ] + ], + ], ], [ 'forms' => [ [ + 'backend' => 'ERP', 'form_id' => null, 'endpoint' => '/api/crm-lead', - 'ref' => null - ] - ] + 'ref' => null, + ], + ], ] ); @@ -85,6 +150,7 @@ class Settings extends BaseSettings 'items' => [ 'type' => 'object', 'properties' => [ + 'backend' => ['type' => 'string'], 'form_id' => ['type' => 'string'], 'model' => ['type' => 'string'], 'ref' => ['type' => 'string'], @@ -99,40 +165,64 @@ class Settings extends BaseSettings 'database' => 'erp', 'forms' => [ [ + 'backend' => 'ERP', 'form_id' => 0, 'model' => 'crm.lead', 'ref' => null, ], ], - ], + ] ); } - protected function input_render($setting, $field, $value) + protected function input_render($setting, $field, $value, $is_root = false) { if (preg_match('/^forms.*form_id$/', $field)) { return $this->render_forms_dropdown($setting, $field, $value); - } elseif (preg_match('/password$/', $field)) { - return $this->password_input_render($setting, $field, $value); - } + } elseif (preg_match('/^forms.*backend$/', $field)) { + return $this->render_backends_dropdown($setting, $field, $value); + } elseif (preg_match('/password$/', $field)) { + return $this->password_input_render($setting, $field, $value); + } return parent::input_render($setting, $field, $value); } + private function render_backends_dropdown($setting, $field, $value) + { + $setting_name = $this->setting_name($setting); + $backends = self::get_backends(); + $options = array_merge( + ['<option value=""></option>'], + array_map(function ($backend) use ($value) { + $selected = $backend == $value ? 'selected' : ''; + return "<option value='{$backend}' {$selected}>{$backend}</option>"; + }, $backends) + ); + return "<select name='{$setting_name}[{$field}]'>" . + implode('', $options) . + '</select>'; + } + private function render_forms_dropdown($setting, $field, $value) { $setting_name = $this->setting_name($setting); $forms = self::get_forms(); - $options = array_merge(['<option value=""></option>'], array_map(function ($form) use ($value) { - $selected = $form->id == $value ? 'selected' : ''; - return "<option value='{$form->id}' {$selected}>{$form->title}</option>"; - }, $forms)); - return "<select name='{$setting_name}[{$field}]'>" . implode('', $options) . '</select>'; + $options = array_merge( + ['<option value=""></option>'], + array_map(function ($form) use ($value) { + $selected = $form->id == $value ? 'selected' : ''; + return "<option value='{$form->id}' {$selected}>{$form->title}</option>"; + }, $forms) + ); + return "<select name='{$setting_name}[{$field}]'>" . + implode('', $options) . + '</select>'; } - private function password_input_render($setting, $field, $value) - { - $setting_name = $this->setting_name($setting); - return "<input type='password' name='{$setting_name}[{$field}]' value='{$value}' />"; - } + private function password_input_render($setting, $field, $value) + { + $setting_name = $this->setting_name($setting); + return "<input type='password' name='{$setting_name}[{$field}]' value='{$value}' />"; + } } diff --git a/wpct-erp-forms.php b/wpct-erp-forms.php index 08a1fa96ea5dd35a01b1ad7b1361f9337a8122a4..13fa46471397050b8e2f39452a98e1a0db98b516 100755 --- a/wpct-erp-forms.php +++ b/wpct-erp-forms.php @@ -18,7 +18,7 @@ use WPCT_ERP_FORMS\GF\Integration as GFIntegration; use WPCT_ABSTRACT\Plugin as BasePlugin; if (!defined('ABSPATH')) { - exit; + exit(); } define('WPCT_ERP_FORMS_VERSION', '2.0.3'); @@ -34,6 +34,7 @@ require_once 'wpct-i18n/wpct-i18n.php'; require_once 'includes/abstract-integration.php'; require_once 'includes/class-menu.php'; require_once 'includes/class-settings.php'; +require_once 'includes/class-rest-controller.php'; class Wpct_Erp_Forms extends BasePlugin { @@ -49,28 +50,48 @@ class Wpct_Erp_Forms extends BasePlugin { parent::__construct(); - if (apply_filters('wpct_is_plugin_active', false, 'contact-form-7/wp-contact-form-7.php')) { + if ( + apply_filters( + 'wpct_is_plugin_active', + false, + 'contact-form-7/wp-contact-form-7.php' + ) + ) { require_once 'includes/integrations/wpcf7/class-integration.php'; $this->_integrations['wpcf7'] = Wpcf7Integration::get_instance(); - } elseif (apply_filters('wpct_is_plugin_active', false, 'gravityforms/gravityforms.php')) { + } elseif ( + apply_filters( + 'wpct_is_plugin_active', + false, + 'gravityforms/gravityforms.php' + ) + ) { require_once 'includes/integrations/gf/class-integration.php'; $this->_integrations['gf'] = GFIntegration::get_instance(); } - add_filter('plugin_action_links', function ($links, $file) { - if ($file !== plugin_basename(__FILE__)) { - return $links; - } + add_filter( + 'plugin_action_links', + function ($links, $file) { + if ($file !== plugin_basename(__FILE__)) { + return $links; + } - $url = admin_url('options-general.php?page=wpct-erp-forms'); - $label = __('Settings'); - $link = "<a href='{$url}'>{$label}</a>"; - array_unshift($links, $link); - return $links; - }, 5, 2); + $url = admin_url('options-general.php?page=wpct-erp-forms'); + $label = __('Settings'); + $link = "<a href='{$url}'>{$label}</a>"; + array_unshift($links, $link); + return $links; + }, + 5, + 2 + ); add_filter('option_wpct-erp-forms_general', function ($value) { - $http_setting = Settings::get_setting('wpct-http-bridge', 'general'); + $http_setting = Settings::get_setting( + 'wpct-http-bridge', + 'general' + ); foreach ($http_setting as $key => $val) { $value[$key] = $val; } @@ -78,39 +99,74 @@ class Wpct_Erp_Forms extends BasePlugin return $value; }); - add_action('updated_option', function ($option, $from, $to) { - if ($option !== 'wpct-erp-forms_general') { - return; - } - - $http_setting = Settings::get_setting('wpct-http-bridge', 'general'); - $bridge_fields = ['base_url', 'api_key']; - foreach ($bridge_fields as $key) { - $http_setting[$key] = $to[$key]; - } - - update_option('wpct-http-bridge_general', $http_setting); - }, 10, 3); - - add_filter('wpct_erp_forms_form_ref', function ($null, $form_id) { - return $this->get_form_ref($form_id); - }, 10, 2); - - add_filter('option_wpct-erp-forms_rest-api', function ($setting) { - return $this->populate_refs($setting); - }, 10, 1); - - add_filter('option_wpct-erp-forms_rpc-api', function ($setting) { - return $this->populate_refs($setting); - }, 10, 1); + add_action( + 'updated_option', + function ($option, $from, $to) { + if ($option !== 'wpct-erp-forms_general') { + return; + } - add_action('updated_option', function ($option, $from, $to) { - $this->on_option_updated($option, $to); - }, 90, 3); + $http_setting = Settings::get_setting( + 'wpct-http-bridge', + 'general' + ); + $http_setting['backends'] = $to['backends']; + update_option('wpct-http-bridge_general', $http_setting); + }, + 10, + 3 + ); + + add_filter( + 'wpct_erp_forms_form_ref', + function ($null, $form_id) { + return $this->get_form_ref($form_id); + }, + 10, + 2 + ); + + add_filter( + 'option_wpct-erp-forms_rest-api', + function ($setting) { + return $this->populate_refs($setting); + }, + 10, + 1 + ); + + add_filter( + 'option_wpct-erp-forms_rpc-api', + function ($setting) { + return $this->populate_refs($setting); + }, + 10, + 1 + ); + + add_action( + 'updated_option', + function ($option, $from, $to) { + $this->on_option_updated($option, $to); + }, + 90, + 3 + ); + + add_action( + 'add_option', + function ($option, $value) { + $this->on_option_updated($option, $value); + }, + 90, + 3 + ); + + add_action('admin_enqueue_scripts', function ($admin_page) { + $this->enqueue_scripts($admin_page); + }); - add_action('add_option', function ($option, $value) { - $this->on_option_updated($option, $value); - }, 90, 3); + new REST_Controller(); } public function init() @@ -192,8 +248,38 @@ class Wpct_Erp_Forms extends BasePlugin $this->set_form_refs($refs); } } + + private function enqueue_scripts($admin_page) + { + if ('settings_page_wpct-erp-forms' !== $admin_page) { + return; + } + + wp_enqueue_script( + 'wpct-erp-forms', + plugins_url('assets/plugin.bundle.js', __FILE__), + [ + 'react', + 'react-jsx-runtime', + 'wp-api-fetch', + 'wp-components', + 'wp-dom-ready', + 'wp-element', + 'wp-i18n', + 'wp-api', + ], + WPCT_ERP_FORMS_VERSION, + ['in_footer' => true] + ); + + wp_enqueue_style('wp-components'); + } } -add_action('plugins_loaded', function () { - $plugin = Wpct_Erp_Forms::get_instance(); -}, 9); +add_action( + 'plugins_loaded', + function () { + $plugin = Wpct_Erp_Forms::get_instance(); + }, + 9 +);