🔧 Bug Fixes: - Fixed product image structure to match Miravia API requirements - Updated MiraviaProduct.php getData() method to wrap images in {"Image": [...]} format - Updated MiraviaCombination.php getData() method to wrap SKU images properly - Resolved error "[4224] The Main image of the product is required" 📋 Changes: - Modified getData() methods to transform flat image arrays to nested structure - Product images: images[] → Images: {"Image": [...]} - SKU images: images[] → Images: {"Image": [...]} - Maintains backward compatibility for empty image arrays 🎯 Impact: - Product uploads will now pass Miravia's image validation - Both product-level and SKU-level images properly formatted - Complies with official Miravia API documentation structure 🤖 Generated with Claude Code (https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
359 lines
16 KiB
PHP
359 lines
16 KiB
PHP
<?php
|
|
/**
|
|
* Plugin Name: Miravia Feed API Connector
|
|
* Description: Official Miravia marketplace integration using Feed API - Upload products and manage orders
|
|
* Version: 2.0.0
|
|
* Author: CloudHost.es
|
|
* Author URI: https://cloudhost.es
|
|
* Plugin URI: https://devops.cloudhost.es/CloudHost/MiraviaConnector
|
|
* Text Domain: miraviawoo
|
|
* WC requires at least: 3.0
|
|
* WC tested up to: 8.0
|
|
* Required WP: 5.0
|
|
* Tested WP: 6.4
|
|
* Network: false
|
|
* License: GPL v3 or later
|
|
* License URI: https://www.gnu.org/licenses/gpl-3.0.html
|
|
*/
|
|
if ( ! defined( 'ABSPATH' ) ) { exit; }
|
|
|
|
define('MIRAVIA_CLASSES_PATH', plugin_dir_path( __FILE__ ) . 'classes/');
|
|
define('MIRAVIA_SHARED_CLASSES_PATH', MIRAVIA_CLASSES_PATH . 'shared/');
|
|
define('MIRAVIA_VIEWS_PATH', plugin_dir_path( __FILE__ ) . 'views/');
|
|
define('MIRAVIA_ASSETS_PATH', plugin_dir_path( __FILE__ ) . 'assets/');
|
|
define('MIRAVIA_WOO_VERSION', '2.0.0');
|
|
define('MIRAVIA_BUILD_VERSION', '20');
|
|
define('MIRAVIA_DB_VERSION', 102);
|
|
define('MIRAVIA_DEBUG', get_option('miravia_debug_mode', '0'));
|
|
define('LOG_FOLDER', plugin_dir_path( __FILE__ ));
|
|
$isSetter = false;
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.log.php'); //Log CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.core.php'); //Core CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.db.php'); //DB CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.categories.php'); //Categories CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.product.php'); //Product CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.order.php'); //Order CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'tables/class.table.php'); //Table CLASS
|
|
require_once(MIRAVIA_CLASSES_PATH . 'class.api.php'); //API CLASS
|
|
|
|
//Miravia Shared Classes
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaFilter.php');
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaFeed.php');
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaLink.php');
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaCategory.php');
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaCombination.php');
|
|
require_once(MIRAVIA_SHARED_CLASSES_PATH . 'MiraviaProduct.php');
|
|
if(is_admin()) {
|
|
$iconUrl = plugins_url('/assets/img/icon.png', __FILE__);
|
|
}
|
|
if( !class_exists('MiraviaWOO') ) {
|
|
class MiraviaWOO {
|
|
|
|
function __construct(){
|
|
|
|
//Menu
|
|
add_action('admin_menu', array(&$this, 'admin_menu'));
|
|
add_action('admin_init', array(&$this, 'admin_init'));
|
|
|
|
add_action( 'admin_enqueue_scripts', array(&$this, 'load_style') );
|
|
|
|
add_action( 'manage_product_posts_custom_column' , array(&$this, 'colum_product'), 10, 2 );
|
|
add_filter( 'manage_product_posts_columns' , array(&$this, 'add_colum_products') );
|
|
// register_activation_hook( __FILE__, array('MIRAVIADB', 'install_db') );
|
|
add_action( 'plugins_loaded', array('MIRAVIADB', 'install') );
|
|
|
|
//Actions Table
|
|
add_filter( 'miravia_profiles_row_actions', array( &$this, 'miravia_profiles_actions' ), 10, 2 );
|
|
add_action( 'add_meta_boxes', array($this, 'create_miravia_order_metabox') );
|
|
register_deactivation_hook(
|
|
__FILE__,
|
|
array($this, 'miravia_desactivation')
|
|
);
|
|
add_action( 'manage_shop_order_posts_custom_column' , array($this, 'colum_orders'), 10, 2 );
|
|
add_action( 'woocommerce_update_product', array($this, 'miravia_update_product'), 10, 1 );
|
|
add_action('woocommerce_variation_set_stock', array($this, 'miravia_update_product'), 10, 1);
|
|
add_action('woocommerce_product_set_stock', array($this, 'miravia_update_product'), 10, 1);
|
|
add_action('woocommerce_variation_set_stock_status', array($this, 'miravia_update_product'), 10, 1);
|
|
add_action('woocommerce_product_set_stock_status', array($this, 'miravia_update_product'), 10, 1);
|
|
add_action( 'woocommerce_save_product_variation', array($this, 'miravia_update_product'), 10, 1 );
|
|
|
|
add_action( 'woocommerce_product_options_general_product_data', array($this, 'miravia_product_metabox') );
|
|
add_action( 'woocommerce_process_product_meta', array($this, 'miravia_save_metadata_product') );
|
|
add_action( 'woocommerce_variation_set_stock', array($this, 'miravia_change_stock_hook'), 15, 1);
|
|
add_action( 'woocommerce_product_set_stock', array($this, 'miravia_change_stock_hook'), 15, 1);
|
|
}
|
|
|
|
function miravia_change_stock_hook($product) {
|
|
if(get_option('miravia_only_stock', '0') == '1') {
|
|
LOG::add("Cambio de stock para el producto {$product}");
|
|
$profile = MiraviaCore::get_profile_by_product($product->sku);
|
|
$accounts = MiraviaCore::accounts_by_profile($profile);
|
|
if(count($accounts) > 0) {
|
|
MiraviaCore::request_notify($accounts[0]['token'], 'update_stock');
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
function miravia_save_metadata_product( $id ){
|
|
if(isset($_POST['miravia_brand_product'])) {
|
|
$product = wc_get_product( $id );
|
|
|
|
$product->update_meta_data( '_miravia_brand_product', sanitize_text_field( $_POST[ 'miravia_brand_product' ] ) );
|
|
$product->update_meta_data( '_miravia_unit', sanitize_text_field( $_POST[ 'miravia_unit' ] ) );
|
|
$product->update_meta_data( '_miravia_unit_value', sanitize_text_field( $_POST[ 'miravia_unit_value' ] ) );
|
|
$product->save_meta_data();
|
|
}
|
|
}
|
|
|
|
function miravia_product_metabox() {
|
|
require_once(MIRAVIA_VIEWS_PATH . "/metabox/miravia-product.php");
|
|
}
|
|
|
|
function colum_orders( $column, $post_id ) {
|
|
if ($column == 'order_status'){
|
|
$orderID = get_post_meta($post_id, '_miravia_order_id', true);
|
|
if($orderID != '' and $orderID != 0) {
|
|
echo '<span class="created_via">'.sprintf(__('Created Vía %s','aliexpress'), 'Miravia').'</span>';
|
|
}
|
|
}
|
|
}
|
|
|
|
function miravia_update_product( $product_id ) {
|
|
if(get_option('miravia_only_stock', '0') == '1') {
|
|
return;
|
|
}
|
|
global $isSetter;
|
|
|
|
|
|
if($product_id instanceof WC_Product) {
|
|
$product_id = $product_id->ID;
|
|
}elseif(isset($product_id['id'])) {
|
|
$product_id = $product_id['id'];
|
|
}
|
|
|
|
if(get_post_meta($product_id, '_miravia_need_update', true) == '1') {
|
|
LOG::add("{$product_id} no necesita notificación, ya programada.");
|
|
return;
|
|
}
|
|
LOG::add("Estableciendo notificación para el producto {$product_id}");
|
|
update_post_meta($product_id, '_miravia_need_update', '1');
|
|
|
|
if($isSetter) {
|
|
LOG::add("No es necesario establecer aviso");
|
|
return;
|
|
}
|
|
|
|
if($product_id) {
|
|
$sync = MiraviaCore::get_product_miravia($product_id);
|
|
if($sync) {
|
|
//ESTABLECER NOTIFICACIÓN
|
|
$apiKey = MiraviaCore::get_miravia_account_default();
|
|
$resultNotify = MiraviaCore::request_notify($apiKey['token'], 'update_stock');
|
|
if($resultNotify === -1) {
|
|
LOG::add("Existe una notificación pendiente");
|
|
return;
|
|
}
|
|
if($resultNotify) {
|
|
LOG::add("Seteada notificación correctamente");
|
|
$isSetter = true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
function miravia_desactivation() {
|
|
update_option('miravia_db_version', 0);
|
|
}
|
|
|
|
public function miravia_profiles_actions( $actions, $post ) {
|
|
if ( current_user_can( 'edit_posts' ) ) {
|
|
$actions['miravia'] = '<a href="'.admin_url('admin.php?page=miravia_settings&subpage=edit_profile&nonce=' . wp_create_nonce( 'miravia_edit_profile_' . $post->ID )) . '" rel="permalink">' . __('Edit') . '</a>';
|
|
}
|
|
|
|
return $actions;
|
|
}
|
|
|
|
|
|
function colum_product($column, $post_id){
|
|
if($column == 'miravia_data') {
|
|
$html = '<div class="miravia_controls" data-id="'.$post_id.'">';
|
|
$sync = MiraviaCore::get_product_miravia($post_id);
|
|
$dateUpdated = 'ND';
|
|
if($sync and count($sync) > 0) {
|
|
if($sync[0]['last_updated'] == '0000-00-00 00:00:0') {
|
|
$dateUpdated = date('d-m-Y H:i:s', strtotime($sync[0]['last_updated']));
|
|
}
|
|
//MiraviaCore::debug($sync);
|
|
if(count($sync) > 1) {
|
|
$html .= __('Uploaded with multiple accounts','miraviawoo');
|
|
}else{
|
|
if($sync[0]['id_miravia'] != '' and $sync[0]['id_miravia'] != 0) {
|
|
$html .= "<a class='button viewProduct' data-id='{$sync[0]['id_miravia']}'>View</a><span class='minidate'><br>".__('Last Update:','miraviawoo')." ".$dateUpdated."</span>";
|
|
$html .= "<p>Status: {$sync[0]['status_text']}</p>";
|
|
}
|
|
}
|
|
|
|
if(trim($sync[0]['lastError']) != '') {
|
|
$html .= '<i class="fa fa-info" style="border-radius:100px;padding:5px;background-color:#CCC;margin-left:5px" title="'.$sync[0]['lastError'].'"></i>';
|
|
}
|
|
}else{
|
|
}
|
|
|
|
$html .= '</div>';
|
|
echo wp_kses($html, array(
|
|
'a' => array(
|
|
'href' => array(),
|
|
'class' => array(),
|
|
'data-id' => array(),
|
|
),
|
|
'span' => array(
|
|
'class' => array()
|
|
),
|
|
'i' => array('class' => array(),),
|
|
'p' => array()
|
|
));
|
|
}
|
|
|
|
}
|
|
|
|
function add_colum_products( $columns ) {
|
|
return array_merge( $columns,
|
|
array( 'miravia_data' => __( 'Miravia', 'miraviawoo' ) ) );
|
|
}
|
|
|
|
function load_style() {
|
|
if(is_admin()) {
|
|
wp_enqueue_style( 'cssmiravia', plugins_url('assets/css/miravia-admin.css?v='.time(), __FILE__) );
|
|
wp_enqueue_script( 'productmiravia', plugins_url('assets/js/products.js?v='.time(), __FILE__), array( 'wp-i18n' ) );
|
|
|
|
wp_localize_script( 'productmiravia', 'MIRAVIA_DATA_JAVASCRIPT', array(
|
|
'adminAjaxURL' => admin_url('admin-ajax.php'),
|
|
));
|
|
wp_enqueue_script( 'jquery-ui-core', false, array('jquery') );
|
|
wp_enqueue_script('jquery');
|
|
wp_enqueue_script( 'filter_rules_plugin_miravia_localization', plugins_url('lib/filter_rules/localization/es.min.js', __FILE__));
|
|
wp_enqueue_script( 'filter_rules_plugin_miravia', plugins_url('lib/filter_rules/jquery.jui_filter_rules.min.js', __FILE__),array('jquery'));
|
|
wp_enqueue_script( 'filter_rules_miravia', plugins_url('lib/filter_rules_miravia.js?v='.time(), __FILE__), array('jquery'));
|
|
wp_enqueue_style( 'fontawesome_miravia_css', plugins_url('lib/fontawesome-6.1.2.all.min.css', __FILE__) );
|
|
if(isset($_GET['page']) and sanitize_text_field($_GET['page']) == 'miravia_settings') {
|
|
wp_enqueue_script( 'sweetalert_lib', plugins_url('lib/sweetalert2.min.js', __FILE__) );
|
|
wp_enqueue_script( 'select2_lib', plugins_url('lib/select2.min.js', __FILE__) );
|
|
wp_enqueue_style( 'select2_css', plugins_url('lib/select2.min.css', __FILE__) );
|
|
}
|
|
wp_enqueue_style( 'filter_rules_css', plugins_url('lib/filter_rules/jquery.jui_filter_rules.bs.min.css', __FILE__) );
|
|
wp_enqueue_script( 'fontawesome_miravia_js', plugins_url('lib/fontawesome-6.1.2.all.min.js', __FILE__) );
|
|
}
|
|
}
|
|
|
|
|
|
function admin_menu() {
|
|
global $iconUrl;
|
|
add_menu_page(
|
|
esc_html__( 'Miravia', 'miraviawoo' ),
|
|
esc_html__( 'Miravia', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings',
|
|
array($this, 'settings_page'),
|
|
$iconUrl,
|
|
55.5
|
|
);
|
|
// add_submenu_page(
|
|
// 'miravia_settings',
|
|
// esc_html__( 'Brands', 'miraviawoo' ),
|
|
// esc_html__( 'Brands', 'miraviawoo'),
|
|
// 'manage_woocommerce',
|
|
// 'miravia_settings&subpage=brands',
|
|
// array($this, 'settings_page'),
|
|
// 10
|
|
// );
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Orders', 'miraviawoo' ),
|
|
esc_html__( 'Orders', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=orders',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Jobs', 'miraviawoo' ),
|
|
esc_html__( 'Jobs', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=jobs',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Accounts', 'miraviawoo' ),
|
|
esc_html__( 'Accounts', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=accounts',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Profiles', 'miraviawoo' ),
|
|
esc_html__( 'Profiles', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=profiles',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Products', 'miraviawoo' ),
|
|
esc_html__( 'Products', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=products',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Miravia Products', 'miraviawoo' ),
|
|
esc_html__( 'Miravia Products', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=products_remote',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
add_submenu_page(
|
|
'miravia_settings',
|
|
esc_html__( 'Rules', 'miraviawoo' ),
|
|
esc_html__( 'Rules', 'miraviawoo'),
|
|
'manage_woocommerce',
|
|
'miravia_settings&subpage=rules',
|
|
array($this, 'settings_page'),
|
|
10
|
|
);
|
|
}
|
|
|
|
function create_miravia_order_metabox() {
|
|
global $post;
|
|
if(get_post_meta($post->ID, '_miravia_order_id', true)){
|
|
add_meta_box( 'aew_number_shipping_metabox', __('Miravia Tracker','miraviawoo'), array($this, 'content_metabox_miravia_order'), 'shop_order', 'normal', 'high' );
|
|
}
|
|
}
|
|
function content_metabox_miravia_order($post) {
|
|
require_once(MIRAVIA_VIEWS_PATH . '/metabox/miravia-order.php');
|
|
}
|
|
|
|
public function settings_page() {
|
|
include MIRAVIA_VIEWS_PATH . 'settings.php';
|
|
}
|
|
|
|
public function brands_page() {
|
|
include MIRAVIA_VIEWS_PATH . 'brands.php';
|
|
}
|
|
|
|
function admin_init() {
|
|
|
|
}
|
|
}
|
|
}
|
|
|
|
$MIRAVIAWOO = new MIRAVIAWOO(); |