Enhanced Ecommerce Google Analytics Plugin for WooCommerce - Version 3.0.1

Version Description

  • 12/03/2021 =
    • Bug fixes
    • Performance improvement
    • Site speed issue got resolved.
Download this release

Release Info

Developer Tatvic
Plugin Icon 128x128 Enhanced Ecommerce Google Analytics Plugin for WooCommerce
Version 3.0.1
Comparing to
See all releases

Code changes from version 3.0.0 to 3.0.1

Files changed (117) hide show
  1. LICENSE.txt +0 -0
  2. admin/class-enhanced-ecommerce-google-analytics-admin.php +256 -75
  3. admin/class-enhanced-ecommerce-google-analytics-settings.php +30 -2
  4. admin/class-tvc-admin-helper.php +435 -0
  5. admin/css/enhanced-ecommerce-google-analytics-admin.css +363 -0
  6. admin/images.zip +0 -0
  7. admin/images/adwords.png +0 -0
  8. admin/images/banner.png +0 -0
  9. admin/images/cotlw.gif +0 -0
  10. admin/images/cotlw.png +0 -0
  11. admin/images/discount.gif +0 -0
  12. admin/images/facebook.jpg +0 -0
  13. admin/images/google_optimize.png +0 -0
  14. admin/images/m1.png +0 -0
  15. admin/images/m2.png +0 -0
  16. admin/images/new-2.gif +0 -0
  17. admin/images/new-img.gif +0 -0
  18. admin/images/no-config-success.svg +0 -1
  19. admin/images/plugin_bk.png +0 -0
  20. admin/images/rating.png +0 -0
  21. admin/images/ratings.png +0 -0
  22. admin/images/refresh.png +0 -0
  23. admin/images/shopify_new.png +0 -0
  24. admin/images/tatvic_logo.png +0 -0
  25. admin/images/woo.png +0 -0
  26. admin/images/woo_banner_adv.gif +0 -0
  27. admin/index.php +0 -0
  28. admin/js/enhanced-ecommerce-google-analytics-admin.js +0 -0
  29. {includes/setup → admin}/js/jquery-3.5.1.min.js +0 -0
  30. admin/partials/about-plugin.php +2 -2
  31. admin/partials/enhanced-ecommerce-google-analytics-admin-display.php +89 -44
  32. admin/partials/general-fields.php +331 -133
  33. admin/partials/sidebar.php +6 -3
  34. enhanced-ecommerce-google-analytics.php +76 -9
  35. includes/application/class-feed-master.php +0 -676
  36. includes/application/class-tvc-email.php +0 -68
  37. includes/application/class-tvc-feed-processor.php +0 -341
  38. includes/application/class-tvc-feed-queries.php +0 -243
  39. includes/application/class-tvc-feed-value-editors.php +0 -240
  40. includes/application/class-tvc-schedules.php +0 -147
  41. includes/application/google/class-feed.php +0 -213
  42. includes/application/tvc-cron-functions.php +0 -54
  43. includes/application/tvc-feed-processing-support.php +0 -1583
  44. includes/application/tvc-feed-processor-functions.php +0 -107
  45. includes/class-enhanced-ecommerce-google-analytics-activator.php +0 -0
  46. includes/class-enhanced-ecommerce-google-analytics-deactivator.php +0 -0
  47. includes/class-enhanced-ecommerce-google-analytics-i18n.php +0 -0
  48. includes/class-enhanced-ecommerce-google-analytics-loader.php +0 -0
  49. includes/class-enhanced-ecommerce-google-analytics.php +58 -8
  50. includes/class-tvc-register-scripts.php +9 -9
  51. includes/data/class-tvc-ajax-file.php +82 -64
  52. includes/data/class-tvc-backup.php +0 -181
  53. includes/data/class-tvc-channel-ftp.php +0 -37
  54. includes/data/class-tvc-channel.php +0 -342
  55. includes/data/class-tvc-data.php +0 -713
  56. includes/data/class-tvc-db-management.php +0 -325
  57. includes/data/class-tvc-tab.php +0 -126
  58. includes/data/class-tvc-variations.php +0 -85
  59. includes/data/tvc-admin-functions.php +0 -372
  60. includes/index.php +0 -0
  61. includes/json/client-secrets.json +0 -26
  62. includes/json/currency.json +0 -252
  63. includes/libraries/tvc-background-process.php +0 -754
  64. includes/setup/CustomApi.php +41 -31
  65. includes/setup/ShoppingApi.php +2 -2
  66. includes/setup/add-campaign.php +3 -1
  67. includes/setup/class-tatvic-category-selector-element.php +1 -1
  68. includes/setup/class-tvc-database-management.php +0 -537
  69. includes/setup/class-tvc-folders.php +0 -147
  70. includes/setup/class-tvc-prepare-taxonomy.php +0 -375
  71. includes/setup/google-ads.php +167 -236
  72. includes/setup/google-shopping-feed-gaa-config.php +407 -464
  73. includes/setup/google-shopping-feed-shopping-campaigns.php +1 -1
  74. includes/setup/google-shopping-feed-sync-product.php +459 -490
  75. includes/setup/google-shopping-feed.php +197 -233
  76. includes/setup/help-html.php +35 -29
  77. includes/setup/img/lock.png +0 -0
  78. includes/setup/img/tick-mark.png +0 -0
  79. includes/setup/img/tvc-lock-large.png +0 -0
  80. includes/setup/img/tvc-lock.png +0 -0
  81. includes/setup/img/tvc-tick-large.png +0 -0
  82. includes/setup/img/tvc-tick.png +0 -0
  83. includes/setup/json/client-secrets.json +1 -1
  84. includes/user-interface/abstract-tvc-category-wrapper.php +0 -87
  85. includes/user-interface/class-tvc-add-options-page.php +0 -64
  86. includes/user-interface/class-tvc-admin-page.php +0 -131
  87. includes/user-interface/class-tvc-i18n-scripts.php +0 -240
  88. includes/user-interface/class-tvc-list-table.php +0 -863
  89. includes/user-interface/class-tvc-main-admin-page.php +0 -117
  90. includes/user-interface/class-tvc-product-feed-category-wrapper.php +0 -51
  91. includes/user-interface/class-tvc-product-feed-page.php +0 -182
  92. includes/user-interface/elements/class-tvc-attribute-selector-element.php +0 -113
  93. includes/user-interface/elements/class-tvc-category-selector-element.php +0 -121
  94. includes/user-interface/js/fontawesome.js +0 -2
  95. includes/user-interface/js/sweetalert.min.js +0 -1
  96. includes/user-interface/js/tvc_backup-list.js +0 -89
  97. includes/user-interface/js/tvc_backup-list.min.js +0 -60
  98. includes/user-interface/js/tvc_feed-form-events.js +0 -331
  99. includes/user-interface/js/tvc_feed-form-events.min.js +0 -1
  100. includes/user-interface/js/tvc_feed-form.js +0 -2604
  101. includes/user-interface/js/tvc_feed-form.min.js +0 -1770
  102. includes/user-interface/js/tvc_feed-html.js +0 -513
  103. includes/user-interface/js/tvc_feed-html.min.js +0 -1
  104. includes/user-interface/js/tvc_feed-list.js +0 -284
  105. includes/user-interface/js/tvc_feed-list.min.js +0 -227
  106. includes/user-interface/js/tvc_msg_events.js +0 -27
  107. includes/user-interface/js/tvc_msg_events.min.js +0 -1
  108. includes/user-interface/js/tvc_setting-form.js +0 -150
  109. includes/user-interface/js/tvc_setting-form.min.js +0 -1
  110. includes/user-interface/js/tvc_support.js +0 -261
  111. includes/user-interface/js/tvc_support.min.js +0 -192
  112. includes/user-interface/js/tvc_verify-inputs.js +0 -79
  113. includes/user-interface/js/tvc_verify-inputs.min.js +0 -1
  114. includes/user-interface/tvc-admin-menu-functions.php +0 -92
  115. index.php +0 -0
  116. languages/enhanced-ecommerce-google-analytics.pot +0 -0
  117. public/class-enhanced-ecommerce-google-analytics-public.php +679 -182
LICENSE.txt CHANGED
File without changes
admin/class-enhanced-ecommerce-google-analytics-admin.php CHANGED
@@ -20,9 +20,8 @@
20
  * @subpackage Enhanced_Ecommerce_Google_Analytics/admin
21
  * @author Chiranjiv Pathak <chiranjiv@tatvic.com>
22
  */
23
- //require __DIR__ . '../includes/setup/CustomerClient.php';
24
 
25
- class Enhanced_Ecommerce_Google_Analytics_Admin {
26
 
27
  /**
28
  * The ID of this plugin.
@@ -52,88 +51,46 @@ class Enhanced_Ecommerce_Google_Analytics_Admin {
52
  protected $ga_id;
53
  protected $ga_LC;
54
  protected $ga_eeT;
55
- protected $customerClient;
56
-
57
- public function __construct($plugin_name, $version) {
58
-
59
  $this->plugin_name = $plugin_name;
60
  $this->version = $version;
61
- if(isset($_SERVER['HTTPS']) && ($_SERVER['HTTPS'] == 'on' || $_SERVER['HTTPS'] == 1) || isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https') {
62
- $protocol = 'https://';
63
- } else {
64
- $protocol = 'http://';
65
- }
66
- $server_name = $_SERVER['SERVER_NAME'];
67
- $domain = $protocol.$server_name;
68
- $woo_country = $this->woo_country();
69
- $country = (!empty($woo_country)) ? $woo_country[0] : 'US';
70
- $currency_code = $this->get_currency_code();
71
- $timezone = get_option('timezone_string');
72
- //sigin with google
73
- $this->returnUrl = "estorenew.tatvic.com/tat_ee/ads-analytics-form.php?domain=".$domain."&country=".$country."&user_currency=".$currency_code."&timezone".$timezone;
74
  $this->accessToken = isset($_GET['access_token']) ? $_GET['access_token'] : '';
75
  $this->refreshToken = isset($_GET['refresh_token']) ? $_GET['refresh_token'] : '';
76
  $this->email = isset($_GET['email']) ? $_GET['email'] : '';
77
-
78
- if(isset($_GET['property_id']) && isset($_GET['ads_id'])) {
79
- $data = unserialize(get_option('ee_options'));
80
- if(isset($data['ga_id']) && ($data['ga_id'] != $_GET['property_id'])) {
81
- $_POST['ga_id'] = $_GET['property_id'];
82
- $_POST['ads_id'] = $_GET['ads_id'];
83
- } else if(isset($data['ga_id']) && ($data['ga_id'] == $_GET['property_id'])) {
84
- if($_GET['ads_id'] != '') {
85
- $_POST['ga_id'] = $_GET['property_id'];
86
- $_POST['ads_id'] = $_GET['ads_id'];
87
- } else {
88
- $_POST['ga_id'] = $_GET['property_id'];
89
- }
90
- } else {
91
- $_POST['ga_id'] = $_GET['property_id'];
92
- $_POST['ads_id'] = $_GET['ads_id'];
93
- }
94
-
95
- Enhanced_Ecommerce_Google_Settings::update_analytics_options('ee_options');
96
- }
97
-
98
- $this->url = "https://estorenew.tatvic.com/tat_ee/ga_rdr_ee.php?return_url=" . $this->returnUrl;
99
- }
100
-
101
- /**
102
- * @return array
103
- * Get woocommerce default set country
104
- */
105
- private function woo_country(){
106
- // The country/state
107
- $store_raw_country = get_option( 'woocommerce_default_country' );
108
- // Split the country/state
109
- $split_country = explode( ":", $store_raw_country );
110
- return $split_country;
111
- }
112
- /**
113
- * @return mixed
114
- */
115
- private function get_currency_code(){
116
- $woo_country = $this->woo_country();
117
- $country = (!empty($woo_country)) ? $woo_country[0] : 'US';
118
- $getCurrency = file_get_contents(ENHANCAD_PLUGIN_DIR . 'includes/json/currency.json');
119
- $contData = json_decode($getCurrency);
120
- return $contData->{$country};
121
  }
 
122
  /**
123
  * Register the stylesheets for the admin area.
124
  *
125
  * @since 1.0.0
126
  */
127
  public function enqueue_styles() {
128
-
129
  $screen = get_current_screen();
130
  if ($screen->id == 'toplevel_page_enhanced-ecommerce-google-analytics-admin-display' || (isset($_GET['page']) && $_GET['page'] == 'enhanced-ecommerce-google-analytics-admin-display')) {
131
  wp_register_style('font_awesome', '//use.fontawesome.com/releases/v5.0.13/css/all.css');
132
  wp_enqueue_style('font_awesome');
133
- wp_register_style('aga_bootstrap', '//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css');
134
- wp_enqueue_style('aga_bootstrap');
135
  wp_register_style('aga_confirm', '//cdnjs.cloudflare.com/ajax/libs/jquery-confirm/3.3.2/jquery-confirm.min.css');
136
  wp_enqueue_style('aga_confirm');
 
 
 
 
 
 
 
 
 
 
 
 
 
 
137
  wp_enqueue_style($this->plugin_name, plugin_dir_url(__FILE__) . 'css/enhanced-ecommerce-google-analytics-admin.css', array(), $this->version, 'all');
138
  }
139
  }
@@ -144,16 +101,34 @@ class Enhanced_Ecommerce_Google_Analytics_Admin {
144
  * @since 1.0.0
145
  */
146
  public function enqueue_scripts() {
147
-
148
  $screen = get_current_screen();
149
  if ($screen->id == 'toplevel_page_enhanced-ecommerce-google-analytics-admin-display' || (isset($_GET['page']) && $_GET['page'] == 'enhanced-ecommerce-google-analytics-admin-display')) {
 
 
 
150
  wp_register_script('popper_bootstrap', '//cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js');
151
  wp_enqueue_script('popper_bootstrap');
152
- wp_register_script('aga_bootstrap', '//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js');
153
  wp_enqueue_script('aga_bootstrap');
 
 
154
  wp_register_script('aga_confirm_js', '//cdnjs.cloudflare.com/ajax/libs/jquery-confirm/3.3.2/jquery-confirm.min.js');
155
  wp_enqueue_script('aga_confirm_js');
156
  wp_enqueue_script($this->plugin_name, plugin_dir_url(__FILE__) . 'js/enhanced-ecommerce-google-analytics-admin.js', array('jquery'), $this->version, false);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
157
  }
158
  }
159
 
@@ -164,7 +139,23 @@ class Enhanced_Ecommerce_Google_Analytics_Admin {
164
  */
165
  public function display_admin_page() {
166
  add_menu_page(
167
- 'Tatvic EE Plugin', 'Tatvic EE Plugin', 'manage_options', "enhanced-ecommerce-google-analytics-admin-display", array($this, 'showPage'), plugin_dir_url(__FILE__) . 'images/tatvic_logo.png', 26
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
168
  );
169
  }
170
  /**
@@ -173,7 +164,9 @@ class Enhanced_Ecommerce_Google_Analytics_Admin {
173
  * @since 1.0.0
174
  */
175
  public function showPage() {
 
176
  require_once( 'partials/enhanced-ecommerce-google-analytics-admin-display.php');
 
177
  if (!empty($_GET['tab'])) {
178
  $get_action = $_GET['tab'];
179
  } else {
@@ -182,28 +175,216 @@ class Enhanced_Ecommerce_Google_Analytics_Admin {
182
  if (method_exists($this, $get_action)) {
183
  $this->$get_action();
184
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
185
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
186
 
187
- public function general_settings() {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
188
  require_once( 'partials/general-fields.php');
189
  }
190
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
191
  public function conversion_tracking() {
192
  require_once( 'partials/conversion-tracking.php');
193
  }
194
-
195
  public function google_optimize() {
196
  require_once( 'partials/google-optimize.php');
197
  }
198
-
199
  public function about_plugin() {
200
  require_once( 'partials/about-plugin.php');
201
  }
202
  public function country_location() {
203
  // date function to hide 30% off sale after certain date
204
  return date_default_timezone_set('Australia/Sydney'); // Change this depending on what timezone your in
205
- }
206
-
207
  public function today() {
208
  $this->country_location();
209
  return strtotime(date('Y-m-d'));
20
  * @subpackage Enhanced_Ecommerce_Google_Analytics/admin
21
  * @author Chiranjiv Pathak <chiranjiv@tatvic.com>
22
  */
 
23
 
24
+ class Enhanced_Ecommerce_Google_Analytics_Admin extends TVC_Admin_Helper {
25
 
26
  /**
27
  * The ID of this plugin.
51
  protected $ga_id;
52
  protected $ga_LC;
53
  protected $ga_eeT;
54
+ protected $setting_status;
55
+ protected $site_url;
56
+ public function __construct($plugin_name, $version) {
 
57
  $this->plugin_name = $plugin_name;
58
  $this->version = $version;
 
 
 
 
 
 
 
 
 
 
 
 
 
59
  $this->accessToken = isset($_GET['access_token']) ? $_GET['access_token'] : '';
60
  $this->refreshToken = isset($_GET['refresh_token']) ? $_GET['refresh_token'] : '';
61
  $this->email = isset($_GET['email']) ? $_GET['email'] : '';
62
+ $this->url = $this->get_connect_url();
63
+ $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
64
  }
65
+
66
  /**
67
  * Register the stylesheets for the admin area.
68
  *
69
  * @since 1.0.0
70
  */
71
  public function enqueue_styles() {
 
72
  $screen = get_current_screen();
73
  if ($screen->id == 'toplevel_page_enhanced-ecommerce-google-analytics-admin-display' || (isset($_GET['page']) && $_GET['page'] == 'enhanced-ecommerce-google-analytics-admin-display')) {
74
  wp_register_style('font_awesome', '//use.fontawesome.com/releases/v5.0.13/css/all.css');
75
  wp_enqueue_style('font_awesome');
76
+ wp_register_style('plugin-bootstrap',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/bootstrap/css/bootstrap.min.css');
77
+ wp_enqueue_style('plugin-bootstrap');
78
  wp_register_style('aga_confirm', '//cdnjs.cloudflare.com/ajax/libs/jquery-confirm/3.3.2/jquery-confirm.min.css');
79
  wp_enqueue_style('aga_confirm');
80
+
81
+ wp_enqueue_style('custom-css', ENHANCAD_PLUGIN_URL . '/includes/setup/css/custom-style.css', array(), $this->version, 'all' );
82
+ if($this->is_current_tab_in(array('sync_product_page','gaa_config_page'))){
83
+ wp_register_style('plugin-select2',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/select2/select2.min.css');
84
+ wp_enqueue_style('plugin-select2');
85
+ wp_register_style('plugin-steps',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/jquery-steps/jquery.steps.css');
86
+ wp_enqueue_style('plugin-steps');
87
+ }
88
+ if($this->is_current_tab_in(array("shopping_campaigns_page","add_campaign_page"))){
89
+ wp_register_style('plugin-select2',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/select2/select2.min.css');
90
+ wp_enqueue_style('plugin-select2');
91
+ wp_register_style('bootstrap-datepicker',ENHANCAD_PLUGIN_URL. '/includes/setup/plugins/datepicker/bootstrap-datepicker.min.css');
92
+ wp_enqueue_style('bootstrap-datepicker');
93
+ }
94
  wp_enqueue_style($this->plugin_name, plugin_dir_url(__FILE__) . 'css/enhanced-ecommerce-google-analytics-admin.css', array(), $this->version, 'all');
95
  }
96
  }
101
  * @since 1.0.0
102
  */
103
  public function enqueue_scripts() {
 
104
  $screen = get_current_screen();
105
  if ($screen->id == 'toplevel_page_enhanced-ecommerce-google-analytics-admin-display' || (isset($_GET['page']) && $_GET['page'] == 'enhanced-ecommerce-google-analytics-admin-display')) {
106
+
107
+ wp_enqueue_script( $this->plugin_name, plugin_dir_url( __FILE__ ) . 'js/sweetalert.min.js', array( 'jquery' ), $this->version, false );
108
+ wp_enqueue_script( 'custom-jquery', ENHANCAD_PLUGIN_URL . '/admin/js/jquery-3.5.1.min.js', array( 'jquery' ), $this->version, false );
109
  wp_register_script('popper_bootstrap', '//cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js');
110
  wp_enqueue_script('popper_bootstrap');
111
+ wp_register_script('aga_bootstrap', '//maxcdn.bootstrapcdn.com/bootstrap/4.5.1/js/bootstrap.min.js');
112
  wp_enqueue_script('aga_bootstrap');
113
+ wp_register_script('aga_bootstrap_mod', 'https://cdn.jsdelivr.net/npm/bootstrap@5.0.0-beta2/dist/js/bootstrap.bundle.min.js');
114
+ wp_enqueue_script('aga_bootstrap_mod');
115
  wp_register_script('aga_confirm_js', '//cdnjs.cloudflare.com/ajax/libs/jquery-confirm/3.3.2/jquery-confirm.min.js');
116
  wp_enqueue_script('aga_confirm_js');
117
  wp_enqueue_script($this->plugin_name, plugin_dir_url(__FILE__) . 'js/enhanced-ecommerce-google-analytics-admin.js', array('jquery'), $this->version, false);
118
+ if($this->is_current_tab_in(array('sync_product_page','gaa_config_page'))){
119
+ wp_register_script('plugin-select2',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/select2/select2.min.js');
120
+ wp_enqueue_script('plugin-select2');
121
+ wp_register_script('plugin-step-js',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/jquery-steps/jquery.steps.js');
122
+ wp_enqueue_script('plugin-step-js');
123
+ }
124
+ if($this->is_current_tab_in(array("shopping_campaigns_page","add_campaign_page"))){
125
+ wp_register_script('plugin-select2',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/select2/select2.min.js');
126
+ wp_enqueue_script('plugin-select2');
127
+ wp_register_script('plugin-chart',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/chart/chart.js');
128
+ wp_enqueue_script('plugin-chart');
129
+ wp_register_script('bootstrap_datepicker',ENHANCAD_PLUGIN_URL . '/includes/setup/plugins/datepicker/bootstrap-datepicker.min.js');
130
+ wp_enqueue_script('bootstrap_datepicker');
131
+ }
132
  }
133
  }
134
 
139
  */
140
  public function display_admin_page() {
141
  add_menu_page(
142
+ 'Tatvic EE Plugin', 'Tatvic EE Plugin', 'manage_options', "enhanced-ecommerce-google-analytics-admin-display", array($this, 'showPage'), plugin_dir_url(__FILE__) . 'images/tatvic_logo.png', 26
143
+ );
144
+ add_submenu_page(
145
+ 'enhanced-ecommerce-google-analytics-admin-display',
146
+ esc_html__('Google Ads', 'actionable-google-analytics-admin-display'),
147
+ esc_html__('Google Ads', 'actionable-google-analytics-admin-display'),
148
+ 'manage_woocommerce',
149
+ 'enhanced-ecommerce-google-analytics-admin-display&tab=google_ads',
150
+ array($this, 'showPage')
151
+ );
152
+ add_submenu_page(
153
+ 'enhanced-ecommerce-google-analytics-admin-display',
154
+ esc_html__('Google Shopping', 'enhanced-ecommerce-google-analytics-admin-display'),
155
+ esc_html__('Google Shopping', 'enhanced-ecommerce-google-analytics-admin-display'),
156
+ 'manage_woocommerce',
157
+ 'enhanced-ecommerce-google-analytics-admin-display&tab=google_shopping_feed',
158
+ array($this, 'showPage')
159
  );
160
  }
161
  /**
164
  * @since 1.0.0
165
  */
166
  public function showPage() {
167
+ echo '<div class="tvc_plugin_container">';
168
  require_once( 'partials/enhanced-ecommerce-google-analytics-admin-display.php');
169
+ new TVC_Tabs();
170
  if (!empty($_GET['tab'])) {
171
  $get_action = $_GET['tab'];
172
  } else {
175
  if (method_exists($this, $get_action)) {
176
  $this->$get_action();
177
  }
178
+ echo '</div>';
179
+ }
180
+ public function check_nall_and_message($val, $msg, $msg_false){
181
+ if((isset($val) && $val != "" && $val != 0) ){
182
+ return $msg;
183
+ }else{
184
+ return $msg_false;
185
+ }
186
+ }
187
+ public function check_setting_status(){
188
+ if(!empty($this->setting_status)){
189
+ return $this->setting_status;
190
+ }else{
191
+ $google_detail = $this->get_ee_options_data();
192
+ $setting_status = array();
193
+ if(isset($google_detail['setting'])){
194
+ $googleDetail = $google_detail['setting'];
195
+ //for google analytic
196
+ if(isset($googleDetail->tracking_option) && isset($googleDetail->measurement_id) && isset($googleDetail->property_id) && $googleDetail->tracking_option == "BOTH" ){
197
+ if($googleDetail->property_id != "" && $googleDetail->measurement_id != ""){
198
+ $setting_status['google_analytic']= true;
199
+ $setting_status['google_analytic_msg']= "";
200
+ }else if($googleDetail->property_id == "" ){
201
+ $setting_status['google_analytic']= false;
202
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
203
+ }else if($googleDetail->measurement_id == "" ){
204
+ $setting_status['google_analytic']= false;
205
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
206
+ }
207
+ }else if(isset($googleDetail->tracking_option) && isset($googleDetail->measurement_id) && $googleDetail->tracking_option == "GA4"){
208
+ if( $googleDetail->measurement_id != ""){
209
+ $setting_status['google_analytic']= true;
210
+ $setting_status['google_analytic_msg']= "";
211
+ }else{
212
+ $setting_status['google_analytic']= false;
213
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
214
+ }
215
+ }else if(isset($googleDetail->tracking_option) && isset($googleDetail->property_id) && $googleDetail->tracking_option == "UA" ){
216
+ if($googleDetail->property_id != ""){
217
+ $setting_status['google_analytic']= true;
218
+ $setting_status['google_analytic_msg']= "";
219
+ }else{
220
+ $setting_status['google_analytic']= false;
221
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
222
+ }
223
+ }else{
224
+ $setting_status['google_analytic']= false;
225
+ $setting_status['google_analytic_msg']= "";
226
+ }
227
+ // for google shopping
228
+ if(property_exists($googleDetail,"google_merchant_center_id") && property_exists($googleDetail,"google_ads_id") ){
229
+ //main tab
230
+ if( $googleDetail->google_merchant_center_id != "" && $googleDetail->google_ads_id != ""){
231
+ $setting_status['google_shopping']= true;
232
+ $setting_status['google_shopping_msg']= "";
233
+ }else if($googleDetail->google_merchant_center_id == ""){
234
+ $setting_status['google_shopping']= false;
235
+ $setting_status['google_shopping_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
236
+ }else if($googleDetail->google_ads_id == ""){
237
+ $setting_status['google_shopping']= false;
238
+ $setting_status['google_shopping_msg']= "Link your Google Ads with Merchant center to start running shopping campaigns <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
239
+ }
240
+ }else{
241
+ $setting_status['google_shopping']= false;
242
+ $setting_status['google_shopping_msg']= "";
243
+ }
244
+
245
+ //google_ads_id
246
+ if(property_exists($googleDetail,"google_ads_id") && property_exists($googleDetail,"google_merchant_center_id") ){
247
+ if( $googleDetail->google_ads_id != "" && $googleDetail->google_merchant_center_id != ""){
248
+ $setting_status['google_ads']= true;
249
+ $setting_status['google_ads_msg']= "";
250
+ }else if($googleDetail->google_merchant_center_id == ""){
251
+ $setting_status['google_ads']= false;
252
+ $setting_status['google_ads_msg']= "Link your Google Ads with Merchant center to start running shopping campaigns <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
253
+ }else if($googleDetail->google_ads_id == ""){
254
+ $setting_status['google_ads']= false;
255
+ $setting_status['google_ads_msg']= "Configure Google Ads account to reach to millions of interested shoppers <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
256
+ }
257
+ }else{
258
+ $setting_status['google_ads']= false;
259
+ $setting_status['google_ads_msg']= "";
260
+ }
261
+ }
262
+ $this->setting_status = $setting_status;
263
+ return $setting_status;
264
+ }
265
  }
266
+ public function check_setting_status_sub_tabs(){
267
+ $google_detail = $this->get_ee_options_data();
268
+ $setting_status = array();
269
+ if(isset($google_detail['setting'])){
270
+ $googleDetail = $google_detail['setting'];
271
+ //sub tab shopping config
272
+ if(property_exists($googleDetail,"google_merchant_center_id") && property_exists($googleDetail,"is_site_verified") && property_exists($googleDetail,"is_domain_claim") && property_exists($googleDetail,"google_ads_id")){
273
+ if( $googleDetail->google_merchant_center_id != "" && $googleDetail->google_ads_id != "" && $googleDetail->is_site_verified == 1 && $googleDetail->is_domain_claim == 1 ){
274
+ $setting_status['google_shopping_conf']= true;
275
+ $setting_status['google_shopping_conf_msg']= "Google Shopping Configuration Success.";
276
+ }else if($googleDetail->google_merchant_center_id == "" || $googleDetail->google_ads_id == "" ){
277
+ $setting_status['google_shopping_conf']= false;
278
+ $setting_status['google_shopping_conf_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
279
+ }else if($googleDetail->is_site_verified ==0 && $googleDetail->is_domain_claim ==0 ){
280
+ $setting_status['google_shopping_conf']= false;
281
+ $setting_status['google_shopping_conf_msg']= "Site verification and domain claim for your merchant center account failed.";
282
+ }else if($googleDetail->is_site_verified ==0 ){
283
+ $setting_status['google_shopping_conf']= false;
284
+ $setting_status['google_shopping_conf_msg']= "Site verification and domain claim for your merchant center account failed.";
285
+ }else if($googleDetail->is_domain_claim ==0 ){
286
+ $setting_status['google_shopping_conf']= false;
287
+ $setting_status['google_shopping_conf_msg']= "Domain claim is pending. Your store url may be linked to other merchant center account.";
288
+ }
289
+ }else{
290
+ $setting_status['google_shopping_conf']= false;
291
+ $missing="";
292
+ }
293
+ //sub tab product sync
294
+ $syncProductList = [];
295
+ $syncProductStat = [];
296
+ if(property_exists($googleDetail,"google_merchant_center_id") && $googleDetail->google_merchant_center_id != ''){
297
+ if(isset($google_detail['prod_sync_status']) && $google_detail['prod_sync_status']){
298
+ $syncProductStat = $google_detail['prod_sync_status'];
299
+ $sync_product_total = (!empty($syncProductStat)) ? $syncProductStat->total : "0";
300
+ $sync_product_approved = (!empty($syncProductStat)) ? $syncProductStat->approved : "0";
301
+ $sync_product_disapproved = (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0";
302
+ $sync_product_pending = (!empty($syncProductStat)) ? $syncProductStat->pending : "0";
303
 
304
+ if($sync_product_total > 1 && $sync_product_approved > 1 && $sync_product_disapproved < 1){
305
+ $setting_status['google_shopping_p_sync']= true;
306
+ $setting_status['google_shopping_p_sync_msg']= "Google Shopping product sync is a success.";
307
+ }else if($sync_product_total < 1){
308
+ $setting_status['google_shopping_p_sync']= false;
309
+ $setting_status['google_shopping_p_sync_msg']= "Sync your product data into Merchant center and get eligible for free listing across Google.";
310
+ }else if($sync_product_disapproved > 0){
311
+ $setting_status['google_shopping_p_sync']= false;
312
+ $setting_status['google_shopping_p_sync_msg']= "There seems to be some problem with your product data. Rectify the issues by selecting right attributes.";
313
+ }
314
+ }
315
+ }else{
316
+ $setting_status['google_shopping_p_sync']= false;
317
+ $setting_status['google_shopping_p_sync_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
318
+ }
319
+
320
+ //sub tab product Campaigns
321
+ if(property_exists($googleDetail,"google_merchant_center_id") && $googleDetail->google_merchant_center_id != ''){
322
+ if(isset($google_detail['campaigns_list']) && $google_detail['campaigns_list']){
323
+ $campaigns_list = $google_detail['campaigns_list'];
324
+ $totalCampaigns = count($campaigns_list);
325
+ if($totalCampaigns < 1){
326
+ $setting_status['google_shopping_p_campaigns']= false;
327
+ $setting_status['google_shopping_p_campaigns_msg']= "Reach out to customers based on their past site behavior by running start shopping campaign.";
328
+ }else{
329
+ $setting_status['google_shopping_p_campaigns']= true;
330
+ }
331
+ }else{
332
+ $setting_status['google_shopping_p_campaigns']= false;
333
+ $setting_status['google_shopping_p_campaigns_msg']= "Reach out to customers based on their past site behavior by running start shopping campaign.";
334
+ }
335
+ }else{
336
+ $setting_status['google_shopping_p_campaigns']= false;
337
+ $setting_status['google_shopping_p_campaigns_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
338
+ }
339
+ }
340
+ return $setting_status;
341
+ }
342
+ public function general_settings() {
343
  require_once( 'partials/general-fields.php');
344
  }
345
+ public function google_ads() {
346
+ require_once(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
347
+ require_once(ENHANCAD_PLUGIN_DIR . 'includes/setup/google-ads.php');
348
+ new GoogleAds();
349
+ }
350
+ public function google_shopping_feed() {
351
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
352
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/google-shopping-feed.php');
353
+ new GoogleShoppingFeed();
354
+ }
355
+ public function gaa_config_page() {
356
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
357
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/google-shopping-feed-gaa-config.php');
358
+ new GAAConfiguration();
359
+ }
360
+ public function sync_product_page() {
361
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
362
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/google-shopping-feed-sync-product.php');
363
+ new SyncProductConfiguration();
364
+ }
365
+ public function shopping_campaigns_page() {
366
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
367
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/google-shopping-feed-shopping-campaigns.php');
368
+ new CampaignsConfiguration();
369
+ }
370
+ public function add_campaign_page() {
371
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/help-html.php');
372
+ include(ENHANCAD_PLUGIN_DIR . 'includes/setup/add-campaign.php');
373
+ new AddCampaign();
374
+ }
375
  public function conversion_tracking() {
376
  require_once( 'partials/conversion-tracking.php');
377
  }
 
378
  public function google_optimize() {
379
  require_once( 'partials/google-optimize.php');
380
  }
 
381
  public function about_plugin() {
382
  require_once( 'partials/about-plugin.php');
383
  }
384
  public function country_location() {
385
  // date function to hide 30% off sale after certain date
386
  return date_default_timezone_set('Australia/Sydney'); // Change this depending on what timezone your in
387
+ }
 
388
  public function today() {
389
  $this->country_location();
390
  return strtotime(date('Y-m-d'));
admin/class-enhanced-ecommerce-google-analytics-settings.php CHANGED
@@ -26,10 +26,15 @@ if ( ! defined( 'ABSPATH' ) ) {
26
  class Enhanced_Ecommerce_Google_Settings {
27
 
28
  public static function add_update_settings($settings) {
 
29
  if ( !get_option($settings)) {
30
  $ee_options = array();
31
  if(is_array($_POST)) {
32
  foreach ($_POST as $key => $value) {
 
 
 
 
33
  if(!isset($_POST[$key])){
34
  $_POST[$key] = '';
35
  }
@@ -38,13 +43,19 @@ class Enhanced_Ecommerce_Google_Settings {
38
  }
39
  }
40
  }
41
- add_option( $settings, serialize( $ee_options ) );
 
 
42
  }
43
  else {
44
  $get_ee_settings = unserialize(get_option($settings));
45
  if(is_array($get_ee_settings)) {
46
  foreach ($get_ee_settings as $key => $value) {
47
- if(!isset($_POST[$key])){
 
 
 
 
48
  $_POST[$key] = '';
49
  }
50
  if( $_POST[$key] != $value ) {
@@ -54,11 +65,16 @@ class Enhanced_Ecommerce_Google_Settings {
54
  }
55
  if(is_array($_POST)) {
56
  foreach($_POST as $key=>$value){
 
 
 
 
57
  if(!array_key_exists($key,$get_ee_settings)){
58
  $get_ee_settings[$key] = $value;
59
  }
60
  }
61
  }
 
62
  update_option($settings, serialize( $get_ee_settings ));
63
  }
64
  self::admin_notice__success();
@@ -69,6 +85,10 @@ class Enhanced_Ecommerce_Google_Settings {
69
  $ee_options = array();
70
  if(is_array($_POST)) {
71
  foreach ($_POST as $key => $value) {
 
 
 
 
72
  if(!isset($_POST[$key])){
73
  $_POST[$key] = $value;
74
  }
@@ -82,6 +102,10 @@ class Enhanced_Ecommerce_Google_Settings {
82
  $get_ee_settings = unserialize(get_option($settings));
83
  if(is_array($get_ee_settings)) {
84
  foreach ($get_ee_settings as $key => $value) {
 
 
 
 
85
  if(!isset($_POST[$key])){
86
  $_POST[$key] = $value;
87
  }
@@ -93,6 +117,10 @@ class Enhanced_Ecommerce_Google_Settings {
93
 
94
  if(is_array($_POST)) {
95
  foreach($_POST as $key=>$value){
 
 
 
 
96
  if(!array_key_exists($key,$get_ee_settings)){
97
  $get_ee_settings[$key] = $value;
98
  }
26
  class Enhanced_Ecommerce_Google_Settings {
27
 
28
  public static function add_update_settings($settings) {
29
+
30
  if ( !get_option($settings)) {
31
  $ee_options = array();
32
  if(is_array($_POST)) {
33
  foreach ($_POST as $key => $value) {
34
+ if($key == "ee_submit_plugin"){
35
+ unset($_POST["ee_submit_plugin"]);
36
+ continue;
37
+ }
38
  if(!isset($_POST[$key])){
39
  $_POST[$key] = '';
40
  }
43
  }
44
  }
45
  }
46
+ if(!add_option( $settings, serialize( $ee_options ) )){
47
+ update_option($settings, serialize( $ee_options ));
48
+ }
49
  }
50
  else {
51
  $get_ee_settings = unserialize(get_option($settings));
52
  if(is_array($get_ee_settings)) {
53
  foreach ($get_ee_settings as $key => $value) {
54
+ if($key == "ee_submit_plugin"){
55
+ unset($_POST["ee_submit_plugin"]);
56
+ continue;
57
+ }
58
+ if(!isset($_POST[$key]) ){
59
  $_POST[$key] = '';
60
  }
61
  if( $_POST[$key] != $value ) {
65
  }
66
  if(is_array($_POST)) {
67
  foreach($_POST as $key=>$value){
68
+ if($key == "ee_submit_plugin"){
69
+ unset($_POST["ee_submit_plugin"]);
70
+ continue;
71
+ }
72
  if(!array_key_exists($key,$get_ee_settings)){
73
  $get_ee_settings[$key] = $value;
74
  }
75
  }
76
  }
77
+
78
  update_option($settings, serialize( $get_ee_settings ));
79
  }
80
  self::admin_notice__success();
85
  $ee_options = array();
86
  if(is_array($_POST)) {
87
  foreach ($_POST as $key => $value) {
88
+ if($key == "ee_submit_plugin"){
89
+ unset($_POST["ee_submit_plugin"]);
90
+ continue;
91
+ }
92
  if(!isset($_POST[$key])){
93
  $_POST[$key] = $value;
94
  }
102
  $get_ee_settings = unserialize(get_option($settings));
103
  if(is_array($get_ee_settings)) {
104
  foreach ($get_ee_settings as $key => $value) {
105
+ if($key == "ee_submit_plugin"){
106
+ unset($_POST["ee_submit_plugin"]);
107
+ continue;
108
+ }
109
  if(!isset($_POST[$key])){
110
  $_POST[$key] = $value;
111
  }
117
 
118
  if(is_array($_POST)) {
119
  foreach($_POST as $key=>$value){
120
+ if($key == "ee_submit_plugin"){
121
+ unset($_POST["ee_submit_plugin"]);
122
+ continue;
123
+ }
124
  if(!array_key_exists($key,$get_ee_settings)){
125
  $get_ee_settings[$key] = $value;
126
  }
admin/class-tvc-admin-helper.php ADDED
@@ -0,0 +1,435 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ Class TVC_Admin_Helper{
3
+ protected $customApiObj;
4
+ protected $ee_options_data = "";
5
+ protected $e_options_settings = "";
6
+ protected $merchantId = "";
7
+ protected $main_merchantId = "";
8
+ protected $subscriptionId = "";
9
+ protected $time_zone = "";
10
+ protected $connect_actual_link = "";
11
+ protected $connect_url = "";
12
+ protected $woo_country = "";
13
+ protected $woo_currency = "";
14
+ protected $currentCustomerId = "";
15
+ protected $user_currency_symbol = "";
16
+ protected $setting_status = "";
17
+ public function __construct($theURL = '') {
18
+ $this->includes();
19
+ $this->customApiObj = new CustomApi();
20
+ }
21
+ public function includes() {
22
+ if (!class_exists('CustomApi.php')) {
23
+ require_once(ENHANCAD_PLUGIN_DIR . 'includes/setup/CustomApi.php');
24
+ }
25
+ if (!class_exists('ShoppingApi')) {
26
+ require_once(ENHANCAD_PLUGIN_DIR . 'includes/setup/ShoppingApi.php');
27
+ }
28
+
29
+ }
30
+
31
+ public function is_ee_options_data_empty(){
32
+ if($this->get_subscriptionId() != ""){
33
+ if(empty($this->get_ee_options_data())){
34
+ $this->set_update_api_to_db();
35
+ }
36
+ }
37
+ }
38
+ public function get_ee_options_data(){
39
+ if(!empty($this->ee_options_data)){
40
+ return $this->ee_options_data;
41
+ }else{
42
+ $this->ee_options_data = unserialize(get_option('ee_api_data'));
43
+ //echo "<pre>";
44
+ //print_r($this->ee_options_data);
45
+ //exit;
46
+ return $this->ee_options_data;
47
+ }
48
+ }
49
+ public function set_update_db_to_api(){
50
+ if($this->get_subscriptionId() != ""){
51
+ $ee_options_settings = $this->get_ee_options_settings();
52
+ $ads_ert = get_option('ads_ert');
53
+ $ads_edrt = get_option('ads_edrt');
54
+
55
+ $tvc_setting_db = [];
56
+ $tvc_setting_db['subscription_id'] = $this->get_subscriptionId();
57
+ $tvc_setting_db['enhanced_e_commerce_tracking'] = (($ee_options_settings['ga_eeT'] == "on" || $ee_options_settings['ga_eeT'])?1:0);
58
+ $tvc_setting_db['add_gtag_snippet'] = (($ee_options_settings['ga_ST'] == "on" || $ee_options_settings['ga_ST'])?1:0);
59
+
60
+
61
+ $tvc_setting_db['google-add'] ="";
62
+ $tvc_setting_db['remarketing_tags'] = (($ads_ert == "on" || $ads_ert)?1:0);
63
+ $tvc_setting_db['dynamic_remarketing_tags'] = (($ads_edrt == "on" || $ads_edrt)?1:0);
64
+ $customApiObj = new CustomApi();
65
+ $response = $customApiObj->updateTrackingOption($tvc_setting_db);
66
+
67
+ }
68
+ //return true;
69
+ }
70
+ public function set_update_api_to_db($googleDetail = null){
71
+ if(empty($googleDetail)){
72
+ $google_detail = $this->customApiObj->getGoogleAnalyticDetail();
73
+ if(isset($google_detail->data['status']) && $google_detail->data['status'] == 200){
74
+ if (isset($google_detail->data['data'])) {
75
+ $googleDetail = $google_detail->data['data'];
76
+ }
77
+ }else{
78
+ //return 0;
79
+ }
80
+ }
81
+ $syncProductStat = [];
82
+ $syncProductList = [];
83
+ $campaigns_list = [];
84
+ if(isset($googleDetail->google_merchant_center_id) || isset($googleDetail->google_ads_id) ){
85
+
86
+ $syncProduct_list_res = $this->customApiObj->getSyncProductList(['merchant_id' => $this->get_merchantId()]);
87
+ if(isset($syncProduct_list_res->data) && isset($syncProduct_list_res->status) && $syncProduct_list_res->status == 200){
88
+ if (isset($syncProduct_list_res->data->statistics)) {
89
+ $syncProductStat = $syncProduct_list_res->data->statistics;
90
+ }
91
+ if (isset($syncProduct_list_res->data->products)) {
92
+ $syncProductList = $syncProduct_list_res->data->products;
93
+ }
94
+ }
95
+
96
+ $shopping_api = new ShoppingApi();
97
+ $campaigns_list_res = $shopping_api->getCampaigns();
98
+ if(isset($campaigns_list_res->data) && isset($campaigns_list_res->status) && $campaigns_list_res->status == 200) {
99
+ if (isset($campaigns_list_res->data['data'])) {
100
+ $campaigns_list = $campaigns_list_res->data['data'];
101
+ }
102
+ }
103
+ }
104
+ $this->set_ee_options_data(array("setting" => $googleDetail, "prod_sync_status" =>$syncProductStat,"prod_sync_list" =>$syncProductList, "campaigns_list"=>$campaigns_list, "sync_time"=>current_time( 'timestamp' )));
105
+ $tvc_msg ="";
106
+ if(!empty($googleDetail)){
107
+ $tvc_msg = "Configuration Setting";
108
+ }
109
+ if(!empty($syncProductList)){
110
+ $tvc_msg = ($tvc_msg != "")?$tvc_msg.", Product Sync":"Product Sync";
111
+ }
112
+ if(!empty($campaigns_list)){
113
+ $tvc_msg = ($tvc_msg != "")?$tvc_msg.", Shopping Campaigns":"Shopping Campaigns";
114
+ }
115
+ return "Success to sync up of ".$tvc_msg.".";
116
+ }
117
+
118
+ public function set_ee_options_data($ee_options_data){
119
+ update_option("ee_api_data", serialize($ee_options_data));
120
+ }
121
+
122
+ public function get_ee_options_settings(){
123
+ if(!empty($this->e_options_settings)){
124
+ return $this->e_options_settings;
125
+ }else{
126
+ $this->e_options_settings = unserialize(get_option('ee_options'));
127
+ return $this->e_options_settings;
128
+ }
129
+ }
130
+
131
+ public function get_subscriptionId(){
132
+ if(!empty($this->subscriptionId)){
133
+ return $this->subscriptionId;
134
+ }else{
135
+ $ee_options_settings = "";
136
+ if(!isset($GLOBALS['tatvicData']['tvc_subscription'])){
137
+ $ee_options_settings = $this->get_ee_options_settings();
138
+ }
139
+ $this->subscriptionId = (isset($GLOBALS['tatvicData']['tvc_subscription'])) ? $GLOBALS['tatvicData']['tvc_subscription'] : $ee_options_settings['subscription_id'];
140
+ return $this->subscriptionId;
141
+ }
142
+
143
+ }
144
+ public function get_merchantId(){
145
+ if(!empty($this->merchantId)){
146
+ return $this->merchantId;
147
+ }else{
148
+ $tvc_merchant = "";
149
+ $google_detail = $this->get_ee_options_data();
150
+ if(!isset($GLOBALS['tatvicData']['tvc_merchant']) && isset($google_detail['setting']->google_merchant_center_id)){
151
+ $tvc_merchant = $google_detail['setting']->google_merchant_center_id;
152
+ }
153
+ $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant'] : $tvc_merchant;
154
+ return $this->merchantId;
155
+ }
156
+ }
157
+ public function get_main_merchantId(){
158
+ if(!empty($this->main_merchantId)){
159
+ return $this->main_merchantId;
160
+ }else{
161
+ $main_merchantId = "";
162
+ $google_detail = $this->get_ee_options_data();
163
+ if(!isset($GLOBALS['tatvicData']['tvc_main_merchant_id']) && isset($google_detail['setting']->merchant_id)){
164
+ $main_merchantId = $google_detail['setting']->merchant_id;
165
+ }
166
+ $this->main_merchantId = (isset($GLOBALS['tatvicData']['tvc_main_merchant_id'])) ? $GLOBALS['tatvicData']['tvc_main_merchant_id'] : $main_merchantId;
167
+ return $this->main_merchantId;
168
+ }
169
+ }
170
+
171
+ public function get_time_zone(){
172
+ if(!empty($this->time_zone)){
173
+ return $this->time_zone;
174
+ }else{
175
+ $timezone = get_option('timezone_string');
176
+ if($timezone == ""){
177
+ $timezone = "America/New_York";
178
+ }
179
+ $this->time_zone = $timezone;
180
+ return $this->time_zone;
181
+ }
182
+ }
183
+
184
+ public function get_connect_actual_link(){
185
+ if(!empty($this->connect_actual_link)){
186
+ return $this->connect_actual_link;
187
+ }else{
188
+ $this->connect_actual_link = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://$_SERVER[HTTP_HOST]";
189
+ return $this->connect_actual_link;
190
+ }
191
+ }
192
+
193
+ public function get_connect_url(){
194
+ if(!empty($this->connect_url)){
195
+ return $this->connect_url;
196
+ }else{
197
+ $this->connect_url = "https://".TVC_AUTH_CONNECT_URL."/config/ga_rdr_gmc.php?return_url=".TVC_AUTH_CONNECT_URL."/config/ads-analytics-form.php?domain=" . $this->get_connect_actual_link() . "&amp;country=" . $this->get_woo_country(). "&amp;user_currency=".$this->get_woo_currency()."&amp;subscription_id=" . $this->get_subscriptionId() . "&amp;confirm_url=" . admin_url() . "&amp;timezone=".$this->get_time_zone();
198
+ return $this->connect_url;
199
+ }
200
+ }
201
+
202
+ public function get_woo_currency(){
203
+ if(!empty($this->woo_currency)){
204
+ return $this->woo_currency;
205
+ }else{
206
+ $this->woo_currency = get_option('woocommerce_currency');
207
+ return $this->woo_currency;
208
+ }
209
+ }
210
+
211
+ public function get_woo_country(){
212
+ if(!empty($this->woo_country)){
213
+ return $this->woo_country;
214
+ }else{
215
+ $store_raw_country = get_option('woocommerce_default_country');
216
+ $country = explode(":", $store_raw_country);
217
+ $this->woo_country = (isset($country[0]))?$country[0]:"";
218
+ return $this->woo_country;
219
+ }
220
+ }
221
+ //tvc_customer = >google_ads_id
222
+ public function get_currentCustomerId(){
223
+ if(!empty($this->currentCustomerId)){
224
+ return $this->currentCustomerId;
225
+ }else{
226
+ $ee_options_settings = "";
227
+ if(!isset($GLOBALS['tatvicData']['tvc_customer'])){
228
+ $ee_options_settings = $this->get_ee_options_settings();
229
+ }
230
+ $this->currentCustomerId = (isset($GLOBALS['tatvicData']['tvc_customer'])) ? $GLOBALS['tatvicData']['tvc_customer'] : $ee_options_settings['google_ads_id'];
231
+ return $this->currentCustomerId;
232
+ }
233
+ }
234
+ public function get_user_currency_symbol(){
235
+ if(!empty($this->get_user_currency_symbol)){
236
+ return $this->get_user_currency_symbol;
237
+ }else{
238
+ $currency_symbol="";
239
+ $currency_symbol_rs = $this->customApiObj->getCampaignCurrencySymbol(['customer_id' => $this->get_currentCustomerId()]);
240
+ if(isset($currency_symbol_rs->data) && isset($currency_symbol_rs->data['status']) && $currency_symbol_rs->data['status'] == 200){
241
+ $currency_symbol = get_woocommerce_currency_symbol($currency_symbol_rs->data['data']->currency);
242
+ }else{
243
+ $currency_symbol = get_woocommerce_currency_symbol("USD");
244
+ }
245
+ $this->currentCustomerId = $currency_symbol;
246
+ return $this->currentCustomerId;
247
+ }
248
+ }
249
+
250
+ public function add_tvc_log($log_string){
251
+ $log = "User: ".date("F j, Y, g:i a").PHP_EOL." Attempt: ".$log_string;
252
+ //Save string to log, use FILE_APPEND to append.
253
+ file_put_contents('log_tvc.log', $log, FILE_APPEND);
254
+ }
255
+
256
+ public function add_spinner_html(){
257
+ $spinner_gif = ENHANCAD_PLUGIN_URL . '/images/ajax-loader.gif';
258
+ echo '<div class="feed-spinner" id="feed-spinner" style="display:none;">
259
+ <img id="img-spinner" src="' . $spinner_gif . '" alt="Loading" />
260
+ </div>';
261
+ }
262
+
263
+ public function get_gmcAttributes() {
264
+ $path = TVC_CHANNEL_DATA_DIR . '/google/gmc_attrbutes.json';
265
+ $str = file_get_contents($path);
266
+ $attributes = $str ? json_decode($str, true) : [];
267
+ return $attributes;
268
+ }
269
+
270
+ public function check_setting_status(){
271
+ if(!empty($this->setting_status)){
272
+ return $this->setting_status;
273
+ }else{
274
+ $google_detail = $this->get_ee_options_data();
275
+ $setting_status = array();
276
+ if(isset($google_detail['setting'])){
277
+ $googleDetail = $google_detail['setting'];
278
+ //for google analytic
279
+ if(isset($googleDetail->tracking_option) && isset($googleDetail->measurement_id) && isset($googleDetail->property_id) && $googleDetail->tracking_option == "BOTH" ){
280
+ if($googleDetail->property_id != "" && $googleDetail->measurement_id != ""){
281
+ $setting_status['google_analytic']= true;
282
+ $setting_status['google_analytic_msg']= "";
283
+ }else if($googleDetail->property_id == "" ){
284
+ $setting_status['google_analytic']= false;
285
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
286
+ }else if($googleDetail->measurement_id == "" ){
287
+ $setting_status['google_analytic']= false;
288
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
289
+ }
290
+ }else if(isset($googleDetail->tracking_option) && isset($googleDetail->measurement_id) && $googleDetail->tracking_option == "GA4"){
291
+ if( $googleDetail->measurement_id != ""){
292
+ $setting_status['google_analytic']= true;
293
+ $setting_status['google_analytic_msg']= "";
294
+ }else{
295
+ $setting_status['google_analytic']= false;
296
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
297
+ }
298
+ }else if(isset($googleDetail->tracking_option) && isset($googleDetail->property_id) && $googleDetail->tracking_option == "UA" ){
299
+ if($googleDetail->property_id != ""){
300
+ $setting_status['google_analytic']= true;
301
+ $setting_status['google_analytic_msg']= "";
302
+ }else{
303
+ $setting_status['google_analytic']= false;
304
+ $setting_status['google_analytic_msg']= "There is a configuration issue in your Google Analytics account set up <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
305
+ }
306
+ }else{
307
+ $setting_status['google_analytic']= false;
308
+ $setting_status['google_analytic_msg']= "";
309
+ }
310
+ // for google shopping
311
+ if(property_exists($googleDetail,"google_merchant_center_id") && property_exists($googleDetail,"google_ads_id") ){
312
+ //main tab
313
+ if( $googleDetail->google_merchant_center_id != "" && $googleDetail->google_ads_id != ""){
314
+ $setting_status['google_shopping']= true;
315
+ $setting_status['google_shopping_msg']= "";
316
+ }else if($googleDetail->google_merchant_center_id == ""){
317
+ $setting_status['google_shopping']= false;
318
+ $setting_status['google_shopping_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
319
+ }else if($googleDetail->google_ads_id == ""){
320
+ $setting_status['google_shopping']= false;
321
+ $setting_status['google_shopping_msg']= "Link your Google Ads with Merchant center to start running shopping campaigns <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
322
+ }
323
+ }else{
324
+ $setting_status['google_shopping']= false;
325
+ $setting_status['google_shopping_msg']= "";
326
+ }
327
+
328
+ //google_ads_id
329
+ if(property_exists($googleDetail,"google_ads_id") && property_exists($googleDetail,"google_merchant_center_id") ){
330
+ if( $googleDetail->google_ads_id != "" && $googleDetail->google_merchant_center_id != ""){
331
+ $setting_status['google_ads']= true;
332
+ $setting_status['google_ads_msg']= "";
333
+ }else if($googleDetail->google_merchant_center_id == ""){
334
+ $setting_status['google_ads']= false;
335
+ $setting_status['google_ads_msg']= "Link your Google Ads with Merchant center to start running shopping campaigns <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
336
+ }else if($googleDetail->google_ads_id == ""){
337
+ $setting_status['google_ads']= false;
338
+ $setting_status['google_ads_msg']= "Configure Google Ads account to reach to millions of interested shoppers <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
339
+ }
340
+ }else{
341
+ $setting_status['google_ads']= false;
342
+ $setting_status['google_ads_msg']= "";
343
+ }
344
+ }
345
+ $this->setting_status = $setting_status;
346
+ return $setting_status;
347
+ }
348
+ }
349
+ public function check_setting_status_sub_tabs(){
350
+ $google_detail = $this->get_ee_options_data();
351
+ $setting_status = array();
352
+ if(isset($google_detail['setting'])){
353
+ $googleDetail = $google_detail['setting'];
354
+ //sub tab shopping config
355
+ if(property_exists($googleDetail,"google_merchant_center_id") && property_exists($googleDetail,"is_site_verified") && property_exists($googleDetail,"is_domain_claim") && property_exists($googleDetail,"google_ads_id")){
356
+ if( $googleDetail->google_merchant_center_id != "" && $googleDetail->google_ads_id != "" && $googleDetail->is_site_verified == 1 && $googleDetail->is_domain_claim == 1 ){
357
+ $setting_status['google_shopping_conf']= true;
358
+ $setting_status['google_shopping_conf_msg']= "Google Shopping Configuration Success.";
359
+ }else if($googleDetail->google_merchant_center_id == "" || $googleDetail->google_ads_id == "" ){
360
+ $setting_status['google_shopping_conf']= false;
361
+ $setting_status['google_shopping_conf_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
362
+ }else if($googleDetail->is_site_verified ==0 && $googleDetail->is_domain_claim ==0 ){
363
+ $setting_status['google_shopping_conf']= false;
364
+ $setting_status['google_shopping_conf_msg']= "Site verification and domain claim for your merchant center account failed.";
365
+ }else if($googleDetail->is_site_verified ==0 ){
366
+ $setting_status['google_shopping_conf']= false;
367
+ $setting_status['google_shopping_conf_msg']= "Site verification and domain claim for your merchant center account failed.";
368
+ }else if($googleDetail->is_domain_claim ==0 ){
369
+ $setting_status['google_shopping_conf']= false;
370
+ $setting_status['google_shopping_conf_msg']= "Domain claim is pending. Your store url may be linked to other merchant center account.";
371
+ }
372
+ }else{
373
+ $setting_status['google_shopping_conf']= false;
374
+ $missing="";
375
+ }
376
+ //sub tab product sync
377
+ $syncProductList = [];
378
+ $syncProductStat = [];
379
+ if(property_exists($googleDetail,"google_merchant_center_id") && $googleDetail->google_merchant_center_id != ''){
380
+ if(isset($google_detail['prod_sync_status']) && $google_detail['prod_sync_status']){
381
+ $syncProductStat = $google_detail['prod_sync_status'];
382
+ $sync_product_total = (!empty($syncProductStat)) ? $syncProductStat->total : "0";
383
+ $sync_product_approved = (!empty($syncProductStat)) ? $syncProductStat->approved : "0";
384
+ $sync_product_disapproved = (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0";
385
+ $sync_product_pending = (!empty($syncProductStat)) ? $syncProductStat->pending : "0";
386
+
387
+ if($sync_product_total > 1 && $sync_product_approved > 1 && $sync_product_disapproved < 1){
388
+ $setting_status['google_shopping_p_sync']= true;
389
+ $setting_status['google_shopping_p_sync_msg']= "Google Shopping product sync is a success.";
390
+ }else if($sync_product_total < 1){
391
+ $setting_status['google_shopping_p_sync']= false;
392
+ $setting_status['google_shopping_p_sync_msg']= "Sync your product data into Merchant center and get eligible for free listing across Google.";
393
+ }else if($sync_product_disapproved > 0){
394
+ $setting_status['google_shopping_p_sync']= false;
395
+ $setting_status['google_shopping_p_sync_msg']= "There seems to be some problem with your product data. Rectify the issues by selecting right attributes.";
396
+ }
397
+ }
398
+ }else{
399
+ $setting_status['google_shopping_p_sync']= false;
400
+ $setting_status['google_shopping_p_sync_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
401
+ }
402
+
403
+ //sub tab product Campaigns
404
+ if(property_exists($googleDetail,"google_merchant_center_id") && $googleDetail->google_merchant_center_id != ''){
405
+ if(isset($google_detail['campaigns_list']) && $google_detail['campaigns_list']){
406
+ $campaigns_list = $google_detail['campaigns_list'];
407
+ $totalCampaigns = count($campaigns_list);
408
+ if($totalCampaigns < 1){
409
+ $setting_status['google_shopping_p_campaigns']= false;
410
+ $setting_status['google_shopping_p_campaigns_msg']= "Reach out to customers based on their past site behavior by running start shopping campaign.";
411
+ }else{
412
+ $setting_status['google_shopping_p_campaigns']= true;
413
+ }
414
+ }else{
415
+ $setting_status['google_shopping_p_campaigns']= false;
416
+ $setting_status['google_shopping_p_campaigns_msg']= "Reach out to customers based on their past site behavior by running start shopping campaign.";
417
+ }
418
+ }else{
419
+ $setting_status['google_shopping_p_campaigns']= false;
420
+ $setting_status['google_shopping_p_campaigns_msg']= "Connect your merchant center account and make your products available to shoppers across Google <a target='_blank' href='".esc_url($this->url)."'>click here</a>.";
421
+ }
422
+ }
423
+ return $setting_status;
424
+ }
425
+
426
+ public function is_current_tab_in($tabs){
427
+ if(isset($_GET['tab']) && is_array($tabs) && in_array($_GET['tab'], $tabs)){
428
+ return true;
429
+ }else if(isset($_GET['tab']) && $_GET['tab'] ==$tabs){
430
+ return true;
431
+ }
432
+ return false;
433
+ }
434
+ }
435
+ ?>
admin/css/enhanced-ecommerce-google-analytics-admin.css CHANGED
@@ -2,6 +2,7 @@
2
  * All of the CSS for your admin-specific functionality should be
3
  * included in this file.
4
  */
 
5
  *{
6
  box-sizing: border-box;
7
  margin:0px;
@@ -10,6 +11,16 @@
10
  body{
11
  background: #f1f1f1 !important;
12
  }
 
 
 
 
 
 
 
 
 
 
13
  .nav-link.active{
14
  color: #fff !important;
15
  background-color: #2D73C5 !important;
@@ -154,3 +165,355 @@ h5{
154
  .left {
155
  float: left;
156
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2
  * All of the CSS for your admin-specific functionality should be
3
  * included in this file.
4
  */
5
+ @import url('https://fonts.googleapis.com/css2?family=Lato:ital,wght@0,400;0,700;1,400;1,700&display=swap');
6
  *{
7
  box-sizing: border-box;
8
  margin:0px;
11
  body{
12
  background: #f1f1f1 !important;
13
  }
14
+ .tvc_plugin_container{
15
+ font-family: 'Lato', sans-serif;
16
+ font-size: 16px;
17
+ }
18
+ .tvc_plugin_container .tvc_plugin_sidebar, .tvc_plugin_container .right-content ol li{
19
+ font-size: 14px;
20
+ }
21
+ .tvc_plugin_container .right-content p, .tvc_plugin_container .right-content ol{
22
+ margin-bottom: 0.5rem;
23
+ }
24
  .nav-link.active{
25
  color: #fff !important;
26
  background-color: #2D73C5 !important;
165
  .left {
166
  float: left;
167
  }
168
+ /* checkbox admin*/
169
+ .wizard-section .wizard-content .wizard .actions ul li a.next-step, .wizard-section .wizard-content .wizard .actions ul li a.prev-step{
170
+ color: #fff !important;
171
+ background-color: #1e7e34 !important;
172
+ border-color: #1c7430;
173
+ cursor: pointer;
174
+ text-decoration: none;
175
+ display: inline-block;
176
+ font-weight: 400;
177
+ color: #212529;
178
+ text-align: center;
179
+ vertical-align: middle;
180
+ -webkit-user-select: none;
181
+ -moz-user-select: none;
182
+ -ms-user-select: none;
183
+ user-select: none;
184
+ background-color: transparent;
185
+ border: 1px solid transparent;
186
+ padding: .375rem .75rem;
187
+ font-size: 1rem;
188
+ line-height: 1.5;
189
+ border-radius: .25rem;
190
+ transition: color .15s ease-in-out,background-color .15s ease-in-out,border-color .15s ease-in-out,box-shadow .15s ease-in-out;
191
+ }
192
+
193
+ .tvc_ee_plugin_form .align-middle{margin: 0 auto;}
194
+ .tvc_ee_plugin_form .align-middle label, label.tvc-custom-control-input{margin: 0 auto; font-size: 15px;}
195
+ .tvc_ee_plugin_form [type="checkbox"]:not(:checked),
196
+ .tvc_ee_plugin_form [type="checkbox"]:checked {
197
+ position: absolute;
198
+ left: 1px;
199
+ top: 7px;
200
+ opacity: 0;
201
+ }
202
+ #ee_plugin_form #ga_PrivacyPolicy{
203
+ left: 1px;
204
+ top: 7px;
205
+ opacity: 0;
206
+ }
207
+
208
+ .tvc_ee_plugin_form [type="checkbox"]:not(:checked)+label,
209
+ .tvc_ee_plugin_form [type="checkbox"]:checked+label {
210
+ position: relative;
211
+ padding-left: 22px;
212
+ cursor: pointer;
213
+ }
214
+
215
+ .tvc_ee_plugin_form [type="checkbox"]:not(:checked)+label:before,
216
+ .tvc_ee_plugin_form [type="checkbox"]:checked+label:before {
217
+ content: '';
218
+ position: absolute;
219
+ left: 0;
220
+ top: 2px;
221
+ width: 16px;
222
+ height: 16px;
223
+ background: #fff;
224
+ border-radius: 3px;
225
+ box-shadow: inset 0 1px 3px rgba(0, 0, 0, .1);
226
+ background-color: #eee;
227
+ outline: none;
228
+ }
229
+
230
+ .tvc_ee_plugin_form [type="checkbox"]:checked+label:before {
231
+ background-color: #2D73C5;
232
+ }
233
+
234
+ .tvc_ee_plugin_form [type="checkbox"]:not(:checked)+label:after,
235
+ .tvc_ee_plugin_form [type="checkbox"]:checked+label:after {
236
+ content: '\2713';
237
+ position: absolute;
238
+ top: 4px;
239
+ left: 2px;
240
+ font-size: 14px;
241
+ font-weight: bold;
242
+ line-height: 0.8;
243
+ color: #fff;
244
+ transition: all .2s;
245
+ }
246
+
247
+
248
+ .tvc_ee_plugin_form [type="checkbox"]:not(:checked)+label:after {
249
+ opacity: 0;
250
+ transform: scale(0);
251
+ }
252
+
253
+ .tvc_ee_plugin_form [type="checkbox"]:checked+label:after {
254
+ opacity: 1;
255
+ transform: scale(1);
256
+ }
257
+ /* Admin nav menu item config-success */
258
+ .nav-tabs .nav-link.active a{color: #fff; text-decoration: none; }
259
+ .nav-tabs .nav-link a{text-decoration: none; max-height: 15px; display: inline-block;}
260
+ .nav-tabs .nav-link.active {
261
+ z-index: 9;
262
+ border-radius: 0;
263
+ }
264
+
265
+ .nav-tabs .nav-link{text-align: center;
266
+ padding: .8rem 0; width: 160px; z-index: 9; border: none;}
267
+
268
+ img.config-success, .nav-tabs li img.config-success, .nav-tabs li img.config-fail{
269
+ width: 16px;
270
+ margin: 3px;
271
+ margin-top: 0px;
272
+ }
273
+ .configuration-section img.config-success, .configuration-section img.config-fail {
274
+ width: 16px;
275
+ margin-left: 5px;
276
+ margin-top: 1px;
277
+ }
278
+ .tvc-tooltip {
279
+ position: relative;
280
+ display: inline-block;
281
+ width: 100%;
282
+ /*margin-top: 3px;*/
283
+ }
284
+ .tvc-tooltip:hover .tvc-tooltiptext {
285
+ visibility: visible;
286
+ opacity: 1;
287
+ z-index: 999;
288
+ }
289
+ .tvc-tooltip .tvc-tooltiptext {
290
+ visibility: hidden;
291
+ position: absolute;
292
+ min-width: 400px;
293
+ background-color: #fff;
294
+ border:1px solid #2D73C5;
295
+ color: #212529;
296
+ text-align: center;
297
+ padding: 8px 0;
298
+ border-radius: 6px;
299
+ z-index: 999;
300
+
301
+ transition: opacity .6s;
302
+ cursor: auto;
303
+ }
304
+ .tvc-tooltip .tvc-tooltiptext a{
305
+ color: #2D73C5;
306
+ }
307
+ .tvc-tooltip-top {
308
+ bottom: 115%;
309
+ left: 50%;
310
+ margin-left: -60px;
311
+ }
312
+ .tvc-tooltip-right{
313
+ top: -2px;
314
+ left: 98%;
315
+ }
316
+ .configuration-section .tvc-tooltip-right{
317
+ top: -4px;
318
+ left: 102%;
319
+ }
320
+ .tvc-tooltip.active .tvc-tooltip-right {
321
+ top: -2px;
322
+ left: 103%;
323
+ }
324
+ .tvc-tooltip-right::after {
325
+ content: "";
326
+ position: absolute;
327
+ top: 50%;
328
+ right: 100%;
329
+ margin-top: -5px;
330
+ border-width: 5px;
331
+ border-style: solid;
332
+ border-color: transparent #2D73C5 transparent transparent;
333
+ }
334
+ .tvc-tooltip-top::after {
335
+ content: "";
336
+ position: absolute;
337
+ top: 100%;
338
+ left: 50%;
339
+ margin-left: -5px;
340
+ border-width: 5px;
341
+ border-style: solid;
342
+ border-color: #555 transparent transparent transparent;
343
+ }
344
+ #ee_plugin_form .align-middle{position: relative;}
345
+
346
+
347
+ /* animate button effect */
348
+ .tvc_animate_btn_wrap {
349
+ height: 100%;
350
+ display: flex;
351
+ /*align-items: center;
352
+ justify-content: center;*/
353
+ }
354
+ .btn.tvc_animate_btn {
355
+ min-width: 114px;
356
+ min-height: 30px;
357
+ letter-spacing: 1.3px;
358
+ color: #fff;
359
+ background: linear-gradient(90deg, rgba(45,105,197,1) 0%, rgba(0,105,217,1) 100%);
360
+ border: none;
361
+ border-radius: 1000px;
362
+ box-shadow: 12px 12px 24px rgba(45,105,197,.64);
363
+ transition: all 0.3s ease-in-out 0s;
364
+ cursor: pointer;
365
+ outline: none;
366
+ position: relative;
367
+ padding: 6px;
368
+ padding-right: 25px;
369
+ }
370
+
371
+ button.tvc_animate_btn::before {
372
+ content: '';
373
+ border-radius: 1000px;
374
+ min-width: calc(112px + 12px);
375
+ min-height: calc(32px + 12px);
376
+ border: 2px solid #2D73C5;
377
+ box-shadow: 0 0 30px rgba(45,105,197,.64);
378
+ position: absolute;
379
+ top: 50%;
380
+ left: 50%;
381
+ transform: translate(-50%, -50%);
382
+ opacity: 0;
383
+ transition: all .3s ease-in-out 0s;
384
+ }
385
+
386
+ .btn.tvc_animate_btn:hover, .btn.tvc_animate_btn:focus {
387
+ color: #fff;
388
+ transform: translateX(4px);
389
+ padding-right: 6px;
390
+ }
391
+
392
+ button.tvc_animate_btn:hover::before, button.tvc_animate_btn:focus::before {
393
+ opacity: 1;
394
+ }
395
+
396
+ button.tvc_animate_btn::after {
397
+ content: '';
398
+ width: 30px; height: 30px;
399
+ border-radius: 100%;
400
+ border: 2px solid #fff;
401
+ position: absolute;
402
+ z-index: 1;
403
+ top: 50%;
404
+ left: 85%;
405
+ transform: translate(-50%, -50%);
406
+ animation: tvc_ring 1.5s infinite;
407
+ }
408
+
409
+ button.tvc_animate_btn:hover::after, button.tvc_animate_btn:focus::after {
410
+ animation: none;
411
+ display: none;
412
+ }
413
+
414
+ @keyframes tvc_ring {
415
+ 0% {
416
+ width: 1px;
417
+ height: 1px;
418
+ opacity: 1;
419
+ }
420
+ 100% {
421
+ width: 35px;
422
+ height: 35px;
423
+ opacity: 0;
424
+ }
425
+ }
426
+ .tvc_title_val{
427
+ width: 144px;
428
+ display: inline-block;
429
+ background-color: #eee;
430
+ padding: 8px 8px;
431
+ line-height: 22px;
432
+ min-height: 30px;
433
+ }
434
+ ul.nav-tabs{
435
+ margin-top: 20px;
436
+ background-color: #fff;
437
+ }
438
+ .wp-core-ui .notice.is-dismissible {
439
+ padding: 0 1.4rem 0 1rem;
440
+ margin: 0.5rem 1.25rem 0;
441
+ }
442
+ #googleShoppingFeed .card{
443
+ padding: 0.7rem;
444
+ }
445
+ #googleShoppingFeed .card .card-body{ padding: 5px;}
446
+ .gsf-sec .card .card-footer{padding: 5px !important;}
447
+ #googleShoppingFeed .card .card-header{padding: 15px 5px;}
448
+ #googleShoppingFeed .card .card-header .confg-title{font-size: 15px;}
449
+ .tvc_plugin_container .modal-dialog{ max-width: 650px;}
450
+ .change_prodct_feed_cat {text-decoration: underline; transition: all ease 0.5s; color: #03a2b7; margin-left: 10px; cursor: pointer;}
451
+ .config-head-active a{ color: #fff !important;}
452
+ #staticBackdrop .modal-body, #tvc_google_connect .modal-body{padding: 2rem;}
453
+ .tvc-nb-spinner {
454
+ display: inline-block;
455
+ position: absolute;
456
+ top: 3px;
457
+ right: 10px;
458
+ margin-left: 10px;
459
+ width: 20px;
460
+ height: 20px;
461
+
462
+ background: transparent;
463
+ border-top: 2px solid #0769D7;
464
+ border-right: 2px solid transparent;
465
+ border-radius: 50%;
466
+ -webkit-animation: 1s spin linear infinite;
467
+ animation: 1s tvc-spin linear infinite;
468
+ }
469
+ #refresh_api{height: 25px;}
470
+ .btn.tvc_api_sync_btn{
471
+ min-width: 114px;
472
+ min-height: 30px;
473
+ letter-spacing: 1.3px;
474
+ color: #fff;
475
+ background: linear-gradient(90deg, rgba(45,105,197,1) 0%, rgba(0,105,217,1) 100%);
476
+ border: none;
477
+ border-radius: 1000px;
478
+ box-shadow: 6px 6px 12px rgb(45 105 197 / 64%);
479
+ transition: all 0.3s ease-in-out 0s;
480
+ cursor: pointer;
481
+ outline: none;
482
+ position: relative;
483
+ padding: 6px;
484
+ }
485
+ #tvc_msg{
486
+ margin-left: 20px;
487
+ display: block;
488
+ display: inline-block;
489
+ color: #1e7e34;
490
+ }
491
+ .tvc-api-sunc{
492
+ margin-bottom: 20px;
493
+ text-align: right;
494
+ }
495
+ .tvc-api-sunc span{
496
+ color: #03a2b7;
497
+ font-weight: 700;
498
+ font-size: 14px;
499
+ margin: 7px 5px;}
500
+ @keyframes tvc-spin {
501
+ 0% { transform: rotate(0deg); }
502
+ 100% { transform: rotate(360deg); }
503
+ }
504
+ .tvc-menu-free-plan{ position: absolute;
505
+ right: 35px;
506
+ top: 31px;}
507
+ .tvc-menu-free-plan span {
508
+ color: #03a2b7;
509
+ font-size: 14px;
510
+ font-weight: 700;
511
+ padding: 7px 16px;
512
+ height: 100% !important;
513
+ vertical-align: middle;
514
+ border-radius: 25px;
515
+ background-color: #EEEEEE;
516
+ border-color: #d1d1d1;
517
+ background-clip: border-box;
518
+ border: 1px solid rgba(0,0,0,.125);
519
+ }
admin/images.zip DELETED
Binary file
admin/images/adwords.png CHANGED
File without changes
admin/images/banner.png CHANGED
File without changes
admin/images/cotlw.gif CHANGED
File without changes
admin/images/cotlw.png CHANGED
File without changes
admin/images/discount.gif CHANGED
File without changes
admin/images/facebook.jpg CHANGED
File without changes
admin/images/google_optimize.png CHANGED
File without changes
admin/images/m1.png CHANGED
File without changes
admin/images/m2.png CHANGED
File without changes
admin/images/new-2.gif CHANGED
File without changes
admin/images/new-img.gif CHANGED
File without changes
admin/images/no-config-success.svg DELETED
@@ -1 +0,0 @@
1
- <svg xmlns="http://www.w3.org/2000/svg" width="31.266" height="31.266" viewBox="0 0 31.266 31.266"><defs><style>.a{fill:#25283d;stroke:#25283d;stroke-width:0.5px;}</style></defs><g transform="translate(0.25 0.25)"><g transform="translate(6.41 6.41)"><path class="a" d="M15.9,29.357H12.051a2.081,2.081,0,0,1-1.923-2.307V24.357a4.452,4.452,0,0,0-1.666-3.333A8.861,8.861,0,0,1,5,13.845,9.123,9.123,0,0,1,13.845,5a9.009,9.009,0,0,1,6.41,2.564,9.126,9.126,0,0,1,2.692,6.41A8.621,8.621,0,0,1,19.614,20.9a4.681,4.681,0,0,0-1.795,3.589v2.948A1.972,1.972,0,0,1,15.9,29.357ZM13.973,6.282a7.862,7.862,0,0,0-7.692,7.563A7.535,7.535,0,0,0,9.23,20a5.586,5.586,0,0,1,2.179,4.359v2.692c0,.256,0,1.026.641,1.026H15.9a.606.606,0,0,0,.641-.641V24.485a6.23,6.23,0,0,1,2.307-4.615,7.475,7.475,0,0,0,2.82-5.9,7.663,7.663,0,0,0-2.307-5.512,7.556,7.556,0,0,0-5.384-2.179Z" transform="translate(-5 -5)"/></g><g transform="translate(11.537 25.638)"><path class="a" d="M16.051,21.282H9.641a.641.641,0,1,1,0-1.282h6.41a.641.641,0,1,1,0,1.282Z" transform="translate(-9 -20)"/></g><g transform="translate(14.742)"><path class="a" d="M12.141,3.846A.606.606,0,0,1,11.5,3.2V.641a.641.641,0,0,1,1.282,0V3.2A.606.606,0,0,1,12.141,3.846Z" transform="translate(-11.5)"/></g><g transform="translate(23.267 4.423)"><path class="a" d="M18.855,6.463a.771.771,0,0,1-.513-.128.62.62,0,0,1,0-.9l1.795-1.795a.635.635,0,0,1,.9.9L19.24,6.334A1.291,1.291,0,0,1,18.855,6.463Z" transform="translate(-18.15 -3.45)"/></g><g transform="translate(26.92 14.742)"><path class="a" d="M24.2,12.782H21.641a.641.641,0,0,1,0-1.282H24.2a.641.641,0,1,1,0,1.282Z" transform="translate(-21 -11.5)"/></g><g transform="translate(23.267 23.395)"><path class="a" d="M20.65,21.263a.771.771,0,0,1-.513-.128L18.342,19.34a.635.635,0,0,1,.9-.9l1.795,1.795a.62.62,0,0,1,0,.9c0,.128-.128.128-.385.128Z" transform="translate(-18.15 -18.25)"/></g><g transform="translate(4.294 23.395)"><path class="a" d="M4.055,21.263a.771.771,0,0,1-.513-.128.62.62,0,0,1,0-.9l1.795-1.795a.635.635,0,1,1,.9.9L4.44,21.134a.471.471,0,0,1-.385.128Z" transform="translate(-3.35 -18.25)"/></g><g transform="translate(0 14.742)"><path class="a" d="M3.2,12.782H.641a.641.641,0,0,1,0-1.282H3.2a.641.641,0,0,1,0,1.282Z" transform="translate(0 -11.5)"/></g><g transform="translate(4.294 4.294)"><path class="a" d="M5.85,6.491a.771.771,0,0,1-.513-.128L3.542,4.44a.635.635,0,0,1,.9-.9L6.234,5.337a.62.62,0,0,1,0,.9c-.128.128-.256.256-.385.256Z" transform="translate(-3.35 -3.35)"/></g><g transform="translate(14.742 9.614)"><path class="a" d="M17.269,13.91a.606.606,0,0,1-.641-.641,4.542,4.542,0,0,0-4.487-4.487.641.641,0,0,1,0-1.282,5.745,5.745,0,0,1,5.769,5.769A.606.606,0,0,1,17.269,13.91Z" transform="translate(-11.5 -7.5)"/></g></g></svg>
 
admin/images/plugin_bk.png CHANGED
File without changes
admin/images/rating.png CHANGED
File without changes
admin/images/ratings.png CHANGED
File without changes
admin/images/refresh.png ADDED
Binary file
admin/images/shopify_new.png CHANGED
File without changes
admin/images/tatvic_logo.png CHANGED
File without changes
admin/images/woo.png CHANGED
File without changes
admin/images/woo_banner_adv.gif CHANGED
File without changes
admin/index.php CHANGED
File without changes
admin/js/enhanced-ecommerce-google-analytics-admin.js CHANGED
File without changes
{includes/setup → admin}/js/jquery-3.5.1.min.js RENAMED
File without changes
admin/partials/about-plugin.php CHANGED
@@ -22,8 +22,8 @@ $endtime = $obj->end_time();
22
  color:green;
23
  }
24
  </style>
25
- <div class="container">
26
- <div class="row" style="margin-left:-11%; !important;">
27
  <div class= "col col-9">
28
  <div class="card mw-100" style="padding:0;">
29
  <?php $message->show_message();?>
22
  color:green;
23
  }
24
  </style>
25
+ <div class="container-fluid">
26
+ <div class="row">
27
  <div class= "col col-9">
28
  <div class="card mw-100" style="padding:0;">
29
  <?php $message->show_message();?>
admin/partials/enhanced-ecommerce-google-analytics-admin-display.php CHANGED
@@ -14,48 +14,93 @@
14
  if (!defined('ABSPATH')) {
15
  exit;
16
  }
17
-
18
- $site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
19
-
20
- if(isset($_GET['tab']) && $_GET['tab'] == 'general_settings'){
21
- $general_class_active = "active";
22
- }
23
- else{
24
- $general_class_active = "";
25
- }
26
- if(isset($_GET['tab']) && $_GET['tab'] == 'about_plugin'){
27
- $advanced_class_active = "active";
28
- }
29
- else{
30
- $advanced_class_active = "";
31
- }
32
- if(empty($_GET['tab'])){
33
- $general_class_active = "active";
34
- }
35
- // date function to hide 30% off sale after certain date
36
- $obj = new Enhanced_Ecommerce_Google_Analytics_Admin($plugin_name = 'enhanced-e-commerce-for-woocommerce-store', $version = PLUGIN_NAME_VERSION);
37
- $today = $obj->today();
38
- $start = $obj->start_date();
39
- $end = $obj->end_date();
40
- $currentime = $obj->current_time();
41
- $endtime = $obj->end_time();
42
- ?>
43
- <header class='background-color:#E8E8E8;height:500px;width:auto;margin-top:100px;margin-left:20px;'>
44
- <img class ="banner" src='<?php echo plugins_url('../images/banner.png', __FILE__ ) ?>' style="margin-left:10px;">
45
- <?php if($today >= $start && $today <= $end && $currentime <= $endtime) { ?>
46
- <div class="banner-new">
47
- <p><img class="banner-blink" src='<?php echo plugins_url('../images/discount.gif', __FILE__ ) ?>' /> On the Premium Version Till 8th Sept 2020</p>
48
- <p class="clickhere-txt"><a href="https://codecanyon.net/item/actionable-google-analytics-for-woocommerce/9899552?utm_source=TatvicEE&utm_medium=DashboardBanner&utm_campaign=SeptCamp" target="_blank">Click here</a></p>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
49
  </div>
50
- <?php } ?>
51
- </header>
52
- <ul class="nav nav-tabs nav-pills" style="margin-left: 10px;margin-top:20px;">
53
- <li class="nav-item">
54
- <a href="<?php echo $site_url.'general_settings'; ?>" class="border-left aga-tab nav-link <?php echo $general_class_active; ?>">General Settings</a>
55
- </li>
56
- <?php if($today >= $start && $today <= $end && $currentime <= $endtime) {?>
57
- <li class="nav-item"><a href="<?php echo $site_url.'about_plugin'; ?>" class="border-left aga-tab nav-link <?php echo $advanced_class_active; ?>">Premium <img class="new-img-blink" src='<?php echo plugins_url('../images/discount.gif', __FILE__ ) ?>' /></a></li>
58
- <?php } else { ?>
59
- <li class="nav-item"><a href="<?php echo $site_url.'about_plugin'; ?>" class="border-left aga-tab nav-link <?php echo $advanced_class_active; ?>">Premium <img class="new-img-blink" src='<?php echo plugins_url('../images/new-2.gif', __FILE__ ) ?>' /></a></li>
60
- <?php } ?>
61
- </ul>
14
  if (!defined('ABSPATH')) {
15
  exit;
16
  }
17
+ class TVC_Tabs {
18
+ protected $TVC_Admin_Helper;
19
+ protected $site_url;
20
+ public function __construct() {
21
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
22
+ $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
23
+ $this->create_tabs();
24
+ }
25
+ protected function info_htnml($validation){
26
+ if($validation == true){
27
+ return '<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="configuration success" class="config-success">';
28
+ }else{
29
+ return '<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/exclaimation.png" alt="configuration success" class="config-fail">';
30
+ }
31
+ }
32
+ /* add active tab class */
33
+ protected function is_active_tabs($tab_name=""){
34
+ if($tab_name!="" && isset($_GET['tab']) && $_GET['tab'] == $tab_name){
35
+ return "active";
36
+ }
37
+ return ;
38
+ }
39
+ protected function create_tabs(){
40
+ $setting_status = $this->TVC_Admin_Helper->check_setting_status();
41
+ //print_r($setting_status); exit;
42
+ /*$today = $obj->today();
43
+ $start = $obj->start_date();
44
+ $end = $obj->end_date();
45
+ $currentime = $obj->current_time();
46
+ $endtime = $obj->end_time();*/
47
+ ?>
48
+ <div class="container-fluid">
49
+ <ul class="nav nav-tabs nav-pills">
50
+ <li class="nav-item">
51
+ <div class="tvc-tooltip <?php echo (empty($_GET['tab']))?'active':$this->is_active_tabs('general_settings'); ?>">
52
+ <?php if(isset($setting_status['google_analytic']) && $setting_status['google_analytic'] == false ){?>
53
+ <?php echo (isset($setting_status['google_analytic_msg'])?'<span class="tvc-tooltiptext tvc-tooltip-right">'.$setting_status['google_analytic_msg'].'</span>':"") ?>
54
+ <?php }?>
55
+ <div class="border-left aga-tab nav-item nav-link <?php echo (empty($_GET['tab']))?'active':$this->is_active_tabs('general_settings'); ?>">
56
+ <?php if(isset($setting_status['google_analytic']) ){
57
+ echo $this->info_htnml($setting_status['google_analytic']);
58
+ }?>
59
+ <a href="<?php echo $this->site_url.'general_settings'; ?>" class=""> Google Analytics</a>
60
+ </div>
61
+ </div>
62
+ </li>
63
+ <li class="nav-item">
64
+ <div class="tvc-tooltip <?php echo $this->is_active_tabs('google_ads'); ?>">
65
+ <?php if(isset($setting_status['google_ads']) && $setting_status['google_ads'] == false ){?>
66
+ <?php echo (isset($setting_status['google_ads'])?'<span class="tvc-tooltiptext tvc-tooltip-right">'.$setting_status['google_ads_msg'].'</span>':"") ?>
67
+ <?php } ?>
68
+ <div class="border-left aga-tab nav-link <?php echo $this->is_active_tabs('google_ads'); ?>">
69
+ <?php if(isset($setting_status['google_ads']) ){
70
+ echo $this->info_htnml($setting_status['google_ads']);
71
+ }?>
72
+ <a href="<?php echo $this->site_url.'google_ads'; ?>" class="">Google Ads</a>
73
+ </div>
74
+ </li>
75
+ <?php
76
+ $sub_tab_active="";
77
+ if(isset($_GET['tab']) && ($_GET['tab'] == 'google_shopping_feed' || $_GET['tab'] == 'gaa_config_page' || $_GET['tab'] == 'sync_product_page' || $_GET['tab'] == 'shopping_campaigns_page' || $_GET['tab'] == 'add_campaign_page')){
78
+ $sub_tab_active="active";
79
+ }
80
+ ?>
81
+ <li class="nav-item">
82
+ <div class="tvc-tooltip <?php echo (($sub_tab_active)?$sub_tab_active:$this->is_active_tabs('google_shopping_feed')); ?>">
83
+ <?php if(isset($setting_status['google_shopping']) && $setting_status['google_shopping'] == false ){?>
84
+ <?php echo (isset($setting_status['google_shopping_msg'])?'<span class="tvc-tooltiptext tvc-tooltip-right">'.$setting_status['google_shopping_msg'].'</span>':"") ?>
85
+ <?php } ?>
86
+ <div class="border-left aga-tab nav-link <?php echo (($sub_tab_active)?$sub_tab_active:$this->is_active_tabs('google_shopping_feed')); ?>">
87
+ <?php if(isset($setting_status['google_shopping']) ){
88
+ echo $this->info_htnml($setting_status['google_shopping']);
89
+ }?>
90
+ <a href="<?php echo $this->site_url.'google_shopping_feed'; ?>" class="">Google Shopping</a>
91
+ </div>
92
+ </li>
93
+ <?php /*if($today >= $start && $today <= $end && $currentime <= $endtime) {?>
94
+ <li class="nav-item">
95
+ <div class="border-left aga-tab nav-link <?php echo $this->is_active_tabs('about_plugin'); ?>"><a href="<?php echo $this->site_url.'about_plugin'; ?>">Premium <img class="new-img-blink" src='<?php echo plugins_url('../images/discount.gif', __FILE__ ) ?>' /></a></div></li>
96
+ <?php } else { ?>
97
+ <li class="nav-item"><div class="border-left aga-tab nav-link <?php echo $this->is_active_tabs('about_plugin'); ?>"><a href="<?php echo $this->site_url.'about_plugin'; ?>">Premium <img class="new-img-blink" src='<?php echo plugins_url('../images/new-2.gif', __FILE__ ) ?>' /></a></div></li>
98
+ <?php }*/ ?>
99
+ <li class="tvc-menu-free-plan">
100
+ <span>Free Plan: 500 Product sync limit</span>
101
+ </li>
102
+ </ul>
103
  </div>
104
+ <?php
105
+ }
106
+ } ?>
 
 
 
 
 
 
 
 
 
admin/partials/general-fields.php CHANGED
@@ -1,55 +1,200 @@
1
  <?php
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2
  $message = new Enhanced_Ecommerce_Google_Settings();
3
  if (isset($_POST['ee_submit_plugin'])) {
 
 
 
 
 
 
 
 
 
 
 
4
  Enhanced_Ecommerce_Google_Settings::add_update_settings('ee_options');
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5
  }
6
  $data = unserialize(get_option('ee_options'));
 
7
  ?>
8
- <div class="container">
9
- <div class="row" style="margin-left:-11%; !important;">
10
  <div class= "col col-9" >
11
  <div class="card mw-100" style="padding:0px;">
12
  <?php $message->show_message(); ?>
13
- <div class="card-header">
14
  <h3>Enhanced Ecommerce Google Analytics <a href = "https://wordpress.org/support/plugin/enhanced-e-commerce-for-woocommerce-store/reviews/" target="_blank" style="float: right">
15
  <div class="rating">
16
  <span>☆</span><span>☆</span><span>☆</span><span>☆</span><span>☆</span>
17
  </div>
18
  </a>
19
  </h3>
20
- </div>
21
  <div class="card-body">
22
- <form id="ee_plugin_form" method="post" action="" enctype="multipart/form-data" >
23
  <table class="table table-bordered">
24
  <tbody>
25
- <tr>
26
- <td>
27
- <label class="align-middle" for="woocommerce_ee_google_analytics_ga_id">Google Analytics ID</label>
28
- </td>
29
- <td>
30
- <!-- <input type="text" id="ga_id" name = "ga_id" required = "required" value="--><?php //echo $data['ga_id']; ?><!--">-->
31
- <!-- <i style="cursor: help;" class="fas fa-question-circle" title="Enter your Google Analytics ID here. You can login into your Google Analytics account to find your ID. e.g. UA-XXXXXX-XX"></i>-->
 
 
 
 
 
 
 
 
 
32
 
33
- <?php if(isset($data['ga_id']) && $data['ga_id'] != '') { ?>
34
- <input style="border: none;box-shadow: none;width: 35%;" type="text" id="ga_id" name = "ga_id" required = "required" disabled value="<?= $data['ga_id']; ?>"/>
35
- <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update analytics id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
36
- <?php } else {?>
37
- <!--signin with google-->
38
- <a target="_blank" class="ee-oauth-container btn darken-4 white black-text" href="<?=esc_url($this->url)?>" style="text-transform:none">
39
- <div class="left">
40
- <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
41
- src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
42
- </div>
43
- <p style="font-size: inherit; margin-top:5px; margin-right:8px; ">Sign In With Google</p>
44
- </a>
45
- <!--sigin with google end-->
46
- <?php } ?>
47
- </td>
 
 
48
 
49
- </tr>
50
- <tr>
51
- <td>
52
- <label class="align-middle" for="woocommerce_ee_google_analytics_ads_id">Linked Google Ads Account <i style="cursor: help;" class="fas fa-question-circle" title="To link Google Ads and Google Analytics, you’ll need administrative access to a Google Ads account and “Edit permissions” to a Google Analytics account.
53
  Why link Google Ads and Analytics account?
54
  When you link Google Ads and Analytics, you can:
55
  See ad and site performance data in the Google Ads reports in Analytics.
@@ -58,118 +203,171 @@ Import cross-device conversions into your Google Ads account when you activate G
58
  Import Analytics metrics like Bounce Rate, Avg. Session Duration, and Pages/Session into your Google Ads account.
59
  Enhance your Google Ads remarketing with Analytics Remarketing and Dynamic Remarketing.
60
  Get richer data in the Analytics Multi-Channel Funnels reports."></i></label>
61
- </td>
62
- <td>
63
- <!-- <input type="text" id="ga_id" name = "ga_id" required = "required" value="--><?php //echo $data['ga_id']; ?><!--">-->
64
- <!-- <i style="cursor: help;" class="fas fa-question-circle" title="Enter your Google Analytics ID here. You can login into your Google Analytics account to find your ID. e.g. UA-XXXXXX-XX"></i>-->
65
-
66
- <?php if(isset($data['ads_id']) && $data['ads_id'] != '') { ?>
67
- <input style="border: none;box-shadow: none;width: 35%;" type="text" id="ads_id" name = "ads_id" disabled value="<?= $data['ads_id']; ?>"/>
68
- <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update ads account id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
69
- <?php } else {?>
70
- <!--signin with google-->
71
- <a target="_blank" class="ee-oauth-container btn darken-4 white black-text" href="<?=esc_url($this->url)?>" style="text-transform:none">
72
- <div class="left">
73
- <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
74
- src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
75
- </div>
76
- <p style="font-size: inherit; margin-top:5px; margin-right:8px; ">Sign In With Google</p>
77
- </a>
78
- <!--sigin with google end-->
79
- <?php } ?>
80
- </td>
81
 
82
- </tr>
83
- <tr>
84
- <td>
85
- <label class="align-middle" for="tracking_code">Tracking Code</label>
86
- </td>
87
- <td>
88
- <label class = "align-middle" for="ga_code">
89
- <?php $ga_ST = !empty($data['ga_ST']) ? 'checked' : ''; ?>
90
- <input type="checkbox" name="ga_ST" id="ga_ST" <?php echo $ga_ST; ?> >
91
- Add Global Site Tracking Code 'gtag.js'
92
- <i style="cursor: help;" class="fas fa-question-circle" title="This feature adds new gtag.js tracking code to your store. You don't need to enable this if gtag.js is implemented via any third party analytics plugin."></i>
93
- <!--<p class="description">This feature adds new gtag.js tracking code to your store. You don't need to enable this if gtag.js is implemented via any third party analytics plugin.</p>-->
94
- </label><br/>
95
- <label class = "align-middle" for="ga_enhance_ecommerce">
96
- <?php $ga_eeT = !empty($data['ga_eeT']) ? 'checked' : ''; ?>
97
- <input type="checkbox" name="ga_eeT" id="ga_eeT" <?php echo $ga_eeT; ?> >
98
- Add Enhanced Ecommerce Tracking Code
99
- <i style="cursor: help;" class="fas fa-question-circle" title="This feature adds Enhanced Ecommerce Tracking Code to your Store"></i>
100
- <!--<p class="description">This feature adds Enhanced Ecommerce Tracking Code to your Store</p>-->
101
- </label><br/>
102
- <label class = "align-middle" for="ga_login_step">
103
- <?php $ga_gUser = !empty($data['ga_gUser']) ? 'checked' : ''; ?>
104
- <input type="checkbox" name="ga_gUser" id="ga_gUser" <?php echo $ga_gUser; ?> >
105
- Add Code to Track the Login Step of Guest Users (Optional)
106
- <i style="cursor: help;" class="fas fa-question-circle" title="If you have Guest Check out enable, we recommend you to add this code"></i>
107
- <!--<p class="description">If you have Guest Check out enable, we recommend you to add this code</p>-->
108
- </label><br/>
109
- </td>
110
- </tr>
111
- <tr>
112
- <td>
113
- <label for="ga_Impr">Impression Thresold</label>
114
- </td>
115
- <td>
116
- <?php $ga_Impr = !empty($data['ga_Impr']) ? $data['ga_Impr'] : 6; ?>
117
- <input type="number" min="1" id="ga_Impr" name = "ga_Impr" value = "<?php echo $ga_Impr; ?>">
118
- <i style="cursor: help;" class="fas fa-question-circle" title="This feature sets Impression threshold for category page. It sends hit after these many numbers of products impressions."></i>
119
- <p class="description"><br><b>Note : To avoid processing load on server we recommend upto 6 Impression Thresold.</b></p>
120
- </td>
121
- </tr>
122
- <tr>
123
- <td>
124
- <label class = "align-middle" for="ga_IPA">I.P. Anoymization</label>
125
- </td>
126
- <td>
127
- <label class = "align-middle" for="ga_IPA">
128
- <?php $ga_IPA = !empty($data['ga_IPA']) ? 'checked' : ''; ?>
129
- <input class="" type="checkbox" name="ga_IPA" id="ga_IPA" <?php echo $ga_IPA; ?>>
130
- Enable I.P. Anonymization
131
- <i style="cursor: help;" class="fas fa-question-circle" title="Use this feature to anonymize (or stop collecting) the I.P Address of your users in Google Analytics. Be in legal compliance by using I.P Anonymization which is important for EU countries As per the GDPR compliance"></i>
132
- <!-- <p class="description">Use this feature to anonymize (or stop collecting) the I.P Address of your users in Google Analytics. Be in legal compliance by using I.P Anonymization which is important for EU countries As per the GDPR compliance</p>-->
133
- </label>
134
- </td>
135
- </tr>
136
- <tr>
137
- <td>
138
- <label class = "align-middle" for="ga_OPTOUT">Google Analytics Opt Out</label>
139
- </td>
140
- <td>
141
- <label class = "align-middle" for="ga_OPTOUT">
142
- <?php $ga_OPTOUT = !empty($data['ga_OPTOUT']) ? 'checked' : ''; ?>
143
- <input class="" type="checkbox" name="ga_OPTOUT" id="ga_OPTOUT" <?php echo $ga_OPTOUT; ?>>
144
- Enable Google Analytics Opt Out (Optional)
145
- <i style="cursor: help;" class="fas fa-question-circle" title="Use this feature to provide website visitors the ability to prevent their data from being used by Google Analytics As per the GDPR compliance.Go through the documentation to check the setup"></i>
146
- <!--<p class="description">Use this feature to provide website visitors the ability to prevent their data from being used by Google Analytics As per the GDPR compliance.Go through the documentation to check the setup</p>-->
147
- </label>
148
- </td>
149
- </tr>
150
- <tr>
151
- <td>
152
- <label class = "align-middle" for="ga_PrivacyPolicy">Privacy Policy</label>
153
- </td>
154
- <td>
155
- <label class = "align-middle" for="ga_PrivacyPolicy">
156
- <?php $ga_PrivacyPolicy = !empty($data['ga_PrivacyPolicy']) ? 'checked' : ''; ?>
157
- <input type="checkbox" onchange="enableSubmit();" name="ga_PrivacyPolicy" id="ga_PrivacyPolicy" required="required" <?php echo $ga_PrivacyPolicy; ?>>
158
- Accept Privacy Policy of Plugin
159
- <p class="description">By using Tatvic Plugin, you agree to Tatvic plugin's <a href= "https://www.tatvic.com/privacy-policy/?ref=plugin_policy&utm_source=plugin_backend&utm_medium=woo_premium_plugin&utm_campaign=GDPR_complaince_ecomm_plugins" target="_blank">Privacy Policy</a></p>
160
- </label>
161
- </td>
162
- </tr>
163
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
164
  </tbody>
165
  </table>
166
  <p class="submit save-for-later" id="save-for-later">
 
 
 
 
 
 
167
  <button type="submit" class="btn btn-primary btn-success" id="ee_submit_plugin" name="ee_submit_plugin">Submit</button>
168
  </p>
169
  </form>
170
  </div>
171
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
172
  </div>
173
  <?php require_once('sidebar.php'); ?>
174
  </div>
175
- </div>
1
  <?php
2
+ echo "<script>var return_url ='".esc_url($this->url)."';</script>";
3
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
4
+ if (isset($_GET['connect']) && isset($_GET['subscription_id'])) {
5
+
6
+ if (isset($_GET['subscription_id']) && $_GET['subscription_id']) {
7
+ $_POST['subscription_id'] = $_GET['subscription_id'];
8
+ Enhanced_Ecommerce_Google_Settings::add_update_settings('ee_options');
9
+ }
10
+ $customApiObj = new CustomApi();
11
+ $google_detail = $customApiObj->getGoogleAnalyticDetail();
12
+ if(isset($google_detail->data['status']) && $google_detail->data['status'] == 200 && !isset($_POST['ee_submit_plugin'])){
13
+ if (isset($google_detail->data['data'])) {
14
+ $googleDetail = $google_detail->data['data'];
15
+ // save API data in DB
16
+ $postData = [
17
+ 'merchant_id' => $googleDetail->merchant_id,
18
+ 'website_url' => $googleDetail->site_url,
19
+ 'subscription_id' => $googleDetail->id,
20
+ 'account_id' => $googleDetail->google_merchant_center_id
21
+ ];
22
+
23
+ if ($googleDetail->is_site_verified == '0') {
24
+ $siteVerificationToken = $customApiObj->siteVerificationToken($postData);
25
+ if (isset($siteVerificationToken->error) && !empty($siteVerificationToken->errors)) {
26
+ } else {
27
+ $myFile = ABSPATH.$siteVerificationToken->data->token; // or .php
28
+ if (!file_exists($myFile)) {
29
+ $fh = fopen($myFile, 'w+');
30
+ chmod($myFile,0777);
31
+ $stringData = "google-site-verification: ".$siteVerificationToken->data->token;
32
+ fwrite($fh, $stringData);
33
+ fclose($fh);
34
+ }
35
+
36
+ $siteVerification = $customApiObj->siteVerification($postData);
37
+ if (isset($siteVerification->error) && !empty($siteVerification->errors)) {
38
+ } else {
39
+ $googleDetail->is_site_verified = '1';
40
+ }
41
+ }
42
+ }
43
+
44
+ if ($googleDetail->is_domain_claim == '0') {
45
+ $claimWebsite = $customApiObj->claimWebsite($postData);
46
+ if (isset($claimWebsite->error) && !empty($claimWebsite->errors)) {
47
+ } else {
48
+ $googleDetail->is_domain_claim = '1';
49
+ }
50
+ }
51
+ $_POST['subscription_id'] = $googleDetail->id;
52
+ $_POST['ga_eeT'] = (isset($googleDetail->enhanced_e_commerce_tracking) && $googleDetail->enhanced_e_commerce_tracking == "1") ? "on" : "";
53
+
54
+ $_POST['ga_ST'] = (isset($googleDetail->add_gtag_snippet) && $googleDetail->add_gtag_snippet == "1") ? "on" : "";
55
+ $_POST['gm_id'] = $googleDetail->measurement_id;
56
+ $_POST['ga_id'] = $googleDetail->property_id;
57
+ $_POST['google_ads_id'] = $googleDetail->google_ads_id;
58
+ $_POST['google_merchant_id'] = $googleDetail->google_merchant_center_id;
59
+ $_POST['tracking_option'] = $googleDetail->tracking_option;
60
+ $_POST['ga_gUser'] = 'on';
61
+ //$_POST['ga_gCkout'] = 'on';
62
+ $_POST['ga_Impr'] = 6;
63
+ $_POST['ga_IPA'] = 'on';
64
+ $_POST['ga_OPTOUT'] = 'on';
65
+ $_POST['ga_PrivacyPolicy'] = 'on';
66
+ $_POST['google-analytic'] = '';
67
+ //update option in wordpress local database
68
+ update_option('ads_tracking_id', $googleDetail->google_ads_id);
69
+ update_option('ads_ert', $googleDetail->remarketing_tags);
70
+ update_option('ads_edrt', $googleDetail->dynamic_remarketing_tags);
71
+ Enhanced_Ecommerce_Google_Settings::add_update_settings('ee_options');
72
+
73
+ if(isset($googleDetail->google_merchant_center_id) || isset($googleDetail->google_ads_id) ){
74
+ if( $googleDetail->google_merchant_center_id != "" && $googleDetail->google_ads_id != ""){
75
+ $TVC_Admin_Helper->set_update_api_to_db($googleDetail);
76
+ wp_redirect("admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=sync_product_page&welcome_msg=true");
77
+ exit;
78
+ }else{
79
+ wp_redirect("admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=gaa_config_page&welcome_msg=true");
80
+ exit;
81
+ }
82
+ }
83
+ }
84
+ }
85
+ } else if(isset($_GET['connect']) && !isset($_POST['ee_submit_plugin'])) {
86
+ $googleDetail = [];
87
+ $class = 'notice notice-error';
88
+ $message_p = esc_html__('Google analytic detail is empty.');
89
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message_p));
90
+ }else{
91
+ $TVC_Admin_Helper->is_ee_options_data_empty();
92
+ }
93
  $message = new Enhanced_Ecommerce_Google_Settings();
94
  if (isset($_POST['ee_submit_plugin'])) {
95
+ if(!empty($_POST['ga_id'])){
96
+ $_POST['tracking_option'] = "UA";
97
+ }
98
+ if(!empty($_POST['gm_id'])){
99
+ $_POST['tracking_option'] = "GA4";
100
+ }
101
+ if(!empty($_POST['gm_id']) && !empty($_POST['ga_id'])){
102
+ $_POST['tracking_option'] = "BOTH";
103
+ }
104
+ update_option('ads_tracking_id', $_POST['google_ads_id']);
105
+
106
  Enhanced_Ecommerce_Google_Settings::add_update_settings('ee_options');
107
+ /* API Save */
108
+ /*if(isset($_POST['ga_eeT'])){
109
+ $_POST['enhanced_e_commerce_tracking']=($_POST['ga_eeT']=="on")?1:0;
110
+ unset($_POST['ga_eeT']);
111
+ }
112
+ if(isset($_POST['ga_ST'])){
113
+ $_POST['add_gtag_snippet']=($_POST['ga_ST']=="on")?1:0;
114
+ unset($_POST['ga_ST']);
115
+ }
116
+ if(isset($_POST['subscription_id']) && $_POST['subscription_id'] >0) {
117
+ $customApiObj = new CustomApi();
118
+ $response = $customApiObj->updateTrackingOption($_POST);
119
+ if (isset($response->errors) && !empty($response->errors)) {
120
+ $error_code = array_keys($response->errors)[0];
121
+ $class = 'notice notice-error';
122
+ $r_message = esc_html__('The tracking options is not added successfully.');
123
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Error : ' . $r_message));
124
+ } else {
125
+ $response = $response->data;
126
+ if (isset($response['status']) && $response['status'] == 200) {
127
+ $class = 'notice notice-success';
128
+ $r_message = esc_html__('The tracking options added successfully.');
129
+ //printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($r_message));
130
+ }
131
+ }
132
+ }else{
133
+ $class = 'notice notice-error';
134
+ $r_message = esc_html__('Connect Google account to enable more features.');
135
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Error : ' . $r_message));
136
+ }*/
137
+
138
  }
139
  $data = unserialize(get_option('ee_options'));
140
+ $ads_trck_id = $TVC_Admin_Helper->get_ee_options_settings();
141
  ?>
142
+ <div class="container-fluid">
143
+ <div class="row">
144
  <div class= "col col-9" >
145
  <div class="card mw-100" style="padding:0px;">
146
  <?php $message->show_message(); ?>
147
+ <?php /* <div class="card-header">
148
  <h3>Enhanced Ecommerce Google Analytics <a href = "https://wordpress.org/support/plugin/enhanced-e-commerce-for-woocommerce-store/reviews/" target="_blank" style="float: right">
149
  <div class="rating">
150
  <span>☆</span><span>☆</span><span>☆</span><span>☆</span><span>☆</span>
151
  </div>
152
  </a>
153
  </h3>
154
+ </div>*/ ?>
155
  <div class="card-body">
156
+ <form id="ee_plugin_form" class="tvc_ee_plugin_form" method="post" action="" enctype="multipart/form-data" >
157
  <table class="table table-bordered">
158
  <tbody>
159
+ <tr>
160
+ <td>
161
+ <label class="align-middle" for="woocommerce_ee_google_analytics_ga_id">Universal Analytics ID</label>
162
+ </td>
163
+ <td>
164
+ <?php if(isset($data['ga_id']) && $data['ga_id'] != '') { ?>
165
+ <span class="tvc_title_val"><?= $data['ga_id']; ?></span>
166
+ <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update analytics id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
167
+ <?php } else {?>
168
+ <div class="tvc_animate_btn_wrap">
169
+ <button type="button" class="btn btn-primary tvc_animate_btn" data-toggle="modal" data-target="#staticBackdrop">
170
+ Connect
171
+ </button>
172
+ </div>
173
+ <?php } ?>
174
+ </td>
175
 
176
+ </tr>
177
+ <tr>
178
+ <td>
179
+ <label class="align-middle" for="woocommerce_ee_google_analytics_ga_id">Google Analytics 4 ID</label>
180
+ </td>
181
+ <td>
182
+ <?php if(isset($data['gm_id']) && $data['gm_id'] != '') { ?>
183
+ <span class="tvc_title_val"><?= $data['gm_id']; ?></span>
184
+ <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update google analytics 4 id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
185
+ <?php } else {?>
186
+ <div class="tvc_animate_btn_wrap">
187
+ <button type="button" class="btn btn-primary tvc_animate_btn" data-toggle="modal" data-target="#staticBackdrop">
188
+ Connect
189
+ </button>
190
+ </div>
191
+ <?php } ?>
192
+ </td>
193
 
194
+ </tr>
195
+ <tr>
196
+ <td>
197
+ <label class="align-middle" for="woocommerce_ee_google_analytics_ads_id">Linked Google Ads Account <i style="cursor: help;" class="fas fa-question-circle" title="To link Google Ads and Google Analytics, you’ll need administrative access to a Google Ads account and “Edit permissions” to a Google Analytics account.
198
  Why link Google Ads and Analytics account?
199
  When you link Google Ads and Analytics, you can:
200
  See ad and site performance data in the Google Ads reports in Analytics.
203
  Import Analytics metrics like Bounce Rate, Avg. Session Duration, and Pages/Session into your Google Ads account.
204
  Enhance your Google Ads remarketing with Analytics Remarketing and Dynamic Remarketing.
205
  Get richer data in the Analytics Multi-Channel Funnels reports."></i></label>
206
+ </td>
207
+ <td>
208
+ <?php if(isset($data['google_ads_id']) && $data['google_ads_id'] != '') { ?>
209
+ <span class="tvc_title_val"><?= $data['google_ads_id']; ?></span>
210
+ <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update ads account id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
211
+ <?php } else {?>
212
+ <div class="tvc_animate_btn_wrap">
213
+ <button type="button" class="btn btn-primary tvc_animate_btn" data-toggle="modal" data-target="#staticBackdrop">
214
+ Connect
215
+ </button>
216
+ </div>
217
+ <?php } ?>
218
+ </td>
 
 
 
 
 
 
 
219
 
220
+ </tr>
221
+ <tr>
222
+ <td>
223
+ <label class="align-middle" for="woocommerce_ee_google_analytics_merchant_id">Linked Google Merchant Center Account</label>
224
+ </td>
225
+ <td>
226
+ <?php if(isset($data['google_merchant_id']) && $data['google_merchant_id'] != '') { ?>
227
+ <span class="tvc_title_val"><?= $data['google_merchant_id']; ?></span>
228
+ <p class="hint-text" style="color: #666;display: inline-block;float: right;padding-top: 5px;">To update merchant account id, <a target="_blank" href="<?=esc_url($this->url)?>">click here</a></p>
229
+ <?php } else {?>
230
+ <div class="tvc_animate_btn_wrap">
231
+ <button type="button" class="btn btn-primary tvc_animate_btn" data-toggle="modal" data-target="#staticBackdrop">
232
+ Connect
233
+ </button>
234
+ </div>
235
+ <?php } ?>
236
+ </td>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
237
 
238
+ </tr>
239
+ <tr>
240
+ <td>
241
+ <label class="align-middle" for="tracking_code">Tracking Code</label>
242
+ </td>
243
+ <td>
244
+ <label class = "align-middle">
245
+ <?php $ga_ST = !empty($data['ga_ST']) ? 'checked' : ''; ?>
246
+ <input type="checkbox" name="ga_ST" id="ga_ST" <?php echo $ga_ST; ?> >
247
+ <label for="ga_ST">Add Global Site Tracking Code 'gtag.js'</label>
248
+
249
+ <i style="cursor: help;" class="fas fa-question-circle" title="This feature adds new gtag.js tracking code to your store. You don't need to enable this if gtag.js is implemented via any third party analytics plugin."></i>
250
+ <!--<p class="description">This feature adds new gtag.js tracking code to your store. You don't need to enable this if gtag.js is implemented via any third party analytics plugin.</p>-->
251
+ </label><br/>
252
+ <label class = "align-middle">
253
+ <?php $ga_eeT = !empty($data['ga_eeT']) ? 'checked' : ''; ?>
254
+ <input type="checkbox" name="ga_eeT" id="ga_eeT" <?php echo $ga_eeT; ?> >
255
+ <label for="ga_eeT">Add Enhanced Ecommerce Tracking Code</label>
256
+
257
+ <i style="cursor: help;" class="fas fa-question-circle" title="This feature adds Enhanced Ecommerce Tracking Code to your Store"></i>
258
+ <!--<p class="description">This feature adds Enhanced Ecommerce Tracking Code to your Store</p>-->
259
+ </label><br/>
260
+ <label class = "align-middle">
261
+ <?php $ga_gUser = !empty($data['ga_gUser']) ? 'checked' : ''; ?>
262
+ <input type="checkbox" name="ga_gUser" id="ga_gUser" <?php echo $ga_gUser; ?> >
263
+ <label for="ga_gUser">Add Code to Track the Login Step of Guest Users (Optional)</label>
264
+
265
+ <i style="cursor: help;" class="fas fa-question-circle" title="If you have Guest Check out enable, we recommend you to add this code"></i>
266
+ <!--<p class="description">If you have Guest Check out enable, we recommend you to add this code</p>-->
267
+ </label><br/>
268
+ </td>
269
+ </tr>
270
+ <tr>
271
+ <td>
272
+ <label for="ga_Impr">Impression Thresold</label>
273
+ </td>
274
+ <td>
275
+ <?php $ga_Impr = !empty($data['ga_Impr']) ? $data['ga_Impr'] : 6; ?>
276
+ <input type="number" min="1" id="ga_Impr" name = "ga_Impr" value = "<?php echo $ga_Impr; ?>">
277
+ <label for="ga_Impr"></label>
278
+ <i style="cursor: help;" class="fas fa-question-circle" title="This feature sets Impression threshold for category page. It sends hit after these many numbers of products impressions."></i>
279
+ <p class="description"><br><b>Note : To avoid processing load on server we recommend upto 6 Impression Thresold.</b></p>
280
+ </td>
281
+ </tr>
282
+ <tr>
283
+ <td>
284
+ <label class = "align-middle" for="ga_IPA">I.P. Anoymization</label>
285
+ </td>
286
+ <td>
287
+ <label class = "align-middle">
288
+ <?php $ga_IPA = !empty($data['ga_IPA']) ? 'checked' : ''; ?>
289
+ <input class="" type="checkbox" name="ga_IPA" id="ga_IPA" <?php echo $ga_IPA; ?>>
290
+ <label for="ga_IPA">Enable I.P. Anonymization</label>
291
+
292
+ <i style="cursor: help;" class="fas fa-question-circle" title="Use this feature to anonymize (or stop collecting) the I.P Address of your users in Google Analytics. Be in legal compliance by using I.P Anonymization which is important for EU countries As per the GDPR compliance"></i>
293
+ <!-- <p class="description">Use this feature to anonymize (or stop collecting) the I.P Address of your users in Google Analytics. Be in legal compliance by using I.P Anonymization which is important for EU countries As per the GDPR compliance</p>-->
294
+ </label>
295
+ </td>
296
+ </tr>
297
+ <tr>
298
+ <td>
299
+ <label class = "align-middle" for="ga_OPTOUT">Google Analytics Opt Out</label>
300
+ </td>
301
+ <td>
302
+ <label class = "align-middle">
303
+ <?php $ga_OPTOUT = !empty($data['ga_OPTOUT']) ? 'checked' : ''; ?>
304
+ <input class="" type="checkbox" name="ga_OPTOUT" id="ga_OPTOUT" <?php echo $ga_OPTOUT; ?>>
305
+ <label for="ga_OPTOUT">Enable Google Analytics Opt Out (Optional)</label>
306
+
307
+ <i style="cursor: help;" class="fas fa-question-circle" title="Use this feature to provide website visitors the ability to prevent their data from being used by Google Analytics As per the GDPR compliance.Go through the documentation to check the setup"></i>
308
+ <!--<p class="description">Use this feature to provide website visitors the ability to prevent their data from being used by Google Analytics As per the GDPR compliance.Go through the documentation to check the setup</p>-->
309
+ </label>
310
+ </td>
311
+ </tr>
312
+ <tr>
313
+ <td>
314
+ <label class = "align-middle" for="ga_PrivacyPolicy">Privacy Policy</label>
315
+ </td>
316
+ <td>
317
+ <label class = "align-middle">
318
+ <?php $ga_PrivacyPolicy = !empty($data['ga_PrivacyPolicy']) ? 'checked' : ''; ?>
319
+ <input type="checkbox" onchange="enableSubmit();" name="ga_PrivacyPolicy" id="ga_PrivacyPolicy" required="required" <?php echo $ga_PrivacyPolicy; ?>>
320
+ <label for="ga_PrivacyPolicy">Accept Privacy Policy of Plugin</label>
321
+
322
+ <p class="description">By using Tatvic Plugin, you agree to Tatvic plugin's <a href= "https://www.tatvic.com/privacy-policy/?ref=plugin_policy&utm_source=plugin_backend&utm_medium=woo_premium_plugin&utm_campaign=GDPR_complaince_ecomm_plugins" target="_blank">Privacy Policy</a></p>
323
+ </label>
324
+ </td>
325
+ </tr>
326
  </tbody>
327
  </table>
328
  <p class="submit save-for-later" id="save-for-later">
329
+
330
+ <input type="hidden" id="ga_id" name = "ga_id" value="<?= (!empty($data['ga_id']))?$data['ga_id']:""; ?>"/>
331
+ <input type="hidden" id="gm_id" name = "gm_id" value="<?= (!empty($data['gm_id']))?$data['gm_id']:""; ?>"/>
332
+ <input type="hidden" id="google_ads_id" name = "google_ads_id" value="<?= (!empty($data['google_ads_id']))?$data['google_ads_id']:""; ?>"/>
333
+ <input type="hidden" id="google_merchant_id" name = "google_merchant_id" value="<?= (!empty($data['google_merchant_id']))?$data['google_merchant_id']:""; ?>"/>
334
+ <input type="hidden" name="subscription_id" value="<?php echo (!empty($data['subscription_id']))?$data['subscription_id']:""; ?>">
335
  <button type="submit" class="btn btn-primary btn-success" id="ee_submit_plugin" name="ee_submit_plugin">Submit</button>
336
  </p>
337
  </form>
338
  </div>
339
  </div>
340
+ <!-- Modal -->
341
+ <div class="modal fade" id="staticBackdrop" data-backdrop="static" data-keyboard="false" tabindex="-1" aria-labelledby="staticBackdropLabel" aria-hidden="true">
342
+ <div class="modal-dialog modal-dialog-centered">
343
+ <div class="modal-content">
344
+ <div class="modal-header">
345
+ <h5 class="modal-title" id="staticBackdropLabel">Connect Tatvic with your website</h5>
346
+ <button type="button" class="close" data-dismiss="modal" aria-label="Close">
347
+ <span aria-hidden="true">&times;</span>
348
+ </button>
349
+ </div>
350
+ <div class="modal-body">
351
+ By continuing from here, you will be redirected to Tatvic’s website to configure your google analytics, google ads and google merchant center accounts.
352
+ <br>
353
+ <br>
354
+ Make sure you sign in with the google account that has all privileges to access google analytics, google ads and google merchant center account.
355
+ </div>
356
+ <div class="modal-footer">
357
+ <a target="_blank" class="ee-oauth-container btn darken-4 white black-text" href="<?=esc_url($this->url)?>" style="text-transform:none; margin: 0 auto;">
358
+ <div class="left">
359
+ <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
360
+ src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
361
+ </div>
362
+ <p style="font-size: inherit; margin-top:5px; margin-right:8px; ">Sign In With Google</p>
363
+ </a>
364
+ <!--sigin with google end-->
365
+ </div>
366
+ </div>
367
+ </div>
368
+ </div>
369
+ <!-- Modal End -->
370
  </div>
371
  <?php require_once('sidebar.php'); ?>
372
  </div>
373
+ </div>
admin/partials/sidebar.php CHANGED
@@ -8,13 +8,15 @@ $endtime = $obj->end_time();
8
 
9
  ?>
10
  <div class="col col-xs-3">
 
11
  <div class="card" style="padding: 0px;">
12
  <div class="card-header">
13
  <h5> Important Links</h5>
14
  </div>
15
  <div class="card-body">
16
  <ul>
17
- <li style="padding-bottom:5px;"><a href="http://plugins.tatvic.com/downloads/EE-Woocommerce-Plugin-Documentation.pdf" target="_blank">Installation Instructions</a></li>
 
18
  <li style="padding-bottom:5px;"><a href="https://wordpress.org/plugins/enhanced-e-commerce-for-woocommerce-store/faq/" target="_blank">FAQ</a></li>
19
  <li style="padding-bottom:5px;"><a href="https://www.tatvic.com/contact/?utm_source=TatvicEE&utm_medium=Dashboard&utm_campaign=WPlisting" target="_blank">Support</a></li>
20
  <li style="padding-bottom:5px;"><a href="https://www.tatvic.com/privacy-policy/?ref=plugin_policy&utm_source=plugin_backend&utm_medium=woo_free_plugin&utm_campaign=GDPR_complaince_ecomm_plugins" target="_blank">Privacy Policy</a></li>
@@ -24,10 +26,10 @@ $endtime = $obj->end_time();
24
  </div>
25
  <div class="card" style="padding: 0px;">
26
  <div class="card-header">
27
- <h4>Rate Us!</h4>
28
  </div>
29
  <div class="card-body">
30
- <ul style="font-weight: 600">
31
  <li style="padding-bottom:5px;">Do you Like our Plugin? Please Spare few minutes to give <h3><a href = "https://wordpress.org/support/plugin/enhanced-e-commerce-for-woocommerce-store/reviews/" target="_blank" style="float: right">
32
  <div class="rating">
33
  <span>☆</span><span>☆</span><span>☆</span><span>☆</span><span>☆</span>
@@ -54,4 +56,5 @@ $endtime = $obj->end_time();
54
  </ul>
55
  </div>
56
  </div>
 
57
  </div>
8
 
9
  ?>
10
  <div class="col col-xs-3">
11
+ <div class="tvc_plugin_sidebar">
12
  <div class="card" style="padding: 0px;">
13
  <div class="card-header">
14
  <h5> Important Links</h5>
15
  </div>
16
  <div class="card-body">
17
  <ul>
18
+ <li style="padding-bottom:5px;"><a href="http://plugins.tatvic.com/help-center/Installation-Manual.pdf" target="_blank">Installation Manual</a></li>
19
+ <li style="padding-bottom:5px;"><a href="http://plugins.tatvic.com/help-center/Google-shopping-Guide.pdf" target="_blank">Google shopping guide</a></li>
20
  <li style="padding-bottom:5px;"><a href="https://wordpress.org/plugins/enhanced-e-commerce-for-woocommerce-store/faq/" target="_blank">FAQ</a></li>
21
  <li style="padding-bottom:5px;"><a href="https://www.tatvic.com/contact/?utm_source=TatvicEE&utm_medium=Dashboard&utm_campaign=WPlisting" target="_blank">Support</a></li>
22
  <li style="padding-bottom:5px;"><a href="https://www.tatvic.com/privacy-policy/?ref=plugin_policy&utm_source=plugin_backend&utm_medium=woo_free_plugin&utm_campaign=GDPR_complaince_ecomm_plugins" target="_blank">Privacy Policy</a></li>
26
  </div>
27
  <div class="card" style="padding: 0px;">
28
  <div class="card-header">
29
+ <h5>Rate Us!</h5>
30
  </div>
31
  <div class="card-body">
32
+ <ul>
33
  <li style="padding-bottom:5px;">Do you Like our Plugin? Please Spare few minutes to give <h3><a href = "https://wordpress.org/support/plugin/enhanced-e-commerce-for-woocommerce-store/reviews/" target="_blank" style="float: right">
34
  <div class="rating">
35
  <span>☆</span><span>☆</span><span>☆</span><span>☆</span><span>☆</span>
56
  </ul>
57
  </div>
58
  </div>
59
+ </div>
60
  </div>
enhanced-ecommerce-google-analytics.php CHANGED
@@ -15,8 +15,8 @@
15
  * @wordpress-plugin
16
  * Plugin Name: Enhanced E-commerce for Woocommerce store
17
  * Plugin URI: https://www.tatvic.com/tatvic-labs/woocommerce-extension/
18
- * Description: Automates Enhanced Ecommerce tracking in Google Analytics using gtag.js.
19
- * Version: 2.3.6.1
20
  * Author: Tatvic
21
  * Author URI: www.tatvic.com
22
  * License: GPL-2.0+
@@ -24,7 +24,7 @@
24
  * Text Domain: www.tatvic.com
25
  * Domain Path: /languages
26
  * WC requires at least: 1.4.1
27
- * WC tested up to: 4.6.1
28
  */
29
 
30
  /**
@@ -33,17 +33,84 @@
33
  if ( ! defined( 'WPINC' ) ) {
34
  die;
35
  }
36
- // Store the directory of the plugin
37
- if ( ! defined( 'ENHANCAD_PLUGIN_DIR' ) ) {
38
- define( 'ENHANCAD_PLUGIN_DIR', plugin_dir_path( __FILE__ ) );
39
- }
40
-
41
  /**
42
  * Currently plugin version.
43
  * Start at version 1.0.0 and use SemVer - https://semver.org
44
  * Rename this for your plugin and update it as you release new versions.
45
  */
46
- define( 'PLUGIN_NAME_VERSION', '2.3.6.1' );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
47
  /**
48
  * The code that runs during plugin activation.
49
  * This action is documented in includes/class-enhanced-ecommerce-google-analytics-activator.php
15
  * @wordpress-plugin
16
  * Plugin Name: Enhanced E-commerce for Woocommerce store
17
  * Plugin URI: https://www.tatvic.com/tatvic-labs/woocommerce-extension/
18
+ * Description: Automates eCommerce tracking in Google Analytics, dynamic remarkting in Google Ads, and provides complete Google Shopping features.
19
+ * Version: 3.0.1
20
  * Author: Tatvic
21
  * Author URI: www.tatvic.com
22
  * License: GPL-2.0+
24
  * Text Domain: www.tatvic.com
25
  * Domain Path: /languages
26
  * WC requires at least: 1.4.1
27
+ * WC tested up to: 5.0.0
28
  */
29
 
30
  /**
33
  if ( ! defined( 'WPINC' ) ) {
34
  die;
35
  }
 
 
 
 
 
36
  /**
37
  * Currently plugin version.
38
  * Start at version 1.0.0 and use SemVer - https://semver.org
39
  * Rename this for your plugin and update it as you release new versions.
40
  */
41
+ define( 'PLUGIN_NAME_VERSION', '3.0.1' );
42
+ $fullName = plugin_basename( __FILE__ );
43
+ $dir = str_replace('/enhanced-ecommerce-google-analytics.php','',$fullName);
44
+ if ( ! defined( 'ENHANCAD_PLUGIN_NAME' ) ) {
45
+ define( 'ENHANCAD_PLUGIN_NAME', $dir);
46
+ }
47
+ // Store the directory of the plugin
48
+ if ( ! defined( 'ENHANCAD_PLUGIN_DIR' ) ) {
49
+ define( 'ENHANCAD_PLUGIN_DIR', plugin_dir_path( __FILE__ ) );
50
+ }
51
+ // Store the url of the plugin
52
+ if ( ! defined( 'ENHANCAD_PLUGIN_URL' ) ) {
53
+ define( 'ENHANCAD_PLUGIN_URL', plugins_url() . '/' . ENHANCAD_PLUGIN_NAME );
54
+ }
55
+ // Store the transient alive time
56
+ if ( ! defined( 'TVC_TRANSIENT_LIVE' ) ) {
57
+ define( 'TVC_TRANSIENT_LIVE', 20 * MINUTE_IN_SECONDS );
58
+ }
59
+ // Store the base uploads folder, should also work in a multi site environment
60
+ if ( ! defined( 'TVC_UPLOADS_DIR' ) ) {
61
+ $wp_upload_dir = wp_get_upload_dir(); // @since 2.10.0 switched from wp_upload_dir to wp_get_upload_dir.
62
+ $upload_dir = is_multisite() && defined( 'UPLOADS' ) ? UPLOADS : $wp_upload_dir['basedir'];
63
+ if ( ! file_exists( $upload_dir ) && ! is_dir( $upload_dir ) ) {
64
+ define( 'TVC_UPLOADS_DIR', $wp_upload_dir['basedir'] );
65
+ } else {
66
+ define( 'TVC_UPLOADS_DIR', $upload_dir );
67
+ }
68
+ }
69
+
70
+ if ( ! defined( 'TVC_UPLOADS_URL' ) ) {
71
+ $wp_upload_dir = wp_upload_dir();
72
+ // correct baseurl for https if required
73
+ if ( is_ssl() ) {
74
+ $url = str_replace( 'http://', 'https://', $wp_upload_dir['baseurl'] );
75
+ } else {
76
+ $url = $wp_upload_dir['baseurl'];
77
+ }
78
+ define( 'TVC_UPLOADS_URL', apply_filters( 'tvc_corrected_uploads_url', $url ) );
79
+ }
80
+ // store the folder that contains the channels data
81
+ if ( ! defined( 'TVC_CHANNEL_DATA_DIR' ) ) {
82
+ define( 'TVC_CHANNEL_DATA_DIR', ENHANCAD_PLUGIN_DIR . 'includes/application' );
83
+ }
84
+ // store the folder that contains the backup files
85
+ if ( ! defined( 'TVC_BACKUP_DIR' ) ) {
86
+ define( 'TVC_BACKUP_DIR', TVC_UPLOADS_DIR . '/tvc-backups' );
87
+ }
88
+ // store the folder that contains the feeds
89
+ if ( ! defined( 'TVC_FEEDS_DIR' ) ) {
90
+ define( 'TVC_FEEDS_DIR', TVC_UPLOADS_DIR . '/tvc-feeds' );
91
+ }
92
+ // Store the plugin constructor
93
+ if ( ! defined( 'TVC_PLUGIN_CONSTRUCTOR' ) ) {
94
+ define( 'TVC_PLUGIN_CONSTRUCTOR', plugin_basename( __FILE__ ) );
95
+ }
96
+ // Store the plugin title
97
+ if ( ! defined( 'TVC_EDD_SL_ITEM_NAME' ) ) {
98
+ define( 'TVC_EDD_SL_ITEM_NAME', 'Tatvic Product Feed Manager' );
99
+ }
100
+ // Store the plugin title
101
+ if ( ! defined( 'TVC_MIN_REQUIRED_WC_VERSION' ) ) {
102
+ define( 'TVC_MIN_REQUIRED_WC_VERSION', '3.0.0' );
103
+ }
104
+ if ( ! defined( 'TVC_API_CALL_URL' ) ) {
105
+ define( 'TVC_API_CALL_URL', 'https://connect.tatvic.com/laravelapi/public/api' );
106
+ }
107
+ if ( ! defined( 'TVC_AUTH_CONNECT_URL' ) ) {
108
+ define( 'TVC_AUTH_CONNECT_URL', 'estorenew.tatvic.com' );
109
+ }
110
+ if(!defined('TVC_Admin_Helper')){
111
+ include(ENHANCAD_PLUGIN_DIR . '/admin/class-tvc-admin-helper.php');
112
+ }
113
+
114
  /**
115
  * The code that runs during plugin activation.
116
  * This action is documented in includes/class-enhanced-ecommerce-google-analytics-activator.php
includes/application/class-feed-master.php DELETED
@@ -1,676 +0,0 @@
1
- <?php
2
-
3
- /**
4
- *
5
- * Defines the plugin name, version, and two examples hooks for how to
6
- * enqueue the admin-specific stylesheet and JavaScript.
7
- *
8
- * @package Google Product Feed Manager
9
- * @subpackage Google Product Feed Manager/Application/Classes
10
- * @author Chetan Rode <chetan@tatvic.com>
11
- */
12
- if ( ! defined( 'ABSPATH' ) ) {
13
- exit;
14
- }
15
-
16
- if ( ! class_exists( 'TVC_Feed_Master_Class' ) ) :
17
-
18
- /**
19
- * Feed Master Class
20
- *
21
- * @since 2.0.0
22
- */
23
- class TVC_Feed_Master_Class {
24
-
25
- use TVC_Processing_Support;
26
-
27
- /**
28
- * Contains the general feed data
29
- *
30
- * @var object
31
- */
32
- protected $_feed = null;
33
-
34
- /**
35
- * Contains the feed is
36
- *
37
- * @var string
38
- */
39
- protected $_feed_id;
40
-
41
- /**
42
- * Instantiation of global background process class
43
- *
44
- * @var stdClass
45
- */
46
- protected $_background_process;
47
-
48
- /**
49
- * Placeholder for the correct channel class
50
- *
51
- * @var stdClass
52
- */
53
- protected $_channel_class;
54
-
55
- /**
56
- * Placeholder for the TVC_Data_Class
57
- *
58
- * @var stdClass
59
- */
60
- protected $_data_class;
61
-
62
- /**
63
- * Path and name of the feed file
64
- *
65
- * @var string
66
- */
67
- protected $_feed_file_path;
68
-
69
- /**
70
- * Initiate new Feed Master class.
71
- *
72
- * @param string $feed_id The id of the feed. Default 0
73
- *
74
- * @global stdClass $background_process
75
- *
76
- */
77
- public function __construct( $feed_id = '0' ) {
78
- $query_class = new TVC_Queries();
79
-
80
- /**
81
- * when this construct is called from a channel class, it will not specify the feed_id so the default 0 is used
82
- * in that case the feed_type_id will always be 1
83
- */
84
-
85
- $feed_type_id = $feed_id > 0 ? $query_class->get_feed_type_id( $feed_id ) : '1';
86
-
87
- $background_class = apply_filters( 'tvc_background_class', 'TVC_Feed_Processor', $feed_type_id );
88
-
89
- $this->_background_process = new $background_class();
90
- $this->_data_class = new TVC_Data();
91
- }
92
-
93
- /**
94
- * The update feed file function that starts the update process
95
- *
96
- * @param bool $silent (default true)
97
- *
98
- * @return string|void or false
99
- */
100
- public function update_feed_file( $silent = true ) {
101
-
102
- $feed_id = TVC_Feed_Controller::get_next_id_from_feed_queue();
103
-
104
- do_action( 'tvc_feed_process_prepared', $feed_id, $silent );
105
-
106
- if ( false === $feed_id ) {
107
- return false;
108
- }
109
-
110
- if ( $silent ) {
111
- set_transient( 'tvc_running_silent', true, TVC_TRANSIENT_LIVE );
112
- }
113
-
114
- $feed_data = $this->_data_class->get_feed_data( $feed_id );
115
-
116
- if ( ! $feed_data ) {
117
- do_action( 'tvc_feed_generation_message', $feed_id, 'The update_feed_file function failed to get the feed data', 'ERROR' );
118
- if ( ! $silent ) {
119
- _e( '1428 - Failed to load the feed data, please to generate a feed in the foreground mode (see Settings page) and then try the background mode again.', 'tvc-product-feed-manager' );
120
- }
121
-
122
- return false;
123
- }
124
-
125
- /**
126
- * store the feed data in a property
127
- */
128
- $this->_feed = $feed_data;
129
-
130
- /**
131
- * only one feed can be processing so if other feeds than the current feed are on a processing
132
- * status, set these to an error status
133
- */
134
- $this->_data_class->check_for_failed_feeds( $this->_feed->feedId );
135
-
136
- $prepare_update = $this->prepare_feed_file_update( $silent );
137
-
138
- if ( true !== $prepare_update ) {
139
- if ( ! $silent ) {
140
- echo $prepare_update;
141
- }
142
-
143
- return false;
144
- }
145
-
146
- TVC_Feed_Controller::set_feed_processing_flag( true );
147
-
148
- $this->prepare_background_process();
149
-
150
- $this->fill_the_background_queue();
151
-
152
- $this->activate_feed_file_update( $this->_feed->feedId );
153
-
154
- delete_transient( 'tvc_running_silent' );
155
-
156
- if ( ! $silent ) {
157
- echo 'started_processing';
158
- }
159
- }
160
-
161
- public function feed_status_check( $feed_id ) {
162
- $queries_class = new TVC_Queries();
163
-
164
- $current_feed_status = $queries_class->get_feed_status_data( $feed_id );
165
-
166
- $current_feed_status['feed_type_name'] = tvc_list_feed_type_text()[ $current_feed_status['feed_type_id'] ];
167
-
168
- if ( '3' === $current_feed_status['status_id'] ) { // status still processing
169
- // get file name, including path
170
- $file_extension = function_exists( 'get_file_type' ) ? get_file_type( $current_feed_status['channel_id'] ) : 'xml';
171
- $feed_file = tvc_get_file_path( $current_feed_status['title'] . '.' . $file_extension );
172
-
173
- // if it is, set the feed status to fail and change the $current_feed_status['status_id'] to 6
174
- if ( TVC_Feed_Controller::feed_processing_failed( $feed_file ) ) {
175
- // change the status of the feed to failed processing
176
- $this->_data_class->update_feed_status( $feed_id, 6 ); // feed status to failed
177
-
178
- // update the current_feed_status variable before returning
179
- $current_feed_status['status_id'] = '6';
180
-
181
- // clear this feed from the feed queue
182
- TVC_Feed_Controller::remove_id_from_feed_queue( $feed_id );
183
- TVC_Feed_Controller::set_feed_processing_flag( false );
184
-
185
- // if running silent (automatic feed update) inform the user about the failed feed
186
- if ( get_transient( 'tvc_running_silent' ) ) {
187
- TVC_Email::send_feed_failed_message();
188
- }
189
-
190
- if ( ! TVC_Feed_Controller::feed_queue_is_empty() ) {
191
- $next_feed_id = TVC_Feed_Controller::get_next_id_from_feed_queue();
192
-
193
- if ( $next_feed_id ) {
194
- // so there is another feed in the queue
195
- $feed_master_class = new TVC_Feed_Master_Class( $next_feed_id );
196
- $feed_master_class->update_feed_file();
197
- }
198
- }
199
-
200
- do_action( 'tvc_feed_processing_failed_file_size_stopped_increasing', $feed_id, TVC_Feed_Controller::nr_ids_remaining_in_queue() );
201
- do_action( 'tvc_register_feed_url', $feed_id, $feed_file );
202
- }
203
-
204
- return $current_feed_status;
205
- } else {
206
- return $current_feed_status;
207
- }
208
- }
209
-
210
- /**
211
- * Perform all preparations for the feed update starts
212
- *
213
- * @param bool $silent (default true)
214
- *
215
- * @return bool true if feed file has been updated successfully
216
- */
217
- private function prepare_feed_file_update( $silent ) {
218
- // prepare the folder structure to support saving feed files
219
- if ( ! file_exists( TVC_FEEDS_DIR ) ) {
220
- TVC_Folders::make_feed_support_folder();
221
- }
222
-
223
- if ( ! is_writable( TVC_FEEDS_DIR ) ) {
224
- /* translators: %s: Folder where the feeds are stored */
225
- return sprintf( esc_html__( '1430 - %s is not a writable folder. Make sure you have admin rights to this folder.', 'tvc-product-feed-manager' ), TVC_FEEDS_DIR );
226
- }
227
-
228
- $initial_feed_status = $this->_feed->status;
229
-
230
- if ( ! $this->set_properties() ) {
231
- $message = sprintf( 'Failed to set the properties of feed %s.', $this->_feed->feedId );
232
- do_action( 'tvc_feed_generation_message', $this->_feed->feedId, $message, 'ERROR' );
233
-
234
- return false;
235
- }
236
-
237
- $this->_data_class->set_nr_of_feed_products( $this->_feed->feedId, '0' ); // 0 products
238
- $this->_data_class->update_feed_status( $this->_feed->feedId, 3 ); // set status to "Processing"
239
-
240
- $file_extension = function_exists( 'get_file_type' ) ? get_file_type( $this->_feed->channel ) : 'xml';
241
-
242
- $this->_feed_file_path = tvc_get_file_path( $this->_feed->title . '.' . $file_extension );
243
-
244
- // clear the existing feed
245
- file_put_contents( $this->_feed_file_path, '' );
246
-
247
- // clear the file size checker
248
- delete_transient( 'tvc_feed_file_size' );
249
-
250
- // clear the list of processed products @since 2.10.0.
251
- delete_option( 'tvc_processed_products' );
252
-
253
- $channel_class = new TVC_Channel();
254
- $channel_name = $channel_class->get_channel_short_name( $this->_feed->channel );
255
-
256
- $logger_message = sprintf( 'Feed %s is a %s feed stored as %s, with an original feed status %s.', $this->_feed->feedId, $channel_name, $this->_feed_file_path, $initial_feed_status );
257
- do_action( 'tvc_feed_generation_message', $this->_feed->feedId, $logger_message );
258
-
259
- return true;
260
- }
261
-
262
- /**
263
- * Store common product metadata in the Background Process properties
264
- */
265
- private function prepare_background_process() {
266
- // start counting from zero
267
- delete_option( 'tvc_processed_products' );
268
-
269
- $this->_background_process->set_feed_data( $this->_feed );
270
- $this->_background_process->set_file_path( $this->_feed_file_path );
271
- $this->_background_process->set_pre_data( $this->get_required_pre_data() );
272
- $this->_background_process->set_channel_details( $this->get_channel_details() );
273
- $this->_background_process->set_relations_table( $this->get_channel_to_woocommerce_field_relations() );
274
- }
275
-
276
- /**
277
- * Fills the background queue
278
- */
279
- private function fill_the_background_queue() {
280
- // start with an empty queue
281
- $this->_background_process->clear_the_queue();
282
- $sw_status_control = 30000 * 3.3;
283
- $product_counter = 0;
284
-
285
- // add the header to the queue
286
- $header_string = $this->get_feed_header();
287
- $this->_background_process->push_to_queue( array( 'file_format_line' => $header_string ) );
288
-
289
- do {
290
- $product_ids = $this->get_product_ids_for_feed();
291
-
292
- // add the product ids to the queue
293
- foreach ( $product_ids as $product_id ) {
294
- $this->_background_process->push_to_queue( $product_id );
295
-
296
- $product_counter++;
297
-
298
- if ( $product_counter > $sw_status_control ) { // HWOTBERH
299
- break;
300
- }
301
- }
302
- } while ( ! empty( $product_ids ) && $sw_status_control > $product_counter );
303
-
304
- delete_transient( 'tvc_start_product_id' );
305
-
306
- // implement the tvc_feed_ids_in_queue filter on the queue.
307
- $this->_background_process->apply_filter_to_queue( $this->_feed->feedId );
308
-
309
- do_action( 'tvc_feed_queue_filled', $this->_feed->feedId, $product_counter );
310
-
311
- $product_ids = null;
312
-
313
- $file_extension = function_exists( 'get_file_type' ) ? get_file_type( $this->_feed->channel ) : 'xml';
314
-
315
- // add the xml footer to the queue
316
- if ( 'xml' === $file_extension ) {
317
- $this->_background_process->push_to_queue(
318
- array(
319
- 'file_format_line' => apply_filters(
320
- 'tvc_footer_string',
321
- $this->_channel_class->footer(),
322
- $this->_feed->feedId,
323
- $this->_feed->feedTypeId
324
- ),
325
- )
326
- );
327
- }
328
- }
329
-
330
- /**
331
- * Start the feed update process in the background
332
- *
333
- * @param string $feed_id
334
- */
335
- private function activate_feed_file_update( $feed_id ) {
336
- // save the queue data and then run the tvc-background-process dispatch function
337
- $this->_background_process->save( $this->_feed->feedId )->dispatch( $feed_id );
338
- }
339
-
340
- /**
341
- * Set all class properties
342
- *
343
- * @return bool
344
- */
345
- private function set_properties() {
346
- // some channels do not use channels and leave the main category empty which causes issues
347
- if ( function_exists( 'channel_uses_category' ) && ! channel_uses_category( $this->_feed->channel ) ) {
348
- $this->_feed->mainCategory = 'No Category Required';
349
- }
350
-
351
- // some channels only accept category id numbers, for these channels retrieve the category numbers
352
- if ( stripos( strrev( $this->_feed->mainCategory ), ')' ) === 0 ) {
353
- $start = stripos( $this->_feed->mainCategory, '(' ) + 1;
354
- $end = stripos( $this->_feed->mainCategory, '(' ) - $start;
355
- $this->_feed->mainCategory = substr( $this->_feed->mainCategory, $start, $end );
356
- }
357
-
358
- // instantiate the correct channel class
359
- $this->_channel_class = new TVC_Google_Feed_Class();
360
- return true;
361
- }
362
-
363
- /**
364
- * Returns the header that is correct for the selected feed type
365
- *
366
- * @return string
367
- */
368
- private function get_feed_header() {
369
- $header_string = '';
370
-
371
- if ( $this->_feed->channel ) {
372
- $file_extension = function_exists( 'get_file_type' ) ? get_file_type( $this->_feed->channel ) : 'xml';
373
- if ( '1' === $this->_feed->channel && ! empty( $this->_feed->feedTitle ) ) {
374
- $header_string = $this->_channel_class->header( $this->_feed->feedTitle, $this->_feed->feedDescription );
375
- } elseif ( 'xml' === $file_extension ) {
376
- $header_string = $this->_channel_class->header( $this->_feed->title );
377
- } elseif ( 'txt' === $file_extension ) {
378
- $header_string = $this->make_tab_delimited_string_from_data_array( $this->get_active_fields() );
379
- } elseif ( 'csv' === $file_extension ) {
380
- $csv_sep = apply_filters( 'tvc_csv_separator', get_correct_csv_header_separator( $this->_feed->channel ) );
381
- $string = $this->make_csv_header_string( $this->get_active_fields(), $csv_sep );
382
- $header_string = $this->_channel_class->header( $string );
383
- }
384
- }
385
-
386
- return apply_filters( 'tvc_header_string', $header_string, $this->_feed->feedId, $this->_feed->feedTypeId );
387
- }
388
-
389
- /**
390
- * ALERT! has a javascript equivalent in channel-functions.js called setAttributeStatus();
391
- */
392
-
393
- /**
394
- * sets the activity status of a specific attribute to true or false depending on its level
395
- *
396
- * @param int $field_level
397
- * @param string $field_value
398
- *
399
- * @return boolean
400
- */
401
- protected function set_attribute_status( $field_level, $field_value ) {
402
- if ( $field_level > 0 && $field_level < 3 ) {
403
- return true;
404
- }
405
- $clean_field_value = trim( $field_value );
406
- if ( ! empty( $clean_field_value ) ) {
407
- return true;
408
- }
409
-
410
- return false;
411
- }
412
-
413
- /**
414
- * Produces an array with the ids of all products that should be added into the feed
415
- *
416
- * @return array with ids
417
- */
418
- private function get_product_ids_for_feed() {
419
- $queries_class = new TVC_Queries();
420
-
421
- $selected_categories = apply_filters( 'tvc_selected_categories', $this->make_category_selection_string(), $this->_feed->feedId );
422
-
423
- $include_variations = '1' === $this->_feed->includeVariations ? true : false;
424
-
425
- $products = $queries_class->get_post_ids( $selected_categories, $include_variations );
426
-
427
- array_filter( $products ); // just to make sure, remove all empty elements
428
-
429
- return $products;
430
- }
431
-
432
- /**
433
- * Returns a comma separated string with selected category numbers to be used as part of a query
434
- *
435
- * @return string
436
- */
437
- private function make_category_selection_string() {
438
- $category_selection_string = '';
439
- $category_mapping = json_decode( $this->_feed->categoryMapping );
440
-
441
- if ( ! empty( $category_mapping ) ) {
442
- foreach ( $category_mapping as $category ) {
443
- $category_selection_string .= $category->shopCategoryId . ', '; // phpcs:ignore
444
- }
445
- }
446
-
447
- return $category_selection_string ? substr( $category_selection_string, 0, - 2 ) : '';
448
- }
449
-
450
- /**
451
- * Get all general data required to make a feed
452
- *
453
- * @return array
454
- */
455
- private function get_required_pre_data() {
456
- // get the feed query string if the user has added to filter out specific products from the feed (Paid version only)
457
- $feed_filter = $this->_data_class->get_filter_query( $this->_feed->feedId );
458
-
459
- // should the feed include product variations?
460
- $include_variations = '1' === $this->_feed->includeVariations ? true : false;
461
-
462
- // get an array with all the field names that are required to make the feed (including the source fields, fields for the queries and fields for static data)
463
- $required_column_names = $this->get_column_names_required_for_feed( $feed_filter );
464
-
465
- // get the fields that are active and have to go into the feed
466
- $active_fields = $this->get_active_fields();
467
-
468
- $database_fields = $this->get_database_fields( $required_column_names );
469
-
470
- return array(
471
- 'filters' => $feed_filter,
472
- 'include_vars' => $include_variations,
473
- 'column_names' => $required_column_names,
474
- 'active_fields' => $active_fields,
475
- 'database_fields' => $database_fields,
476
- );
477
- }
478
-
479
- /**
480
- * Get category name and description name from the active channel
481
- *
482
- * @return array
483
- */
484
- private function get_channel_details() {
485
- return function_exists( 'channel_file_text_data' ) ? channel_file_text_data( $this->_feed->channel ) :
486
- array(
487
- 'channel_id' => $this->_feed->channel,
488
- 'category_name' => 'google_product_category',
489
- 'description_name' => 'description',
490
- );
491
- }
492
-
493
- /**
494
- * returns the column names from the database that are required to get the data necessary to make the feed
495
- *
496
- * @param object $feed_filter_object
497
- *
498
- * @return array
499
- */
500
- private function get_column_names_required_for_feed( $feed_filter_object ) {
501
- $support_class = new TVC_Feed_Support();
502
-
503
- $fields = array();
504
- $filter_columns = $support_class->get_column_names_from_feed_filter_array( $feed_filter_object );
505
-
506
- foreach ( $this->_feed->attributes as $attribute ) {
507
- if ( 'category_mapping' !== $attribute->fieldName ) {
508
- $column_names = $this->get_db_column_name_from_attribute( $attribute );
509
- foreach ( $column_names as $name ) {
510
- if ( ! empty( $name ) ) {
511
- array_push( $fields, $name );
512
- }
513
- }
514
- }
515
- }
516
-
517
- $result = array_unique( array_merge( $fields, $filter_columns ) ); // remove doubles
518
-
519
- if ( empty( $result ) ) {
520
- tvc_write_log_file( 'Function get_column_names_required_for_feed returned zero columns' );
521
- }
522
-
523
- return array_merge( $result ); // and resort the result before returning
524
- }
525
-
526
- /**
527
- * returns all active column names that are stored in the feed attributes
528
- *
529
- * @param array $attribute
530
- *
531
- * @return array
532
- */
533
- public function get_db_column_name_from_attribute( $attribute ) {
534
- $column_names = array();
535
-
536
- if ( property_exists( $attribute, 'isActive' ) && $attribute->isActive ) { // only select the active attributes
537
- // source columns
538
- if ( ! empty( $attribute->value ) ) {
539
- $source_columns = $this->get_source_columns_from_attribute_value( $attribute->value );
540
- $condition_columns = $this->get_condition_columns_from_attribute_value( $attribute->value );
541
- $query_columns = $this->get_queries_columns_from_attribute_value( $attribute->value );
542
-
543
- // TODO: I think the first $column_names array can be removed from the array_merge
544
- $column_names = array_merge( $column_names, $source_columns, $condition_columns, $query_columns );
545
- }
546
-
547
- // advised sources
548
- if ( ! empty( $attribute->advisedSource )
549
- && strpos( $attribute->advisedSource, esc_html__( 'Fill with a static value', 'tvc-product-feed-manager' ) ) === false
550
- && strpos( $attribute->advisedSource, esc_html__( 'Use the settings in the Merchant Center', 'tvc-product-feed-manager' ) ) === false ) {
551
-
552
- // add the relevant advised sources
553
- array_push( $column_names, $attribute->advisedSource );
554
- } elseif ( property_exists( $attribute, 'advisedSource' )
555
- && strpos( $attribute->advisedSource, esc_html__( 'Use the settings in the Merchant Center', 'tvc-product-feed-manager' ) ) !== false ) {
556
-
557
- array_push( $column_names, 'woo_shipping' );
558
- }
559
- }
560
- return $column_names;
561
- }
562
-
563
- /**
564
- * extract the active fields from the attributes
565
- *
566
- * @return array
567
- */
568
- private function get_active_fields() {
569
- $active_fields = array();
570
-
571
- foreach ( $this->_feed->attributes as $attribute ) {
572
- if ( $attribute->isActive && 'category_mapping' !== $attribute->fieldName ) {
573
- $push = false;
574
-
575
- if ( '1' === $attribute->fieldLevel ) {
576
- $push = true;
577
- } else {
578
- $value_object = property_exists( $attribute, 'value' ) ? json_decode( $attribute->value ) : new stdClass();
579
-
580
- if ( ! empty( $attribute->value ) && property_exists( $value_object, 'm' ) && property_exists( $value_object->m[0], 's' ) ) {
581
- $push = true;
582
- } elseif ( ! empty( $attribute->advisedSource ) ) {
583
- $push = true;
584
- } elseif ( ! empty( $attribute->value ) && property_exists( $value_object, 't' ) ) {
585
- $push = true;
586
- } elseif ( ! empty( $attribute->value ) && property_exists( $value_object, 'v' ) ) {
587
- $push = true;
588
- }
589
- }
590
-
591
- if ( true === $push ) {
592
- array_push( $active_fields, $attribute->fieldName );
593
- }
594
- }
595
- }
596
-
597
- if ( empty( $active_fields ) ) {
598
- tvc_write_log_file( 'Function get_active_fields returned zero fields.' );
599
- }
600
-
601
- return $active_fields;
602
- }
603
-
604
- /**
605
- * gather all required column names from the database
606
- *
607
- * @param array $active_field_names
608
- *
609
- * @return array
610
- */
611
- private function get_database_fields( $active_field_names ) {
612
- $queries_class = new TVC_Queries();
613
-
614
- $post_fields = array();
615
- $meta_fields = array();
616
- $custom_fields = array();
617
- $active_custom_fields = array();
618
- $active_third_party_custom_fields = array();
619
- $post_columns_string = '';
620
-
621
- $columns_in_post_table = $queries_class->get_columns_from_post_table(); // get all post table column names
622
- $all_custom_columns = $queries_class->get_custom_product_attributes(); // get all custom name labels
623
- $third_party_custom_fields = $this->_data_class->get_third_party_custom_fields();
624
-
625
- // convert the query results to an array with only the name labels
626
- foreach ( $columns_in_post_table as $column ) {
627
- array_push( $post_fields, $column->Field );
628
- } // $post_fields containing the required names from the post table
629
- foreach ( $all_custom_columns as $custom ) {
630
- array_push( $custom_fields, $custom->attribute_name );
631
- }
632
- // $custom_fields containing the custom names
633
- // filter the post columns, the meta columns and the custom columns to only those that are actually in use
634
-
635
- foreach ( $active_field_names as $column ) {
636
- if ( in_array( $column, $post_fields ) && 'ID' !== $column ) { // because ID is always required, it's excluded here and hard coded in the query
637
- $post_columns_string .= $column . ', '; // here a string is required to push in the query
638
- } elseif ( in_array( $column, $custom_fields ) ) {
639
- array_push( $active_custom_fields, $column );
640
- } elseif ( in_array( $column, $third_party_custom_fields ) ) {
641
- array_push( $active_third_party_custom_fields, $column );
642
- } else {
643
- array_push( $meta_fields, $column );
644
- }
645
- }
646
-
647
- return array(
648
- 'post_column_string' => $post_columns_string,
649
- 'meta_fields' => $meta_fields,
650
- 'active_custom_fields' => $active_custom_fields,
651
- 'third_party_custom_fields' => $third_party_custom_fields,
652
- );
653
- }
654
-
655
- /**
656
- * header text, override this function in the class-feed.php if required for a channel specific header
657
- *
658
- * @param string $title
659
- *
660
- * @return string
661
- */
662
- protected function header( $title ) {
663
- return apply_filters( 'tvc_xml_header', $title );
664
- }
665
-
666
- /**
667
- * footer text, override if required for a channel specific footer
668
- *
669
- * @return string
670
- */
671
- protected function footer() {
672
- return apply_filters( 'tvc_xml_footer', '</products></rss>' );
673
- }
674
- }
675
- // end of TVC_Feed_Master_Class
676
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/class-tvc-email.php DELETED
@@ -1,68 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Email Class.
5
- *
6
- * @package Google Product Feed Manager/Application/Classes
7
- * @version 1.2.0
8
- * @since 2.3.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_Email' ) ) :
16
-
17
- /**
18
- * Email Class
19
- */
20
- class TVC_Email {
21
-
22
- public static function send_feed_failed_message() {
23
- $to = get_option( 'tvc_notice_mailaddress' ) ? get_option( 'tvc_notice_mailaddress' ) : get_bloginfo( 'admin_email' );
24
-
25
- if ( ! $to ) {
26
- return false;
27
- }
28
- $header = self::feed_failed_header();
29
- $message = self::feed_failed_message();
30
-
31
- return self::send( $to, $header, $message );
32
- }
33
-
34
- private static function feed_failed_header() {
35
- return sprintf( 'Feed generation failure on your %s shop', get_bloginfo( 'name' ) );
36
- }
37
-
38
- private static function feed_failed_message() {
39
- $message = sprintf(
40
- 'This is an automatic message from your %s plugin. One or more product feeds on your %s shop failed to generate. Please check the status of your feeds and try to manually regenerate them again.
41
-
42
- Should this problem persist, please open a support ticket.',
43
- TVC_EDD_SL_ITEM_NAME,
44
- get_bloginfo( 'name' )
45
- );
46
-
47
- return $message;
48
- }
49
-
50
- /**
51
- * Sends the email
52
- *
53
- * @param string $to to address
54
- * @param string $subject the subject
55
- * @param string $message the message
56
- *
57
- * @return bool whether the mail contents was send successfully
58
- */
59
- private static function send( $to, $subject, $message ) {
60
- if ( is_email( $to ) ) {
61
- return (bool) wp_mail( $to, $subject, $message );
62
- } else {
63
- return false;
64
- }
65
- }
66
- }
67
- // end of TVC_Email class
68
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/class-tvc-feed-processor.php DELETED
@@ -1,341 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * Google Product Feed Controller Class.
5
- *
6
- * @package Google Product Feed Manager/Application/Classes
7
- * @version 1.5.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Feed_Processor' ) ) :
15
-
16
-
17
- /**
18
- * Feed Processor Class
19
- *
20
- * @since 1.10.0
21
- */
22
- class TVC_Feed_Processor extends TVC_Background_Process {
23
-
24
- use TVC_Processing_Support;
25
- use TVC_Feed_Processor_Functions;
26
-
27
- /**
28
- * Action identifier
29
- *
30
- * @var string
31
- */
32
- protected $action = 'feed_generation_process';
33
-
34
- /**
35
- * Path to the feed file
36
- *
37
- * @var string
38
- */
39
- private $_feed_file_path;
40
-
41
- /**
42
- * General feed data
43
- *
44
- * @var stdClass
45
- */
46
- private $_feed_data;
47
-
48
- /**
49
- * Required pre feed generation data
50
- *
51
- * @var array
52
- */
53
- private $_pre_data;
54
-
55
- /**
56
- * Contains the channel specific main category title and description title
57
- *
58
- * @var array
59
- */
60
- private $_channel_details;
61
-
62
- /**
63
- * Contains the relations between WooCommerce and channel fields
64
- *
65
- * @var array
66
- */
67
- private $_relation_table;
68
-
69
- /**
70
- * Placeholder for the correct channel class
71
- *
72
- * @var string
73
- */
74
- private $_channel_class;
75
-
76
- /**
77
- * Task
78
- *
79
- * Starts a single feed update task
80
- *
81
- * @param array product
82
- * @param stdClass feed_data
83
- * @param string feed_file_path
84
- * @param array pre_data
85
- * @param array channel_details
86
- * @param array relation_table
87
- *
88
- * @return boolean
89
- */
90
- protected function task( $task_data, $feed_data, $feed_file_path, $pre_data, $channel_details, $relation_table ) {
91
- if ( ! $task_data ) {
92
- return false;
93
- }
94
-
95
- $this->_feed_data = $feed_data;
96
- $this->_feed_file_path = $feed_file_path;
97
- $this->_pre_data = $pre_data;
98
- $this->_channel_details = $channel_details;
99
- $this->_relation_table = $relation_table;
100
-
101
- if ( ! $this->_channel_details['channel_id'] ) {
102
- return false;
103
- }
104
-
105
- // instantiate the correct channel class
106
- $this->_channel_class = new TVC_Google_Feed_Class();
107
-
108
- return $this->do_task( $task_data );
109
- }
110
-
111
- /**
112
- * Complete
113
- */
114
- public function complete() {
115
- parent::complete();
116
-
117
- // remove the properties from the options table
118
- $properties_key = get_site_option( 'tvc_background_process_key' );
119
- delete_site_option( 'tvc_background_process_key' );
120
- delete_site_option( 'file_path_' . $properties_key );
121
- delete_site_option( 'feed_data_' . $properties_key );
122
- delete_site_option( 'pre_data_' . $properties_key );
123
- delete_site_option( 'channel_details_' . $properties_key );
124
- delete_site_option( 'relations_table_' . $properties_key );
125
-
126
- $feed_status = '0' !== $this->_feed_data->status && '3' !== $this->_feed_data->status && '4' !== $this->_feed_data->status ? $this->_feed_data->status : $this->_feed_data->baseStatusId;
127
- $feed_title = $this->_feed_data->title . '.' . pathinfo( $this->_feed_file_path, PATHINFO_EXTENSION );
128
- $this->register_feed_update( $this->_feed_data->feedId, $feed_title, count( $this->processed_products ), $feed_status );
129
- $this->clear_the_queue();
130
-
131
- // now the feed is ready to go, remove the feed id from the feed queue
132
- TVC_Feed_Controller::remove_id_from_feed_queue( $this->_feed_data->feedId );
133
- TVC_Feed_Controller::set_feed_processing_flag( false );
134
-
135
- $message = sprintf( 'Completed feed %s. The feed should contain %d products and its status has been set to %s.', $this->_feed_data->feedId, count( $this->processed_products ), $feed_status );
136
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
137
- do_action( 'tvc_register_feed_url', $this->_feed_data->feedId, $this->_feed_data->url );
138
-
139
- if ( ! TVC_Feed_Controller::feed_queue_is_empty() ) {
140
- do_action( 'tvc_next_in_queue_feed_update_activated', $this->_feed_data->feedId );
141
-
142
- // so there is another feed in the queue
143
- $feed_master_class = new TVC_Feed_Master_Class( $this->_feed_data->feedId );
144
- $feed_master_class->update_feed_file();
145
- }
146
- }
147
-
148
- /**
149
- * Task action
150
- * Selects the required action
151
- *
152
- * @param array $task_data
153
- *
154
- * @return boolean
155
- */
156
- private function do_task( $task_data ) {
157
-
158
- if ( array_key_exists( 'product_id', $task_data ) ) {
159
- return $this->add_product_to_feed( $task_data['product_id'] );
160
- } elseif ( array_key_exists( 'file_format_line', $task_data ) ) {
161
- $task_data['file_format_line'] = str_replace( '<wf-connection-string>', '<link>', $task_data['file_format_line'] );
162
-
163
- return $this->add_file_format_line_to_feed( $task_data );
164
- } elseif ( array_key_exists( 'error_message', $task_data ) ) {
165
- return $this->add_error_message_to_feed( $task_data );
166
- } else {
167
- return false;
168
- }
169
- }
170
-
171
- /**
172
- * Ads a single product based on a product id to the feed file
173
- *
174
- * @param string $product_id
175
- *
176
- * @return boolean
177
- */
178
- private function add_product_to_feed( $product_id ) {
179
- if ( ! $product_id ) {
180
- $message = 'Add product to feed process started without product id';
181
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
182
-
183
- return false;
184
- }
185
-
186
- $wc_product = wc_get_product( $product_id );
187
-
188
- if ( false === $wc_product ) {
189
- $message = sprintf( 'Failed to get the WooCommerce product data from product with id %s.', $product_id );
190
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
191
-
192
- return false;
193
- }
194
-
195
- do_action( 'tvc_started_product_processing', $this->_feed_data->feedId, $product_id );
196
-
197
- $class_data = new TVC_Data();
198
-
199
- $product_placeholder = array();
200
- $post_columns_query_string = $this->_pre_data['database_fields']['post_column_string'] ? substr( $this->_pre_data['database_fields']['post_column_string'], 0, - 2 ) : '';
201
- $product_parent_id = $product_id;
202
- $product_data = (array) $this->get_products_main_data( $product_id, $wc_product->get_parent_id(), $post_columns_query_string );
203
-
204
- /**
205
- * Users can use the tvc_leave_links_in_descriptions filter if they want to keep links in the product descriptions by changing the
206
- * filter output to true. They can also target specific feeds.
207
- *
208
- * @since 2.6.0
209
- */
210
- if ( ! apply_filters( 'tvc_leave_links_in_descriptions', false, $this->_feed_data->feedId ) ) {
211
- $this->remove_links_from_product_data_description( $product_data );
212
- }
213
-
214
- if ( ( $wc_product instanceof WC_Product_Variation && $this->_pre_data['include_vars'] )
215
- || ( $wc_product instanceof WC_Product_Variable ) && $this->_pre_data['include_vars'] ) {
216
-
217
- $product_parent_id = $wc_product->get_parent_id();
218
-
219
- // add parent data when this item is not available in the variation
220
- if ( $post_columns_query_string ) {
221
- $class_data->add_parent_data( $product_data, $product_parent_id, $post_columns_query_string );
222
- }
223
-
224
- $wpmr_variation_data = $class_data->get_own_variation_data( $product_id );
225
-
226
- // get correct variation data
227
- TVC_Variations::fill_product_data_with_variation_data( $product_data, $wc_product, $wpmr_variation_data, $this->_feed_data->language );
228
- }
229
-
230
- $row_category = $this->get_mapped_category( $product_parent_id, $this->_feed_data->mainCategory, json_decode( $this->_feed_data->categoryMapping ) );
231
-
232
- if ( ! $row_category ) {
233
- $message = sprintf( 'Could not identify the correct category map for product %s', $product_id );
234
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
235
-
236
- return false;
237
- }
238
-
239
- $row_filtered = $this->is_product_filtered( $this->_pre_data['filters'], $product_data );
240
-
241
- // only process the product if its not filtered out
242
- if ( ! $row_filtered ) {
243
- // for each row loop through each field
244
- foreach ( $this->_pre_data['active_fields'] as $field ) {
245
- $field_meta_data = $this->get_meta_data_from_specific_field( $field, $this->_feed_data->attributes );
246
-
247
- // get the field data based on the user settings
248
- $feed_object = $this->process_product_field(
249
- $product_data,
250
- $field_meta_data,
251
- $this->_channel_details['category_name'],
252
- $row_category,
253
- $this->_feed_data->language,
254
- $this->_relation_table
255
- );
256
-
257
- $key = key( $feed_object );
258
-
259
- // for an xml file only add fields that contain data
260
- if ( ( ! empty( $feed_object[ $key ] ) || '0' === $feed_object[ $key ] ) || 'xml' !== pathinfo( $this->_feed_file_path, PATHINFO_EXTENSION ) ) {
261
-
262
- // catch the DraftImages key for the Ricardo.ch channel
263
- if ( 'DraftImages' !== $key ) {
264
- $product_placeholder[ $key ] = $feed_object[ $key ];
265
- } else {
266
- $support_class = new TVC_Feed_Support();
267
- $support_class->process_ricardo_draftimages( $product_placeholder, $feed_object[ $key ] );
268
- }
269
- }
270
- }
271
- } else {
272
- $message = sprintf( 'Product %s is filtered out', $product_id );
273
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
274
-
275
- return 'filtered';
276
- }
277
-
278
- if ( $product_placeholder ) {
279
- // The tvc_feed_item_value filter allows users to modify the data that goes into the feed. The $data variable contains an array
280
- // with all the data that goes into the feed, with the items name as key
281
- $product_placeholder = apply_filters( 'tvc_feed_item_value', $product_placeholder, $this->_feed_data->feedId, $product_id );
282
-
283
- return $this->write_product_object( $product_placeholder, $this->_feed_data->feedId, $product_id );
284
- } else {
285
- return false;
286
- }
287
- }
288
-
289
- /**
290
- * Appends a product to the feed
291
- *
292
- * @param array $feed_product_object
293
- * @param string $feed_id
294
- * @param string $product_id
295
- *
296
- * @return string product added or boolean false
297
- */
298
- private function write_product_object( $feed_product_object, $feed_id, $product_id ) {
299
- /**
300
- * @since 2.3.0
301
- */
302
- do_action( 'tvc_add_product_to_feed', $feed_id, $product_id );
303
-
304
- $product_text = $this->generate_feed_text( $feed_product_object );
305
-
306
- if ( false === file_put_contents( $this->_feed_file_path, $product_text, FILE_APPEND ) ) {
307
- tvc_write_log_file( sprintf( 'Could not write product %s to the feed', $product_id ) );
308
-
309
- return false;
310
- } else {
311
- return 'product added';
312
- }
313
- }
314
-
315
- /**
316
- * convert the feed data of a single product into xml or csv text depending on the channel
317
- *
318
- * @param array $data
319
- *
320
- * @return string
321
- */
322
- protected function generate_feed_text( $data ) {
323
- switch ( pathinfo( $this->_feed_file_path, PATHINFO_EXTENSION ) ) {
324
- case 'xml':
325
- return $this->convert_data_to_xml( $data, $this->_channel_details['category_name'], $this->_channel_details['description_name'], $this->_channel_details['channel_id'] );
326
-
327
- case 'txt':
328
- return $this->convert_data_to_txt( $data );
329
-
330
- case 'csv':
331
- $csv_sep = apply_filters( 'tvc_csv_separator', get_correct_csv_separator( $this->_channel_details['channel_id'] ) );
332
-
333
- return $this->convert_data_to_csv( $data, $this->_pre_data['active_fields'], $csv_sep );
334
-
335
- case 'tsv':
336
- return $this->convert_data_to_tsv( $data );
337
- }
338
- return '';
339
- }
340
- }
341
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/class-tvc-feed-queries.php DELETED
@@ -1,243 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * Google Feed Queries Class.
5
- *
6
- * @package Google Product Feed Manager/Application/Classes
7
- * @version 2.1.1
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Feed_Queries' ) ) :
15
-
16
- /**
17
- * Feed Queries Class
18
- */
19
- class TVC_Feed_Queries {
20
-
21
- /**
22
- * @param $query
23
- * @param $value
24
- * @return bool
25
- */
26
- public function includes_query( $query, $value ) {
27
- return $query[3] && strpos( strtolower( $value ), strtolower( trim( $query[3] ) ) ) !== false ? false : true;
28
- }
29
-
30
- /**
31
- * @param $query
32
- * @param $value
33
- * @return bool
34
- */
35
- public function does_not_include_query( $query, $value ) {
36
- return $query[3] && strpos( strtolower( $value ), strtolower( trim( $query[3] ) ) ) === false ? false : true;
37
- }
38
-
39
- /**
40
- * @param $query
41
- * @param $value
42
- * @return bool
43
- */
44
- public function is_equal_to_query( $query, $value ) {
45
- return strtolower( $value ) === strtolower( trim( $query[3] ) ) ? false : true;
46
- }
47
-
48
- /**
49
- * @param $query
50
- * @param $value
51
- * @return bool
52
- */
53
- public function is_not_equal_to_query( $query, $value ) {
54
- return strtolower( $value ) !== strtolower( trim( $query[3] ) ) ? false : true;
55
- }
56
-
57
- /**
58
- * @param $value
59
- * @return bool
60
- */
61
- public function is_empty( $value ) {
62
- if ( ! is_array( $value ) ) {
63
- $value = trim( $value );
64
- }
65
-
66
- return empty( $value ) ? false : true;
67
- }
68
-
69
- /**
70
- * @param $value
71
- * @return bool
72
- */
73
- public function is_not_empty_query( $value ) {
74
- if ( ! is_array( $value ) ) {
75
- $value = trim( $value );
76
- }
77
-
78
- return ! empty( $value ) ? false : true;
79
- }
80
-
81
- /**
82
- * @param $query
83
- * @param $value
84
- * @return bool
85
- */
86
- public function starts_with_query( $query, $value ) {
87
- if ( ! empty( $value ) && strrpos( strtolower( $value ), strtolower( trim( $query[3] ) ), - strlen( $value ) ) !== false ) {
88
- return false;
89
- } else {
90
- return true;
91
- }
92
- }
93
-
94
- /**
95
- * @param $query
96
- * @param $value
97
- * @return bool
98
- */
99
- public function does_not_start_with_query( $query, $value ) {
100
- if ( empty( $value ) || strrpos( strtolower( $value ), strtolower( trim( $query[3] ) ), - strlen( $value ) ) === false ) {
101
- return false;
102
- } else {
103
- return true;
104
- }
105
- }
106
-
107
- /**
108
- * @param $query
109
- * @param $value
110
- * @return bool
111
- */
112
- public function ends_with_query( $query, $value ) {
113
- $search_string = trim( $query[3] );
114
- $value_length = strlen( $value );
115
-
116
- if ( ! empty( $value ) && ( $value_length - strlen( $search_string ) ) >= 0 && strpos( $value, $search_string, $value_length ) !== false ) {
117
- return false;
118
- } else {
119
- return true;
120
- }
121
- }
122
-
123
- /**
124
- * @param $query
125
- * @param $value
126
- * @return bool
127
- */
128
- public function does_not_end_with_query( $query, $value ) {
129
- $search_string = trim( $query[3] );
130
- $value_length = strlen( $value );
131
-
132
- if ( ! empty( $value ) && ( $value_length - strlen( $search_string ) ) >= 0 && strpos( $value, $search_string, $value_length ) !== false ) {
133
- return true;
134
- } else {
135
- return false;
136
- }
137
- }
138
-
139
- /**
140
- * @param $query
141
- * @param $value
142
- * @return bool
143
- */
144
- public function is_greater_than_query( $query, $value ) {
145
- $data_nr = $this->convert_to_us_notation( trim( $value ) );
146
- $condition_nr = $this->convert_to_us_notation( trim( $query[3] ) );
147
-
148
- if ( is_numeric( $data_nr ) && is_numeric( $condition_nr ) ) {
149
- return (float) $data_nr > (float) $condition_nr ? false : true;
150
- } else {
151
- return false;
152
- }
153
- }
154
-
155
- /**
156
- * @param $query
157
- * @param $value
158
- * @return bool
159
- */
160
- public function is_greater_or_equal_to_query( $query, $value ) {
161
- $data_nr = $this->convert_to_us_notation( trim( $value ) );
162
- $condition_nr = $this->convert_to_us_notation( trim( $query[3] ) );
163
-
164
- if ( is_numeric( $data_nr ) && is_numeric( trim( $condition_nr ) ) ) {
165
- return (float) $data_nr >= (float) $condition_nr ? false : true;
166
- } else {
167
- return false;
168
- }
169
- }
170
-
171
- /**
172
- * @param $query
173
- * @param $value
174
- * @return bool
175
- */
176
- public function is_smaller_than_query( $query, $value ) {
177
- $data_nr = $this->convert_to_us_notation( trim( $value ) );
178
- $condition_nr = $this->convert_to_us_notation( trim( $query[3] ) );
179
-
180
- if ( is_numeric( $data_nr ) && is_numeric( $condition_nr ) ) {
181
- return (float) $data_nr < (float) $condition_nr ? false : true;
182
- } else {
183
- return false;
184
- }
185
- }
186
-
187
- /**
188
- * @param $query
189
- * @param $value
190
- * @return bool
191
- */
192
- public function is_smaller_or_equal_to_query( $query, $value ) {
193
- $data_nr = $this->convert_to_us_notation( trim( $value ) );
194
- $condition_nr = $this->convert_to_us_notation( trim( $query[3] ) );
195
-
196
- if ( is_numeric( $data_nr ) && is_numeric( $condition_nr ) ) {
197
- return (float) $data_nr <= (float) $condition_nr ? false : true;
198
- } else {
199
- return false;
200
- }
201
- }
202
-
203
- /**
204
- * @param $query
205
- * @param $value
206
- * @return bool
207
- */
208
- public function is_between_query( $query, $value ) {
209
- $data_nr = $this->convert_to_us_notation( trim( $value ) );
210
- $condition_nr_low = $this->convert_to_us_notation( trim( $query[3] ) );
211
- $condition_nr_high = $this->convert_to_us_notation( trim( $query[5] ) );
212
-
213
- if ( is_numeric( $data_nr ) && is_numeric( $condition_nr_low ) && is_numeric( $condition_nr_high ) ) {
214
- if ( (float) $data_nr > (float) $condition_nr_low && (float) $data_nr < (float) $condition_nr_high ) {
215
- return false;
216
- } else {
217
- return true;
218
- }
219
- } else {
220
- return false;
221
- }
222
- }
223
-
224
- /**
225
- * @param $current_value
226
- * @return mixed
227
- */
228
- private function convert_to_us_notation( $current_value ) {
229
- $decimal_sep = get_option( 'woocommerce_price_decimal_sep' );
230
- $thousands_sep = get_option( 'woocommerce_price_thousand_sep' );
231
-
232
- if ( ! preg_match( '/[a-zA-Z]/', $current_value ) ) { // only remove the commas if the current value has no letters
233
- $no_thousands_sep = str_replace( $thousands_sep, '', $current_value );
234
-
235
- return ',' === $decimal_sep ? str_replace( ',', '.', $no_thousands_sep ) : $no_thousands_sep;
236
- } else {
237
- return $current_value;
238
- }
239
- }
240
- }
241
- // end of TVC_Feed_Queries_Class
242
-
243
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/class-tvc-feed-value-editors.php DELETED
@@ -1,240 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Feed Value Editors Class.
5
- *
6
- * @package TVC Product Feed Manager/Application/Classes
7
- * @version 1.6.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
-
15
- if ( ! class_exists( 'TVC_Feed_Value_Editors' ) ) :
16
-
17
- /**
18
- * Feed Value Editors Class
19
- */
20
- class TVC_Feed_Value_Editors {
21
-
22
- /**
23
- * @param $condition
24
- * @return mixed
25
- */
26
- public function overwrite_value( $condition ) {
27
- return $condition[2];
28
- }
29
-
30
- /**
31
- * @param $condition
32
- * @param $current_value
33
- * @return mixed
34
- */
35
- public function replace_value( $condition, $current_value ) {
36
- return str_replace( $condition[2], $condition[3], $current_value );
37
- }
38
-
39
- /**
40
- * @param $element_name
41
- * @param $current_value
42
- * @return string
43
- */
44
- public function convert_to_element( $element_name, $current_value ) {
45
- return "!sub:$element_name[2]|$current_value";
46
- }
47
-
48
- /**
49
- * @param $condition
50
- * @param $current_value
51
- * @return mixed
52
- */
53
- public function remove_value( $condition, $current_value ) {
54
- return str_replace( $condition[2], '', $current_value );
55
- }
56
-
57
- /**
58
- * @param $condition
59
- * @param $current_value
60
- * @return string
61
- */
62
- public function add_prefix_value( $condition, $current_value ) {
63
- return $condition[2] . $current_value;
64
- }
65
-
66
- /**
67
- * @param $condition
68
- * @param $current_value
69
- * @return string
70
- */
71
- public function add_suffix_value( $condition, $current_value ) {
72
- return $current_value . $condition[2];
73
- }
74
-
75
- /**
76
- * @param $condition
77
- * @param $current_value
78
- * @param $combination_string
79
- * @param $combined_data_elements
80
- * @param $feed_language
81
- * @return float|int|mixed|string
82
- */
83
- public function recalculate_value( $condition, $current_value, $combination_string, $combined_data_elements, $feed_language ) {
84
- if ( ! $combination_string ) {
85
- $values = $this->make_recalculate_inputs( $current_value, $condition[3] );
86
- $calculated_value = $this->recalculate( $condition[2], floatval( $values['main_val'] ), floatval( $values['sub_val'] ) );
87
-
88
- return $this->is_money_value( $current_value ) ? tvc_prep_money_values( $calculated_value, $feed_language ) : $calculated_value;
89
-
90
- } else {
91
- if ( count( $combined_data_elements ) > 1 ) {
92
- $combined_string_values = array();
93
-
94
- foreach ( $combined_data_elements as $element ) {
95
- $values = $this->make_recalculate_inputs( $element, $condition[3] );
96
-
97
- $reg_match = '/[0-9.,]/'; // only numbers and decimals
98
-
99
- $calculated_value = preg_match( $reg_match, $values['main_val'] ) && preg_match( $reg_match, $values['sub_val'] ) ?
100
- $this->recalculate( $condition[2], floatval( $values['main_val'] ), floatval( $values['sub_val'] ) ) : $values['main_val'];
101
-
102
- $end_value = $this->is_money_value( $element ) ? tvc_prep_money_values( $calculated_value, $feed_language ) : $calculated_value;
103
-
104
- array_push( $combined_string_values, $end_value );
105
- }
106
-
107
- return $this->make_combined_result_string( $combined_string_values, $combination_string );
108
- } else {
109
- return '';
110
- }
111
- }
112
- }
113
-
114
- /**
115
- * @param $values
116
- * @param $combination_string
117
- * @return mixed|string
118
- */
119
- private function make_combined_result_string( $values, $combination_string ) {
120
- $separators = $this->combination_separators();
121
- $result_string = $values[0];
122
-
123
- $combinations = explode( '|', $combination_string );
124
-
125
- for ( $i = 1; $i < count( $combinations ); $i ++ ) {
126
- $sep = explode( '#', $combinations[ $i ] );
127
- $result_string .= $separators[ (int) $sep[0] ];
128
- $result_string .= $values[ $i ];
129
- }
130
- return $result_string;
131
- }
132
-
133
- public function combination_separators() {
134
- return array(
135
- '',
136
- ' ',
137
- ', ',
138
- '.',
139
- '; ',
140
- ':',
141
- '-',
142
- '/',
143
- '\\',
144
- '||',
145
- '_',
146
- ); // should correspond with tvc_getCombinedSeparatorList()
147
- }
148
-
149
- /**
150
- * @param $current_value
151
- * @param $current_sub_value
152
- * @return array
153
- */
154
- private function make_recalculate_inputs( $current_value, $current_sub_value ) {
155
- if ( ! preg_match( '/[a-zA-Z]/', $current_value ) ) { // only remove the commas if the current value has no letters
156
- $main_value = tvc_number_format_parse( $current_value );
157
- } else {
158
- $main_value = $current_value;
159
- }
160
-
161
- $sub_value = tvc_number_format_parse( $current_sub_value );
162
-
163
- return array(
164
- 'main_val' => $main_value,
165
- 'sub_val' => $sub_value,
166
- );
167
- }
168
-
169
- /**
170
- * @param $meta_data
171
- * @param $feed_language
172
- * @return string
173
- */
174
- public function prep_meta_values( $meta_data, $feed_language ) {
175
- $result = $meta_data->meta_value;
176
-
177
- if ( tvc_meta_key_is_money( $meta_data->meta_key ) ) {
178
- $result = tvc_prep_money_values( $result, $feed_language );
179
- }
180
-
181
- return is_string( $result ) ? trim( $result ) : $result;
182
- }
183
-
184
- /**
185
- * Checks is a certain value could be a money value or not
186
- *
187
- * @param int or string $value
188
- *
189
- * @return boolean true if it is a money value
190
- */
191
- public function is_money_value( $value ) {
192
- // replace a comma separator with a period so it can be recognized as numeric
193
- $possible_number = tvc_number_format_parse( $value );
194
-
195
- // if its not a number it cannot be a money value
196
- if ( ! is_numeric( $possible_number ) ) {
197
- return false;
198
- }
199
-
200
- $last_pos = strrpos( (string) $value, get_option( 'woocommerce_price_decimal_sep' ) );
201
- $value_length = strlen( (string) $value );
202
-
203
- $actual_decimals = $value_length - $last_pos - 1;
204
-
205
- return absint( get_option( 'woocommerce_price_num_decimals', 2 ) ) === $actual_decimals ? true : false;
206
- }
207
-
208
- /**
209
- * @param $math
210
- * @param $main_value
211
- * @param $sub_value
212
- * @return float|int|string
213
- */
214
- private function recalculate( $math, $main_value, $sub_value ) {
215
- $result = 0;
216
-
217
- if ( is_numeric( $main_value ) && is_numeric( $sub_value ) ) {
218
- switch ( $math ) {
219
- case 'add':
220
- $result = $main_value + $sub_value;
221
- break;
222
-
223
- case 'subtract':
224
- $result = $main_value - $sub_value;
225
- break;
226
-
227
- case 'multiply':
228
- $result = $main_value * $sub_value;
229
- break;
230
-
231
- case 'divide':
232
- $result = 0 !== $sub_value ? $main_value / $sub_value : 0;
233
- break;
234
- }
235
- }
236
- return $result;
237
- }
238
- }
239
- // End of TVC_Feed_Value_Editors class
240
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/class-tvc-schedules.php DELETED
@@ -1,147 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Schedules Class.
5
- *
6
- * @package TVC Product Feed Manager/Application/Classes
7
- * @version 1.1.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
-
15
- if ( ! class_exists( 'TVC_Schedules' ) ) :
16
-
17
- /**
18
- * Feed Schedules Class
19
- */
20
- class TVC_Schedules {
21
-
22
- /* --------------------------------------------------------------------------------------------------*
23
- * Public functions
24
- * -------------------------------------------------------------------------------------------------- */
25
-
26
- /**
27
- * Initiates the automatic feed updates
28
- */
29
- public function update_active_feeds() {
30
- $data_class = new TVC_Data();
31
-
32
- $current_timestamp = date( 'Y-m-d H:i:s', current_time( 'timestamp' ) );
33
- $active_feeds_schedules = $data_class->get_schedule_data();
34
- $failed_feeds = $data_class->get_failed_feeds();
35
- $active_feed_id = null;
36
-
37
- // update scheduled feeds
38
- foreach ( $active_feeds_schedules as $schedule ) {
39
- $active_feed_id = $schedule['product_feed_id'];
40
- $update_time = $this->new_activation_time( $schedule['updated'], $schedule['schedule'] );
41
-
42
- // activate the feed update when the update time is reached
43
- if ( $update_time < $current_timestamp ) {
44
- TVC_Feed_Controller::add_id_to_feed_queue( $schedule['product_feed_id'] );
45
-
46
- $data_class->update_feed_status( $schedule['product_feed_id'], 4 ); // feed status to waiting in queue
47
- }
48
- }
49
-
50
- // if there is no feed processing in progress and the feed queue is not empty, start updating the current feed
51
- if ( ! TVC_Feed_Controller::feed_queue_is_empty() && ! TVC_Feed_Controller::feed_is_processing() ) {
52
- do_action( 'tvc_automatic_feed_update_triggered', $active_feed_id );
53
- $feed_master_class = new TVC_Feed_Master_Class( $active_feed_id );
54
- $feed_master_class->update_feed_file( true );
55
- }
56
-
57
- // update previously failed feeds
58
- if ( 'true' === get_option( 'tvc_auto_feed_fix' ) ) {
59
- foreach ( $failed_feeds as $failed_feed ) {
60
- TVC_Feed_Controller::add_id_to_feed_queue( $failed_feed['product_feed_id'] );
61
-
62
- // if there is no feed processing in progress, start updating the current feed
63
- if ( ! TVC_Feed_Controller::feed_is_processing() ) {
64
- do_action( 'tvc_automatic_feed_prepare_update_triggered', $active_feed_id );
65
-
66
- $feed_master_class = new TVC_Feed_Master_Class( $active_feed_id );
67
- $feed_master_class->update_feed_file( true );
68
- } else {
69
- $data_class->update_feed_status( $failed_feed['product_feed_id'], 4 ); // feed status to waiting in queue
70
- }
71
- }
72
- }
73
- }
74
-
75
- /* --------------------------------------------------------------------------------------------------*
76
- * Private functions
77
- * -------------------------------------------------------------------------------------------------- */
78
-
79
- /**
80
- * Returns the time at which the feed should be updated
81
- *
82
- * @param string $last_update time string with the data and time the feed has been update last
83
- * @param string $update_frequency registered update frequency
84
- *
85
- * @return string Containing the time in Y-m-d H:i:s format
86
- */
87
- private function new_activation_time( $last_update, $update_frequency ) {
88
- $update_split = explode( ':', $update_frequency );
89
-
90
- $hrs = isset( $update_split[1] ) ? $update_split[1] : '00';
91
- $min = isset( $update_split[2] ) ? $update_split[2] : '00';
92
- $freq = isset( $update_split[3] ) ? $update_split[3] : 1;
93
-
94
- $planned_update_time = $hrs . ':' . $min . ':00';
95
- $planned_update_time = '00:00:00' !== $planned_update_time ? $planned_update_time : '23:59:00';
96
- $last_update_time = date( 'H:i:s', strtotime( $last_update ) );
97
- $days = $update_split[0] <= 1
98
- && ( ( strtotime( $last_update_time ) <= strtotime( $planned_update_time ) )
99
- || ( '00' === $hrs && '00' === $min ) )
100
- ? 0 : $update_split[0];
101
-
102
- if ( $freq < 2 ) { // update only once a day, every $update_split[0] days
103
- $update_date = date_add( date_create( date( 'Y-m-d', strtotime( $last_update ) ) ), date_interval_create_from_date_string( $days . ' days' ) );
104
-
105
- return date_format( $update_date, 'Y-m-d' ) . ' ' . $planned_update_time;
106
- } else { // update more than once a day
107
- $update_hrs = $this->get_update_hours( $freq );
108
- $update_date = date_add( date_create( $last_update ), date_interval_create_from_date_string( $update_hrs . ' hours' ) );
109
-
110
- return date_format( $update_date, 'Y-m-d H:i' ) . ':00';
111
- }
112
- }
113
-
114
- /**
115
- * Returns the daily update options
116
- *
117
- * @param string $selection selected number of hours
118
- *
119
- * @return int Hours difference between updates
120
- */
121
- private function get_update_hours( $selection ) {
122
- switch ( $selection ) {
123
- case '2':
124
- return 12;
125
-
126
- case '4':
127
- return 6;
128
-
129
- case '6':
130
- return 4;
131
-
132
- case '8':
133
- return 3;
134
-
135
- case '12':
136
- return 2;
137
-
138
- case '24':
139
- return 1;
140
-
141
- default:
142
- return 24;
143
- }
144
- }
145
- }
146
- // end of TVC_Schedules class
147
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/google/class-feed.php DELETED
@@ -1,213 +0,0 @@
1
- <?php
2
- /**
3
- * Google Product Feed Manager Google Feed Class.
4
- *
5
- * @package Google Product Feed Manager/Channels
6
- * @version 11.0
7
- */
8
-
9
- // Prevent direct access
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Google_Feed_Class' ) ) :
15
-
16
- /**
17
- * TVC_Google_Feed_Class class
18
- */
19
- class TVC_Google_Feed_Class extends TVC_Feed_Master_Class {
20
-
21
- private $_version = '11.0';
22
-
23
- public function __construct() {
24
- parent::__construct();
25
- }
26
-
27
- public function get_version() {
28
- return $this->_version;
29
- }
30
-
31
- public function get_file_text() {
32
- return $this->generate_file_text( '1', 'google_product_category', 'description', 'xml' );
33
- }
34
-
35
- public function woocommerce_to_feed_fields() {
36
- $fields = new stdClass();
37
-
38
- // ALERT! Any changes made to this object also need to be done to the woocommerceToGoogleFields() function in the google-source.js file
39
- $fields->id = 'ID';
40
- $fields->title = 'post_title';
41
- $fields->google_product_category = 'category';
42
- $fields->description = 'post_content';
43
- $fields->link = 'permalink';
44
- $fields->image_link = 'attachment_url';
45
- $fields->additional_image_link = '_wp_attachement_metadata';
46
- $fields->price = '_regular_price';
47
- $fields->identifier_exists = 'Fill with a static value';
48
- $fields->sale_price = '_sale_price';
49
- $fields->sale_price_effective_date = '_sale_price_dates_from';
50
- $fields->item_group_id = 'item_group_id';
51
- $fields->mpn = 'ID';
52
- $fields->tax = 'Use the settings in the Merchant Center';
53
- $fields->shipping = 'Use the settings in the Merchant Center';
54
-
55
- return $fields;
56
- }
57
-
58
- // overrides the set_feed_output_attribute_levels function in TVC_Feed_Master_Class
59
- // ALERT! This function is equivalent for the setGoogleOutputAttributeLevels() function in google-source.js
60
- public function set_feed_output_attribute_levels( &$main_data ) {
61
- $country = $main_data->country;
62
-
63
- for ( $i = 0; $i < count( $main_data->attributes ); $i ++ ) {
64
- if ( '0' === $main_data->attributes[ $i ]->fieldLevel ) {
65
- switch ( $main_data->attributes[ $i ]->fieldName ) {
66
- case 'google_product_category':
67
- $main_data->attributes[ $i ]->fieldLevel = $this->google_needs_product_cat( $main_data->mainCategory ) === true ? 1 : 4;
68
- break;
69
-
70
- case 'is_bundle':
71
- case 'multipack':
72
- $main_data->attributes[ $i ]->fieldLevel = in_array( $country, $this->special_product_countries() ) ? 1 : 4;
73
- break;
74
-
75
- case 'brand':
76
- $main_data->attributes[ $i ]->fieldLevel = $this->google_requires_brand( $main_data->mainCategory ) === true ? 1 : 4;
77
- break;
78
-
79
- case 'item_group_id':
80
- $main_data->attributes[ $i ]->fieldLevel = in_array( $country, $this->special_clothing_group_countries() ) ? 1 : 4;
81
- break;
82
-
83
- case 'gender':
84
- case 'age_group':
85
- case 'color':
86
- case 'size':
87
- if ( in_array( $country, $this->special_clothing_group_countries() )
88
- && $this->google_clothing_and_accessories( $main_data->mainCategory ) === true ) {
89
- $main_data->attributes[ $i ]->fieldLevel = 1;
90
- } else {
91
- $main_data->attributes[ $i ]->fieldLevel = 4;
92
- }
93
-
94
- break;
95
-
96
- case 'tax':
97
- // In accordance with the Google Feed Specifications update of september 2015
98
- $main_data->attributes[ $i ]->fieldLevel = 'US' === $country ? 1 : 4;
99
- break;
100
-
101
- case 'shipping':
102
- // In accordance with the Google Feed Specifications update of september 2015
103
- $main_data->attributes[ $i ]->fieldLevel = in_array( $country, $this->special_shipping_countries() ) ? 1 : 4;
104
- break;
105
-
106
- case 'subscription_cost':
107
- case 'subscription_cost-period':
108
- case 'subscription_cost-period_length':
109
- case 'subscription_cost-amount':
110
- $main_data->attributes[ $i ]->fieldLevel = in_array( $country, $this->special_subscription_countries() ) ? 4 : 0;
111
- break;
112
-
113
- default:
114
- break;
115
- }
116
-
117
- $main_data->attributes[ $i ]->isActive =
118
- $this->set_attribute_status( (int) $main_data->attributes[ $i ]->fieldLevel, $main_data->attributes[ $i ]->value );
119
- }
120
- }
121
- }
122
-
123
- public function keys_that_have_sub_tags() {
124
- return array( 'installment', 'loyalty_points', 'shipping', 'tax', 'subscription_cost' );
125
- }
126
-
127
- // ALERT! This function is equivalent to the tvc_doublesFieldsAllowed() function in the tvc_google-source.js file
128
- public function keys_that_can_be_used_more_than_once() {
129
- return array( 'display_ads_similar_id', 'excluded_destination', 'adwords_labels', 'shipping' );
130
- }
131
-
132
- public function sub_keys_for_sub_tags() {
133
- return array(
134
- 'installment-months',
135
- 'installment-amount',
136
- 'loyalty_points-name',
137
- 'loyalty_points-pointsValue',
138
- 'loyalty_points-ratio',
139
- 'shipping-country',
140
- 'shipping-region',
141
- 'shipping-service',
142
- 'shipping-price',
143
- 'tax-country',
144
- 'tax-region',
145
- 'tax-rate',
146
- 'tax-tax_ship',
147
- 'subscription_cost-period',
148
- 'subscription_cost-period_length',
149
- 'subscription_cost-amount',
150
- );
151
- }
152
-
153
- // ALERT! This function is equivalent to the googleSpecialClothingGroupCountries() function in google-source.js
154
- private function special_clothing_group_countries() {
155
- return array( 'US', 'GB', 'DE', 'FR', 'JP', 'BR' ); // Brazil added based on the new Feed Specifications from september 2015
156
- }
157
-
158
- // ALERT! This function is equivalent to the googleSpecialShippingCountries() function in google-source.js
159
- private function special_shipping_countries() {
160
- return array( 'US', 'GB', 'DE', 'AU', 'FR', 'CH', 'CZ', 'NL', 'IT', 'ES', 'JP' );
161
- }
162
-
163
- // ALERT! This function is equivalent to the googleSpecialProductCountries() function in google-source.js
164
- private function special_product_countries() {
165
- return array( 'US', 'GB', 'DE', 'AU', 'FR', 'CH', 'CZ', 'NL', 'IT', 'ES', 'JP', 'BR' );
166
- }
167
-
168
- // ALERT! This function is equivalent to the googleSpecialSubscriptionCountries() function in google-source.js
169
- private function special_subscription_countries() {
170
- return array( 'DE', 'FR', 'GB' );
171
- }
172
-
173
- private function google_clothing_and_accessories( $category ) {
174
- return stristr( $category, 'Apparel & Accessories' ) !== false ? true : false;
175
- }
176
-
177
- private function google_needs_product_cat( $category ) {
178
- return stristr( $category, 'Apparel & Accessories' ) !== false
179
- || stristr( $category, 'Media' ) !== false
180
- || stristr( $category, 'Software' ) !== false ? true : false;
181
- }
182
-
183
- private function google_requires_brand( $category ) {
184
- return false === stristr( $category, 'Media' ) ? true : false;
185
- }
186
-
187
- protected function header( $title, $description = '' ) {
188
- // the check for convert_to_data_string function can be remove when all users have switched to plugin version 1.6 or higher
189
- $title_string = method_exists( $this, 'data_string' ) ? $this->data_string( $title )
190
- : $this->convert_to_character_data_string( $title );
191
- $home_link = method_exists( $this, 'data_string' ) ? $this->data_string( get_option( 'home' ) )
192
- : $this->convert_to_character_data_string( get_option( 'home' ) );
193
- $descr = '' !== $description ? $description : $title;
194
- $description_string = method_exists( $this, 'data_string' ) ? $this->data_string( $descr )
195
- : $this->convert_to_character_data_string( $descr );
196
- $title_tag = '<wf-connection-string>';
197
-
198
- return '<?xml version="1.0"?>
199
- <rss version="2.0" xmlns:g="http://base.google.com/ns/1.0">
200
- <channel>
201
- <title>' . $title_string . '</title>'
202
- . $title_tag . $home_link . '</link>
203
- <description>' . $description_string . '</description>';
204
- }
205
-
206
- protected function footer() {
207
- return '</channel></rss>';
208
- }
209
- }
210
-
211
- // end of TVC_Google_Feed_Class
212
-
213
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/tvc-cron-functions.php DELETED
@@ -1,54 +0,0 @@
1
- <?php
2
- /**
3
- * @package TVC Product Feed Manager/Application/Functions
4
- * @version 1.3.0
5
- */
6
-
7
- if ( ! defined( 'ABSPATH' ) ) {
8
- exit;
9
- }
10
- /**
11
- * Activates the feed update schedules using Cron Jobs
12
- */
13
- function tvc_update_feeds() {
14
- // include the required WordPress files
15
- require_once( ABSPATH . 'wp-load.php' );
16
- require_once( ABSPATH . 'wp-admin/includes/admin.php' );
17
- require_once( ABSPATH . 'wp-admin/includes/file.php' ); // required for using the file system
18
- require_once( ABSPATH . 'wp-admin/includes/plugin.php' ); // required to prevent a fatal error about not finding the is_plugin_active function
19
- // include all product feed manager files
20
- require_once( ENHANCAD_PLUGIN_DIR . 'includes/user-interface/tvc-messaging-functions.php' );
21
- //require_once( ENHANCAD_PLUGIN_DIR . 'includes/tvc-wpincludes.php' );
22
- //require_once( ENHANCAD_PLUGIN_DIR . 'includes/data/tvc-admin-functions.php' );
23
- //require_once( ENHANCAD_PLUGIN_DIR . 'includes/user-interface/tvc-url-functions.php' );
24
- //require_once( ENHANCAD_PLUGIN_DIR . 'includes/application/tvc-feed-processing-support.php' );
25
- //require_once( ENHANCAD_PLUGIN_DIR . 'includes/application/tvc-feed-processor-functions.php' );
26
-
27
- // WooCommerce needs to be installed and active
28
- if ( ! tvc_wc_installed_and_active() ) {
29
- tvc_write_log_file( 'Tried to start the auto update process but failed because WooCommerce is not installed.' );
30
- exit;
31
- }
32
-
33
- // Feed Manager requires at least WooCommerce version 3.0.0
34
- if ( ! tvc_wc_min_version_required() ) {
35
- tvc_write_log_file( sprintf( 'Tried to start the auto update process but failed because WooCommerce is older than version %s', TVC_MIN_REQUIRED_WC_VERSION ) );
36
- exit;
37
- }
38
-
39
- WC_Post_types::register_taxonomies(); // make sure the woocommerce taxonomies are loaded
40
- WC_Post_types::register_post_types(); // make sure the woocommerce post types are loaded
41
-
42
- // include all required classes
43
- //include_classes();
44
- //include_channels();
45
-
46
- do_action( 'tvc_automatic_feed_processing_triggered' );
47
-
48
- // update the database if required
49
- tvc_check_db_version();
50
-
51
- // start updating the active feeds
52
- $tvc_schedules = new TVC_Schedules();
53
- $tvc_schedules->update_active_feeds();
54
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/tvc-feed-processing-support.php DELETED
@@ -1,1583 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * @package TVC Product Feed Manager/Application/Functions
5
- * @version 1.4.0
6
- */
7
-
8
- trait TVC_Processing_Support {
9
-
10
- protected $_selected_number;
11
-
12
- /**
13
- * Returns the correct category for this specific product
14
- *
15
- * @param string $id
16
- * @param string $main_category
17
- * @param string $category_mapping
18
- *
19
- * @return string
20
- */
21
- protected function get_mapped_category( $id, $main_category, $category_mapping ) {
22
- $result = false;
23
- $support_class = new TVC_Feed_Support();
24
- $yoast_primary_category = TVC_Taxonomies::get_yoast_primary_cat( $id );
25
- $yoast_cat_is_selected = $yoast_primary_category ? $support_class->category_is_selected( $yoast_primary_category[0]->term_id, $category_mapping ) : false;
26
-
27
- $product_categories = $yoast_primary_category && false !== $yoast_cat_is_selected ? $yoast_primary_category :
28
- wp_get_post_terms( $id, 'product_cat', array( 'taxonomy' => 'product_cat' ) ); // get the categories from a specific product in the shop
29
-
30
- if ( $product_categories && ! is_wp_error( $product_categories ) ) {
31
- // loop through each category
32
- foreach ( $product_categories as $category ) {
33
- // check if this category is selected in the category mapping
34
- $shop_category_id = $support_class->category_is_selected( $category->term_id, $category_mapping );
35
-
36
- // only add this product when at least one of the categories is selected in the category mapping
37
- if ( false !== $shop_category_id ) {
38
- switch ( $category_mapping[ $shop_category_id ]->feedCategories ) {
39
- case 'wp_mainCategory':
40
- $result = $main_category;
41
- break;
42
-
43
- case 'wp_ownCategory':
44
- $result = TVC_Taxonomies::get_shop_categories( $id, ' > ' );
45
- break;
46
-
47
- default:
48
- $result = $category_mapping[ $shop_category_id ]->feedCategories;
49
- }
50
-
51
- // found a selected category so now return the result
52
- return $result; // fixed ticket #1117
53
-
54
- } else { // if this product was not selected in the category mapping, it is possible it has been filtered in so map to the default category
55
- $result = $main_category;
56
- }
57
- }
58
- } else {
59
- if ( is_wp_error( $product_categories ) ) {
60
- echo tvc_handle_wp_errors_response(
61
- $product_categories,
62
- sprintf(
63
- /* translators: %s: link to the support page */
64
- esc_html__( '2131 - Please try to refresh the page and open a support ticket at %s if the issue persists.', 'tvc-product-feed-manager'),
65
- TVC_SUPPORT_PAGE_URL
66
- )
67
- );
68
- }
69
-
70
- return false;
71
- }
72
-
73
- return $result;
74
- }
75
-
76
- /**
77
- * Checks if this product has been filtered out of the feed
78
- *
79
- * @param string $feed_filter_strings
80
- * @param array $product_data
81
- *
82
- * @return boolean
83
- */
84
- protected function is_product_filtered( $feed_filter_strings, $product_data ) {
85
- if ( $feed_filter_strings ) {
86
- return $this->filter_result( json_decode( $feed_filter_strings[0]['meta_value'] ), $product_data ) ? true : false;
87
- } else {
88
- return false;
89
- }
90
- }
91
-
92
- /**
93
- * @param $feed_id
94
- * @return array
95
- */
96
- protected function get_meta_parent_ids( $feed_id ) {
97
- $queries_class = new TVC_Queries();
98
-
99
- $query_result = $queries_class->get_meta_parents( $feed_id );
100
- $ids = array();
101
-
102
- foreach ( $query_result as $result ) {
103
- array_push( $ids, $result['ID'] );
104
- }
105
-
106
- return $ids;
107
- }
108
-
109
- /**
110
- * return an array with source column names from an attribute string
111
- *
112
- * @param string $value_string
113
- *
114
- * @return array
115
- */
116
- protected function get_source_columns_from_attribute_value( $value_string ) {
117
- $source_columns = array();
118
-
119
- $value_object = json_decode( $value_string );
120
-
121
- if ( property_exists( $value_object, 'm' ) ) {
122
- foreach ( $value_object->m as $source ) {
123
- // TODO: I guess I should further reduce the "if" loops by combining them more then now
124
- if ( is_object( $source ) && property_exists( $source, 's' ) ) {
125
- if ( property_exists( $source->s, 'source' ) ) {
126
- if ( 'combined' !== $source->s->source ) {
127
- array_push( $source_columns, $source->s->source );
128
- } else {
129
- if ( property_exists( $source->s, 'f' ) ) {
130
- $source_columns = array_merge( $source_columns, $this->get_combined_sources_from_combined_string( $source->s->f ) );
131
- }
132
- }
133
- }
134
- }
135
- }
136
- }
137
- return $source_columns;
138
- }
139
-
140
- /**
141
- * return an array with condition column names from an attribute string
142
- *
143
- * @param string $value_string
144
- *
145
- * @return array
146
- */
147
- protected function get_condition_columns_from_attribute_value( $value_string ) {
148
- $condition_columns = array();
149
-
150
- $value_object = json_decode( $value_string );
151
-
152
- if ( property_exists( $value_object, 'm' ) ) {
153
- foreach ( $value_object->m as $source ) {
154
- if ( is_object( $source ) && property_exists( $source, 'c' ) ) {
155
- for ( $i = 0; $i < count( $source->c ); $i ++ ) {
156
- array_push( $condition_columns, $this->get_names_from_string( $source->c[ $i ]->{$i + 1} ) );
157
- }
158
- }
159
- }
160
- }
161
- return $condition_columns;
162
- }
163
-
164
- /**
165
- * return an array with query column names from an attribute string
166
- *
167
- * @param string $value_string
168
- *
169
- * @return array
170
- */
171
- protected function get_queries_columns_from_attribute_value( $value_string ) {
172
- $query_columns = array();
173
-
174
- $value_object = json_decode( $value_string );
175
-
176
- if ( property_exists( $value_object, 'v' ) ) {
177
- foreach ( $value_object->v as $changed_value ) {
178
- if ( property_exists( $changed_value, 'q' ) ) {
179
- for ( $i = 0; $i < count( $changed_value->q ); $i ++ ) {
180
- array_push( $query_columns, $this->get_names_from_string( $changed_value->q[ $i ]->{$i + 1} ) );
181
- }
182
- }
183
- }
184
- }
185
- return $query_columns;
186
- }
187
-
188
- /**
189
- * extract a column name from a string
190
- *
191
- * @param string $string
192
- *
193
- * @return array
194
- */
195
- protected function get_names_from_string( $string ) {
196
- $condition_string_array = explode( '#', $string );
197
-
198
- return $condition_string_array[1];
199
- }
200
-
201
- /**
202
- * split the combined string into single combination items
203
- *
204
- * @param string $combined_string
205
- *
206
- * @return array
207
- */
208
- public function get_combined_sources_from_combined_string( $combined_string ) {
209
- $result = array();
210
- $combined_string_array = explode( '|', $combined_string );
211
-
212
- array_push( $result, $combined_string_array[0] );
213
-
214
- for ( $i = 1; $i < count( $combined_string_array ); $i ++ ) {
215
- $a = explode( '#', $combined_string_array[ $i ] );
216
- if ( array_key_exists( 1, $a ) ) {
217
- array_push( $result, $a[1] );
218
- }
219
- }
220
-
221
- return $result;
222
- }
223
-
224
- /**
225
- * Gets the meta data from a specific field
226
- *
227
- * @param string $field
228
- * @param stdClass $attributes
229
- *
230
- * @return stdClass attribute
231
- */
232
- protected function get_meta_data_from_specific_field( $field, $attributes ) {
233
- $i = 0;
234
-
235
- while ( true ) {
236
- if ( $attributes[ $i ]->fieldName !== $field ) {
237
- $i ++;
238
- if ( $i > 1000 ) {
239
- break;
240
- }
241
- } else {
242
- return $attributes[ $i ];
243
- }
244
- }
245
-
246
- return new stdClass();
247
- }
248
-
249
- /**
250
- * Generate the value of a field based on what the user has selected in filters, combined data, static data eg.
251
- *
252
- * @param array $product_data
253
- * @param stdClass $field_meta_data
254
- * @param string $main_category_feed_title
255
- * @param string $row_category
256
- * @param string $feed_language
257
- * @param array $relation_table
258
- *
259
- * @return array Returns an key=>value array of a specific product field where the key contains the field name and the value the field value
260
- */
261
- protected function process_product_field( $product_data, $field_meta_data, $main_category_feed_title, $row_category, $feed_language, $relation_table ) {
262
-
263
- $product_object[ $field_meta_data->fieldName ] = $this->get_correct_field_value(
264
- $field_meta_data,
265
- $product_data,
266
- $main_category_feed_title,
267
- $row_category,
268
- $feed_language,
269
- $relation_table
270
- );
271
-
272
- return $product_object;
273
- }
274
-
275
- /**
276
- * Processes a single field of a single product in the feed
277
- *
278
- * @param stdClass $field_meta_data containing the meta data of the field
279
- * @param array $product_data containing the product data of the field
280
- * @param string $main_category_feed_title main category title
281
- * @param string $row_category complete category string
282
- * @param string $feed_language language of the feed
283
- * @param array $relation_table table with the shop and merchant category relations
284
- *
285
- * @return string
286
- */
287
- protected function get_correct_field_value( $field_meta_data, $product_data, $main_category_feed_title, $row_category, $feed_language, $relation_table ) {
288
- $this->_selected_number = 0;
289
-
290
- // do not process category strings, but only fields that are requested
291
- if ( property_exists( $field_meta_data, 'fieldName' ) && $field_meta_data->fieldName !== $main_category_feed_title
292
- && $this->meta_data_contains_category_data( $field_meta_data ) === false ) {
293
-
294
- $value_object = property_exists( $field_meta_data, 'value' ) && '' !== $field_meta_data->value ? json_decode( $field_meta_data->value ) : new stdClass();
295
-
296
- if ( property_exists( $field_meta_data, 'value' ) && '' !== $field_meta_data->value && property_exists( $value_object, 'm' ) ) { // seems to be something we need to work on
297
- $advised_source = property_exists( $field_meta_data, 'advisedSource' ) ? $field_meta_data->advisedSource : '';
298
-
299
- // get the end value depending on the filter settings
300
- $end_row_value = $this->get_correct_end_row_value( $value_object->m, $product_data, $advised_source );
301
-
302
- } else { // no queries, edit values or alternative sources for this field
303
-
304
- if ( property_exists( $field_meta_data, 'advisedSource' ) && '' !== $field_meta_data->advisedSource ) {
305
- $db_title = $field_meta_data->advisedSource;
306
- } else {
307
- $support_class = new TVC_Feed_Support();
308
- $source_title = property_exists( $field_meta_data, 'fieldName' ) ? $field_meta_data->fieldName : '';
309
- $db_title = $support_class->find_relation( $source_title, $relation_table );
310
- }
311
-
312
- $end_row_value = array_key_exists( $db_title, $product_data ) ? $product_data[ $db_title ] : '';
313
- }
314
-
315
- // change value if requested
316
- if ( property_exists( $field_meta_data, 'value' ) && '' !== $field_meta_data->value && property_exists( $value_object, 'v' ) ) {
317
- $pos = $this->_selected_number;
318
-
319
- if ( property_exists( $value_object, 'm' ) && property_exists( $value_object->m[ $pos ], 's' ) ) {
320
- $combination_string = property_exists( $value_object->m[ $pos ]->s, 'f' ) ? $value_object->m[ $pos ]->s->f : false;
321
- $is_money = property_exists( $value_object->m[ $pos ]->s, 'source' ) ? tvc_meta_key_is_money( $value_object->m[ $pos ]->s->source ) : false;
322
- } else {
323
- $combination_string = false;
324
- $is_money = false;
325
- }
326
-
327
- $row_value = ! $is_money ? $end_row_value : tvc_prep_money_values( $end_row_value . $feed_language );
328
- $end_row_value = $this->get_edited_end_row_value( $value_object->v, $row_value, $product_data, $combination_string, $feed_language );
329
- }
330
- } else {
331
- $end_row_value = $row_category;
332
- }
333
-
334
- return $end_row_value;
335
- }
336
-
337
- /**
338
- * @param $value
339
- * @param $product_data
340
- * @param $advised_source
341
- * @return array|mixed|string
342
- */
343
- protected function get_correct_end_row_value( $value, $product_data, $advised_source ) {
344
- $end_row_value = '';
345
- $nr_values = count( $value ); // added @since 1.9.4
346
- $value_counter = 1; // added @since 1.9.4
347
-
348
- foreach ( $value as $filter ) {
349
- if ( true === $this->get_filter_status( $filter, $product_data ) && '' === $end_row_value ) {
350
-
351
- $end_row_value = $this->get_row_source_data( $filter, $product_data, $advised_source );
352
- break;
353
- } else {
354
- // no "or else" value seems to be selected
355
- if ( $value_counter >= $nr_values ) {
356
- return $end_row_value;
357
- } // added @since 1.9.4
358
-
359
- $this->_selected_number ++;
360
- }
361
-
362
- $value_counter ++; // added @since 1.9.4
363
- }
364
-
365
- // not found a condition that was correct so lets take the "for all other products" data to fetch the correct row_value
366
- if ( '' === $end_row_value ) {
367
- $end_row_value = $this->get_row_source_data( end( $value ), $product_data, $advised_source );
368
- }
369
-
370
- return $end_row_value;
371
- }
372
-
373
- /**
374
- * Removes links from a the post content and post excerpts in a product data array.
375
- *
376
- * @since 2.6.0
377
- *
378
- * @param $product_data array
379
- */
380
- protected function remove_links_from_product_data_description( &$product_data ) {
381
- $pattern = '#<a.*?>(.*?)</a>#i'; // link pattern
382
- $replacement = '\1';
383
-
384
- if ( array_key_exists( 'post_content', $product_data ) ) {
385
- $product_data['post_content'] = preg_replace( $pattern, $replacement, $product_data['post_content'] );
386
- }
387
-
388
- if ( array_key_exists( 'post_excerpt', $product_data ) ) {
389
- $product_data['post_excerpt'] = preg_replace( $pattern, $replacement, $product_data['post_excerpt'] );
390
- }
391
- }
392
-
393
- /**
394
- * @param $filter
395
- * @param $product_data
396
- * @return bool
397
- */
398
- protected function get_filter_status( $filter, $product_data ) {
399
- if ( property_exists( $filter, 'c' ) ) {
400
- // check if the query is true for this field
401
- return $this->filter_result( $filter->c, $product_data );
402
- } else {
403
- // apparently there is no condition so the result is always true
404
- return true;
405
- }
406
- }
407
-
408
- /**
409
- * @param $conditions
410
- * @param $product_data
411
- * @return bool
412
- */
413
- protected function filter_result( $conditions, $product_data ) {
414
- $query_results = array();
415
- $support_class = new TVC_Feed_Support();
416
-
417
- // run each query on the data
418
- foreach ( $conditions as $condition ) {
419
- $condition_string = $support_class->get_query_string_from_query_object( $condition );
420
-
421
- $query_split = explode( '#', $condition_string );
422
-
423
- $row_result = $support_class->check_query_result_on_specific_row( $query_split, $product_data ) === true ? 'false' : 'true';
424
-
425
- array_push( $query_results, $query_split[0] . '#' . $row_result );
426
- }
427
-
428
- // return the final filter result, based on the specific results
429
- return $this->connect_query_results( $query_results );
430
- }
431
-
432
- /**
433
- * Recieves an array with condition results and generates a single end result based on the "and" or "or"
434
- * connection between the conditions
435
- *
436
- * @param array with $results
437
- *
438
- * @return boolean
439
- */
440
- protected function connect_query_results( $results ) {
441
- $and_results = array();
442
- $end_result = true;
443
- $or_results = array();
444
-
445
- if ( count( $results ) > 0 ) {
446
- foreach ( $results as $query_result ) {
447
- $result_split = explode( '#', $query_result );
448
-
449
- if ( '2' === $result_split[0] ) {
450
- array_push( $or_results, $and_results ); // store the current "and" result for processing as "or" result
451
-
452
- $and_results = array(); // clear the "and" array
453
- }
454
-
455
- $and_result = $result_split[1]; // === 'false' ? 'false' : 'true';
456
-
457
- array_push( $and_results, $and_result );
458
- }
459
-
460
- if ( count( $and_results ) > 0 ) {
461
- array_push( $or_results, $and_results );
462
- }
463
-
464
- if ( count( $or_results ) > 0 ) {
465
- $end_result = false;
466
-
467
- foreach ( $or_results as $or_result ) {
468
- $a = true;
469
-
470
- foreach ( $or_result as $and_array ) {
471
- if ( 'false' === $and_array ) {
472
- $a = false;
473
- }
474
- }
475
-
476
- if ( $a ) {
477
- $end_result = true;
478
- }
479
- }
480
- } else { // no "or" results found
481
- $end_result = false;
482
- }
483
- } else {
484
- $end_result = false;
485
- }
486
-
487
- return $end_result;
488
- }
489
-
490
- /**
491
- * @param $filter
492
- * @param $product_data
493
- * @param $advised_source
494
- * @return array|mixed|string
495
- */
496
- protected function get_row_source_data( $filter, $product_data, $advised_source ) {
497
- $row_source_data = '';
498
-
499
- if ( property_exists( $filter, 's' ) ) {
500
- if ( property_exists( $filter->s, 'static' ) ) {
501
- $row_source_data = $filter->s->static;
502
- } elseif ( property_exists( $filter->s, 'source' ) ) {
503
- if ( 'combined' !== $filter->s->source ) {
504
- $row_source_data = array_key_exists( $filter->s->source, $product_data ) ? $product_data[ $filter->s->source ] : '';
505
- } else {
506
- $row_source_data = $this->generate_combined_string( $filter->s->f, $product_data );
507
- }
508
- }
509
- } else {
510
- // return the advised source data
511
- if ( '' !== $advised_source ) {
512
- $row_source_data = array_key_exists( $advised_source, $product_data ) ? $product_data[ $advised_source ] : '';
513
- }
514
- }
515
-
516
- return $row_source_data;
517
- }
518
-
519
- /**
520
- * @param $combined_sources
521
- * @param $row
522
- * @return array|string
523
- */
524
- protected function generate_combined_string( $combined_sources, $row ) {
525
- $source_selectors_array = explode( '|', $combined_sources ); //split the combined source string in an array containing every single source
526
- $values_class = new TVC_Feed_Value_Editors();
527
- $separators = $values_class->combination_separators(); // array with all possible separators
528
-
529
- // if one of the row results is an array, the final output needs to be an array
530
- $result_is_array = $this->check_if_any_source_has_array_data( $source_selectors_array, $row );
531
- $result = $result_is_array ? array() : '';
532
-
533
- if ( ! $result_is_array ) {
534
- $result = $this->make_combined_string( $source_selectors_array, $separators, $row, false );
535
- } else {
536
- for ( $i = 0; $i < count( $result_is_array ); $i ++ ) {
537
- $combined_string = $this->make_combined_string( $source_selectors_array, $separators, $row, $i );
538
- array_push( $result, $combined_string );
539
- }
540
- }
541
-
542
- return $result;
543
- }
544
-
545
- /**
546
- * Distracts the keys from the $sources string (separated by a #) and looks if any of these keys
547
- * are linked to an array in the $data_row
548
- *
549
- * @param array $sources
550
- * @param array $data_row
551
- *
552
- * @return array|bool from the data_row or false
553
- */
554
- protected function check_if_any_source_has_array_data( $sources, $data_row ) {
555
- foreach ( $sources as $source ) {
556
- $split_source = explode( '#', $source );
557
-
558
- if ( count( $split_source ) > 1 && 'static' === $split_source[1] ) {
559
- $last_key = 'static';
560
- } elseif ( 'static' === $split_source[0] ) {
561
- $last_key = 'static';
562
- } else {
563
- $last_key = array_pop( $split_source );
564
- }
565
-
566
- if ( array_key_exists( $last_key, $data_row ) && is_array( $data_row[ $last_key ] ) ) {
567
- return $data_row[ $last_key ];
568
- }
569
- }
570
-
571
- return false;
572
- }
573
-
574
- /**
575
- * @param $meta_data
576
- * @return bool
577
- */
578
- protected function meta_data_contains_category_data( $meta_data ) {
579
- if ( ! property_exists( $meta_data, 'value' ) || empty( $meta_data->value ) ) {
580
- return false;
581
- }
582
-
583
- $meta_obj = json_decode( $meta_data->value );
584
-
585
- return property_exists( $meta_obj, 't' ) ? true : false;
586
- }
587
-
588
- /**
589
- * @param $change_parameters
590
- * @param $original_output
591
- * @param $product_data
592
- * @param $combination_string
593
- * @param $feed_language
594
- * @return float|int|mixed|string
595
- */
596
- protected function get_edited_end_row_value( $change_parameters, $original_output, $product_data, $combination_string, $feed_language ) {
597
- $result_is_filtered = false;
598
- $support_class = new TVC_Feed_Support();
599
- $y = 0;
600
- $final_output = '';
601
-
602
- for ( $i = 0; $i < ( count( $change_parameters ) - 1 ); $i ++ ) {
603
- if ( property_exists( $change_parameters[ $i ], 'q' ) ) {
604
- $filter_result = $this->filter_result( $change_parameters[ $i ]->q, $product_data );
605
-
606
- if ( true === $filter_result ) {
607
- $combined_data_elements = $combination_string ? $this->get_combined_elements( $product_data, $combination_string ) : '';
608
- $final_output = $support_class->edit_value(
609
- $original_output,
610
- $change_parameters[ $i ]->{$i + 1},
611
- $combination_string,
612
- $combined_data_elements,
613
- $feed_language
614
- );
615
-
616
- $result_is_filtered = true;
617
- }
618
- }
619
-
620
- $y ++;
621
- }
622
-
623
- if ( false === $result_is_filtered ) {
624
- $combined_data_elements = $combination_string ? $this->get_combined_elements( $product_data, $combination_string ) : '';
625
- $final_output = $support_class->edit_value(
626
- $original_output,
627
- $change_parameters[ $y ]->{$y + 1},
628
- $combination_string,
629
- $combined_data_elements,
630
- $feed_language
631
- );
632
- }
633
-
634
- return $final_output;
635
- }
636
-
637
- /**
638
- * @param $product_data
639
- * @param $combination_string
640
- * @return array
641
- */
642
- protected function get_combined_elements( $product_data, $combination_string ) {
643
- $result = array();
644
- $found_all_data = true;
645
-
646
- $combination_elements = explode( '|', $combination_string );
647
-
648
- if ( false === strpos( $combination_elements[0], 'static#' ) ) {
649
- if ( array_key_exists( $combination_elements[0], $product_data ) ) {
650
- array_push( $result, $product_data[ $combination_elements[0] ] );
651
- } else {
652
- $found_all_data = false;
653
- }
654
- } else {
655
- $element = explode( '#', $combination_elements[0] );
656
- array_push( $result, $element[1] );
657
- }
658
-
659
- for ( $i = 1; $i <= count( $combination_elements ) - 1; $i ++ ) {
660
- $pos = strpos( $combination_elements[ $i ], '#' );
661
- $selector = substr( $combination_elements[ $i ], ( false !== $pos ? $pos + 1 : 0 ) );
662
-
663
- if ( substr( $selector, 0, 7 ) === 'static#' ) {
664
- $selector = explode( '#', $selector );
665
- array_push( $result, $selector[1] );
666
- } elseif ( array_key_exists( $selector, $product_data ) ) {
667
- array_push( $result, $product_data[ $selector ] );
668
- } else {
669
- //array_push( $result, $selector );
670
- $found_all_data = false;
671
- }
672
- }
673
-
674
- if ( $found_all_data ) {
675
- return $result;
676
- } else {
677
- $message = sprintf( 'Missing the data for one or both combined elements of the combination %s in the product with id %s.', $combination_string, $product_data['ID'] );
678
- do_action( 'tvc_feed_generation_message', $this->_feed_data->feedId, $message );
679
- return array();
680
- }
681
- }
682
-
683
- /**
684
- * @param $source_selectors_array
685
- * @param $separators
686
- * @param $row
687
- * @param $array_pos
688
- * @return string
689
- */
690
- protected function make_combined_string( $source_selectors_array, $separators, $row, $array_pos ) {
691
- $combined_string = '';
692
-
693
- foreach ( $source_selectors_array as $source ) {
694
- $split_source = explode( '#', $source );
695
-
696
- // get the separator
697
- $separators_id = count( $split_source ) > 1 && 'static' !== $split_source[0] ? $split_source[0] : 0;
698
- $sep = $separators[ $separators_id ];
699
-
700
- $data_key = count( $split_source ) > 1 && 'static' !== $split_source[0] ? $split_source[1] : $split_source[0];
701
-
702
- if ( ( array_key_exists( $data_key, $row ) && $row[ $data_key ] ) || 'static' === $data_key ) {
703
- if ( 'static' !== $data_key && ! is_array( $row[ $data_key ] ) ) { // not static and no array
704
- $combined_string .= $sep;
705
- $combined_string .= 'static' !== $data_key ? $row[ $data_key ] : $split_source[2];
706
- } elseif ( 'static' === $data_key ) { // static inputs
707
- $static_string = count( $split_source ) > 2 ? $split_source[2] : $split_source[1];
708
- $combined_string .= $sep . $static_string;
709
- } else { // array inputs
710
- $input_array = $row[ $data_key ][ $array_pos ];
711
- $combined_string .= $sep . $input_array;
712
- }
713
- }
714
- }
715
-
716
- return $combined_string;
717
- }
718
-
719
- /**
720
- * get an array with the relations between the WooCommerce fields and the channel fields
721
- *
722
- * @return array
723
- */
724
- public function get_channel_to_woocommerce_field_relations() {
725
- $relations = array();
726
-
727
- foreach ( $this->_feed->attributes as $attribute ) {
728
-
729
- // get the source name except for the category_mapping field
730
- if ( 'category_mapping' !== $attribute->fieldName ) {
731
- $source = $this->get_source_from_attribute( $attribute );
732
- }
733
-
734
- if ( ! empty( $source ) ) {
735
- // correct Google product category source
736
- if ( 'google_product_category' === $attribute->fieldName ) {
737
- $source = 'google_product_category';
738
- }
739
-
740
- // correct Google identifier exists source
741
- if ( 'identifier_exists' === $attribute->fieldName ) {
742
- $source = 'identifier_exists';
743
- }
744
-
745
- // fill the relations array
746
- $a = array(
747
- 'field' => $attribute->fieldName,
748
- 'db' => $source,
749
- );
750
- array_push( $relations, $a );
751
- }
752
- }
753
-
754
- if ( empty( $relations ) ) {
755
- tvc_write_log_file( 'Function get_channel_to_woocommerce_field_relations returned zero relations.' );
756
- }
757
-
758
- return $relations;
759
- }
760
-
761
- /**
762
- * extract the source name from the attribute string
763
- *
764
- * @param array $attribute
765
- *
766
- * @return string
767
- */
768
- protected function get_source_from_attribute( $attribute ) {
769
-
770
- $value_source = property_exists( $attribute, 'value' ) ? $this->get_source_from_attribute_value( $attribute->value ) : '';
771
-
772
- if ( ! empty( $value_source ) ) {
773
- $source = $value_source;
774
- } elseif ( property_exists( $attribute, 'advisedSource' ) && '' !== $attribute->advisedSource ) {
775
- $source = $attribute->advisedSource;
776
- } else {
777
- $source = $attribute->fieldName;
778
- }
779
-
780
- return $source;
781
- }
782
-
783
- /**
784
- * extract the source value from the attribute string
785
- *
786
- * @param string $value
787
- *
788
- * @return string
789
- */
790
- protected function get_source_from_attribute_value( $value ) {
791
- $source = '';
792
-
793
- if ( $value ) {
794
- $value_string = $this->get_source_string( $value );
795
-
796
- $value_object = json_decode( $value_string );
797
-
798
- if ( is_object( $value_object ) && property_exists( $value_object, 'source' ) ) {
799
- $source = $value_object->source;
800
- }
801
- }
802
-
803
- return $source;
804
- }
805
-
806
- /**
807
- * get the value
808
- *
809
- * @param string $value_string
810
- *
811
- * @return string
812
- */
813
- protected function get_source_string( $value_string ) {
814
- $source_string = '';
815
-
816
- if ( ! empty( $value_string ) ) {
817
- $value_object = json_decode( $value_string );
818
-
819
- if ( property_exists( $value_object, 'm' ) && property_exists( $value_object->m[0], 's' ) ) {
820
- $source_string = json_encode( $value_object->m[0]->s );
821
- }
822
- }
823
-
824
- return $source_string;
825
- }
826
-
827
- /**
828
- * makes an xml string of one product including its variations
829
- *
830
- * @param array $data
831
- * @param string $category_name
832
- * @param string $description_name
833
- *
834
- * @return string
835
- */
836
- protected function convert_data_to_xml( $data, $category_name, $description_name, $channel ) {
837
- return $data ? $this->make_xml_string_row( $data, $category_name, $description_name, $channel ) : '';
838
- }
839
-
840
- /**
841
- * makes an xml string for one product
842
- *
843
- * @param array $product Contains all the data from the product.
844
- * @param string $category_name Selected category name.
845
- * @param string $description_name The name of the description.
846
- * @param string $channel Contains the channel id.
847
- *
848
- * @return string
849
- */
850
- protected function make_xml_string_row( $product, $category_name, $description_name, $channel ) {
851
- $product_node_name = function_exists( 'product_node_name' ) ? product_node_name( $channel ) : 'item';
852
- $node_pre_tag_name = function_exists( 'get_node_pretag' ) ? get_node_pretag( $channel ) : 'g:';
853
- $product_node = apply_filters( 'tvc_xml_product_node_name', $product_node_name, $channel );
854
- $node_pre_tag = apply_filters( 'tvc_xml_product_pre_tag_name', $node_pre_tag_name, $channel );
855
- $tags_with_sub_tags = $this->_channel_class->keys_that_have_sub_tags();
856
- $tags_repeated_fields = $this->_channel_class->keys_that_can_be_used_more_than_once();
857
- $sub_keys_for_subs = $this->_channel_class->sub_keys_for_sub_tags();
858
-
859
- $this->_channel_class->add_xml_sub_tags( $product, $sub_keys_for_subs, $tags_with_sub_tags, $node_pre_tag );
860
- $xml_string = "<$product_node>";
861
-
862
- // for each product value item
863
- foreach ( $product as $key => $value ) {
864
- if ( ! is_array( $value ) ) {
865
- $xml_string .= $this->make_xml_string( $key, $value, $category_name, $description_name, $node_pre_tag, $tags_with_sub_tags, $tags_repeated_fields, $channel );
866
- } else {
867
- $xml_string .= $this->make_array_string( $key, $value, $node_pre_tag, $channel );
868
- }
869
- }
870
-
871
- $xml_string .= "</$product_node>";
872
-
873
- return $xml_string;
874
- }
875
-
876
- /**
877
- * makes an csv string of one product including its variations
878
- *
879
- * @param array $data
880
- * @param array $active_fields
881
- * @param string $csv_separator
882
- *
883
- * @return string
884
- */
885
- protected function convert_data_to_csv( $data, $active_fields, $csv_separator ) {
886
- if ( $data ) {
887
- if ( count( $data ) > count( $active_fields ) ) {
888
- $support_class = new TVC_Feed_Support();
889
- $support_class->correct_active_fields_list( $active_fields );
890
- }
891
-
892
- // the first row in a csv file should contain the index, the following rows the data
893
- return $this->make_comma_separated_string_from_data_array( $data, $active_fields, $this->_feed_data->channel, $csv_separator );
894
- } else {
895
- return '';
896
- }
897
- }
898
-
899
- /**
900
- * makes a tab separated string for a tsv file
901
- *
902
- * @param array $data
903
- *
904
- * @return string
905
- */
906
- protected function convert_data_to_tsv( $data ) {
907
- if ( $data ) {
908
- return $this->make_tab_delimited_string_from_data_array( $data );
909
- } else {
910
- return '';
911
- }
912
- }
913
-
914
- /**
915
- * @param $data
916
- * @return string
917
- */
918
- protected function convert_data_to_txt( $data ) {
919
- if ( $data ) {
920
- return $this->make_tab_delimited_string_from_data_array( $data );
921
- } else {
922
- return '';
923
- }
924
- }
925
-
926
- /**
927
- * takes one row data and converts it to a tab delimited string
928
- *
929
- * @param array $row_data
930
- *
931
- * @return string
932
- */
933
- protected function make_tab_delimited_string_from_data_array( $row_data ) {
934
- $row_string = '';
935
-
936
- foreach ( $row_data as $row_item ) {
937
- $a_row_item = ! is_array( $row_item ) ? preg_replace( "/\r|\n/", "", $row_item ) : implode( ', ', $row_item );
938
- $clean_row_item = strip_tags( $a_row_item );
939
- $row_string .= $clean_row_item . "\t";
940
- }
941
-
942
- $row = trim( $row_string ); // removes the tab at the end of the line
943
-
944
- return $row . "\r\n";
945
- }
946
-
947
- /**
948
- * Takes the data for one row and converts it to a comma separated string that fits into the feed.
949
- *
950
- * @param array $row_data Array with the attribute name => attribute data.
951
- * @param array $active_fields Array containing the attributes that are active and need to go into the feed.
952
- * @param string $channel Channel id.
953
- * @param string $separator Requested data separator (default ,).
954
- *
955
- * @return string
956
- */
957
- public function make_comma_separated_string_from_data_array( $row_data, $active_fields, $channel, $separator = ',' ) {
958
- $row_string = '';
959
-
960
- $quotes_not_allowed = channel_requires_no_quotes_on_empty_attributes( $channel );
961
-
962
- // @since 2.11.0 allows choosing another separator for array data.
963
- $separator_for_arrays = apply_filters( 'tvc_separator_for_arrays_in_csv_feed', '|' );
964
-
965
- // Loop through the active attributes.
966
- foreach ( $active_fields as $row_item ) {
967
- if ( array_key_exists( $row_item, $row_data ) ) {
968
- $clean_row_item = ! is_array( $row_data[ $row_item ] ) ? preg_replace( "/\r|\n/", '', $row_data[ $row_item ] ) : implode( $separator_for_arrays, $row_data[ $row_item ] );
969
- } else {
970
- $clean_row_item = '';
971
- }
972
-
973
- $quotes = $quotes_not_allowed && '' === $clean_row_item ? '' : '"';
974
-
975
- $remove_double_quotes_from_string = str_replace( '"', "'", $clean_row_item );
976
- $row_string .= $quotes . $remove_double_quotes_from_string . $quotes . $separator;
977
- }
978
-
979
- $row = rtrim( $row_string, $separator ); // Removes the comma at the end of the line.
980
-
981
- return $row . "\r\n";
982
- }
983
-
984
- /**
985
- * makes the header string for a csv file
986
- *
987
- * @param array $active_fields
988
- * @param string $separator
989
- *
990
- * @return string
991
- */
992
- protected function make_csv_header_string( $active_fields, $separator ) {
993
- $header = implode( $separator, $active_fields );
994
-
995
- return $header . "\r\n";
996
- }
997
-
998
- /**
999
- * make an array of product element strings
1000
- *
1001
- * @param string $key
1002
- * @param array $value
1003
- * @param string $google_node_pre_tag
1004
- * @param string $channel
1005
- *
1006
- * @return string
1007
- */
1008
- protected function make_array_string( $key, $value, $google_node_pre_tag, $channel ) {
1009
- $xml_strings = '';
1010
- $tags_with_sub_tags = $this->_channel_class->keys_that_have_sub_tags();
1011
- $tags_repeated_fields = $this->_channel_class->keys_that_can_be_used_more_than_once();
1012
-
1013
- for ( $i = 0; $i < count( $value ); $i ++ ) {
1014
- $xml_key = 'Extra_Afbeeldingen' === $key ? 'Extra_Image_' . ( $i + 1 ) : $key; // required for Beslist.nl
1015
- $xml_strings .= $this->make_xml_string( $xml_key, $value[ $i ], '', '', $google_node_pre_tag, $tags_with_sub_tags, $tags_repeated_fields, $channel );
1016
- }
1017
-
1018
- return $xml_strings;
1019
- }
1020
-
1021
- /**
1022
- * Generates an xml node.
1023
- *
1024
- * Returns an xml node for a product tag and uses the product data to make the node.
1025
- *
1026
- * @since 1.1.0
1027
- * @access public
1028
- *
1029
- * @param string $key Note id.
1030
- * @param string $xml_value Note value.
1031
- * @param string $category_name Category name.
1032
- * @param string $description_name Description name.
1033
- * @param string $google_node_pre_tag Pre node tag.
1034
- * @param array $tags_with_sub_tags Array with tags that have a sub tag construction.
1035
- * @param array $tags_repeated_fields Array with tags that are allowed to be placed in the feed more than once
1036
- * @param string $channel Selected channel id.
1037
- *
1038
- * @return string Node string in xml format eg. <id>43</id>.
1039
- */
1040
- protected function make_xml_string( $key, $xml_value, $category_name, $description_name, $google_node_pre_tag, $tags_with_sub_tags, $tags_repeated_fields, $channel ) {
1041
- $xml_string = '';
1042
- $repeated_field = ! in_array( $key, $tags_repeated_fields ) ? false : true;
1043
- $subtag_sep = apply_filters( 'tvc_sub_tag_separator', '||' );
1044
-
1045
- if ( substr( $xml_value, 0, 5 ) === '!sub:' ) {
1046
- $sub_array = explode( "|", $xml_value );
1047
- $sa = $sub_array[0];
1048
- $st = explode( ":", $sa );
1049
- $sub_tag = $st[1];
1050
- $xml_value = "<$google_node_pre_tag$sub_tag>$sub_array[1]</$google_node_pre_tag$sub_tag>";
1051
- }
1052
-
1053
- if ( $repeated_field && ! is_array( $xml_value ) ) {
1054
- $xml_value = explode( $subtag_sep, $xml_value );
1055
- }
1056
-
1057
- // keys to be added in a CDATA bracket to the xml feed
1058
- $cdata_keys = apply_filters( 'tvc_cdata_keys', array(
1059
- $category_name,
1060
- $description_name,
1061
- 'title'
1062
- ) );
1063
-
1064
- if ( ! is_array( $xml_value ) && ! in_array( $key, $tags_with_sub_tags ) ) {
1065
- if ( in_array( $key, $cdata_keys ) ) {
1066
- $xml_value = $this->convert_to_character_data_string( $xml_value ); // put in a ![CDATA[...]] bracket
1067
- } else {
1068
- $xml_value = $this->convert_to_xml_value( $xml_value );
1069
- }
1070
- }
1071
-
1072
- $google_suffix_exceptions = apply_filters( 'tvc_google_suffux_exceptions', array(
1073
- 'title',
1074
- 'link'
1075
- ) );
1076
-
1077
- // as of October 2016 google removed the need for a g: suffix only for title and link. Facebook still requires it
1078
- if ( in_array( $key, $google_suffix_exceptions ) ) {
1079
- $google_node_pre_tag = $channel === '1' ? '' : $google_node_pre_tag;
1080
- }
1081
-
1082
- if ( $key !== '' ) {
1083
- if ( is_array( $xml_value ) && $repeated_field ) {
1084
- foreach ( $xml_value as $value_item ) {
1085
- $xml_string .= $this->add_xml_string( $key, $value_item, $google_node_pre_tag );
1086
- }
1087
- } else {
1088
- $xml_string = $this->add_xml_string( $key, $xml_value, $google_node_pre_tag );
1089
- }
1090
- }
1091
-
1092
- return $xml_string;
1093
- }
1094
-
1095
- /**
1096
- * Generates a single xml line string
1097
- *
1098
- * @since 1.9.0
1099
- *
1100
- * @param string $key
1101
- * @param string $xml_value
1102
- * @param string $google_node_pre_tag
1103
- *
1104
- * @return string
1105
- */
1106
- protected function add_xml_string( $key, $xml_value, $google_node_pre_tag ) {
1107
- $not_allowed_characters = array( ' ', '-' );
1108
- $clean_key = str_replace( $not_allowed_characters, '_', $key );
1109
-
1110
- return "<$google_node_pre_tag$clean_key>$xml_value</$google_node_pre_tag$clean_key>";
1111
- }
1112
-
1113
- /**
1114
- * converts an ordinary xml string into a CDATA string
1115
- *
1116
- * @param string $string
1117
- *
1118
- * @return string
1119
- */
1120
- protected function convert_to_character_data_string( $string ) {
1121
- return "<![CDATA[ $string ]]>";
1122
- }
1123
-
1124
- /**
1125
- * can be overridden by a channel specific function in its class-feed.php
1126
- *
1127
- * @since 1.9.0
1128
- *
1129
- * @param $product array Pointer to the product data.
1130
- * @param $sub_keys_for_subs array Array with the tags that can be placed in the feed as a sub tag (eg. <loyalty_points><ratio>).
1131
- * @param $tags_repeated_fields array Array with tags of fields that can have more than one instance in the feed.
1132
- * @param $node_pre_tag string The channel dependant pre tag (eg. g: for Google Feeds).
1133
- *
1134
- * @return array The product with the correct xml tags.
1135
- */
1136
- public function add_xml_sub_tags( &$product, $sub_keys_for_subs, $tags_repeated_fields, $node_pre_tag ) {
1137
- $sub_tags = array_intersect_key( $product, array_flip( $sub_keys_for_subs ) );
1138
-
1139
- if ( count( $sub_tags ) < 1 ) {
1140
- return $product;
1141
- }
1142
-
1143
- $subtag_sep = apply_filters( 'tvc_sub_tag_separator', '||' );
1144
- $tags_value = array();
1145
-
1146
- foreach ( $sub_tags as $key => $value ) {
1147
- $split = explode( '-', $key );
1148
-
1149
- if ( in_array( $split[0], $tags_repeated_fields ) ) {
1150
- $tags_counter = 0;
1151
- $value_array = is_array( $value ) ? $value : explode( $subtag_sep, $value );
1152
-
1153
- foreach ( $value_array as $sub_value ) {
1154
- $prev_string = array_key_exists( $tags_counter, $tags_value ) ? $tags_value[ $tags_counter ] : '';
1155
- $tags_value[ $tags_counter ] = $prev_string . '<' . $node_pre_tag . $split[1] . '>' . $sub_value . '</' . $node_pre_tag . $split[1] . '>';
1156
- $tags_counter ++;
1157
- }
1158
- } else {
1159
- $tags_value = array_key_exists( $split[0], $product ) ? $product[ $split[0] ] : '';
1160
- $tags_value .= '<' . $node_pre_tag . $split[1] . '>' . $value . '</' . $node_pre_tag . $split[1] . '>';
1161
- }
1162
-
1163
- unset( $product[ $key ] );
1164
- $product[ $split[0] ] = $tags_value;
1165
- }
1166
-
1167
- return $product;
1168
- }
1169
-
1170
- /**
1171
- * can be overridden by a channel specific function in its class-feed.php
1172
- *
1173
- * @since 1.9.0
1174
- *
1175
- * @return array
1176
- */
1177
- public function keys_that_have_sub_tags() {
1178
- return array();
1179
- }
1180
-
1181
- /**
1182
- * can be overridden by a channel specific function in its class-feed.php
1183
- *
1184
- * @since 2.1.0
1185
- *
1186
- * @return array
1187
- */
1188
- public function sub_keys_for_sub_tags() {
1189
- return array();
1190
- }
1191
-
1192
- /**
1193
- * can be overridden by a channel specific function in its class-feed.php
1194
- *
1195
- * @since 1.9.0
1196
- *
1197
- * @return array
1198
- */
1199
- public function keys_that_can_be_used_more_than_once() {
1200
- return array();
1201
- }
1202
-
1203
- /**
1204
- * replaces certain characters to get a valid xml value
1205
- *
1206
- * @param string $value_string
1207
- *
1208
- * @return string
1209
- */
1210
- public function convert_to_xml_value( $value_string ) {
1211
- $string_without_tags = strip_tags( $value_string );
1212
- $prep_string = str_replace(
1213
- array(
1214
- '&amp;',
1215
- '&lt;',
1216
- '&gt;',
1217
- '&apos;',
1218
- '&quot;',
1219
- '&nbsp;',
1220
- ),
1221
- array(
1222
- '&',
1223
- '<',
1224
- '>',
1225
- '\'',
1226
- '"',
1227
- 'nbsp;',
1228
- ),
1229
- $string_without_tags
1230
- );
1231
-
1232
- $clean_xml_string = str_replace(
1233
- array(
1234
- '&',
1235
- '<',
1236
- '>',
1237
- '\'',
1238
- '"',
1239
- 'nbsp;',
1240
- '`',
1241
- ),
1242
- array(
1243
- '&amp;',
1244
- '&lt;',
1245
- '&gt;',
1246
- '&apos;',
1247
- '&quot;',
1248
- ' ',
1249
- '',
1250
- ),
1251
- $prep_string
1252
- );
1253
-
1254
- return $clean_xml_string;
1255
- }
1256
-
1257
- /**
1258
- * get formal woocommerce custom fields data
1259
- *
1260
- * @param string $id
1261
- * @param string $parent_product_id @since 2.0.9
1262
- * @param string $field
1263
- *
1264
- * @return string
1265
- */
1266
- protected function get_custom_field_data( $id, $parent_product_id, $field ) {
1267
- $custom_string = '';
1268
- $taxonomy = 'pa_' . $field;
1269
- $custom_values = get_the_terms( $id, $taxonomy );
1270
-
1271
- if ( ! $custom_values && 0 !== $parent_product_id ) {
1272
- $custom_values = get_the_terms( $parent_product_id, $taxonomy );
1273
- }
1274
-
1275
- if ( $custom_values ) {
1276
- foreach ( $custom_values as $custom_value ) {
1277
- $custom_string .= $custom_value->name . ', ';
1278
- }
1279
- }
1280
-
1281
- return $custom_string ? substr( $custom_string, 0, - 2 ) : '';
1282
- }
1283
-
1284
- /**
1285
- * get third party custom field data
1286
- *
1287
- * @since 1.6.0
1288
- *
1289
- * @param string $feed_id
1290
- * @param string $parent_product_id @since 2.0.9
1291
- * @param string $field
1292
- *
1293
- * @return string
1294
- */
1295
- protected function get_third_party_custom_field_data( $feed_id, $parent_product_id, $field ) {
1296
- $result = '';
1297
- $product_brand = '';
1298
-
1299
- // YITH Brands plugin
1300
- if ( get_option( 'yith_wcbr_brands_label' ) === $field ) { // YITH Brands plugin active
1301
- if ( has_term( '', 'yith_product_brand', $feed_id ) ) {
1302
- $product_brand = get_the_terms( $feed_id, 'yith_product_brand' );
1303
- }
1304
-
1305
- if ( ! $product_brand && 0 !== $parent_product_id && has_term( '', 'yith_product_brand', $parent_product_id ) ) {
1306
- $product_brand = get_the_terms( $parent_product_id, 'yith_product_brand' );
1307
- }
1308
-
1309
- if ( $product_brand && ! is_wp_error( $product_brand ) ) {
1310
- foreach ( $product_brand as $brand ) {
1311
- $result .= $brand->name . ', ';
1312
- }
1313
- }
1314
- }
1315
-
1316
- // WooCommerce Brands plugin
1317
- if (
1318
- in_array(
1319
- 'woocommerce-brands/woocommerce-brands.php',
1320
- apply_filters(
1321
- 'active_plugins',
1322
- get_option( 'active_plugins' )
1323
- )
1324
- )
1325
- ) {
1326
-
1327
- if ( has_term( '', 'product_brand', $feed_id ) ) {
1328
- $product_brand = get_the_terms( $feed_id, 'product_brand' );
1329
- }
1330
-
1331
- if ( ! $product_brand && 0 !== $parent_product_id && has_term( '', 'product_brand', $parent_product_id ) ) {
1332
- $product_brand = get_the_terms( $parent_product_id, 'product_brand' );
1333
- }
1334
-
1335
- if ( $product_brand && ! is_wp_error( $product_brand ) ) {
1336
- foreach ( $product_brand as $brand ) {
1337
- $result .= $brand->name . ', ';
1338
- }
1339
- } elseif ( is_wp_error( $product_brand ) ) {
1340
- do_action( 'tvc_feed_generation_warning', $feed_id, $product_brand ); // @since 2.3.0
1341
- }
1342
- }
1343
-
1344
- return $result ? substr( $result, 0, - 2 ) : '';
1345
- }
1346
-
1347
- /**
1348
- * adds data to the product that require a procedure to get
1349
- *
1350
- * @param object $product
1351
- * @param array $active_field_names
1352
- * @param string $selected_language
1353
- * @param string $feed_id
1354
- *
1355
- * @return bool
1356
- */
1357
- protected function add_procedural_data( &$product, $active_field_names, $selected_language, $feed_id ) {
1358
- $woocommerce_product = wc_get_product( $product->ID );
1359
-
1360
- if ( false === $woocommerce_product ) {
1361
- $msg = sprintf( 'Failed to get the WooCommerce products procedural data from product %s.', $product->ID );
1362
- do_action( 'tvc_feed_generation_warning', $feed_id, $msg ); // @since 2.3.0
1363
-
1364
- return false;
1365
- }
1366
-
1367
- $woocommerce_parent_id = $woocommerce_product->get_parent_id();
1368
- $woocommerce_product_parent = $woocommerce_product && ( $woocommerce_product->is_type( 'variable' ) ||
1369
- $woocommerce_product->is_type( 'variation' ) ) ? wc_get_product( $woocommerce_parent_id ) : null;
1370
-
1371
- if ( false === $woocommerce_product_parent || null === $woocommerce_product_parent ) {
1372
- // this product has no parent id so it is possible this is the main of a variable product
1373
- // So to make sure the general variation data like min_variation_price are available, copy the product
1374
- // in the parent product
1375
- $woocommerce_product_parent = $woocommerce_product;
1376
- }
1377
-
1378
- if ( in_array( 'shipping_class', $active_field_names ) ) {
1379
- if ( $woocommerce_product_parent ) {
1380
- $product->shipping_class = $woocommerce_product_parent->get_shipping_class();
1381
- } elseif ( $woocommerce_product ) {
1382
- $product->shipping_class = $woocommerce_product->get_shipping_class();
1383
- }
1384
- }
1385
-
1386
- if ( in_array( 'permalink', $active_field_names ) ) {
1387
- $permalink = get_permalink( $product->ID );
1388
- if ( false === $permalink && 0 !== $woocommerce_parent_id ) {
1389
- $permalink = get_permalink( $woocommerce_parent_id );
1390
- }
1391
-
1392
- // WPML support
1393
- $product->permalink = has_filter( 'tvc_get_wpml_permalink' )
1394
- ? apply_filters( 'tvc_get_wpml_permalink', $permalink, $selected_language ) : $permalink;
1395
- }
1396
-
1397
- if ( in_array( 'attachment_url', $active_field_names ) ) {
1398
- // WPML support -> Returns an elements ID in the selected language.
1399
- $object_id = has_filter( 'wpml_object_id' ) ? apply_filters( 'wpml_object_id', $product->ID, 'attachment', true ) : $product->ID;
1400
- $attachment_url = wp_get_attachment_url( get_post_thumbnail_id( $object_id ) );
1401
-
1402
- // If the attachment url is empty and the product has a parent try getting the attachment url of the parent.
1403
- if ( false === $attachment_url && 0 !== $woocommerce_parent_id ) {
1404
- // WPML support -> Returns an elements ID in the selected language.
1405
- $parent_object_id = has_filter( 'wpml_object_id' ) ? apply_filters( 'wpml_object_id', $woocommerce_parent_id, 'attachment', true ) : $woocommerce_parent_id;
1406
- $attachment_url = wp_get_attachment_url( get_post_thumbnail_id( $parent_object_id ) );
1407
- }
1408
-
1409
- // WPML support -> Filter the permalink and convert it to a language-specific permalink.
1410
- $product->attachment_url = has_filter( 'tvc_get_wpml_permalink' )
1411
- ? apply_filters( 'tvc_get_wpml_permalink', $attachment_url, $selected_language ) : $attachment_url;
1412
- }
1413
-
1414
- if ( in_array( 'product_cat', $active_field_names ) ) {
1415
- $product->product_cat = TVC_Taxonomies::get_shop_categories( $product->ID );
1416
- if ( '' === $product->product_cat && 0 !== $woocommerce_parent_id ) {
1417
- $product->product_cat = TVC_Taxonomies::get_shop_categories( $woocommerce_parent_id );
1418
- }
1419
- }
1420
-
1421
- if ( in_array( 'product_cat_string', $active_field_names ) ) {
1422
- $product->product_cat_string = TVC_Taxonomies::make_shop_taxonomies_string( $product->ID );
1423
- if ( '' === $product->product_cat_string && 0 !== $woocommerce_parent_id ) {
1424
- $product->product_cat_string = TVC_Taxonomies::make_shop_taxonomies_string( $woocommerce_parent_id );
1425
- }
1426
- }
1427
-
1428
- if ( in_array( 'last_update', $active_field_names ) ) {
1429
- $product->last_update = date( 'Y-m-d H:i:s', current_time( 'timestamp' ) );
1430
- }
1431
-
1432
- if ( in_array( '_wp_attachement_metadata', $active_field_names ) ) {
1433
- $attachment_id = 0 === $woocommerce_parent_id ? $product->ID : $woocommerce_parent_id;
1434
- $product->_wp_attachement_metadata = $this->get_product_image_gallery( $attachment_id, $selected_language );
1435
- }
1436
-
1437
- if ( in_array( 'product_tags', $active_field_names ) ) {
1438
- $product->product_tags = $this->get_product_tags( $product->ID );
1439
- }
1440
-
1441
- if ( in_array( 'wc_currency', $active_field_names ) ) {
1442
- // WPML support
1443
- $product->wc_currency = has_filter( 'tvc_get_wpml_currency' )
1444
- ? apply_filters( 'tvc_get_wpml_currency', get_woocommerce_currency(), $selected_language ) : get_woocommerce_currency();
1445
- }
1446
-
1447
- if ( $woocommerce_product_parent && ( $woocommerce_product_parent->is_type( 'variable' ) || $woocommerce_product_parent->is_type( 'variation' ) ) ) {
1448
- if ( in_array( '_min_variation_price', $active_field_names ) ) {
1449
- $product->_min_variation_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_price(), $selected_language ) : '';
1450
- }
1451
-
1452
- if ( in_array( '_max_variation_price', $active_field_names ) ) {
1453
- $product->_max_variation_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_price( 'max' ), $selected_language ) : '';
1454
- }
1455
-
1456
- if ( in_array( '_min_variation_regular_price', $active_field_names ) ) {
1457
- $product->_min_variation_regular_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_regular_price(), $selected_language ) : '';
1458
- }
1459
-
1460
- if ( in_array( '_max_variation_regular_price', $active_field_names ) ) {
1461
- $product->_max_variation_regular_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_regular_price( 'max' ), $selected_language ) : '';
1462
- }
1463
-
1464
- if ( in_array( '_min_variation_sale_price', $active_field_names ) ) {
1465
- $product->_min_variation_sale_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_sale_price(), $selected_language ) : '';
1466
- }
1467
-
1468
- if ( in_array( '_max_variation_sale_price', $active_field_names ) ) {
1469
- $product->_max_variation_sale_price = $woocommerce_product_parent ? tvc_prep_money_values( $woocommerce_product_parent->get_variation_sale_price( 'max' ), $selected_language ) : '';
1470
- }
1471
-
1472
- if ( in_array( 'item_group_id', $active_field_names ) ) {
1473
- $parent_sku = $woocommerce_product_parent ? $woocommerce_product_parent->get_sku() : '';
1474
-
1475
- if ( $parent_sku ) {
1476
- $product->item_group_id = $parent_sku; // best practise
1477
- } elseif ( $woocommerce_product_parent && $woocommerce_parent_id ) {
1478
- $product->item_group_id = 'GID' . $woocommerce_parent_id;
1479
- } else {
1480
- $product->item_group_id = '';
1481
- }
1482
- }
1483
- } else {
1484
- if ( ! $woocommerce_product_parent->is_type( 'simple' ) && ! $woocommerce_product_parent->is_type( 'grouped' )
1485
- && ! $woocommerce_product_parent->is_type( 'virtual' ) && ! $woocommerce_product_parent->is_type( 'downloadable' )
1486
- && ! $woocommerce_product_parent->is_type( 'external' ) ) {
1487
- $msg = sprintf(
1488
- 'Product type of product %s could not be identified. The products shows as type %s',
1489
- $product->ID,
1490
- function_exists( 'get_product_type' ) ? get_product_type( $product->ID ) : 'unknown'
1491
- );
1492
- do_action( 'tvc_feed_generation_warning', $feed_id, $msg ); // @since 2.3.0
1493
- }
1494
- }
1495
-
1496
- // @since 2.1.4
1497
- if ( in_array( 'empty', $active_field_names ) ) {
1498
- $product->empty = '';
1499
- }
1500
-
1501
- // @since 2.2.0
1502
- if ( in_array( 'product_type', $active_field_names ) ) {
1503
- $product->type = $woocommerce_product ? $woocommerce_product->get_type() : 'unknown';
1504
- }
1505
-
1506
- // @since 2.2.0
1507
- if ( in_array( 'product_variation_title_without_attributes', $active_field_names ) ) {
1508
- $product_title = get_post_field( 'post_title', $product->ID );
1509
-
1510
- if ( false !== strpos( $product_title, ' - ' ) ) { // assuming that the woocommerce_product_variation_title_attributes_separator is ' - '
1511
- $title_parts = explode( ' - ', $product_title );
1512
- $product_title = $title_parts[0];
1513
- }
1514
-
1515
- $product->product_variation_title_without_attributes = $product_title;
1516
- }
1517
-
1518
- $woocommerce_product = null;
1519
-
1520
- return true;
1521
- }
1522
-
1523
- /**
1524
- * get additional images
1525
- *
1526
- * @param string $post_id
1527
- * @param string $selected_language
1528
- *
1529
- * @return array|string
1530
- */
1531
- protected function get_product_image_gallery( $post_id, $selected_language ) {
1532
- $image_urls = array();
1533
- $images = 1;
1534
- $max_nr_images = 10;
1535
-
1536
- $prdct = wc_get_product( $post_id );
1537
- $attachment_ids = $prdct->get_gallery_image_ids();
1538
-
1539
- foreach ( $attachment_ids as $attachment_id ) {
1540
- $link = wp_get_attachment_url( $attachment_id );
1541
-
1542
- // WPML support
1543
- $image_link = has_filter( 'tvc_get_wpml_permalink' )
1544
- ? apply_filters( 'tvc_get_wpml_permalink', $link, $selected_language ) : $link;
1545
-
1546
- // correct baseurl for https if required
1547
- if ( is_ssl() ) {
1548
- $url = str_replace( 'http://', 'https://', $image_link );
1549
- } else {
1550
- $url = $image_link;
1551
- }
1552
-
1553
- array_push( $image_urls, $url );
1554
- $images ++;
1555
-
1556
- if ( $images > $max_nr_images ) {
1557
- break;
1558
- }
1559
- }
1560
-
1561
- return ! empty( $image_urls ) ? $image_urls : '';
1562
- }
1563
-
1564
- protected function get_product_tags( $id ) {
1565
- $product_tags_string = '';
1566
- $product_tag_values = get_the_terms( $id, 'product_tag' );
1567
- $post_tag_values = get_the_tags( $id );
1568
-
1569
- if ( $product_tag_values ) {
1570
- foreach ( $product_tag_values as $product_tag ) {
1571
- $product_tags_string .= $product_tag->name . ', ';
1572
- }
1573
- }
1574
-
1575
- if ( $post_tag_values ) {
1576
- foreach ( $post_tag_values as $post_tag ) {
1577
- $product_tags_string .= $post_tag->name . ', ';
1578
- }
1579
- }
1580
-
1581
- return $product_tags_string ? substr( $product_tags_string, 0, - 2 ) : '';
1582
- }
1583
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/application/tvc-feed-processor-functions.php DELETED
@@ -1,107 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * @package TVC Product Review Feed Manager/Functions
5
- * @version 1.0.0
6
- */
7
-
8
- if ( ! defined( 'ABSPATH' ) ) {
9
- exit;
10
- }
11
-
12
- trait TVC_Feed_Processor_Functions {
13
-
14
- /**
15
- * Adds a string to the feed
16
- *
17
- * @param array $line_data
18
- *
19
- * @return boolean
20
- */
21
- private function add_file_format_line_to_feed( $line_data ) {
22
- return false !== file_put_contents( $this->_feed_file_path, $line_data['file_format_line'], FILE_APPEND ) ? true : false;
23
- }
24
-
25
- /**
26
- * Adds an error message to the feed
27
- *
28
- * @param array $error_message_data
29
- *
30
- * @return boolean
31
- */
32
- private function add_error_message_to_feed( $error_message_data ) {
33
- return false !== file_put_contents( $this->_feed_file_path, $error_message_data['feed_line_message'], FILE_APPEND ) ? true : false;
34
- }
35
-
36
- /**
37
- * register the update in the database
38
- *
39
- * @param string $feed_id
40
- * @param string $feed_name
41
- * @param string $nr_products
42
- * @param string $status
43
- */
44
- private function register_feed_update( $feed_id, $feed_name, $nr_products, $status = null ) {
45
- $data_class = new TVC_Data();
46
-
47
- // register the update and update the feed Last Change time
48
- $data_class->update_feed_data( $feed_id, tvc_get_file_url( $feed_name ), $nr_products );
49
-
50
- $actual_status = $status ? $status : $data_class->get_feed_status( $feed_id );
51
-
52
- if ( '4' !== $actual_status && '5' !== $actual_status && '6' !== $actual_status ) { // no errors
53
- $data_class->update_feed_status( $feed_id, intval( $status ) ); // put feed on status hold if no errors are reported
54
- }
55
- }
56
-
57
- /**
58
- * @param $product_id
59
- * @param $parent_product_id
60
- * @param $post_columns_query_string
61
- * @return array|mixed|object|void|null
62
- */
63
- private function get_products_main_data( $product_id, $parent_product_id, $post_columns_query_string ) {
64
- $queries_class = new TVC_Queries();
65
- $prep_meta_class = new TVC_Feed_Value_Editors();
66
-
67
- $product_data = $queries_class->read_post_data( $product_id, $post_columns_query_string );
68
-
69
- // WPML support
70
- if ( has_filter( 'wpml_translation' ) ) {
71
- $product_data = apply_filters( 'wpml_translation', $product_data, $this->_feed_data->language );
72
- }
73
-
74
- // parent ids are required to get the main data from product variations
75
- $meta_parent_ids = 0 !== $parent_product_id ? array( $parent_product_id ) : $this->get_meta_parent_ids( $product_id );
76
-
77
- array_unshift( $meta_parent_ids, $product_id ); // add the product id to the parent ids
78
-
79
- $meta_data = $queries_class->read_meta_data( $product_id, $parent_product_id, $meta_parent_ids, $this->_pre_data['database_fields']['meta_fields'] );
80
-
81
- foreach ( $meta_data as $meta ) {
82
- $meta_value = $prep_meta_class->prep_meta_values( $meta, $this->_feed_data->language );
83
-
84
- if ( property_exists( $product_data, $meta->meta_key ) ) {
85
- $meta_key = $meta->meta_key;
86
-
87
- if ( '' === $product_data->$meta_key ) {
88
- $product_data = (object) array_merge( (array) $product_data, array( $meta->meta_key => $meta_value ) );
89
- }
90
- } else {
91
- $product_data = (object) array_merge( (array) $product_data, array( $meta->meta_key => $meta_value ) );
92
- }
93
- }
94
-
95
- foreach ( $this->_pre_data['database_fields']['active_custom_fields'] as $field ) {
96
- $product_data->{$field} = $this->get_custom_field_data( $product_data->ID, $parent_product_id, $field );
97
- }
98
-
99
- foreach ( $this->_pre_data['database_fields']['third_party_custom_fields'] as $third_party_field ) {
100
- $product_data->{$third_party_field} = $this->get_third_party_custom_field_data( $product_data->ID, $parent_product_id, $third_party_field );
101
- }
102
-
103
- $this->add_procedural_data( $product_data, $this->_pre_data['column_names'], $this->_feed_data->language, $this->_feed_data->feedId );
104
-
105
- return $product_data;
106
- }
107
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/class-enhanced-ecommerce-google-analytics-activator.php CHANGED
File without changes
includes/class-enhanced-ecommerce-google-analytics-deactivator.php CHANGED
File without changes
includes/class-enhanced-ecommerce-google-analytics-i18n.php CHANGED
File without changes
includes/class-enhanced-ecommerce-google-analytics-loader.php CHANGED
File without changes
includes/class-enhanced-ecommerce-google-analytics.php CHANGED
@@ -27,10 +27,6 @@
27
  * @subpackage Enhanced_Ecommerce_Google_Analytics/includes
28
  * @author Chiranjiv Pathak <chiranjiv@tatvic.com>
29
  */
30
-
31
-
32
-
33
-
34
  class Enhanced_Ecommerce_Google_Analytics {
35
 
36
  /**
@@ -113,8 +109,63 @@ class Enhanced_Ecommerce_Google_Analytics {
113
  * The class responsible for defining internationalization functionality
114
  * of the plugin.
115
  */
116
- require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-enhanced-ecommerce-google-analytics-i18n.php';
117
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
118
  /**
119
  * The class responsible for defining all actions that occur in the admin area.
120
  */
@@ -173,7 +224,6 @@ class Enhanced_Ecommerce_Google_Analytics {
173
  * @access private
174
  */
175
  private function define_public_hooks() {
176
-
177
  $plugin_public = new Enhanced_Ecommerce_Google_Analytics_Public( $this->get_plugin_name(), $this->get_version() );
178
  $this->loader->add_action("wp_head", $plugin_public, "ee_settings");
179
  $this->loader->add_action("wp_footer", $plugin_public, "t_products_impre_clicks");
@@ -252,7 +302,7 @@ class Enhanced_Ecommerce_Google_Analytics {
252
  $setting_url = 'admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=general_settings';
253
  $links[] = '<a href="' . get_admin_url(null, $setting_url) . '">Settings</a>';
254
  $links[] = '<a href="https://wordpress.org/plugins/enhanced-e-commerce-for-woocommerce-store/#faq" target="_blank">FAQ</a>';
255
- $links[] = '<a href="http://plugins.tatvic.com/downloads/EE-Woocommerce-Plugin-Documentation.pdf" target="_blank">Documentation</a>';
256
  $links[] = '<a href="https://1.envato.market/Yvn3R" target="_blank"><b>Upgrade to Premium</b></a>';
257
  return $links;
258
  }
27
  * @subpackage Enhanced_Ecommerce_Google_Analytics/includes
28
  * @author Chiranjiv Pathak <chiranjiv@tatvic.com>
29
  */
 
 
 
 
30
  class Enhanced_Ecommerce_Google_Analytics {
31
 
32
  /**
109
  * The class responsible for defining internationalization functionality
110
  * of the plugin.
111
  */
112
+ require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-enhanced-ecommerce-google-analytics-i18n.php';
113
+ // Feed Manager Files
114
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-admin-page.php';
115
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/tvc-admin-menu-functions.php';
116
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/tvc-admin-functions.php';
117
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/setup/class-tvc-database-management.php';
118
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/setup/class-tvc-folders.php';
119
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/setup/class-tvc-prepare-taxonomy.php';
120
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-admin-page.php';
121
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-add-options-page.php';
122
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-main-admin-page.php';
123
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-list-table.php';
124
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-queries.php';
125
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/elements/class-tvc-form-element.php';
126
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-options-page.php';
127
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-tab.php';
128
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/abstract-tvc-main-input-wrapper.php';
129
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-product-feed-main-input-wrapper.php';
130
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/abstract-tvc-attribute-mapping-wrapper.php';
131
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-product-feed-attribute-mapping-wrapper.php';
132
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/elements/class-tvc-main-input-selector-element.php';
133
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-feed-form-control.php';
134
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-file.php';
135
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-data.php';
136
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/elements/class-tvc-attribute-selector-element.php';
137
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/elements/class-tvc-category-selector-element.php';
138
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/abstract-tvc-category-wrapper.php';
139
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-product-feed-category-wrapper.php';
140
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/tvc-url-functions.php';
141
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-i18n-scripts.php';
142
+ // require_once plugin_dir_path(dirname(__FILE__)) . 'includes/user-interface/class-tvc-product-feed-page.php';
143
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-ajax-calls.php';
144
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-ajax-data.php';
145
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-ajax-file.php';
146
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-backup.php';
147
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-channel.php';
148
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-channel-ftp.php';
149
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-feed-crud-handler.php';
150
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-taxonomies.php';
151
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/data/class-tvc-variations.php';
152
+ //Application folder include
153
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-feed-queries.php';
154
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-email.php';
155
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-feed-value-editors.php';
156
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/tvc-cron-functions.php';
157
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/tvc-support-fields.php';
158
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/libraries/tvc-async-request.php';
159
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/libraries/tvc-background-process.php';
160
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/tvc-feed-processing-support.php';
161
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/tvc-feed-processor-functions.php';
162
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-feed-processor.php';
163
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-feed-support.php';
164
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-feed-controller.php';
165
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-feed-master.php';
166
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/class-tvc-schedules.php';
167
+ //require_once plugin_dir_path(dirname(__FILE__)) . 'includes/application/google/class-feed.php';
168
+ require_once plugin_dir_path(dirname(__FILE__)) . 'includes/class-tvc-register-scripts.php';
169
  /**
170
  * The class responsible for defining all actions that occur in the admin area.
171
  */
224
  * @access private
225
  */
226
  private function define_public_hooks() {
 
227
  $plugin_public = new Enhanced_Ecommerce_Google_Analytics_Public( $this->get_plugin_name(), $this->get_version() );
228
  $this->loader->add_action("wp_head", $plugin_public, "ee_settings");
229
  $this->loader->add_action("wp_footer", $plugin_public, "t_products_impre_clicks");
302
  $setting_url = 'admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=general_settings';
303
  $links[] = '<a href="' . get_admin_url(null, $setting_url) . '">Settings</a>';
304
  $links[] = '<a href="https://wordpress.org/plugins/enhanced-e-commerce-for-woocommerce-store/#faq" target="_blank">FAQ</a>';
305
+ $links[] = '<a href="http://plugins.tatvic.com/help-center/Installation-Manual.pdf" target="_blank">Documentation</a>';
306
  $links[] = '<a href="https://1.envato.market/Yvn3R" target="_blank"><b>Upgrade to Premium</b></a>';
307
  return $links;
308
  }
includes/class-tvc-register-scripts.php CHANGED
@@ -22,7 +22,7 @@ if ( ! class_exists( 'TVC_Register_Scripts' ) ) :
22
  $this->_version_stamp = defined( 'WP_DEBUG' ) && WP_DEBUG ? time() : $premium_version_nr . '1.0';
23
  $this->_js_min = defined( 'WP_DEBUG' ) && WP_DEBUG ? '' : '.min';
24
  // add hooks
25
- add_action( 'admin_enqueue_scripts', array( $this, 'tvc_register_required_scripts' ) );
26
  add_action( 'admin_enqueue_scripts', array( $this, 'tvc_register_required_nonce' ) );
27
  // only load the next hooks when on the Settings page
28
  if ( tvc_on_plugins_settings_page() ) {
@@ -42,8 +42,8 @@ if ( ! class_exists( 'TVC_Register_Scripts' ) ) :
42
  $screen = get_current_screen();
43
 
44
  if($screen->id == 'toplevel_page_aga-envato-api' || $screen->id == 'aga-google-shopping_page_tvc-product-feed-manager' || $screen->id == 'aga-google-shopping_page_tvc-configuration-page'){
45
- wp_register_style("tvc_gmc_style-1", ENHANCAD_PLUGIN_URL . '/admin/css/style.css');
46
- wp_enqueue_style( "tvc_gmc_style-1");
47
  wp_register_style("tvc_gmc_style-2", ENHANCAD_PLUGIN_URL . '/css/style.css');
48
  wp_enqueue_style( "tvc_gmc_style-2");
49
  wp_register_style("tvc-product-feed-manager-1", ENHANCAD_PLUGIN_URL . '/css/actionable-google-analytics-admin.css');
@@ -128,14 +128,14 @@ if ( ! class_exists( 'TVC_Register_Scripts' ) ) :
128
  */
129
  public function tvc_register_required_options_page_scripts() {
130
  // enqueue notice handling script
131
- wp_enqueue_style( 'tvc-product-feed-manager-setting', ENHANCAD_PLUGIN_URL . '/css/tvc_setting-page' . $this->_js_min . '.css', '', $this->_version_stamp, 'screen' );
132
- wp_enqueue_script( 'tvc_message-handling-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_msg_events' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
133
- wp_enqueue_style('font_awesome','//use.fontawesome.com/releases/v5.0.13/css/all.css');
134
  //==wp_enqueue_script( 'tvc_backup-list-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_backup-list'. $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp,'screen' );
135
  wp_enqueue_script( 'tvc_data-handling-script', ENHANCAD_PLUGIN_URL . '/includes/data/js/tvc_ajaxdatahandling' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
136
- wp_enqueue_script( 'tvc_setting-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_setting-form' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
137
- wp_enqueue_script( 'tvc_event-listener-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_feed-form-events' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
138
- wp_enqueue_script( 'tvc_form-support-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_support' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
139
  }
140
  /**
141
  * Generate the nonce's for the Settings page.
22
  $this->_version_stamp = defined( 'WP_DEBUG' ) && WP_DEBUG ? time() : $premium_version_nr . '1.0';
23
  $this->_js_min = defined( 'WP_DEBUG' ) && WP_DEBUG ? '' : '.min';
24
  // add hooks
25
+ //add_action( 'admin_enqueue_scripts', array( $this, 'tvc_register_required_scripts' ) );
26
  add_action( 'admin_enqueue_scripts', array( $this, 'tvc_register_required_nonce' ) );
27
  // only load the next hooks when on the Settings page
28
  if ( tvc_on_plugins_settings_page() ) {
42
  $screen = get_current_screen();
43
 
44
  if($screen->id == 'toplevel_page_aga-envato-api' || $screen->id == 'aga-google-shopping_page_tvc-product-feed-manager' || $screen->id == 'aga-google-shopping_page_tvc-configuration-page'){
45
+ //wp_register_style("tvc_gmc_style-1", ENHANCAD_PLUGIN_URL . '/admin/css/style.css');
46
+ //wp_enqueue_style( "tvc_gmc_style-1");
47
  wp_register_style("tvc_gmc_style-2", ENHANCAD_PLUGIN_URL . '/css/style.css');
48
  wp_enqueue_style( "tvc_gmc_style-2");
49
  wp_register_style("tvc-product-feed-manager-1", ENHANCAD_PLUGIN_URL . '/css/actionable-google-analytics-admin.css');
128
  */
129
  public function tvc_register_required_options_page_scripts() {
130
  // enqueue notice handling script
131
+ //wp_enqueue_style( 'tvc-product-feed-manager-setting', ENHANCAD_PLUGIN_URL . '/css/tvc_setting-page' . $this->_js_min . '.css', '', $this->_version_stamp, 'screen' );
132
+ //wp_enqueue_script( 'tvc_message-handling-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_msg_events' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
133
+ //wp_enqueue_style('font_awesome','//use.fontawesome.com/releases/v5.0.13/css/all.css');
134
  //==wp_enqueue_script( 'tvc_backup-list-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_backup-list'. $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp,'screen' );
135
  wp_enqueue_script( 'tvc_data-handling-script', ENHANCAD_PLUGIN_URL . '/includes/data/js/tvc_ajaxdatahandling' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
136
+ //wp_enqueue_script( 'tvc_setting-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_setting-form' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
137
+ //wp_enqueue_script( 'tvc_event-listener-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_feed-form-events' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
138
+ //wp_enqueue_script( 'tvc_form-support-script', ENHANCAD_PLUGIN_URL . '/includes/user-interface/js/tvc_support' . $this->_js_min . '.js', array( 'jquery' ), $this->_version_stamp, true );
139
  }
140
  /**
141
  * Generate the nonce's for the Settings page.
includes/data/class-tvc-ajax-file.php CHANGED
@@ -10,15 +10,16 @@ if(!defined('ABSPATH')){
10
  }
11
 
12
  if(!class_exists('TVC_Ajax_File')) :
13
-
14
  /**
15
  * Ajax File Class
16
  */
17
  class TVC_Ajax_File extends TVC_Ajax_Calls {
18
-
 
 
19
  public function __construct(){
20
  parent::__construct();
21
-
22
  // hooks
23
  add_action('wp_ajax_tvcajax-get-campaign-categories', array($this, 'tvcajax_get_campaign_categories'));
24
  add_action('wp_ajax_tvcajax-update-campaign-status', array($this, 'tvcajax_update_campaign_status'));
@@ -41,8 +42,45 @@ if(!class_exists('TVC_Ajax_File')) :
41
  add_action('wp_ajax_tvcajax-gmc-category-lists', array($this, 'tvcajax_get_gmc_categories'));
42
  add_action('wp_ajax_tvcajax-custom-metrics-dimension', array($this, 'tvcajax_custom_metrics_dimension'));
43
  add_action('wp_ajax_tvcajax-store-time-taken', array($this, 'tvcajax_store_time_taken'));
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
44
  }
45
-
46
  /**
47
  * Delete the campaign
48
  */
@@ -54,7 +92,7 @@ if(!class_exists('TVC_Ajax_File')) :
54
  $customerId = filter_input(INPUT_POST, 'customerId');
55
  $campaignId = filter_input(INPUT_POST, 'campaignId');
56
 
57
- $url = 'https://connect.tatvic.com/laravelapi/public/api/campaigns/delete';
58
 
59
  $data = [
60
  'merchant_id' => $merchantId,
@@ -121,7 +159,7 @@ if(!class_exists('TVC_Ajax_File')) :
121
  $campaignName = filter_input(INPUT_POST, 'campaignName');
122
  $budget = filter_input(INPUT_POST, 'budget');
123
  $status = filter_input(INPUT_POST, 'status');
124
- $url = 'https://connect.tatvic.com/laravelapi/public/api/campaigns/update';
125
  $shoppingObj = new ShoppingApi();
126
  $campaignData = $shoppingObj->getCampaignDetails($campaignId);
127
 
@@ -186,7 +224,7 @@ if(!class_exists('TVC_Ajax_File')) :
186
 
187
  $country_code = filter_input(INPUT_POST, 'countryCode');
188
  $customer_id = filter_input(INPUT_POST, 'customerId');
189
- $url = 'https://connect.tatvic.com/laravelapi/public/api/products/categories';
190
 
191
  $data = [
192
  'customer_id' => $customer_id,
@@ -532,9 +570,7 @@ if(!class_exists('TVC_Ajax_File')) :
532
  $country_code = filter_input(INPUT_POST, 'countryCode');
533
  $customer_id = filter_input(INPUT_POST, 'customerId');
534
  $parent = filter_input(INPUT_POST, 'parent');
535
- //$url = 'https://connect.tatvic.com/laravelapi/public/api/products/gmc-categories';
536
- //$url = 'http://127.0.0.1:8000/api/products/gmc-categories';
537
- $url = 'https://connect.tatvic.com/laravelapi/public/api/products/gmc-categories';
538
 
539
  $data = [
540
  'customer_id' => $customer_id,
@@ -594,7 +630,8 @@ if(!class_exists('TVC_Ajax_File')) :
594
  */
595
  public function tvcajax_product_syncup(){
596
  // make sure this call is legal
597
-
 
598
  if($this->safe_ajax_call(filter_input(INPUT_POST, 'productSyncupNonce'), 'tvcajax-product-syncup-nonce')){
599
 
600
 
@@ -617,6 +654,7 @@ if(!class_exists('TVC_Ajax_File')) :
617
  $mappedCatsDB = [];
618
  $mappedCats = [];
619
  $mappedAttrs = [];
 
620
  foreach($formArray as $key => $value){
621
  if(preg_match("/^category-name-/i", $key)){
622
  if($value != ''){
@@ -675,22 +713,11 @@ if(!class_exists('TVC_Ajax_File')) :
675
  array(
676
  'key' => '_stock_status',
677
  'value' => 'instock'
678
- ),
679
- array(
680
- 'relation' => 'or',
681
- array(
682
- 'key' => '_sale_price',
683
- 'value' => '',
684
- 'compare' => '!=',
685
- ),
686
- array(
687
- 'key' => '_price',
688
- 'value' => '',
689
- 'compare' => '!=',
690
- )
691
  )
692
  )
693
  ));
 
 
694
  foreach($all_products as $postkey => $postvalue){
695
  $postmeta = [];
696
  $postmeta = $this->getPostMetaData($postvalue->ID);
@@ -698,9 +725,6 @@ if(!class_exists('TVC_Ajax_File')) :
698
  $postObj = (object) array_merge((array) $postvalue, (array) $postmeta);
699
  $product = [];
700
  foreach($formArray as $key => $value){
701
-
702
- // $product['content_language'] = 'en';
703
- // $product['target_country'] = 'US';
704
  $product['channel'] = 'online';
705
  $product['google_product_category'] = $mappedCat;
706
  $product['link'] = get_permalink($postvalue->ID);
@@ -709,13 +733,18 @@ if(!class_exists('TVC_Ajax_File')) :
709
  $product['image_link'] = wp_get_attachment_image_url($image_id, 'full');
710
  }else if($key == 'price'){
711
  $product[$key]['value'] = $postObj->_price;
712
- $product[$key]['currency'] = (get_option('woocommerce_currency') != '' ? get_option('woocommerce_currency') : 'USD');
 
 
 
713
  }else if($key == 'sale_price'){
714
  $product[$key]['value'] = $postObj->_sale_price;
715
- $product[$key]['currency'] = (get_option('woocommerce_currency') != '' ? get_option('woocommerce_currency') : 'USD');
 
 
 
716
  }else if($key == 'target_country'){
717
- $product[$key] = ($postObj->$value != '' ? $postObj->$value : (isset($this->woo_country()[0]) ? $this->woo_country()[0] : ''));
718
- //$product[$key] = ($postObj->$value != '' ? $postObj->$value : get_option('woocommerce_default_country'));
719
  }else if($key == 'content_language'){
720
  $product[$key] = ($postObj->$value != '' ? $postObj->$value : 'en');
721
  }else if(isset($postObj->$value)){
@@ -744,23 +773,12 @@ if(!class_exists('TVC_Ajax_File')) :
744
  array(
745
  'key' => '_stock_status',
746
  'value' => 'instock'
747
- ),
748
- array(
749
- 'relation' => 'or',
750
- array(
751
- 'key' => '_sale_price',
752
- 'value' => '',
753
- 'compare' => '!=',
754
- ),
755
- array(
756
- 'key' => '_price',
757
- 'value' => '',
758
- 'compare' => '!=',
759
- )
760
  )
761
  )
762
  );
763
  $loop = new WP_Query($qArgs);
 
 
764
  foreach($loop->posts as $postkey => $postvalue){
765
  $postmeta = [];
766
  $postmeta = $this->getPostMetaData($postvalue->ID);
@@ -770,16 +788,22 @@ if(!class_exists('TVC_Ajax_File')) :
770
  foreach($formArray as $key => $value){
771
  $product['content_language'] = 'en';
772
  //$product['target_country'] = 'US';
773
- $product['target_country'] = (isset($this->woo_country()[0]) ? $this->woo_country()[0] : '');
774
  $product['channel'] = 'online';
775
  if($key == 'price'){
776
  $product[$key]['value'] = $postObj->_price;
777
  // $product[$key]['currency'] = 'USD';
778
- $product[$key]['currency'] = (get_option('woocommerce_currency') != '' ? get_option('woocommerce_currency') : 'USD');
 
 
 
779
  }else if($key == 'sale_price'){
780
  $product[$key]['value'] = $postObj->_sale_price;
781
  //$product[$key]['currency'] = 'USD';
782
- $product[$key]['currency'] = (get_option('woocommerce_currency') != '' ? get_option('woocommerce_currency') : 'USD');
 
 
 
783
  }else if($key == 'target_country'){
784
  $product[$key] = ($postObj->$value != '' ? $postObj->$value : (isset($this->woo_country()[0]) ? $this->woo_country()[0] : ''));
785
  }else if(isset($postObj->$value)){
@@ -806,46 +830,40 @@ if(!class_exists('TVC_Ajax_File')) :
806
  'entries' => $entries,
807
  ];
808
 
809
- $url = 'https://connect.tatvic.com/laravelapi/public/api/products/batch';
810
  //$url = 'http://127.0.0.1:8000/api/products/batch';
811
 
812
  $args = array(
 
813
  'headers' => array(
814
  'Authorization' => "Bearer MTIzNA==",
815
  'Content-Type' => 'application/json',
816
- 'AccessToken' => $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
817
  ),
818
  'body' => wp_json_encode($data)
819
  );
820
 
821
  // Send remote request
822
- /* echo "<pre>";
823
- print_r($args); */
824
  $request = wp_remote_post($url, $args);
825
 
826
- /* print_r($request); */
827
- /* die; */
828
  // Retrieve information
829
  $response_code = wp_remote_retrieve_response_code($request);
830
  $response_message = wp_remote_retrieve_response_message($request);
831
  $response_body = json_decode(wp_remote_retrieve_body($request));
832
-
 
833
  if((isset($response_body->error) && $response_body->error == '')){
834
- echo json_encode(['status' => 'success']);
835
- // return new WP_REST_Response(
836
- // array(
837
- // 'status' => $response_code,
838
- // 'message' => $response_message,
839
- // 'data' => $response_body->data
840
- // )
841
- // );
842
  }else{
843
  foreach($response_body->errors as $err){
844
  $message = $err;
845
  break;
846
  }
847
  echo json_encode(['status' => 'error', 'message' => $message]);
848
- // return new WP_Error($response_code, $response_message, $response_body);
849
  }
850
 
851
  // echo json_encode( $categories );
@@ -983,7 +1001,7 @@ if(!class_exists('TVC_Ajax_File')) :
983
  } else {
984
  $ee_subscription_id = null;
985
  }
986
- $url = 'https://connect.tatvic.com/laravelapi/public/api/customer-subscriptions/update-setup-time';
987
  $data = [
988
  'subscription_id' => $ee_subscription_id,
989
  'setup_start_time' => date('Y-m-d H:i:s'),
10
  }
11
 
12
  if(!class_exists('TVC_Ajax_File')) :
 
13
  /**
14
  * Ajax File Class
15
  */
16
  class TVC_Ajax_File extends TVC_Ajax_Calls {
17
+ private $apiDomain;
18
+ protected $access_token;
19
+ protected $refresh_token;
20
  public function __construct(){
21
  parent::__construct();
22
+ $this->apiDomain = TVC_API_CALL_URL;
23
  // hooks
24
  add_action('wp_ajax_tvcajax-get-campaign-categories', array($this, 'tvcajax_get_campaign_categories'));
25
  add_action('wp_ajax_tvcajax-update-campaign-status', array($this, 'tvcajax_update_campaign_status'));
42
  add_action('wp_ajax_tvcajax-gmc-category-lists', array($this, 'tvcajax_get_gmc_categories'));
43
  add_action('wp_ajax_tvcajax-custom-metrics-dimension', array($this, 'tvcajax_custom_metrics_dimension'));
44
  add_action('wp_ajax_tvcajax-store-time-taken', array($this, 'tvcajax_store_time_taken'));
45
+ add_action('wp_ajax_tvc_call_api_sync', array($this, 'tvc_call_api_sync'));
46
+ }
47
+ public function tvc_call_api_sync(){
48
+ if($this->safe_ajax_call(filter_input(INPUT_POST, 'apiSyncupNonce'), 'tvc_call_api_sync-nonce')){
49
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
50
+ $tvc_msg = $TVC_Admin_Helper->set_update_api_to_db();
51
+ sleep(2);
52
+ echo json_encode(array('status' => 'success', 'message' => $tvc_msg));
53
+ exit;
54
+ }
55
+ exit;
56
+ }
57
+ public function get_tvc_access_token(){
58
+ if(!empty($this->access_token)){
59
+ return $this->access_token;
60
+ }else if(isset($_SESSION['access_token']) && $_SESSION['access_token']){
61
+ $this->access_token = $_SESSION['access_token'];
62
+ return $this->access_token;
63
+ }else{
64
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
65
+ $google_detail = $TVC_Admin_Helper->get_ee_options_data();
66
+ $this->access_token = $google_detail['setting']->access_token;
67
+ return $this->access_token;
68
+ }
69
+ }
70
+
71
+ public function get_tvc_refresh_token(){
72
+ if(!empty($this->refresh_token)){
73
+ return $this->refresh_token;
74
+ }else if(isset($_SESSION['refresh_token']) && $_SESSION['refresh_token']){
75
+ $this->refresh_token = $_SESSION['refresh_token'];
76
+ return $this->refresh_token;
77
+ }else{
78
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
79
+ $google_detail = $TVC_Admin_Helper->get_ee_options_data();
80
+ $this->refresh_token = $google_detail['setting']->refresh_token;
81
+ return $this->refresh_token;
82
+ }
83
  }
 
84
  /**
85
  * Delete the campaign
86
  */
92
  $customerId = filter_input(INPUT_POST, 'customerId');
93
  $campaignId = filter_input(INPUT_POST, 'campaignId');
94
 
95
+ $url = $this->apiDomain.'/campaigns/delete';
96
 
97
  $data = [
98
  'merchant_id' => $merchantId,
159
  $campaignName = filter_input(INPUT_POST, 'campaignName');
160
  $budget = filter_input(INPUT_POST, 'budget');
161
  $status = filter_input(INPUT_POST, 'status');
162
+ $url = $this->apiDomain.'/campaigns/update';
163
  $shoppingObj = new ShoppingApi();
164
  $campaignData = $shoppingObj->getCampaignDetails($campaignId);
165
 
224
 
225
  $country_code = filter_input(INPUT_POST, 'countryCode');
226
  $customer_id = filter_input(INPUT_POST, 'customerId');
227
+ $url = $this->apiDomain.'/products/categories';
228
 
229
  $data = [
230
  'customer_id' => $customer_id,
570
  $country_code = filter_input(INPUT_POST, 'countryCode');
571
  $customer_id = filter_input(INPUT_POST, 'customerId');
572
  $parent = filter_input(INPUT_POST, 'parent');
573
+ $url = $this->apiDomain.'/products/gmc-categories';
 
 
574
 
575
  $data = [
576
  'customer_id' => $customer_id,
630
  */
631
  public function tvcajax_product_syncup(){
632
  // make sure this call is legal
633
+ ini_set('max_execution_time', '0');
634
+ ini_set('memory_limit','-1');
635
  if($this->safe_ajax_call(filter_input(INPUT_POST, 'productSyncupNonce'), 'tvcajax-product-syncup-nonce')){
636
 
637
 
654
  $mappedCatsDB = [];
655
  $mappedCats = [];
656
  $mappedAttrs = [];
657
+ $skipProducts = [];
658
  foreach($formArray as $key => $value){
659
  if(preg_match("/^category-name-/i", $key)){
660
  if($value != ''){
713
  array(
714
  'key' => '_stock_status',
715
  'value' => 'instock'
 
 
 
 
 
 
 
 
 
 
 
 
 
716
  )
717
  )
718
  ));
719
+ $tvc_currency = ((get_option('woocommerce_currency') != '')? get_option('woocommerce_currency') : 'USD');
720
+ $tvc_country = (isset($this->woo_country()[0]) ? $this->woo_country()[0] : '');
721
  foreach($all_products as $postkey => $postvalue){
722
  $postmeta = [];
723
  $postmeta = $this->getPostMetaData($postvalue->ID);
725
  $postObj = (object) array_merge((array) $postvalue, (array) $postmeta);
726
  $product = [];
727
  foreach($formArray as $key => $value){
 
 
 
728
  $product['channel'] = 'online';
729
  $product['google_product_category'] = $mappedCat;
730
  $product['link'] = get_permalink($postvalue->ID);
733
  $product['image_link'] = wp_get_attachment_image_url($image_id, 'full');
734
  }else if($key == 'price'){
735
  $product[$key]['value'] = $postObj->_price;
736
+ $product[$key]['currency'] = $tvc_currency;
737
+ if ($postObj->_price == '' || $postObj->_price == null) {
738
+ $skipProducts[$postObj->ID] = $postObj;
739
+ }
740
  }else if($key == 'sale_price'){
741
  $product[$key]['value'] = $postObj->_sale_price;
742
+ $product[$key]['currency'] = $tvc_currency;
743
+ if ($postObj->_sale_price == '' || $postObj->_sale_price == null) {
744
+ $skipProducts[$postObj->ID] = $postObj;
745
+ }
746
  }else if($key == 'target_country'){
747
+ $product[$key] = ($postObj->$value != '' ? $postObj->$value : $tvc_country);
 
748
  }else if($key == 'content_language'){
749
  $product[$key] = ($postObj->$value != '' ? $postObj->$value : 'en');
750
  }else if(isset($postObj->$value)){
773
  array(
774
  'key' => '_stock_status',
775
  'value' => 'instock'
 
 
 
 
 
 
 
 
 
 
 
 
 
776
  )
777
  )
778
  );
779
  $loop = new WP_Query($qArgs);
780
+ $tvc_currency = ((get_option('woocommerce_currency') != '')? get_option('woocommerce_currency') : 'USD');
781
+ $tvc_country = (isset($this->woo_country()[0]) ? $this->woo_country()[0] : '');
782
  foreach($loop->posts as $postkey => $postvalue){
783
  $postmeta = [];
784
  $postmeta = $this->getPostMetaData($postvalue->ID);
788
  foreach($formArray as $key => $value){
789
  $product['content_language'] = 'en';
790
  //$product['target_country'] = 'US';
791
+ $product['target_country'] = $tvc_country;
792
  $product['channel'] = 'online';
793
  if($key == 'price'){
794
  $product[$key]['value'] = $postObj->_price;
795
  // $product[$key]['currency'] = 'USD';
796
+ $product[$key]['currency'] = $tvc_currency;
797
+ if ($postObj->_price == '' || $postObj->_price == null) {
798
+ $skipProducts[$postObj->ID] = $postObj;
799
+ }
800
  }else if($key == 'sale_price'){
801
  $product[$key]['value'] = $postObj->_sale_price;
802
  //$product[$key]['currency'] = 'USD';
803
+ $product[$key]['currency'] = $tvc_currency;
804
+ if ($postObj->_sale_price == '' || $postObj->_sale_price == null) {
805
+ $skipProducts[$postObj->ID] = $postObj;
806
+ }
807
  }else if($key == 'target_country'){
808
  $product[$key] = ($postObj->$value != '' ? $postObj->$value : (isset($this->woo_country()[0]) ? $this->woo_country()[0] : ''));
809
  }else if(isset($postObj->$value)){
830
  'entries' => $entries,
831
  ];
832
 
833
+ $url = $this->apiDomain.'/products/batch';
834
  //$url = 'http://127.0.0.1:8000/api/products/batch';
835
 
836
  $args = array(
837
+ 'timeout' => 10000,
838
  'headers' => array(
839
  'Authorization' => "Bearer MTIzNA==",
840
  'Content-Type' => 'application/json',
841
+ 'AccessToken' => $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
842
  ),
843
  'body' => wp_json_encode($data)
844
  );
845
 
846
  // Send remote request
847
+ //echo "<pre>";
848
+ //print_r($args);
849
  $request = wp_remote_post($url, $args);
850
 
851
+ //print_r($request);
852
+
853
  // Retrieve information
854
  $response_code = wp_remote_retrieve_response_code($request);
855
  $response_message = wp_remote_retrieve_response_message($request);
856
  $response_body = json_decode(wp_remote_retrieve_body($request));
857
+ //print_r($response_body);
858
+ //die;
859
  if((isset($response_body->error) && $response_body->error == '')){
860
+ echo json_encode(['status' => 'success', 'skipProducts' => count($skipProducts)]);
 
 
 
 
 
 
 
861
  }else{
862
  foreach($response_body->errors as $err){
863
  $message = $err;
864
  break;
865
  }
866
  echo json_encode(['status' => 'error', 'message' => $message]);
 
867
  }
868
 
869
  // echo json_encode( $categories );
1001
  } else {
1002
  $ee_subscription_id = null;
1003
  }
1004
+ $url = $this->apiDomain.'/customer-subscriptions/update-setup-time';
1005
  $data = [
1006
  'subscription_id' => $ee_subscription_id,
1007
  'setup_start_time' => date('Y-m-d H:i:s'),
includes/data/class-tvc-backup.php DELETED
@@ -1,181 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Backup Class.
5
- *
6
- * @package WP Product Feed Manager/Data/Classes
7
- * @version 1.0.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Backup' ) ) :
15
-
16
- class TVC_Backup {
17
-
18
- private $_wpdb;
19
-
20
- /**
21
- * @var string placeholder containing the wp table prefix
22
- */
23
- private $_table_prefix;
24
-
25
- /**
26
- * TVC_Queries Constructor
27
- */
28
- public function __construct() {
29
- // get global WordPress database functions
30
- global $wpdb;
31
-
32
- // assign the global wpdb to a variable
33
- $this->_wpdb = &$wpdb;
34
-
35
- // assign the wp table prefix to a variable
36
- $this->_table_prefix = $this->_wpdb->prefix;
37
- }
38
-
39
- /**
40
- * Reads the data from all plugin related tables ands stores the data in a sql like string
41
- * The return string contains a timestamp, the database version, the option settings and the table content
42
- *
43
- * @since 1.7.0
44
- * @return string sql like string with the backup data
45
- */
46
- public function read_full_backup_data() {
47
- $main_table = $this->_table_prefix . 'feedmanager_product_feed';
48
- $meta_table = $this->_table_prefix . 'feedmanager_product_feedmeta';
49
- $channel_table = $this->_table_prefix . 'feedmanager_channel';
50
-
51
- $main_table_columns = $this->_wpdb->get_col( "DESC {$main_table}", 0 );
52
- $meta_table_columns = $this->_wpdb->get_col( "DESC {$meta_table}", 0 );
53
- $channel_table_columns = $this->_wpdb->get_col( "DESC {$channel_table}", 0 );
54
-
55
- $main_table_content = $this->make_table_backup_string( $this->_wpdb->get_results( "SELECT * FROM $main_table", ARRAY_N ), $main_table_columns );
56
- $meta_table_content = $this->make_table_backup_string( $this->_wpdb->get_results( "SELECT * FROM $meta_table", ARRAY_N ), $meta_table_columns );
57
- $channel_table_content = $this->make_table_backup_string( $this->_wpdb->get_results( "SELECT * FROM $channel_table", ARRAY_N ), $channel_table_columns );
58
-
59
- $db_version = get_option( 'tvc_db_version' );
60
- $ftp_passive = 'inactive';
61
- $auto_fix = get_option( 'tvc_auto_feed_fix', 'false' );
62
- $third_party_attributes = get_option( 'tvc_third_party_attribute_keywords', '%wpmr%,%cpf%,%unit%,%bto%,%yoast%' );
63
- $disabled_background_mode = get_option( 'tvc_disabled_background_mode', 'false' ); // @since 2.0.7
64
- $process_logger_option = get_option( 'tvc_process_logger_status', 'false' ); // @since 2.9.0
65
- $show_pi_option = get_option( 'tvc_show_product_identifiers', 'false' ); // @since 2.10.0
66
- $sep_string = '# backup string for database ->';
67
- $time_stamp = current_time( 'timestamp' );
68
-
69
- $table_content = "$time_stamp#$db_version#$ftp_passive#$auto_fix#$third_party_attributes#$disabled_background_mode#$process_logger_option#$show_pi_option";
70
- $table_content .= "$sep_string $main_table # <- # $main_table_content ";
71
- $table_content .= "$sep_string $meta_table # <- # $meta_table_content ";
72
- $table_content .= "$sep_string $channel_table # <- # $channel_table_content";
73
-
74
- return $table_content;
75
- }
76
-
77
- /**
78
- * Restores the data in the database tables
79
- *
80
- * @since 1.7.0
81
- *
82
- * @param array $table_queries
83
- *
84
- * @return boolean
85
- */
86
- public function restore_backup_data( $table_queries ) {
87
- // retrieve the initial data strings
88
- $product_feed_table_data = explode( ' # ', $table_queries[0][1] );
89
- $product_feedmeta_table_data = explode( ' # ', $table_queries[1][1] );
90
- $channel_table_data = explode( ' # ', $table_queries[2][1] );
91
-
92
- // table names
93
- $main_table = $this->_table_prefix . 'feedmanager_product_feed';
94
- $meta_table = $this->_table_prefix . 'feedmanager_product_feedmeta';
95
- $channel_table = $this->_table_prefix . 'feedmanager_channel';
96
-
97
- // clear the current data
98
- $this->_wpdb->query( "TRUNCATE TABLE $main_table" );
99
- $this->_wpdb->query( "TRUNCATE TABLE $meta_table" );
100
- $this->_wpdb->query( "TRUNCATE TABLE $channel_table" );
101
-
102
- // get the columns
103
- $product_feed_table_columns = explode( ', ', $product_feed_table_data[0] );
104
- $product_feedmeta_table_columns = explode( ', ', $product_feedmeta_table_data[0] );
105
- $channel_table_columns = explode( ', ', $channel_table_data[0] );
106
-
107
- // get the data
108
- $product_feed_table_queries = explode( PHP_EOL, $product_feed_table_data[1] );
109
- $product_feedmeta_table_queries = explode( PHP_EOL, $product_feedmeta_table_data[1] );
110
- $channel_table_queries = explode( PHP_EOL, $channel_table_data[1] );
111
-
112
- // restore the feedmanager_product_feed table
113
- foreach ( $product_feed_table_queries as $table_data ) {
114
- $product_feed_data = explode( "\t", $table_data );
115
-
116
- if ( count( $product_feed_table_columns ) === count( $product_feed_data ) ) {
117
- $data = array();
118
-
119
- for ( $i = 0; $i < count( $product_feed_data ); $i ++ ) {
120
- $data[ $product_feed_table_columns[ $i ] ] = $product_feed_data[ $i ];
121
- }
122
-
123
- $this->_wpdb->replace( $main_table, $data );
124
- }
125
- }
126
-
127
- // restore the feedmanager_product_feedmeta table
128
- foreach ( $product_feedmeta_table_queries as $table_metadata ) {
129
- $product_feed_metadata = explode( "\t", $table_metadata );
130
-
131
- if ( count( $product_feedmeta_table_columns ) === count( $product_feed_metadata ) ) {
132
- $data = array();
133
-
134
- for ( $i = 0; $i < count( $product_feed_metadata ); $i ++ ) {
135
- $data[ $product_feedmeta_table_columns[ $i ] ] = $product_feed_metadata[ $i ];
136
- }
137
-
138
- $this->_wpdb->replace( $meta_table, $data );
139
- }
140
- }
141
-
142
- // restore the feedmanager_channel table
143
- foreach ( $channel_table_queries as $table_channeldata ) {
144
- $channel_data = explode( "\t", $table_channeldata );
145
-
146
- if ( count( $channel_table_columns ) === count( $channel_data ) ) {
147
- $data = array();
148
-
149
- for ( $i = 0; $i < count( $channel_data ); $i ++ ) {
150
- $data[ $channel_table_columns[ $i ] ] = $channel_data[ $i ];
151
- }
152
-
153
- $this->_wpdb->replace( $channel_table, $data );
154
- }
155
- }
156
-
157
- return true;
158
- }
159
-
160
- /**
161
- * Returns a tab separated string with the query results.
162
- *
163
- * @param (string) $query_result
164
- * @param {array} $columns
165
- *
166
- * @return (string) backup string
167
- */
168
- private function make_table_backup_string( $query_result, $columns ) {
169
- $string = implode( $columns, ', ' ) . ' # ';
170
-
171
- foreach ( $query_result as $row ) {
172
- $string .= implode( "\t", $row ) . "\r\n";
173
- }
174
-
175
- return $string;
176
- }
177
- }
178
-
179
- // end of TVC_Backup class
180
-
181
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-channel-ftp.php DELETED
@@ -1,37 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Feed Manager Channel FTP Class.
5
- *
6
- * @package TVC Product Feed Manager/Data/Classes
7
- * @version 2.2.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
-
15
- if ( ! class_exists( 'TVC_Channel_FTP' ) ) :
16
-
17
- /**
18
- * Channel FTP Class
19
- */
20
- class TVC_Channel_FTP {
21
-
22
- /**
23
- * Gets the correct channel zip file from the wp server
24
- *
25
- * @since 1.9.3 - switched from ftp to cURL procedures
26
- *
27
- * @param string $channel
28
- * @param string $code
29
- *
30
- * @return boolean
31
- */
32
-
33
- }
34
-
35
- // end of TVC_Channel_FTP class
36
-
37
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-channel.php DELETED
@@ -1,342 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Channels Class.
5
- *
6
- * @package TVC Product Feed Manager/Data/Classes
7
- * @version 1.6.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Channel' ) ) :
15
-
16
- /**
17
- * Channel Class
18
- */
19
- class TVC_Channel {
20
- /**
21
- * Placeholder for the Channel Classes
22
- *
23
- * @var string
24
- */
25
- private $_channels;
26
-
27
- public function __construct() {
28
- // TVC_CHANNEL_RELATED
29
- $this->_channels = array(
30
- new Channel( '0', 'usersetup', 'Free User Setup' ),
31
- new Channel( '1', 'google', 'Google Merchant Centre' ),
32
- new Channel( '2', 'bing', 'Bing Merchant Centre' ),
33
- new Channel( '3', 'beslis', 'Beslis.nl' ),
34
- new Channel( '4', 'pricegrabber', 'PriceGrabber' ),
35
- new Channel( '5', 'shopping', 'Shopping.com (eBay)' ),
36
- new Channel( '6', 'amazon', 'Amazon product ads' ),
37
- new Channel( '7', 'connexity', 'Connexity' ),
38
- new Channel( '8', 'become', 'Become' ),
39
- // Become has been taken over by Connexity, https://merchants.become.com/DataFeedSpecification.html links to Connexity
40
- new Channel( '9', 'nextag', 'Nextag' ),
41
- new Channel( '10', 'kieskeurig', 'Kieskeurig.nl' ),
42
- new Channel( '11', 'vergelijk', 'Vergelijk.nl' ),
43
- new Channel( '12', 'koopjespakker', 'Koopjespakker.nl' ),
44
- new Channel( '13', 'avantlink', 'AvantLink' ),
45
- new Channel( '14', 'zbozi', 'Zbozi' ),
46
- new Channel( '15', 'comcon', 'Commerce Connector' ),
47
- new Channel( '16', 'facebook', 'Facebook' ),
48
- new Channel( '17', 'bol', 'Bol.com' ),
49
- new Channel( '18', 'adtraction', 'Adtraction' ),
50
- new Channel( '19', 'ricardo', 'Ricardo.ch' ),
51
- new Channel( '20', 'ebay', 'eBay' ),
52
- new Channel( '21', 'shopzilla', 'Shopzilla' ),
53
- new Channel( '22', 'converto', 'Converto' ),
54
- new Channel( '23', 'idealo', 'Idealo' ),
55
- new Channel( '24', 'heureka', 'Heureka' ),
56
- new Channel( '25', 'pepperjam', 'Pepperjam' ),
57
- new Channel( '26', 'galaxus_data', 'Galaxus Product Data' ),
58
- new Channel( '27', 'galaxus_properties', 'Galaxus Product Properties' ),
59
- new Channel( '28', 'galaxus_stock_pricing', 'Galaxus Product Stock Pricing' ),
60
- new Channel( '996', '_tsv', 'Custom TSV Export' ),
61
- new Channel( '997', '_txt', 'Custom TXT Export' ),
62
- new Channel( '998', '_csv', 'Custom CSV Export' ),
63
- new Channel( '999', '', 'Custom XML Export' ),
64
- );
65
- }
66
-
67
- /**
68
- * Returns channel data from a specific channel
69
- *
70
- * @param string $channel_name channel name
71
- *
72
- * @return string Channel class
73
- */
74
- public function get_active_channel_details( $channel_name ) {
75
- foreach ( $this->_channels as $channel ) {
76
- if ( $channel->channel_short === $channel_name ) {
77
- return $channel;
78
- }
79
- }
80
- return false;
81
- }
82
-
83
- public function get_channel_short_name( $channel_id ) {
84
- foreach ( $this->_channels as $channel ) {
85
- if ( $channel->channel_id === $channel_id ) {
86
- return $channel->channel_short;
87
- }
88
- }
89
- return false;
90
- }
91
-
92
- public function get_channel_name( $channel_id ) {
93
- foreach ( $this->_channels as $channel ) {
94
- if ( $channel->channel_id === $channel_id ) {
95
- return $channel->channel_name;
96
- }
97
- }
98
- return false;
99
- }
100
-
101
- public function get_installed_channel_names() {
102
- $file_class = new TVC_File();
103
-
104
- return $file_class->get_installed_channels_from_file();
105
- }
106
-
107
- public function remove_channel( $channel, $nonce ) {
108
- if ( wp_verify_nonce( $nonce, 'delete-channel-nonce' ) ) {
109
- $this->remove_channel_source( $channel );
110
- }
111
- }
112
-
113
- public function update_channel( $channel, $code, $nonce ) {
114
- if ( wp_verify_nonce( $nonce, 'update-channel-nonce' ) ) {
115
- $this->update_channel_source( $channel, $code );
116
- } else {
117
- tvc_write_log_file( sprintf( 'Failed to update channel %s because then nonce was not accepted. Given nonce = %s', $channel, $nonce ) );
118
- }
119
- }
120
-
121
- public function install_channel( $channel, $code, $nonce ) {
122
- if ( wp_verify_nonce( $nonce, 'install-channel-nonce' ) ) {
123
- $this->install_channel_source( $channel, $code );
124
- } else {
125
- tvc_write_log_file( sprintf( 'Failed to install channel %s because then nonce was not accepted. Given nonce = %s', $channel, $nonce ) );
126
- }
127
- }
128
-
129
- public function get_channels_from_server() {
130
- $response = "Google Merchant Centre";
131
- return $response;
132
- }
133
-
134
- public function get_number_of_updates_from_server( $channel_updated ) {
135
- if ( date( 'Ymd' ) === get_option( 'tvc_channel_update_check_date' ) ) {
136
- if ( $channel_updated ) {
137
- tvc_decrease_update_ready_channels();
138
- }
139
-
140
- return get_option( 'tvc_channels_to_update' );
141
- } else {
142
- $response = $this->get_channels_from_server();
143
-
144
- if ( ! is_wp_error( $response ) ) {
145
- $available_channels = json_decode( $response['body'] );
146
-
147
- if ( $available_channels ) {
148
- $installed_channels_names = $this->get_installed_channel_names();
149
-
150
- $this->add_status_data_to_available_channels( $available_channels, $installed_channels_names, false );
151
-
152
- $stored_count = $this->count_updatable_channels( $available_channels );
153
-
154
- $count = $channel_updated ? ( $stored_count - 1 ) : $stored_count;
155
- update_option( 'tvc_channels_to_update', $count > 0 ? $count : 0 );
156
- update_option( 'tvc_channel_update_check_date', date( 'Ymd' ) );
157
-
158
- return $count;
159
- }
160
- } else {
161
- echo tvc_handle_wp_errors_response(
162
- $response,
163
- sprintf(
164
- /* translators: %s: url to the support page */
165
- esc_html__(
166
- '2141 - Please open a support ticket at %s for support on this issue.',
167
- 'tvc-product-feed-manager'
168
- ),
169
- TVC_SUPPORT_PAGE_URL
170
- )
171
- );
172
-
173
- return false;
174
- }
175
- }
176
-
177
- return 0;
178
- }
179
-
180
- public function add_status_data_to_available_channels( &$available_channels, $installed_channels, $updated ) {
181
- for ( $i = 0; $i < count( $available_channels ); $i ++ ) {
182
- if ( in_array( $available_channels[ $i ]->short_name, $installed_channels ) ) {
183
- $available_channels[ $i ]->status = 'installed';
184
-
185
- $available_channels[ $i ]->installed_version = $available_channels[ $i ]->short_name === $updated ? $available_channels[ $i ]->version
186
- : $this->get_channel_file_version( $available_channels[ $i ]->short_name, 0 );
187
- } else {
188
- $available_channels[ $i ]->status = 'not installed';
189
- $available_channels[ $i ]->installed_version = '0';
190
- }
191
- }
192
- }
193
-
194
- private function get_channel_file_version( $channel_name, $rerun_counter ) {
195
- if ( $rerun_counter < 3 ) {
196
- if ( class_exists( 'TVC_' . ucfirst( $channel_name ) . '_Feed_Class' ) ) {
197
- $class_var = 'TVC_' . ucfirst( $channel_name ) . '_Feed_Class';
198
-
199
- $channel_class = new $class_var();
200
-
201
- return $channel_class->get_version();
202
- } else {
203
- // reset the registered channels in the channel table
204
- $db_class = new TVC_Database_Management();
205
- $db_class->reset_channel_registration();
206
-
207
- include_channels(); // include the channel classes
208
-
209
- $rerun_counter ++;
210
-
211
- return $this->get_channel_file_version( $channel_name, $rerun_counter );
212
- }
213
- } else {
214
- if ( tvc_on_any_own_plugin_page() ) {
215
- /* translators: %s: Name of a channel */
216
- echo tvc_show_wp_error( sprintf( esc_html__( 'Channel %s is not installed correctly. Please try to Deactivate and then Activate the Feed Manager Plugin in your Plugins page.', 'tvc-product-feed-manager' ), $channel_name ) );
217
- tvc_write_log_file( sprintf( 'Error: Channel %s is not installed correctly.', $channel_name ) );
218
- }
219
-
220
- return 'unknown';
221
- }
222
- }
223
-
224
- private function count_updatable_channels( $channel_data ) {
225
- $counter = 0;
226
-
227
- foreach ( $channel_data as $channel ) {
228
- if ( 'installed' === $channel->status && ( $channel->version > $channel->installed_version ) ) {
229
- $counter ++;
230
- }
231
- }
232
-
233
- return $counter;
234
- }
235
-
236
- private function update_channel_source( $channel, $code ) {
237
- $file_class = new TVC_File();
238
- $ftp_class = new TVC_Channel_FTP();
239
-
240
- // remove the out dated channel source files from the server
241
- $file_class->delete_channel_source_files( $channel );
242
-
243
- $get_result = $ftp_class->get_channel_source_files( $channel, $code );
244
-
245
- // get the update files from .com
246
- if ( false !== $get_result ) {
247
- // unzip the file
248
- $file_class->unzip_channel_file( $channel );
249
-
250
- // register the update
251
- tvc_decrease_update_ready_channels();
252
- }
253
- }
254
-
255
- private function remove_channel_source( $channel_short ) {
256
- $data_class = new TVC_Data();
257
- $file_class = new TVC_File();
258
-
259
- // get the channel id that needs to be removed
260
- $channel_id = $data_class->get_channel_id_from_short_name( $channel_short );
261
-
262
- // unregister the channel
263
- wp_dequeue_script( 'tvc_' . $channel_short . '-source-script' );
264
-
265
- if ( $channel_id ) {
266
- // remove channel related feed files
267
- $file_class->delete_channel_feed_files( $channel_id );
268
-
269
- // remove any channel related feed data and feed meta
270
- $data_class->delete_channel_feeds( $channel_id );
271
- }
272
-
273
- // remove the channel from the feedmanager_channel table
274
- $data_class->delete_channel( $channel_short );
275
-
276
- // remove the channel source files from the server
277
- $file_class->delete_channel_source_files( $channel_short );
278
- }
279
-
280
- private function install_channel_source( $channel_name, $code ) {
281
- $ftp_class = new TVC_Channel_FTP();
282
- $file_class = new TVC_File();
283
- $data_class = new TVC_Data();
284
-
285
- if ( plugin_version_supports_channel( $channel_name ) ) {
286
- $get_result = $ftp_class->get_channel_source_files( $channel_name, $code );
287
-
288
- // get the update files from .com
289
- if ( false !== $get_result ) {
290
-
291
- // unzip the file
292
- $file_class->unzip_channel_file( $channel_name );
293
-
294
- // register the new channel
295
- $channel_details = $this->get_active_channel_details( $channel_name );
296
-
297
- if ( false !== $channel_details ) {
298
- $data_class->register_channel( $channel_name, $channel_details );
299
- } else {
300
- tvc_write_log_file( sprintf( 'Unable to register channel %s' . $channel_name ) );
301
- }
302
- } else {
303
- tvc_write_log_file(
304
- sprintf(
305
- 'Could not get the %s channel file from the server. Get_result message is %s.',
306
- $channel_name,
307
- $get_result
308
- )
309
- );
310
- }
311
- } else {
312
- echo tvc_show_wp_warning(
313
- sprintf(
314
- /* translators: %s: Name of the selected channel */
315
- esc_html__(
316
- 'Channel %s is not supported by your current plugin version. Please update your plugin to the latest version and try uploading this channel again.',
317
- 'tvc-product-feed-manager'
318
- ),
319
- $channel_name
320
- ),
321
- 'tvc-product-feed-manager'
322
- );
323
- }
324
- }
325
- }
326
-
327
- // end of TVC_Channel class
328
-
329
- class Channel {
330
- public $channel_id;
331
- public $channel_short;
332
- public $channel_name;
333
-
334
- public function __construct( $id, $short, $name ) {
335
- $this->channel_id = $id;
336
- $this->channel_short = $short;
337
- $this->channel_name = $name;
338
- }
339
- }
340
-
341
- // end of Channel class
342
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-data.php DELETED
@@ -1,713 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * WP Data Class.
5
- *
6
- * @package WP Product Feed Manager/Data/Classes
7
- * @version 3.5.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Data' ) ) :
15
-
16
- /**
17
- * Data Class
18
- */
19
- class TVC_Data {
20
-
21
- private $_queries_class;
22
- private $_files_class;
23
-
24
- public function __construct() {
25
- $this->_queries_class = new TVC_Queries();
26
- $this->_files_class = new TVC_File();
27
- }
28
-
29
- public function get_countries() {
30
- return $this->_queries_class->read_countries();
31
- }
32
-
33
- /**
34
- * @param $channel_short_name
35
- * @return string|null
36
- */
37
- public function get_channel_id_from_short_name( $channel_short_name ) {
38
- return $this->_queries_class->get_channel_id( $channel_short_name );
39
- }
40
-
41
- public function get_channels() {
42
- return $this->_queries_class->read_channels();
43
- }
44
-
45
- /**
46
- * @param $channel_short
47
- * @return bool|false|int
48
- */
49
- public function delete_channel( $channel_short ) {
50
- $result = $this->_queries_class->remove_channel_from_db( $channel_short );
51
-
52
- if ( ! $result || 0 == $result ) {
53
- $result = $this->_queries_class->clean_channel_table();
54
- }
55
-
56
- return $result;
57
- }
58
-
59
- /**
60
- * @param $channel_id
61
- */
62
- public function delete_channel_feeds( $channel_id ) {
63
- $feeds = $this->_queries_class->get_feeds_from_specific_channel( $channel_id );
64
-
65
- foreach ( $feeds as $feed_id ) {
66
- $this->_queries_class->delete_meta( $feed_id['product_feed_id'] );
67
- $this->_queries_class->delete_feed( $feed_id['product_feed_id'] );
68
- }
69
- }
70
-
71
- public function get_sources() {
72
- return $this->_queries_class->read_sources();
73
- }
74
-
75
- /**
76
- * @param $country_code
77
- * @return array|object|stdClass|void|null
78
- */
79
- public function get_country_id_from_short_code( $country_code ) {
80
- if ( '0' !== $country_code && 0 !== $country_code ) {
81
- return $this->_queries_class->get_country_id( $country_code );
82
- } else {
83
- $id = new stdClass();
84
- $id->country_id = '233';
85
-
86
- return $id;
87
- }
88
- }
89
-
90
- public function get_schedule_data() {
91
- return $this->_queries_class->read_active_schedule_data();
92
- }
93
-
94
- public function get_failed_feeds() {
95
- return $this->_queries_class->read_failed_feeds();
96
- }
97
-
98
- /**
99
- * @param $feed_id
100
- * @return mixed
101
- */
102
- public function get_feed_status( $feed_id ) {
103
- $feed_status = $this->_queries_class->get_current_feed_status( $feed_id );
104
-
105
- return $feed_status[0]->status_id;
106
- }
107
-
108
- /**
109
- * @param $feed_id
110
- * @param $nr
111
- * @return false|int
112
- */
113
- public function set_nr_of_feed_products( $feed_id, $nr ) {
114
- return $this->_queries_class->set_nr_feed_products( $feed_id, $nr );
115
- }
116
-
117
- /**
118
- * @param $feed_id
119
- * @return array|object|void|null
120
- */
121
- public function get_nr_of_feed_products( $feed_id ) {
122
- return $this->_queries_class->get_nr_feed_products( $feed_id );
123
- }
124
-
125
- /**
126
- * @param $feed_id
127
- * @param $feed_url
128
- * @param $nr_products
129
- * @return false|int
130
- */
131
- public function update_feed_data( $feed_id, $feed_url, $nr_products ) {
132
- return $this->_queries_class->update_feed_update_data( $feed_id, $feed_url, $nr_products );
133
- }
134
-
135
- /**
136
- * Sets the status id of a feed
137
- *
138
- * 0 = unknown
139
- * 1 = OK (will be updated automatically)
140
- * 2 = On hold (will not be updated automatically)
141
- * 3 = Processing
142
- * 4 = In processing queue
143
- * 5 = Has errors
144
- * 6 = Failed processing
145
- *
146
- * @param string $feed_id
147
- * @param int $status
148
- *
149
- * @return bool True if the update succeeded.
150
- */
151
- public function update_feed_status( $feed_id, $status ) {
152
-
153
- $message_level = 'MESSAGE';
154
-
155
- switch ( $status ) {
156
- case 1:
157
- $message = sprintf( 'The feed status of feed %s has been set to OK (1)', $feed_id );
158
- break;
159
-
160
- case 2:
161
- $message = sprintf( 'The feed status of feed %s has been set to On Hold (2)', $feed_id );
162
- break;
163
-
164
- case 3:
165
- $message = sprintf( 'The feed status of feed %s has been set to Processing (3)', $feed_id );
166
- break;
167
-
168
- case 4:
169
- $message = sprintf( 'The feed status of feed %s has been set to In processing queue (4)', $feed_id );
170
- break;
171
-
172
- case 5:
173
- $message = sprintf( 'The feed status of feed %s has been set to Has errors (5)', $feed_id );
174
- $message_level = 'ERROR';
175
- break;
176
-
177
- case 6:
178
- $message = sprintf( 'The feed status of feed %s has been set to Failed processing (6)', $feed_id );
179
- $message_level = 'ERROR';
180
- break;
181
-
182
- default:
183
- $message = sprintf( 'Tried to update the status of feed %s but the status is unknown!', $feed_id );
184
- $message_level = 'ERROR';
185
- }
186
-
187
- do_action( 'tvc_feed_generation_message', $feed_id, $message, $message_level );
188
-
189
- return $this->_queries_class->update_feed_file_status( $feed_id, $status );
190
- }
191
-
192
- /**
193
- * Fills output fields with stored meta data
194
- *
195
- * @access public
196
- *
197
- * @param string $feed_id
198
- * @param array $outputs
199
- *
200
- * @return array
201
- */
202
- public function fill_output_fields_with_metadata( $feed_id, $outputs ) {
203
- // read the meta data from the database
204
- $metadata = $this->_queries_class->read_metadata( $feed_id );
205
-
206
- // loop through the output rows
207
- for ( $i = 0; $i < count( $outputs ); $i ++ ) {
208
- // check if there is specific meta data for this output row
209
- if ( count( $metadata ) > 0 ) {
210
- foreach ( $metadata as $meta ) {
211
- // look for a match
212
- if ( $meta['meta_key'] === $outputs[ $i ]->field_label ) {
213
- // put the meta data in the value variable of the output row
214
- $outputs[ $i ]->value = $meta['meta_value'];
215
- break; // break is required to stop the foreach loop and prevent the following loop from clearing the value
216
- } else {
217
- // as long as there is no match, leave the value empty
218
- $outputs[ $i ]->value = '';
219
- }
220
- }
221
- } else {
222
- $outputs[ $i ]->value = '';
223
- }
224
- }
225
-
226
- return $outputs;
227
- }
228
-
229
- /**
230
- * Collects the source fields from all the different attributes.
231
- *
232
- * @param string $source_id The source id (not in use at the moment). Default 1.
233
- *
234
- * @return mixed|void|null
235
- */
236
- public function get_source_fields( $source_id = '1' ) {
237
- $source_fields = null;
238
-
239
- switch ( $source_id ) {
240
- case '1':
241
- $data_class = new TVC_Data();
242
-
243
- $custom_product_attributes = $this->_queries_class->get_custom_product_attributes();
244
- $custom_product_fields = $this->_queries_class->get_custom_product_fields();
245
- $product_attributes = $this->_queries_class->get_all_product_attributes();
246
- $product_taxonomies = get_taxonomies();
247
- $third_party_custom_fields = $data_class->get_third_party_custom_fields();
248
-
249
- $combined_source_fields = $this->combine_custom_attributes_and_feeds(
250
- $custom_product_attributes,
251
- $custom_product_fields,
252
- $product_attributes,
253
- $product_taxonomies,
254
- $third_party_custom_fields
255
- );
256
-
257
- $source_fields = apply_filters( 'tvc_all_source_fields', $combined_source_fields );
258
- break;
259
-
260
- default:
261
- if ( 'valid' === get_option( 'tvc_lic_status' ) ) { // error message for paid versions
262
- echo '<div id="error">' . __(
263
- 'Could not add custom fields because I could not identify the channel.
264
- If not already done add the correct channel in the Manage Channels page.
265
- Also try to deactivate and then activate the plugin.',
266
- 'tvc-product-feed-manager'
267
- ) . '</div>';
268
-
269
- tvc_write_log_file( sprintf( 'Could not define the channel in a valid Premium plugin version. Feed id = %s', $source_id ) );
270
- } else { // error message for free version
271
- echo '<div id="error">' . __(
272
- 'Could not identify the channel.
273
- Try to deactivate and then activate the plugin.
274
- If that does not work remove the plugin through the WordPress Plugins page and than reinstall and activate it again.',
275
- 'tvc-product-feed-manager'
276
- ) . '</div>';
277
-
278
- tvc_write_log_file( sprintf( 'Could not define the channel in a free plugin version. Feed id = %s', $source_id ) );
279
- }
280
- break;
281
- }
282
- return $source_fields;
283
- }
284
-
285
- /**
286
- * Get the attribute data of a specific feed.
287
- *
288
- * @param string $feed_id The id of the feed from which the attribute data is needed.
289
- * @param string $channel_id The id of the channel of the feed.
290
- *
291
- * @return array The attribute data.
292
- */
293
- public function get_attribute_data( $feed_id, $channel_id ) {
294
- $is_custom = function_exists( 'tvc_channel_is_custom_channel' ) ? tvc_channel_is_custom_channel( $channel_id ) : false;
295
- $channel_name = trim( $this->_queries_class->get_channel_short_name_from_db( $channel_id ) );
296
-
297
- if ( ! $is_custom ) {
298
- // read the output fields
299
- $attributes_data = $this->_files_class->get_output_fields_for_specific_channel( $channel_name );
300
-
301
- // if the feed is a stored feed, look for meta data to add (a feed an id of -1 is a new feed that not yet has been saved)
302
- if ( $feed_id >= 0 ) {
303
- // add meta data to the feeds output fields
304
- $attributes_data = $this->fill_output_fields_with_metadata( $feed_id, $attributes_data );
305
- }
306
- } else {
307
- $attributes_data = $this->get_custom_fields_with_metadata( $feed_id );
308
- }
309
- return $attributes_data;
310
- }
311
-
312
- /**
313
- * @param $feed_id
314
- * @return array|bool|object|null
315
- */
316
- public function get_filter_query( $feed_id ) {
317
- return $this->_queries_class->get_product_filter_query( $feed_id );
318
- }
319
-
320
- /**
321
- * @param $variation_id
322
- * @return array
323
- */
324
- public function get_own_variation_data( $variation_id ) {
325
- return $this->_queries_class->get_own_variable_product_attributes( $variation_id );
326
- }
327
-
328
- /**
329
- * @param $product_data
330
- * @param $parent_id
331
- * @param $post_columns_query_string
332
- */
333
- public function add_parent_data( &$product_data, $parent_id, $post_columns_query_string ) {
334
- $parent_product_data = (array) $this->_queries_class->read_post_data( $parent_id, $post_columns_query_string );
335
- $sources_that_always_use_parent_data = apply_filters( 'sources_that_always_use_data_from_parent', array( 'post_excerpt' ) );
336
-
337
- $columns = explode( ', ', $post_columns_query_string );
338
-
339
- foreach ( $columns as $column ) {
340
- if ( ( '' === $product_data[ $column ] && array_key_exists( $column, $parent_product_data ) && '' !== $parent_product_data[ $column ] )
341
- || in_array( $column, $sources_that_always_use_parent_data ) ) {
342
- $product_data[ $column ] = $parent_product_data[ $column ];
343
- }
344
- }
345
- }
346
-
347
- /**
348
- * @param $feed_id
349
- * @return array
350
- */
351
- public function get_custom_fields_with_metadata( $feed_id ) {
352
- // read the meta data from the database
353
- $metadata = $this->_queries_class->read_metadata( $feed_id );
354
- $outputs = array();
355
-
356
- // loop through the output rows
357
- for ( $i = 0; $i < count( $metadata ); $i ++ ) {
358
- $object = new stdClass();
359
-
360
- $object->field_id = $i + 1;
361
- $object->category_id = '5';
362
- $object->field_label = $metadata[ $i ]['meta_key'];
363
- $object->value = $metadata[ $i ]['meta_value'];
364
-
365
- array_push( $outputs, $object );
366
- }
367
-
368
- return $outputs;
369
- }
370
-
371
- public function get_third_party_custom_fields() {
372
- $custom_fields = array();
373
-
374
- // YITH Brands plugin
375
- $yith_brand_label = get_option( 'yith_wcbr_brands_label' );
376
- if ( $yith_brand_label ) {
377
- array_push( $custom_fields, $yith_brand_label );
378
- }
379
-
380
- // WooCommerce Brands
381
- if ( in_array(
382
- 'woocommerce-brands/woocommerce-brands.php',
383
- apply_filters(
384
- 'active_plugins',
385
- get_option( 'active_plugins' )
386
- )
387
- ) ) {
388
- array_push( $custom_fields, 'Brand' );
389
- }
390
-
391
- return $custom_fields;
392
- }
393
-
394
- /**
395
- * Checks if other feeds than the active feed are still on processing status. If so, set these feeds to error
396
- *
397
- * @param string $active_feed_id
398
- *
399
- * @since 1.10.0
400
- *
401
- */
402
- public function check_for_failed_feeds( $active_feed_id ) {
403
- $processing_feeds = $this->_queries_class->get_feed_ids_with_specific_status( '3' );
404
- $failed_feed_ids = '';
405
-
406
- foreach ( $processing_feeds as $feed ) {
407
- if ( $active_feed_id !== $feed->product_feed_id ) {
408
- $this->update_feed_status( $feed->product_feed_id, 6 );
409
- $failed_feed_ids .= ', ' . $feed->product_feed_id;
410
- }
411
- }
412
-
413
- if ( $failed_feed_ids ) {
414
- $message = sprintf( 'Starting the update of feed %s, the following feeds where still registered as being active: %s and are now set to the status FAIL.', $active_feed_id, $failed_feed_ids );
415
- do_action( 'tvc_feed_generation_message', $active_feed_id, $message, 'ERROR' );
416
- }
417
- }
418
-
419
- /**
420
- * Converts feed data items that are send through an ajax call to the corresponding database names.
421
- *
422
- * @param $feed_data
423
- *
424
- * @return array
425
- * @since 2.5.0
426
- *
427
- */
428
- public function convert_ajax_feed_data_to_database_format( $feed_data ) {
429
- $result = array();
430
-
431
- foreach ( $feed_data as $data_item ) {
432
- if ( 'product_feed_id' !== $data_item->name ) {
433
-
434
- if ( 'url' === $data_item->name ) {
435
- $data_item->value = $this->verify_url( $data_item->value );
436
- }
437
-
438
- $result[ $data_item->name ] = $data_item->value;
439
- }
440
- }
441
-
442
- return $result;
443
- }
444
-
445
- /**
446
- * Gets the correct data types from the feed data and puts them into an array in the correct order.
447
- *
448
- * @param $feed_data
449
- * @param $ajax_feed_data
450
- *
451
- * @return array
452
- * @since 2.5.0
453
- *
454
- */
455
- public function get_types_from_feed_data( $feed_data, $ajax_feed_data ) {
456
- $result = array();
457
-
458
- foreach ( $feed_data as $data_key => $value ) {
459
- $feed_item = array_filter(
460
- $ajax_feed_data,
461
- function ( $item ) use ( $data_key ) {
462
- return $item->name == $data_key;
463
- }
464
- );
465
-
466
- array_push( $result, reset( $feed_item )->type );
467
- }
468
-
469
- return $result;
470
- }
471
-
472
- /**
473
- * @param $feed_id
474
- * @return bool|stdClass
475
- */
476
- public function get_feed_data( $feed_id ) {
477
- // get the main data
478
- $main_feed_data = $this->_queries_class->read_feed( $feed_id );
479
- $main_data = $this->convert_data_to_feed_data( $main_feed_data[0] );
480
-
481
- if ( false === $main_data ) {
482
- return $main_data;
483
- }
484
-
485
- $main_data->attributes = array();
486
-
487
- $channel = trim( $this->_queries_class->get_channel_short_name_from_db( $main_feed_data[0]['channel'] ) );
488
- $is_custom = function_exists( 'tvc_channel_is_custom_channel' ) ? tvc_channel_is_custom_channel( $channel ) : false;
489
-
490
- // read the output fields
491
- if ( ! $is_custom ) {
492
- $outputs = apply_filters( 'tvc_get_feed_attributes', $this->_files_class->get_output_fields_for_specific_channel( $channel ), $feed_id, $main_feed_data[0]['feed_type_id'] );
493
- } else {
494
- $outputs = $this->get_custom_fields_with_metadata( $feed_id );
495
- }
496
-
497
- // add meta data to the feeds output fields
498
- $output_fields = $this->fill_output_fields_with_metadata( $feed_id, $outputs );
499
- $inputs = $this->get_advised_inputs( $main_data->channel, $main_feed_data[0]['feed_type_id'] );
500
-
501
- for ( $i = 0; $i < count( $output_fields ); $i ++ ) {
502
- $output_title = $output_fields[ $i ]->field_label;
503
- $is_active = false;
504
-
505
- if ( $output_fields[ $i ]->category_id > 0 && $output_fields[ $i ]->category_id < 3 ) {
506
- $is_active = true;
507
- }
508
- if ( ! empty( $output_fields[ $i ]->value ) && 'undefined' !== $output_fields[ $i ]->value ) {
509
- $is_active = true;
510
- }
511
-
512
- $advised_source = property_exists( $inputs, $output_title ) ? $advised_source = $inputs->{$output_title} : '';
513
- $this->add_attribute( $main_data->attributes, $i, $output_title, $advised_source, $output_fields[ $i ]->value, $output_fields[ $i ]->category_id, $is_active, 0, 0, 0 );
514
- }
515
-
516
- $this->set_output_attribute_levels( $main_data );
517
-
518
- return $main_data;
519
- }
520
-
521
- /**
522
- * @param $main_data
523
- */
524
- // ALERT has a relation with the tvc_setOutputAttributeLevels() function in the logic.js file
525
- private function set_output_attribute_levels( &$main_data ) {
526
- $channel_base_class = new TVC_Channel();
527
- $channel_short_name = $channel_base_class->get_channel_short_name( $main_data->channel );
528
-
529
- if ( class_exists( 'TVC_' . ucfirst( $channel_short_name ) . '_Feed_Class' ) ) {
530
- $class_name = 'TVC_' . ucfirst( $channel_short_name ) . '_Feed_Class';
531
- $feed_class = new $class_name();
532
-
533
- if ( method_exists( $feed_class, 'set_feed_output_attribute_levels' ) ) {
534
- $feed_class->set_feed_output_attribute_levels( $main_data );
535
- }
536
- }
537
- }
538
-
539
- /**
540
- * @param $attribute
541
- * @param $id
542
- * @param $title
543
- * @param $advised_source
544
- * @param $value
545
- * @param $field_level
546
- * @param $is_active
547
- * @param $nr_queries
548
- * @param $nr_value_edits
549
- * @param $nr_value_conditions
550
- */
551
- private function add_attribute(
552
- &$attribute, $id, $title, $advised_source, $value, $field_level, $is_active,
553
- $nr_queries, $nr_value_edits, $nr_value_conditions
554
- ) {
555
-
556
- $attribute_object = new stdClass();
557
-
558
- $attribute_object->rowId = $id;
559
- $attribute_object->fieldName = $title;
560
- $attribute_object->advisedSource = $advised_source;
561
- $attribute_object->value = $value;
562
- $attribute_object->fieldLevel = $field_level;
563
- $attribute_object->isActive = $is_active;
564
- $attribute_object->nrQueries = $nr_queries;
565
- $attribute_object->nrValueEdits = $nr_value_edits;
566
- $attribute_object->nrValueConditions = $nr_value_conditions;
567
-
568
- array_push( $attribute, $attribute_object );
569
- }
570
-
571
- /**
572
- * @param $data
573
- * @return bool|stdClass
574
- */
575
- private function convert_data_to_feed_data( $data ) {
576
-
577
- if ( ! key_exists( 'product_feed_id', $data ) ) {
578
- return false;
579
- }
580
-
581
- $feed = new stdClass();
582
-
583
- $feed->feedId = $data['product_feed_id'];
584
- $feed->title = $data['title'];
585
- $feed->mainCategory = $data['main_category'];
586
- $feed->categoryMapping = $data['category_mapping'];
587
- $feed->isAggregator = $data['is_aggregator'];
588
- $feed->includeVariations = $data['include_variations'];
589
- $feed->feedTitle = $data['feed_title'] !== null ? $data['feed_title'] : '';
590
- $feed->feedDescription = $data['feed_description'] !== null ? $data['feed_description'] : '';
591
- $feed->url = $data['url'];
592
- $feed->dataSource = $data['source'];
593
- $feed->channel = $data['channel'];
594
- $feed->country = $data['country'];
595
- $feed->status = $data['status_id'];
596
- $feed->baseStatusId = $data['base_status_id'];
597
- $feed->feedTypeId = $data['feed_type_id'];
598
- $feed->updateSchedule = $data['schedule'];
599
- $feed->language = $data['language'] !== null ? $data['language'] : '';
600
-
601
- return $feed;
602
- }
603
-
604
- /**
605
- * @param $channel_id
606
- * @param $feed_type_id
607
- * @return mixed|void
608
- */
609
- // TVC_CHANNEL_RELATED
610
- private function get_advised_inputs( $channel_id, $feed_type_id ) {
611
- $feed_class = new TVC_Google_Feed_Class();
612
- // as long as only WooCommerce is supported, I can get away with only switching on a specific channel
613
- $advised_inputs = $feed_class->woocommerce_to_feed_fields();
614
- return apply_filters( 'tvc_advised_inputs', $advised_inputs, $feed_type_id );
615
- }
616
-
617
- /**
618
- * Makes sure that the url is correct and has no forbidden characters before it's being stored in the database
619
- *
620
- * @param $url string complete url
621
- *
622
- * @return string verified url
623
- */
624
- private function verify_url( $url ) {
625
- $forbidden_name_chars = tvc_forbidden_file_name_characters();
626
- $last_slash = strrpos( $url, '/' );
627
- $url_string = substr( $url, 0, $last_slash + 1 );
628
- $feed_name = substr( $url, $last_slash + 1 );
629
- $correct_feed_name = str_replace( $forbidden_name_chars, '-', $feed_name );
630
- return $url_string . $correct_feed_name;
631
- }
632
-
633
- /**
634
- * @param $channel_short_name
635
- * @param $channel_data
636
- */
637
- public function register_channel( $channel_short_name, $channel_data ) {
638
- if ( ! $this->_queries_class->get_channel_id( $channel_short_name ) ) { // make sure the channel is not yet registered
639
- $this->_queries_class->register_a_channel( $channel_short_name, $channel_data->channel_id, $channel_data->channel_name );
640
- }
641
- }
642
-
643
- /**
644
- * @param $attributes
645
- * @param $feeds
646
- * @param $product_attributes
647
- * @param $product_taxonomies
648
- * @param $third_party_fields
649
- * @return mixed
650
- */
651
- private function combine_custom_attributes_and_feeds( $attributes, $feeds, $product_attributes, $product_taxonomies, $third_party_fields ) {
652
- $prev_dup_array = array(); // used to prevent doubles
653
-
654
- foreach ( $feeds as $feed ) {
655
- $obj = new stdClass();
656
-
657
- $obj->attribute_name = $feed;
658
- $obj->attribute_label = $feed;
659
-
660
- array_push( $attributes, $obj );
661
- array_push( $prev_dup_array, $obj->attribute_label );
662
- }
663
-
664
- foreach ( $product_taxonomies as $taxonomy ) {
665
- if ( ! in_array( $taxonomy, $prev_dup_array ) ) {
666
- $obj = new stdClass();
667
- $obj->attribute_name = $taxonomy;
668
- $obj->attribute_label = $taxonomy;
669
-
670
- array_push( $attributes, $obj );
671
- array_push( $prev_dup_array, $taxonomy );
672
- }
673
- }
674
-
675
- foreach ( $product_attributes as $attribute_string ) {
676
- $attribute_object = maybe_unserialize( $attribute_string->meta_value );
677
-
678
- if ( $attribute_object && ( is_object( $attribute_object ) || is_array( $attribute_object ) ) ) {
679
- foreach ( $attribute_object as $attribute ) {
680
- if ( ! in_array( $attribute['name'], $prev_dup_array ) ) {
681
- $obj = new stdClass();
682
- $obj->attribute_name = $attribute['name'];
683
- $obj->attribute_label = $attribute['name'];
684
-
685
- array_push( $attributes, $obj );
686
- array_push( $prev_dup_array, $attribute['name'] );
687
- }
688
- }
689
- } else {
690
- if ( $attribute_object ) {
691
- tvc_write_log_file( $attribute_object, 'debug' );
692
- }
693
- }
694
- }
695
-
696
- foreach ( $third_party_fields as $field_label ) {
697
- if ( ! in_array( $field_label, $prev_dup_array ) ) {
698
- $obj = new stdClass();
699
- $obj->attribute_name = $field_label;
700
- $obj->attribute_label = $field_label;
701
-
702
- array_push( $attributes, $obj );
703
- array_push( $prev_dup_array, $field_label );
704
- }
705
- }
706
- return $attributes;
707
- }
708
- }
709
- // end of TVC_Data_Class
710
-
711
- endif;
712
-
713
- $dataclass = new TVC_Data();
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-db-management.php DELETED
@@ -1,325 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Db Management Class.
5
- *
6
- * @package TVC Product Feed Manager/Data/Classes
7
- * @version 1.9.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Db_Management' ) ) :
15
-
16
- /**
17
- * Db Management Class
18
- */
19
- class TVC_Db_Management {
20
-
21
- public static function table_exists( $table_name ) {
22
- global $wpdb;
23
-
24
- if ( $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $wpdb->prefix . $table_name ) ) === $wpdb->prefix . $table_name ) {
25
- return true;
26
- } else {
27
- return false;
28
- }
29
- }
30
-
31
- /**
32
- * Makes a duplicate of a selected feed and stores it in the database.
33
- *
34
- * @param string $feed_id Feed id of the feed that needs to be duplicated.
35
- *
36
- * @return boolean False if duplication process failed.
37
- */
38
- public static function duplicate_feed( $feed_id ) {
39
- $queries_class = new TVC_Queries();
40
- $support_class = new TVC_Feed_Support();
41
-
42
- // Get the feed data.
43
- $feed_data = $queries_class->get_feed_row( $feed_id );
44
-
45
- // Get the meta data.
46
- $meta_data = $queries_class->read_metadata( $feed_id );
47
-
48
- // Get the Feed Filter data.
49
- $feed_filter_data = $queries_class->get_product_filter_query( $feed_id );
50
-
51
- // Get the category mapping.
52
- $category_mapping = $queries_class->read_category_mapping( $feed_id );
53
-
54
- // Generate a new unique feed name.
55
- $feed_data->title = $support_class->next_unique_feed_name( $feed_data->title );
56
- $feed_data->url = esc_html__( 'Feed needs to be generated first', 'tvc-product-feed-manager' );
57
-
58
- $feed_data_to_store = array(
59
- 'channel_id' => $feed_data->channel_id,
60
- 'language' => $feed_data->language,
61
- 'is_aggregator' => $feed_data->is_aggregator,
62
- 'include_variations' => $feed_data->include_variations,
63
- 'country_id' => $feed_data->country_id,
64
- 'source_id' => $feed_data->source_id,
65
- 'title' => $feed_data->title,
66
- 'feed_title' => $feed_data->feed_title,
67
- 'feed_description' => $feed_data->feed_description,
68
- 'main_category' => $feed_data->main_category,
69
- 'url' => $feed_data->url,
70
- 'status_id' => $feed_data->status_id,
71
- 'schedule' => $feed_data->schedule,
72
- 'products' => 0,
73
- 'feed_type_id' => $feed_data->feed_type_id,
74
- 'aggregator_name' => $feed_data->aggregator_name,
75
- 'publisher_name' => $feed_data->publisher_name,
76
- 'publisher_favicon_url' => $feed_data->publisher_favicon_url,
77
- );
78
-
79
- $feed_data_types = array(
80
- '%d',
81
- '%s',
82
- '%d',
83
- '%d',
84
- '%d',
85
- '%d',
86
- '%s',
87
- '%s',
88
- '%s',
89
- '%s',
90
- '%s',
91
- '%d',
92
- '%s',
93
- '%d',
94
- '%d',
95
- '%s',
96
- '%s',
97
- '%s',
98
- );
99
-
100
- // Store a copy of the new feed in the database.
101
- $new_feed_id = $queries_class->create_feed( $feed_data_to_store, $feed_data_types );
102
-
103
- return $new_feed_id > 0 ? $queries_class->insert_meta_data( $new_feed_id, $meta_data, $feed_filter_data, $category_mapping ) : false;
104
- }
105
-
106
- /**
107
- * Backups all plugin related data from the database to a file
108
- *
109
- * @since 1.7.2
110
- *
111
- * @param string $backup_file_name
112
- *
113
- * @return boolean
114
- */
115
- public static function backup_database_tables( $backup_file_name ) {
116
- $backup_class = new TVC_Backup();
117
- $file_class = new TVC_File();
118
-
119
- $backup_file = TVC_BACKUP_DIR . '/' . $backup_file_name . '.sql';
120
- $backup_path = str_replace( '\\', '/', $backup_file );
121
-
122
- // prepare the folder structure to support saving backup files
123
- if ( ! file_exists( TVC_BACKUP_DIR ) ) {
124
- TVC_Folders::make_backup_folder();
125
- }
126
-
127
- if ( ! file_exists( $backup_path ) ) {
128
- $backup_file_text = $backup_class->read_full_backup_data();
129
-
130
- return $file_class->write_full_backup_file( $backup_path, $backup_file_text );
131
- } else {
132
- echo tvc_show_wp_warning( esc_html__( 'A backup file with the selected name already exists. Please choose an other name or delete the existing file first.', 'tvc-product-feed-manager' ) );
133
-
134
- return false;
135
- }
136
- }
137
-
138
- /**
139
- * Checks the existing backup files for non compliant versions
140
- *
141
- * @since 1.8.0
142
- *
143
- * @return boolean true if a non compliant backup file exists
144
- */
145
- public static function invalid_backup_exist() {
146
- if ( ! file_exists( TVC_BACKUP_DIR ) ) {
147
- return false;
148
- }
149
-
150
- $files = tvc_list_sql_files( TVC_BACKUP_DIR );
151
-
152
- if ( count( $files ) === 0 ) {
153
- return false;
154
- }
155
-
156
- foreach ( $files as $file ) {
157
- $backup_string = file_get_contents( $file );
158
-
159
- // get the db version
160
- $backup_version_string = ltrim( substr( $backup_string, stripos( $backup_string, '#' ) ), '#' );
161
- $backup_db_version = substr( $backup_version_string, 0, strpos( $backup_version_string, '#' ) );
162
-
163
- if ( $backup_db_version < get_option( 'tvc_db_version' ) ) {
164
- return true;
165
- }
166
- }
167
-
168
- return false;
169
- }
170
-
171
- /**
172
- * Restores the data from a backup file
173
- *
174
- * @since 1.7.2
175
- *
176
- * @param string name of the backup file
177
- *
178
- * @return boolean if restored successfully, string when not
179
- */
180
- public static function restore_backup( $backup_file_name ) {
181
- $backup_class = new TVC_Backup();
182
-
183
- $backup_file = TVC_BACKUP_DIR . '/' . $backup_file_name;
184
- $backup_path = str_replace( '\\', '/', $backup_file );
185
-
186
- $current_db_version = get_option( 'tvc_db_version' );
187
-
188
- if ( file_exists( $backup_path ) ) {
189
- $table_queries = array();
190
- $backup_string = file_get_contents( $backup_file );
191
-
192
- // remove the date string
193
- $backup_string = substr( $backup_string, stripos( $backup_string, '#' ) );
194
-
195
- // get the db version
196
- $backup_db_version = ltrim( $backup_string, '#' );
197
- $backup_db_version = substr( $backup_db_version, 0, strpos( $backup_db_version, '#' ) );
198
-
199
- if ( $backup_db_version < $current_db_version ) {
200
- return esc_html__( 'The backup file is of an older version of the database and can not be restored as it is not compatible with the current database.', 'tvc-product-feed-manager' );
201
- }
202
-
203
- // remove the version
204
- $backup_string = self::remove_left_data_part( $backup_string );
205
-
206
- // remove the ftp passive setting
207
- $backup_string = self::remove_left_data_part( $backup_string );
208
-
209
- // reset the auto feed fix setting
210
- $auto_feed_fix_setting = ltrim( $backup_string, '#' );
211
- $auto_feed_fix_setting = substr( $auto_feed_fix_setting, 1, strpos( $auto_feed_fix_setting, '#' ) );
212
- update_option( 'tvc_auto_feed_fix', $auto_feed_fix_setting );
213
-
214
- // remove the auto feed fix setting
215
- $backup_string = self::remove_left_data_part( $backup_string );
216
-
217
- // reset the disable background option
218
- $disable_background_setting = ltrim( $backup_string, '#' );
219
- $disable_background_setting = substr( $disable_background_setting, 1, strpos( $disable_background_setting, '#' ) );
220
- update_option( 'tvc_disabled_background_mode', $disable_background_setting );
221
-
222
- // remove the disable background option string
223
- $backup_string = self::remove_left_data_part( $backup_string );
224
-
225
- // reset the show product identifiers option string
226
- $show_product_identifiers_setting = ltrim( $backup_string, '#' );
227
- $show_product_identifiers_setting = substr( $show_product_identifiers_setting, 1, strpos( $show_product_identifiers_setting, '#' ) );
228
- update_option( 'tvc_show_product_identifiers', $show_product_identifiers_setting );
229
-
230
- // remove the show product identifiers option string
231
- $backup_string = self::remove_left_data_part( $backup_string );
232
-
233
- // split the string in table specific rows
234
- $table_strings = explode( '# backup string for database -> ', $backup_string );
235
-
236
- foreach ( $table_strings as $string ) {
237
- $table_name = substr( $string, 0, stripos( $string, '#' ) );
238
- $query_string = substr( $string, stripos( $string, '#' ), strlen( $string ) );
239
- array_push( $table_queries, [ trim( $table_name ), ltrim( $query_string, '# <- # ' ) ] );
240
- }
241
-
242
- // remove the first (empty) element
243
- array_shift( $table_queries );
244
-
245
- return $backup_class->restore_backup_data( $table_queries );
246
- } else {
247
- return esc_html__( 'A backup file with the selected name does not exists.', 'tvc-product-feed-manager' );
248
- }
249
- }
250
-
251
- /**
252
- * Deletes an existing backup file
253
- *
254
- * @since 1.7.2
255
- *
256
- * @param string name of the backup file to be deleted
257
- */
258
- public static function delete_backup_file( $backup_file_name ) {
259
- $backup_file = TVC_BACKUP_DIR . '/' . $backup_file_name;
260
-
261
- // only return results when the user is an admin with manage options
262
- if ( is_admin() ) {
263
- /* translators: %s: Selected backup file */
264
- echo file_exists( $backup_file ) ? unlink( $backup_file ) : tvc_show_wp_error( sprintf( esc_html__( 'Could not find file %s.', 'tvc-product-feed-manager' ), $backup_file ) );
265
- } else {
266
- echo tvc_show_wp_error( esc_html__( 'Error deleting the feed. You do not have the correct authorities to delete the file.', 'tvc-product-feed-manager' ) );
267
- }
268
- }
269
-
270
- /**
271
- * Duplicate an existing backup file
272
- *
273
- * @since 1.7.2
274
- *
275
- * @param string name of the backup file to be duplicated
276
- */
277
- public static function duplicate_backup_file( $backup_file_name ) {
278
- $support_class = new TVC_Feed_Support();
279
-
280
- $backup_file_name_without_extension = rtrim( $backup_file_name, '.sql' );
281
- $new_backup_file_title = $support_class->next_unique_feed_name( $backup_file_name_without_extension );
282
- $new_backup_file_name = $new_backup_file_title . '.sql';
283
-
284
- if ( ! copy( TVC_BACKUP_DIR . '/' . $backup_file_name, TVC_BACKUP_DIR . '/' . $new_backup_file_name ) ) {
285
- /* translators: %s: selected backup file name */
286
- sprintf( esc_html__( 'Failed to make a copy of %s', 'tvc-product-feed-manager' ), $backup_file_name );
287
- } else {
288
- echo true;
289
- }
290
- }
291
-
292
- /**
293
- * Clears several options that could hinder a new feed process.
294
- */
295
- public static function clean_options_table() {
296
- // @since 2.10.0.
297
- delete_option( 'tvc_processed_products' );
298
-
299
- $queries_class = new TVC_Queries();
300
- $queries_class->clear_feed_batch_options();
301
- // also clear the multi site feed batch data
302
- if ( is_multisite() ) {
303
- $queries_class->clear_feed_batch_sitemeta();
304
- }
305
- }
306
-
307
- /**
308
- * Resets the status_id's of failed feeds.
309
- *
310
- * @since 2.7.0
311
- */
312
- public static function reset_status_of_failed_feeds() {
313
- $queries_class = new TVC_Queries();
314
- $queries_class->reset_all_feed_status();
315
- }
316
-
317
- private static function remove_left_data_part( $data_string ) {
318
- $ds = ltrim( $data_string, '#' );
319
-
320
- return substr( $ds, stripos( $ds, '#' ) );
321
- }
322
- }
323
-
324
-
325
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-tab.php DELETED
@@ -1,126 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Tab Class.
5
- *
6
- * @package TVC Product Feed Manager/Data/Classes
7
- * @version 1.0.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Tab' ) ) :
15
-
16
- class TVC_Tab {
17
-
18
- /*
19
- * Contains the page identifier string
20
- */
21
- private $_page_identifier;
22
-
23
- /*
24
- * Is the selected tab or not
25
- */
26
- private $_tab_status;
27
-
28
- /*
29
- * Contains the title of the tab
30
- */
31
- private $_tab_title;
32
-
33
- /*
34
- * Contains a class identifier
35
- */
36
- private $_class_identifier;
37
-
38
- /**
39
- * TVC_Tab constructor.
40
- *
41
- * @param string $page_identifier
42
- * @param bool $tab_status
43
- * @param string $tab_title
44
- * @param string $class_identifier
45
- */
46
- public function __construct( $page_identifier, $tab_status, $tab_title, $class_identifier ) {
47
-
48
- $this->_page_identifier = $page_identifier;
49
- $this->_tab_status = $tab_status;
50
- $this->_tab_title = $tab_title;
51
- $this->_class_identifier = $class_identifier;
52
- }
53
-
54
- /**
55
- * Returns the tabs url parameters page and tab
56
- *
57
- * @return string
58
- */
59
- public function get_page_tab_url() {
60
- return 'page=tvc-product-feed-manager&tab=' . $this->_page_identifier;
61
- }
62
-
63
- public function get_page_identifier() {
64
- return $this->_page_identifier;
65
- }
66
-
67
- public function get_class_identifier() {
68
- return $this->_class_identifier;
69
- }
70
-
71
- /**
72
- * Returns a string that can be used in the tabs html code to identify it as the active tab
73
- *
74
- * @return string
75
- */
76
- public function tab_selected_string() {
77
- return $this->_tab_status ? ' nav-tab-active' : '';
78
- }
79
-
80
- /**
81
- * Returns the tab title
82
- *
83
- * @return string
84
- */
85
- public function get_tab_title() {
86
- return $this->_tab_title;
87
- }
88
-
89
- /**
90
- * Returns the main input wrapper class name
91
- *
92
- * @return string
93
- */
94
- public function get_main_input_wrapper_class() {
95
- return 'TVC_' . $this->_class_identifier . '_Main_Input_Wrapper';
96
- }
97
-
98
- /**
99
- * Returns the category selector wrapper class name
100
- *
101
- * @return string
102
- */
103
- public function get_category_selector_wrapper_class() {
104
- return 'TVC_' . $this->_class_identifier . '_Category_Wrapper';
105
- }
106
-
107
- /**
108
- * Returns the attribute mapping wrapper class name
109
- *
110
- * @return string
111
- */
112
- public function get_attribute_mapping_wrapper_class() {
113
- return 'TVC_' . $this->_class_identifier . '_Attribute_Mapping_Wrapper';
114
- }
115
-
116
- /**
117
- * Set this tab as the selected tab
118
- */
119
- public function set_tab_as_selected() {
120
- $this->_tab_status = true;
121
- }
122
- }
123
-
124
- // end of TVC_Tab class
125
-
126
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/class-tvc-variations.php DELETED
@@ -1,85 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Feed Manager Variations Class.
5
- *
6
- * @package TVC Product Feed Manager/Data/Classes
7
- * @version 1.9.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Variations' ) ) :
15
-
16
- /**
17
- * Variations Class
18
- */
19
- class TVC_Variations {
20
-
21
- /**
22
- * Fills the product attributes with the correct variation data
23
- *
24
- * @param array $product_data
25
- * @param WC_Product_Variation $woocommerce_variation_data
26
- * @param array $wpmr_variation_data
27
- * @param string $feed_language
28
- */
29
- public static function fill_product_data_with_variation_data( &$product_data, $woocommerce_variation_data, $wpmr_variation_data, $feed_language ) {
30
- $permalink = array_key_exists( 'permalink', $product_data ) ? $product_data['permalink'] : ''; // some channels don't require permalinks
31
- $conversions = self::variation_conversion_table( $woocommerce_variation_data, $permalink, $feed_language );
32
-
33
- $variation_attributes = $woocommerce_variation_data->get_variation_attributes();
34
-
35
- foreach ( $product_data as $key => $field_value ) {
36
- if ( in_array( $key, array_keys( $conversions ) ) && $field_value !== $conversions[ $key ] && $conversions[ $key ] ) {
37
- $product_data[ $key ] = $conversions[ $key ];
38
- }
39
-
40
- if ( array_key_exists( $key, $variation_attributes ) && $variation_attributes[ $key ] ) {
41
- $slug_value = $variation_attributes[ $key ];
42
- $product_data[ $key ] = get_term_by( 'slug', $slug_value, ltrim( $key, 'attribute_' ) )->name;
43
- continue;
44
- }
45
-
46
- if ( array_key_exists( 'attribute_pa_' . $key, $variation_attributes ) && $variation_attributes[ 'attribute_pa_' . $key ] ) {
47
- $slug_value = $variation_attributes[ 'attribute_pa_' . $key ];
48
- $product_data[ $key ] = get_term_by( 'slug', $slug_value, 'pa_' . $key )->name;
49
- continue;
50
- }
51
-
52
- if ( $wpmr_variation_data && array_key_exists( $key, $wpmr_variation_data ) ) {
53
- $product_data[ $key ] = $wpmr_variation_data[ $key ];
54
- }
55
- }
56
- }
57
-
58
- private static function variation_conversion_table( $variation_data, $main_permalink, $feed_language ) {
59
- return array(
60
- 'ID' => (string) $variation_data->get_id(),
61
- '_downloadable' => $variation_data->get_downloadable( 'feed' ),
62
- '_virtual' => $variation_data->get_virtual( 'feed' ),
63
- '_manage_stock' => $variation_data->get_manage_stock( 'feed' ),
64
- '_stock' => $variation_data->get_stock_quantity( 'feed' ),
65
- '_backorders' => $variation_data->get_backorders( 'feed' ),
66
- '_stock_status' => $variation_data->get_stock_status( 'feed' ),
67
- '_sku' => $variation_data->get_sku( 'feed' ),
68
- '_weight' => $variation_data->get_weight( 'feed' ),
69
- '_length' => $variation_data->get_length( 'feed' ),
70
- '_width' => $variation_data->get_width( 'feed' ),
71
- '_height' => $variation_data->get_height( 'feed' ),
72
- 'post_content' => $variation_data->get_description( 'feed' ),
73
- '_regular_price' => tvc_prep_money_values( $variation_data->get_regular_price( 'feed' ), $feed_language ),
74
- '_sale_price' => tvc_prep_money_values( $variation_data->get_sale_price( 'feed' ), $feed_language ),
75
- '_sale_price_dates_from' => $variation_data->get_date_on_sale_from( 'feed' ) && ( $date = $variation_data->get_date_on_sale_from( 'feed' )->getTimestamp() ) ? tvc_convert_price_date_to_feed_format( $date ) : '',
76
- '_sale_price_dates_to' => $variation_data->get_date_on_sale_to( 'feed' ) && ( $date = $variation_data->get_date_on_sale_to( 'feed' )->getTimestamp() ) ? tvc_convert_price_date_to_feed_format( $date ) : '',
77
- 'attachment_url' => wp_get_attachment_url( get_post_thumbnail_id( $variation_data->get_id() ) ),
78
- 'permalink' => $main_permalink,
79
- );
80
- }
81
- }
82
-
83
- // End of TVC_Variations_Class
84
-
85
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/data/tvc-admin-functions.php DELETED
@@ -1,372 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * @package TVC Product Feed Manager/Data/Functions
5
- * @version 2.7.0
6
- */
7
-
8
- if ( ! defined( 'ABSPATH' ) ) {
9
- exit;
10
- }
11
-
12
- /**
13
- * Converts a string containing a date-time stamp as stored in the meta data to a date time string
14
- * that can be used in a feed file
15
- *
16
- * @param string $date_stamp The timestamp that needs to be converted to a string that can be stored in a feed file
17
- *
18
- * @return string A string containing the time or an empty string if the $date_stamp is empty
19
- * @since 1.1.0
20
- *
21
- */
22
- function tvc_convert_price_date_to_feed_format( $date_stamp ) {
23
- if ( $date_stamp ) {
24
- // register the date
25
- $feed_string = date( 'Y-m-d', $date_stamp );
26
-
27
- // if set, add the time
28
- if ( date( 'H', $date_stamp ) !== '00' || date( 'i', $date_stamp ) !== '00' || date( 's', $date_stamp ) !== '00' ) {
29
- $feed_string .= 'T' . date( 'H:i:s', $date_stamp );
30
- }
31
-
32
- return $feed_string;
33
- } else {
34
- return '';
35
- }
36
- }
37
-
38
- /**
39
- * After a channel has been updated this function decreases the 'tvc_channels_to_update' option with one
40
- *
41
- * @since 1.4.1
42
- */
43
- function tvc_decrease_update_ready_channels() {
44
- $old = get_option( 'tvc_channels_to_update' );
45
-
46
- if ( $old > 0 ) {
47
- update_option( 'tvc_channels_to_update', $old - 1 );
48
- } else {
49
- update_option( 'tvc_channels_to_update', 0 );
50
- }
51
- }
52
-
53
- /**
54
- * Checks the current database version and updates it if required
55
- *
56
- * @since 2.4.0
57
- */
58
- function tvc_check_db_version() {
59
- $db_management = new TVC_Database_Management();
60
- $db_management->verify_db_version();
61
- }
62
-
63
- /**
64
- * Checks if a specific source key is a money related key or not
65
- *
66
- * @param string $key The source key to be checked
67
- *
68
- * @return boolean True if the source key is money related, false if not
69
- * @since 1.1.0
70
- *
71
- */
72
- function tvc_meta_key_is_money( $key ) {
73
- // money keys
74
- $special_price_keys = array(
75
- '_max_variation_price',
76
- '_max_variation_regular_price',
77
- '_max_variation_sale_price',
78
- '_min_variation_price',
79
- '_min_variation_regular_price',
80
- '_min_variation_sale_price',
81
- '_regular_price',
82
- '_sale_price',
83
- );
84
-
85
- return in_array( $key, $special_price_keys ) ? true : false;
86
- }
87
-
88
- /**
89
- * Takes a value and formats it to a money value using the WooCommerce thousands separator, decimal separator and number of decimals values
90
- *
91
- * @param string $money_value The money value to be formatted
92
- * @param string $feed_language Selected Language in WPML add-on, leave empty if no exchange rate correction is required @since 1.9.0
93
- *
94
- * @return string A formatted money value
95
- * @since 1.9.0 added WPML support
96
- *
97
- * @since 1.1.0
98
- */
99
- function tvc_prep_money_values( $money_value, $feed_language = '' ) {
100
- $thousand_separator = get_option( 'woocommerce_price_thousand_sep' );
101
-
102
- if ( ! is_float( $money_value ) ) {
103
- $val = tvc_number_format_parse( $money_value );
104
- $money_value = floatval( $val );
105
- }
106
-
107
- if ( has_filter( 'tvc_wpml_exchange_money_values' ) ) {
108
- return apply_filters( 'tvc_wpml_exchange_money_values', $money_value, $feed_language );
109
- } else {
110
- $decimal_point = get_option( 'woocommerce_price_decimal_sep' );
111
- $number_decimals = absint( get_option( 'woocommerce_price_num_decimals', 2 ) );
112
-
113
- // To prevent Google Merchant Centre to interpret a thousand separator as a decimal separator we need to remove
114
- // the thousand separator if the decimals setting in WC is 0 and a period is used as decimal separator. Eg 1.452 would be interpreted by Google as 1,452.
115
- // @since 2.11.0
116
- if ( 0 === $number_decimals && '.' === $thousand_separator ) {
117
- $thousand_separator = '';
118
- }
119
-
120
- return number_format( $money_value, $number_decimals, $decimal_point, $thousand_separator );
121
- }
122
- }
123
-
124
- /**
125
- * Checks if there are invalid backups
126
- *
127
- * @return boolean true if there are no backups or these backups are current
128
- * @since 1.8.0
129
- *
130
- */
131
- function tvc_check_backup_status() {
132
- if ( ! TVC_Db_Management::invalid_backup_exist() ) {
133
- return true;
134
- } else {
135
- return false;
136
- }
137
- }
138
-
139
- /**
140
- * Checks a folder given by $path for sql files and returns their names including the path
141
- *
142
- * @param $path
143
- * @since 2.6.0
144
- *
145
- * @return array
146
- */
147
- function tvc_list_sql_files( $path ) {
148
- $files = array();
149
-
150
- if ( is_dir( $path ) ) {
151
- $handle = opendir( $path );
152
- if ( $handle ) {
153
- while ( false !== ( $name = readdir( $handle ) ) ) {
154
- if ( preg_match( '/[a-zA-Z0-9-_ ]{2,}[.](sql)$/', $name ) ) {
155
- $files[] = $path . '/' . $name;
156
- }
157
- }
158
- }
159
- }
160
-
161
- return $files;
162
- }
163
-
164
- /**
165
- * Forces the database to load and update and adds the auto update cron event if it does not exists
166
- *
167
- * @return boolean
168
- * @since 1.9.0
169
- *
170
- */
171
- function tvc_reinitiate_plugin() {
172
- if ( ! wp_get_schedule( 'tvc_feed_update_schedule' ) ) {
173
- // add the schedule cron
174
- wp_schedule_event( time(), 'hourly', 'tvc_feed_update_schedule' );
175
- add_action( 'tvc_feed_update_schedule', 'activate_feed_update_schedules' );
176
- }
177
-
178
- // remakes the database
179
- $db = new TVC_Database_Management();
180
- $db->force_reinitiate_db();
181
-
182
- $plugin_prefixes = apply_filters( 'tvc_edd_plugin_prefix_list', array( 'tvc' ) );
183
-
184
- // resets the license nr
185
- foreach ( $plugin_prefixes as $plugin_prefix ) {
186
- delete_option( $plugin_prefix . '_lic_status' );
187
- delete_option( $plugin_prefix . '_lic_status_date' );
188
- delete_option( $plugin_prefix . '_lic_key' );
189
- delete_option( $plugin_prefix . '_lic_expires' );
190
- delete_option( $plugin_prefix . '_license_notice_suppressed' );
191
- }
192
-
193
- // reset the keyed options
194
- TVC_Db_Management::clean_options_table();
195
-
196
- do_action( 'tvc_plugin_reinitialized' );
197
-
198
- return true;
199
- }
200
-
201
- /**
202
- * Recursively implodes an array
203
- *
204
- * @since 2.8.0
205
- *
206
- * @param array $array
207
- * @param string $glue
208
- * @param bool $include_keys
209
- * @param bool $trim_all
210
- *
211
- * @return string
212
- */
213
- function tvc_recursive_implode( array $array, $glue = ',', $include_keys = false, $trim_all = true ) {
214
- $glued_string = '';
215
-
216
- // Recursively iterates array and adds key/value to glued string
217
- array_walk_recursive(
218
- $array,
219
- function ( $value, $key ) use ( $glue, $include_keys, &$glued_string ) {
220
- $include_keys and $glued_string .= $key . ' => ';
221
- $glued_string .= $value . $glue;
222
- }
223
- );
224
-
225
- // Removes last $glue from string
226
- if ( strlen( $glue ) > 0 && $glued_string ) {
227
- substr( $glued_string, 0, - strlen( $glue ) );
228
- }
229
-
230
- // Trim ALL whitespace
231
- if ( $trim_all && $glued_string ) {
232
- preg_replace( '/(\s)/ixsm', '', $glued_string );
233
- }
234
-
235
- return (string) $glued_string;
236
- }
237
-
238
- function tvc_clear_feed_process_data() {
239
- TVC_Feed_Controller::clear_feed_queue();
240
- TVC_Feed_Controller::set_feed_processing_flag( false );
241
- TVC_Db_Management::clean_options_table();
242
- TVC_Db_Management::reset_status_of_failed_feeds();
243
-
244
- do_action( 'tvc_feed_process_data_cleared' );
245
-
246
- return true;
247
- }
248
-
249
- /**
250
- * Takes a string with spaces and capital letters and converts it to a string with dashes and lower case letters
251
- *
252
- * @param $string_with_dashes
253
- *
254
- * @return string
255
- */
256
- function tvc_convert_string_with_spaces_to_lower_case_string_with_dashes( $string_with_dashes ) {
257
- return strtolower( str_replace( ' ', '-', $string_with_dashes ) );
258
- }
259
-
260
- /**
261
- * Converts any number string to a string with a number that has no thousands separator
262
- * and a period as decimal separator
263
- *
264
- * @param string $number_string
265
- *
266
- * @return string
267
- */
268
- function tvc_number_format_parse( $number_string ) {
269
- $decimal_separator = get_option( 'woocommerce_price_decimal_sep' );
270
- $thousand_separator = get_option( 'woocommerce_price_thousand_sep' );
271
-
272
- // convert a number string that is a actual standard number format whilst the woocommerce options are not standard
273
- // to the woocommerce standard. This sometimes happens with meta values
274
- if ( ! empty( $decimal_separator ) && strpos( $number_string, $decimal_separator ) === false ) {
275
- $number_string = ! empty( $thousand_separator ) && strpos( $number_string, $thousand_separator ) === false ? $number_string : str_replace( $thousand_separator, $decimal_separator, $number_string );
276
- }
277
-
278
- $no_thousands_sep = str_replace( $thousand_separator, '', $number_string );
279
-
280
- return '.' !== $decimal_separator ? str_replace( $decimal_separator, '.', $no_thousands_sep ) : $no_thousands_sep;
281
- }
282
-
283
- /**
284
- * returns the path to the feed file including feed name and extension
285
- *
286
- * @param string $feed_name
287
- *
288
- * @return string
289
- */
290
- function tvc_get_file_path( $feed_name ) {
291
- $forbidden_name_chars = tvc_forbidden_file_name_characters();
292
- $feed_name = str_replace( $forbidden_name_chars, '-', $feed_name );
293
-
294
- // previous to plugin version 1.3.0 feeds where stored in the plugins but after that version they are stored in the upload folder
295
- if ( file_exists( WP_PLUGIN_DIR . '/tvc-product-feed-manager-support/feeds/' . $feed_name ) ) {
296
- return WP_PLUGIN_DIR . '/tvc-product-feed-manager-support/feeds/' . $feed_name;
297
- } elseif ( file_exists( TVC_FEEDS_DIR . '/' . $feed_name ) ) {
298
- return TVC_FEEDS_DIR . '/' . $feed_name;
299
- } else { // as of version 1.5.0 all spaces in new filenames are replaced by a dash
300
- return TVC_FEEDS_DIR . '/' . $feed_name;
301
- }
302
- }
303
-
304
- /**
305
- * Returns the url of the feed file including feed name and extension.
306
- *
307
- * @param string $feed_name Name of the feed file.
308
- *
309
- * @return string URL to the feed file.
310
- */
311
- function tvc_get_file_url( $feed_name ) {
312
- $forbidden_name_chars = tvc_forbidden_file_name_characters();
313
- $feed_name = str_replace( $forbidden_name_chars, '-', $feed_name );
314
-
315
- // previous to plugin version 1.3.0 feeds where stored in the plugins but after that version they are stored in the upload folder
316
- if ( file_exists( WP_PLUGIN_DIR . '/tvc-product-feed-manager-support/feeds/' . $feed_name ) ) {
317
- $file_url = plugins_url() . '/tvc-product-feed-manager-support/feeds/' . $feed_name;
318
- } else { // as of version 1.5.0 all spaces in new filenames are replaced by a dash
319
- $file_url = TVC_UPLOADS_URL . '/tvc-feeds/' . $feed_name;
320
- }
321
-
322
- return apply_filters( 'tvc_feed_url', $file_url, $feed_name );
323
- }
324
-
325
- /**
326
- * @return array with forbidden characters
327
- */
328
- function tvc_forbidden_file_name_characters() {
329
- return array( ' ', '<', '>', ':', '?', ',' ); // characters that are not allowed in a feed file name
330
- }
331
-
332
- /**
333
- * For backward compatibility, the old feed statuses are converted to all lowercase and without spaces
334
- *
335
- * @param array $list
336
- *
337
- * @since 2.1.0
338
- *
339
- */
340
- function tvc_correct_old_feeds_list_status( &$list ) {
341
- for ( $i = 0; $i < count( $list ); $i ++ ) {
342
- $list[ $i ]->status = strtolower( str_replace( ' ', '_', $list[ $i ]->status ) );
343
- }
344
- }
345
-
346
- /**
347
- * Checks if the WooCommerce plugin is installed and active
348
- *
349
- * @return boolean true if WooCommerce is installed and active, false if not
350
- * @since 2.3.0
351
- */
352
- function tvc_wc_installed_and_active() {
353
- return is_plugin_active( 'woocommerce/woocommerce.php' ) || is_plugin_active_for_network( 'woocommerce/woocommerce.php' ) ? true : false;
354
- }
355
-
356
- /**
357
- * Checks if the WooCommerce plugin has the minimal required version
358
- *
359
- * @return boolean true if WooCommerce version is at least 3.0.0
360
- * @since 2.3.0
361
- */
362
- function tvc_wc_min_version_required() {
363
- // To prevent several PHP Warnings if the WC folder name has been changed whilst the plugin is still registered.
364
- // @since 2.11.0.
365
- if ( ! file_exists( ENHANCAD_PLUGIN_DIR . '../woocommerce/woocommerce.php' ) ) {
366
- return false;
367
- }
368
-
369
- $wc_version = get_plugin_data( ENHANCAD_PLUGIN_DIR . '../woocommerce/woocommerce.php' )['Version'];
370
-
371
- return version_compare( $wc_version, TVC_MIN_REQUIRED_WC_VERSION, '>=' ) ? true : false;
372
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/index.php CHANGED
File without changes
includes/json/client-secrets.json DELETED
@@ -1,26 +0,0 @@
1
- {
2
- "web": {
3
- "client_id": "929004569091-pq3q5mve6nsmhg5lfu2vu5gq44acfp45.apps.googleusercontent.com",
4
- "project_id": "tatvic.com:api-project-929004569091",
5
- "auth_uri": "https://accounts.google.com/o/oauth2/auth",
6
- "token_uri": "https://oauth2.googleapis.com/token",
7
- "auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
8
- "client_secret": "fpZsRhxOq4slRF0advdaT6ZS",
9
- "manager_customer_id": "6847954029",
10
- "manager_refresh_token": "1//0g7GDPfnauJb1CgYIARAAGBASNwF-L9IrqRrwDXC1EZLd_hOzUko6lPxJ-uZ9DlEltKV6QDcY3q9nbDlqFDPFut_2i0vKWGbTtc8",
11
- "developer_token": "Pz7O94tto128j0u1Nl7DAg",
12
- "redirect_uris": [
13
- "https://plugins.tatvic.com/ga_rdr.php",
14
- "https://plugins.tatvic.com/tatdev/ga_rdr.php",
15
- "https://plugins.tatvic.com/tatprod/ga_rdr.php",
16
- "https://plugins.tatvic.com/tat_ga/ga_rdr.php",
17
- "https://plugins.tatvic.com/tat_ga/ga_rdr_new.php",
18
- "https://plugins.tatvic.com/tat_ga/ga_rdr_ee.php",
19
- "https://estorenew.tatvic.com/tat_ee/ga_rdr_ee.php",
20
- "https://estorenew.tatvic.com/test/ga_rdr_ee.php"
21
- ],
22
- "javascript_origins": [
23
- "https://plugins.tatvic.com"
24
- ]
25
- }
26
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/json/currency.json DELETED
@@ -1,252 +0,0 @@
1
- {
2
- "BD": "BDT",
3
- "BE": "EUR",
4
- "BF": "XOF",
5
- "BG": "BGN",
6
- "BA": "BAM",
7
- "BB": "BBD",
8
- "WF": "XPF",
9
- "BL": "EUR",
10
- "BM": "BMD",
11
- "BN": "BND",
12
- "BO": "BOB",
13
- "BH": "BHD",
14
- "BI": "BIF",
15
- "BJ": "XOF",
16
- "BT": "BTN",
17
- "JM": "JMD",
18
- "BV": "NOK",
19
- "BW": "BWP",
20
- "WS": "WST",
21
- "BQ": "USD",
22
- "BR": "BRL",
23
- "BS": "BSD",
24
- "JE": "GBP",
25
- "BY": "BYR",
26
- "BZ": "BZD",
27
- "RU": "RUB",
28
- "RW": "RWF",
29
- "RS": "RSD",
30
- "TL": "USD",
31
- "RE": "EUR",
32
- "TM": "TMT",
33
- "TJ": "TJS",
34
- "RO": "RON",
35
- "TK": "NZD",
36
- "GW": "XOF",
37
- "GU": "USD",
38
- "GT": "GTQ",
39
- "GS": "GBP",
40
- "GR": "EUR",
41
- "GQ": "XAF",
42
- "GP": "EUR",
43
- "JP": "JPY",
44
- "GY": "GYD",
45
- "GG": "GBP",
46
- "GF": "EUR",
47
- "GE": "GEL",
48
- "GD": "XCD",
49
- "GB": "GBP",
50
- "GA": "XAF",
51
- "SV": "USD",
52
- "GN": "GNF",
53
- "GM": "GMD",
54
- "GL": "DKK",
55
- "GI": "GIP",
56
- "GH": "GHS",
57
- "OM": "OMR",
58
- "TN": "TND",
59
- "JO": "JOD",
60
- "HR": "HRK",
61
- "HT": "HTG",
62
- "HU": "HUF",
63
- "HK": "HKD",
64
- "HN": "HNL",
65
- "HM": "AUD",
66
- "VE": "VEF",
67
- "PR": "USD",
68
- "PS": "ILS",
69
- "PW": "USD",
70
- "PT": "EUR",
71
- "SJ": "NOK",
72
- "PY": "PYG",
73
- "IQ": "IQD",
74
- "PA": "PAB",
75
- "PF": "XPF",
76
- "PG": "PGK",
77
- "PE": "PEN",
78
- "PK": "PKR",
79
- "PH": "PHP",
80
- "PN": "NZD",
81
- "PL": "PLN",
82
- "PM": "EUR",
83
- "ZM": "ZMK",
84
- "EH": "MAD",
85
- "EE": "EUR",
86
- "EG": "EGP",
87
- "ZA": "ZAR",
88
- "EC": "USD",
89
- "IT": "EUR",
90
- "VN": "VND",
91
- "SB": "SBD",
92
- "ET": "ETB",
93
- "SO": "SOS",
94
- "ZW": "ZWL",
95
- "SA": "SAR",
96
- "ES": "EUR",
97
- "ER": "ERN",
98
- "ME": "EUR",
99
- "MD": "MDL",
100
- "MG": "MGA",
101
- "MF": "EUR",
102
- "MA": "MAD",
103
- "MC": "EUR",
104
- "UZ": "UZS",
105
- "MM": "MMK",
106
- "ML": "XOF",
107
- "MO": "MOP",
108
- "MN": "MNT",
109
- "MH": "USD",
110
- "MK": "MKD",
111
- "MU": "MUR",
112
- "MT": "EUR",
113
- "MW": "MWK",
114
- "MV": "MVR",
115
- "MQ": "EUR",
116
- "MP": "USD",
117
- "MS": "XCD",
118
- "MR": "MRO",
119
- "IM": "GBP",
120
- "UG": "UGX",
121
- "TZ": "TZS",
122
- "MY": "MYR",
123
- "MX": "MXN",
124
- "IL": "ILS",
125
- "FR": "EUR",
126
- "IO": "USD",
127
- "SH": "SHP",
128
- "FI": "EUR",
129
- "FJ": "FJD",
130
- "FK": "FKP",
131
- "FM": "USD",
132
- "FO": "DKK",
133
- "NI": "NIO",
134
- "NL": "EUR",
135
- "NO": "NOK",
136
- "NA": "NAD",
137
- "VU": "VUV",
138
- "NC": "XPF",
139
- "NE": "XOF",
140
- "NF": "AUD",
141
- "NG": "NGN",
142
- "NZ": "NZD",
143
- "NP": "NPR",
144
- "NR": "AUD",
145
- "NU": "NZD",
146
- "CK": "NZD",
147
- "XK": "EUR",
148
- "CI": "XOF",
149
- "CH": "CHF",
150
- "CO": "COP",
151
- "CN": "CNY",
152
- "CM": "XAF",
153
- "CL": "CLP",
154
- "CC": "AUD",
155
- "CA": "CAD",
156
- "CG": "XAF",
157
- "CF": "XAF",
158
- "CD": "CDF",
159
- "CZ": "CZK",
160
- "CY": "EUR",
161
- "CX": "AUD",
162
- "CR": "CRC",
163
- "CW": "ANG",
164
- "CV": "CVE",
165
- "CU": "CUP",
166
- "SZ": "SZL",
167
- "SY": "SYP",
168
- "SX": "ANG",
169
- "KG": "KGS",
170
- "KE": "KES",
171
- "SS": "SSP",
172
- "SR": "SRD",
173
- "KI": "AUD",
174
- "KH": "KHR",
175
- "KN": "XCD",
176
- "KM": "KMF",
177
- "ST": "STD",
178
- "SK": "EUR",
179
- "KR": "KRW",
180
- "SI": "EUR",
181
- "KP": "KPW",
182
- "KW": "KWD",
183
- "SN": "XOF",
184
- "SM": "EUR",
185
- "SL": "SLL",
186
- "SC": "SCR",
187
- "KZ": "KZT",
188
- "KY": "KYD",
189
- "SG": "SGD",
190
- "SE": "SEK",
191
- "SD": "SDG",
192
- "DO": "DOP",
193
- "DM": "XCD",
194
- "DJ": "DJF",
195
- "DK": "DKK",
196
- "VG": "USD",
197
- "DE": "EUR",
198
- "YE": "YER",
199
- "DZ": "DZD",
200
- "US": "USD",
201
- "UY": "UYU",
202
- "YT": "EUR",
203
- "UM": "USD",
204
- "LB": "LBP",
205
- "LC": "XCD",
206
- "LA": "LAK",
207
- "TV": "AUD",
208
- "TW": "TWD",
209
- "TT": "TTD",
210
- "TR": "TRY",
211
- "LK": "LKR",
212
- "LI": "CHF",
213
- "LV": "EUR",
214
- "TO": "TOP",
215
- "LT": "LTL",
216
- "LU": "EUR",
217
- "LR": "LRD",
218
- "LS": "LSL",
219
- "TH": "THB",
220
- "TF": "EUR",
221
- "TG": "XOF",
222
- "TD": "XAF",
223
- "TC": "USD",
224
- "LY": "LYD",
225
- "VA": "EUR",
226
- "VC": "XCD",
227
- "AE": "AED",
228
- "AD": "EUR",
229
- "AG": "XCD",
230
- "AF": "AFN",
231
- "AI": "XCD",
232
- "VI": "USD",
233
- "IS": "ISK",
234
- "IR": "IRR",
235
- "AM": "AMD",
236
- "AL": "ALL",
237
- "AO": "AOA",
238
- "AQ": "",
239
- "AS": "USD",
240
- "AR": "ARS",
241
- "AU": "AUD",
242
- "AT": "EUR",
243
- "AW": "AWG",
244
- "IN": "INR",
245
- "AX": "EUR",
246
- "AZ": "AZN",
247
- "IE": "EUR",
248
- "ID": "IDR",
249
- "UA": "UAH",
250
- "QA": "QAR",
251
- "MZ": "MZN"
252
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/libraries/tvc-background-process.php DELETED
@@ -1,754 +0,0 @@
1
- <?php
2
-
3
- if ( ! defined( 'ABSPATH' ) ) {
4
- exit;
5
- }
6
-
7
- /**
8
- * Abstract TVC_Background_Process class, derived from https://github.com/A5hleyRich/wp-background-processing.
9
- *
10
- * @abstract
11
- * @package TVC-Background-Processing
12
- * @extends TVC_Async_Request
13
- */
14
- abstract class TVC_Background_Process extends TVC_Async_Request {
15
-
16
- /**
17
- * Action
18
- *
19
- * (default value: 'background_process')
20
- *
21
- * @var string
22
- */
23
- protected $action = 'background_process';
24
-
25
- /**
26
- * Start time of current process.
27
- *
28
- * (default value: 0)
29
- *
30
- * @var int
31
- */
32
- protected $start_time = 0;
33
-
34
- /**
35
- * Cron_hook_identifier
36
- *
37
- * @var mixed
38
- */
39
- protected $cron_hook_identifier;
40
-
41
- /**
42
- * Cron_interval_identifier
43
- *
44
- * @var mixed
45
- */
46
- protected $cron_interval_identifier;
47
-
48
- /**
49
- * Keeps track of the number of products that where added to the feed
50
- *
51
- * @var int
52
- */
53
- protected $processed_products;
54
-
55
- /**
56
- * Initiate new background process
57
- */
58
- public function __construct() {
59
- parent::__construct();
60
-
61
- $this->cron_hook_identifier = $this->identifier . '_cron';
62
- $this->cron_interval_identifier = $this->identifier . '_cron_interval';
63
- $this->processed_products = get_option( 'tvc_processed_products' ) ? explode( ',', get_option( 'tvc_processed_products' ) ) : array();
64
-
65
- add_action( $this->cron_hook_identifier, array( $this, 'handle_cron_health_check' ) );
66
- add_filter( 'cron_schedules', array( $this, 'schedule_cron_health_check' ) );
67
- }
68
-
69
- /**
70
- * Dispatch the feed generation process.
71
- *
72
- * @access public
73
- * @param string $feed_id
74
- *
75
- * @return array
76
- */
77
- public function dispatch( $feed_id ) {
78
- // Schedule the cron health check.
79
- $this->schedule_event();
80
-
81
- // Perform the remote post.
82
- return parent::dispatch( $feed_id );
83
- }
84
-
85
- /**
86
- * Push to queue
87
- *
88
- * @param mixed $data Data.
89
- *
90
- * @return $this
91
- */
92
- public function push_to_queue( $data ) {
93
- $this->data[] = $data;
94
-
95
- return $this;
96
- }
97
-
98
- /**
99
- * Implements the tvc_feed_ids_in_queue filter on the queue.
100
- *
101
- * @param string $feed_id Feed id to enable using the filter on a specific feed.
102
- *
103
- * @since 2.10.0.
104
- * @return mixed|void Filtered queue.
105
- */
106
- public function apply_filter_to_queue( $feed_id ) {
107
- // Remove the feed header from the queue.
108
- $feed_header = array_shift( $this->data );
109
-
110
- // Apply the filter.
111
- $ids = apply_filters( 'tvc_feed_ids_in_queue', $this->data, $feed_id );
112
-
113
- // Add the feed header again.
114
- array_unshift( $ids, $feed_header );
115
-
116
- $this->data = $ids;
117
- }
118
-
119
- /**
120
- * Clears the queue
121
- *
122
- * @return $this
123
- */
124
- public function clear_the_queue() {
125
- $this->data = null;
126
-
127
- return $this;
128
- }
129
-
130
- /**
131
- * Set the path to the feed file
132
- *
133
- * @param string $file_path
134
- *
135
- * @return $this
136
- */
137
- public function set_file_path( $file_path ) {
138
- $this->file_path = $file_path;
139
-
140
- return $this;
141
- }
142
-
143
- /**
144
- * Set the language of the feed
145
- *
146
- * @param array $feed_data
147
- *
148
- * @return $this
149
- */
150
- public function set_feed_data( $feed_data ) {
151
- $this->feed_data = $feed_data;
152
-
153
- return $this;
154
- }
155
-
156
- /**
157
- * Set the feed pre data
158
- *
159
- * @param array $pre_data
160
- *
161
- * @return $this
162
- */
163
- public function set_pre_data( $pre_data ) {
164
- $this->pre_data = $pre_data;
165
-
166
- return $this;
167
- }
168
-
169
- /**
170
- * Set the channel specific main category title and description title
171
- *
172
- * @param array $channel_details
173
- *
174
- * @return $this
175
- */
176
- public function set_channel_details( $channel_details ) {
177
- $this->channel_details = $channel_details;
178
-
179
- return $this;
180
- }
181
-
182
- /**
183
- * Sets the relation table
184
- *
185
- * @param array $relations_table
186
- *
187
- * @return $this
188
- */
189
- public function set_relations_table( $relations_table ) {
190
- $this->relations_table = $relations_table;
191
-
192
- return $this;
193
- }
194
-
195
- /**
196
- * Save queue data.
197
- *
198
- * @param string $feed_id
199
- *
200
- * @return $this
201
- */
202
- public function save( $feed_id ) {
203
- $key = $this->generate_key( $feed_id );
204
-
205
- if ( ! empty( $this->data ) ) {
206
- update_site_option( 'tvc_background_process_key', $key );
207
- update_site_option( $key, $this->data );
208
- update_site_option( 'feed_data_' . $key, $this->feed_data );
209
- update_site_option( 'file_path_' . $key, $this->file_path );
210
- update_site_option( 'pre_data_' . $key, $this->pre_data );
211
- update_site_option( 'channel_details_' . $key, $this->channel_details );
212
- update_site_option( 'relations_table_' . $key, $this->relations_table );
213
- }
214
-
215
- return $this;
216
- }
217
-
218
- /**
219
- * Update queue
220
- *
221
- * @param string $key Key.
222
- * @param array $data Data.
223
- *
224
- * @return $this
225
- */
226
- public function update( $key, $data ) {
227
- if ( ! empty( $data ) ) {
228
- update_site_option( 'tvc_background_process_key', $key );
229
- update_site_option( $key, $data );
230
- }
231
-
232
- return $this;
233
- }
234
-
235
- /**
236
- * Delete queue and properties stored in the options table
237
- *
238
- * @param string $key Key.
239
- *
240
- * @return $this
241
- */
242
- public function delete( $key ) {
243
- delete_site_option( $key );
244
-
245
- return $this;
246
- }
247
-
248
- /**
249
- * Generate key
250
- *
251
- * Generates a unique key based on microtime. Queue items are
252
- * given a unique key so that they can be merged upon save.
253
- *
254
- * @param string $feed_id
255
- * @param int $length Length
256
- *
257
- * @return string
258
- */
259
- protected function generate_key( $feed_id, $length = 64 ) {
260
- $unique = md5( microtime() . rand() );
261
- $prepend = $this->identifier . '_batch_' . $feed_id . '_';
262
-
263
- return substr( $prepend . $unique, 0, $length );
264
- }
265
-
266
- /**
267
- * Maybe process queue
268
- *
269
- * Checks whether data exists within the queue and that
270
- * the process is not already running.
271
- */
272
- public function maybe_handle() {
273
- // Don't lock up other requests while processing
274
- session_write_close();
275
-
276
- $background_mode_disabled = get_option( 'tvc_disabled_background_mode', 'false' );
277
-
278
- if ( 'false' === $background_mode_disabled && $this->is_process_running() ) {
279
- // Background process already running.
280
- wp_die();
281
- }
282
-
283
- if ( $this->is_queue_empty() ) {
284
- // No data to process.
285
- wp_die();
286
- }
287
-
288
- if ( 'false' === $background_mode_disabled ) {
289
- check_ajax_referer( $this->identifier, 'nonce' );
290
- }
291
-
292
- $this->handle();
293
-
294
- if ( 'true' === $background_mode_disabled ) {
295
- echo 'foreground_processing_complete';
296
- }
297
-
298
- wp_die();
299
- }
300
-
301
- /**
302
- * Is queue empty
303
- *
304
- * @return bool
305
- */
306
- protected function is_queue_empty() {
307
- global $wpdb;
308
-
309
- $table = $wpdb->options;
310
- $column = 'option_name';
311
-
312
- if ( is_multisite() ) {
313
- $table = $wpdb->sitemeta;
314
- $column = 'meta_key';
315
- }
316
-
317
- $key = $wpdb->esc_like( $this->identifier . '_batch_' ) . '%';
318
-
319
- $count = $wpdb->get_var(
320
- $wpdb->prepare(
321
- // phpcs:ignore
322
- " SELECT COUNT(*) FROM {$table} WHERE {$column} LIKE %s",
323
- $key
324
- )
325
- );
326
-
327
- return ( $count > 0 ) ? false : true;
328
- }
329
-
330
- /**
331
- * Is process running
332
- *
333
- * Check whether the current process is already running
334
- * in a background process.
335
- */
336
- public function is_process_running() {
337
- if ( get_site_transient( $this->identifier . '_process_lock' ) ) {
338
- // Process already running.
339
- return true;
340
- }
341
-
342
- return false;
343
- }
344
-
345
- /**
346
- * Lock process
347
- *
348
- * Lock the process so that multiple instances can't run simultaneously.
349
- * Override if applicable, but the duration should be greater than that
350
- * defined in the time_exceeded() method.
351
- */
352
- protected function lock_process() {
353
- $this->start_time = time(); // Set start time of current process.
354
-
355
- $lock_duration = ( property_exists( $this, 'queue_lock_time' ) ) ? $this->queue_lock_time : 60; // 1 minute
356
- $lock_duration = apply_filters( $this->identifier . '_queue_lock_time', $lock_duration );
357
-
358
- set_site_transient( $this->identifier . '_process_lock', microtime(), $lock_duration );
359
- }
360
-
361
- /**
362
- * Unlock process
363
- *
364
- * Unlock the process so that other instances can spawn.
365
- *
366
- * @return $this
367
- */
368
- protected function unlock_process() {
369
- delete_site_transient( $this->identifier . '_process_lock' );
370
-
371
- return $this;
372
- }
373
-
374
- /**
375
- * Get batch
376
- *
377
- * @return stdClass|bool Return the first batch from the queue or false if it does not exists.
378
- */
379
- protected function get_batch() {
380
- global $wpdb;
381
-
382
- $table = $wpdb->options;
383
- $column = 'option_name';
384
- $key_column = 'option_id';
385
- $value_column = 'option_value';
386
-
387
- if ( is_multisite() ) {
388
- $table = $wpdb->sitemeta;
389
- $column = 'meta_key';
390
- $key_column = 'meta_id';
391
- $value_column = 'meta_value';
392
- }
393
-
394
- $key = $wpdb->esc_like( $this->identifier . '_batch_' ) . '%';
395
-
396
- $query = $wpdb->get_row(
397
- $wpdb->prepare(
398
- // phpcs:ignore
399
- " SELECT * FROM {$table} WHERE {$column} LIKE %s ORDER BY {$key_column} ASC LIMIT 1",
400
- $key
401
- )
402
- );
403
-
404
- // @since 2.10.0 added an extra validation if the batch still exists.
405
- if ( $query && property_exists( $query, $column ) && property_exists( $query, $value_column ) ) {
406
- $batch = new stdClass();
407
- $batch->key = $query->$column;
408
- $batch->data = maybe_unserialize( $query->$value_column );
409
- } else {
410
- return false;
411
- }
412
-
413
- return $batch;
414
- }
415
-
416
- /**
417
- * Handle
418
- *
419
- * Pass each queue item to the task handler, while remaining
420
- * within server memory and time limit constraints.
421
- *
422
- * @return void|bool
423
- */
424
- protected function handle() {
425
- $this->lock_process();
426
-
427
- do {
428
- $batch = $this->get_batch();
429
-
430
- if ( ! $batch ) { // @since 2.10.0
431
- $this->end_batch( false, 'failed' );
432
- return false;
433
- }
434
-
435
- $properties_key = get_site_option( 'tvc_background_process_key' );
436
- $feed_file_path = get_site_option( 'file_path_' . $properties_key );
437
- $feed_data = get_site_option( 'feed_data_' . $properties_key );
438
- $pre_data = get_site_option( 'pre_data_' . $properties_key );
439
- $channel_details = get_site_option( 'channel_details_' . $properties_key );
440
- $relations_table = get_site_option( 'relations_table_' . $properties_key );
441
-
442
- // phpcs:ignore
443
- $feed_id = $feed_data->feedId;
444
-
445
- // @since 2.10.0.
446
- if ( ! $properties_key ) {
447
- $message = 'Tried to get the next batch but the tvc_background_process_key is empty.';
448
- do_action( 'tvc_feed_generation_message', $feed_id, $message, 'ERROR' );
449
- $this->end_batch( $feed_id, 'failed' );
450
- return false;
451
- }
452
-
453
- // @since 2.10.0.
454
- if ( ! $feed_data || empty( $feed_data ) || ! property_exists( $feed_data, 'feedId' ) ) {
455
- $message = 'Tried to get the next batch the feed data could not be loaded correctly.';
456
- do_action( 'tvc_feed_generation_message', $feed_id, $message, 'ERROR' );
457
- $this->end_batch( false, 'failed' );
458
- return false;
459
- }
460
-
461
- // When in fore-ground mode increase the set time limit to enable larger feeds.
462
- // @since 2.11.0.
463
- if ( 'true' === get_option( 'tvc_disabled_background_mode', 'false' ) && function_exists( 'wc_set_time_limit' ) ) {
464
- wc_set_time_limit( 30 * MINUTE_IN_SECONDS );
465
- }
466
-
467
- $initial_memory = function_exists( 'ini_get' ) ? ini_get( 'memory_limit' ) : 'unknown';
468
-
469
- do_action( 'tvc_feed_processing_batch_activated', $feed_id, $initial_memory, count( $batch->data ) );
470
-
471
- foreach ( $batch->data as $key => $value ) {
472
- // if it's not an array, then its a product id
473
- if ( ! is_array( $value ) ) {
474
- $value = array( 'product_id' => $value );
475
- }
476
-
477
- // prevent doubles in the feed
478
- if ( array_key_exists( 'product_id', $value ) && in_array( $value['product_id'], $this->processed_products ) ) {
479
- unset( $batch->data[ $key ] ); // remove this product from the queue
480
- continue;
481
- }
482
-
483
- // run the task
484
- $task = $this->task( $value, $feed_data, $feed_file_path, $pre_data, $channel_details, $relations_table );
485
-
486
- // if there was no failure and the id is known, add the product id to the list of processed products
487
- if ( 'product added' === $task && array_key_exists( 'product_id', $value ) ) {
488
- array_push( $this->processed_products, $value['product_id'] );
489
- }
490
-
491
- unset( $batch->data[ $key ] ); // remove this product from the queue
492
-
493
- if ( $this->time_exceeded( $feed_id ) || $this->memory_exceeded( $feed_id ) ) {
494
- // Batch limits reached.
495
- $this->delete( $batch->key );
496
- break;
497
- }
498
- }
499
-
500
- // Update or delete current batch.
501
- if ( ! empty( $batch->data ) ) {
502
- $this->update( $batch->key, $batch->data );
503
- } else {
504
- $this->delete( $batch->key );
505
- }
506
- } while ( ! $this->time_exceeded( $feed_id ) && ! $this->memory_exceeded( $feed_id ) && ! $this->is_queue_empty() );
507
-
508
- $this->unlock_process();
509
-
510
- // If the queue is not empty, restart the process
511
- if ( ! $this->is_queue_empty() ) {
512
- update_option( 'tvc_processed_products', implode( ',', $this->processed_products ) );
513
-
514
- // @since 2.3.0
515
- do_action( 'tvc_activated_next_batch', $feed_id );
516
-
517
- // @since 2.11.0
518
- // The feed process is still running so update the file grow monitor to prevent it from initiating a failed feed.
519
- TVC_Feed_Controller::update_file_grow_monitoring_timer();
520
-
521
- $this->dispatch( $feed_id );
522
- } else {
523
-
524
- $this->end_batch( $feed_id );
525
- }
526
- }
527
-
528
- /**
529
- * Memory exceeded
530
- *
531
- * Ensures the batch process never exceeds 90%
532
- * of the maximum WordPress memory.
533
- *
534
- * @param string $feed_id
535
- *
536
- * @return bool
537
- */
538
- protected function memory_exceeded( $feed_id ) {
539
- $memory_limit = $this->get_memory_limit() * 0.9; // 90% of max memory
540
- $current_memory = memory_get_usage( true );
541
- $return = false;
542
-
543
- if ( $current_memory >= $memory_limit ) {
544
- do_action( 'tvc_batch_memory_limit_exceeded', $feed_id, $current_memory, $memory_limit );
545
- $return = true;
546
- }
547
-
548
- return apply_filters( $this->identifier . '_memory_exceeded', $return );
549
- }
550
-
551
- /**
552
- * Get memory limit
553
- *
554
- * @return int
555
- */
556
- protected function get_memory_limit() {
557
- if ( function_exists( 'ini_get' ) ) {
558
- $memory_limit = ini_get( 'memory_limit' );
559
- } else {
560
- // Sensible default.
561
- $memory_limit = '128M';
562
- }
563
-
564
- if ( ! $memory_limit || - 1 === intval( $memory_limit ) ) {
565
- // Unlimited, set to 32GB.
566
- $memory_limit = '32000M';
567
- }
568
-
569
- return intval( $memory_limit ) * 1024 * 1024;
570
- }
571
-
572
- /**
573
- * Time exceeded.
574
- *
575
- * Ensures the batch never exceeds a sensible time limit.
576
- * A timeout limit of 30s is common on shared hosting.
577
- *
578
- * @param string $feed_id
579
- *
580
- * @return bool
581
- */
582
- protected function time_exceeded( $feed_id ) {
583
- $finish = $this->start_time + apply_filters( 'tvc_default_time_limit', 30 );
584
- $return = false;
585
-
586
- if ( time() >= $finish ) {
587
- do_action( 'tvc_batch_time_limit_exceeded', $feed_id, apply_filters( 'tvc_default_time_limit', 30 ) );
588
- $return = true;
589
- }
590
-
591
- return apply_filters( $this->identifier . '_time_exceeded', $return );
592
- }
593
-
594
- /**
595
- * Ends the current batch. Clean up the batch data and start a new feed if there is one in the feed queue.
596
- *
597
- * @since 2.10.0.
598
- *
599
- * @param string $feed_id
600
- * @param string $status Use "failed" for failing batches. Default status is ready.
601
- */
602
- protected function end_batch( $feed_id, $status = 'ready' ) {
603
- $this->clear_the_queue();
604
-
605
- $this->complete(); // complete processing this feed
606
-
607
- if ( 'failed' === $status && $feed_id ) {
608
- // Set the feed status to failed (6).
609
- $data_class = new TVC_Data();
610
- $data_class->update_feed_status( $feed_id, 6 );
611
-
612
- // Log the failure.
613
- $message = 'Batch ended prematurely.';
614
- do_action( 'tvc_feed_generation_message', $feed_id, $message, 'ERROR' );
615
- }
616
-
617
- if ( ! TVC_Feed_Controller::feed_queue_is_empty() ) {
618
- do_action( 'tvc_activated_next_feed', TVC_Feed_Controller::get_next_id_from_feed_queue() );
619
-
620
- $this->dispatch( TVC_Feed_Controller::get_next_id_from_feed_queue() ); // start with the next feed in the queue
621
- }
622
- }
623
-
624
- /**
625
- * Complete.
626
- *
627
- * Override if applicable, but ensure that the below actions are
628
- * performed, or, call parent::complete().
629
- */
630
- public function complete() {
631
- delete_option( 'tvc_processed_products' );
632
-
633
- // Unschedule the cron health check.
634
- $this->clear_scheduled_event();
635
- $this->unlock_process();
636
- }
637
-
638
- /**
639
- * Schedule cron health check
640
- *
641
- * @access public
642
- *
643
- * @param mixed $schedules Schedules.
644
- *
645
- * @return mixed
646
- */
647
- public function schedule_cron_health_check( $schedules ) {
648
- $interval = apply_filters( $this->identifier . '_cron_interval', 5 );
649
-
650
- if ( property_exists( $this, 'cron_interval' ) ) {
651
- $interval = apply_filters( $this->identifier . '_cron_interval', $this->cron_interval_identifier );
652
- }
653
-
654
- // Adds every 5 minutes to the existing schedules.
655
- $schedules[ $this->identifier . '_cron_interval' ] = array(
656
- 'interval' => MINUTE_IN_SECONDS * $interval,
657
-
658
- 'display' => sprintf(
659
- /* translators: %d: Cron check interval */
660
- _n(
661
- 'Every %d minute',
662
- 'Every %d minutes',
663
- $interval,
664
- 'tvc-product-feed-manager'
665
- ),
666
- $interval
667
- ),
668
- );
669
-
670
- return $schedules;
671
- }
672
-
673
- /**
674
- * Handle cron health check
675
- *
676
- * Restart the background process if not already running
677
- * and data exists in the queue.
678
- */
679
- public function handle_cron_health_check() {
680
- if ( $this->is_process_running() ) {
681
- // Background process already running.
682
- exit;
683
- }
684
-
685
- if ( $this->is_queue_empty() ) {
686
- // No data to process.
687
- $this->clear_scheduled_event();
688
- exit;
689
- }
690
-
691
- $this->handle();
692
-
693
- exit;
694
- }
695
-
696
- /**
697
- * Schedule event
698
- */
699
- protected function schedule_event() {
700
- if ( ! wp_next_scheduled( $this->cron_hook_identifier ) ) {
701
- if ( ! wp_schedule_event( time(), $this->cron_interval_identifier, $this->cron_hook_identifier ) ) {
702
- tvc_show_wp_error( esc_html__( 'Could not schedule the cron event required to start the feed process. Please check if your wp cron is configured correctly and is running.', 'tvc-product-feed-manager' ) );
703
- }
704
- }
705
- }
706
-
707
- /**
708
- * Clear scheduled event
709
- */
710
- protected function clear_scheduled_event() {
711
- $timestamp = wp_next_scheduled( $this->cron_hook_identifier );
712
-
713
- if ( $timestamp ) {
714
- wp_unschedule_event( $timestamp, $this->cron_hook_identifier );
715
- }
716
- }
717
-
718
- /**
719
- * Cancel Process
720
- *
721
- * Stop processing queue items, clear cronjob and delete batch.
722
- *
723
- */
724
- public function cancel_process() {
725
- if ( ! $this->is_queue_empty() ) {
726
- $batch = $this->get_batch();
727
-
728
- $this->delete( $batch->key );
729
-
730
- wp_clear_scheduled_hook( $this->cron_hook_identifier );
731
- }
732
-
733
- }
734
-
735
- /**
736
- * Task
737
- *
738
- * Override this method to perform any actions required on each
739
- * queue item. Return the modified item for further processing
740
- * in the next pass through. Or, return false to remove the
741
- * item from the queue.
742
- *
743
- * @param mixed $item Queue item to iterate over.
744
- * @param array $feed_data
745
- * @param string $feed_file_path
746
- * @param array $pre_data
747
- * @param array $channel_details
748
- * @param array $relation_table
749
- *
750
- * @return mixed
751
- */
752
- abstract protected function task( $item, $feed_data, $feed_file_path, $pre_data, $channel_details, $relation_table );
753
-
754
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/setup/CustomApi.php CHANGED
@@ -1,16 +1,40 @@
1
  <?php
2
-
3
- class CustomApi {
4
-
5
  private $apiDomain;
6
  private $token;
7
-
 
8
  public function __construct() {
9
- $this->apiDomain = 'https://connect.tatvic.com/laravelapi/public/api';
10
- // $this->apiDomain = 'http://127.0.0.1:8000/api';
11
- // $this->apiDomain = 'https://6d0ba8fc5ce0.ngrok.io/tatvic-gmc-middletier/public/api';
12
  $this->token = 'MTIzNA==';
13
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14
  public function is_allow_call_api(){
15
  $ee_options_data = unserialize(get_option('ee_options'));
16
  if(isset($ee_options_data['subscription_id'])) {
@@ -19,14 +43,7 @@ class CustomApi {
19
  return false;
20
  }
21
  }
22
- public function get_api_access_token(){
23
- if($this->is_allow_call_api){
24
-
25
- }
26
- }
27
- public function get_api_refresh_token(){
28
-
29
- }
30
  public function getFeatureList() {
31
  try {
32
 
@@ -86,6 +103,8 @@ class CustomApi {
86
  }
87
 
88
  public function getGoogleAnalyticDetail() {
 
 
89
  try {
90
  $url = $this->apiDomain . '/customer-subscriptions/subscription-detail';
91
  $ee_options_data = unserialize(get_option('ee_options'));
@@ -117,21 +136,13 @@ class CustomApi {
117
  $response_body = json_decode(wp_remote_retrieve_body($request));
118
  if ((isset($response_body->error) && $response_body->error == '')) {
119
  if ($response_body->data) {
120
- // "<pre>";
121
- //print_r($response_body->data);
122
- //echo "</pre>";
123
- //exit;
124
- // The country/state
125
  $store_raw_country = get_option('woocommerce_default_country');
126
  // Split the country/state
127
  $split_country = explode(":", $store_raw_country);
128
 
129
  $GLOBALS['tatvicData']['tvc_customer'] = $response_body->data->google_ads_id;
130
- // $GLOBALS['tatvicData']['tvc_customer'] = TVC_CUSTOMER;
131
  $GLOBALS['tatvicData']['tvc_merchant'] = $response_body->data->google_merchant_center_id;
132
- // $GLOBALS['tatvicData']['tvc_merchant'] = TVC_MERCHANT;
133
  $GLOBALS['tatvicData']['tvc_account'] = $response_body->data->ua_analytic_account_id;
134
- // $GLOBALS['tatvicData']['tvc_account'] = TVC_ACCOUNT;
135
  $GLOBALS['tatvicData']['tvc_subscription'] = $response_body->data->id;
136
  $GLOBALS['tatvicData']['tvc_country'] = $split_country[0];
137
  $GLOBALS['tatvicData']['tvc_gmc_id'] = $response_body->data->google_merchant_center_id;
@@ -321,8 +332,7 @@ class CustomApi {
321
  $header = array(
322
  "Authorization: Bearer MTIzNA==",
323
  "content-type: application/json",
324
- "AccessToken:".$this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
325
- //"AccessToken:".$_SESSION['access_token']
326
  );
327
  $curl_url = $this->apiDomain . "/products/list";
328
  $postData = json_encode($postData);
@@ -395,7 +405,7 @@ class CustomApi {
395
  'headers' => array(
396
  'Authorization' => "Bearer $this->token",
397
  'Content-Type' => 'application/json',
398
- 'AccessToken' => $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
399
  ),
400
  'body' => wp_json_encode($postData)
401
  );
@@ -432,7 +442,7 @@ class CustomApi {
432
  'headers' => array(
433
  'Authorization' => "Bearer $this->token",
434
  'Content-Type' => 'application/json',
435
- 'AccessToken' => $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
436
  ),
437
  'body' => wp_json_encode($postData)
438
  );
@@ -639,7 +649,7 @@ class CustomApi {
639
  $url = $this->apiDomain . '/gmc/site-verification-token';
640
  $this->header = array("Authorization: Bearer MTIzNA==",
641
  "content-type: application/json",
642
- "AccessToken:" . $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
643
  );
644
 
645
  $data = [
@@ -672,7 +682,7 @@ class CustomApi {
672
  $url = $this->apiDomain . '/gmc/site-verification';
673
  $this->header = array("Authorization: Bearer MTIzNA==",
674
  "content-type: application/json",
675
- "AccessToken:" . $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
676
  );
677
 
678
  $data = [
@@ -706,13 +716,13 @@ class CustomApi {
706
  $url = $this->apiDomain . '/gmc/claim-website';
707
  $this->header = array("Authorization: Bearer MTIzNA==",
708
  "content-type: application/json",
709
- "AccessToken:" . $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token'])
710
  );
711
  $data = [
712
  'merchant_id' => $postData['merchant_id'],
713
  'account_id' => $postData['account_id'],
714
  'website' => $postData['website_url'],
715
- 'access_token' => $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token']),
716
  'subscription_id' => $postData['subscription_id'],
717
  ];
718
 
1
  <?php
2
+ class CustomApi{
 
 
3
  private $apiDomain;
4
  private $token;
5
+ protected $access_token;
6
+ protected $refresh_token;
7
  public function __construct() {
8
+ $this->apiDomain = TVC_API_CALL_URL;
 
 
9
  $this->token = 'MTIzNA==';
10
  }
11
+ public function get_tvc_access_token(){
12
+ if(!empty($this->access_token)){
13
+ return $this->access_token;
14
+ }else if(isset($_SESSION['access_token']) && $_SESSION['access_token']){
15
+ $this->access_token = $_SESSION['access_token'];
16
+ return $this->access_token;
17
+ }else{
18
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
19
+ $google_detail = $TVC_Admin_Helper->get_ee_options_data();
20
+ $this->access_token = $google_detail['setting']->access_token;
21
+ return $this->access_token;
22
+ }
23
+ }
24
+
25
+ public function get_tvc_refresh_token(){
26
+ if(!empty($this->refresh_token)){
27
+ return $this->refresh_token;
28
+ }else if(isset($_SESSION['refresh_token']) && $_SESSION['refresh_token']){
29
+ $this->refresh_token = $_SESSION['refresh_token'];
30
+ return $this->refresh_token;
31
+ }else{
32
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
33
+ $google_detail = $TVC_Admin_Helper->get_ee_options_data();
34
+ $this->refresh_token = $google_detail['setting']->refresh_token;
35
+ return $this->refresh_token;
36
+ }
37
+ }
38
  public function is_allow_call_api(){
39
  $ee_options_data = unserialize(get_option('ee_options'));
40
  if(isset($ee_options_data['subscription_id'])) {
43
  return false;
44
  }
45
  }
46
+
 
 
 
 
 
 
 
47
  public function getFeatureList() {
48
  try {
49
 
103
  }
104
 
105
  public function getGoogleAnalyticDetail() {
106
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
107
+ $TVC_Admin_Helper->add_tvc_log("==> getGoogleAnalyticDetail");
108
  try {
109
  $url = $this->apiDomain . '/customer-subscriptions/subscription-detail';
110
  $ee_options_data = unserialize(get_option('ee_options'));
136
  $response_body = json_decode(wp_remote_retrieve_body($request));
137
  if ((isset($response_body->error) && $response_body->error == '')) {
138
  if ($response_body->data) {
 
 
 
 
 
139
  $store_raw_country = get_option('woocommerce_default_country');
140
  // Split the country/state
141
  $split_country = explode(":", $store_raw_country);
142
 
143
  $GLOBALS['tatvicData']['tvc_customer'] = $response_body->data->google_ads_id;
 
144
  $GLOBALS['tatvicData']['tvc_merchant'] = $response_body->data->google_merchant_center_id;
 
145
  $GLOBALS['tatvicData']['tvc_account'] = $response_body->data->ua_analytic_account_id;
 
146
  $GLOBALS['tatvicData']['tvc_subscription'] = $response_body->data->id;
147
  $GLOBALS['tatvicData']['tvc_country'] = $split_country[0];
148
  $GLOBALS['tatvicData']['tvc_gmc_id'] = $response_body->data->google_merchant_center_id;
332
  $header = array(
333
  "Authorization: Bearer MTIzNA==",
334
  "content-type: application/json",
335
+ "AccessToken:".$this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
 
336
  );
337
  $curl_url = $this->apiDomain . "/products/list";
338
  $postData = json_encode($postData);
405
  'headers' => array(
406
  'Authorization' => "Bearer $this->token",
407
  'Content-Type' => 'application/json',
408
+ 'AccessToken' => $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
409
  ),
410
  'body' => wp_json_encode($postData)
411
  );
442
  'headers' => array(
443
  'Authorization' => "Bearer $this->token",
444
  'Content-Type' => 'application/json',
445
+ 'AccessToken' => $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
446
  ),
447
  'body' => wp_json_encode($postData)
448
  );
649
  $url = $this->apiDomain . '/gmc/site-verification-token';
650
  $this->header = array("Authorization: Bearer MTIzNA==",
651
  "content-type: application/json",
652
+ "AccessToken:" . $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
653
  );
654
 
655
  $data = [
682
  $url = $this->apiDomain . '/gmc/site-verification';
683
  $this->header = array("Authorization: Bearer MTIzNA==",
684
  "content-type: application/json",
685
+ "AccessToken:" . $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
686
  );
687
 
688
  $data = [
716
  $url = $this->apiDomain . '/gmc/claim-website';
717
  $this->header = array("Authorization: Bearer MTIzNA==",
718
  "content-type: application/json",
719
+ "AccessToken:" . $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token())
720
  );
721
  $data = [
722
  'merchant_id' => $postData['merchant_id'],
723
  'account_id' => $postData['account_id'],
724
  'website' => $postData['website_url'],
725
+ 'access_token' => $this->generateAccessToken($this->get_tvc_access_token(), $this->get_tvc_refresh_token()),
726
  'subscription_id' => $postData['subscription_id'],
727
  ];
728
 
includes/setup/ShoppingApi.php CHANGED
@@ -12,7 +12,7 @@ class ShoppingApi {
12
  $this->customApiObj->getGoogleAnalyticDetail();
13
 
14
  $queries = new TVC_Queries();
15
- $this->apiDomain = 'https://connect.tatvic.com/laravelapi/public/api';
16
  //$this->apiDomain = 'http://127.0.0.1:8000/api';
17
  $this->token = 'MTIzNA==';
18
  $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant'] : "";
@@ -37,7 +37,7 @@ class ShoppingApi {
37
 
38
  // Send remote request
39
  $request = wp_remote_post($url, $args);
40
-
41
  // Retrieve information
42
  $response_code = wp_remote_retrieve_response_code($request);
43
  $response_message = wp_remote_retrieve_response_message($request);
12
  $this->customApiObj->getGoogleAnalyticDetail();
13
 
14
  $queries = new TVC_Queries();
15
+ $this->apiDomain = TVC_API_CALL_URL;
16
  //$this->apiDomain = 'http://127.0.0.1:8000/api';
17
  $this->token = 'MTIzNA==';
18
  $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant'] : "";
37
 
38
  // Send remote request
39
  $request = wp_remote_post($url, $args);
40
+ //print_r($request);
41
  // Retrieve information
42
  $response_code = wp_remote_retrieve_response_code($request);
43
  $response_message = wp_remote_retrieve_response_message($request);
includes/setup/add-campaign.php CHANGED
@@ -8,10 +8,12 @@ class AddCampaign {
8
  public $gmail;
9
  public $merchantId;
10
  public $new_campaign;
 
11
 
12
  public function __construct() {
13
  global $wpdb;
14
  $this->includes();
 
15
  $this->customApiObj = new CustomApi();
16
  $this->customApiObj->getGoogleAnalyticDetail();
17
 
@@ -133,7 +135,7 @@ class AddCampaign {
133
 
134
  $campaigns_list_res = $campaigns_list_res->data;
135
 
136
- if ($campaigns_list_res['status'] == 200) {
137
  $campaigns_list = $campaigns_list_res['data'];
138
  }
139
  }
8
  public $gmail;
9
  public $merchantId;
10
  public $new_campaign;
11
+ protected $TVC_Admin_Helper;
12
 
13
  public function __construct() {
14
  global $wpdb;
15
  $this->includes();
16
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
17
  $this->customApiObj = new CustomApi();
18
  $this->customApiObj->getGoogleAnalyticDetail();
19
 
135
 
136
  $campaigns_list_res = $campaigns_list_res->data;
137
 
138
+ if (isset($campaigns_list_res['status']) && $campaigns_list_res['status'] == 200) {
139
  $campaigns_list = $campaigns_list_res['data'];
140
  }
141
  }
includes/setup/class-tatvic-category-selector-element.php CHANGED
@@ -74,7 +74,7 @@ if ( ! class_exists( 'Tatvic_Category_Selector_Element' ) ) :
74
  <input type="hidden" name="category-'.$id.'" id="category-'.$id.'" value="'.$cat_id.'">
75
  <input type="hidden" name="category-name-'.$id.'" id="category-name-'.$id.'" value="'.$cat_name.'">
76
  </div>
77
- <label id="label-'.$ident.'_0">'.$cat_name.'</label><span class="change_prodct_feed_cat" data-id="'.$ident.'_0">Edit</span>
78
  <select class="form-control" style="display:none;" id="' . $ident . '_0" catId="'.$id.'" onchange="selectSubCategory(this)"></select>';
79
 
80
  for ( $i = 1; $i < $category_levels; $i ++ ) {
74
  <input type="hidden" name="category-'.$id.'" id="category-'.$id.'" value="'.$cat_id.'">
75
  <input type="hidden" name="category-name-'.$id.'" id="category-name-'.$id.'" value="'.$cat_name.'">
76
  </div>
77
+ <label id="label-'.$ident.'_0">'.$cat_name.'</label><span class="change_prodct_feed_cat" data-cat-id="'.$id.'" data-id="'.$ident.'_0">Edit</span>
78
  <select class="form-control" style="display:none;" id="' . $ident . '_0" catId="'.$id.'" onchange="selectSubCategory(this)"></select>';
79
 
80
  for ( $i = 1; $i < $category_levels; $i ++ ) {
includes/setup/class-tvc-database-management.php DELETED
@@ -1,537 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * Tatvic Database Class.
5
- *
6
- * @package Tatvic Product Feed Manager/Data/Classes
7
- * @version 3.2.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Database_Management' ) ) :
15
-
16
- /**
17
- * TVC_Database
18
- */
19
- class TVC_Database_Management {
20
- /* --------------------------------------------------------------------------------------------------*
21
- * Attributes
22
- * -------------------------------------------------------------------------------------------------- */
23
-
24
- private $_version = '1.10.0'; // as of plugin version 2.10.0
25
- private $_wpdb;
26
- private $_charset_collate = '';
27
- private $_image_folder;
28
-
29
- /**
30
- * TVC_Tables
31
- *
32
- * @access public
33
- */
34
- public function __construct() {
35
- global $wpdb;
36
-
37
- // include what needs to be included
38
- $this->includes();
39
-
40
- // assign the global wpdb to a variable
41
- $this->_wpdb = &$wpdb;
42
-
43
- // set the charset for the new database tables
44
- if ( $this->_wpdb->has_cap( 'collation' ) ) {
45
- $this->_charset_collate = $wpdb->get_charset_collate();
46
- }
47
-
48
- // url to the image folder
49
- $this->_image_folder = esc_url( ENHANCAD_PLUGIN_URL . '/images/' );
50
- }
51
-
52
- /**
53
- * Adds the required tables to the WordPress database
54
- */
55
- public function make() {
56
- // make the tables
57
- $this->make_or_update_the_tables();
58
-
59
- // fill the tables with preset data
60
- $this->fill_the_tables();
61
-
62
- do_action( 'tvc_installed' );
63
- }
64
-
65
- /**
66
- * Checks if there is a need to update the database after a plugin update and performs the update if required
67
- *
68
- * @since 1.8.0
69
- */
70
- public function verify_db_version() {
71
- $actual_db_version = get_option( 'tvc_db_version' ) ? get_option( 'tvc_db_version' ) : $this->get_current_db_version();
72
- if ( $actual_db_version < $this->_version ) {
73
- $this->make_or_update_the_tables();
74
-
75
- // update table as of version 1.7.0
76
- if ( $this->_version <= '1.8.0' ) {
77
- $this->update_status_table();
78
- }
79
- }
80
-
81
- do_action( 'tvc_db_verified' );
82
- }
83
-
84
- /**
85
- * Forces a database update
86
- *
87
- * @since 1.9.0
88
- */
89
- public function force_reinitiate_db() {
90
- $this->make_or_update_the_tables();
91
- }
92
-
93
- public function reset_channel_registration() {
94
- $this->fill_channel_table();
95
- }
96
-
97
- /* --------------------------------------------------------------------------------------------------*
98
- * Private functions
99
- * -------------------------------------------------------------------------------------------------- */
100
-
101
- private function includes() {
102
- // required for dbDelta
103
- require_once( ABSPATH . 'wp-admin/includes/upgrade.php' );
104
- }
105
-
106
- /**
107
- * makes or updates the required database tables
108
- *
109
- * @since 1.9.2
110
- */
111
- private function make_or_update_the_tables() {
112
- $this->channel_table();
113
- $this->country_table();
114
- $this->feed_table();
115
- $this->feedmeta_table();
116
- $this->status_table();
117
- $this->categories_table();
118
- $this->sources_table();
119
- $this->merchant_id_table();
120
- $this->ads_account_id_table();
121
- //$this->error_table(); // deselected @since 2.2.0
122
-
123
- // store the db version
124
- update_option( 'tvc_db_version', $this->_version );
125
- }
126
-
127
- /**
128
- * fill the tables with preset data
129
- *
130
- * @since 1.9.2
131
- */
132
- private function fill_the_tables() {
133
- $this->fill_channel_table();
134
- $this->fill_country_table();
135
- $this->fill_merchant_table();
136
- $this->fill_status_table();
137
- $this->fill_categories_table();
138
- }
139
-
140
- /**
141
- * creates the feed table
142
- */
143
- private function feed_table() {
144
- $table_name = $this->_wpdb->prefix . 'feedmanager_product_feed';
145
-
146
- $sql = "CREATE TABLE $table_name (
147
- product_feed_id int NOT NULL AUTO_INCREMENT,
148
- channel_id smallint NOT NULL,
149
- language varchar(7),
150
- is_aggregator smallint NOT NULL DEFAULT 0,
151
- include_variations smallint NOT NULL DEFAULT 0,
152
- country_id smallint NOT NULL DEFAULT 233,
153
- source_id smallint NOT NULL,
154
- title varchar(100) NOT NULL UNIQUE DEFAULT '',
155
- feed_title varchar(100),
156
- feed_description varchar(200),
157
- aggregator_name varchar(200),
158
- publisher_name varchar(200),
159
- publisher_favicon_url varchar(200),
160
- main_category varchar(200) NOT NULL DEFAULT '',
161
- url varchar(200) NOT NULL DEFAULT '',
162
- status_id smallint NOT NULL DEFAULT 1,
163
- base_status_id smallint NOT NULL DEFAULT 2,
164
- feed_type_id smallint NOT NULL DEFAULT 1,
165
- updated datetime NOT NULL,
166
- schedule varchar(50) NOT NULL DEFAULT '1:00:00',
167
- products int NOT NULL DEFAULT 1,
168
- timestamp timestamp DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
169
- gmc_feed_id int NULL,
170
- PRIMARY KEY (product_feed_id)
171
- ) " . $this->_charset_collate . ';';
172
-
173
- dbDelta( $sql );
174
- }
175
-
176
- /**
177
- * creates a meta table for the feeds
178
- */
179
- private function feedmeta_table() {
180
- $table_name = $this->_wpdb->prefix . 'feedmanager_product_feedmeta';
181
-
182
- $sql = "CREATE TABLE $table_name (
183
- meta_id int NOT NULL AUTO_INCREMENT,
184
- product_feed_id int NOT NULL,
185
- meta_key varchar(191),
186
- meta_value longtext,
187
- PRIMARY KEY (meta_id),
188
- KEY product_feed_id (product_feed_id),
189
- KEY meta_key (meta_key)
190
- ) " . $this->_charset_collate . ';';
191
-
192
- dbDelta( $sql );
193
- }
194
-
195
- /**
196
- * create a feed status table
197
- */
198
- private function status_table() {
199
- $table_name = $this->_wpdb->prefix . 'feedmanager_feed_status';
200
-
201
- $sql = "CREATE TABLE $table_name (
202
- status_id smallint NOT NULL,
203
- status varchar(20) NOT NULL UNIQUE DEFAULT 'OK',
204
- color char(7)NOT NULL UNIQUE,
205
- PRIMARY KEY (status_id)
206
- ) " . $this->_charset_collate . ';';
207
-
208
- dbDelta( $sql );
209
- }
210
-
211
- /**
212
- * Create table contains merchant ID and status
213
- */
214
- private function merchant_id_table(){
215
- $table_name = $this->_wpdb->prefix . 'feedmanager_default_center';
216
- $sql = "CREATE TABLE $table_name (
217
- merchant_id INT(25) NOT NULL,
218
- status TINYINT(1) NULL,
219
- censent VARCHAR (10) NULL,
220
- account_name VARCHAR (25) NULL,
221
- user_email VARCHAR (30) NULL,
222
- website_url VARCHAR (30) NULL,
223
- is_admin TINYINT(1) NULL,
224
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
225
- updated_at TIMESTAMP NULL ON UPDATE CURRENT_TIMESTAMP,
226
- claim TINYINT(1) NULL,
227
- PRIMARY KEY (merchant_id)
228
- ) " . $this->_charset_collate . ';';
229
-
230
- dbDelta( $sql );
231
- }
232
-
233
- /**
234
- * Create table contains merchant ID and status
235
- */
236
- private function ads_account_id_table(){
237
- $table_name = $this->_wpdb->prefix . 'adsmanager_default_center';
238
- $sql = "CREATE TABLE $table_name (
239
- account_id VARCHAR(50) NOT NULL,
240
- merchant_id VARCHAR(50) NULL,
241
- merchant_center_linked TINYINT(1) NULL,
242
- status TINYINT(1) NULL,
243
- created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
244
- updated_at TIMESTAMP NULL ON UPDATE CURRENT_TIMESTAMP,
245
- PRIMARY KEY (account_id)
246
- ) " . $this->_charset_collate . ';';
247
-
248
- dbDelta( $sql );
249
- }
250
-
251
- /**
252
- * creates the channel table
253
- */
254
- private function channel_table() {
255
- $table_name = $this->_wpdb->prefix . 'feedmanager_channel';
256
-
257
- $sql = "CREATE TABLE $table_name (
258
- channel_id int NOT NULL DEFAULT 0,
259
- name varchar(100) NOT NULL UNIQUE DEFAULT '',
260
- short varchar(50) NOT NULL UNIQUE DEFAULT '',
261
- PRIMARY KEY (channel_id)
262
- ) " . $this->_charset_collate . ';';
263
-
264
- dbDelta( $sql );
265
- }
266
-
267
- /**
268
- * creates the country table
269
- */
270
- private function country_table() {
271
- $table_name = $this->_wpdb->prefix . 'feedmanager_country';
272
-
273
- $sql = "CREATE TABLE $table_name (
274
- country_id int NOT NULL AUTO_INCREMENT,
275
- name_short varchar(3) NOT NULL UNIQUE DEFAULT '',
276
- name varchar(100) NOT NULL UNIQUE DEFAULT '',
277
- PRIMARY KEY (country_id)
278
- ) " . $this->_charset_collate . ';';
279
-
280
- dbDelta( $sql );
281
- }
282
-
283
- /**
284
- * creates the sources table
285
- */
286
- private function sources_table() {
287
- $table_name = $this->_wpdb->prefix . 'feedmanager_source';
288
-
289
- $sql = "CREATE TABLE $table_name (
290
- source_id int NOT NULL UNIQUE,
291
- name varchar(100) NOT NULL UNIQUE DEFAULT '',
292
- PRIMARY KEY (source_id)
293
- ) " . $this->_charset_collate . ';';
294
-
295
- dbDelta( $sql );
296
- }
297
-
298
- private function categories_table() {
299
- $table_name = $this->_wpdb->prefix . 'feedmanager_field_categories';
300
-
301
- $sql = "CREATE TABLE $table_name (
302
- category_id int NOT NULL,
303
- category_label varchar(100) NOT NULL,
304
- PRIMARY KEY (category_id)
305
- ) " . $this->_charset_collate . ';';
306
-
307
- dbDelta( $sql );
308
- }
309
-
310
- /**
311
- * fills the countries table with supported contries
312
- */
313
- private function fill_country_table() {
314
- $table_name = $this->_wpdb->prefix . 'feedmanager_country';
315
-
316
- $count = $this->_wpdb->get_var( "SELECT COUNT(*) FROM $table_name" );
317
-
318
- // only fill the table if its still empty
319
- if ( 0 == $count ) {
320
- $sql = "INSERT INTO $table_name
321
- (name_short, name) VALUES
322
- ('AD', 'Andorra'), ('AE', 'United Arab Emirates'), ('AF', 'Afghanistan'), ('AG', 'Antigua and Barbuda'), ('AI', 'Anguilla'), ('AL', 'Albania'),
323
- ('AM', 'Armenia'), ('AO', 'Angola'), ('AQ', 'Antarctica'), ('AR', 'Argentina'), ('AS', 'American Samoa'), ('AT', 'Austria'), ('AU', 'Australia'),
324
- ('AW', 'Aruba'), ('AX', 'Åland'), ('AZ', 'Azerbaijan'), ('BA', 'Bosnia and Herzegovina'), ('BB', 'Barbados'), ('BD', 'Bangladesh'), ('BE', 'Belgium'),
325
- ('BF', 'Burkina Faso'), ('BG', 'Bulgaria'), ('BH', 'Bahrain'), ('BI', 'Burundi'), ('BJ', 'Benin'), ('BL', 'Saint Barthélemy'), ('BM', 'Bermuda'),
326
- ('BN', 'Brunei'), ('BO', 'Bolivia'), ('BQ', 'Bonaire'), ('BR', 'Brazil'), ('BS', 'Bahamas'), ('BT', 'Bhutan'), ('BV', 'Bouvet Island'), ('BW', 'Botswana'),
327
- ('BY', 'Belarus'), ('BZ', 'Belize'), ('CA', 'Canada'), ('CC', 'Cocos [Keeling] Islands'), ('CD', 'Democratic Republic of the Congo'),
328
- ('CF', 'Central African Republic'), ('CG', 'Republic of the Congo'), ('CH', 'Switzerland'), ('CI', 'Ivory Coast'), ('CK', 'Cook Islands'),
329
- ('CL', 'Chile'), ('CM', 'Cameroon'), ('CN', 'China'), ('CO', 'Colombia'), ('CR', 'Costa Rica'), ('CU', 'Cuba'), ('CV', 'Cape Verde'),
330
- ('CW', 'Curacao'), ('CX', 'Christmas Island'), ('CY', 'Cyprus'), ('CZ', 'Czech Republic'), ('DE', 'Germany'), ('DJ', 'Djibouti'), ('DK', 'Denmark'),
331
- ('DM', 'Dominica'), ('DO', 'Dominican Republic'), ('DZ', 'Algeria'), ('EC', 'Ecuador'), ('EE', 'Estonia'), ('EG', 'Egypt'), ('EH', 'Western Sahara'),
332
- ('ER', 'Eritrea'), ('ES', 'Spain'), ('ET', 'Ethiopia'), ('FI', 'Finland'), ('FJ', 'Fiji'), ('FK', 'Falkland Islands'), ('FM', 'Micronesia'),
333
- ('FO', 'Faroe Islands'), ('FR', 'France'), ('GA', 'Gabon'), ('GB', 'United Kingdom'), ('GD', 'Grenada'), ('GE', 'Georgia'), ('GF', 'French Guiana'),
334
- ('GG', 'Guernsey'), ('GH', 'Ghana'), ('GI', 'Gibraltar'), ('GL', 'Greenland'), ('GM', 'Gambia'), ('GN', 'Guinea'), ('GP', 'Guadeloupe'),
335
- ('GQ', 'Equatorial Guinea'), ('GR', 'Greece'), ('GS', 'South Georgia and the South Sandwich Islands'), ('GT', 'Guatemala'), ('GU', 'Guam'),
336
- ('GW', 'Guinea-Bissau'), ('GY', 'Guyana'), ('HK', 'Hong Kong'), ('HM', 'Heard Island and McDonald Islands'), ('HN', 'Honduras'), ('HR', 'Croatia'),
337
- ('HT', 'Haiti'), ('HU', 'Hungary'), ('ID', 'Indonesia'), ('IE', 'Ireland'), ('IL', 'Israel'), ('IM', 'Isle of Man'), ('IN', 'India'),
338
- ('IO', 'British Indian Ocean Territory'), ('IQ', 'Iraq'), ('IR', 'Iran'), ('IS', 'Iceland'), ('IT', 'Italy'), ('JE', 'Jersey'), ('JM', 'Jamaica'),
339
- ('JO', 'Jordan'), ('JP', 'Japan'), ('KE', 'Kenya'), ('KG', 'Kyrgyzstan'), ('KH', 'Cambodia'), ('KI', 'Kiribati'), ('KM', 'Comoros'),
340
- ('KN', 'Saint Kitts and Nevis'), ('KP', 'North Korea'), ('KR', 'South Korea'), ('KW', 'Kuwait'), ('KY', 'Cayman Islands'), ('KZ', 'Kazakhstan'),
341
- ('LA', 'Laos'), ('LB', 'Lebanon'), ('LC', 'Saint Lucia'), ('LI', 'Liechtenstein'), ('LK', 'Sri Lanka'), ('LR', 'Liberia'), ('LS', 'Lesotho'),
342
- ('LT', 'Lithuania'), ('LU', 'Luxembourg'), ('LV', 'Latvia'), ('LY', 'Libya'), ('MA', 'Morocco'), ('MC', 'Monaco'), ('MD', 'Moldova'),
343
- ('ME', 'Montenegro'), ('MF', 'Saint Martin'), ('MG', 'Madagascar'), ('MH', 'Marshall Islands'), ('MK', 'Macedonia'), ('ML', 'Mali'),
344
- ('MM', 'Myanmar [Burma]'), ('MN', 'Mongolia'), ('MO', 'Macao'), ('MP', 'Northern Mariana Islands'), ('MQ', 'Martinique'), ('MR', 'Mauritania'),
345
- ('MS', 'Montserrat'), ('MT', 'Malta'), ('MU', 'Mauritius'), ('MV', 'Maldives'), ('MW', 'Malawi'), ('MX', 'Mexico'), ('MY', 'Malaysia'),
346
- ('MZ', 'Mozambique'), ('NA', 'Namibia'), ('NC', 'New Caledonia'), ('NE', 'Niger'), ('NF', 'Norfolk Island'), ('NG', 'Nigeria'),
347
- ('NI', 'Nicaragua'), ('NL', 'Netherlands'), ('NO', 'Norway'), ('NP', 'Nepal'), ('NR', 'Nauru'), ('NU', 'Niue'), ('NZ', 'New Zealand'), ('OM', 'Oman'),
348
- ('PA', 'Panama'), ('PE', 'Peru'), ('PF', 'French Polynesia'), ('PG', 'Papua New Guinea'), ('PH', 'Philippines'), ('PK', 'Pakistan'), ('PL', 'Poland'),
349
- ('PM', 'Saint Pierre and Miquelon'), ('PN', 'Pitcairn Islands'), ('PR', 'Puerto Rico'), ('PS', 'Palestine'), ('PT', 'Portugal'), ('PW', 'Palau'),
350
- ('PY', 'Paraguay'), ('QA', 'Qatar'), ('RE', 'Réunion'), ('RO', 'Romania'), ('RS', 'Serbia'), ('RU', 'Russia'), ('RW', 'Rwanda'), ('SA', 'Saudi Arabia'),
351
- ('SB', 'Solomon Islands'), ('SC', 'Seychelles'), ('SD', 'Sudan'), ('SE', 'Sweden'), ('SG', 'Singapore'), ('SH', 'Saint Helena'), ('SI', 'Slovenia'),
352
- ('SJ', 'Svalbard and Jan Mayen'), ('SK', 'Slovakia'), ('SL', 'Sierra Leone'), ('SM', 'San Marino'), ('SN', 'Senegal'), ('SO', 'Somalia'), ('SR', 'Suriname'),
353
- ('SS', 'South Sudan'), ('ST', 'São Tomé and Príncipe'), ('SV', 'El Salvador'), ('SX', 'Sint Maarten'), ('SY', 'Syria'), ('SZ', 'Swaziland'),
354
- ('TC', 'Turks and Caicos Islands'), ('TD', 'Chad'), ('TF', 'French Southern Territories'), ('TG', 'Togo'), ('TH', 'Thailand'), ('TJ', 'Tajikistan'),
355
- ('TK', 'Tokelau'), ('TL', 'East Timor'), ('TM', 'Turkmenistan'), ('TN', 'Tunisia'), ('TO', 'Tonga'), ('TR', 'Turkey'), ('TT', 'Trinidad and Tobago'),
356
- ('TV', 'Tuvalu'), ('TW', 'Taiwan'), ('TZ', 'Tanzania'), ('UA', 'Ukraine'), ('UG', 'Uganda'), ('UM', 'U.S. Minor Outlying Islands'), ('US', 'United States'),
357
- ('UY', 'Uruguay'), ('UZ', 'Uzbekistan'), ('VA', 'Vatican City'), ('VC', 'Saint Vincent and the Grenadines'), ('VE', 'Venezuela'),
358
- ('VG', 'British Virgin Islands'), ('VI', 'U.S. Virgin Islands'), ('VN', 'Vietnam'), ('VU', 'Vanuatu'), ('WF', 'Wallis and Futuna'), ('WS', 'Samoa'),
359
- ('XK', 'Kosovo'), ('YE', 'Yemen'), ('YT', 'Mayotte'), ('ZA', 'South Africa'), ('ZM', 'Zambia'), ('ZW', 'Zimbabwe')";
360
-
361
- $this->_wpdb->query( $sql );
362
- }
363
- }
364
-
365
- private function fill_merchant_table() {
366
- $table_name = $this->_wpdb->prefix . 'feedmanager_source';
367
-
368
- $count = $this->_wpdb->get_var( "SELECT COUNT(*) FROM $table_name" );
369
-
370
- // only fill the table if its still empty
371
- if ( 0 == $count ) {
372
- $sql = "INSERT INTO $table_name
373
- (source_id, name) VALUES ('1', 'WooCommerce')";
374
-
375
- $this->_wpdb->query( $sql );
376
- }
377
- }
378
-
379
- private function fill_status_table() {
380
- $table_name = $this->_wpdb->prefix . 'feedmanager_feed_status';
381
-
382
- $count = $this->_wpdb->get_var( "SELECT COUNT(*) FROM $table_name" );
383
-
384
- // only fill the table if its still empty
385
- if ( 0 == $count ) {
386
- $sql = "INSERT INTO $table_name
387
- (status_id, status, color) VALUES
388
- ('0', 'unknown', '#6549F7'),
389
- ('1', 'ok', '#0073AA'),
390
- ('2', 'on_hold', '#0173AA'),
391
- ('3', 'processing', '#0000FF'),
392
- ('4', 'in_processing_queue', '#00CCFF'),
393
- ('5', 'has_errors', '#FF0000'),
394
- ('6', 'failed_processing', '#FF3300')";
395
-
396
- $this->_wpdb->query( $sql );
397
- }
398
- }
399
-
400
- private function fill_categories_table() {
401
- $table_name = $this->_wpdb->prefix . 'feedmanager_field_categories';
402
-
403
- $count = $this->_wpdb->get_var( "SELECT COUNT(*) FROM $table_name" );
404
-
405
- // only fill the table if its still empty
406
- if ( 0 == $count ) {
407
- $sql = "INSERT INTO $table_name
408
- (category_id, category_label) VALUES
409
- (1, 'required'), (2, 'highly recommended'), (3, 'recommended'), (4, 'optional'), (5, 'custom')";
410
-
411
- $this->_wpdb->query( $sql );
412
- }
413
- }
414
-
415
- /**
416
- * Gets the current database version from the database
417
- *
418
- * @since 1.8.0
419
- *
420
- * @return string containing the curren db version
421
- */
422
- private function get_current_db_version() {
423
- $table_name = $this->_wpdb->prefix . 'feedmanager_product_feedmeta';
424
-
425
- return $this->_wpdb->get_var( "SELECT meta_value FROM $table_name WHERE product_feed_id = 0" );
426
- }
427
-
428
- /**
429
- * fills the channel table with supported merchants
430
- */
431
- private function fill_channel_table() {
432
- $channel_class = new TVC_Channel();
433
- $data_class = new TVC_Data();
434
-
435
- $table_name = $this->_wpdb->prefix . 'feedmanager_channel';
436
- $channel_names = $channel_class->get_installed_channel_names();
437
-
438
- // remove the current channels
439
- $this->_wpdb->query( "DELETE FROM $table_name" );
440
-
441
- foreach ( $channel_names as $channel_short_name ) {
442
- $channel_data = $channel_class->get_active_channel_details( $channel_short_name );
443
-
444
- if ( null !== $channel_data && false !== $channel_data ) {
445
- $data_class->register_channel( $channel_short_name, $channel_data );
446
- }
447
- }
448
- }
449
-
450
- /**
451
- * Updates the status table to version 2.2.0
452
- *
453
- * @since 2.2.0
454
- */
455
- private function update_status_table() {
456
- $table_name = $this->_wpdb->prefix . 'feedmanager_feed_status';
457
- $count = $this->_wpdb->get_var( "SELECT COUNT(*) FROM $table_name" );
458
-
459
- if ( $count <= 7 ) {
460
- $format = array( '%d', '%s', '%s' );
461
-
462
- $this->_wpdb->replace(
463
- $table_name,
464
- array(
465
- 'status_id' => '0',
466
- 'status' => 'unknown',
467
- 'color' => '#6549F7',
468
- ),
469
- $format
470
- );
471
-
472
- $this->_wpdb->replace(
473
- $table_name,
474
- array(
475
- 'status_id' => '1',
476
- 'status' => 'ok',
477
- 'color' => '#0073AA',
478
- ),
479
- $format
480
- );
481
-
482
- $this->_wpdb->replace(
483
- $table_name,
484
- array(
485
- 'status_id' => '2',
486
- 'status' => 'on_hold',
487
- 'color' => '#0173AA',
488
- ),
489
- $format
490
- );
491
-
492
- $this->_wpdb->replace(
493
- $table_name,
494
- array(
495
- 'status_id' => '3',
496
- 'status' => 'processing',
497
- 'color' => '#0000FF',
498
- ),
499
- $format
500
- );
501
-
502
- $this->_wpdb->replace(
503
- $table_name,
504
- array(
505
- 'status_id' => '4',
506
- 'status' => 'in_processing_queue',
507
- 'color' => '#00CCFF',
508
- ),
509
- $format
510
- );
511
-
512
- $this->_wpdb->replace(
513
- $table_name,
514
- array(
515
- 'status_id' => '5',
516
- 'status' => 'has_errors',
517
- 'color' => '#FF0000',
518
- ),
519
- $format
520
- );
521
-
522
- $this->_wpdb->replace(
523
- $table_name,
524
- array(
525
- 'status_id' => '6',
526
- 'status' => 'failed_processing',
527
- 'color' => '#FF3300',
528
- ),
529
- $format
530
- );
531
- }
532
- }
533
- }
534
-
535
- // end of TVC_Database class
536
-
537
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/setup/class-tvc-folders.php DELETED
@@ -1,147 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Folder Class.
5
- *
6
- * @package TVC Product Feed Manager/Setup/Classes
7
- * @version 2.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Folders' ) ) :
15
-
16
-
17
- /**
18
- * Folder Class
19
- */
20
- class TVC_Folders {
21
-
22
- public static function make_feed_support_folder() {
23
- if ( ! file_exists( TVC_FEEDS_DIR ) ) {
24
- self::make_tvc_dir( TVC_FEEDS_DIR );
25
- }
26
- }
27
-
28
- public static function make_channels_support_folder() {
29
- if ( ! file_exists( TVC_CHANNEL_DATA_DIR ) ) {
30
- self::make_tvc_dir( TVC_CHANNEL_DATA_DIR );
31
- }
32
- }
33
-
34
- public static function make_backup_folder() {
35
- if ( ! file_exists( TVC_BACKUP_DIR ) ) {
36
- self::make_tvc_dir( TVC_BACKUP_DIR );
37
- }
38
- }
39
-
40
- public static function make_tvc_dir( $dir ) {
41
- wp_mkdir_p( $dir );
42
- }
43
-
44
- public static function update_tvc_channel_dir() {
45
- $old_channel_folder = WP_PLUGIN_DIR . '/tvc-product-feed-manager-support/channels';
46
-
47
- if ( file_exists( $old_channel_folder ) ) {
48
- if ( file_exists( TVC_CHANNEL_DATA_DIR ) ) { // if channels folder already exists, remove it to prevent the rename function from failing
49
- self::delete_folder( TVC_CHANNEL_DATA_DIR );
50
- }
51
-
52
- if ( ! self::copy_folder( $old_channel_folder, TVC_CHANNEL_DATA_DIR ) ) {
53
- return false;
54
- }
55
-
56
- if ( ! self::delete_folder( $old_channel_folder ) ) {
57
- require_once( WP_PLUGIN_DIR . '/tvc-google-analytics-with-google-product-feed/includes/user-interface/tvc-messaging-functions.php' );
58
- /* translators: %s: old channel folder */
59
- echo tvc_show_wp_warning( sprintf( __( 'Unable to remove the %s folder. This folder is not required any more. Please try removing this folder manually using ftp software or an equivalent methode.', 'tvc-product-feed-manager' ), $old_channel_folder ) );
60
- }
61
- }
62
- }
63
-
64
- /**
65
- * Deletes a directory and all its content
66
- *
67
- * @param string $folder_name
68
- *
69
- * @return boolean true when the directory has been deleted
70
- */
71
- public static function delete_folder( $folder_name ) {
72
- if ( is_dir( $folder_name ) ) {
73
-
74
- $dir_handle = opendir( $folder_name );
75
-
76
- if ( ! $dir_handle ) {
77
- return false;
78
- }
79
-
80
- while ( $file = readdir( $dir_handle ) ) {
81
- if ( $file != "." && $file != ".." ) { // do not change this as it can cause serious issues with uninstalling the plugin
82
- if ( ! is_dir( $folder_name . "/" . $file ) ) {
83
- // only remove .xml, .js, .txt or .log files and a class-feed.php files. Do not delete .php or other system files
84
- if ( preg_match( '/.*(.xml$|.js$|.txt$|.log$)|\b(class-feed.php)\b/', $file ) ) {
85
- unlink( $folder_name . "/" . $file );
86
- }
87
- } else {
88
- self::delete_folder( $folder_name . '/' . $file );
89
- }
90
- }
91
- }
92
-
93
- closedir( $dir_handle );
94
- rmdir( $folder_name );
95
-
96
- return true;
97
- } else {
98
- return false;
99
- }
100
- }
101
-
102
- public static function copy_folder( $source_folder, $target_folder ) {
103
- $result = true;
104
- $dir = opendir( $source_folder );
105
-
106
- self::make_tvc_dir( $target_folder );
107
-
108
- while ( false !== ( $file = readdir( $dir ) ) ) {
109
-
110
- if ( ! $result ) {
111
- break;
112
- }
113
-
114
- if ( ( '.' != $file ) && ( '..' != $file ) ) {
115
- if ( is_dir( $source_folder . '/' . $file ) ) {
116
- self::copy_folder( $source_folder . '/' . $file, $target_folder . '/' . $file );
117
-
118
- } else {
119
- $result = copy( $source_folder . '/' . $file, $target_folder . '/' . $file );
120
- }
121
- }
122
-
123
- closedir( $dir );
124
- }
125
-
126
- return $result;
127
- }
128
-
129
- public static function folder_is_empty( $folder ) {
130
- if ( ! is_readable( $folder ) ) {
131
- return null;
132
- }
133
-
134
- $handle = opendir( $folder );
135
-
136
- while ( false !== ( $entry = readdir( $handle ) ) ) {
137
- if ( $entry != "." && $entry != ".." ) {
138
- return false;
139
- }
140
- }
141
-
142
- return true;
143
- }
144
- }
145
- // end of TVC_Folders_Class
146
-
147
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/setup/class-tvc-prepare-taxonomy.php DELETED
@@ -1,375 +0,0 @@
1
- <?php
2
-
3
- // Prevent direct access
4
- if ( ! defined( 'ABSPATH' ) ) {
5
- exit;
6
- }
7
-
8
- if ( ! class_exists( 'TVC_Prepare_Taxonomy' ) ) :
9
-
10
- /**
11
- * The TVC_Prepare_Taxonomy_Class contains functions that can convert taxonomy files provided by channel providers
12
- * to the format that WP Product Feed Manager requires as taxonomy files.
13
- *
14
- * @class TVC_Prepare_Taxonomy_Class
15
- * @version dev
16
- */
17
- class TVC_Prepare_Taxonomy {
18
-
19
- public static function remove_merchant_rates_from_pricegrabber_category_file() {
20
-
21
- $path = TVC_CHANNEL_DATA_DIR . '/pricegrabber/taxonomy.en-US.txt';
22
- $rpath = TVC_CHANNEL_DATA_DIR . '/pricegrabber/taxonomy_new.en-US.txt';
23
-
24
- $fhr = fopen( $path, 'r' );
25
- $fhw = fopen( $rpath, 'w' );
26
-
27
- while ( ! feof( $fhr ) ) {
28
-
29
- $line = fgets( $fhr );
30
-
31
- if ( strpos( $line, ',$' ) !== false ) {
32
- $tline = $line ? substr( $line, 0, strpos( $line, ',$' ) ) : '';
33
- $newline = $tline . "\r\n";
34
- } else {
35
- $newline = $line;
36
- }
37
-
38
- fputs( $fhw, $newline );
39
- }
40
- }
41
-
42
- public static function prepare_amazone_category_file() {
43
-
44
- $path = TVC_CHANNEL_DATA_DIR . '/amazon/taxonomy.en-US.txt';
45
- $rpath = TVC_CHANNEL_DATA_DIR . '/amazon/taxonomy_new.en-US.txt';
46
-
47
- $fhr = fopen( $path, 'r' );
48
- $fhw = fopen( $rpath, 'w' );
49
-
50
- while ( ! feof( $fhr ) ) {
51
-
52
- $line = fgets( $fhr );
53
-
54
- if ( strpos( $line, '/' ) !== false ) {
55
- $newline = str_replace( '/', ' > ', $line );
56
- } else {
57
- $newline = $line;
58
- }
59
-
60
- fputs( $fhw, $newline );
61
- }
62
- }
63
-
64
- public static function prepare_vergelijk_category_file() {
65
-
66
- $path = TVC_CHANNEL_DATA_DIR . '/vergelijk/taxonomy.nl-NL.txt';
67
- $rpath = TVC_CHANNEL_DATA_DIR . '/vergelijk/taxonomy_new.nl-NL.txt';
68
-
69
- $fhr = fopen( $path, 'r' );
70
- $fhw = fopen( $rpath, 'w' );
71
-
72
- while ( ! feof( $fhr ) ) {
73
-
74
- $line = fgets( $fhr );
75
-
76
- $removed_tabs = str_replace( "\t", '|', $line );
77
-
78
- $explode = explode( '|', $removed_tabs );
79
-
80
- $category = $explode[1];
81
-
82
- str_replace( '"', '', $category );
83
-
84
- $newline = $category . ' > ' . $explode[3] . ' > ' . $explode[5];
85
-
86
- fputs( $fhw, $newline );
87
- }
88
-
89
- // now remove the doubles
90
- $l = file( $rpath );
91
- $lines = array_unique( $l );
92
- file_put_contents( $rpath, $lines );
93
- }
94
-
95
- public static function prepare_bol_content_category_file() {
96
- $path = TVC_CHANNEL_DATA_DIR . '/bol_content/taxonomy.nl-NL.txt';
97
- $rpath = TVC_CHANNEL_DATA_DIR . '/bol_content/taxonomy_new.nl-NL.txt';
98
-
99
- $fhr = fopen( $path, 'r' );
100
- $fhw = fopen( $rpath, 'w' );
101
-
102
- while ( ! feof( $fhr ) ) {
103
-
104
- $line = fgets( $fhr );
105
-
106
- $new_line = preg_replace( "/\t/", ' > ', $line );
107
-
108
- fputs( $fhw, $new_line );
109
- }
110
-
111
- // now remove the doubles
112
- $l = file( $rpath );
113
- $lines = array_unique( $l );
114
- file_put_contents( $rpath, $lines );
115
- }
116
-
117
- public static function convert_kieskeurig_category_file() {
118
-
119
- $path = TVC_CHANNEL_DATA_DIR . '/kieskeurig/taxonomy.nl-NL.txt';
120
- $rpath = TVC_CHANNEL_DATA_DIR . '/kieskeurig/taxonomy_new.nl-NL.txt';
121
- $newline = '';
122
-
123
- $fhr = fopen( $path, 'r' );
124
- $fhw = fopen( $rpath, 'w' );
125
-
126
- $r_1 = '';
127
- $r_2 = '';
128
-
129
- $c = 0;
130
-
131
- while ( ! feof( $fhr ) ) {
132
-
133
- $line = fgets( $fhr );
134
-
135
- if ( $c < 2 ) { // remove the first two lines
136
- $newline = '';
137
- $c ++;
138
- } else {
139
-
140
- $line_cats = explode( "\t", $line );
141
-
142
- if ( '' !== $line_cats[0] ) {
143
-
144
- $r_1 = $line_cats[0];
145
-
146
- $newline = '';
147
- } elseif ( '' !== $line_cats[2] ) {
148
-
149
- $r_2 = $line_cats[2];
150
-
151
- $newline = '';
152
- } elseif ( '' !== $line_cats[5] ) {
153
-
154
- $cat_1 = '' === $line_cats[0] ? $r_1 : $line_cats[0];
155
- $cat_2 = '' === $line_cats[2] ? $r_2 : $line_cats[2];
156
- $cat_3 = $line_cats[5];
157
-
158
- $newline = $cat_1 . ' > ' . $cat_2 . ' > ' . $cat_3 . "\r\n";
159
- }
160
- }
161
-
162
- fputs( $fhw, $newline );
163
- }
164
- }
165
-
166
- public static function prepare_beslis_category_file() {
167
-
168
- $path = TVC_CHANNEL_DATA_DIR . '/beslis/category_overview.xml';
169
- $rpath = TVC_CHANNEL_DATA_DIR . '/beslis/taxonomy-new.nl-NL.txt';
170
-
171
- $fhw = fopen( $rpath, 'w' );
172
-
173
- $xml = simplexml_load_file( $path );
174
-
175
- foreach ( $xml->categories->maincat as $main_cat ) {
176
-
177
- $newline = (string) $main_cat['name'][0];
178
-
179
- fputs( $fhw, $newline . "\r\n" );
180
-
181
- foreach ( $main_cat as $level_1 ) {
182
-
183
- $level_1_line = $newline . ' > ' . (string) $level_1['name'][0];
184
-
185
- fputs( $fhw, $level_1_line . "\r\n" );
186
-
187
- foreach ( $level_1 as $level_2 ) {
188
-
189
- $level_2_line = $level_1_line . ' > ' . (string) $level_2['name'][0];
190
-
191
- fputs( $fhw, $level_2_line . "\r\n" );
192
- }
193
- }
194
- }
195
- }
196
-
197
- public static function prepare_heureka_category_file() {
198
- $path = TVC_CHANNEL_DATA_DIR . '/heureka/category_overview.xml';
199
- $rpath = TVC_CHANNEL_DATA_DIR . '/heureka/taxonomy-new.cs-CZ.txt';
200
- $cat_prefix = 'Heureka.cz | ';
201
-
202
- $fhw = fopen( $rpath, 'w' );
203
-
204
- $xml = simplexml_load_file( $path );
205
-
206
- foreach ( $xml->CATEGORY as $main_cat ) {
207
- $newline = $main_cat[0]->CATEGORY_NAME;
208
-
209
- if ( ! empty( $newline ) ) {
210
- fputs( $fhw, $newline . "\r\n" );
211
- }
212
-
213
- foreach ( $main_cat as $level_1 ) {
214
- $level_1_string = substr( $level_1[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
215
- $level_1_line = str_replace( ' | ', ' > ', $level_1_string );
216
-
217
- if ( ! empty( $level_1_line ) ) {
218
- fputs( $fhw, $level_1_line . "\r\n" );
219
- }
220
-
221
- foreach ( $level_1 as $level_2 ) {
222
- $level_2_string = substr( $level_2[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
223
- $level_2_line = str_replace( ' | ', ' > ', $level_2_string );
224
-
225
- if ( ! empty( $level_2_line ) ) {
226
- fputs( $fhw, $level_2_line . "\r\n" );
227
- }
228
-
229
- foreach ( $level_2 as $level_3 ) {
230
- $level_3_string = substr( $level_3[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
231
- $level_3_line = str_replace( ' | ', ' > ', $level_3_string );
232
-
233
- if ( ! empty( $level_3_line ) ) {
234
- fputs( $fhw, $level_3_line . "\r\n" );
235
- }
236
-
237
- foreach ( $level_3 as $level_4 ) {
238
- $level_4_string = substr( $level_4[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
239
- $level_4_line = str_replace( ' | ', ' > ', $level_4_string );
240
-
241
- if ( ! empty( $level_4_line ) ) {
242
- fputs( $fhw, $level_4_line . "\r\n" );
243
- }
244
-
245
- foreach ( $level_4 as $level_5 ) {
246
- $level_5_string = substr( $level_5[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
247
- $level_5_line = str_replace( ' | ', ' > ', $level_5_string );
248
-
249
- if ( ! empty( $level_5_line ) ) {
250
- fputs( $fhw, $level_5_line . "\r\n" );
251
- }
252
-
253
- foreach ( $level_5 as $level_6 ) {
254
- $level_6_string = substr( $level_6[0]->CATEGORY_FULLNAME, strlen( $cat_prefix ) );
255
- $level_6_line = str_replace( ' | ', ' > ', $level_6_string );
256
-
257
- if ( ! empty( $level_6_line ) ) {
258
- fputs( $fhw, $level_6_line . "\r\n" );
259
- }
260
- }
261
- }
262
- }
263
- }
264
- }
265
- }
266
- }
267
- }
268
-
269
- public static function prepare_nextag_category_file() {
270
-
271
- $path = TVC_CHANNEL_DATA_DIR . '/nextag/taxonomy.en-US.txt';
272
- $rpath = TVC_CHANNEL_DATA_DIR . '/nextag/taxonomy_new.en-US.txt';
273
-
274
- $fhr = fopen( $path, 'r' );
275
- $fhw = fopen( $rpath, 'w' );
276
-
277
- while ( ! feof( $fhr ) ) {
278
-
279
- $line = fgets( $fhr );
280
-
281
- if ( strpos( $line, '/' ) !== false ) {
282
-
283
- $newline = str_replace( '/', '>', $line );
284
- } else {
285
-
286
- $newline = $line;
287
- }
288
-
289
- fputs( $fhw, trim( $newline ) . "\r\n" );
290
- }
291
- }
292
-
293
- public static function prepare_ricardo_category_file() {
294
-
295
- $path = TVC_CHANNEL_DATA_DIR . '/ricardo/taxonomy_source.fr-CH.txt';
296
- $rpath = TVC_CHANNEL_DATA_DIR . '/ricardo/taxonomy.fr-CH.txt';
297
-
298
- $fhr = fopen( $path, 'r' );
299
- $fhw = fopen( $rpath, 'w' );
300
-
301
- while ( ! feof( $fhr ) ) {
302
-
303
- $line = trim( fgets( $fhr ) );
304
-
305
- $first_tab_pos = strpos( $line, "\t" );
306
- // get the number
307
- $cat_nr = substr( $line, 0, $first_tab_pos );
308
-
309
- // remove the number
310
- $line = str_replace( $cat_nr . "\t", '', $line );
311
-
312
- if ( strpos( $line, "\t" ) !== false ) {
313
-
314
- $newline = str_replace( "\t", ' > ', $line );
315
- } else {
316
-
317
- $newline = $line;
318
- }
319
-
320
- $newline = trim( $newline, ' > ' );
321
-
322
- fputs( $fhw, trim( $newline . ' (' . $cat_nr . ')' ) . "\r\n" );
323
- }
324
-
325
- }
326
-
327
- public static function prepare_ebay_category_file() {
328
-
329
- $path = TVC_CHANNEL_DATA_DIR . '/ebay/taxonomy_source.en-US.txt';
330
- $rpath = TVC_CHANNEL_DATA_DIR . '/ebay/taxonomy.en-US.txt';
331
-
332
- $fhr = fopen( $path, 'r' );
333
- $fhw = fopen( $rpath, 'w' );
334
-
335
- while ( ! feof( $fhr ) ) {
336
-
337
- $line = trim( fgets( $fhr ) );
338
-
339
- $line_items = explode( ';', $line );
340
-
341
- if ( $line_items[0] && $line_items[1] ) {
342
- fputs( $fhw, trim( $line_items[1] . ' (' . $line_items[0] . ')' ) . "\r\n" );
343
- }
344
- }
345
- }
346
-
347
- public static function prepare_koopjespakker_category_file() {
348
-
349
- $path = TVC_CHANNEL_DATA_DIR . '/koopjespakker/taxonomy.en-US.txt';
350
- $rpath = TVC_CHANNEL_DATA_DIR . '/koopjespakker/taxonomy_new.en-US.txt';
351
-
352
- $fhr = fopen( $path, 'r' );
353
- $fhw = fopen( $rpath, 'w' );
354
-
355
- while ( ! feof( $fhr ) ) {
356
-
357
- $line = fgets( $fhr );
358
-
359
- $newline_1 = str_replace( '/', '>', $line );
360
- $newline_2 = str_replace( '|', '>', $newline_1 );
361
-
362
- $newline = trim( $newline_2 );
363
-
364
- if ( '' !== $newline && strpos( $line, 'concat' ) === false && strpos( $line, 'Options' ) === false ) {
365
- fputs( $fhw, $newline . "\r\n" );
366
- }
367
- }
368
- }
369
-
370
- }
371
-
372
-
373
- // end of TVC_Prepare_Taxonomy_Class
374
-
375
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/setup/google-ads.php CHANGED
@@ -1,254 +1,185 @@
1
  <?php
2
-
3
  class GoogleAds {
 
 
 
 
 
 
 
 
 
 
 
4
 
5
- public function __construct($theURL = '') {
6
- $this->includes();
7
- $this->customApiObj = new CustomApi();
8
- $this->customApiObj->getGoogleAnalyticDetail();
9
-
10
- $this->returnUrl = $_SERVER['REQUEST_URI'];
11
- // $this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
12
-
13
- $this->subscriptionId = (isset($GLOBALS['tatvicData']['tvc_subscription'])) ? $GLOBALS['tatvicData']['tvc_subscription'] : "";
14
- $timezone = get_option('timezone_string');
15
- if($timezone == ""){
16
- $timezone = "America/New_York";
17
- }
18
- $actual_link = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://$_SERVER[HTTP_HOST]";
19
- $this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=estorenew.tatvic.com/config/ads-analytics-form.php?domain=" . $actual_link . "&amp;country=" . (isset($this->woo_country()[0]) ? $this->woo_country()[0] : '') . "&amp;user_currency=".get_option('woocommerce_currency')."&amp;subscription_id=" . $this->subscriptionId . "&amp;confirm_url=" . admin_url() . "&amp;timezone=".$timezone;
20
-
21
-
22
- $this->html_run();
23
- }
24
-
25
- public function includes() {
26
- if (!class_exists('CustomApi.php')) {
27
- require_once(__DIR__ . '/CustomApi.php');
28
- }
29
- if (!class_exists('ShoppingApi')) {
30
- require_once(__DIR__ . '/ShoppingApi.php');
31
- }
 
32
  }
33
-
34
- public function html_run() {
35
- $this->create_form();
36
- }
37
-
38
- public function create_form() {
39
- $api_obj = new CustomApi();
40
-
41
- if (isset($_POST['google-add'])) {
42
- $response = $api_obj->updateTrackingOption($_POST);
43
-
44
- if (isset($response->errors) && !empty($response->errors)) {
45
- $error_code = array_keys($response->errors)[0];
46
- $class = 'notice notice-error';
47
- if (isset($response->error_data[$error_code]->errors->key[0])) {
48
- $message = esc_html__($licenceRes->error_data[$response]->errors->key[0], 'sample-text-domain');
49
- } else {
50
- $message = esc_html__(isset($response->error_data[$error_code]->errors[0]) ? $response->error_data[$error_code]->errors[0] : 'Something Went Wrong', 'sample-text-domain');
51
- }
52
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Error : ' . $message));
53
- } else {
54
- $response = $response->data;
55
- if ($response['status'] == 200) {
56
- $class = 'notice notice-success';
57
- $message = esc_html__('The tracking options added successfully.');
58
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
59
- // $url = admin_url('admin.php?page=tvc-configuration-page');
60
- //wp_redirect($url);
61
- }
62
- }
63
- }
64
- if (isset($_POST['verify-licence-key'])) {
65
- $licenceRes = $api_obj->verifyLicenceKey($_POST);
66
- if (isset($licenceRes->errors) && !empty($licenceRes->errors)) {
67
- $error_code = array_keys($licenceRes->errors)[0];
68
- $class = 'notice notice-error';
69
- if (isset($licenceRes->error_data[$error_code]->errors->key[0])) {
70
- $message = esc_html__($licenceRes->error_data[$error_code]->errors->key[0], 'sample-text-domain');
71
- } else {
72
- $message = esc_html__(isset($licenceRes->error_data[$error_code]->errors[0]) ? $licenceRes->error_data[$error_code]->errors[0] : 'Something Went Wrong', 'sample-text-domain');
73
- }
74
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Error : ' . $message));
75
- } else {
76
- $licenceRes = $licenceRes->data;
77
- if ($licenceRes['status'] == 200) {
78
- $class = 'notice notice-success';
79
- $message = esc_html__('Your licence key is valid ');
80
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
81
- // $url = admin_url('admin.php?page=tvc-configuration-page');
82
- //wp_redirect($url);
83
- }
84
- }
85
- }
86
- $googleDetail = [];
87
- $google_detail = $api_obj->getGoogleAnalyticDetail();
88
- //print_r($google_detail);
89
- if (isset($google_detail->data['status']) && $google_detail->data['status'] == 200) {
90
- // if (count($google_detail->data['data']) > 0) {
91
- if ($google_detail->data['data']) {
92
- $googleDetail = $google_detail->data['data'];
93
- }
94
- } else {
95
- $googleDetail = [];
96
- $class = 'notice notice-error';
97
- $message = esc_html__('Connect Google Ads account to enable features.');
98
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
99
- }
100
- //update option in wordpress local database
101
- if(!empty($googleDetail)){
102
- update_option('ads_ert', $googleDetail->remarketing_tags);
103
- update_option('ads_edrt', $googleDetail->dynamic_remarketing_tags);
104
- update_option('ads_tracking_id', $googleDetail->google_ads_snippets);
105
- }
106
-
107
- echo '<div class="container-fluid">
108
  <div class="row">
109
  <div class= "col col-12">
110
  <div class="card mw-100" style="padding: 0px;">
111
  <div class="card-body">
112
  <div class="tab-pane show active" id="googleAds">
113
  <div class="row">
114
- <div class="col-md-6 col-lg-8 border-right">
115
- <div class="licence">
116
- <p>You are using our free plugin, no licence needed ! Happy analyzing..!! :)</p>
117
- <p>To unlock more features of google products, consider our <a href="https://codecanyon.net/item/actionable-google-analytics-for-woocommerce/9899552?utm_source=TatvicEE&utm_medium=DashboardBuyBottom&utm_campaign=WPlisting" target="_blank" class="text-underline">pro version.</a></p>
118
- </div>
119
- <form method="post" name="google-analytic" class="tvc_ee_plugin_form">
120
- <input type="hidden" name="subscription_id" value="';
121
- echo (isset($GLOBALS['tatvicData']['tvc_subscription'])) ? $GLOBALS['tatvicData']['tvc_subscription'] : "";
122
- echo '">
123
- <div class="google-account-analytics">
124
- <div class="row mb-3">
125
- <div class="col-6 col-md-6">
126
- <h2 class="ga-title">Connected Google Ads account:</h2>
127
- </div>
128
- <div class="col-6 col-md-3">
129
- <p class="ga-text">' . (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '' ? $googleDetail->google_ads_id : '--');
130
- echo '</div>
131
- <div class="col-6 col-md-3">';
132
- if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
133
- echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
134
- } else {
135
- echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
136
- }
137
- echo '</div>
138
- </div>
139
- <div class="row mb-3">
140
- <div class="col-6 col-md-6">
141
- <h2 class="ga-title">Linked Google Analytics Account:</h2>
142
- </div>
143
- <div class="col-6 col-md-3">
144
- <p class="ga-text">' . (isset($googleDetail->property_id) && $googleDetail->property_id != '' ? $googleDetail->property_id : '--') . '
145
- </p>';
146
- echo '</div>
147
- <div class="col-6 col-md-3">';
148
- if (isset($googleDetail->property_id) && $googleDetail->property_id != '') {
149
- echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
150
- } else {
151
- echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
152
- }
153
- echo '</div>
154
- </div>
155
- <div class="row mb-3">
156
- <div class="col-6 col-md-6">
157
- <h2 class="ga-title">Linked Google Merchant Center Account:</h2>
158
- </div>
159
- <div class="col-6 col-md-3">
160
- <p class="ga-text">' . (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '' ? $googleDetail->google_merchant_center_id : '--') . '
161
- </p>';
162
- echo '</div>
163
- <div class="col-6 col-md-3">';
164
- if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {
165
- echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
166
- } else {
167
- echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
168
- }
169
- echo '</div>
170
- </div>';
171
- if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
172
- echo '<div class="row">
173
- <div class="col-md-12">
174
- <div class="form-group">
175
- <div class="tvc-custom-control tvc-custom-checkbox">
176
- <input type="checkbox" class="tvc-custom-control-input" id="customCheck1" name="remarketing_tags" value="1"';
177
- echo ($googleDetail->remarketing_tags == 1) ? 'checked="checked"' : '';
178
- echo '>
179
- <label class="tvc-custom-control-input" for="customCheck1">Enable remarketing tags</label>
180
- </div>
181
- </div>
182
- </div>
183
- <div class="col-md-12">
184
- <div class="form-group">
185
- <div class="tvc-custom-control tvc-custom-checkbox">
186
- <input type="checkbox" class="tvc-custom-control-input" id="customCheck2" name="dynamic_remarketing_tags" value="1"';
187
- echo ($googleDetail->dynamic_remarketing_tags == 1) ? 'checked="checked"' : '';
188
- echo '>
189
- <label class="tvc-custom-control-input" for="customCheck2">Enable dynamic remarketing tags</label>
190
- </div>
191
- </div>
192
- </div>
193
- <div class="col-md-12">
194
- <div class="form-group">
195
- <div class="tvc-custom-control tvc-custom-checkbox">
196
- <input type="checkbox" class="tvc-custom-control-input" id="customCheck3" name="link_google_analytics_with_google_ads" value="1"';
197
- echo ($googleDetail->link_google_analytics_with_google_ads == 1) ? 'checked="checked"' : '';
198
- echo '>
199
- <label class="tvc-custom-control-input" for="customCheck3">Link Google analytics with google ads</label>
200
- </div>
201
- </div>
202
- </div>
203
-
204
- </div>';
205
- }else{
206
- $icon_img ='<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="configuration success" class="config-success">';
207
- ?>
208
- <h2 class="ga-title">Connect Google Ads account to enable below features.</h2>
209
- <br>
210
- <ul>
211
- <li><?php echo $icon_img;?>Enable remarketing tags</li>
212
- <li><?php echo $icon_img;?>Enable dynamic remarketing tags</li>
213
- <li><?php echo $icon_img;?>Link Google analytics with google ads</li>
214
-
215
- </ul>
216
- <?php
217
- }
218
- echo '</div>';
219
- if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
220
- echo '<div class="text-left">
221
- <button type="submit" class="btn btn-primary btn-success" name="google-add">Save</button>
222
- </div>';
223
- }
224
- echo '</form>
225
- </div>
226
- <div class="col-md-6 col-lg-4">
227
- <div class="right-content">
228
- '.get_tvc_google_ads_help_html().'
229
- </div>
230
- </div>
231
  </div>
232
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
233
  </div>
234
  </div>
235
  </div>
236
  </div>
237
- </div>'.get_connect_google_popup_html();
 
238
  }
239
-
240
- /**
241
- * @return array
242
- * Get woocommerce default set country
243
- */
244
- public function woo_country() {
245
- // The country/state
246
- $store_raw_country = get_option('woocommerce_default_country');
247
- // Split the country/state
248
- $split_country = explode(":", $store_raw_country);
249
- return $split_country;
250
- }
251
-
252
  }
253
-
254
  ?>
1
  <?php
 
2
  class GoogleAds {
3
+ protected $TVC_Admin_Helper="";
4
+ protected $url = "";
5
+ protected $subscriptionId = "";
6
+ protected $google_detail;
7
+ public function __construct($theURL = '') {
8
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
9
+ $this->url = $this->TVC_Admin_Helper->get_connect_url();
10
+ $this->subscriptionId = $this->TVC_Admin_Helper->get_subscriptionId();
11
+ $this->google_detail = $this->TVC_Admin_Helper->get_ee_options_data();
12
+ $this->create_form();
13
+ }
14
 
15
+ public function create_form() {
16
+ if (isset($_POST['google-add'])) {
17
+ $googleDetail = $this->google_detail;
18
+ $googleDetail_setting = $this->google_detail['setting'];
19
+ if(isset($_POST['remarketing_tags'])){
20
+ update_option('ads_ert', $_POST['remarketing_tags']);
21
+ $googleDetail_setting->remarketing_tags = $_POST['remarketing_tags'];
22
+ }else{
23
+ update_option('ads_ert', 0);
24
+ $googleDetail_setting->remarketing_tags = 0;
25
+ }
26
+ if(isset($_POST['dynamic_remarketing_tags'])){
27
+ update_option('ads_edrt', $_POST['dynamic_remarketing_tags']);
28
+ $googleDetail_setting->dynamic_remarketing_tags = $_POST['dynamic_remarketing_tags'];
29
+ }else{
30
+ update_option('ads_edrt', 0);
31
+ $googleDetail_setting->dynamic_remarketing_tags = 0;
32
+ }
33
+ if(isset($_POST['link_google_analytics_with_google_ads'])){
34
+ $googleDetail_setting->link_google_analytics_with_google_ads = $_POST['link_google_analytics_with_google_ads'];
35
+ }else{
36
+ $googleDetail_setting->link_google_analytics_with_google_ads = 0;
37
+ }
38
+ $googleDetail['setting'] =$googleDetail_setting;
39
+ $this->TVC_Admin_Helper->set_ee_options_data($googleDetail);
40
+ $class = 'notice notice-success';
41
+ $message = esc_html__('The tracking options added successfully.');
42
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
43
  }
44
+
45
+ $googleDetail = [];
46
+ if(isset($this->google_detail['setting'])){
47
+ if ($this->google_detail['setting']) {
48
+ $googleDetail = $this->google_detail['setting'];
49
+ }
50
+ }?>
51
+ <div class="container-fluid">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
52
  <div class="row">
53
  <div class= "col col-12">
54
  <div class="card mw-100" style="padding: 0px;">
55
  <div class="card-body">
56
  <div class="tab-pane show active" id="googleAds">
57
  <div class="row">
58
+ <div class="col-md-6 col-lg-8 border-right">
59
+ <div class="licence">
60
+ <p>You are using our free plugin, no licence needed ! Happy analyzing..!! :)</p>
61
+ <p>To unlock more features of google products, consider our <a href="https://codecanyon.net/item/actionable-google-analytics-for-woocommerce/9899552?utm_source=TatvicEE&utm_medium=DashboardBuyBottom&utm_campaign=WPlisting" target="_blank" class="text-underline">pro version.</a></p>
62
+ </div>
63
+ <form method="post" name="google-analytic" class="tvc_ee_plugin_form">
64
+ <input type="hidden" name="subscription_id" value="<?php echo (($this->subscriptionId)?$this->subscriptionId:"");?>">
65
+ <div class="google-account-analytics">
66
+ <div class="row mb-3">
67
+ <div class="col-6 col-md-6">
68
+ <h2 class="ga-title">Connected Google Ads account:</h2>
69
+ </div>
70
+ <div class="col-6 col-md-3">
71
+ <p class="ga-text">
72
+ <?php echo ((isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') ? $googleDetail->google_ads_id : '--'); ?>
73
+ </p>
74
+ </div>
75
+ <div class="col-6 col-md-3">
76
+ <?php
77
+ if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
78
+ echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
79
+ } else {
80
+ echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
81
+ }?>
82
+ </div>
83
+ </div>
84
+ <div class="row mb-3">
85
+ <div class="col-6 col-md-6">
86
+ <h2 class="ga-title">Linked Google Analytics Account:</h2>
87
+ </div>
88
+ <div class="col-6 col-md-3">
89
+ <p class="ga-text">
90
+ <?php echo (isset($googleDetail->property_id) && $googleDetail->property_id != '' ? $googleDetail->property_id : '--');?>
91
+ </p>
92
+ </div>
93
+ <div class="col-6 col-md-3">
94
+ <?php
95
+ if (isset($googleDetail->property_id) && $googleDetail->property_id != '') {
96
+ echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
97
+ } else {
98
+ echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
99
+ } ?>
100
+ </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
101
  </div>
102
+ <div class="row mb-3">
103
+ <div class="col-6 col-md-6">
104
+ <h2 class="ga-title">Linked Google Merchant Center Account:</h2>
105
+ </div>
106
+ <div class="col-6 col-md-3">
107
+ <p class="ga-text"><?php echo (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '' ? $googleDetail->google_merchant_center_id : '--'); ?>
108
+ </p>
109
+ </div>
110
+ <div class="col-6 col-md-3">
111
+ <?php
112
+ if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {
113
+ echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
114
+ } else {
115
+ echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
116
+ } ?>
117
+ </div>
118
+ </div>
119
+ <?php
120
+ if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') { ?>
121
+ <div class="row">
122
+ <div class="col-md-12">
123
+ <div class="form-group">
124
+ <div class="tvc-custom-control tvc-custom-checkbox">
125
+ <input type="checkbox" class="tvc-custom-control-input" id="customCheck1" name="remarketing_tags" value="1" <?php echo ($googleDetail->remarketing_tags == 1) ? 'checked="checked"' : ''; ?> >
126
+ <label class="tvc-custom-control-input" for="customCheck1">Enable remarketing tags</label>
127
+ </div>
128
+ </div>
129
+ </div>
130
+ <div class="col-md-12">
131
+ <div class="form-group">
132
+ <div class="tvc-custom-control tvc-custom-checkbox">
133
+ <input type="checkbox" class="tvc-custom-control-input" id="customCheck2" name="dynamic_remarketing_tags" value="1" <?php echo ($googleDetail->dynamic_remarketing_tags == 1) ? 'checked="checked"' : ''; ?>>
134
+ <label class="tvc-custom-control-input" for="customCheck2">Enable dynamic remarketing tags</label>
135
+ </div>
136
+ </div>
137
+ </div>
138
+ <div class="col-md-12">
139
+ <div class="form-group">
140
+ <div class="tvc-custom-control tvc-custom-checkbox">
141
+ <input type="checkbox" class="tvc-custom-control-input" id="customCheck3" name="link_google_analytics_with_google_ads" value="1" <?php echo ($googleDetail->link_google_analytics_with_google_ads == 1) ? 'checked="checked"' : ''; ?> >
142
+ <label class="tvc-custom-control-input" for="customCheck3">Link Google analytics with google ads</label>
143
+ </div>
144
+ </div>
145
+ </div>
146
+ </div>
147
+ <?php
148
+ }else{
149
+ $icon_img ='<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="configuration success" class="config-success">';
150
+ ?>
151
+ <h2 class="ga-title">Connect Google Ads account to enable below features.</h2>
152
+ <br>
153
+ <ul>
154
+ <li><?php echo $icon_img;?>Enable remarketing tags</li>
155
+ <li><?php echo $icon_img;?>Enable dynamic remarketing tags</li>
156
+ <li><?php echo $icon_img;?>Link Google analytics with google ads</li>
157
+
158
+ </ul>
159
+ <?php
160
+ } ?>
161
+ </div>
162
+ <?php
163
+ if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') { ?>
164
+ <div class="text-left">
165
+ <button type="submit" class="btn btn-primary btn-success" name="google-add">Save</button>
166
+ </div>
167
+ <?php } ?>
168
+ </form>
169
+ </div>
170
+ <div class="col-md-6 col-lg-4">
171
+ <div class="right-content">
172
+ <?php echo get_tvc_google_ads_help_html(); ?>
173
+ </div>
174
+ </div>
175
+ </div>
176
+ </div>
177
  </div>
178
  </div>
179
  </div>
180
  </div>
181
+ </div>
182
+ <?php echo get_connect_google_popup_html();
183
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
184
  }
 
185
  ?>
includes/setup/google-shopping-feed-gaa-config.php CHANGED
@@ -1,497 +1,440 @@
1
  <?php
2
-
3
  class GAAConfiguration {
4
-
5
- public $merchantId;
6
- public $customApiObj;
7
-
8
- public function __construct() {
9
- $this->includes();
10
- $this->returnUrl = $_SERVER['REQUEST_URI'];
11
- //$this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
12
-
13
- $this->customApiObj = new CustomApi();
14
- $this->customApiObj->getGoogleAnalyticDetail();
15
-
16
- $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant'] : "";
17
- $this->accountId = (isset($GLOBALS['tatvicData']['tvc_main_merchant_id'])) ? $GLOBALS['tatvicData']['tvc_main_merchant_id'] : "";
18
- $this->currentCustomerId = (isset($GLOBALS['tatvicData']['tvc_customer'])) ? $GLOBALS['tatvicData']['tvc_customer'] : "";
19
- $this->subscriptionId = (isset($GLOBALS['tatvicData']['tvc_subscription'])) ? $GLOBALS['tatvicData']['tvc_subscription'] : "";
20
- $this->country = (isset($GLOBALS['tatvicData']['tvc_country'])) ? $GLOBALS['tatvicData']['tvc_country'] : "";
21
- $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
22
-
23
- $actual_link = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://$_SERVER[HTTP_HOST]";
24
- $store_currency = $this->get_store_currency();
25
- $timezone = get_option('timezone_string');
26
- if($timezone == ""){
27
- $timezone = "America/New_York";
28
- }
29
- $this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=estorenew.tatvic.com/config/ads-analytics-form.php?domain=" . $actual_link . "&amp;country=" . (isset($this->woo_country()[0]) ? $this->woo_country()[0] : '') . "&amp;user_currency=".$store_currency."&amp;subscription_id=" . $this->subscriptionId . "&amp;confirm_url=" . admin_url() . "&amp;timezone=" . $timezone;
30
- $this->html_run();
31
- }
32
-
33
- public function get_store_currency(){
34
-
35
- $country = (!empty($this->woo_country()[0])) ? $this->woo_country()[0] : 'US';
36
- $getCurrency = file_get_contents(ENHANCAD_PLUGIN_DIR . 'includes/setup/json/currency.json');
37
- $contData = json_decode($getCurrency);
38
- return ((get_option('woocommerce_currency') != '') ? get_option('woocommerce_currency') : ((!empty($contData->{$country}))?$contData->{$country}:"") );
39
- }
40
- public function includes() {
41
- if (!class_exists('CustomApi.php')) {
42
- require_once(__DIR__ . '/CustomApi.php');
43
- }
44
- if (!class_exists('Tatvic_Category_Wrapper')) {
45
- require_once(__DIR__ . '/tatvic-category-wrapper.php');
46
- }
47
  }
48
-
49
- public function html_run() {
50
- $this->spinner();
51
- $this->create_form();
52
- }
53
-
54
- public function spinner() {
55
- $spinner_gif = ENHANCAD_PLUGIN_URL . '/images/ajax-loader.gif';
56
- echo '<div class="feed-spinner" id="feed-spinner" style="display:none;">
57
- <img id="img-spinner" src="' . $spinner_gif . '" alt="Loading" />
58
- </div>';
59
- }
60
-
61
- public function gmcAttributes() {
62
- $path = TVC_CHANNEL_DATA_DIR . '/google/gmc_attrbutes.json';
63
- $str = file_get_contents($path);
64
- $attributes = $str ? json_decode($str, true) : [];
65
- return $attributes;
 
 
 
66
  }
67
-
68
- public function wooCommerceAttributes() {
69
- $queries = new TVC_Queries();
70
- $column1 = json_decode(json_encode($queries->getTableColumns('wp_posts')), true);
71
- $column2 = json_decode(json_encode($queries->getTableData('wp_postmeta', ['meta_key'])), true);
72
- return array_merge($column1, $column2);
73
- }
74
-
75
- public function create_form() {
76
- $category_wrapper_obj = new Tatvic_Category_Wrapper();
77
- $category_wrapper = $category_wrapper_obj->category_table_content('mapping');
78
-
79
- if (isset($_POST['google-analytic'])) {
80
- $this->customApiObj->updateTrackingOption($_POST);
81
- }
82
- $googleDetail = [];
83
- $google_detail = $this->customApiObj->getGoogleAnalyticDetail();
84
- if (isset($google_detail->data['status']) && $google_detail->data['status'] == 200) {
85
- if (isset($google_detail->data['data'])) {
86
- $googleDetail = $google_detail->data['data'];
87
- }
88
- } else {
89
- $googleDetail = [];
90
- $class = 'notice notice-error';
91
- $message = esc_html__('Connect Google account to enable features.');
92
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
93
- }
94
-
95
-
96
- echo '<div class="container-fluid">
97
  <div class="row">
98
  <div class= "col col-12">
99
  <div class="card mw-100" style="padding:0;">
100
  <div class="card-body">
101
- <div class="tab-pane show active" id="googleShoppingFeed">
102
- <div class="row">
103
- <div class="col-md-6 col-lg-8 border-right">
104
- <div class="configuration-section" id="config-pt1">
105
- '.get_google_shopping_tabs_html($this->site_url,(isset($googleDetail->google_merchant_center_id))?$googleDetail->google_merchant_center_id:"").'
106
- </div>
107
- <div class="mt-3" id="config-pt2">
108
- <div class="google-account-analytics" id="gaa-config">
109
- <div class="licence">
110
- <p>You are using our free plugin, no licence needed ! Happy analyzing..!! :)</p>
111
- <p>To unlock more features of google products, consider our <a href="https://codecanyon.net/item/actionable-google-analytics-for-woocommerce/9899552?utm_source=TatvicEE&utm_medium=DashboardBuyBottom&utm_campaign=WPlisting" target="_blank" class="text-underline">pro version.</a></p>
112
- </div>
113
- <div class="row mb-3">
114
- <div class="col-6 col-md-6">
115
- <h2 class="ga-title">Connected Google Merchant center account:</h2>
116
- </div>
117
- <div class="col-6 col-md-3">
118
- <p class="ga-text">' . (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '' ? $googleDetail->google_merchant_center_id : 'N/A') . '</p>';
119
- echo '</div>
120
- <div class="col-6 col-md-3">';
121
-
122
- if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {
123
- echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
124
- } else {
125
- echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
126
- }
127
- echo '</div>
128
- </div>
129
- <div class="row mb-3">
130
- <div class="col-6 col-md-6">
131
- <h2 class="ga-title">Linked Google Ads Account:</h2>
132
- </div>
133
- <div class="col-6 col-md-3">
134
- <p class="ga-text">' . (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '' ? $googleDetail->google_ads_id : 'N/A') . '</p>';
135
- echo '</div>
136
- <div class="col-6 col-md-3">';
137
- if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
138
- echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
139
- } else {
140
- echo '<p class="ga-text text-right">Click here to <a href="#" data-toggle="modal" data-target="#tvc_google_connect" class="text-underline">connect</a></p>';
141
- }
142
- echo '</div>
143
- </div>';
144
- if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {
145
- echo '<div class="row mb-3">
146
- <div class="col-6 col-md-6">
147
- <h2 class="ga-title">Sync Products:</h2>
148
- </div>
149
- <div class="col-6 col-md-6">
150
-
151
-
152
- <button type="button" class="btn btn-primary btn-success" data-toggle="modal" data-target="#syncProduct">Sync New Products</button>
153
-
154
- </div>
155
- </div>
156
-
157
- <div class="row mb-3">
158
- <div class="col-6 col-md-6">
159
- <h2 class="ga-title">Smart Shopping Campaigns:</h2>
160
- </div>
161
- <div class="col-6 col-md-6">
162
- <a href="admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=add_campaign_page" class="btn btn-primary btn-success">Create Smart Shopping Campaign</a>
163
- </div>
164
- </div>';
165
- }else{
166
- echo '<div class="row mb-3">
167
- <div class="col-6 col-md-6">
168
- <h2 class="ga-title">Sync Products:</h2>
169
  </div>
170
- <div class="col-6 col-md-6">
171
- <button type="button" class="btn btn-primary btn-success" data-toggle="modal" data-target="#tvc_google_connect">Sync New Products</button>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
172
  </div>
 
 
 
 
173
  </div>
174
- <div class="row mb-3">
175
- <div class="col-6 col-md-6">
176
- <h2 class="ga-title">Smart Shopping Campaigns:</h2>
177
- </div>
178
- <div class="col-6 col-md-6">
179
- <a href="#" class="btn btn-primary btn-success" data-toggle="modal" data-target="#tvc_google_connect">Create Smart Shopping Campaign</a>
180
- </div>
181
- </div>';
182
-
183
- }
184
- echo '</div>
185
- </div>
186
- </div>
187
- <div class="col-md-6 col-lg-4">
188
- <div class="right-content">
189
- '.get_tvc_help_html().'
190
- </div>
191
- </div>
192
- </div>
193
- </div>
194
  </div>
195
  </div>
196
  </div>
197
  </div>
198
  </div>
199
  <div class="modal fade popup-modal create-campaign" id="syncProduct" data-backdrop="false">
200
- <div class="modal-dialog modal-dialog-centered">
201
- <div class="modal-content">
202
- <div class="modal-body mt-3">
203
- <h5>Map your product attributes <span style="float:right"><button type="button" class="close" data-dismiss="modal"> &times; </button> </span></h5>
204
- <p>Google Merchant Center uses attributes to format your product information for Shopping Ads. Map your product attributes to the Merchant Center product attributes below. You can also edit each product’s individual attributes after you sync your products. Not all fields below are marked required, however based on your shop\'s categories and your country you might map a few optional attributes as well. See the full guide <a target="_blank" href="https://support.google.com/merchants/answer/7052112">here</a>.
205
- </p>
206
- <div class="wizard-section campaign-wizard">
207
- <div class="wizard-content">
208
- <input type="hidden" name="merchant_id" id="merchant_id" value="' . $this->merchantId . '">
209
- <input type="hidden" name="platform_customer_id" id="platform_customer_id" value="111">
210
- <form class="tab-wizard wizard- wizard" id="productSync" method="POST">
211
- <h5>
212
- <span class="wiz-title">Category Mapping</span>
213
- </h5>
214
- <section>
215
- <div class="card-wrapper">
216
- <div class="row">
217
- <div class="col-6">
218
- <h6 class="heading-tbl">WooCommerce Category</h6>
219
- </div>
220
- <div class="col-6">
221
- <h6 class="heading-tbl">Google Merchant Center Category</h6>
222
- </div>
223
- </div>' . $category_wrapper . '
224
- </div>
225
- </section>
226
- <!-- Step 2 -->
227
- <h5>
228
- <span class="wiz-title">Product Attribution Mapping</span>
229
- </h5>
230
- <section>
231
- <div class="card-wrapper">
232
- <div class="row">
233
- <div class="col-6">
234
- <h6 class="heading-tbl">Google Merchant center product attributes</h6>
235
- </div>
236
- <div class="col-6">
237
- <h6 class="heading-tbl">WooCommerce product attributes</h6>
238
- </div>
239
- </div>';
240
-
241
- foreach ($this->gmcAttributes() as $key => $attribute) {
242
- echo '<div class="row">
243
- <div class="col-6 align-self-center">
244
- <div class="form-group">
245
- <span class="td-head">' . $attribute["field"] . " " . (isset($attribute["required"]) && $attribute["required"] == 1 ? '<span style="color: red;"> *</span>' : "") . '</span>
246
- <small class="form-label-control">' . (isset($attribute["desc"])? $attribute["desc"]:"") . '</small>
247
- </div>
248
- </div>
249
- <div class="col-6 align-self-center">
250
- <div class="form-group">';
251
- if($attribute["field"]=='link'){
252
- echo "product link";
253
- }else if($attribute["field"]=='channel'){
254
- echo "online";
255
- }else{
256
- echo '<select class="form-control select2 ' . (isset($attribute["required"]) && $attribute["required"] == 1 ? "field-required" : "") . '" name="' . $attribute["field"] . '" >
257
- <option value="0">Please Select Attribute</option>';
258
-
259
- foreach ($this->wooCommerceAttributes() as $wKey => $wAttribute) {
260
- echo '<option value="' . $wAttribute["field"] . '"';
261
- echo (isset($attribute['required']) && $attribute['required'] == 1 && $attribute['wAttribute'] == $wAttribute["field"]) ? "selected" : "";
262
- echo '>' . $wAttribute["field"] . '</option>';
263
- }
264
- echo '</select>';
265
- }
266
- echo '</div>
267
- </div>
268
- </div>';
269
- }
270
- echo '</div>
271
- </section>
272
- </form>
273
  </div>
 
274
  </div>
275
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
276
  </div>
 
277
  </div>
278
- </div>'.get_connect_google_popup_html().'
279
-
280
  <script type="text/javascript">
281
- $(document).ready(function() {
282
- $(".select2").select2();
283
- });
284
-
285
- $(".tab-wizard").steps({
286
- headerTag: "h5",
287
- bodyTag: "section",
288
- transitionEffect: "fade",
289
- titleTemplate: \'<span class="step">#index#</span> #title#\',
290
- labels: {
291
- finish: "Finish",
292
- next: "Next",
293
- previous: "Previous",
294
- },
295
- onStepChanged: function(event, currentIndex, priorIndex) {
296
- $(\'.steps .current\').prevAll().addClass(\'disabled\');
297
- },
298
- onFinished: function(event, currentIndex) {
299
- //check for required fields
300
- var valid=true;
301
- jQuery(".field-required").each(function() {
302
- if($(this).val()==0 && valid){
303
- valid=false;
304
- }
305
- });
306
- if(!valid){
307
- alert("Please select all required fields");
308
- }else{
309
- submitProductSyncUp();
310
- }
311
- //check for required fields end
312
-
313
- }
314
  });
315
-
316
- function submitProductSyncUp() {
317
- var merchantId = ' . $this->merchantId . ';
318
- var accountId = ' . $this->accountId . ';
319
- var customerId = ' . $this->currentCustomerId . ';
320
- var subscriptionId = ' . $this->subscriptionId . ';
321
- var platformCustomerId = jQuery("#platform_customer_id").val();
322
-
323
- var formData = jQuery("#productSync").serialize();
324
- console.log(formData);
325
- jQuery("#feed-spinner").css("display", "block");
326
-
327
- jQuery.post(
328
- myAjaxNonces.ajaxurl,
329
- {
330
- action: "tvcajax-product-syncup",
331
- merchantId: merchantId,
332
- customerId: customerId,
333
- accountId: accountId,
334
- subscriptionId: subscriptionId,
335
- platformCustomerId: platformCustomerId,
336
- data: formData,
337
- productSyncupNonce: myAjaxNonces.productSyncupNonce,
338
-
339
- },
340
- function( response ) {
341
- jQuery("#feed-spinner").css("display", "none");
342
- console.log(response);
343
- var rsp = JSON.parse(response)
344
- if (rsp.status == "success") {
345
- $(\'#syncProduct\').modal(\'hide\');
346
- var message = "Your product are now being synced in your merchant center account. It takes up to 30 minutes to reflect the product data in merchant center. As soon as they are updated, they will be shown in the \"Product Sync\" dashboard.";
347
- alert(message);
348
- window.location.replace("'.$this->site_url.'sync_product_page");
349
- } else {
350
- //var message = "Products sync face some unprocessable entity";
351
- var message = rsp.message;
352
- alert(message);
353
- }
354
- }
355
- );
356
-
357
- }
358
-
359
- $(document).on("show.bs.modal", "#syncProduct", function (e) {
360
- jQuery("#feed-spinner").css("display", "block");
361
- selectCategory();
362
- $("select[id^=catmap]").each(function(){
363
- removeChildCategory($(this).attr("id"))
364
- });
365
- });
366
-
367
- function selectCategory() {
368
- var country_id = "' . $this->country . '";
369
- var customer_id = ' . $this->currentCustomerId . ';
370
- var parent = "";
371
- jQuery.post(
372
- myAjaxNonces.ajaxurl,
373
- {
374
- action: "tvcajax-gmc-category-lists",
375
- countryCode: country_id,
376
- customerId: customer_id,
377
- parent: parent,
378
- gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce,
379
-
380
- },
381
- function( response ) {
382
- var categories = JSON.parse(response);
383
- var obj;
384
- $("select[id^=catmap]").each(function(){
385
- obj = $("#catmap-"+$(this).attr("catid")+"_0");
386
- obj.empty();
387
- obj.append("<option id=' . "0" . ' value=' . "0" . ' resourcename=' . "0" . '>Select a category</option>");
388
- $.each(categories, function (i, value) {
389
- obj.append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
390
-
391
- });
392
- });
393
- jQuery("#feed-spinner").css("display", "none");
394
- }
395
- );
396
  }
 
 
397
 
398
- function selectSubCategory(thisObj) {
399
- var selectId;
400
- var wooCategoryId;
401
- var GmcCategoryId;
402
- var GmcParent;
403
-
404
- selectId = thisObj.id;
405
- wooCategoryId = $(thisObj).attr("catid");
406
- GmcCategoryId = $(thisObj).find(":selected").val();
407
- GmcParent = $(thisObj).find(":selected").attr("resourcename");
408
-
409
- //$("#"+selectId).select2().find(":selected").val();
410
- // $("#"+selectId).select2().find(":selected").data("id");
411
- console.log(selectId+"--"+wooCategoryId+"--"+GmcCategoryId+"--"+GmcParent);
412
-
413
- jQuery("#feed-spinner").css("display", "block");
414
- removeChildCategory(selectId);
415
- selectChildCategoryValue(wooCategoryId)
416
- if (GmcParent != undefined) {
417
- var country_id = "' . $this->country . '";
418
- var customer_id = ' . $this->currentCustomerId . ';
419
- jQuery.post(
420
- myAjaxNonces.ajaxurl,
421
- {
422
- action: "tvcajax-gmc-category-lists",
423
- countryCode: country_id,
424
- customerId: customer_id,
425
- parent: GmcParent,
426
- gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce,
427
-
428
- },
429
- function( response ) {
430
- var categories = JSON.parse(response);
431
- var newId;
432
- var slitedId = selectId.split("_");
433
- newId = slitedId[0]+"_"+ ++slitedId[1];
434
- if (categories.length === 0) {
435
-
436
- } else {
437
- console.log(newId);
438
- $("#"+newId).empty();
439
- $("#"+newId).append("<option id=' . "0" . ' value=' . "0" . ' resourcename=' . "0" . '>Select a sub-category</option>");
440
- $.each(categories, function (i, value) {
441
- $("#"+newId).append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
442
- });
443
- $("#"+newId).addClass("form-control");
444
- //$("#"+newId).select2();
445
- $("#"+newId).css("display", "block");
446
- }
447
- jQuery("#feed-spinner").css("display", "none");
448
- }
449
- );
450
- }
451
- }
452
 
453
- function removeChildCategory(currentId){
454
- var currentSplit = currentId.split("_");
455
- var childEleId;
456
- for (i = ++currentSplit[1]; i < 6; i++) {
457
- childEleId = currentSplit[0]+"_"+ i;
458
- console.log($("#"+childEleId));
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
459
 
460
- $("#"+childEleId).empty();
461
- $("#"+childEleId).removeClass("form-control");
462
- $("#"+childEleId).css("display", "none");
463
- if ($("#"+childEleId).data("select2")) {
464
- $("#"+childEleId).off("select2:select");
465
- $("#"+childEleId).select2("destroy");
466
- $("#"+childEleId).removeClass("select2");
467
- }
468
- }
 
 
 
 
 
469
  }
 
470
 
471
- function selectChildCategoryValue(wooCategoryId){
472
- var childCatvala;
473
- for (i = 0; i < 6; i++) {
474
- childCatvala = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").attr("id");
475
-
476
- if ($("#catmap-"+wooCategoryId+"_"+0).find(":selected").attr("id") <= 0) {
477
- $("#category-"+wooCategoryId).val(0);
478
- } else {
479
- if (childCatvala > 0) {
480
- $("#category-"+wooCategoryId).val(childCatvala);
481
- }
482
  }
483
  }
484
  }
485
-
486
- </script>';
487
- }
488
- public function woo_country() {
489
- // The country/state
490
- $store_raw_country = get_option('woocommerce_default_country');
491
- // Split the country/state
492
- $split_country = explode(":", $store_raw_country);
493
- return $split_country;
494
- }
495
  }
496
-
497
- ?>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
  <?php
 
2
  class GAAConfiguration {
3
+ protected $merchantId;
4
+ protected $TVC_Admin_Helper;
5
+ protected $currentCustomerId;
6
+ protected $subscriptionId;
7
+ protected $country;
8
+ public function __construct() {
9
+ ini_set('max_execution_time', '0');
10
+ ini_set('memory_limit','-1');
11
+ $this->includes();
12
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
13
+ $this->merchantId = $this->TVC_Admin_Helper->get_merchantId();
14
+ $this->accountId = $this->TVC_Admin_Helper->get_main_merchantId();
15
+ $this->currentCustomerId = $this->TVC_Admin_Helper->get_currentCustomerId();
16
+ $this->subscriptionId = $this->TVC_Admin_Helper->get_subscriptionId();
17
+ $this->country = $this->TVC_Admin_Helper->get_woo_country();
18
+ $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
19
+ $this->url = $this->TVC_Admin_Helper->get_connect_url();
20
+ $this->html_run();
21
+ }
22
+ public function includes() {
23
+ if (!class_exists('Tatvic_Category_Wrapper')) {
24
+ require_once(__DIR__ . '/tatvic-category-wrapper.php');
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
25
  }
26
+ }
27
+
28
+ public function html_run() {
29
+ $this->TVC_Admin_Helper->add_spinner_html();
30
+ $this->create_form();
31
+ }
32
+
33
+ public function wooCommerceAttributes() {
34
+ $queries = new TVC_Queries();
35
+ global $wpdb;
36
+ $tve_table_prefix = $wpdb->prefix;
37
+ $column1 = json_decode(json_encode($queries->getTableColumns($tve_table_prefix.'posts')), true);
38
+ $column2 = json_decode(json_encode($queries->getTableData($tve_table_prefix.'postmeta', ['meta_key'])), true);
39
+ return array_merge($column1, $column2);
40
+ }
41
+
42
+ public function create_form() {
43
+ if(isset($_GET['welcome_msg']) && $_GET['welcome_msg'] == true){
44
+ $class = 'notice notice-success';
45
+ $message = esc_html__('Get your WooCommerce products in front of the millions of shoppers across Google by setting up your Google Merchant Center account from below.');
46
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
47
  }
48
+ $category_wrapper_obj = new Tatvic_Category_Wrapper();
49
+ $category_wrapper = $category_wrapper_obj->category_table_content('mapping');
50
+ $googleDetail = [];
51
+ $google_detail = $this->TVC_Admin_Helper->get_ee_options_data();
52
+ if(isset($google_detail['setting'])){
53
+ if ($google_detail['setting']) {
54
+ $googleDetail = $google_detail['setting'];
55
+ }
56
+ }?>
57
+ <div class="container-fluid">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
58
  <div class="row">
59
  <div class= "col col-12">
60
  <div class="card mw-100" style="padding:0;">
61
  <div class="card-body">
62
+ <div class="tab-pane show active" id="googleShoppingFeed">
63
+ <div class="row">
64
+ <div class="col-md-6 col-lg-8 border-right">
65
+ <div class="configuration-section" id="config-pt1">
66
+ <?php echo get_google_shopping_tabs_html($this->site_url,(isset($googleDetail->google_merchant_center_id))?$googleDetail->google_merchant_center_id:""); ?>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
67
  </div>
68
+ <div class="mt-3" id="config-pt2">
69
+ <div class="google-account-analytics" id="gaa-config">
70
+ <div class="licence">
71
+ <p>You are using our free plugin, no licence needed ! Happy analyzing..!! :)</p>
72
+ <p>To unlock more features of google products, consider our <a href="https://codecanyon.net/item/actionable-google-analytics-for-woocommerce/9899552?utm_source=TatvicEE&utm_medium=DashboardBuyBottom&utm_campaign=WPlisting" target="_blank" class="text-underline">pro version.</a></p>
73
+ </div>
74
+ <div class="row mb-3">
75
+ <div class="col-6 col-md-6">
76
+ <h2 class="ga-title">Connected Google Merchant center account:</h2>
77
+ </div>
78
+ <div class="col-6 col-md-3">
79
+ <p class="ga-text"><?php echo (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '' ? $googleDetail->google_merchant_center_id : 'N/A'); ?></p>
80
+ </div>
81
+ <div class="col-6 col-md-3">
82
+ <?php
83
+ if(isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != ''){
84
+ echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
85
+ }else{
86
+ echo '<p class="ga-text text-right">Click here to <a href="#" class="text-underline" data-toggle="modal" data-target="#tvc_google_connect">connect</a></p>';
87
+ }?>
88
+ </div>
89
+ </div>
90
+ <div class="row mb-3">
91
+ <div class="col-6 col-md-6">
92
+ <h2 class="ga-title">Linked Google Ads Account:</h2>
93
+ </div>
94
+ <div class="col-6 col-md-3">
95
+ <p class="ga-text"><?php echo (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '' ? $googleDetail->google_ads_id : 'N/A');?></p>
96
+ </div>
97
+ <div class="col-6 col-md-3">
98
+ <?php
99
+ if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != '') {
100
+ echo '<p class="ga-text text-right">Click here to <a target="_blank" href="' . $this->url . '" class="text-underline">update</a></p>';
101
+ } else {
102
+ echo '<p class="ga-text text-right">Click here to <a href="#" data-toggle="modal" data-target="#tvc_google_connect" class="text-underline">connect</a></p>';
103
+ } ?>
104
+ </div>
105
+ </div>
106
+ <?php
107
+ if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {?>
108
+ <div class="row mb-3">
109
+ <div class="col-6 col-md-6">
110
+ <h2 class="ga-title">Sync Products:</h2>
111
+ </div>
112
+ <div class="col-6 col-md-6">
113
+ <button type="button" class="btn btn-primary btn-success" data-toggle="modal" data-target="#syncProduct">Sync New Products</button>
114
+ </div>
115
+ </div>
116
+ <div class="row mb-3">
117
+ <div class="col-6 col-md-6">
118
+ <h2 class="ga-title">Smart Shopping Campaigns:</h2>
119
+ </div>
120
+ <div class="col-6 col-md-6">
121
+ <a href="admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=add_campaign_page" class="btn btn-primary btn-success">Create Smart Shopping Campaign</a>
122
+ </div>
123
+ </div>
124
+ <?php }else{ ?>
125
+ <div class="row mb-3">
126
+ <div class="col-6 col-md-6">
127
+ <h2 class="ga-title">Sync Products:</h2>
128
+ </div>
129
+ <div class="col-6 col-md-6">
130
+ <button type="button" class="btn btn-primary btn-success" data-toggle="modal" data-target="#tvc_google_connect">Sync New Products</button>
131
+ </div>
132
+ </div>
133
+ <div class="row mb-3">
134
+ <div class="col-6 col-md-6">
135
+ <h2 class="ga-title">Smart Shopping Campaigns:</h2>
136
+ </div>
137
+ <div class="col-6 col-md-6">
138
+ <a href="#" class="btn btn-primary btn-success" data-toggle="modal" data-target="#tvc_google_connect">Create Smart Shopping Campaign</a>
139
+ </div>
140
+ </div>
141
+ <?php } ?>
142
+ </div>
143
  </div>
144
+ </div>
145
+ <div class="col-md-6 col-lg-4">
146
+ <div class="right-content"> <?php echo get_tvc_help_html(); ?></div>
147
+ </div>
148
  </div>
149
+ </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
150
  </div>
151
  </div>
152
  </div>
153
  </div>
154
  </div>
155
  <div class="modal fade popup-modal create-campaign" id="syncProduct" data-backdrop="false">
156
+ <div class="modal-dialog modal-dialog-centered">
157
+ <div class="modal-content">
158
+ <div class="modal-body mt-3">
159
+ <h5>Map your product attributes <span style="float:right"><button type="button" class="close" data-dismiss="modal"> &times; </button> </span></h5>
160
+ <p>Google Merchant Center uses attributes to format your product information for Shopping Ads. Map your product attributes to the Merchant Center product attributes below. You can also edit each product’s individual attributes after you sync your products. Not all fields below are marked required, however based on your shop\'s categories and your country you might map a few optional attributes as well. See the full guide <a target="_blank" href="https://support.google.com/merchants/answer/7052112">here</a>.
161
+ </p>
162
+ <div class="wizard-section campaign-wizard">
163
+ <div class="wizard-content">
164
+ <input type="hidden" name="merchant_id" id="merchant_id" value="<?php echo $this->merchantId; ?>">
165
+ <form class="tab-wizard wizard- wizard" id="productSync" method="POST">
166
+ <h5><span class="wiz-title">Category Mapping</span></h5>
167
+ <section>
168
+ <div class="card-wrapper">
169
+ <div class="row">
170
+ <div class="col-6">
171
+ <h6 class="heading-tbl">WooCommerce Category</h6>
172
+ </div>
173
+ <div class="col-6">
174
+ <h6 class="heading-tbl">Google Merchant Center Category</h6>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
175
  </div>
176
+ </div><?php echo $category_wrapper; ?>
177
  </div>
178
+ </section>
179
+ <!-- Step 2 -->
180
+ <h5><span class="wiz-title">Product Attribution Mapping</span></h5>
181
+ <section>
182
+ <div class="card-wrapper">
183
+ <div class="row">
184
+ <div class="col-6">
185
+ <h6 class="heading-tbl">Google Merchant center product attributes</h6>
186
+ </div>
187
+ <div class="col-6">
188
+ <h6 class="heading-tbl">WooCommerce product attributes</h6>
189
+ </div>
190
+ </div>
191
+ <?php
192
+ foreach ($this->TVC_Admin_Helper->get_gmcAttributes() as $key => $attribute) {
193
+ echo '<div class="row">
194
+ <div class="col-6 align-self-center">
195
+ <div class="form-group">
196
+ <span class="td-head">' . $attribute["field"] . " " . (isset($attribute["required"]) && $attribute["required"] == 1 ? '<span style="color: red;"> *</span>' : "") . '</span>
197
+ <small class="form-label-control">' . (isset($attribute["desc"])? $attribute["desc"]:"") . '</small>
198
+ </div>
199
+ </div>
200
+ <div class="col-6 align-self-center">
201
+ <div class="form-group">';
202
+ if($attribute["field"]=='link'){
203
+ echo "product link";
204
+ }else if($attribute["field"]=='channel'){
205
+ echo "online";
206
+ }else{
207
+ echo '<select class="form-control select2 ' . (isset($attribute["required"]) && $attribute["required"] == 1 ? "field-required" : "") . '" name="' . $attribute["field"] . '" >
208
+ <option value="0">Please Select Attribute</option>';
209
+ foreach ($this->wooCommerceAttributes() as $wKey => $wAttribute) {
210
+ echo '<option value="' . $wAttribute["field"] . '"';
211
+ echo (isset($attribute['required']) && $attribute['required'] == 1 && $attribute['wAttribute'] == $wAttribute["field"]) ? "selected" : "";
212
+ echo '>' . $wAttribute["field"] . '</option>';
213
+ }
214
+ echo '</select>';
215
+ }
216
+ echo '</div>
217
+ </div>
218
+ </div>';
219
+ }?>
220
+ </div>
221
+ </section>
222
+ </form>
223
+ </div>
224
  </div>
225
+ </div>
226
  </div>
227
+ </div>
228
+ </div><?php echo get_connect_google_popup_html()?>
229
  <script type="text/javascript">
230
+ $(document).ready(function() {
231
+ $(".select2").select2();
232
+ });
233
+ $(".tab-wizard").steps({
234
+ headerTag: "h5",
235
+ bodyTag: "section",
236
+ transitionEffect: "fade",
237
+ titleTemplate: '<span class="step">#index#</span> #title#',
238
+ labels: {
239
+ finish: "Sync Products",
240
+ next: "Next",
241
+ previous: "Previous",
242
+ },
243
+ onStepChanged: function(event, currentIndex, priorIndex) {
244
+ $('.steps .current').prevAll().addClass('disabled');
245
+ },
246
+ onFinished: function(event, currentIndex) {
247
+ var valid=true;
248
+ jQuery(".field-required").each(function() {
249
+ if($(this).val()==0 && valid){
250
+ valid=false;
251
+ }
 
 
 
 
 
 
 
 
 
 
 
252
  });
253
+ if(!valid){
254
+ alert("Please select all required fields");
255
+ }else{
256
+ submitProductSyncUp();
257
+ }//check for required fields end
258
+ }
259
+ });
260
+
261
+ function submitProductSyncUp() {
262
+ var merchantId = '<?php echo $this->merchantId; ?>';
263
+ var accountId = '<?php echo $this->accountId; ?>';
264
+ var customerId = '<?php echo $this->currentCustomerId; ?>';
265
+ var subscriptionId = '<?php echo $this->subscriptionId; ?>';
266
+ var platformCustomerId = jQuery("#platform_customer_id").val();
267
+ var formData = jQuery("#productSync").serialize();
268
+ //console.log(formData);
269
+ jQuery("#feed-spinner").css("display", "block");
270
+ jQuery.post(
271
+ myAjaxNonces.ajaxurl,
272
+ {
273
+ action: "tvcajax-product-syncup",
274
+ merchantId: merchantId,
275
+ customerId: customerId,
276
+ accountId: accountId,
277
+ subscriptionId: subscriptionId,
278
+ platformCustomerId: platformCustomerId,
279
+ data: formData,
280
+ productSyncupNonce: myAjaxNonces.productSyncupNonce
281
+ },
282
+ function( response ) {
283
+ jQuery("#feed-spinner").css("display", "none");
284
+ console.log(response);
285
+ var rsp = JSON.parse(response)
286
+ if (rsp.status == "success") {
287
+ $('#syncProduct').modal('hide');
288
+ var message = "Your product are now being synced in your merchant center account. It takes up to 30 minutes to reflect the product data in merchant center. As soon as they are updated, they will be shown in the \"Product Sync\" dashboard.";
289
+ if (rsp.skipProducts > 0) {
290
+ message = message + "\n Because of pricing issues, " + rsp.skipProducts + " products did not sync.";
291
+ }
292
+ alert(message);
293
+ window.location.replace("<?php echo $this->site_url.'sync_product_page'; ?>");
294
+ } else {
295
+ //var message = "Products sync face some unprocessable entity";
296
+ var message = rsp.message;
297
+ alert(message);
298
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
299
  }
300
+ );
301
+ }
302
 
303
+ $(document).on("show.bs.modal", "#syncProduct", function (e) {
304
+ jQuery("#feed-spinner").css("display", "block");
305
+ selectCategory();
306
+ $("select[id^=catmap]").each(function(){
307
+ removeChildCategory($(this).attr("id"))
308
+ });
309
+ });
310
+
311
+ function selectCategory() {
312
+ var country_id = "<?php echo $this->country; ?>";
313
+ var customer_id = '<?php echo $this->currentCustomerId?>';
314
+ var parent = "";
315
+ jQuery.post(
316
+ myAjaxNonces.ajaxurl,
317
+ {
318
+ action: "tvcajax-gmc-category-lists",
319
+ countryCode: country_id,
320
+ customerId: customer_id,
321
+ parent: parent,
322
+ gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce
323
+ },
324
+ function( response ) {
325
+ var categories = JSON.parse(response);
326
+ var obj;
327
+ $("select[id^=catmap]").each(function(){
328
+ obj = $("#catmap-"+$(this).attr("catid")+"_0");
329
+ obj.empty();
330
+ obj.append("<option id='0' value='0' resourcename='0'>Select a category</option>");
331
+ $.each(categories, function (i, value) {
332
+ obj.append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
333
+ });
334
+ });
335
+ jQuery("#feed-spinner").css("display", "none");
336
+ });
337
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
338
 
339
+ function selectSubCategory(thisObj) {
340
+ var selectId;
341
+ var wooCategoryId;
342
+ var GmcCategoryId;
343
+ var GmcParent;
344
+ selectId = thisObj.id;
345
+ wooCategoryId = $(thisObj).attr("catid");
346
+ GmcCategoryId = $(thisObj).find(":selected").val();
347
+ GmcParent = $(thisObj).find(":selected").attr("resourcename");
348
+ //$("#"+selectId).select2().find(":selected").val();
349
+ // $("#"+selectId).select2().find(":selected").data("id");
350
+ //console.log(selectId+"--"+wooCategoryId+"--"+GmcCategoryId+"--"+GmcParent);
351
+
352
+ jQuery("#feed-spinner").css("display", "block");
353
+ removeChildCategory(selectId);
354
+ selectChildCategoryValue(wooCategoryId);
355
+ if (GmcParent != undefined) {
356
+ var country_id = "<?php echo $this->country; ?>";
357
+ var customer_id = '<?php echo $this->currentCustomerId?>';
358
+ jQuery.post(
359
+ myAjaxNonces.ajaxurl,
360
+ {
361
+ action: "tvcajax-gmc-category-lists",
362
+ countryCode: country_id,
363
+ customerId: customer_id,
364
+ parent: GmcParent,
365
+ gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce
366
+ },
367
+ function( response ) {
368
+ var categories = JSON.parse(response);
369
+ var newId;
370
+ var slitedId = selectId.split("_");
371
+ newId = slitedId[0]+"_"+ ++slitedId[1];
372
+ if(categories.length === 0){
373
+ }else{
374
+ //console.log(newId);
375
+ $("#"+newId).empty();
376
+ $("#"+newId).append("<option id='0' value='0' resourcename='0'>Select a sub-category</option>");
377
+ $.each(categories, function (i, value) {
378
+ $("#"+newId).append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
379
+ });
380
+ $("#"+newId).addClass("form-control");
381
+ //$("#"+newId).select2();
382
+ $("#"+newId).css("display", "block");
383
+ }
384
+ jQuery("#feed-spinner").css("display", "none");
385
+ }
386
+ );
387
+ }
388
+ }
389
 
390
+ function removeChildCategory(currentId){
391
+ var currentSplit = currentId.split("_");
392
+ var childEleId;
393
+ for (i = ++currentSplit[1]; i < 6; i++) {
394
+ childEleId = currentSplit[0]+"_"+ i;
395
+ //console.log($("#"+childEleId));
396
+ $("#"+childEleId).empty();
397
+ $("#"+childEleId).removeClass("form-control");
398
+ $("#"+childEleId).css("display", "none");
399
+ if ($("#"+childEleId).data("select2")) {
400
+ $("#"+childEleId).off("select2:select");
401
+ $("#"+childEleId).select2("destroy");
402
+ $("#"+childEleId).removeClass("select2");
403
+ }
404
  }
405
+ }
406
 
407
+ function selectChildCategoryValue(wooCategoryId){
408
+ var childCatvala;
409
+ for(i = 0; i < 6; i++){
410
+ childCatvala = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").attr("id");
411
+ childCatname = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").text();
412
+ if($("#catmap-"+wooCategoryId+"_"+0).find(":selected").attr("id") <= 0){
413
+ $("#category-"+wooCategoryId).val(0);
414
+ }else{
415
+ if(childCatvala > 0){
416
+ $("#category-"+wooCategoryId).val(childCatvala);
417
+ $("#category-name-"+wooCategoryId).val(childCatname);
418
  }
419
  }
420
  }
 
 
 
 
 
 
 
 
 
 
421
  }
422
+ $( ".wizard-content" ).on( "click", ".change_prodct_feed_cat", function() {
423
+ // console.log( $( this ).attr("data-id") );
424
+ $(this).hide();
425
+ var feed_select_cat_id = $( this ).attr("data-id");
426
+ var woo_cat_id = $( this ).attr("data-cat-id");
427
+
428
+ jQuery("#category-"+woo_cat_id).val("0");
429
+ jQuery("#category-name-"+woo_cat_id).val("");
430
+ jQuery("#label-"+feed_select_cat_id).hide();
431
+ jQuery("#"+feed_select_cat_id).slideDown();
432
+ });
433
+ function changeProdctFeedCat(feed_select_cat_id){
434
+ jQuery("#label-"+feed_select_cat_id).hide();
435
+ jQuery("#"+feed_select_cat_id).slideDown();
436
+ }
437
+ </script>
438
+ <?php
439
+ } //create_form
440
+ } ?>
includes/setup/google-shopping-feed-shopping-campaigns.php CHANGED
@@ -10,7 +10,7 @@ class CampaignsConfiguration
10
  {
11
  $this->includes();
12
  $this->returnUrl = $_SERVER['REQUEST_URI'];
13
- $this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
14
 
15
  $this->customApiObj = new CustomApi();
16
  //$this->customApiObj->getGoogleAnalyticDetail();
10
  {
11
  $this->includes();
12
  $this->returnUrl = $_SERVER['REQUEST_URI'];
13
+ $this->url = "https://".TVC_AUTH_CONNECT_URL."/config/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
14
 
15
  $this->customApiObj = new CustomApi();
16
  //$this->customApiObj->getGoogleAnalyticDetail();
includes/setup/google-shopping-feed-sync-product.php CHANGED
@@ -1,533 +1,502 @@
1
  <?php
2
-
3
  class SyncProductConfiguration
4
  {
5
- public $merchantId;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
6
 
7
- public $customApiObj;
8
- protected $currentCustomerId;
9
- protected $subscriptionId;
10
- public function __construct()
11
- {
12
- $this->includes();
13
- $this->returnUrl = $_SERVER['REQUEST_URI'];
14
- $this->url = "https://estorenew.tatvic.com/config/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
15
 
16
- $this->customApiObj = new CustomApi();
17
- $this->customApiObj->getGoogleAnalyticDetail();
18
- $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant']:"";
19
- $this->accountId = (isset($GLOBALS['tatvicData']['tvc_main_merchant_id'])) ? $GLOBALS['tatvicData']['tvc_main_merchant_id'] : "";
20
- $this->currentCustomerId = (isset($GLOBALS['tatvicData']['tvc_customer'])) ? $GLOBALS['tatvicData']['tvc_customer'] : "";
21
- $this->subscriptionId = (isset($GLOBALS['tatvicData']['tvc_subscription'])) ? $GLOBALS['tatvicData']['tvc_subscription'] : "";
22
-
23
- $this->country = (isset($GLOBALS['tatvicData']['tvc_country'])) ? $GLOBALS['tatvicData']['tvc_country'] : "";
24
- $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
25
- //$actual_link = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://$_SERVER[HTTP_HOST]";
26
- //$store_currency = $this->get_store_currency();
27
- $this->html_run();
28
- }
29
 
30
- public function includes()
31
- {
32
- if (!class_exists('CustomApi.php')) {
33
- require_once(__DIR__ . '/CustomApi.php');
34
- }
35
- if (!class_exists('Tatvic_Category_Wrapper')) {
36
- require_once(__DIR__ . '/tatvic-category-wrapper.php');
37
- }
38
- }
39
 
40
- public function html_run()
41
- {
42
- $this->spinner();
43
- $this->create_form();
 
 
 
 
 
 
 
 
 
 
 
44
  }
45
-
46
- public function spinner() {
47
- $spinner_gif = ENHANCAD_PLUGIN_URL . '/images/ajax-loader.gif';
48
- echo '<div class="feed-spinner" id="feed-spinner" style="display:none;">
49
- <img id="img-spinner" src="' . $spinner_gif . '" alt="Loading" />
50
- </div>';
51
  }
52
- public function gmcAttributes() {
53
- $path = TVC_CHANNEL_DATA_DIR . '/google/gmc_attrbutes.json';
54
- $str = file_get_contents($path);
55
- $attributes = $str ? json_decode($str, true) : [];
56
- return $attributes;
57
  }
58
- public function wooCommerceAttributes() {
59
- $queries = new TVC_Queries();
60
- global $wpdb;
61
- $tve_table_prefix = $wpdb->prefix;
62
- $column1 = json_decode(json_encode($queries->getTableColumns($tve_table_prefix.'posts')), true);
63
- $column2 = json_decode(json_encode($queries->getTableData($tve_table_prefix.'postmeta', ['meta_key'])), true);
64
- return array_merge($column1, $column2);
65
  }
66
-
67
- public function create_form()
68
- {
69
- $category_wrapper_obj = new Tatvic_Category_Wrapper();
70
- $category_wrapper = $category_wrapper_obj->category_table_content('mapping');
71
-
72
- $syncProduct_list_res = $this->customApiObj->getSyncProductList(['merchant_id' => $this->merchantId]);
73
- if (isset($syncProduct_list_res->data) && isset($syncProduct_list_res->status) && $syncProduct_list_res->status == 200) {
74
- if (isset($syncProduct_list_res->data->products)) {
75
- $syncProductList = $syncProduct_list_res->data->products;
76
- }
77
- if (isset($syncProduct_list_res->data->statistics)) {
78
- $syncProductStat = $syncProduct_list_res->data->statistics;
79
- }
80
- } else {
81
- $syncProductList = [];
82
- $syncProductStat = [];
83
- $class = 'notice notice-error';
84
- $message = esc_html__('Not any Product found on this GMC account.');
85
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
86
- }
87
- $google_detail = $this->customApiObj->getGoogleAnalyticDetail();
88
- if ($google_detail->data['status'] == 200) {
89
- if (isset($google_detail->data['data'])) {
90
- $googleDetail = $google_detail->data['data'];
91
- }
92
- } else {
93
- $googleDetail = [];
94
- $class = 'notice notice-error';
95
- $message = esc_html__('Google analytic detail is empty.');
96
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
97
- }
98
-
99
- echo '<div class="container-fluid">
100
  <div class="row">
101
  <div class= "col col-12">
102
  <div class="card mw-100" style="padding:0;">
103
  <div class="card-body">
104
- <div class="tab-pane show active" id="googleShoppingFeed">
105
- <div class="row">
106
- <div class="col-md-6 col-lg-8 border-right">
107
- <div class="configuration-section" id="config-pt1">
108
- '.get_google_shopping_tabs_html($this->site_url,$googleDetail->google_merchant_center_id).'
109
- </div>
110
- <div class="mt-3" id="config-pt2">
111
- <div class="sync-new-product" id="sync-product">
112
- <div class="row">
113
- <div class="col-12">
114
- <div class="d-flex justify-content-between ">
115
- <p class="mb-0 align-self-center">Products in your Merchant Center account</p>
116
- <button class="btn btn-primary btn-success align-self-center" data-toggle="modal" data-target="#syncProduct">Sync New Products</button>
117
- <a href="admin.php?page=enhanced-ecommerce-google-analytics-admin-display&amp;tab=add_campaign_page" class="btn btn-primary btn-success">Create Smart Shopping Campaign</a>
118
- </div>
119
- </div>
120
- </div>
121
- <div class="product-card">
122
- <div class="row">
123
- <div class="col-sm-6 col-lg-3">
124
- <div class="card">
125
- <h3 class="pro-title">Total Products</h3>
126
- <p class="pro-count">';
127
- echo (!empty($syncProductStat)) ? $syncProductStat->total : "0";
128
- echo '</p>
129
- </div>
130
- </div>
131
- <div class="col-sm-6 col-lg-3">
132
- <div class="card pending">
133
- <h3 class="pro-title">Pending Review</h3>
134
- <p class="pro-count">';
135
- echo (!empty($syncProductStat)) ? $syncProductStat->pending : "0";
136
- echo '</p>
137
- </div>
138
- </div>
139
- <div class="col-sm-6 col-lg-3">
140
- <div class="card approved">
141
- <h3 class="pro-title">Approved</h3>
142
- <p class="pro-count">';
143
- echo (!empty($syncProductStat)) ? $syncProductStat->approved : "0";
144
- echo '</p>
145
- </div>
146
- </div>
147
- <div class="col-sm-6 col-lg-3">
148
- <div class="card disapproved">
149
- <h3 class="pro-title">Disapproved</h3>
150
- <p class="pro-count">';
151
- echo (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0";
152
- echo '</p>
153
- </div>
154
- </div>
155
- </div>
156
- </div>
157
- <div class="row">
158
- <div class="col-12">
159
- <div class="account-performance">
160
- <div class="table-section">
161
- <div class="table-responsive">
162
- <table class="table" style="width:100%">
163
- <thead>
164
- <tr>
165
- <th></th>
166
- <th style="vertical-align: top;">Product</th>
167
- <th style="vertical-align: top;">Google status</th>
168
- <th style="vertical-align: top;">Issues</th>
169
- </tr>
170
- </thead>
171
- <tbody>';
172
-
173
- if (isset($syncProductList) && count($syncProductList) > 0) {
174
- foreach ($syncProductList as $skey => $sValue) {
175
- echo '<tr>
176
- <td class="product-image">
177
- <img src="'.$sValue->imageLink.'" alt=""/>
178
- </td>
179
- <td>'.$sValue->name.'</td>
180
- <td>'.$sValue->googleStatus.'</td>
181
- <td>';
182
- if (count($sValue->issues) > 0) {
183
-
184
- $str = '';
185
- foreach ($sValue->issues as $key => $issue) {
186
- if ($key <= 2) {
187
- ($key <= 1) ? $str .= $issue.", <br>" : "";
188
- }
189
- ($key == 3) ? $str .= "..." : "";
190
-
191
- }
192
- echo $str;
193
-
194
- } else {
195
- echo "---";
196
- }
197
- echo '</td>
198
- </tr>';
199
- }
200
- }else{
201
- echo '<tr>
202
- <td colspan="4">
203
- Record not found
204
- </td>
205
- </tr>';
206
- }
207
- echo '</tbody>
208
- </table>
209
- </div>
210
- </div>
211
- </div>
212
- </div>
213
- </div>
214
- </div>
215
- </div>
216
  </div>
217
-
218
- <div class="col-md-6 col-lg-4">
219
- <div class="right-content">'.get_tvc_help_html().'
220
- </div>
221
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
222
  </div>
223
- </div>
 
 
 
 
 
 
 
 
224
  </div>
225
  </div>
226
  </div>
227
  </div>
228
  </div>
229
- ';
230
- echo '<div class="modal fade popup-modal create-campaign" id="syncProduct" data-backdrop="false">
231
- <div class="modal-dialog modal-dialog-centered">
232
- <div class="modal-content">
233
- <div class="modal-body mt-3">
234
- <h5>Map your product attributes <span style="float:right"><button type="button" class="close" data-dismiss="modal"> &times; </button> </span></h5>
235
- <p>Google Merchant Center uses attributes to format your product information for Shopping Ads. Map your product attributes to the Merchant Center product attributes below. You can also edit each product’s individual attributes after you sync your products. Not all fields below are marked required, however based on your shop\'s categories and your country you might map a few optional attributes as well. See the full guide <a target="_blank" href="https://support.google.com/merchants/answer/7052112">here</a>.
236
- </p>
237
- <div class="wizard-section campaign-wizard">
238
- <div class="wizard-content">
239
- <input type="hidden" name="merchant_id" id="merchant_id" value="' . $this->merchantId . '">
240
- <input type="hidden" name="platform_customer_id" id="platform_customer_id" value="111">
241
- <form class="tab-wizard wizard- wizard" id="productSync" method="POST">
242
- <h5>
243
- <span class="wiz-title">Category Mapping</span>
244
- </h5>
245
- <section>
246
- <div class="card-wrapper">
247
- <div class="row">
248
- <div class="col-6">
249
- <h6 class="heading-tbl">WooCommerce Category</h6>
250
- </div>
251
- <div class="col-6">
252
- <h6 class="heading-tbl">Google Merchant Center Category</h6>
253
- </div>
254
- </div>' . $category_wrapper . '
255
- </div>
256
- </section>
257
- <!-- Step 2 -->
258
- <h5>
259
- <span class="wiz-title">Product Attribution Mapping</span>
260
- </h5>
261
- <section>
262
- <div class="card-wrapper">
263
- <div class="row">
264
- <div class="col-6">
265
- <h6 class="heading-tbl">Google Merchant center product attributes</h6>
266
- </div>
267
- <div class="col-6">
268
- <h6 class="heading-tbl">WooCommerce product attributes</h6>
269
- </div>
270
- </div>';
271
-
272
- foreach ($this->gmcAttributes() as $key => $attribute) {
273
- echo '<div class="row">
274
- <div class="col-6 align-self-center">
275
- <div class="form-group">
276
- <span class="td-head">' . $attribute["field"] . " " . (isset($attribute["required"]) && $attribute["required"] == 1 ? '<span style="color: red;"> *</span>' : "") . '</span>
277
- <small class="form-label-control">' .(isset($attribute["desc"])? $attribute["desc"]:"") . '</small>
278
- </div>
279
- </div>
280
- <div class="col-6 align-self-center">
281
- <div class="form-group">';
282
- if($attribute["field"]=='link'){
283
- echo "product link";
284
- }else if($attribute["field"]=='channel'){
285
- echo "online";
286
- }else{
287
- echo '<select class="form-control select2 ' . (isset($attribute["required"]) && $attribute["required"] == 1 ? "field-required" : "") . '" name="' . $attribute["field"] . '" >
288
- <option value="0">Please Select Attribute</option>';
289
-
290
- foreach ($this->wooCommerceAttributes() as $wKey => $wAttribute) {
291
- echo '<option value="' . $wAttribute["field"] . '"';
292
- echo (isset($attribute['required']) && $attribute['required'] == 1 && $attribute['wAttribute'] == $wAttribute["field"]) ? "selected" : "";
293
- echo '>' . $wAttribute["field"] . '</option>';
294
- }
295
- echo '</select>';
296
- }
297
- echo '</div>
298
- </div>
299
- </div>';
300
- }
301
- echo '</div>
302
- </section>
303
- </form>
304
  </div>
 
305
  </div>
306
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
307
  </div>
 
308
  </div>
 
309
  </div>
310
-
311
  <script type="text/javascript">
312
- $(document).ready(function() {
313
- $(".select2").select2();
314
- });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
315
 
316
- $(".tab-wizard").steps({
317
- headerTag: "h5",
318
- bodyTag: "section",
319
- transitionEffect: "fade",
320
- titleTemplate: \'<span class="step">#index#</span> #title#\',
321
- labels: {
322
- finish: "Finish",
323
- next: "Next",
324
- previous: "Previous",
325
- },
326
- onStepChanged: function(event, currentIndex, priorIndex) {
327
- $(\'.steps .current\').prevAll().addClass(\'disabled\');
328
- },
329
- onFinished: function(event, currentIndex) {
330
- //check for required fields
331
- var valid=true;
332
- jQuery(".field-required").each(function() {
333
- if($(this).val()==0 && valid){
334
- valid=false;
335
- }
336
- });
337
- if(!valid){
338
- alert("Please select all required fields");
339
- }else{
340
- submitProductSyncUp();
341
- }
342
- //check for required fields end
343
-
344
- }
345
  });
346
-
347
- function submitProductSyncUp() {
348
- var merchantId = ' . $this->merchantId . ';
349
- var accountId = ' . $this->accountId . ';
350
- var customerId = ' . $this->currentCustomerId . ';
351
- var subscriptionId = ' . $this->subscriptionId . ';
352
- var platformCustomerId = jQuery("#platform_customer_id").val();
353
-
354
- var formData = jQuery("#productSync").serialize();
355
- console.log(formData);
356
- jQuery("#feed-spinner").css("display", "block");
357
-
358
- jQuery.post(
359
- myAjaxNonces.ajaxurl,
360
- {
361
- action: "tvcajax-product-syncup",
362
- merchantId: merchantId,
363
- customerId: customerId,
364
- accountId: accountId,
365
- subscriptionId: subscriptionId,
366
- platformCustomerId: platformCustomerId,
367
- data: formData,
368
- productSyncupNonce: myAjaxNonces.productSyncupNonce,
369
 
370
- },
371
- function( response ) {
372
- jQuery("#feed-spinner").css("display", "none");
373
- console.log(response);
374
- var rsp = JSON.parse(response)
375
- if (rsp.status == "success") {
376
- $(\'#syncProduct\').modal(\'hide\');
377
- var message = "Your product are now being synced in your merchant center account. It takes up to 30 minutes to reflect the product data in merchant center. As soon as they are updated, they will be shown in the \"Product Sync\" dashboard.";
378
- alert(message);
379
- window.location.replace("'.$this->site_url.'sync_product_page");
380
- } else {
381
- //var message = "Products sync face some unprocessable entity";
382
- var message = rsp.message;
383
- alert(message);
384
- }
385
- }
386
- );
387
-
388
- }
389
-
390
- $(document).on("show.bs.modal", "#syncProduct", function (e) {
391
- console.log("calll");
392
- jQuery("#feed-spinner").css("display", "block");
393
- selectCategory();
394
- $("select[id^=catmap]").each(function(){
395
- removeChildCategory($(this).attr("id"))
396
- });
397
- });
398
-
399
- function selectCategory() {
400
- var country_id = "' . $this->country . '";
401
- var customer_id = ' . $this->currentCustomerId . ';
402
- var parent = "";
403
- jQuery.post(
404
- myAjaxNonces.ajaxurl,
405
- {
406
- action: "tvcajax-gmc-category-lists",
407
- countryCode: country_id,
408
- customerId: customer_id,
409
- parent: parent,
410
- gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce,
411
-
412
- },
413
- function( response ) {
414
- var categories = JSON.parse(response);
415
- var obj;
416
- $("select[id^=catmap]").each(function(){
417
- obj = $("#catmap-"+$(this).attr("catid")+"_0");
418
- obj.empty();
419
- obj.append("<option id=' . "0" . ' value=' . "0" . ' resourcename=' . "0" . '>Select a category</option>");
420
- $.each(categories, function (i, value) {
421
- obj.append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
422
-
423
- });
424
- });
425
- jQuery("#feed-spinner").css("display", "none");
426
- }
427
- );
428
- }
429
- $( ".wizard-content" ).on( "click", ".change_prodct_feed_cat", function() {
430
- console.log( $( this ).attr("data-id") );
431
- $(this).hide();
432
- var feed_select_cat_id = $( this ).attr("data-id");
433
- jQuery("#label-"+feed_select_cat_id).hide();
434
- jQuery("#"+feed_select_cat_id).slideDown();
435
- });
436
- function changeProdctFeedCat(feed_select_cat_id){
437
- jQuery("#label-"+feed_select_cat_id).hide();
438
- jQuery("#"+feed_select_cat_id).slideDown();
439
  }
440
- function selectSubCategory(thisObj) {
441
- var selectId;
442
- var wooCategoryId;
443
- var GmcCategoryId;
444
- var GmcParent;
445
 
446
- selectId = thisObj.id;
447
- wooCategoryId = $(thisObj).attr("catid");
448
- GmcCategoryId = $(thisObj).find(":selected").val();
449
- GmcParent = $(thisObj).find(":selected").attr("resourcename");
 
 
 
450
 
451
- //$("#"+selectId).select2().find(":selected").val();
452
- // $("#"+selectId).select2().find(":selected").data("id");
453
- console.log(selectId+"--"+wooCategoryId+"--"+GmcCategoryId+"--"+GmcParent);
454
-
455
- jQuery("#feed-spinner").css("display", "block");
456
- removeChildCategory(selectId);
457
- selectChildCategoryValue(wooCategoryId)
458
- if (GmcParent != undefined) {
459
- var country_id = "' . $this->country . '";
460
- var customer_id = ' . $this->currentCustomerId . ';
461
- jQuery.post(
462
- myAjaxNonces.ajaxurl,
463
- {
464
- action: "tvcajax-gmc-category-lists",
465
- countryCode: country_id,
466
- customerId: customer_id,
467
- parent: GmcParent,
468
- gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce,
469
-
470
- },
471
- function( response ) {
472
- var categories = JSON.parse(response);
473
- var newId;
474
- var slitedId = selectId.split("_");
475
- newId = slitedId[0]+"_"+ ++slitedId[1];
476
- if (categories.length === 0) {
477
-
478
- } else {
479
- console.log(newId);
480
- $("#"+newId).empty();
481
- $("#"+newId).append("<option id=' . "0" . ' value=' . "0" . ' resourcename=' . "0" . '>Select a sub-category</option>");
482
- $.each(categories, function (i, value) {
483
- $("#"+newId).append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
484
- });
485
- $("#"+newId).addClass("form-control");
486
- //$("#"+newId).select2();
487
- $("#"+newId).css("display", "block");
488
- }
489
- jQuery("#feed-spinner").css("display", "none");
490
- }
491
- );
492
- }
493
- }
494
 
495
- function removeChildCategory(currentId){
496
- var currentSplit = currentId.split("_");
497
- var childEleId;
498
- for (i = ++currentSplit[1]; i < 6; i++) {
499
- childEleId = currentSplit[0]+"_"+ i;
500
- console.log($("#"+childEleId));
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
501
 
502
- $("#"+childEleId).empty();
503
- $("#"+childEleId).removeClass("form-control");
504
- $("#"+childEleId).css("display", "none");
505
- if ($("#"+childEleId).data("select2")) {
506
- $("#"+childEleId).off("select2:select");
507
- $("#"+childEleId).select2("destroy");
508
- $("#"+childEleId).removeClass("select2");
509
- }
510
- }
 
 
 
 
 
511
  }
 
512
 
513
- function selectChildCategoryValue(wooCategoryId){
514
- var childCatvala;
515
- var childCatname;
516
- for (i = 0; i < 6; i++) {
517
- childCatvala = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").attr("id");
518
- childCatname = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").text();
519
- if ($("#catmap-"+wooCategoryId+"_"+0).find(":selected").attr("id") <= 0) {
520
- $("#category-"+wooCategoryId).val(0);
521
- } else {
522
- if (childCatvala > 0) {
523
- $("#category-"+wooCategoryId).val(childCatvala);
524
- $("#category-name-"+wooCategoryId).val(childCatname);
525
- }
526
  }
527
  }
528
  }
529
-
530
- </script>';
531
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
532
  }
533
  ?>
1
  <?php
 
2
  class SyncProductConfiguration
3
  {
4
+ protected $merchantId;
5
+ protected $TVC_Admin_Helper;
6
+ protected $currentCustomerId;
7
+ protected $subscriptionId;
8
+ protected $country;
9
+ public function __construct(){
10
+ $this->includes();
11
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
12
+ $this->merchantId = $this->TVC_Admin_Helper->get_merchantId();
13
+ $this->accountId = $this->TVC_Admin_Helper->get_main_merchantId();
14
+ $this->currentCustomerId = $this->TVC_Admin_Helper->get_currentCustomerId();
15
+ $this->subscriptionId = $this->TVC_Admin_Helper->get_subscriptionId();
16
+ $this->country = $this->TVC_Admin_Helper->get_woo_country();
17
+ $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
18
+ $this->html_run();
19
+ }
20
 
21
+ public function includes(){
22
+ if (!class_exists('Tatvic_Category_Wrapper')) {
23
+ require_once(__DIR__ . '/tatvic-category-wrapper.php');
24
+ }
25
+ }
 
 
 
26
 
27
+ public function html_run(){
28
+ $this->TVC_Admin_Helper->add_spinner_html();
29
+ $this->create_form();
30
+ }
 
 
 
 
 
 
 
 
 
31
 
32
+ public function wooCommerceAttributes() {
33
+ $queries = new TVC_Queries();
34
+ global $wpdb;
35
+ $tve_table_prefix = $wpdb->prefix;
36
+ $column1 = json_decode(json_encode($queries->getTableColumns($tve_table_prefix.'posts')), true);
37
+ $column2 = json_decode(json_encode($queries->getTableData($tve_table_prefix.'postmeta', ['meta_key'])), true);
38
+ return array_merge($column1, $column2);
39
+ }
 
40
 
41
+ public function create_form(){
42
+ if(isset($_GET['welcome_msg']) && $_GET['welcome_msg'] == true){
43
+ $class = 'notice notice-success';
44
+ $message = esc_html__('Congratulation..! Everthing is now set up. One more step - Sync your WooCommerce products into your Merchant Center and reach out to millions of shopper across Google.');
45
+ printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
46
+ }
47
+ $category_wrapper_obj = new Tatvic_Category_Wrapper();
48
+ $category_wrapper = $category_wrapper_obj->category_table_content('mapping');
49
+ $syncProductStat = [];
50
+ $syncProductList = [];
51
+ $last_api_sync_up ="";
52
+ $google_detail = $this->TVC_Admin_Helper->get_ee_options_data();
53
+ if(isset($google_detail['prod_sync_status'])){
54
+ if ($google_detail['prod_sync_status']) {
55
+ $syncProductStat = $google_detail['prod_sync_status'];
56
  }
57
+ }
58
+ if(isset($google_detail['prod_sync_list'])){
59
+ if ($google_detail['prod_sync_list']) {
60
+ $syncProductList = $google_detail['prod_sync_list'];
 
 
61
  }
62
+ }
63
+ if(isset($google_detail['setting'])){
64
+ if ($google_detail['setting']) {
65
+ $googleDetail = $google_detail['setting'];
 
66
  }
67
+ }
68
+ if(isset($google_detail['sync_time'])){
69
+ if ($google_detail['sync_time']) {
70
+ $last_api_sync_up = date( 'Y-m-d H:i',$google_detail['sync_time']);
 
 
 
71
  }
72
+ }
73
+ ?>
74
+ <div class="container-fluid">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
75
  <div class="row">
76
  <div class= "col col-12">
77
  <div class="card mw-100" style="padding:0;">
78
  <div class="card-body">
79
+ <div class="tab-pane show active" id="googleShoppingFeed">
80
+ <div class="row">
81
+ <div class="col-md-6 col-lg-8 border-right">
82
+ <div class="configuration-section" id="config-pt1">
83
+ <?php if($this->subscriptionId != ""){?>
84
+ <div class="tvc-api-sunc">
85
+ <span>
86
+ <?php if($last_api_sync_up){
87
+ echo "Details last synced at ".$last_api_sync_up;
88
+ }else{
89
+ echo "Refresh sync up";
90
+ }?></span><img id="refresh_api" onclick="call_tvc_api_sync_up();" src="<?php echo ENHANCAD_PLUGIN_URL.'/admin/images/refresh.png'; ?>">
91
+ </div>
92
+ <?php } ?>
93
+ <?php echo get_google_shopping_tabs_html($this->site_url,$googleDetail->google_merchant_center_id); ?>
94
+ </div>
95
+ <div class="mt-3" id="config-pt2">
96
+ <div class="sync-new-product" id="sync-product">
97
+ <div class="row">
98
+ <div class="col-12">
99
+ <div class="d-flex justify-content-between ">
100
+ <p class="mb-0 align-self-center">Products in your Merchant Center account</p>
101
+ <button class="btn btn-primary btn-success align-self-center" data-toggle="modal" data-target="#syncProduct">Sync New Products</button>
102
+ <a href="admin.php?page=enhanced-ecommerce-google-analytics-admin-display&amp;tab=add_campaign_page" class="btn btn-primary btn-success">Create Smart Shopping Campaign</a>
103
+ </div>
104
+ </div>
105
+ </div>
106
+ <div class="product-card">
107
+ <div class="row">
108
+ <div class="col-sm-6 col-lg-3">
109
+ <div class="card">
110
+ <h3 class="pro-title">Total Products</h3>
111
+ <p class="pro-count"><?php
112
+ echo ((!empty($syncProductStat)) ? $syncProductStat->total : "0"); ?></p>
113
+ </div>
114
+ </div>
115
+ <div class="col-sm-6 col-lg-3">
116
+ <div class="card pending">
117
+ <h3 class="pro-title">Pending Review</h3>
118
+ <p class="pro-count">
119
+ <?php echo (!empty($syncProductStat)) ? $syncProductStat->pending : "0";?></p>
120
+ </div>
121
+ </div>
122
+ <div class="col-sm-6 col-lg-3">
123
+ <div class="card approved">
124
+ <h3 class="pro-title">Approved</h3>
125
+ <p class="pro-count"><?php echo (!empty($syncProductStat)) ? $syncProductStat->approved : "0";?></p>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
126
  </div>
127
+ </div>
128
+ <div class="col-sm-6 col-lg-3">
129
+ <div class="card disapproved">
130
+ <h3 class="pro-title">Disapproved</h3>
131
+ <p class="pro-count"><?php
132
+ echo (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0"; ?></p>
133
+ </div>
134
+ </div>
135
+ </div>
136
+ </div>
137
+ <div class="row">
138
+ <div class="col-12">
139
+ <div class="account-performance">
140
+ <div class="table-section">
141
+ <div class="table-responsive">
142
+ <table class="table" style="width:100%">
143
+ <thead>
144
+ <tr>
145
+ <th></th>
146
+ <th style="vertical-align: top;">Product</th>
147
+ <th style="vertical-align: top;">Google status</th>
148
+ <th style="vertical-align: top;">Issues</th>
149
+ </tr>
150
+ </thead>
151
+ <tbody>
152
+ <?php
153
+ if (isset($syncProductList) && count($syncProductList) > 0) {
154
+ foreach ($syncProductList as $skey => $sValue) {
155
+ echo '<tr><td class="product-image">
156
+ <img src="'.$sValue->imageLink.'" alt=""/></td>
157
+ <td>'.$sValue->name.'</td>
158
+ <td>'.$sValue->googleStatus.'</td>
159
+ <td>';
160
+ if (count($sValue->issues) > 0) {
161
+ $str = '';
162
+ foreach ($sValue->issues as $key => $issue) {
163
+ if ($key <= 2) {
164
+ ($key <= 1) ? $str .= $issue.", <br>" : "";
165
+ }
166
+ ($key == 3) ? $str .= "..." : "";
167
+ }
168
+ echo $str;
169
+ } else {
170
+ echo "---";
171
+ }
172
+ echo '</td></tr>';
173
+ }
174
+ }else{
175
+ echo '<tr><td colspan="4">Record not found</td></tr>';
176
+ } ?>
177
+ </tbody>
178
+ </table>
179
+ </div>
180
+ </div>
181
+ </div>
182
  </div>
183
+ </div>
184
+ </div>
185
+ </div>
186
+ </div>
187
+ <div class="col-md-6 col-lg-4">
188
+ <div class="right-content"> <?php echo get_tvc_help_html(); ?></div>
189
+ </div>
190
+ </div>
191
+ </div>
192
  </div>
193
  </div>
194
  </div>
195
  </div>
196
  </div>
197
+ <div class="modal fade popup-modal create-campaign" id="syncProduct" data-backdrop="false">
198
+ <div class="modal-dialog modal-dialog-centered">
199
+ <div class="modal-content">
200
+ <div class="modal-body mt-3">
201
+ <h5>Map your product attributes <span style="float:right"><button type="button" class="close" data-dismiss="modal"> &times; </button> </span></h5>
202
+ <p>Google Merchant Center uses attributes to format your product information for Shopping Ads. Map your product attributes to the Merchant Center product attributes below. You can also edit each product’s individual attributes after you sync your products. Not all fields below are marked required, however based on your shop\'s categories and your country you might map a few optional attributes as well. See the full guide <a target="_blank" href="https://support.google.com/merchants/answer/7052112">here</a>.
203
+ </p>
204
+ <div class="wizard-section campaign-wizard">
205
+ <div class="wizard-content">
206
+ <input type="hidden" name="merchant_id" id="merchant_id" value="<?php echo $this->merchantId; ?>">
207
+ <form class="tab-wizard wizard- wizard" id="productSync" method="POST">
208
+ <h5><span class="wiz-title">Category Mapping</span></h5>
209
+ <section>
210
+ <div class="card-wrapper">
211
+ <div class="row">
212
+ <div class="col-6">
213
+ <h6 class="heading-tbl">WooCommerce Category</h6>
214
+ </div>
215
+ <div class="col-6">
216
+ <h6 class="heading-tbl">Google Merchant Center Category</h6>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
217
  </div>
218
+ </div><?php echo $category_wrapper; ?>
219
  </div>
220
+ </section>
221
+ <!-- Step 2 -->
222
+ <h5><span class="wiz-title">Product Attribution Mapping</span></h5>
223
+ <section>
224
+ <div class="card-wrapper">
225
+ <div class="row">
226
+ <div class="col-6">
227
+ <h6 class="heading-tbl">Google Merchant center product attributes</h6>
228
+ </div>
229
+ <div class="col-6">
230
+ <h6 class="heading-tbl">WooCommerce product attributes</h6>
231
+ </div>
232
+ </div>
233
+ <?php
234
+ foreach ($this->TVC_Admin_Helper->get_gmcAttributes() as $key => $attribute) {
235
+ echo '<div class="row">
236
+ <div class="col-6 align-self-center">
237
+ <div class="form-group">
238
+ <span class="td-head">' . $attribute["field"] . " " . (isset($attribute["required"]) && $attribute["required"] == 1 ? '<span style="color: red;"> *</span>' : "") . '</span>
239
+ <small class="form-label-control">' . (isset($attribute["desc"])? $attribute["desc"]:"") . '</small>
240
+ </div>
241
+ </div>
242
+ <div class="col-6 align-self-center">
243
+ <div class="form-group">';
244
+ if($attribute["field"]=='link'){
245
+ echo "product link";
246
+ }else if($attribute["field"]=='channel'){
247
+ echo "online";
248
+ }else{
249
+ echo '<select class="form-control select2 ' . (isset($attribute["required"]) && $attribute["required"] == 1 ? "field-required" : "") . '" name="' . $attribute["field"] . '" >
250
+ <option value="0">Please Select Attribute</option>';
251
+ foreach ($this->wooCommerceAttributes() as $wKey => $wAttribute) {
252
+ echo '<option value="' . $wAttribute["field"] . '"';
253
+ echo (isset($attribute['required']) && $attribute['required'] == 1 && $attribute['wAttribute'] == $wAttribute["field"]) ? "selected" : "";
254
+ echo '>' . $wAttribute["field"] . '</option>';
255
+ }
256
+ echo '</select>';
257
+ }
258
+ echo '</div>
259
+ </div>
260
+ </div>';
261
+ }?>
262
+ </div>
263
+ </section>
264
+ </form>
265
+ </div>
266
  </div>
267
+ </div>
268
  </div>
269
+ </div>
270
  </div>
 
271
  <script type="text/javascript">
272
+ function call_tvc_api_sync_up(){
273
+ var tvs_this = event.target;
274
+ $("#tvc_msg").remove();
275
+ $("#refresh_api").css("visibility","hidden");
276
+ $(tvs_this).after('<div class="tvc-nb-spinner" id="tvc-nb-spinner"></div>');
277
+ jQuery.post(myAjaxNonces.ajaxurl,{
278
+ action: "tvc_call_api_sync",
279
+ apiSyncupNonce: myAjaxNonces.apiSyncupNonce
280
+ },function( response ){
281
+ var rsp = JSON.parse(response);
282
+ if(rsp.status == "success"){
283
+ $("#tvc-nb-spinner").remove();
284
+ $(tvs_this).after('<span id="tvc_msg">'+rsp.message+"</span>");
285
+ setTimeout(function(){ $("#tvc_msg").remove(); location.reload();}, 4000);
286
+ }
287
+ });
288
+ }
289
+
290
 
291
+ $(document).ready(function() {
292
+ $(".select2").select2();
293
+ });
294
+ $(".tab-wizard").steps({
295
+ headerTag: "h5",
296
+ bodyTag: "section",
297
+ transitionEffect: "fade",
298
+ titleTemplate: '<span class="step">#index#</span> #title#',
299
+ labels: {
300
+ finish: "Sync Products",
301
+ next: "Next",
302
+ previous: "Previous",
303
+ },
304
+ onStepChanged: function(event, currentIndex, priorIndex) {
305
+ $('.steps .current').prevAll().addClass('disabled');
306
+ },
307
+ onFinished: function(event, currentIndex) {
308
+ var valid=true;
309
+ jQuery(".field-required").each(function() {
310
+ if($(this).val()==0 && valid){
311
+ valid=false;
312
+ }
 
 
 
 
 
 
 
313
  });
314
+ if(!valid){
315
+ alert("Please select all required fields");
316
+ }else{
317
+ submitProductSyncUp();
318
+ }//check for required fields end
319
+ }
320
+ });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
321
 
322
+ function submitProductSyncUp() {
323
+ var merchantId = '<?php echo $this->merchantId; ?>';
324
+ var accountId = '<?php echo $this->accountId; ?>';
325
+ var customerId = '<?php echo $this->currentCustomerId; ?>';
326
+ var subscriptionId = '<?php echo $this->subscriptionId; ?>';
327
+ var platformCustomerId = jQuery("#platform_customer_id").val();
328
+ var formData = jQuery("#productSync").serialize();
329
+ //console.log(formData);
330
+ jQuery("#feed-spinner").css("display", "block");
331
+ jQuery.post(
332
+ myAjaxNonces.ajaxurl,
333
+ {
334
+ action: "tvcajax-product-syncup",
335
+ merchantId: merchantId,
336
+ customerId: customerId,
337
+ accountId: accountId,
338
+ subscriptionId: subscriptionId,
339
+ platformCustomerId: platformCustomerId,
340
+ data: formData,
341
+ productSyncupNonce: myAjaxNonces.productSyncupNonce
342
+ },
343
+ function( response ) {
344
+ jQuery("#feed-spinner").css("display", "none");
345
+ //console.log(response);
346
+ var rsp = JSON.parse(response);
347
+ if (rsp.status == "success") {
348
+ $('#syncProduct').modal('hide');
349
+ var message = "Your product are now being synced in your merchant center account. It takes up to 30 minutes to reflect the product data in merchant center. As soon as they are updated, they will be shown in the \"Product Sync\" dashboard.";
350
+ if (rsp.skipProducts > 0) {
351
+ message = message + "\n Because of pricing issues, " + rsp.skipProducts + " products did not sync.";
352
+ }
353
+ alert(message);
354
+ window.location.replace("<?php echo $this->site_url.'sync_product_page'; ?>");
355
+ } else {
356
+ //var message = "Products sync face some unprocessable entity";
357
+ var message = rsp.message;
358
+ alert(message);
359
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
360
  }
361
+ );
362
+ }
 
 
 
363
 
364
+ $(document).on("show.bs.modal", "#syncProduct", function (e) {
365
+ jQuery("#feed-spinner").css("display", "block");
366
+ selectCategory();
367
+ $("select[id^=catmap]").each(function(){
368
+ removeChildCategory($(this).attr("id"))
369
+ });
370
+ });
371
 
372
+ function selectCategory() {
373
+ var country_id = "<?php echo $this->country; ?>";
374
+ var customer_id = '<?php echo $this->currentCustomerId?>';
375
+ var parent = "";
376
+ jQuery.post(
377
+ myAjaxNonces.ajaxurl,
378
+ {
379
+ action: "tvcajax-gmc-category-lists",
380
+ countryCode: country_id,
381
+ customerId: customer_id,
382
+ parent: parent,
383
+ gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce
384
+ },
385
+ function( response ) {
386
+ var categories = JSON.parse(response);
387
+ var obj;
388
+ $("select[id^=catmap]").each(function(){
389
+ obj = $("#catmap-"+$(this).attr("catid")+"_0");
390
+ obj.empty();
391
+ obj.append("<option id='0' value='0' resourcename='0'>Select a category</option>");
392
+ $.each(categories, function (i, value) {
393
+ obj.append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
394
+ });
395
+ });
396
+ jQuery("#feed-spinner").css("display", "none");
397
+ });
398
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
399
 
400
+ function selectSubCategory(thisObj) {
401
+ var selectId;
402
+ var wooCategoryId;
403
+ var GmcCategoryId;
404
+ var GmcParent;
405
+ selectId = thisObj.id;
406
+ wooCategoryId = $(thisObj).attr("catid");
407
+ GmcCategoryId = $(thisObj).find(":selected").val();
408
+ GmcParent = $(thisObj).find(":selected").attr("resourcename");
409
+ //$("#"+selectId).select2().find(":selected").val();
410
+ // $("#"+selectId).select2().find(":selected").data("id");
411
+ //console.log(selectId+"--"+wooCategoryId+"--"+GmcCategoryId+"--"+GmcParent);
412
+
413
+ jQuery("#feed-spinner").css("display", "block");
414
+ removeChildCategory(selectId);
415
+ selectChildCategoryValue(wooCategoryId);
416
+ if (GmcParent != undefined) {
417
+ var country_id = "<?php echo $this->country; ?>";
418
+ var customer_id = '<?php echo $this->currentCustomerId?>';
419
+ jQuery.post(
420
+ myAjaxNonces.ajaxurl,
421
+ {
422
+ action: "tvcajax-gmc-category-lists",
423
+ countryCode: country_id,
424
+ customerId: customer_id,
425
+ parent: GmcParent,
426
+ gmcCategoryListsNonce: myAjaxNonces.gmcCategoryListsNonce
427
+ },
428
+ function( response ) {
429
+ var categories = JSON.parse(response);
430
+ var newId;
431
+ var slitedId = selectId.split("_");
432
+ newId = slitedId[0]+"_"+ ++slitedId[1];
433
+ if(categories.length === 0){
434
+ }else{
435
+ //console.log(newId);
436
+ $("#"+newId).empty();
437
+ $("#"+newId).append("<option id='0' value='0' resourcename='0'>Select a sub-category</option>");
438
+ $.each(categories, function (i, value) {
439
+ $("#"+newId).append("<option id=" + JSON.stringify(value.id) + " value=" + JSON.stringify(value.id) + " resourceName=" + JSON.stringify(value.resourceName) + ">" + value.name + "</option>");
440
+ });
441
+ $("#"+newId).addClass("form-control");
442
+ //$("#"+newId).select2();
443
+ $("#"+newId).css("display", "block");
444
+ }
445
+ jQuery("#feed-spinner").css("display", "none");
446
+ }
447
+ );
448
+ }
449
+ }
450
 
451
+ function removeChildCategory(currentId){
452
+ var currentSplit = currentId.split("_");
453
+ var childEleId;
454
+ for (i = ++currentSplit[1]; i < 6; i++) {
455
+ childEleId = currentSplit[0]+"_"+ i;
456
+ //console.log($("#"+childEleId));
457
+ $("#"+childEleId).empty();
458
+ $("#"+childEleId).removeClass("form-control");
459
+ $("#"+childEleId).css("display", "none");
460
+ if ($("#"+childEleId).data("select2")) {
461
+ $("#"+childEleId).off("select2:select");
462
+ $("#"+childEleId).select2("destroy");
463
+ $("#"+childEleId).removeClass("select2");
464
+ }
465
  }
466
+ }
467
 
468
+ function selectChildCategoryValue(wooCategoryId){
469
+ var childCatvala;
470
+ for(i = 0; i < 6; i++){
471
+ childCatvala = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").attr("id");
472
+ childCatname = $("#catmap-"+wooCategoryId+"_"+i).find(":selected").text();
473
+ if($("#catmap-"+wooCategoryId+"_"+0).find(":selected").attr("id") <= 0){
474
+ $("#category-"+wooCategoryId).val(0);
475
+ }else{
476
+ if(childCatvala > 0){
477
+ $("#category-"+wooCategoryId).val(childCatvala);
478
+ $("#category-name-"+wooCategoryId).val(childCatname);
 
 
479
  }
480
  }
481
  }
482
+ }
483
+ $( ".wizard-content" ).on( "click", ".change_prodct_feed_cat", function() {
484
+ // console.log( $( this ).attr("data-id") );
485
+ $(this).hide();
486
+ var feed_select_cat_id = $( this ).attr("data-id");
487
+ var woo_cat_id = $( this ).attr("data-cat-id");
488
+
489
+ jQuery("#category-"+woo_cat_id).val("0");
490
+ jQuery("#category-name-"+woo_cat_id).val("");
491
+ jQuery("#label-"+feed_select_cat_id).hide();
492
+ jQuery("#"+feed_select_cat_id).slideDown();
493
+ });
494
+ function changeProdctFeedCat(feed_select_cat_id){
495
+ jQuery("#label-"+feed_select_cat_id).hide();
496
+ jQuery("#"+feed_select_cat_id).slideDown();
497
+ }
498
+ </script>
499
+ <?php
500
+ }
501
  }
502
  ?>
includes/setup/google-shopping-feed.php CHANGED
@@ -1,250 +1,214 @@
1
  <?php
2
-
3
  class GoogleShoppingFeed {
4
-
5
- public $merchantId;
6
- public $site_url;
7
- public $customApiObj;
8
-
9
- public function __construct() {
10
- $this->includes();
11
- $this->post_data = $_POST;
12
- $this->returnUrl = $_SERVER['REQUEST_URI'];
13
- $this->customApiObj = new CustomApi();
14
- $this->customApiObj->getGoogleAnalyticDetail();
15
- $this->merchantId = (isset($GLOBALS['tatvicData']['tvc_merchant'])) ? $GLOBALS['tatvicData']['tvc_merchant'] : "";
16
- $this->currentCustomerId = (isset($GLOBALS['tatvicData']['tvc_customer'])) ? $GLOBALS['tatvicData']['tvc_customer'] : "";
17
- $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
18
-
19
- $this->html_run();
20
- }
21
-
22
- public function includes() {
23
- if (!class_exists('CustomApi.php')) {
24
- require_once(__DIR__ . '/CustomApi.php');
25
- }
26
- if (!class_exists('ShoppingApi')) {
27
- require_once(__DIR__ . '/ShoppingApi.php');
28
- }
29
- if (!class_exists('SmartShoppingCampaign')) {
30
- require_once(__DIR__ . '/SmartShoppingCampaign.php');
31
- }
32
- }
33
-
34
- public function html_run() {
35
- $this->create_form();
36
- }
37
- public function add_list_html($title, $val){
38
- return '<li>
39
- <div class="row">
40
- <div class="col-7 col-md-8 align-self-center pr-0">
41
- <span class="text">'.$title.'</span>
42
- </div>
43
- <div class="col-5 col-md-4 align-self-center text-right">
44
- <span class="text"><strong>'. $val.'</strong></span>
45
- </div>
46
- </div>
47
- </li>';
48
- }
49
- public function configuration_list_html($title, $val){
50
- $imge = (isset($val) && $val != "" && $val != 0) ? '<img src="' . ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="config-success"/>' : '<img src="' . ENHANCAD_PLUGIN_URL.'/admin/images/exclaimation.png" alt="no-config-success"/>';
51
- return '<li>
52
- <div class="row">
53
- <div class="col-7 col-md-7 col-lg-9 align-self-center pr-0">
54
- <span class="text">'.$title.'</span>
55
- </div>
56
- <div class="col-5 col-md-5 col-lg-3 align-self-center text-right">
57
- <div class="list-image">'.$imge.'</div>
58
- </div>
59
- </div>
60
- </li>';
61
  }
62
 
63
- private function get_currency_symbol() {
64
- //$campaignClsObj = new SmartShoppingCampaign();
65
- //$currency = $campaignClsObj->getCustomerCurrency();
66
- //return get_woocommerce_currency_symbol($currency);
67
- $currency_symbol = $this->customApiObj->getCampaignCurrencySymbol(['customer_id' => $this->currentCustomerId]);
68
- if (isset($currency_symbol->data) && isset($currency_symbol->data['status'])) {
69
- if ($currency_symbol->data['status'] == 200) {
70
- $currency = get_woocommerce_currency_symbol($currency_symbol->data['data']->currency);
71
- }
72
- } else {
73
- $currency = $currency = get_woocommerce_currency_symbol("USD");
74
- }
75
- return $currency;
76
  }
77
-
78
- public function create_form() {
79
- $syncProductList = [];
80
- $syncProductStat = [];
81
- $google_detail = $this->customApiObj->getGoogleAnalyticDetail();
82
- if (isset($google_detail->data['status']) && $google_detail->data['status'] == 200) {
83
- if (isset($google_detail->data['data'])) {
84
- $googleDetail = $google_detail->data['data'];
85
- }
86
- } else {
87
- $googleDetail = [];
 
 
 
 
 
 
 
 
 
 
88
  }
89
- /* echo "<pre>"; */
90
- if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != '') {
91
- $syncProduct_list_res = $this->customApiObj->getSyncProductList(['merchant_id' => $this->merchantId]);
92
- if (isset($syncProduct_list_res->data) && isset($syncProduct_list_res->status) && $syncProduct_list_res->status == 200) {
93
- if (isset($syncProduct_list_res->data->products)) {
94
- $syncProductList = $syncProduct_list_res->data->products;
95
- }
96
- if (isset($syncProduct_list_res->data->statistics)) {
97
- $syncProductStat = $syncProduct_list_res->data->statistics;
98
- }
99
- } else {
100
- $syncProductList = [];
101
- $syncProductStat = [];
102
- $class = 'notice notice-error';
103
- $message = esc_html__('Not any Product found on this GMC account.');
104
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
105
- }
106
  }
107
-
108
- $campaigns_list = [];
109
-
110
- $api_old_obj = new ShoppingApi();
111
-
112
- $totalCampaigns = 0;
113
- $totalActiveWooProduct = 0;
114
- $campaignActive = 0;
115
- $campaignClicks = 0;
116
- $campaignCost = 0;
117
- $campaignConversions = 0;
118
- $campaignSales = 0;
119
-
120
- // Get currency
121
- $currency = $this->get_currency_symbol();
122
-
123
- // Total active products in WooCommerce
124
- $args = array('post_type' => 'product', 'post_status' => 'publish', 'posts_per_page' => -1);
125
- $products = new WP_Query($args);
126
- $totalActiveWooProduct = $products->found_posts;
127
-
128
- $campaigns_list_res = $api_old_obj->getCampaigns();
129
- if (isset($campaigns_list_res->errors) && !empty($campaigns_list_res->errors)) {
130
-
131
- } else {
132
- $campaigns_list_res = $campaigns_list_res->data;
133
- if ($campaigns_list_res['status'] == 200) {
134
- $campaigns_list = $campaigns_list_res['data'];
135
- $totalCampaigns = count($campaigns_list);
136
- foreach ($campaigns_list as $campaign) {
137
- if ($campaign->active == 1) {
138
- $campaignActive = $campaignActive + $campaign->active;
139
- }
140
- $campaignClicks = $campaignClicks + $campaign->clicks;
141
- $campaignCost = $campaignCost + $campaign->cost;
142
- $campaignConversions = $campaignConversions + $campaign->conversions;
143
- $campaignSales = $campaignSales + $campaign->sales;
144
- }
145
- if (count($campaigns_list) > 0) {
146
- $campaignConversions = $campaignConversions / count($campaigns_list);
147
- }
148
- }
149
- }
150
- $sync_product_total = (!empty($syncProductStat)) ? $syncProductStat->total : "0";
151
- $sync_product_approved = (!empty($syncProductStat)) ? $syncProductStat->approved : "0";
152
- $sync_product_disapproved = (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0";
153
- $sync_product_pending = (!empty($syncProductStat)) ? $syncProductStat->pending : "0";
154
- $campaignActive = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignActive : '0');
155
- $campaignCost = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $currency . $campaignCost : '0');
156
- $campaignClicks = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignClicks : '0');
157
- $campaignConversions = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignConversions . "%" : '0');
158
- $campaign_sales = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $currency . $campaignSales : '0');
159
-
160
- echo '<div class="container-fluid">
161
  <div class="row">
162
  <div class= "col col-12">
163
  <div class="card mw-100" style="padding:0;">
164
  <div class="card-body">
165
- <div class="tab-pane show active" id="googleShoppingFeed">
166
- <div class="row">
167
- <div class="col-md-6 col-lg-8 border-right">
168
- <div class="configuration-section" id="config-pt1">
169
- <div class="row confg-card gsf-sec">
170
- <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
171
- <div class="card configure-card">
172
- <div class="card-header">
173
- <h4 class="confg-title">Configuration</h4>
174
- </div>
175
- <div class="card-body">
176
- <ul class="list-unstyled">'.
177
- $this->configuration_list_html("Google merchant center",(isset($googleDetail->google_merchant_center_id))?$googleDetail->google_merchant_center_id:"")
178
- .$this->configuration_list_html("Site Verified",((isset($googleDetail->is_site_verified)))?$googleDetail->is_site_verified:"")
179
- .$this->configuration_list_html("Domain claim",((isset($googleDetail->is_domain_claim)))?$googleDetail->is_domain_claim:"")
180
- .$this->configuration_list_html("Google Ads linking",((isset($googleDetail->google_ads_id)))?$googleDetail->google_ads_id:"")
181
- //.$this->configuration_list_html("Product sync",$googleDetail->is_product_sync)
182
- .'</ul>
183
- </div>
184
- <div class="card-footer">
185
- <a href="' . $this->site_url . 'gaa_config_page" class="btn btn-primary btn-success w-100" id="configuration">Edit</a>
186
- </div>
187
- </div>
188
- </div>
189
- <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
190
- <div class="card">
191
- <div class="card-header">
192
- <h4 class="confg-title">Product Sync</h4>
193
- </div>
194
- <div class="card-body">
195
- <ul class="list-unstyled">'.$this->add_list_html("Active products in WooCommerce",$totalActiveWooProduct)
196
- .$this->add_list_html("Total synced products in Merchant center", $sync_product_total)
197
- .$this->add_list_html("Approved", $sync_product_approved)
198
- .$this->add_list_html("Disapproved", $sync_product_disapproved)
199
- .$this->add_list_html("Pending", $sync_product_pending).'
200
- </ul>
201
- </div>';
202
- if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != "") {
203
- echo '<div class="card-footer">
204
- <a href="' . $this->site_url . 'sync_product_page" class="btn btn-primary btn-success w-100" id="product-sync">Edit</a>
205
- </div>';
206
- }
207
-
208
- echo '</div>
209
- </div>
210
- <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
211
- <div class="card">
212
- <div class="card-header">
213
- <h4 class="confg-title">Smart Shopping Campaigns</h4>
214
- </div>
215
- <div class="card-body">
216
- <ul class="list-unstyled">'
217
- .$this->add_list_html("Total campaign",$totalCampaigns)
218
- .$this->add_list_html("Active campaigns",$campaignActive)
219
- .$this->add_list_html("Cost",$campaignCost)
220
- .$this->add_list_html("Click",$campaignClicks)
221
- .$this->add_list_html("Conversion%",$campaignConversions)
222
- .$this->add_list_html("Sales",$campaign_sales).'
223
- </ul>
224
- </div>';
225
- if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "") {
226
- echo '<div class="card-footer">
227
- <a href="' . $this->site_url . 'shopping_campaigns_page" id="smart-shopping-campaigns" class="btn btn-primary btn-success w-100">Edit</a>
228
- </div>';
229
- }
230
- echo '</div>
231
- </div>
232
- </div>
233
- </div>
234
- </div>
235
- <div class="col-md-6 col-lg-4">
236
- <div class="right-content">'.get_tvc_help_html().'
237
- </div>
238
- </div>
239
- </div>
240
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
241
  </div>
242
  </div>
243
  </div>
244
  </div>
245
- </div>';
246
- }
247
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
248
  }
249
-
250
  ?>
1
  <?php
 
2
  class GoogleShoppingFeed {
3
+ public $site_url="";
4
+ protected $TVC_Admin_Helper="";
5
+ public function __construct() {
6
+ $this->TVC_Admin_Helper = new TVC_Admin_Helper();
7
+ $this->subscriptionId = $this->TVC_Admin_Helper->get_subscriptionId();
8
+ $this->site_url = "admin.php?page=enhanced-ecommerce-google-analytics-admin-display&tab=";
9
+ $this->create_form();
10
+ }
11
+ public function add_list_html($title, $val){
12
+ return '<li>
13
+ <div class="row">
14
+ <div class="col-7 col-md-8 align-self-center pr-0">
15
+ <span class="text">'.$title.'</span>
16
+ </div>
17
+ <div class="col-5 col-md-4 align-self-center text-right">
18
+ <span class="text"><strong>'. $val.'</strong></span>
19
+ </div>
20
+ </div>
21
+ </li>';
22
+ }
23
+ public function configuration_list_html($title, $val){
24
+ $imge = (isset($val) && $val != "" && $val != 0) ? '<img src="' . ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="config-success"/>' : '<img src="' . ENHANCAD_PLUGIN_URL.'/admin/images/exclaimation.png" alt="no-config-success"/>';
25
+ return '<li>
26
+ <div class="row">
27
+ <div class="col-7 col-md-7 col-lg-9 align-self-center pr-0">
28
+ <span class="text">'.$title.'</span>
29
+ </div>
30
+ <div class="col-5 col-md-5 col-lg-3 align-self-center text-right">
31
+ <div class="list-image">'.$imge.'</div>
32
+ </div>
33
+ </div>
34
+ </li>';
35
+ }
36
+ public function create_form() {
37
+ $googleDetail = [];
38
+ $google_detail = $this->TVC_Admin_Helper->get_ee_options_data();
39
+ if(isset($google_detail['setting'])){
40
+ if ($google_detail['setting']) {
41
+ $googleDetail = $google_detail['setting'];
42
+ }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
43
  }
44
 
45
+ $syncProductStat = [];
46
+ $args = array('post_type' => 'product', 'post_status' => 'publish', 'posts_per_page' => -1);
47
+ $products = new WP_Query($args);
48
+ $totalActiveWooProduct = $products->found_posts;
49
+ if(isset($google_detail['prod_sync_status'])){
50
+ if ($google_detail['prod_sync_status']) {
51
+ $syncProductStat = $google_detail['prod_sync_status'];
52
+ }
 
 
 
 
 
53
  }
54
+ $sync_product_total = (!empty($syncProductStat)) ? $syncProductStat->total : "0";
55
+ $sync_product_approved = (!empty($syncProductStat)) ? $syncProductStat->approved : "0";
56
+ $sync_product_disapproved = (!empty($syncProductStat)) ? $syncProductStat->disapproved : "0";
57
+ $sync_product_pending = (!empty($syncProductStat)) ? $syncProductStat->pending : "0";
58
+
59
+ $totalCampaigns = 0;$campaignActive = 0; $campaignClicks = 0;
60
+ $campaignCost = 0; $campaignConversions = 0; $campaignSales = 0;
61
+ // Get currency
62
+ $currency = $this->TVC_Admin_Helper->get_user_currency_symbol();
63
+ if(isset($google_detail['campaigns_list'])){
64
+ if ($google_detail['campaigns_list']) {
65
+ $campaigns_list = $google_detail['campaigns_list'];
66
+ $totalCampaigns = count($campaigns_list);
67
+ foreach ($campaigns_list as $campaign) {
68
+ if ($campaign->active == 1) {
69
+ $campaignActive = $campaignActive + $campaign->active;
70
+ }
71
+ $campaignClicks = $campaignClicks + $campaign->clicks;
72
+ $campaignCost = $campaignCost + $campaign->cost;
73
+ $campaignConversions = $campaignConversions + $campaign->conversions;
74
+ $campaignSales = $campaignSales + $campaign->sales;
75
  }
76
+ if (count($campaigns_list) > 0) {
77
+ $campaignConversions = $campaignConversions / count($campaigns_list);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
78
  }
79
+ }
80
+ $campaignActive = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignActive : '0');
81
+ $campaignCost = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $currency . $campaignCost : '0');
82
+ $campaignClicks = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignClicks : '0');
83
+ $campaignConversions = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $campaignConversions . "%" : '0');
84
+ $campaignSales = (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "" ? $currency . $campaignSales : '0');
85
+ }
86
+ $last_api_sync_up = "";
87
+ if(isset($google_detail['sync_time'])){
88
+ if ($google_detail['sync_time']) {
89
+ $last_api_sync_up = date( 'Y-m-d H:i',$google_detail['sync_time']);
90
+ }
91
+ }
92
+ ?>
93
+ <div class="container-fluid">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
94
  <div class="row">
95
  <div class= "col col-12">
96
  <div class="card mw-100" style="padding:0;">
97
  <div class="card-body">
98
+ <div class="tab-pane show active" id="googleShoppingFeed">
99
+ <div class="row">
100
+ <div class="col-md-6 col-lg-8 border-right">
101
+ <?php if($this->subscriptionId != ""){?>
102
+ <div class="tvc-api-sunc">
103
+ <span>
104
+ <?php if($last_api_sync_up){
105
+ echo "Details last synced at ".$last_api_sync_up;
106
+ }else{
107
+ echo "Refresh sync up";
108
+ }?></span><img id="refresh_api" onclick="call_tvc_api_sync_up();" src="<?php echo ENHANCAD_PLUGIN_URL.'/admin/images/refresh.png'; ?>">
109
+ </div>
110
+ <?php } ?>
111
+ <div class="configuration-section" id="config-pt1">
112
+ <div class="row confg-card gsf-sec">
113
+ <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
114
+ <div class="card configure-card">
115
+ <div class="card-header">
116
+ <h4 class="confg-title">Configuration</h4>
117
+ </div>
118
+ <div class="card-body">
119
+ <ul class="list-unstyled"><?php
120
+ echo $this->configuration_list_html("Google merchant center",(isset($googleDetail->google_merchant_center_id))?$googleDetail->google_merchant_center_id:"")
121
+ .$this->configuration_list_html("Site Verified",((isset($googleDetail->is_site_verified)))?$googleDetail->is_site_verified:"")
122
+ .$this->configuration_list_html("Domain claim",((isset($googleDetail->is_domain_claim)))?$googleDetail->is_domain_claim:"")
123
+ .$this->configuration_list_html("Google Ads linking",((isset($googleDetail->google_ads_id)))?$googleDetail->google_ads_id:"");
124
+ ?>
125
+ </ul>
126
+ </div>
127
+ <div class="card-footer">
128
+ <a href="<?php echo $this->site_url.'gaa_config_page'; ?>" class="btn btn-primary btn-success w-100" id="configuration">Edit</a>
129
+ </div>
130
+ </div>
131
+ </div>
132
+ <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
133
+ <div class="card">
134
+ <div class="card-header">
135
+ <h4 class="confg-title">Product Sync</h4>
136
+ </div>
137
+ <div class="card-body">
138
+ <ul class="list-unstyled">
139
+ <?php
140
+ echo $this->add_list_html("Active products in WooCommerce",$totalActiveWooProduct)
141
+ .$this->add_list_html("Total synced products in Merchant center", $sync_product_total)
142
+ .$this->add_list_html("Approved", $sync_product_approved)
143
+ .$this->add_list_html("Disapproved", $sync_product_disapproved)
144
+ .$this->add_list_html("Pending", $sync_product_pending);
145
+ ?>
146
+ </ul>
147
+ </div>
148
+ <?php
149
+ if (isset($googleDetail->google_merchant_center_id) && $googleDetail->google_merchant_center_id != "") {?>
150
+ <div class="card-footer">
151
+ <a href="<?php echo $this->site_url.'sync_product_page'; ?>" class="btn btn-primary btn-success w-100" id="product-sync">Edit</a>
152
+ </div>
153
+ <?php } ?>
154
+ </div>
155
+ </div>
156
+ <div class="col-md-12 col-lg-4 mb-3 mb-lg-0">
157
+ <div class="card">
158
+ <div class="card-header">
159
+ <h4 class="confg-title">Smart Shopping Campaigns</h4>
160
+ </div>
161
+ <div class="card-body">
162
+ <ul class="list-unstyled">
163
+ <?php
164
+ echo $this->add_list_html("Total campaign",$totalCampaigns)
165
+ .$this->add_list_html("Active campaigns",$campaignActive)
166
+ .$this->add_list_html("Cost",$campaignCost)
167
+ .$this->add_list_html("Click",$campaignClicks)
168
+ .$this->add_list_html("Conversion%",$campaignConversions)
169
+ .$this->add_list_html("Sales",$campaignSales); ?>
170
+ </ul>
171
+ </div>
172
+ <?php if (isset($googleDetail->google_ads_id) && $googleDetail->google_ads_id != "") { ?>
173
+ <div class="card-footer">
174
+ <a href="<?php echo $this->site_url.'shopping_campaigns_page'; ?>" id="smart-shopping-campaigns" class="btn btn-primary btn-success w-100">Edit</a>
175
+ </div>
176
+ <?php }?>
177
+ </div>
178
+ </div>
179
+ </div>
180
+ </div>
181
+ </div>
182
+ <div class="col-md-6 col-lg-4">
183
+ <div class="right-content"><?php echo get_tvc_help_html(); ?></div>
184
+ </div>
185
+ </div>
186
+ </div>
187
  </div>
188
  </div>
189
  </div>
190
  </div>
191
+ </div>
192
+ <script type="text/javascript">
193
+ function call_tvc_api_sync_up(){
194
+ var tvs_this = event.target;
195
+ $("#tvc_msg").remove();
196
+ $("#refresh_api").css("visibility","hidden");
197
+ $(tvs_this).after('<div class="tvc-nb-spinner" id="tvc-nb-spinner"></div>');
198
+ jQuery.post(myAjaxNonces.ajaxurl,{
199
+ action: "tvc_call_api_sync",
200
+ apiSyncupNonce: myAjaxNonces.apiSyncupNonce
201
+ },function( response ){
202
+ var rsp = JSON.parse(response);
203
+ if(rsp.status == "success"){
204
+ $("#tvc-nb-spinner").remove();
205
+ $(tvs_this).after('<span id="tvc_msg">'+rsp.message+"</span>");
206
+ setTimeout(function(){ $("#tvc_msg").remove(); location.reload();}, 4000);
207
+ }
208
+ });
209
+ }
210
+ </script>
211
+ <?php
212
+ }
213
  }
 
214
  ?>
includes/setup/help-html.php CHANGED
@@ -1,45 +1,51 @@
1
  <?php
2
  function get_connect_google_popup_html(){
3
- $obj = new Enhanced_Ecommerce_Google_Analytics_Admin($plugin_name = 'enhanced-e-commerce-for-woocommerce-store', $version = PLUGIN_NAME_VERSION);
4
- $url =$obj->get_connect_url();
5
  return '<div class="modal fade" id="tvc_google_connect" data-backdrop="static" data-keyboard="false" tabindex="-1" aria-labelledby="staticBackdropLabel" aria-hidden="true">
6
- <div class="modal-dialog modal-dialog-centered">
7
- <div class="modal-content">
8
- <div class="modal-header">
9
- <h5 class="modal-title" id="staticBackdropLabel">Connect Tatvic with your website</h5>
10
- <button type="button" class="close" data-dismiss="modal" aria-label="Close">
11
- <span aria-hidden="true">&times;</span>
12
- </button>
13
- </div>
14
- <div class="modal-body">
15
- By continuing from here, you will be redirected to Tatvic’s website to configure your google analytics, google ads and google merchant center accounts.
16
- <br>
17
- <br>
18
- Make sure you sign in with the google account that has all privileges to access google analytics, google ads and google merchant center account.
19
- </div>
20
- <div class="modal-footer">
21
- <a target="_blank" class="ee-oauth-container btn darken-4 white black-text" href="'. $url.'" style="text-transform:none; margin: 0 auto;">
22
- <div class="left">
23
- <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
24
- src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
25
- </div>
26
- <p style="font-size: inherit; margin-top:5px; margin-right:8px; ">Sign In With Google</p>
27
- </a>
28
- <!--sigin with google end-->
29
  </div>
30
- </div>
 
 
31
  </div>
32
- </div>';
 
 
 
 
 
 
 
 
 
33
  }
34
  function get_google_shopping_tabs_html($site_url, $google_merchant_center_id){
35
- $obj = new Enhanced_Ecommerce_Google_Analytics_Admin($plugin_name = 'enhanced-e-commerce-for-woocommerce-store', $version = PLUGIN_NAME_VERSION);
36
  $site_url_p = (isset($google_merchant_center_id) && $google_merchant_center_id != '')?$site_url:"javascript:void(0);";
37
  $site_url_p_target ="";
38
  if(isset($google_merchant_center_id) && $google_merchant_center_id == ''){
39
  $site_url_p_target = 'data-toggle="modal" data-target="#tvc_google_connect"';
40
  }
41
  $tab = (isset($_GET['tab']) && $_GET['tab'])?$_GET['tab']:"";
42
- $setting_status = $obj->check_setting_status_sub_tabs();
 
43
  //echo "<pre>";
44
  //print_r($setting_status);
45
  $google_shopping_conf_msg ="";
1
  <?php
2
  function get_connect_google_popup_html(){
3
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
 
4
  return '<div class="modal fade" id="tvc_google_connect" data-backdrop="static" data-keyboard="false" tabindex="-1" aria-labelledby="staticBackdropLabel" aria-hidden="true">
5
+ <div class="modal-dialog modal-dialog-centered">
6
+ <div class="modal-content">
7
+ <div class="modal-header">
8
+ <h5 class="modal-title" id="staticBackdropLabel">Connect Tatvic with your website</h5>
9
+ <button type="button" class="close" data-dismiss="modal" aria-label="Close">
10
+ <span aria-hidden="true">&times;</span>
11
+ </button>
12
+ </div>
13
+ <div class="modal-body">
14
+ By continuing from here, you will be redirected to Tatvic’s website to configure your google analytics, google ads and google merchant center accounts.
15
+ <br>
16
+ <br>
17
+ Make sure you sign in with the google account that has all privileges to access google analytics, google ads and google merchant center account.
18
+ </div>
19
+ <div class="modal-footer">
20
+ <a target="_blank" class="ee-oauth-container btn darken-4 white black-text" href="'. $TVC_Admin_Helper->get_connect_url().'" style="text-transform:none; margin: 0 auto;">
21
+ <div class="left">
22
+ <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
23
+ src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
 
 
 
 
24
  </div>
25
+ <p style="font-size: inherit; margin-top:5px; margin-right:8px; ">Sign In With Google</p>
26
+ </a>
27
+ <!--sigin with google end-->
28
  </div>
29
+ </div>
30
+ </div>
31
+ </div>';
32
+ }
33
+ function info_htnml($validation){
34
+ if($validation == true){
35
+ return '<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/config-success.svg" alt="configuration success" class="config-success">';
36
+ }else{
37
+ return '<img src="'.ENHANCAD_PLUGIN_URL.'/admin/images/exclaimation.png" alt="configuration success" class="config-fail">';
38
+ }
39
  }
40
  function get_google_shopping_tabs_html($site_url, $google_merchant_center_id){
 
41
  $site_url_p = (isset($google_merchant_center_id) && $google_merchant_center_id != '')?$site_url:"javascript:void(0);";
42
  $site_url_p_target ="";
43
  if(isset($google_merchant_center_id) && $google_merchant_center_id == ''){
44
  $site_url_p_target = 'data-toggle="modal" data-target="#tvc_google_connect"';
45
  }
46
  $tab = (isset($_GET['tab']) && $_GET['tab'])?$_GET['tab']:"";
47
+ $TVC_Admin_Helper = new TVC_Admin_Helper();
48
+ $setting_status = $TVC_Admin_Helper->check_setting_status_sub_tabs();
49
  //echo "<pre>";
50
  //print_r($setting_status);
51
  $google_shopping_conf_msg ="";
includes/setup/img/lock.png DELETED
Binary file
includes/setup/img/tick-mark.png DELETED
Binary file
includes/setup/img/tvc-lock-large.png DELETED
Binary file
includes/setup/img/tvc-lock.png DELETED
Binary file
includes/setup/img/tvc-tick-large.png DELETED
Binary file
includes/setup/img/tvc-tick.png DELETED
Binary file
includes/setup/json/client-secrets.json CHANGED
@@ -10,7 +10,7 @@
10
  "manager_refresh_token": "1//0glkEtsa8PNuwCgYIARAAGBASNwF-L9IrBZQjIINEw2MMO_M_mRdKwoNCBwJtHXtahh5Bj4oQR01ErmhaBB2TqE68rkP8JaELISU",
11
  "developer_token": "R0IEth5fQ1Ac59qB2Wf8Aw",
12
  "redirect_uris": [
13
- "https://estorenew.tatvic.com/config/ga_rdr_gmc.php"
14
  ],
15
  "javascript_origins": [
16
  "https://plugins.tatvic.com"
10
  "manager_refresh_token": "1//0glkEtsa8PNuwCgYIARAAGBASNwF-L9IrBZQjIINEw2MMO_M_mRdKwoNCBwJtHXtahh5Bj4oQR01ErmhaBB2TqE68rkP8JaELISU",
11
  "developer_token": "R0IEth5fQ1Ac59qB2Wf8Aw",
12
  "redirect_uris": [
13
+ "https://preprodestore.tatvic.com/config/ga_rdr_gmc.php"
14
  ],
15
  "javascript_origins": [
16
  "https://plugins.tatvic.com"
includes/user-interface/abstract-tvc-category-wrapper.php DELETED
@@ -1,87 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Category Wrapper Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @since 2.4.0
8
- * @version 1.0.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_Category_Wrapper' ) ) :
16
-
17
- abstract class TVC_Category_Wrapper {
18
-
19
- protected abstract function display();
20
-
21
- /**
22
- * Returns the code for the category mapping, containing all shop categories as rows.
23
- *
24
- * @param string $mode displays a normal category selector or a category mapping selector when 'mapping' is given. Default = 'normal'.
25
- * @return string
26
- */
27
- protected function category_table_content( $mode = 'normal' ) {
28
- $shop_categories = TVC_Taxonomies::get_shop_categories_list();
29
-
30
- return $this->category_rows( $shop_categories, 0, $mode );
31
- }
32
-
33
- /**
34
- * Returns the code for the product filter.
35
- *
36
- * @return string
37
- */
38
- protected function product_filter() {
39
- return TVC_Category_Selector_Element::product_filter_selector();
40
- }
41
-
42
- private function category_rows( $shop_categories, $category_depth_level, $mode ) {
43
- $html_code = '';
44
- $level_indicator = '';
45
-
46
- for ( $i = 0; $i < $category_depth_level; $i ++ ) {
47
- $level_indicator .= '— ';
48
- }
49
-
50
- if ( $shop_categories ) {
51
- foreach ( $shop_categories as $category ) {
52
- $category_children = $this->get_sub_categories( $category );
53
-
54
- $html_code .= TVC_Category_Selector_Element::category_mapping_row( $category, $category_children, $level_indicator, $mode );
55
-
56
- if ( $category->children && count( (array) $category->children ) > 0 ) {
57
- $html_code .= self::category_rows( $category->children, $category_depth_level + 1, $mode );
58
- }
59
- }
60
- } else {
61
- $html_code .= esc_html__( 'No shop categories found.', 'tvc-product-feed-manager' );
62
- }
63
-
64
- return $html_code;
65
- }
66
-
67
- private function get_sub_categories( $category ) {
68
- $array_string = '';
69
-
70
- if ( $category->children && count( (array) $category->children ) ) {
71
- $array_string .= '[';
72
-
73
- foreach ( $category->children as $child ) {
74
- $array_string .= $child->term_id . ', ';
75
- }
76
-
77
- $array_string = substr( $array_string, 0, - 2 );
78
- $array_string .= ']';
79
- }
80
-
81
- return $array_string;
82
- }
83
- }
84
-
85
- // end of TVC_Category_Wrapper class
86
-
87
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-add-options-page.php DELETED
@@ -1,64 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Feed Manager Add Options Page Class.
5
- *
6
- * @package TVC Product Feed Manager/User Interface/Classes
7
- * @version 1.4.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Add_Options_Page' ) ) :
15
-
16
- class TVC_Add_Options_Page extends TVC_Admin_Page {
17
- private $_options_form;
18
-
19
- public function __construct() {
20
- parent::__construct();
21
-
22
- add_option( 'wp_enqueue_scripts', TVC_i18n_Scripts::tvc_settings_i18n() );
23
- add_option( 'wp_enqueue_scripts', TVC_i18n_Scripts::tvc_backup_list_i18n() );
24
-
25
- $this->_options_form = new TVC_Options_Page();
26
- }
27
-
28
- public function show() {
29
- echo $this->options_page_header();
30
-
31
- echo $this->message_field();
32
-
33
- echo $this->options_page_body();
34
-
35
- echo $this->options_page_footer();
36
- }
37
-
38
- private function options_page_header() {
39
- $spinner_gif = ENHANCAD_PLUGIN_URL . '/images/ajax-loader.gif';
40
-
41
- return
42
- '
43
- <div class="wrap">
44
- <div class="feed-spinner" id="feed-spinner" style="display:none;">
45
- <img id="img-spinner" src="' . $spinner_gif . '" alt="Loading" />
46
- </div>
47
- <div class="tvc-main-wrapper tvc-header-wrapper" id="tvc-header-wrapper">
48
- <div class="header-text"><h1>' . esc_html__( 'Google Feed Manager Settings', 'tvc-product-feed-manager' ) . '</h1></div>
49
- <div class="logo"></div>
50
- </div>
51
- ';
52
- }
53
-
54
- private function options_page_body() {
55
- $this->_options_form->display();
56
- }
57
-
58
- private function options_page_footer() {
59
- }
60
- }
61
-
62
- // end of TVC_Add_Options_Page class
63
-
64
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-admin-page.php DELETED
@@ -1,131 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * Google Product Feed Manager Admin Page Class.
5
- *
6
- * @package Google Product Feed Manager/User Interface/Classes
7
- * @version 1.3.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Admin_Page' ) ) :
15
-
16
- /**
17
- * TVC Admin Page Class
18
- */
19
- class TVC_Admin_Page {
20
-
21
- public $tab_data;
22
-
23
- public function __construct() {
24
-
25
- $tvc_active_tab = isset( $_GET['tab'] ) ? $_GET['tab'] : null;
26
-
27
- $this->tab_data = apply_filters(
28
- 'tvc_main_form_tabs',
29
- array(
30
- array(
31
- 'page' => 'tvc-product-feed-manager&tab=feed-list',
32
- 'tab_status' => 'feed-list' === $tvc_active_tab ? ' nav-tab-active' : '',
33
- 'title' => esc_html__('Feed List', 'tvc-product-feed-manager'),
34
- ),
35
- array(
36
- 'page' => 'tvc-product-feed-manager&tab=product-feed',
37
- 'tab_status' => 'product-feed' === $tvc_active_tab ? ' nav-tab-active' : '',
38
- 'title' => esc_html__('Product Feed', 'tvc-product-feed-manager'),
39
- ),
40
- ),
41
- $tvc_active_tab
42
- );
43
- }
44
-
45
- /**
46
- * Returns a string containing the standard header for an admin page.
47
- *
48
- * @param string $header_text
49
- *
50
- * @return string
51
- */
52
- protected function admin_page_header( $header_text = 'Google Shopping Feeds by Tatvic' ) {
53
- $spinner_gif = ENHANCAD_PLUGIN_URL . '/images/ajax-loader.gif';
54
- $feed_queue = implode( ',', get_site_option( 'tvc_feed_queue', array() ) ); // Get the active feed queue.
55
-
56
- return
57
- '<div class="wrap">
58
- <div class="feed-spinner" id="feed-spinner" style="display:none;">
59
- <img id="img-spinner" src="' . $spinner_gif . '" alt="Loading" />
60
- </div>
61
- <div class="data" id="tvc-product-feed-manager-data" style="display:none;"><div id="wp-plugin-url">' . TVC_UPLOADS_URL . '</div><div id="tvc-feed-list-feeds-in-queue">' . $feed_queue . '</div></div>
62
- <div class="tvc-main-wrapper tvc-header-wrapper" id="header-wrapper">
63
- <div class="header-text"><h1>' . $header_text . '</h1></div>
64
-
65
- </div>
66
- ';
67
- }
68
-
69
- protected function message_field( $alert = '' ) {
70
- $display_alert = empty( $alert ) ? 'none' : 'block';
71
-
72
- return
73
- '<div class="message-field notice notice-error" id="error-message" style="display:none;"></div>
74
- <div class="message-field notice notice-success" id="success-message" style="display:none;"></div>
75
- <div class="message-field notice notice-warning" id="disposable-warning-message" style="display:' . $display_alert . ';"><p>' . $alert . '</p>
76
- <button type="button" id="disposable-notice-button" class="notice-dismiss"></button>
77
- </div>'
78
-
79
- ;
80
- }
81
-
82
- /**
83
- * returns the html code for the tabs
84
- *
85
- * @return string
86
- */
87
- protected function tabs() {
88
- return TVC_Form_Element::main_form_tabs();
89
- }
90
-
91
- /**
92
- * returns the html code for the sub tabs
93
- *
94
- * @return string
95
- */
96
- protected function subtabs() {
97
- return TVC_Form_Element::sub_form_tabs();
98
- }
99
-
100
- /**
101
- * Returns the html code for the tab header.
102
- *
103
- * @param string $header_title String for the tab header text.
104
- * @param string $header_sub_title String for the sub title below the tab header text.
105
- *
106
- * @return string Html code containing the tab header.
107
- *@since 2.11.0.
108
- */
109
- protected function tab_header( $header_title, $header_sub_title ) {
110
- $tvc_active_tab = isset( $_GET['tab'] ) ? $_GET['tab'] : null;
111
-
112
- if('feed-list' === $tvc_active_tab || $tvc_active_tab == null) {
113
- $header_html = '<div class="bg-wrap d-inline-block" id="tab-header"><strong style="font-size: 20px;">' . $header_title . '</strong>
114
- <div><p>' . $header_sub_title . '</p></div></div>';
115
- $header_html .= '<div class="button-wrapper float-right" id="page-bottom-buttons">';
116
- $header_html .= '<input class="button-primary feed-list-lower-button" type="button" ' .
117
- 'onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=product-feed\'" name="new" value="' .
118
- __( 'Add New Feed', 'tvc-product-feed-manager' ) . '" id="add-new-feed-button" />
119
- <input class="button-primary feed-list-lower-button" type="button" data-toggle="modal" data-target="#conversionModal" name="create-campaign" value="' .
120
- __( 'Create Smart shopping Campaign', 'tvc-product-feed-manager' ) . '" id="create-campaign-button" />';
121
- $header_html .= '</div>';
122
- } else {
123
- $header_html = '<div class="bg-wrap" id="tab-header"><strong style="font-size: 20px;">' . $header_title . '</strong>
124
- <div><p>' . $header_sub_title . '</p></div>';
125
- }
126
-
127
- return $header_html;
128
- }
129
- }
130
- // end of TVC_Admin_Page class
131
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-i18n-scripts.php DELETED
@@ -1,240 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * WP Product Feed Manager i18n Scripts Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @since 2.2.0
8
- * @version 1.1.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_i18n_Scripts' ) ) :
16
-
17
- /**
18
- * Internationalisation Class
19
- */
20
- class TVC_i18n_Scripts {
21
-
22
- /**
23
- * Localizes the javascript strings that are used on the feed settings pages
24
- *
25
- * @return string translated text
26
- */
27
- public static function tvc_feed_settings_i18n() {
28
- $pars = array(
29
- 'prohibited_feed_name_characters' => esc_html__( 'You are using characters in your file name that are not allowed!', 'tvc-product-feed-manager' ),
30
- 'feed_name_exists' => esc_html__( 'You already have a feed with this name! Please use another name.', 'tvc-product-feed-manager' ),
31
- 'invalid_url' => esc_html__( 'The url you entered is invalid. Please try again', 'tvc-product-feed-manager' ),
32
- 'save_data_failed' => esc_html__( 'Saving the data to the database has failed! Please try again.', 'tvc-product-feed-manager' ),
33
- 'no_category_required' => esc_html__( 'no category required', 'tvc-product-feed-manager' ),
34
- 'no_feed_generated' => esc_html__( 'no feed generated', 'tvc-product-feed-manager' ),
35
- 'feed_started' => esc_html__( 'Started processing your feed in the background.', 'tvc-product-feed-manager' ),
36
- 'feed_queued' => esc_html__( 'Pushed the feed into the background queue. Processing starts after all other feeds are processed.', 'tvc-product-feed-manager' ),
37
- 'feed_writing_error' => esc_html__( 'Error writing the feed. You do not have the correct authorities to write the file.', 'tvc-product-feed-manager' ),
38
- 'feed_initiation_error' => esc_html__( 'Error generating the feed. Feed generation initialization failed. Please check your error logs for more information about the issue.', 'tvc-product-feed-manager' ),
39
- /* translators: %xmlResult%: a string containing the error message */
40
- 'feed_general_error' => esc_html__( 'Generating the feed has failed! Error return code = %xmlResult%', 'tvc-product-feed-manager' ),
41
- /* translators: %feedname%: name of the feed */
42
- 'feed_status_unknown' => esc_html__( 'The status of feed %feedname% is unknown.', 'tvc-product-feed-manager' ),
43
- /* translators: %feedname%: name of the feed */
44
- 'feed_status_ready' => esc_html__( 'Product feed %feedname% is now ready. It contains %prodnr% products.', 'tvc-product-feed-manager' ),
45
- 'feed_status_still_processing' => esc_html__( 'Still processing the feed in the background. You can wait for it to finish, but you can also close this form if you want.', 'tvc-product-feed-manager' ),
46
- 'feed_status_added_to_queue' => esc_html__( 'This feed has been added to the feed queue and will be processed when it is next.', 'tvc-product-feed-manager' ),
47
- /* translators: %feedname%: name of the feed */
48
- 'feed_status_error' => esc_html__( 'Product feed %feedname% has some errors!', 'tvc-product-feed-manager' ),
49
- /* translators: %feedname%: name of the feed */
50
- 'feed_status_failed' => esc_html__( 'Product feed %feedname% has failed!', 'tvc-product-feed-manager' ),
51
- 'variation_only_for_premium' => esc_html__( 'The option to add product variations to the feed is not available in the free version. Unlock this option by upgrading to the Premium plugin. For more information goto', 'tvc-product-feed-manager' ),
52
- 'select_a_sub_category' => esc_html__( 'Select a sub-category', 'tvc-product-feed-manager' ),
53
- /* translators: %feedname%: name of the feed */
54
- 'duplicated_field' => esc_html__( 'You already have a field %fieldname% defined!', 'tvc-product-feed-manager' ),
55
- 'select_all_source_fields_warning' => esc_html__( 'Make sure to select all source fields before adding a new one!', 'tvc-product-feed-manager' ),
56
- 'fill_current_condition_warning' => esc_html__( 'Please fill in the current condition before adding a new one!', 'tvc-product-feed-manager' ),
57
- 'select_a_source_field_warning' => esc_html__( 'Please select a source field first before you select the conditions.', 'tvc-product-feed-manager' ),
58
- 'select_a_valid_source_warning' => esc_html__( 'Please select a valid source before adding a condition to that source.', 'tvc-product-feed-manager' ),
59
- 'advanced_filter_only_for_premium' => esc_html__( 'The Advanced Filter option is not available in the free version. Unlock the Advanced Filter option by upgrading to the Premium plugin. For more information goto.', 'tvc-product-feed-manager' ),
60
- 'all_products_except' => esc_html__( 'except the ones where' ),
61
- 'fill_filter_warning' => esc_html__( 'Please fill in the filter values before adding a new one' ),
62
- 'no_separator' => esc_html__( 'No separator', 'tvc-product-feed-manager' ),
63
- 'space' => esc_html__( 'space', 'tvc-product-feed-manager' ),
64
- 'comma' => esc_html__( 'comma', 'tvc-product-feed-manager' ),
65
- 'point' => esc_html__( 'point', 'tvc-product-feed-manager' ),
66
- 'semicolon' => esc_html__( 'semicolon', 'tvc-product-feed-manager' ),
67
- 'colon' => esc_html__( 'colon', 'tvc-product-feed-manager' ),
68
- 'dash' => esc_html__( 'dash', 'tvc-product-feed-manager' ),
69
- 'slash' => esc_html__( 'slash', 'tvc-product-feed-manager' ),
70
- 'backslash' => esc_html__( 'backslash', 'tvc-product-feed-manager' ),
71
- 'double_pipe' => esc_html__( 'double pipe', 'tvc-product-feed-manager' ),
72
- 'underscore' => esc_html__( 'underscore', 'tvc-product-feed-manager' ),
73
- 'other' => esc_html__( 'other', 'tvc-product-feed-manager' ),
74
- /* translators: %other%: either the word "other" or an empty space */
75
- 'all_other_products' => esc_html__( 'for all %other% products', 'tvc-product-feed-manager' ),
76
- 'edit_values' => esc_html__( 'edit values', 'tvc-product-feed-manager' ),
77
- 'and_change_values' => esc_html__( 'and change values', 'tvc-product-feed-manager' ),
78
- 'remove_value_editor' => esc_html__( 'remove value editor', 'tvc-product-feed-manager' ),
79
- 'to' => esc_html__( 'to', 'tvc-product-feed-manager' ),
80
- 'with_element_name' => esc_html__( 'with element name', 'tvc-product-feed-manager' ),
81
- 'defined_by_category_mapping_tble' => esc_html__( 'Defined by the Category Mapping Table.', 'tvc-product-feed-manager' ),
82
- 'use_advised_source' => esc_html__( 'Use advised source', 'tvc-product-feed-manager' ),
83
- 'combined_source_fields' => esc_html__( 'Combine source fields', 'tvc-product-feed-manager' ),
84
- 'category_mapping' => esc_html__( 'Category Mapping', 'tvc-product-feed-manager' ),
85
- 'select_a_source_field' => esc_html__( 'Select a source field', 'tvc-product-feed-manager' ),
86
- 'fill_with_static_value' => esc_html__( 'Fill with a static value', 'tvc-product-feed-manager' ),
87
- 'map_to_default_category' => esc_html__( 'Map to Default Category', 'tvc-product-feed-manager' ),
88
- 'use_shop_category' => esc_html__( 'Use Shop Category', 'tvc-product-feed-manager' ),
89
- 'an_empty_field' => esc_html__( 'an empty field', 'tvc-product-feed-manager' ),
90
- 'add_recommended_output' => esc_html__( 'Add recommended output', 'tvc-product-feed-manager' ),
91
- 'add_optional_output' => esc_html__( 'Add optional output', 'tvc-product-feed-manager' ),
92
- 'no_category_selected' => esc_html__( 'You\'ve not selected a Shop Category in the Category Mapping Table. With no Shop Category selected, your feed will be empty. Are you sure you still want to save this feed?', 'tvc-product-feed-manager' ),
93
- 'file_name_required' => esc_html__( 'A file name is required!', 'tvc-product-feed-manager' ),
94
- 'query_requirements' => esc_html__( 'Add at least one query in the previous change value row before adding a new row.', 'tvc-product-feed-manager' ),
95
- 'first_fill_in_change_value' => esc_html__( 'Please first fill in a change value option before adding a query to it.', 'tvc-product-feed-manager' ),
96
- );
97
-
98
- self::add_general_words( $pars );
99
-
100
- wp_localize_script(
101
- 'tvc_feed-settings-script',
102
- 'tvc_feed_settings_form_vars',
103
- $pars
104
- );
105
- }
106
-
107
- /**
108
- * Localizes the javascript strings that are used on the feed list pages
109
- *
110
- * @return string translated text
111
- */
112
- public static function tvc_list_table_i18n() {
113
- $pars = array(
114
- 'processing_the_feed' => esc_html__( 'Processing the feed, please wait...', 'tvc-product-feed-manager' ),
115
- 'processing_failed' => esc_html__( 'Processing failed, please try again', 'tvc-product-feed-manager' ),
116
- 'processing_queue' => esc_html__( 'In processing queue', 'tvc-product-feed-manager' ),
117
- 'no_data_found' => esc_html__( 'No data found', 'tvc-product-feed-manager' ),
118
- 'list_deactivate' => esc_html__( 'Auto-off', 'tvc-product-feed-manager' ),
119
- 'list_activate' => esc_html__( 'Auto-on', 'tvc-product-feed-manager' ),
120
- 'list_edit' => esc_html__( 'Edit', 'tvc-product-feed-manager' ),
121
- 'list_view' => esc_html__( 'View', 'tvc-product-feed-manager' ),
122
- 'other' => esc_html__( 'Other', 'tvc-product-feed-manager' ),
123
- 'unknown_text' => esc_html__( 'Unknown', 'tvc-product-feed-manager' ),
124
- 'on_hold' => esc_html__( 'Ready (manual)', 'tvc-product-feed-manager' ),
125
- 'processing' => esc_html__( 'Processing', 'tvc-product-feed-manager' ),
126
- 'has_errors' => esc_html__( 'Has errors', 'tvc-product-feed-manager' ),
127
- 'failed_processing' => esc_html__( 'Failed processing', 'tvc-product-feed-manager' ),
128
- 'status_ok' => esc_html__( 'Ready (auto)', 'tvc-product-feed-manager' ),
129
- /* translators: %feedname%: name of the feed */
130
- 'added_feed_copy' => esc_html__( 'Added a copy of feed %feedname% to the list.', 'tvc-product-feed-manager' ),
131
- /* translators: %feedname%: name of the feed */
132
- 'confirm_delete_feed' => esc_html__( 'Please confirm you want to delete feed %feedname%.', 'tvc-product-feed-manager' ),
133
- /* translators: %feedname%: name of the feed */
134
- 'feed_removed' => esc_html__( 'Feed %feedname% removed from the server.', 'tvc-product-feed-manager' ),
135
- 'list_language' => esc_html__( 'Feed Language' ),
136
- 'feed_not_generated' => esc_html__( 'This feed does not yet exists, please (re)generate this feed first.' ),
137
- );
138
-
139
- self::add_general_words( $pars );
140
-
141
- wp_localize_script(
142
- 'tvc_feed-list-script',
143
- 'tvc_feed_list_form_vars',
144
- $pars
145
- );
146
- }
147
-
148
- /**
149
- * Localizes the javascript strings that are used on the settings page
150
- *
151
- * @return string translated text
152
- */
153
- public static function tvc_settings_i18n() {
154
- $pars = array(
155
- 'first_enter_file_name' => esc_html__( 'First enter a file name for the backup file.', 'tvc-product-feed-manager' ),
156
- /* translators: %backup_file_name%: name of the backup file*/
157
- 'confirm_file_deletion' => esc_html__( 'Please confirm you want to delete backup %backup_file_name%.', 'tvc-product-feed-manager' ),
158
- /* translators: %backup_file_name%: name of the backup file*/
159
- 'file_deleted' => esc_html__( '%backup_file_name% deleted.', 'tvc-product-feed-manager' ),
160
- /* translators: %backup_file_name%: name of the backup file*/
161
- 'confirm_file_restoring' => esc_html__( 'Are you sure you want to restore backup %backup_file_name%? This will overwrite your current settings and feed data!', 'tvc-product-feed-manager' ),
162
- /* translators: %backup_file_name%: name of the backup file*/
163
- 'file_restored' => esc_html__( '%backup_file_name% restored', 'tvc-product-feed-manager' ),
164
- /* translators: %backup_file_name%: name of the backup file*/
165
- 'file_duplicated' => esc_html__( '%backup_file_name% duplicated', 'tvc-product-feed-manager' ),
166
- );
167
-
168
- wp_localize_script(
169
- 'tvc_setting-script',
170
- 'tvc_setting_form_vars',
171
- $pars
172
- );
173
- }
174
-
175
- /**
176
- * Localizes the javascript strings that are used in the backup list
177
- *
178
- * @return string translated text
179
- */
180
- public static function tvc_backup_list_i18n() {
181
- $pars = array(
182
- 'list_restore' => esc_html__( 'Restore', 'tvc-product-feed-manager' ),
183
- 'no_backup' => esc_html__( 'No backup found', 'tvc-product-feed-manager' ),
184
- );
185
-
186
- self::add_general_words( $pars );
187
-
188
- wp_localize_script(
189
- 'tvc_backup-list-script',
190
- 'tvc_backup_list_form_vars',
191
- $pars
192
- );
193
- }
194
-
195
- /**
196
- * Localizes the javascript strings that are used on the manage channels page
197
- *
198
- * @return string translated text
199
- */
200
- public static function tvc_manage_channels_i18n() {
201
- $pars = array(
202
- 'confirm_removing_channel' => esc_html__( 'Please confirm you want to remove this channel! Removing this channel will also remove all its feed files.', 'tvc-product-feed-manager' ),
203
- );
204
-
205
- wp_localize_script(
206
- 'tvc_data-script',
207
- 'tvc_manage_channels_vars',
208
- $pars
209
- );
210
- }
211
-
212
- /**
213
- * Adds localized words that are used on more than one page
214
- *
215
- * @param array $pars page specific words
216
- *
217
- * @return string translated text
218
- */
219
- private static function add_general_words( &$pars ) {
220
- $pars['edit'] = esc_html__( 'edit', 'tvc-product-feed-manager' );
221
- $pars['select'] = esc_html__( 'select', 'tvc-product-feed-manager' );
222
- $pars['selected'] = esc_html__( 'selected', 'tvc-product-feed-manager' );
223
- $pars['delete'] = esc_html__( 'delete', 'tvc-product-feed-manager' );
224
- $pars['remove'] = esc_html__( 'remove', 'tvc-product-feed-manager' );
225
- $pars['add'] = esc_html__( 'add', 'tvc-product-feed-manager' );
226
- $pars['if_pref'] = esc_html__( 'if', 'tvc-product-feed-manager' );
227
- $pars['or'] = esc_html__( 'or', 'tvc-product-feed-manager' );
228
- $pars['and'] = esc_html__( 'and', 'tvc-product-feed-manager' );
229
- $pars['list_duplicate'] = esc_html__( 'Clone Feed', 'tvc-product-feed-manager' );
230
- $pars['list_regenerate'] = esc_html__( 'Update Feed', 'tvc-product-feed-manager' );
231
- $pars['list_delete'] = esc_html__( 'Delete', 'tvc-product-feed-manager' );
232
- $pars['ok'] = esc_html__( 'Ready (auto)', 'tvc-product-feed-manager' );
233
- }
234
-
235
- }
236
-
237
-
238
- // end of TVC_i18n_Scripts class
239
-
240
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-list-table.php DELETED
@@ -1,863 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC List Table Class.
5
- *
6
- * @package TVC Product Feed Manager/User Interface/Classes
7
- * @version 1.4.0
8
- */
9
- if (!defined('ABSPATH')) {
10
- exit;
11
- }
12
-
13
- if (!class_exists('TVC_List_Table')) :
14
-
15
- /**
16
- * List Table Class
17
- */
18
- class TVC_List_Table {
19
-
20
- private $_column_titles = array();
21
- private $_table_id;
22
- private $_table_id_string;
23
- private $_table_list;
24
- private $queries;
25
- private $curl_url;
26
- private $returnUrl;
27
- private $theURL;
28
- private $merchantID;
29
- private $merchant_feeds = array();
30
-
31
- public function __construct() {
32
-
33
- $this->queries = new TVC_Queries();
34
- $this->_table_id = '';
35
- $this->_table_id_string = '';
36
- //$this->_table_list = $this->queries->get_feeds_list();
37
- $this->merchantID = $this->queries->get_set_merchant_id();
38
- $this->_table_feeds = $this->queries->get_feeds_list();
39
- $this->merchant_feeds = $this->tvc_merchant_fetch_all_feeds();
40
- $this->_table_list = $this->merge_all_feeds();
41
- $this->curl_url = "https://www.googleapis.com/content/v2/accounts/authinfo?scope=https://www.googleapis.com/auth/content";
42
-
43
- $this->returnUrl = $_SERVER['REQUEST_URI'];
44
- $this->theURL = "http://plugins.tatvic.com/tat_ga/ga_rdr_gmc.php?return_url=" . $_SERVER['HTTP_HOST'] . $this->returnUrl;
45
-
46
- add_option('wp_enqueue_scripts', TVC_i18n_Scripts::tvc_feed_settings_i18n());
47
- add_option('wp_enqueue_scripts', TVC_i18n_Scripts::tvc_list_table_i18n());
48
- }
49
-
50
- public function generateAccessToken($access_token, $refresh_token) {
51
- $request = "https://www.googleapis.com/oauth2/v1/tokeninfo?"
52
- . "access_token=" . $access_token;
53
-
54
- $ch = curl_init();
55
- curl_setopt($ch, CURLOPT_URL, $request);
56
- curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
57
- curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE);
58
- $response = curl_exec($ch);
59
- $result = json_decode($response);
60
-
61
- if (isset($result->error) && $result->error) {
62
- $credentials_file = ENHANCAD_PLUGIN_DIR . 'includes/setup/json/client-secrets.json';
63
- $str = file_get_contents($credentials_file);
64
- $credentials = $str ? json_decode($str, true) : [];
65
- $url = 'https://www.googleapis.com/oauth2/v4/token';
66
- $header = array("content-type: application/json");
67
- $clientId = $credentials['web']['client_id'];
68
- $clientSecret = $credentials['web']['client_secret'];
69
- $refreshToken = $refresh_token;
70
- $data = [
71
- "grant_type" => 'refresh_token',
72
- "client_id" => $clientId,
73
- 'client_secret' => $clientSecret,
74
- 'refresh_token' => $refreshToken,
75
- ];
76
-
77
- $postData = json_encode($data);
78
- $ch = curl_init();
79
- curl_setopt_array($ch, array(
80
- CURLOPT_URL => $url, //esc_url($this->curl_url),
81
- CURLOPT_RETURNTRANSFER => true,
82
- CURLOPT_TIMEOUT => 0,
83
- CURLOPT_HTTPHEADER => $header,
84
- CURLOPT_POSTFIELDS => $postData
85
- ));
86
- $response = curl_exec($ch);
87
- $response = json_decode($response);
88
- return $response->access_token;
89
- } else {
90
- return $access_token;
91
- }
92
- }
93
-
94
- /**
95
- * Sets the column titles
96
- *
97
- * @param array of strings containing the column titles
98
- */
99
- public function set_column_titles($titles) {
100
- if (!empty($titles)) {
101
- $this->_column_titles = $titles;
102
- }
103
- }
104
-
105
- public function set_table_id($id) {
106
- if ($id !== $this->_table_id) {
107
- $this->_table_id = $id;
108
- $this->_table_id_string = ' id="' . $id . '"';
109
- }
110
- }
111
-
112
- public function display() {
113
-
114
- if (isset($_GET['access_token'])) {
115
- $this->admin_notice_signin_success();
116
- echo $this->feed_home_page();
117
- }
118
- if (isset($_POST['add_conversion_tag'])) {
119
- echo "<script>parent.location='admin.php?page=tvc-configuration-page'</script>";
120
- }
121
- if (isset($_POST['create_campaign'])) {
122
- $campaign_name = $_POST['campaign_name'];
123
- $campaign_budget = $_POST['campaign_budget'];
124
-
125
- include(ENHANCAD_PLUGIN_DIR . 'includes/setup/SmartShoppingCampaign.php');
126
- $campaignClsObj = new SmartShoppingCampaign();
127
- $campaignClsObj->createConversionAction();
128
- $response = $campaignClsObj->createSmartShoppingCampaign($campaign_name, $campaign_budget);
129
- if (isset($response['error'])) {
130
- $class = 'notice notice-error';
131
- $message = esc_html__(isset($response['error']->message) ? $response['error']->message : $response['error'], 'sample-text-domain');
132
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Error : ' . $message));
133
- } else {
134
- $class = 'notice notice-success';
135
- $message = esc_html__('Smart Shopping Campaign Created Successfully with Resource name ' . $response, 'sample-text-domain');
136
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
137
- }
138
- }
139
- echo '<table class="wp-list-table tablepress widefat fixed posts" id="feedlisttable">';
140
-
141
- echo $this->table_header();
142
-
143
- echo $this->table_body();
144
-
145
- echo $this->table_footer();
146
-
147
- echo '</table>';
148
-
149
- // echo $this->create_campaign_modal();
150
-
151
- echo $this->conversion_modal();
152
- }
153
-
154
- /**
155
- * @return array
156
- * Get woocommerce default set country
157
- */
158
- private function woo_country() {
159
- // The country/state
160
- $store_raw_country = get_option('woocommerce_default_country');
161
- // Split the country/state
162
- $split_country = explode(":", $store_raw_country);
163
- return $split_country;
164
- }
165
-
166
- /**
167
- * @return mixed
168
- */
169
- private function get_currency_symbol() {
170
- $woo_country = $this->woo_country();
171
- $country = (!empty($woo_country)) ? $woo_country[0] : 'US';
172
- $getCurrency = file_get_contents(ENHANCAD_PLUGIN_DIR . "includes/setup/json/currency.json");
173
- $contData = json_decode($getCurrency);
174
- return get_woocommerce_currency_symbol($contData->{$country});
175
- }
176
-
177
- private function conversion_modal() {
178
- $html = '';
179
- $html .= '<form method="post">
180
- <div class="modal fade" id="conversionModal" tabindex="-1" role="dialog" aria-labelledby="modal-title" aria-hidden="true">
181
- <div class="modal-dialog modal-dialog-centered" role="document">
182
- <div class="modal-content">
183
- <div class="modal-body">
184
- <button type="button" class="close gmc_tandc_close" data-dismiss="modal" aria-label="Close">
185
- <span aria-hidden="true">&times;</span>
186
- </button>
187
- <h2 class="modal-title lead" style="font-weight: 400;">Conversion Tracking Tags</h2>
188
- <br>
189
- <p><b>Please note: </b>if you already have Google Ads Conversion Actions with <a href="https://support.google.com/google-ads/answer/6095947" target="_blank">transaction-specific conversion values</a> configured on your site for this Google Ads account, then you do not need to set new conversion tags on your site.</p>
190
- </div>
191
- <div class="form-group text-left">
192
- <input class="form-check-input" type="checkbox" name="addConversion" id="feed-form-checkbox" value="1" checked>&nbsp;&nbsp;
193
- <label class="form-check-label ml-5 p-1" for="addConversion">Yes, set new conversion tracking tags on my site</label>
194
- </div>
195
- <div class="mx-auto p-3">
196
- <button type="submit" class="btn btn-primary" id="addConversionTag" name="add_conversion_tag" >Continue</button>
197
- </div>
198
- </div>
199
- </div>
200
- </div>
201
- </form>';
202
- return $html;
203
- }
204
-
205
- private function create_campaign_modal() {
206
-
207
- $currency = $this->get_currency_symbol();
208
- $html = '';
209
- $html .= '<form method="post">
210
- <div class="modal fade" id="createCampaignModal" tabindex="-1" role="dialog" aria-labelledby="modal-title" aria-hidden="true">
211
- <div class="modal-dialog modal-dialog-centered" role="document">
212
-
213
- <div class="modal-content">
214
- <div class="modal-body">
215
- <button type="button" class="close gmc_tandc_close" data-dismiss="modal" aria-label="Close">
216
- <span aria-hidden="true">&times;</span>
217
- </button>
218
- <h2 class="modal-title lead" style="font-weight: 400;">Create a new Smart Shopping Campaign</h2>
219
- </div>
220
- <div class="form-group row" style="margin-bottom: 0">
221
- <div class="col-md-12 row">
222
- <label for="campaign-name" class="col-md-5 ml-3 mt-2 text-left">Campaign name </label>
223
- <input type="text" class="form-control col-md-6" name="campaign_name" id="campaign-name" required>
224
- </div>
225
- <div class="col-md-12 row mt-2">
226
- <label for="campaign-budget" class="col-md-5 ml-3 mt-2 text-left">Campaign Budget (' . $currency . ') </label>
227
- <input type="text" class="form-control col-md-6" name="campaign_budget" id="campaign-budget" required>
228
- </div>
229
- </div>
230
-
231
- <div class="mx-auto p-3">
232
- <button type="submit" class="btn btn-primary" id="create_campaign" name="create_campaign">Save Campaign</button>
233
- </div>
234
- </div>
235
-
236
- </div>
237
- </div>
238
- </form>';
239
-
240
- return $html;
241
- }
242
-
243
- private function table_header() {
244
- $html = '<thead><tr>';
245
-
246
- foreach ($this->_column_titles as $title) {
247
- $html .= '<th id="tvc-feed-list-table-header-column-' . strtolower($title) . '">' . $title . '</th>';
248
- }
249
-
250
- $html .= '</tr></thead>';
251
-
252
- return $html;
253
- }
254
-
255
- private function table_footer() {
256
- $html = '<tfoot><tr>';
257
-
258
- foreach ($this->_column_titles as $title) {
259
- $html .= '<th>' . $title . '</th>';
260
- }
261
-
262
- $html .= '</tr></tfoot>';
263
-
264
- return $html;
265
- }
266
-
267
- private function getColorByStatus($status = '') {
268
-
269
- if ($status == 'ok' || $status == 'success' || $status == 'none') {
270
- return '#0073AA';
271
- } else if ($status == 'on_hold') {
272
- return '#0173AA';
273
- } else if ($status == 'processing' || $status == 'in progress') {
274
- return '#0000FF';
275
- } else if ($status == 'in_processing_queue') {
276
- return '#00CCFF';
277
- } else if ($status == 'has_errors') {
278
- return '#FF0000';
279
- } else if ($status == 'failed_processing' || $status == 'failure') {
280
- return '#FF3300';
281
- } else {
282
- return "#6549F7";
283
- }
284
- }
285
-
286
- private function table_body() {
287
- $html = '<tbody' . $this->_table_id_string . '>';
288
- $alternator = 0;
289
- $nr_products = '';
290
- $show_type_column = apply_filters('tvc_special_feeds_add_on_active', false);
291
- $feed_types = tvc_list_feed_type_text();
292
- // foreach ($this->merchant_feeds as $merchant_feed) {
293
- // $html .= '<tr id="tvc-feed-row"';
294
- // $html .= 0 === ( $alternator % 2 ) ? ' class="tvc-feed-row alternate">' : ' class="tvc-feed-row">';
295
- // $html .= '<td id="title-' . $merchant_feed->id . '" value="' . $merchant_feed->id . '">' . $merchant_feed->name . '</td>';
296
- // $html .= '<td id="url">' . ($merchant_feed->fetchSchedule->fetchUrl) . '</td>';
297
- // $html .= $this->tvc_merchant_feed_api( esc_url($merchant_feed->fetchSchedule->fetchUrl),$merchant_feed->id );
298
- // $html .= '<td id="updated-' . $merchant_feed->id . '">' .$merchant_feed->id . '</td>';
299
- // $html .= '<td id="url">' . esc_url($merchant_feed->fetchSchedule->fetchUrl) . '</td>';
300
- // $html .= '<td id="url">' . esc_url($merchant_feed->id) . '</td>';
301
- // $html .= '<td id="url">' . esc_url($merchant_feed->id) . '</td>';
302
- // // $html .= '<td id="url">' . esc_url($merchant_feed->id) . '</td>';
303
- // $html .= '</tr>';
304
- //
305
- // $alternator++;
306
- // }
307
- foreach ($this->_table_list as $list_item) {
308
- $feed_ready_status = ('on_hold' === $list_item->status || 'ok' === strtolower($list_item->status) || 'success' === $list_item->status);
309
- $feed_name_id = tvc_convert_string_with_spaces_to_lower_case_string_with_dashes($list_item->title);
310
-
311
- if ($feed_ready_status) {
312
- $nr_products = $list_item->products;
313
- } elseif ('processing' === $list_item->status || 'in progress' === $list_item->status) {
314
- $nr_products = esc_html__('Processing the feed, please wait...', 'tvc-product-feed-manager');
315
- } elseif ('failed_processing' === $list_item->status || 'in_processing_queue' === $list_item->status || 'none' === $list_item->status || 'failure' === $list_item->status) {
316
- $nr_products = esc_html__('Unknown', 'tvc-product-feed-manager');
317
- }
318
-
319
- $color = $list_item->type == 'local' ? $list_item->color : $this->getColorByStatus($list_item->status);
320
-
321
- $html .= '<tr id="tvc-feed-row"';
322
- $html .= 0 === ($alternator % 2) ? ' class="tvc-feed-row alternate">' : ' class="tvc-feed-row">'; // alternate background color per row
323
- $html .= '<td id="title-' . $list_item->product_feed_id . '" value="' . $feed_name_id . '">' . $list_item->title . '</td>';
324
- $html .= '<td id="url">' . esc_url($list_item->url) . '</td>';
325
-
326
- $html .= $list_item->type == 'local' ? $this->tvc_merchant_feed_api(esc_url($list_item->url), $list_item->product_feed_id) : '<td></td>';
327
-
328
- $html .= '<td id="updated-' . $list_item->product_feed_id . '">' . $list_item->updated . '</td>';
329
- $html .= '<td id="products-' . $list_item->product_feed_id . '"><a href="https://merchants.google.com/mc/items?a=' . $this->merchantID . '" target="_blank">' . $nr_products . '</a></td>';
330
- $html .= $show_type_column ? '<td id="type-' . $list_item->product_feed_id . '">' . $feed_types[$list_item->feed_type_id] . '</td>' : '';
331
- $html .= '<td id="feed-status-' . $list_item->product_feed_id . '" value="' . $list_item->status . '" style="color:' . $color . '"><strong>';
332
- $html .= $list_item->type == 'local' ? $this->list_status_text($list_item->status) : $this->list_merchant_feeds_status_text($list_item->status);
333
- $html .= '</strong></td>';
334
- $html .= '<td id="actions-' . $list_item->product_feed_id . '">';
335
-
336
- if ($list_item->type == 'local') {
337
- if ($feed_ready_status) {
338
- $html .= $this->feed_ready_action_links($list_item->product_feed_id, $list_item->url, $list_item->status, $list_item->title, $feed_types[$list_item->feed_type_id]);
339
- } else {
340
- $html .= $this->feed_not_ready_action_links($list_item->product_feed_id, $list_item->url, $list_item->title, $feed_types[$list_item->feed_type_id]);
341
- }
342
- }
343
-
344
-
345
- $html .= '</td>';
346
- $html .= '</tr>';
347
-
348
- $alternator++;
349
- }
350
-
351
- $html .= '</tbody>';
352
-
353
- return $html;
354
- }
355
-
356
- private function merge_all_feeds() {
357
- $feeds_data = [];
358
- if (!empty($this->_table_feeds)) {
359
- $feeds = [];
360
- $localFeeds = [];
361
- foreach ($this->_table_feeds as $list_item) {
362
-
363
- if (!empty($this->merchant_feeds)) {
364
- foreach ($this->merchant_feeds as $merchant_feed) {
365
-
366
- if (isset($list_item->gmc_feed_id) && ($merchant_feed->id == $list_item->gmc_feed_id)) {
367
-
368
- $localFeeds['id'] = $list_item->product_feed_id;
369
- $localFeeds['title'] = $list_item->title;
370
- $localFeeds['type'] = 'local';
371
- $localFeeds['url'] = $list_item->url;
372
- $localFeeds['status'] = $list_item->status;
373
- $localFeeds['updated'] = $list_item->updated;
374
- $localFeeds['product_feed_id'] = $list_item->product_feed_id;
375
- $localFeeds['products'] = $list_item->products;
376
- $localFeeds['color'] = $list_item->color;
377
- $localFeeds['feed_type_id'] = $list_item->feed_type_id;
378
- } else {
379
- $feeds['id'] = $merchant_feed->id;
380
- $feeds['title'] = $merchant_feed->name;
381
- $feeds['type'] = 'merchant';
382
- $feeds['url'] = str_replace('drive://', 'https://drive.google.com/', $merchant_feed->fetchSchedule->fetchUrl);
383
- $feeds['status'] = $merchant_feed->status;
384
- $feeds['updated'] = $merchant_feed->lastUploaded;
385
- $feeds['product_feed_id'] = $merchant_feed->id;
386
- $feeds['products'] = $merchant_feed->products;
387
- $feeds['color'] = '';
388
- $feeds['feed_type_id'] = '';
389
-
390
- $localFeeds['id'] = $list_item->product_feed_id;
391
- $localFeeds['title'] = $list_item->title;
392
- $localFeeds['type'] = 'local';
393
- $localFeeds['url'] = $list_item->url;
394
- $localFeeds['status'] = $list_item->status;
395
- $localFeeds['updated'] = $list_item->updated;
396
- $localFeeds['product_feed_id'] = $list_item->product_feed_id;
397
- $localFeeds['products'] = $list_item->products;
398
- $localFeeds['color'] = $list_item->color;
399
- $localFeeds['feed_type_id'] = $list_item->feed_type_id;
400
- }
401
- }
402
- } else {
403
- $localFeeds['id'] = $list_item->product_feed_id;
404
- $localFeeds['title'] = $list_item->title;
405
- $localFeeds['type'] = 'local';
406
- $localFeeds['url'] = $list_item->url;
407
- $localFeeds['status'] = $list_item->status;
408
- $localFeeds['updated'] = $list_item->updated;
409
- $localFeeds['product_feed_id'] = $list_item->product_feed_id;
410
- $localFeeds['products'] = $list_item->products;
411
- $localFeeds['color'] = $list_item->color;
412
- $localFeeds['feed_type_id'] = $list_item->feed_type_id;
413
- }
414
- if (!empty($localFeeds)) {
415
- array_push($feeds_data, (object) $localFeeds);
416
- }
417
- }
418
- if (!empty($feeds)) {
419
- array_push($feeds_data, (object) $feeds);
420
- }
421
- } else {
422
- if (!empty($this->merchant_feeds)) {
423
- foreach ($this->merchant_feeds as $merchant_feed) {
424
- $feeds = [];
425
- $feeds['id'] = $merchant_feed->id;
426
- $feeds['title'] = $merchant_feed->name;
427
- $feeds['type'] = 'merchant';
428
- $feeds['url'] = str_replace('drive://', 'https://drive.google.com/', $merchant_feed->fetchSchedule->fetchUrl);
429
- $feeds['status'] = $merchant_feed->status;
430
- $feeds['updated'] = $merchant_feed->lastUploaded;
431
- $feeds['product_feed_id'] = $merchant_feed->id;
432
- $feeds['products'] = $merchant_feed->products;
433
- array_push($feeds_data, (object) $feeds);
434
- }
435
- }
436
- }
437
-
438
- return $feeds_data;
439
- }
440
-
441
- private function list_status_text($status) {
442
-
443
- switch ($status) {
444
- case 'OK': // sometimes the status is stored in capital letters
445
- case 'ok':
446
- return esc_html__('Ready (auto)', 'tvc-product-feed-manager');
447
-
448
- case 'on_hold':
449
- return esc_html__('Ready (manual)', 'tvc-product-feed-manager');
450
-
451
- case 'processing':
452
- return esc_html__('Processing', 'tvc-product-feed-manager');
453
-
454
- case 'in_processing_queue':
455
- return esc_html__('In processing queue', 'tvc-product-feed-manager');
456
-
457
- case 'has_errors':
458
- return esc_html__('Has errors', 'tvc-product-feed-manager');
459
-
460
- case 'failed_processing':
461
- return esc_html__('Failed processing', 'tvc-product-feed-manager');
462
-
463
- default:
464
- return esc_html__('Unknown', 'tvc-product-feed-manager');
465
- }
466
- }
467
-
468
- /**
469
- * Generates the code for the Action buttons used in the feed list row where the feed is in ready mode.
470
- * This function is the PHP equal for the feedReadyActions() function in the tvc_feed-list.js file.
471
- *
472
- * @param string $feed_id
473
- * @param string $feed_url
474
- * @param string $status
475
- * @param string $title
476
- * @param string $feed_type
477
- *
478
- * @return string with the html code
479
- */
480
- private function feed_ready_action_links($feed_id, $feed_url, $status, $title, $feed_type) {
481
- $file_exists = 'No feed generated' !== $feed_url;
482
- $url_strings = explode('/', $feed_url);
483
- $file_name = stripos($feed_url, '/') ? end($url_strings) : $title;
484
- $change_status = 'ok' === strtolower($status) ? esc_html__('Auto-off', 'tvc-product-feed-manager') : esc_html__('Auto-on', 'tvc-product-feed-manager');
485
- $feed_tab_link = tvc_convert_string_with_spaces_to_lower_case_string_with_dashes($feed_type);
486
- $action_id = tvc_convert_string_with_spaces_to_lower_case_string_with_dashes($title);
487
-
488
- $html = '<strong><a href="javascript:void(0);" id="tvc-edit-' . $action_id . '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' . $feed_tab_link . '&id=' . $feed_id . '\'">' . esc_html__('Edit', 'tvc-product-feed-manager') . '</a>';
489
- $html .= $file_exists ? ' | <a href="javascript:void(0);" id="tvc-view-' . $action_id . '-action" onclick="tvc_viewFeed(\'' . $feed_url . '\')">' . esc_html__('View', 'tvc-product-feed-manager') . '</a>' : '';
490
- $html .= ' | <a href="javascript:void(0);" id="tvc-delete-' . $action_id . '-action" onclick="tvc_deleteSpecificFeed(' . $feed_id . ', \'' . $file_name . '\')">' . esc_html__('Delete', 'tvc-product-feed-manager') . '</a>';
491
- $html .= $file_exists ? '<a href="javascript:void(0);" id="tvc-deactivate-' . $action_id . '-action" onclick="tvc_deactivateFeed(' . $feed_id . ')" id="feed-status-switch-' . $feed_id . '"> | ' . $change_status . '</a>' : '';
492
- $html .= ' | <a href="javascript:void(0);" id="tvc-duplicate-' . $action_id . '-action" onclick="tvc_duplicateFeed(' . $feed_id . ', \'' . $title . '\')">' . esc_html__('Clone Feed', 'tvc-product-feed-manager') . '</a>';
493
- $html .= 'Product Feed' === $feed_type ? ' | <a href="javascript:void(0);" id="tvc-regenerate-' . $action_id . '-action" onclick="tvc_regenerateFeed(' . $feed_id . ')">' . esc_html__('Update Feed', 'tvc-product-feed-manager') . '</a></strong>' : '';
494
- return $html;
495
- }
496
-
497
- /**
498
- * Generates the code for the Action buttons used in the feed list row where the feed is in processing or error mode.
499
- * This function is the PHP equal for the feedNotReadyActions() function in the tvc_feed-list.js file.
500
- *
501
- * @param string $feed_id
502
- * @param string $feed_url
503
- * @param string $title
504
- * @param string $feed_type
505
- *
506
- * @return string with the html code
507
- */
508
- private function feed_not_ready_action_links($feed_id, $feed_url, $title, $feed_type) {
509
- if (stripos($feed_url, '/')) {
510
- $url_array = explode('/', $feed_url);
511
- $file_name = end($url_array);
512
- } else {
513
- $file_name = $title;
514
- }
515
-
516
- $feed_tab_link = tvc_convert_string_with_spaces_to_lower_case_string_with_dashes($feed_type);
517
- $action_id = tvc_convert_string_with_spaces_to_lower_case_string_with_dashes($title);
518
-
519
- $html = '<strong><a href="javascript:void(0);" id="tvc-edit-' . $action_id . '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' . $feed_tab_link . '&id=' . $feed_id . '\'">' . esc_html__('Edit', 'tvc-product-feed-manager') . '</a>';
520
- $html .= ' | <a href="javascript:void(0);" id="tvc-delete-' . $action_id . '-action" onclick="tvc_deleteSpecificFeed(' . $feed_id . ', \'' . $file_name . '\')">' . esc_html__('Delete', 'tvc-product-feed-manager') . '</a>';
521
- $html .= 'Product Feed' === $feed_type ? ' | <a href="javascript:void(0);" id="tvc-regenerate-' . $action_id . '-action" onclick="tvc_regenerateFeed(' . $feed_id . ')">' . esc_html__('Update Feed', 'tvc-product-feed-manager') . '</a></strong>' : '';
522
- $html .= $this->feed_status_checker_script($feed_id);
523
- return $html;
524
- }
525
-
526
- private function tvc_merchant_feed_api($feed_url, $feed_id) {
527
-
528
- if (!isset($_SESSION['access_token']) && isset($_GET['access_token'])) {
529
- $this->admin_notice_signin_success();
530
- setcookie('access_token', $_GET['access_token']);
531
- }
532
- $this->api_data($feed_url, $feed_id);
533
- $gmcID = $this->queries->getGmcFeedId($feed_id);
534
- if ($gmcID[0]->gmc_feed_id != 0) {
535
- return '<td><strong><a href="javascript:void(0);" name="submit" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=feed-list&url=' . $feed_url . '&id=' . $feed_id . '\'">' . esc_html__('Update Feed ' . $gmcID[0]->gmc_feed_id, 'tvc-product-feed-manager') . '</a></strong></td>';
536
- } else {
537
- return '<td><strong><a href="javascript:void(0);" name="submit" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=feed-list&url=' . $feed_url . '&id=' . $feed_id . '\'">' . esc_html__('Push Feed', 'tvc-product-feed-manager') . '</a></strong></td>';
538
- }
539
- }
540
-
541
- public function tvc_merchant_fetch_all_feeds() {
542
- $access_token = $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token']);
543
- if (!empty($access_token)) {
544
-
545
- try {
546
- $header = array("Authorization: Bearer " . $access_token, "content-type: application/json");
547
- $ch = curl_init();
548
- $fetchFeedsURL = esc_url("https://www.googleapis.com/content/v2.1/" . $this->merchantID . "/datafeeds");
549
- curl_setopt_array($ch, array(
550
- CURLOPT_URL => $fetchFeedsURL,
551
- CURLOPT_RETURNTRANSFER => true,
552
- CURLOPT_TIMEOUT => 20,
553
- CURLOPT_HTTPHEADER => $header
554
- ));
555
- $response = json_decode(curl_exec($ch));
556
- if (isset($response->error) && $response->error->code == '401') {
557
- /* $message = $response->error->message;
558
- $reason = $response->error->errors[0]->reason;
559
- $this->admin_notice_response_error($message, $reason);
560
- include(ENHANCAD_PLUGIN_DIR . 'includes/setup/tvc-configuration-page.php');
561
- new Configuration();
562
- exit(1); */
563
- return [];
564
- } else {
565
- if (!empty($response->resources) && $response->kind == "content#datafeedsListResponse") {
566
- $statuses = $this->tvc_merchant_fetch_feed_status();
567
-
568
- if ($statuses && count($statuses) > 0) {
569
- foreach ($response->resources as $key => &$resource) {
570
- if ($resource->id == $statuses[$key]->datafeedId) {
571
- $resource->status = $statuses[$key]->processingStatus;
572
- $resource->products = isset($statuses[$key]->itemsValid) ? $statuses[$key]->itemsValid : '';
573
- $resource->lastUploaded = isset($statuses[$key]->lastUploadDate) ? $statuses[$key]->lastUploadDate : '';
574
- }
575
- }
576
- }
577
- // print_r($response->resources);
578
- return $response->resources;
579
- }
580
- }
581
- } catch (Exception $e) {
582
- echo $e->getMessage();
583
- return [];
584
- }
585
- } else {
586
- return [];
587
- }
588
- }
589
-
590
- public function tvc_merchant_fetch_feed_status() {
591
- $access_token = $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token']);
592
- if (!empty($access_token)) {
593
-
594
- try {
595
- $header = array("Authorization: Bearer " . $access_token, "content-type: application/json");
596
- $ch = curl_init();
597
- $fetchFeedsURL = esc_url("https://www.googleapis.com/content/v2.1/" . $this->merchantID . "/datafeedstatuses");
598
- curl_setopt_array($ch, array(
599
- CURLOPT_URL => $fetchFeedsURL,
600
- CURLOPT_RETURNTRANSFER => true,
601
- CURLOPT_TIMEOUT => 20,
602
- CURLOPT_HTTPHEADER => $header
603
- ));
604
- $response = json_decode(curl_exec($ch));
605
- if (isset($response->error) && $response->error->code == '401') {
606
- $message = $response->error->message;
607
- $reason = $response->error->errors[0]->reason;
608
- $this->admin_notice_response_error($message, $reason);
609
- include(ENHANCAD_PLUGIN_DIR . 'includes/setup/tvc-configuration-page.php');
610
- new Configuration();
611
- exit(1);
612
- } else {
613
- if (!empty($response->resources) && $response->kind == "content#datafeedstatusesListResponse") {
614
- return $response->resources;
615
- }
616
- }
617
- } catch (Exception $e) {
618
- echo $e->getMessage();
619
- return [];
620
- }
621
- }
622
- }
623
-
624
- private function list_merchant_feeds_status_text($status) {
625
- switch ($status) {
626
- case 'failure':
627
- return esc_html__('Failed processing', 'tvc-product-feed-manager');
628
-
629
- case 'in progress':
630
- return esc_html__('Processing', 'tvc-product-feed-manager');
631
-
632
- case 'none':
633
- return esc_html__('Ready (manual)', 'tvc-product-feed-manager');
634
-
635
- case 'success':
636
- return esc_html__('Ready (auto)', 'tvc-product-feed-manager');
637
-
638
- default:
639
- return esc_html__('Unknown', 'tvc-product-feed-manager');
640
- }
641
- }
642
-
643
- public function api_data($feed_url, $feed_id) {
644
-
645
- $feedUrl = isset($_GET['url']) ? $_GET['url'] : '';
646
-
647
- if ($feedUrl == $feed_url) {
648
- if ($feed_id != '') {
649
- $countryID = $this->queries->getCountryID($feed_id);
650
- $countryCode = $this->queries->getCountryCode($countryID);
651
- $scheduleTime = $this->queries->getScheduleTime($feed_id);
652
- $feedData = $this->queries->getFeedData($feed_id);
653
- $time = $scheduleTime[0]->schedule;
654
- $Time = explode(":", $time);
655
- $dayofweek = strtolower(jddayofweek($Time[0], 1));
656
- $items = array();
657
- $gmcFeedId = $this->queries->getGmcFeedId($feed_id);
658
- if (!empty($this->merchantID)) {
659
- $timeZone = get_option('timezone_string');
660
- $hour = intval($Time[1]);
661
- $gmcid = intval(trim($gmcFeedId[0]->gmc_feed_id));
662
- if ($gmcid != 0) {
663
- $items["id"] = $gmcid;
664
- }
665
- $items["contentType"] = "products";
666
- $items["fileName"] = isset($feedData[0]->title) ? $feedData[0]->title : 'Unname File';
667
- $items["name"] = isset($feedData[0]->feed_title) ? $feedData[0]->feed_title : 'Unname Feed';
668
- $items["fetchSchedule"] = array(
669
- "weekday" => isset($dayofweek) ? $dayofweek : "sunday",
670
- "hour" => isset($hour) ? $hour : 0,
671
- "timeZone" => trim($timeZone),
672
- "fetchUrl" => trim($feedUrl),
673
- "paused" => false
674
- );
675
- $items["kind"] = "content#datafeed";
676
- $items["format"]["quotingMode"] = "value quoting";
677
- $items["targets"] = array([
678
- "country" => $countryCode[0]->name_short,
679
- "language" => "en",
680
- "includedDestinations" => array(
681
- "SurfacesAcrossGoogle"
682
- )
683
- ]
684
- );
685
- $pushData = json_encode($items);
686
- $access_token = $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token']);
687
- if (!empty($access_token)) {
688
- $header = array("Authorization: Bearer " . $access_token, "content-type: application/json");
689
- $ch = curl_init();
690
- if ($gmcid != 0) {
691
- $insertURL = esc_url("https://www.googleapis.com/content/v2.1/" . $this->merchantID . "/datafeeds/" . $gmcid);
692
-
693
- curl_setopt_array($ch, array(
694
- CURLOPT_URL => $insertURL,
695
- CURLOPT_RETURNTRANSFER => true,
696
- CURLOPT_TIMEOUT => 20,
697
- CURLOPT_HTTPHEADER => $header,
698
- CURLOPT_PUT => $pushData
699
- ));
700
- } else {
701
- $insertURL = esc_url("https://www.googleapis.com/content/v2.1/" . $this->merchantID . "/datafeeds");
702
- curl_setopt_array($ch, array(
703
- CURLOPT_URL => $insertURL,
704
- CURLOPT_RETURNTRANSFER => true,
705
- CURLOPT_TIMEOUT => 20,
706
- CURLOPT_HTTPHEADER => $header,
707
- CURLOPT_POSTFIELDS => $pushData
708
- ));
709
- }
710
-
711
- try {
712
- $response = json_decode(curl_exec($ch));
713
-
714
- $feedID = trim($response->id);
715
- $feedName = !empty($response->name) ? $response->name : '';
716
- if ($feedID != '') {
717
- $this->queries->insertGmcFeedId($feedID, $feed_id);
718
- }
719
- if (isset($response->error) && $response->error->code == '400' || $response->error->code == '500' || $response->error->code == '409' || $response->error->code == '404') {
720
- $message = $response->error->message;
721
- $reason = $response->error->errors[0]->reason;
722
- $this->admin_notice_response_error($message, $reason);
723
- } else {
724
- if ($_GET['status'] == 'update' && $_GET['tab'] == 'feed-list') {
725
- $this->api_update__success($feedName, $feedID);
726
- echo $this->product_feed_redirect_url($feedID);
727
- }
728
- if ($_GET['tab'] == 'feed-list' && !isset($_GET['status'])) {
729
- $this->admin_notice__success($feedName, $feedID);
730
- echo $this->feed_list_redirect_url();
731
- }
732
- if ($_GET['tab'] == 'product-feed' && $_GET['id'] == $feed_id && !isset($_GET['status'])) {
733
- $this->admin_notice__success($feedName, $feedID);
734
- echo $this->product_feed_redirect_url($feedID);
735
- }
736
- }
737
- } catch (Exception $e) {
738
- echo $e->getMessage();
739
- }
740
- } else {
741
-
742
- echo "<script>parent.location='admin.php?page=tvc-configuration-page'</script>";
743
- }
744
- }
745
- }
746
- }
747
- }
748
-
749
- public static function feed_list_redirect_url() {
750
- return "<script>parent.location='admin.php?page=tvc-product-feed-manager&tab=feed-list'</script>";
751
- }
752
-
753
- public static function product_feed_redirect_url($feedID) {
754
- return "<script>parent.location='admin.php?page=tvc-product-feed-manager&tab=product-feed&id='.$feedID</script>";
755
- }
756
-
757
- public static function feed_home_page() {
758
- return "<script>parent.location='admin.php?page=tvc-product-feed-manager'</script>";
759
- }
760
-
761
- private static function admin_notice__success($feedName, $feedID) {
762
- $class = 'notice notice-success';
763
- $message = esc_html__('Products feed name ' . ucwords($feedName) . ' Successfully Generated and Feed ID is ' . $feedID, 'sample-text-domain');
764
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
765
- }
766
-
767
- private static function admin_notice_signin_success() {
768
- $class = 'notice notice-success';
769
- $message = esc_html__('You are successfully logged in', 'sample-text-domain');
770
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
771
- }
772
-
773
- private static function admin_notice_signin_required() {
774
- $class = 'notice notice-error';
775
- $message = esc_html__('Google Sign In required for API Update!', 'sample-text-domain');
776
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
777
- }
778
-
779
- private static function api_update__success($feedName, $feedID) {
780
- $class = 'notice notice-success';
781
- $message = esc_html__('Products feed name ' . ucwords($feedName) . ' Successfully Update', 'sample-text-domain');
782
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
783
- }
784
-
785
- private static function api_item_update_error($errMessage) {
786
- $class = 'notice notice-error';
787
- $message = esc_html__($errMessage, 'sample-text-domain');
788
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html($message));
789
- }
790
-
791
- private static function admin_notice_response_error($message, $reason) {
792
- $class = 'notice notice-error';
793
- $message = esc_html__($message, 'sample-text-domain');
794
- printf('<div class="%1$s"><p>%2$s</p></div>', esc_attr($class), esc_html('Reason : ' . $reason . ' ' . $message));
795
- }
796
-
797
- private function tvc_authinfo_api() {
798
- $access_token = $this->generateAccessToken($_SESSION['access_token'], $_SESSION['refresh_token']);
799
- if (!empty($access_token)) {
800
- $header = array("Authorization: Bearer " . $access_token, "content-type: application/json");
801
- $ch = curl_init();
802
- curl_setopt_array($ch, array(
803
- CURLOPT_URL => esc_url($this->curl_url),
804
- CURLOPT_RETURNTRANSFER => true,
805
- CURLOPT_TIMEOUT => 20,
806
- CURLOPT_HTTPHEADER => $header,
807
- ));
808
- $response = curl_exec($ch);
809
- return json_decode($response);
810
- }
811
- }
812
-
813
- private function tvc_google_auth() {
814
-
815
- return '<td>
816
- <a class="oauth-container btn darken-4 white black-text" href="' . esc_url($this->theURL) . '" style="text-transform:none">
817
- <div class="left">
818
- <img width="20px" style="margin-top:7px; margin-right:8px" alt="Google sign-in"
819
- src="https://upload.wikimedia.org/wikipedia/commons/thumb/5/53/Google_%22G%22_Logo.svg/512px-Google_%22G%22_Logo.svg.png" />
820
- </div>
821
- Sign In
822
- </a>
823
- <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0-beta/css/materialize.min.css">
824
- <script src="https://cdnjs.cloudflare.com/ajax/libs/materialize/1.0.0-beta/js/materialize.min.js"></script>
825
- </td>';
826
- }
827
-
828
- /**
829
- * Returns a script that is placed on rows of feeds that are still processing or waiting in the queue. This script then runs every 10 seconds and checks the status
830
- * of that specific feed generation processes. It is responsible for showing the correct status of this feed in the feed list.
831
- *
832
- * @param string $feed_id
833
- *
834
- * @return string script to be placed on the feed list page on the row of a running or waiting feed.
835
- */
836
- private function feed_status_checker_script($feed_id) {
837
- return '<script type="text/javascript">
838
- var tvcStatusCheck_' . $feed_id . ' = null;
839
- (function(){
840
- tvcStatusCheck_' . $feed_id . ' = window.setInterval(tvc_checkAndSetStatus_' . $feed_id . ', 10000, ' . $feed_id . ' );
841
- })();
842
- function tvc_checkAndSetStatus_' . $feed_id . '( feedId ) {
843
- tvc_getCurrentFeedStatus( feedId, function( result ) {
844
- var data = JSON.parse( result );
845
- tvc_resetFeedStatus( data );
846
- if( data["status_id"] !== "3" && data["status_id"] !== "4" ) {
847
- window.clearInterval( tvcStatusCheck_' . $feed_id . ' );
848
- tvcRemoveFromQueueString( feedId );
849
- }
850
- } );
851
- }
852
- </script>';
853
- }
854
-
855
- }
856
-
857
-
858
-
859
-
860
-
861
-
862
- // end of TVC_List_Table class
863
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-main-admin-page.php DELETED
@@ -1,117 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Main Admin Page Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @version 1.8.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Main_Admin_Page' ) ) :
15
-
16
- /**
17
- * Main Admin Page Class
18
- */
19
- class TVC_Main_Admin_Page extends TVC_Admin_Page {
20
-
21
- private $_list_table;
22
-
23
- function __construct() {
24
-
25
- parent::__construct();
26
-
27
- tvc_check_db_version();
28
-
29
- $this->_list_table = new TVC_List_Table();
30
-
31
- $this->prepare_feed_list();
32
- }
33
-
34
- /**
35
- * Collects the html code for the main page and displays it.
36
- */
37
- public function show() {
38
-
39
- echo $this->admin_page_header();
40
-
41
- echo $this->message_field();
42
-
43
- if ( tvc_wc_installed_and_active() ) {
44
- if ( ! tvc_wc_min_version_required() ) {
45
- echo tvc_update_your_woocommerce_version_message();
46
- exit;
47
- }
48
-
49
- echo $this->tabs();
50
-
51
- echo $this->tab_header( __( 'Feed List Table', 'tvc-product-feed-manager' ), __( 'Use the table below to manage your existing feeds.', 'tvc-product-feed-manager' ) );
52
-
53
- echo $this->main_admin_page();
54
-
55
- echo $this->main_admin_buttons();
56
- } else {
57
- echo tvc_you_have_no_woocommerce_installed_message();
58
- }
59
- }
60
-
61
- /**
62
- * Prepares the list table
63
- */
64
- private function prepare_feed_list() {
65
- $show_type_column = apply_filters( 'tvc_special_feeds_add_on_active', false );
66
-
67
- $this->_list_table->set_table_id( 'tvc-feed-list' );
68
-
69
- $list_columns = array(
70
- 'col_feed_name' => __( 'Feed Name', 'tvc-product-feed-manager' ),
71
- 'col_feed_url' => __( 'Feed XML', 'tvc-product-feed-manager' ),
72
- 'col_feed_api' => __( 'Push Feed to Merchant Center', 'tvc-product-feed-manager' ),
73
- 'col_feed_last_change' => __( 'Updated', 'tvc-product-feed-manager' ),
74
- 'col_feed_products' => __( 'Products', 'tvc-product-feed-manager' ),
75
- );
76
-
77
- if ( $show_type_column ) {
78
- $list_columns['col_feed_type'] = __( 'Type', 'tvc-product-feed-manager' );
79
- }
80
-
81
- $list_columns['col_feed_status'] = __( 'Status', 'tvc-product-feed-manager' );
82
- $list_columns['col_feed_actions'] = __( 'Actions', 'tvc-product-feed-manager' );
83
-
84
- // set the column names
85
- $this->_list_table->set_column_titles( $list_columns );
86
- }
87
-
88
- /**
89
- * Returns a html string containing the main admin page body code
90
- *
91
- * @return string html
92
- */
93
- private function main_admin_page() {
94
- return $this->main_admin_body_top();
95
- }
96
-
97
- /**
98
- * Activates the html for the main body top.
99
- */
100
- private function main_admin_body_top() {
101
- $this->_list_table->display();
102
- }
103
-
104
- private function main_admin_buttons() {
105
- $wrapper_opening_html = '<div class="button-wrapper" id="page-bottom-buttons">';
106
- $button_html = '<input class="button-primary feed-list-lower-button" type="button" ' .
107
- 'onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=product-feed\'" name="new" value="' .
108
- __( 'Add New Feed', 'tvc-product-feed-manager' ) . '" id="add-new-feed-button" />';
109
- $wrapper_closing_html = '</div>';
110
-
111
- return $wrapper_opening_html . apply_filters( 'tvc_main_admin_bottom_buttons', $button_html ) . $wrapper_closing_html;
112
- }
113
-
114
- }
115
-
116
- // end of TVC_Main_Admin_Page class
117
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-product-feed-category-wrapper.php DELETED
@@ -1,51 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Product Feed Category Wrapper Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @since 2.4.0
8
- * @version 1.0.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_Product_Feed_Category_Wrapper' ) ) :
16
-
17
- class TVC_Product_Feed_Category_Wrapper extends TVC_Category_Wrapper {
18
-
19
- /**
20
- * Display the product feed category mapping table.
21
- *
22
- * @return void
23
- */
24
- public function display() {
25
-
26
- // Start with the section code.
27
- echo '<section class="tvc-edit-feed-form-element-wrapper tvc-category-mapping-wrapper" id="tvc-category-map" style="display:none;">';
28
- echo '<div id="category-mapping-header" class="header"><h3>' . __( 'Category Mapping', 'tvc-product-feed-manager' ) . ':</h3></div>';
29
- echo '<table class="fm-category-mapping-table widefat" cellspacing="0" id="category-mapping-table">';
30
-
31
- // The category mapping table header.
32
- echo TVC_Category_Selector_Element::category_selector_table_head( 'mapping' );
33
-
34
- echo '<tbody id="tvc-category-mapping-body">';
35
-
36
- // The content of the table.
37
- echo $this->category_table_content( 'mapping' );
38
-
39
- echo '</tbody>';
40
-
41
- // Closing the section.
42
- echo '</table></section>';
43
-
44
- // Add the product filter element.
45
- echo $this->product_filter();
46
- }
47
- }
48
-
49
- // end of TVC_Product_Feed_Category_Wrapper class
50
-
51
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/class-tvc-product-feed-page.php DELETED
@@ -1,182 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * WP Product Feed Manager Add Feed Page Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @version 3.2.0
8
- */
9
-
10
- if ( ! defined( 'ABSPATH' ) ) {
11
- exit;
12
- }
13
-
14
- if ( ! class_exists( 'TVC_Product_Feed_Page' ) ) :
15
-
16
- /**
17
- * TVC Feed Form Class
18
- */
19
- class TVC_Product_Feed_Page extends TVC_Admin_Page {
20
-
21
- /**
22
- * @var string|null contains the feed id, null for a new feed.
23
- */
24
- private $_feed_id;
25
-
26
- /**
27
- * @var array|null contains the feed data.
28
- */
29
- private $_feed_data;
30
-
31
- private $feedURL;
32
-
33
- public function __construct() {
34
- global $wpdb;
35
- parent::__construct();
36
-
37
- tvc_check_db_version();
38
-
39
- $this->_feed_id = array_key_exists( 'id', $_GET ) && $_GET['id'] ? $_GET['id'] : null;
40
-
41
- $this->set_feed_data();
42
-
43
- add_option( 'wp_enqueue_scripts', TVC_i18n_Scripts::tvc_feed_settings_i18n(), 100 );
44
- add_option( 'wp_enqueue_scripts', TVC_i18n_Scripts::tvc_list_table_i18n() );
45
- }
46
-
47
- /**
48
- * Collects the html code for the product feed form page and displays it.
49
- */
50
- public function show() {
51
-
52
- $tab_header_sub_title = $this->_feed_id ? __( 'Here you can edit the parameters of your feed.', 'tvc-product-feed-manager' ) :
53
- __( 'Here you can setup your new feed. Start by entering a name for your feed and selecting a channel.', 'tvc-product-feed-manager' );
54
-
55
- echo $this->admin_page_header();
56
-
57
- echo $this->message_field();
58
-
59
- if ( tvc_wc_installed_and_active() ) {
60
- if ( ! tvc_wc_min_version_required() ) {
61
- echo tvc_update_your_woocommerce_version_message();
62
- exit;
63
- }
64
-
65
- echo $this->tabs();
66
-
67
- echo $this->subtabs();
68
-
69
- echo $this->tab_header( __( '', 'tvc-product-feed-manager' ), $tab_header_sub_title );
70
-
71
- echo $this->product_feed_page_data_holder();
72
-
73
- echo $this->main_input_table_wrapper();
74
-
75
- echo $this->category_selector_table_wrapper();
76
-
77
- echo $this->feed_top_buttons();
78
-
79
- echo $this->attribute_mapping_table_wrapper();
80
-
81
- } else {
82
- echo tvc_you_have_no_woocommerce_installed_message();
83
- }
84
- }
85
-
86
- /**
87
- * Fills the $feed_data_holder with the correct data that then can be passed through to the edit feed page.
88
- *
89
- * @return string Containing the data that is required to build the edit feed page.
90
- */
91
- private function product_feed_page_data_holder() {
92
- $feed_data_holder = TVC_Form_Element::feed_data_holder( $this->_feed_data );
93
- $feed_data_holder .= TVC_Form_Element::ajax_to_db_conversion_data_holder();
94
- $feed_data_holder .= TVC_Form_Element::feed_url_holder();
95
- $feed_data_holder .= TVC_Form_Element::used_feed_names();
96
-
97
- return $feed_data_holder;
98
- }
99
-
100
- /**
101
- * Fetches feed data from the database and stores it in the _feed_data variable. This data is required to build the edit feed page. Stores empty
102
- * data when the page is opened from a new feed.
103
- */
104
- private function set_feed_data() {
105
-
106
- if ( $this->_feed_id ) {
107
- $queries_class = new TVC_Queries();
108
- $data_class = new TVC_Data();
109
-
110
- $feed_data = $queries_class->read_feed( $this->_feed_id )[0];
111
- $feed_filter = $queries_class->get_product_filter_query( $this->_feed_id );
112
- $source_fields = $data_class->get_source_fields( '1' );
113
- $attribute_data = $data_class->get_attribute_data( $this->_feed_id, $feed_data['channel'] );
114
-
115
- } else {
116
- $source_fields = [];
117
- $attribute_data = [];
118
- $feed_filter = '';
119
- $feed_data = null; // a new feed
120
- }
121
-
122
- /* $feed_data variable contains category feed data fetch from database */
123
-
124
- $this->_feed_data = array(
125
- 'feed_id' => $this->_feed_id ? $this->_feed_id : false,
126
- 'feed_file_name' => $feed_data ? $feed_data['title'] : '',
127
- 'channel_id' => $feed_data ? $feed_data['channel'] : '',
128
- 'language' => $feed_data ? $feed_data['language'] : '',
129
- 'target_country' => $feed_data ? $feed_data['country'] : '',
130
- 'category_mapping' => $feed_data ? $feed_data['category_mapping'] : '',
131
- 'main_category' => $feed_data ? $feed_data['main_category'] : '',
132
- 'include_variations' => $feed_data ? $feed_data['include_variations'] : '',
133
- 'is_aggregator' => $feed_data ? $feed_data['is_aggregator'] : '',
134
- 'url' => $feed_data ? $feed_data['url'] : '',
135
- 'source' => $feed_data ? $feed_data['source'] : '',
136
- 'feed_title' => $feed_data ? $feed_data['feed_title'] : '',
137
- 'feed_description' => $feed_data ? $feed_data['feed_description'] : '',
138
- 'schedule' => $feed_data ? $feed_data['schedule'] : '',
139
- 'status_id' => $feed_data ? $feed_data['status_id'] : '',
140
- 'feed_filter' => $feed_filter ? $feed_filter : null,
141
- 'attribute_data' => $attribute_data,
142
- 'source_fields' => $source_fields,
143
- );
144
- }
145
-
146
- /**
147
- * Returns the html code for the main input table.
148
- */
149
- private function main_input_table_wrapper() {
150
- $main_input_wrapper = new TVC_Product_Feed_Main_Input_Wrapper();
151
- $main_input_wrapper->display();
152
- }
153
-
154
- /**
155
- * Returns the html code for the category mapping table.
156
- */
157
- private function category_selector_table_wrapper() {
158
- $category_table_wrapper = new TVC_Product_Feed_Category_Wrapper();
159
- $category_table_wrapper->display();
160
- }
161
-
162
- /**
163
- * Return the html code for the attribute mapping table.
164
- */
165
- private function attribute_mapping_table_wrapper() {
166
- $attribute_mapping_wrapper = new TVC_Product_Feed_Attribute_Mapping_Wrapper();
167
- $attribute_mapping_wrapper->display();
168
- }
169
-
170
- /**
171
- * Returns the html code for the Save & Generate Feed and Save Feed buttons at the top of the attributes list.
172
- *
173
- * @return string
174
- */
175
- private function feed_top_buttons() {
176
- return TVC_Form_Element::feed_generation_buttons( 'tvc-generate-feed-button-top', 'tvc-save-feed-button-top', 'tvc-view-feed-button-top' );
177
- }
178
- }
179
-
180
- // end of TVC_Product_Feed_Form class
181
-
182
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/elements/class-tvc-attribute-selector-element.php DELETED
@@ -1,113 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Attribute Selector Element Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @since 2.4.0
8
- * @version 1.0.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_Attribute_Selector_Element' ) ) :
16
-
17
- class TVC_Attribute_Selector_Element {
18
-
19
- /**
20
- * Returns the code for the required fields.
21
- *
22
- * @return string
23
- */
24
- public static function required_fields() {
25
- return '<div id="required-fields" style="display:initial;">
26
- <legend class="field-level">
27
- <h4 id="tvc-required-attributes-header">' . esc_html__( 'Required attributes', 'tvc-product-feed-manager' ) . ':</h4>
28
- </legend>'
29
- . self::field_form_table_titles() .
30
- '<div class="field-table" id="required-field-table"></div>
31
- </div>';
32
- }
33
-
34
- /**
35
- * Returns the code for the highly recommended fields.
36
- *
37
- * @return string
38
- */
39
- public static function highly_recommended_fields() {
40
- return '<div id="highly-recommended-fields" style="display:none;">
41
- <legend class="field-level">
42
- <h4 id="tvc-highly-recommended-attributes-header">' . esc_html__( 'Highly recommended attributes', 'tvc-product-feed-manager' ) . ':</h4>
43
- </legend>'
44
- . self::field_form_table_titles() .
45
- '<div class="field-table" id="highly-recommended-field-table"></div>
46
- </div>';
47
- }
48
-
49
- /**
50
- * Returns the code for the recommended fields.
51
- *
52
- * @return string
53
- */
54
- public static function recommended_fields() {
55
- return '<div id="recommended-fields" style="display:none;">
56
- <legend class="field-level">
57
- <h4 id="tvc-recommended-attributes-header">' . esc_html__( 'Recommended attributes', 'tvc-product-feed-manager' ) . ':</h4>
58
- </legend>'
59
- . self::field_form_table_titles() .
60
- '<div class="field-table" id="recommended-field-table"></div>
61
- </div>';
62
- }
63
-
64
- /**
65
- * Returns the code for the optional fields.
66
- *
67
- * @return string
68
- */
69
- public static function optional_fields() {
70
- return '<div id="optional-fields" style="display:initial;">
71
- <legend class="field-level">
72
- <h4 id="tvc-optional-attributes-header">' . esc_html__( 'Optional attributes', 'tvc-product-feed-manager' ) . ':</h4>
73
- </legend>'
74
- . self::field_form_table_titles() .
75
- '<div class="field-table" id="optional-field-table"></div>
76
- </div>';
77
- }
78
-
79
- /**
80
- * Returns the code for the custom fields.
81
- *
82
- * @return string
83
- */
84
- public static function custom_fields() {
85
- return '<div id="custom-fields" style="display:initial;">
86
- <legend class="field-level">
87
- <h4 id="tvc-custom-attributes-header">' . esc_html__( 'Custom attributes', 'tvc-product-feed-manager' ) . ':</h4>
88
- </legend>'
89
- . self::field_form_table_titles() .
90
- '<div class="field-table" id="custom-field-table"></div>
91
- </div>';
92
- }
93
-
94
- /**
95
- * Returns the feed form table titles
96
- *
97
- * @return string
98
- */
99
- private static function field_form_table_titles() {
100
- return '<div class="tvc-field-header-wrapper">
101
- <div class="field-header col20w">' . esc_html__( 'Add to feed', 'tvc-product-feed-manager' ) . '&nbsp;<i class="fas fa-question-circle" title="Google mechandise product data"></i></div>
102
- <div
103
- class="field-header col30w">' . esc_html__( 'From WooCommerce source', 'tvc-product-feed-manager' ) . '&nbsp;<i class="fas fa-question-circle" title="WooCommerce Product Data"></i></div>
104
- <div class="field-header col40w">' . esc_html__( 'Condition', 'tvc-product-feed-manager' ) . '</div>
105
- <div class="field-header col50w" style="float:right">' . esc_html__( 'Edit Value', 'tvc-product-feed-manager' ) . '</div>
106
- <div class="end-row">&nbsp;</div>
107
- </div>';
108
- }
109
- }
110
-
111
- // end of TVC_Attribute_Selector_Element class
112
-
113
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/elements/class-tvc-category-selector-element.php DELETED
@@ -1,121 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * TVC Category Selector Element Class.
5
- *
6
- * @package WP Product Feed Manager/User Interface/Classes
7
- * @since 2.4.0
8
- * @version 1.0.0
9
- */
10
-
11
- if ( ! defined( 'ABSPATH' ) ) {
12
- exit;
13
- }
14
-
15
- if ( ! class_exists( 'TVC_Category_Selector_Element' ) ) :
16
-
17
- class TVC_Category_Selector_Element {
18
-
19
- /**
20
- * Returns the category mapping table head code.
21
- *
22
- * @param string $mode displays a normal category selector or a category mapping selector when 'mapping' is given. Default = 'normal'.
23
- *
24
- * @return string
25
- */
26
- public static function category_selector_table_head( $mode = 'normal' ) {
27
- $mode_column = 'mapping' === $mode ? esc_html__( 'Merchant Center Category', 'tvc-product-feed-manager' ) : __( 'Description', 'tvc-product-feed-manager' );
28
-
29
- return '<thead class="wp-list-table widefat fixed striped"><tr>
30
- <td id="shop-category-selector" class="manage-column column-cb check-column" style="width:5%;">
31
- <label class="screen-reader-text" for="tvc-categories-select-all">Select All</label>
32
- <input id="tvc-categories-select-all" type="checkbox">
33
- </td>
34
- <th scope="row" class="manage-column column-name col30w">' . esc_html__( 'Store Category', 'tvc-product-feed-manager' ) . '&nbsp;<i class="fas fa-question-circle" title="WooCommerce Category"></i></th>
35
- <th scope="row" class="manage-column column-name col55w">' . $mode_column . '&nbsp;<i class="fas fa-question-circle" title="Google Merchant Center Category"></i></th>
36
- <th scope="row" class="manage-column column-name col10w">' . esc_html__( 'Products', 'tvc-product-feed-manager' ) . '</th>
37
- </tr></thead>';
38
- }
39
-
40
- /**
41
- * Returns the code for a single row meant for the category mapping table.
42
- *
43
- * @param object $category object containing data of the active category like term_id and name
44
- * @param string $category_children a string with the children of the active category
45
- * @param string $level_indicator current active level
46
- * @param string $mode defines if the category mapping row should contain a description (normal) or a catgory mapping (mapping) column
47
- *
48
- * @return string
49
- */
50
- public static function category_mapping_row( $category, $category_children, $level_indicator, $mode ) {
51
- $category_row_class = 'mapping' === $mode ? 'tvc-category-mapping-selector' : 'tvc-category-selector';
52
- $mode_column = 'mapping' === $mode ? self::category_mapping_selector( 'catmap', $category->term_id, false ) : self::category_description_data_item( $category->term_id );
53
-
54
- return '<tr id="category-' . $category->term_id . '"><th class="check-column" scope="row" id="shop-category-selector">
55
- <input class="' . $category_row_class . '" data-children="' . $category_children . '" id="feed-selector-' . $category->term_id . '"
56
- type="checkbox" value="' . $category->term_id . '" title="Select ' . $category->name . '">
57
- </th><td id="shop-category" class="col30w">' .
58
- $level_indicator . $category->name .
59
- '</td><td class="field-header col55w"><div id="feed-category-' . $category->term_id . '"></div>' .
60
- $mode_column . '</td>
61
- <td class="category-count col10w">' . $category->category_count . '</td></tr>';
62
- }
63
-
64
- /**
65
- * Returns the code for a category input selector.
66
- *
67
- * @param string $identifier identifier for the selector
68
- * @param string $id id of the selector
69
- * @param boolean $start_visible should this selector start visible
70
- *
71
- * @return string
72
- */
73
- public static function category_mapping_selector( $identifier, $id, $start_visible ) {
74
- $display = $start_visible ? 'initial' : 'none';
75
- $ident = '-1' !== $id ? $identifier . '-' . $id : $identifier;
76
- $category_levels = apply_filters( 'tvc_category_selector_level', 6 );
77
-
78
- $html_code = '<div id="category-selector-' . $ident . '" style="display:' . $display . '">';
79
- $html_code .= '<div id="selected-categories"></div><select class="tvc-main-input-selector tvc-cat-selector" id="' . $ident . '_0" disabled></select>';
80
-
81
- for ( $i = 1; $i < $category_levels; $i ++ ) {
82
- $html_code .= '<select class="tvc-main-input-selector tvc-cat-selector" id="' . $ident . '_' . $i . '" value="0" style="display:none;"></select>';
83
- }
84
-
85
- $html_code .= '<div>';
86
-
87
- return $html_code;
88
- }
89
-
90
- /**
91
- * Returns the code for the category description column.
92
- *
93
- * @param string $category_id
94
- *
95
- * @return string
96
- */
97
- private static function category_description_data_item( $category_id ) {
98
- $category_description = '' !== category_description( $category_id ) ? category_description( $category_id ) : '—';
99
-
100
- $html_code = '<span aria-hidden="true">' . $category_description . '</span>';
101
-
102
- return $html_code;
103
- }
104
-
105
- /**
106
- * Returns the code for the product filter selector.
107
- *
108
- * @return string
109
- */
110
- public static function product_filter_selector() {
111
- return '<section class="main-product-filter-wrapper" id="main-product-filter-wrapper" style="display:none;">
112
- <div class="product-filter-condition-wrapper">
113
- </div>
114
- </section>
115
- <section class=master-feed-filter-wrapper></section>';
116
- }
117
- }
118
-
119
- // end of TVC_Category_Selector_Element class
120
-
121
- endif;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/fontawesome.js DELETED
@@ -1,2 +0,0 @@
1
- window.FontAwesomeKitConfig = {"asyncLoading":{"enabled":false},"autoA11y":{"enabled":true},"baseUrl":"https://kit-free.fontawesome.com","detectConflictsUntil":null,"license":"free","method":"css","minify":{"enabled":true},"v4FontFaceShim":{"enabled":true},"v4shim":{"enabled":true},"version":"latest"};
2
- !function(){function r(e){var t,n=[],i=document,o=i.documentElement.doScroll,r="DOMContentLoaded",a=(o?/^loaded|^c/:/^loaded|^i|^c/).test(i.readyState);a||i.addEventListener(r,t=function(){for(i.removeEventListener(r,t),a=1;t=n.shift();)t()}),a?setTimeout(e,0):n.push(e)}!function(){if(!(void 0===window.Element||"classList"in document.documentElement)){var e,t,n,i=Array.prototype,o=i.push,r=i.splice,a=i.join;d.prototype={add:function(e){this.contains(e)||(o.call(this,e),this.el.className=this.toString())},contains:function(e){return-1!=this.el.className.indexOf(e)},item:function(e){return this[e]||null},remove:function(e){if(this.contains(e)){for(var t=0;t<this.length&&this[t]!=e;t++);r.call(this,t,1),this.el.className=this.toString()}},toString:function(){return a.call(this," ")},toggle:function(e){return this.contains(e)?this.remove(e):this.add(e),this.contains(e)}},window.DOMTokenList=d,e=Element.prototype,t="classList",n=function(){return new d(this)},Object.defineProperty?Object.defineProperty(e,t,{get:n}):e.__defineGetter__(t,n)}function d(e){for(var t=(this.el=e).className.replace(/^\s+|\s+$/g,"").split(/\s+/),n=0;n<t.length;n++)o.call(this,t[n])}}();function a(e){var t,n,i,o;prefixesArray=e||["fa"],prefixesSelectorString="."+Array.prototype.join.call(e,",."),t=document.querySelectorAll(prefixesSelectorString),Array.prototype.forEach.call(t,function(e){n=e.getAttribute("title"),e.setAttribute("aria-hidden","true"),i=!e.nextElementSibling||!e.nextElementSibling.classList.contains("sr-only"),n&&i&&((o=document.createElement("span")).innerHTML=n,o.classList.add("sr-only"),e.parentNode.insertBefore(o,e.nextSibling))})}var d=function(e,t){var n=document.createElement("link");n.href=e,n.media="all",n.rel="stylesheet",t&&t.detectingConflicts&&t.detectionIgnoreAttr&&n.setAttributeNode(document.createAttribute(t.detectionIgnoreAttr)),document.getElementsByTagName("head")[0].appendChild(n)},c=function(e,t){!function(e,t){var n,i=t&&t.before||void 0,o=t&&t.media||void 0,r=window.document,a=r.createElement("link");if(t&&t.detectingConflicts&&t.detectionIgnoreAttr&&a.setAttributeNode(document.createAttribute(t.detectionIgnoreAttr)),i)n=i;else{var d=(r.body||r.getElementsByTagName("head")[0]).childNodes;n=d[d.length-1]}var c=r.styleSheets;a.rel="stylesheet",a.href=e,a.media="only x",function e(t){if(r.body)return t();setTimeout(function(){e(t)})}(function(){n.parentNode.insertBefore(a,i?n:n.nextSibling)});var s=function(e){for(var t=a.href,n=c.length;n--;)if(c[n].href===t)return e();setTimeout(function(){s(e)})};function l(){a.addEventListener&&a.removeEventListener("load",l),a.media=o||"all"}a.addEventListener&&a.addEventListener("load",l),(a.onloadcssdefined=s)(l)}(e,t)},e=function(e,t,n){var i=t&&void 0!==t.autoFetchSvg?t.autoFetchSvg:void 0,o=t&&void 0!==t.async?t.async:void 0,r=t&&void 0!==t.autoA11y?t.autoA11y:void 0,a=document.createElement("script"),d=document.scripts[0];a.src=e,void 0!==r&&a.setAttribute("data-auto-a11y",r?"true":"false"),i&&(a.setAttributeNode(document.createAttribute("data-auto-fetch-svg")),a.setAttribute("data-fetch-svg-from",t.fetchSvgFrom)),o&&a.setAttributeNode(document.createAttribute("defer")),n&&n.detectingConflicts&&n.detectionIgnoreAttr&&a.setAttributeNode(document.createAttribute(n.detectionIgnoreAttr)),d.parentNode.appendChild(a)};function s(e,t){var n=t&&t.addOn||"",i=t&&t.baseFilename||e.license+n,o=t&&t.minify?".min":"",r=t&&t.fileSuffix||e.method,a=t&&t.subdir||e.method;return e.baseUrl+"/releases/"+("latest"===e.version?"latest":"v".concat(e.version))+"/"+a+"/"+i+o+"."+r}var t,n,i,o,l;try{if(window.FontAwesomeKitConfig){var u,f=window.FontAwesomeKitConfig,m={detectingConflicts:f.detectConflictsUntil&&new Date<=new Date(f.detectConflictsUntil),detectionIgnoreAttr:"data-fa-detection-ignore",detectionTimeoutAttr:"data-fa-detection-timeout",detectionTimeout:null};"js"===f.method&&(o=m,l={async:(i=f).asyncLoading.enabled,autoA11y:i.autoA11y.enabled},"pro"===i.license&&(l.autoFetchSvg=!0,l.fetchSvgFrom=i.baseUrl+"/releases/"+("latest"===i.version?"latest":"v".concat(i.version))+"/svgs"),i.v4shim.enabled&&e(s(i,{addOn:"-v4-shims",minify:i.minify.enabled})),e(s(i,{minify:i.minify.enabled}),l,o)),"css"===f.method&&function(e,t){var n,i=a.bind(a,["fa","fab","fas","far","fal","fad"]);e.autoA11y.enabled&&(r(i),n=i,"undefined"!=typeof MutationObserver&&new MutationObserver(n).observe(document,{childList:!0,subtree:!0})),e.v4shim.enabled&&(e.license,e.asyncLoading.enabled?c(s(e,{addOn:"-v4-shims",minify:e.minify.enabled}),t):d(s(e,{addOn:"-v4-shims",minify:e.minify.enabled}),t));e.v4FontFaceShim.enabled&&(e.asyncLoading.enabled?c(s(e,{addOn:"-v4-font-face",minify:e.minify.enabled}),t):d(s(e,{addOn:"-v4-font-face",minify:e.minify.enabled}),t));var o=s(e,{minify:e.minify.enabled});e.asyncLoading.enabled?c(o,t):d(o,t)}(f,m),m.detectingConflicts&&((u=document.currentScript.getAttribute(m.detectionTimeoutAttr))&&(m.detectionTimeout=u),document.currentScript.setAttributeNode(document.createAttribute(m.detectionIgnoreAttr)),t=f,n=m,r(function(){var e=document.createElement("script");n&&n.detectionIgnoreAttr&&e.setAttributeNode(document.createAttribute(n.detectionIgnoreAttr)),n&&n.detectionTimeoutAttr&&n.detectionTimeout&&e.setAttribute(n.detectionTimeoutAttr,n.detectionTimeout),e.src=s(t,{baseFilename:"conflict-detection",fileSuffix:"js",subdir:"js",minify:t.minify.enabled}),e.async=!0,document.body.appendChild(e)}))}}catch(e){}}();
 
 
includes/user-interface/js/sweetalert.min.js DELETED
@@ -1 +0,0 @@
1
- !function(t,e){"object"==typeof exports&&"object"==typeof module?module.exports=e():"function"==typeof define&&define.amd?define([],e):"object"==typeof exports?exports.swal=e():t.swal=e()}(this,function(){return function(t){function e(o){if(n[o])return n[o].exports;var r=n[o]={i:o,l:!1,exports:{}};return t[o].call(r.exports,r,r.exports,e),r.l=!0,r.exports}var n={};return e.m=t,e.c=n,e.d=function(t,n,o){e.o(t,n)||Object.defineProperty(t,n,{configurable:!1,enumerable:!0,get:o})},e.n=function(t){var n=t&&t.__esModule?function(){return t.default}:function(){return t};return e.d(n,"a",n),n},e.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},e.p="",e(e.s=8)}([function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o="swal-button";e.CLASS_NAMES={MODAL:"swal-modal",OVERLAY:"swal-overlay",SHOW_MODAL:"swal-overlay--show-modal",MODAL_TITLE:"swal-title",MODAL_TEXT:"swal-text",ICON:"swal-icon",ICON_CUSTOM:"swal-icon--custom",CONTENT:"swal-content",FOOTER:"swal-footer",BUTTON_CONTAINER:"swal-button-container",BUTTON:o,CONFIRM_BUTTON:o+"--confirm",CANCEL_BUTTON:o+"--cancel",DANGER_BUTTON:o+"--danger",BUTTON_LOADING:o+"--loading",BUTTON_LOADER:o+"__loader"},e.default=e.CLASS_NAMES},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0}),e.getNode=function(t){var e="."+t;return document.querySelector(e)},e.stringToNode=function(t){var e=document.createElement("div");return e.innerHTML=t.trim(),e.firstChild},e.insertAfter=function(t,e){var n=e.nextSibling;e.parentNode.insertBefore(t,n)},e.removeNode=function(t){t.parentElement.removeChild(t)},e.throwErr=function(t){throw t=t.replace(/ +(?= )/g,""),"SweetAlert: "+(t=t.trim())},e.isPlainObject=function(t){if("[object Object]"!==Object.prototype.toString.call(t))return!1;var e=Object.getPrototypeOf(t);return null===e||e===Object.prototype},e.ordinalSuffixOf=function(t){var e=t%10,n=t%100;return 1===e&&11!==n?t+"st":2===e&&12!==n?t+"nd":3===e&&13!==n?t+"rd":t+"th"}},function(t,e,n){"use strict";function o(t){for(var n in t)e.hasOwnProperty(n)||(e[n]=t[n])}Object.defineProperty(e,"__esModule",{value:!0}),o(n(25));var r=n(26);e.overlayMarkup=r.default,o(n(27)),o(n(28)),o(n(29));var i=n(0),a=i.default.MODAL_TITLE,s=i.default.MODAL_TEXT,c=i.default.ICON,l=i.default.FOOTER;e.iconMarkup='\n <div class="'+c+'"></div>',e.titleMarkup='\n <div class="'+a+'"></div>\n',e.textMarkup='\n <div class="'+s+'"></div>',e.footerMarkup='\n <div class="'+l+'"></div>\n'},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1);e.CONFIRM_KEY="confirm",e.CANCEL_KEY="cancel";var r={visible:!0,text:null,value:null,className:"",closeModal:!0},i=Object.assign({},r,{visible:!1,text:"Cancel",value:null}),a=Object.assign({},r,{text:"OK",value:!0});e.defaultButtonList={cancel:i,confirm:a};var s=function(t){switch(t){case e.CONFIRM_KEY:return a;case e.CANCEL_KEY:return i;default:var n=t.charAt(0).toUpperCase()+t.slice(1);return Object.assign({},r,{text:n,value:t})}},c=function(t,e){var n=s(t);return!0===e?Object.assign({},n,{visible:!0}):"string"==typeof e?Object.assign({},n,{visible:!0,text:e}):o.isPlainObject(e)?Object.assign({visible:!0},n,e):Object.assign({},n,{visible:!1})},l=function(t){for(var e={},n=0,o=Object.keys(t);n<o.length;n++){var r=o[n],a=t[r],s=c(r,a);e[r]=s}return e.cancel||(e.cancel=i),e},u=function(t){var n={};switch(t.length){case 1:n[e.CANCEL_KEY]=Object.assign({},i,{visible:!1});break;case 2:n[e.CANCEL_KEY]=c(e.CANCEL_KEY,t[0]),n[e.CONFIRM_KEY]=c(e.CONFIRM_KEY,t[1]);break;default:o.throwErr("Invalid number of 'buttons' in array ("+t.length+").\n If you want more than 2 buttons, you need to use an object!")}return n};e.getButtonListOpts=function(t){var n=e.defaultButtonList;return"string"==typeof t?n[e.CONFIRM_KEY]=c(e.CONFIRM_KEY,t):Array.isArray(t)?n=u(t):o.isPlainObject(t)?n=l(t):!0===t?n=u([!0,!0]):!1===t?n=u([!1,!1]):void 0===t&&(n=e.defaultButtonList),n}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(2),i=n(0),a=i.default.MODAL,s=i.default.OVERLAY,c=n(30),l=n(31),u=n(32),f=n(33);e.injectElIntoModal=function(t){var e=o.getNode(a),n=o.stringToNode(t);return e.appendChild(n),n};var d=function(t){t.className=a,t.textContent=""},p=function(t,e){d(t);var n=e.className;n&&t.classList.add(n)};e.initModalContent=function(t){var e=o.getNode(a);p(e,t),c.default(t.icon),l.initTitle(t.title),l.initText(t.text),f.default(t.content),u.default(t.buttons,t.dangerMode)};var m=function(){var t=o.getNode(s),e=o.stringToNode(r.modalMarkup);t.appendChild(e)};e.default=m},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(3),r={isOpen:!1,promise:null,actions:{},timer:null},i=Object.assign({},r);e.resetState=function(){i=Object.assign({},r)},e.setActionValue=function(t){if("string"==typeof t)return a(o.CONFIRM_KEY,t);for(var e in t)a(e,t[e])};var a=function(t,e){i.actions[t]||(i.actions[t]={}),Object.assign(i.actions[t],{value:e})};e.setActionOptionsFor=function(t,e){var n=(void 0===e?{}:e).closeModal,o=void 0===n||n;Object.assign(i.actions[t],{closeModal:o})},e.default=i},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(3),i=n(0),a=i.default.OVERLAY,s=i.default.SHOW_MODAL,c=i.default.BUTTON,l=i.default.BUTTON_LOADING,u=n(5);e.openModal=function(){o.getNode(a).classList.add(s),u.default.isOpen=!0};var f=function(){o.getNode(a).classList.remove(s),u.default.isOpen=!1};e.onAction=function(t){void 0===t&&(t=r.CANCEL_KEY);var e=u.default.actions[t],n=e.value;if(!1===e.closeModal){var i=c+"--"+t;o.getNode(i).classList.add(l)}else f();u.default.promise.resolve(n)},e.getState=function(){var t=Object.assign({},u.default);return delete t.promise,delete t.timer,t},e.stopLoading=function(){for(var t=document.querySelectorAll("."+c),e=0;e<t.length;e++){t[e].classList.remove(l)}}},function(t,e){var n;n=function(){return this}();try{n=n||Function("return this")()||(0,eval)("this")}catch(t){"object"==typeof window&&(n=window)}t.exports=n},function(t,e,n){(function(e){t.exports=e.sweetAlert=n(9)}).call(e,n(7))},function(t,e,n){(function(e){t.exports=e.swal=n(10)}).call(e,n(7))},function(t,e,n){"undefined"!=typeof window&&n(11),n(16);var o=n(23).default;t.exports=o},function(t,e,n){var o=n(12);"string"==typeof o&&(o=[[t.i,o,""]]);var r={insertAt:"top"};r.transform=void 0;n(14)(o,r);o.locals&&(t.exports=o.locals)},function(t,e,n){e=t.exports=n(13)(void 0),e.push([t.i,'.swal-icon--error{border-color:#f27474;-webkit-animation:animateErrorIcon .5s;animation:animateErrorIcon .5s}.swal-icon--error__x-mark{position:relative;display:block;-webkit-animation:animateXMark .5s;animation:animateXMark .5s}.swal-icon--error__line{position:absolute;height:5px;width:47px;background-color:#f27474;display:block;top:37px;border-radius:2px}.swal-icon--error__line--left{-webkit-transform:rotate(45deg);transform:rotate(45deg);left:17px}.swal-icon--error__line--right{-webkit-transform:rotate(-45deg);transform:rotate(-45deg);right:16px}@-webkit-keyframes animateErrorIcon{0%{-webkit-transform:rotateX(100deg);transform:rotateX(100deg);opacity:0}to{-webkit-transform:rotateX(0deg);transform:rotateX(0deg);opacity:1}}@keyframes animateErrorIcon{0%{-webkit-transform:rotateX(100deg);transform:rotateX(100deg);opacity:0}to{-webkit-transform:rotateX(0deg);transform:rotateX(0deg);opacity:1}}@-webkit-keyframes animateXMark{0%{-webkit-transform:scale(.4);transform:scale(.4);margin-top:26px;opacity:0}50%{-webkit-transform:scale(.4);transform:scale(.4);margin-top:26px;opacity:0}80%{-webkit-transform:scale(1.15);transform:scale(1.15);margin-top:-6px}to{-webkit-transform:scale(1);transform:scale(1);margin-top:0;opacity:1}}@keyframes animateXMark{0%{-webkit-transform:scale(.4);transform:scale(.4);margin-top:26px;opacity:0}50%{-webkit-transform:scale(.4);transform:scale(.4);margin-top:26px;opacity:0}80%{-webkit-transform:scale(1.15);transform:scale(1.15);margin-top:-6px}to{-webkit-transform:scale(1);transform:scale(1);margin-top:0;opacity:1}}.swal-icon--warning{border-color:#f8bb86;-webkit-animation:pulseWarning .75s infinite alternate;animation:pulseWarning .75s infinite alternate}.swal-icon--warning__body{width:5px;height:47px;top:10px;border-radius:2px;margin-left:-2px}.swal-icon--warning__body,.swal-icon--warning__dot{position:absolute;left:50%;background-color:#f8bb86}.swal-icon--warning__dot{width:7px;height:7px;border-radius:50%;margin-left:-4px;bottom:-11px}@-webkit-keyframes pulseWarning{0%{border-color:#f8d486}to{border-color:#f8bb86}}@keyframes pulseWarning{0%{border-color:#f8d486}to{border-color:#f8bb86}}.swal-icon--success{border-color:#a5dc86}.swal-icon--success:after,.swal-icon--success:before{content:"";border-radius:50%;position:absolute;width:60px;height:120px;background:#fff;-webkit-transform:rotate(45deg);transform:rotate(45deg)}.swal-icon--success:before{border-radius:120px 0 0 120px;top:-7px;left:-33px;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);-webkit-transform-origin:60px 60px;transform-origin:60px 60px}.swal-icon--success:after{border-radius:0 120px 120px 0;top:-11px;left:30px;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);-webkit-transform-origin:0 60px;transform-origin:0 60px;-webkit-animation:rotatePlaceholder 4.25s ease-in;animation:rotatePlaceholder 4.25s ease-in}.swal-icon--success__ring{width:80px;height:80px;border:4px solid hsla(98,55%,69%,.2);border-radius:50%;box-sizing:content-box;position:absolute;left:-4px;top:-4px;z-index:2}.swal-icon--success__hide-corners{width:5px;height:90px;background-color:#fff;padding:1px;position:absolute;left:28px;top:8px;z-index:1;-webkit-transform:rotate(-45deg);transform:rotate(-45deg)}.swal-icon--success__line{height:5px;background-color:#a5dc86;display:block;border-radius:2px;position:absolute;z-index:2}.swal-icon--success__line--tip{width:25px;left:14px;top:46px;-webkit-transform:rotate(45deg);transform:rotate(45deg);-webkit-animation:animateSuccessTip .75s;animation:animateSuccessTip .75s}.swal-icon--success__line--long{width:47px;right:8px;top:38px;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);-webkit-animation:animateSuccessLong .75s;animation:animateSuccessLong .75s}@-webkit-keyframes rotatePlaceholder{0%{-webkit-transform:rotate(-45deg);transform:rotate(-45deg)}5%{-webkit-transform:rotate(-45deg);transform:rotate(-45deg)}12%{-webkit-transform:rotate(-405deg);transform:rotate(-405deg)}to{-webkit-transform:rotate(-405deg);transform:rotate(-405deg)}}@keyframes rotatePlaceholder{0%{-webkit-transform:rotate(-45deg);transform:rotate(-45deg)}5%{-webkit-transform:rotate(-45deg);transform:rotate(-45deg)}12%{-webkit-transform:rotate(-405deg);transform:rotate(-405deg)}to{-webkit-transform:rotate(-405deg);transform:rotate(-405deg)}}@-webkit-keyframes animateSuccessTip{0%{width:0;left:1px;top:19px}54%{width:0;left:1px;top:19px}70%{width:50px;left:-8px;top:37px}84%{width:17px;left:21px;top:48px}to{width:25px;left:14px;top:45px}}@keyframes animateSuccessTip{0%{width:0;left:1px;top:19px}54%{width:0;left:1px;top:19px}70%{width:50px;left:-8px;top:37px}84%{width:17px;left:21px;top:48px}to{width:25px;left:14px;top:45px}}@-webkit-keyframes animateSuccessLong{0%{width:0;right:46px;top:54px}65%{width:0;right:46px;top:54px}84%{width:55px;right:0;top:35px}to{width:47px;right:8px;top:38px}}@keyframes animateSuccessLong{0%{width:0;right:46px;top:54px}65%{width:0;right:46px;top:54px}84%{width:55px;right:0;top:35px}to{width:47px;right:8px;top:38px}}.swal-icon--info{border-color:#c9dae1}.swal-icon--info:before{width:5px;height:29px;bottom:17px;border-radius:2px;margin-left:-2px}.swal-icon--info:after,.swal-icon--info:before{content:"";position:absolute;left:50%;background-color:#c9dae1}.swal-icon--info:after{width:7px;height:7px;border-radius:50%;margin-left:-3px;top:19px}.swal-icon{width:80px;height:80px;border-width:4px;border-style:solid;border-radius:50%;padding:0;position:relative;box-sizing:content-box;margin:20px auto}.swal-icon:first-child{margin-top:32px}.swal-icon--custom{width:auto;height:auto;max-width:100%;border:none;border-radius:0}.swal-icon img{max-width:100%;max-height:100%}.swal-title{color:rgba(0,0,0,.65);font-weight:600;text-transform:none;position:relative;display:block;padding:13px 16px;font-size:27px;line-height:normal;text-align:center;margin-bottom:0}.swal-title:first-child{margin-top:26px}.swal-title:not(:first-child){padding-bottom:0}.swal-title:not(:last-child){margin-bottom:13px}.swal-text{font-size:16px;position:relative;float:none;line-height:normal;vertical-align:top;text-align:left;display:inline-block;margin:0;padding:0 10px;font-weight:400;color:rgba(0,0,0,.64);max-width:calc(100% - 20px);overflow-wrap:break-word;box-sizing:border-box}.swal-text:first-child{margin-top:45px}.swal-text:last-child{margin-bottom:45px}.swal-footer{text-align:right;padding-top:13px;margin-top:13px;padding:13px 16px;border-radius:inherit;border-top-left-radius:0;border-top-right-radius:0}.swal-button-container{margin:5px;display:inline-block;position:relative}.swal-button{background-color:#7cd1f9;color:#fff;border:none;box-shadow:none;border-radius:5px;font-weight:600;font-size:14px;padding:10px 24px;margin:0;cursor:pointer}.swal-button[not:disabled]:hover{background-color:#78cbf2}.swal-button:active{background-color:#70bce0}.swal-button:focus{outline:none;box-shadow:0 0 0 1px #fff,0 0 0 3px rgba(43,114,165,.29)}.swal-button[disabled]{opacity:.5;cursor:default}.swal-button::-moz-focus-inner{border:0}.swal-button--cancel{color:#555;background-color:#efefef}.swal-button--cancel[not:disabled]:hover{background-color:#e8e8e8}.swal-button--cancel:active{background-color:#d7d7d7}.swal-button--cancel:focus{box-shadow:0 0 0 1px #fff,0 0 0 3px rgba(116,136,150,.29)}.swal-button--danger{background-color:#e64942}.swal-button--danger[not:disabled]:hover{background-color:#df4740}.swal-button--danger:active{background-color:#cf423b}.swal-button--danger:focus{box-shadow:0 0 0 1px #fff,0 0 0 3px rgba(165,43,43,.29)}.swal-content{padding:0 20px;margin-top:20px;font-size:medium}.swal-content:last-child{margin-bottom:20px}.swal-content__input,.swal-content__textarea{-webkit-appearance:none;background-color:#fff;border:none;font-size:14px;display:block;box-sizing:border-box;width:100%;border:1px solid rgba(0,0,0,.14);padding:10px 13px;border-radius:2px;transition:border-color .2s}.swal-content__input:focus,.swal-content__textarea:focus{outline:none;border-color:#6db8ff}.swal-content__textarea{resize:vertical}.swal-button--loading{color:transparent}.swal-button--loading~.swal-button__loader{opacity:1}.swal-button__loader{position:absolute;height:auto;width:43px;z-index:2;left:50%;top:50%;-webkit-transform:translateX(-50%) translateY(-50%);transform:translateX(-50%) translateY(-50%);text-align:center;pointer-events:none;opacity:0}.swal-button__loader div{display:inline-block;float:none;vertical-align:baseline;width:9px;height:9px;padding:0;border:none;margin:2px;opacity:.4;border-radius:7px;background-color:hsla(0,0%,100%,.9);transition:background .2s;-webkit-animation:swal-loading-anim 1s infinite;animation:swal-loading-anim 1s infinite}.swal-button__loader div:nth-child(3n+2){-webkit-animation-delay:.15s;animation-delay:.15s}.swal-button__loader div:nth-child(3n+3){-webkit-animation-delay:.3s;animation-delay:.3s}@-webkit-keyframes swal-loading-anim{0%{opacity:.4}20%{opacity:.4}50%{opacity:1}to{opacity:.4}}@keyframes swal-loading-anim{0%{opacity:.4}20%{opacity:.4}50%{opacity:1}to{opacity:.4}}.swal-overlay{position:fixed;top:0;bottom:0;left:0;right:0;text-align:center;font-size:0;overflow-y:auto;background-color:rgba(0,0,0,.4);z-index:10000;pointer-events:none;opacity:0;transition:opacity .3s}.swal-overlay:before{content:" ";display:inline-block;vertical-align:middle;height:100%}.swal-overlay--show-modal{opacity:1;pointer-events:auto}.swal-overlay--show-modal .swal-modal{opacity:1;pointer-events:auto;box-sizing:border-box;-webkit-animation:showSweetAlert .3s;animation:showSweetAlert .3s;will-change:transform}.swal-modal{width:478px;opacity:0;pointer-events:none;background-color:#fff;text-align:center;border-radius:5px;position:static;margin:20px auto;display:inline-block;vertical-align:middle;-webkit-transform:scale(1);transform:scale(1);-webkit-transform-origin:50% 50%;transform-origin:50% 50%;z-index:10001;transition:opacity .2s,-webkit-transform .3s;transition:transform .3s,opacity .2s;transition:transform .3s,opacity .2s,-webkit-transform .3s}@media (max-width:500px){.swal-modal{width:calc(100% - 20px)}}@-webkit-keyframes showSweetAlert{0%{-webkit-transform:scale(1);transform:scale(1)}1%{-webkit-transform:scale(.5);transform:scale(.5)}45%{-webkit-transform:scale(1.05);transform:scale(1.05)}80%{-webkit-transform:scale(.95);transform:scale(.95)}to{-webkit-transform:scale(1);transform:scale(1)}}@keyframes showSweetAlert{0%{-webkit-transform:scale(1);transform:scale(1)}1%{-webkit-transform:scale(.5);transform:scale(.5)}45%{-webkit-transform:scale(1.05);transform:scale(1.05)}80%{-webkit-transform:scale(.95);transform:scale(.95)}to{-webkit-transform:scale(1);transform:scale(1)}}',""])},function(t,e){function n(t,e){var n=t[1]||"",r=t[3];if(!r)return n;if(e&&"function"==typeof btoa){var i=o(r);return[n].concat(r.sources.map(function(t){return"/*# sourceURL="+r.sourceRoot+t+" */"})).concat([i]).join("\n")}return[n].join("\n")}function o(t){return"/*# sourceMappingURL=data:application/json;charset=utf-8;base64,"+btoa(unescape(encodeURIComponent(JSON.stringify(t))))+" */"}t.exports=function(t){var e=[];return e.toString=function(){return this.map(function(e){var o=n(e,t);return e[2]?"@media "+e[2]+"{"+o+"}":o}).join("")},e.i=function(t,n){"string"==typeof t&&(t=[[null,t,""]]);for(var o={},r=0;r<this.length;r++){var i=this[r][0];"number"==typeof i&&(o[i]=!0)}for(r=0;r<t.length;r++){var a=t[r];"number"==typeof a[0]&&o[a[0]]||(n&&!a[2]?a[2]=n:n&&(a[2]="("+a[2]+") and ("+n+")"),e.push(a))}},e}},function(t,e,n){function o(t,e){for(var n=0;n<t.length;n++){var o=t[n],r=m[o.id];if(r){r.refs++;for(var i=0;i<r.parts.length;i++)r.parts[i](o.parts[i]);for(;i<o.parts.length;i++)r.parts.push(u(o.parts[i],e))}else{for(var a=[],i=0;i<o.parts.length;i++)a.push(u(o.parts[i],e));m[o.id]={id:o.id,refs:1,parts:a}}}}function r(t,e){for(var n=[],o={},r=0;r<t.length;r++){var i=t[r],a=e.base?i[0]+e.base:i[0],s=i[1],c=i[2],l=i[3],u={css:s,media:c,sourceMap:l};o[a]?o[a].parts.push(u):n.push(o[a]={id:a,parts:[u]})}return n}function i(t,e){var n=v(t.insertInto);if(!n)throw new Error("Couldn't find a style target. This probably means that the value for the 'insertInto' parameter is invalid.");var o=w[w.length-1];if("top"===t.insertAt)o?o.nextSibling?n.insertBefore(e,o.nextSibling):n.appendChild(e):n.insertBefore(e,n.firstChild),w.push(e);else{if("bottom"!==t.insertAt)throw new Error("Invalid value for parameter 'insertAt'. Must be 'top' or 'bottom'.");n.appendChild(e)}}function a(t){if(null===t.parentNode)return!1;t.parentNode.removeChild(t);var e=w.indexOf(t);e>=0&&w.splice(e,1)}function s(t){var e=document.createElement("style");return t.attrs.type="text/css",l(e,t.attrs),i(t,e),e}function c(t){var e=document.createElement("link");return t.attrs.type="text/css",t.attrs.rel="stylesheet",l(e,t.attrs),i(t,e),e}function l(t,e){Object.keys(e).forEach(function(n){t.setAttribute(n,e[n])})}function u(t,e){var n,o,r,i;if(e.transform&&t.css){if(!(i=e.transform(t.css)))return function(){};t.css=i}if(e.singleton){var l=h++;n=g||(g=s(e)),o=f.bind(null,n,l,!1),r=f.bind(null,n,l,!0)}else t.sourceMap&&"function"==typeof URL&&"function"==typeof URL.createObjectURL&&"function"==typeof URL.revokeObjectURL&&"function"==typeof Blob&&"function"==typeof btoa?(n=c(e),o=p.bind(null,n,e),r=function(){a(n),n.href&&URL.revokeObjectURL(n.href)}):(n=s(e),o=d.bind(null,n),r=function(){a(n)});return o(t),function(e){if(e){if(e.css===t.css&&e.media===t.media&&e.sourceMap===t.sourceMap)return;o(t=e)}else r()}}function f(t,e,n,o){var r=n?"":o.css;if(t.styleSheet)t.styleSheet.cssText=x(e,r);else{var i=document.createTextNode(r),a=t.childNodes;a[e]&&t.removeChild(a[e]),a.length?t.insertBefore(i,a[e]):t.appendChild(i)}}function d(t,e){var n=e.css,o=e.media;if(o&&t.setAttribute("media",o),t.styleSheet)t.styleSheet.cssText=n;else{for(;t.firstChild;)t.removeChild(t.firstChild);t.appendChild(document.createTextNode(n))}}function p(t,e,n){var o=n.css,r=n.sourceMap,i=void 0===e.convertToAbsoluteUrls&&r;(e.convertToAbsoluteUrls||i)&&(o=y(o)),r&&(o+="\n/*# sourceMappingURL=data:application/json;base64,"+btoa(unescape(encodeURIComponent(JSON.stringify(r))))+" */");var a=new Blob([o],{type:"text/css"}),s=t.href;t.href=URL.createObjectURL(a),s&&URL.revokeObjectURL(s)}var m={},b=function(t){var e;return function(){return void 0===e&&(e=t.apply(this,arguments)),e}}(function(){return window&&document&&document.all&&!window.atob}),v=function(t){var e={};return function(n){return void 0===e[n]&&(e[n]=t.call(this,n)),e[n]}}(function(t){return document.querySelector(t)}),g=null,h=0,w=[],y=n(15);t.exports=function(t,e){if("undefined"!=typeof DEBUG&&DEBUG&&"object"!=typeof document)throw new Error("The style-loader cannot be used in a non-browser environment");e=e||{},e.attrs="object"==typeof e.attrs?e.attrs:{},e.singleton||(e.singleton=b()),e.insertInto||(e.insertInto="head"),e.insertAt||(e.insertAt="bottom");var n=r(t,e);return o(n,e),function(t){for(var i=[],a=0;a<n.length;a++){var s=n[a],c=m[s.id];c.refs--,i.push(c)}if(t){o(r(t,e),e)}for(var a=0;a<i.length;a++){var c=i[a];if(0===c.refs){for(var l=0;l<c.parts.length;l++)c.parts[l]();delete m[c.id]}}}};var x=function(){var t=[];return function(e,n){return t[e]=n,t.filter(Boolean).join("\n")}}()},function(t,e){t.exports=function(t){var e="undefined"!=typeof window&&window.location;if(!e)throw new Error("fixUrls requires window.location");if(!t||"string"!=typeof t)return t;var n=e.protocol+"//"+e.host,o=n+e.pathname.replace(/\/[^\/]*$/,"/");return t.replace(/url\s*\(((?:[^)(]|\((?:[^)(]+|\([^)(]*\))*\))*)\)/gi,function(t,e){var r=e.trim().replace(/^"(.*)"$/,function(t,e){return e}).replace(/^'(.*)'$/,function(t,e){return e});if(/^(#|data:|http:\/\/|https:\/\/|file:\/\/\/)/i.test(r))return t;var i;return i=0===r.indexOf("//")?r:0===r.indexOf("/")?n+r:o+r.replace(/^\.\//,""),"url("+JSON.stringify(i)+")"})}},function(t,e,n){var o=n(17);"undefined"==typeof window||window.Promise||(window.Promise=o),n(21),String.prototype.includes||(String.prototype.includes=function(t,e){"use strict";return"number"!=typeof e&&(e=0),!(e+t.length>this.length)&&-1!==this.indexOf(t,e)}),Array.prototype.includes||Object.defineProperty(Array.prototype,"includes",{value:function(t,e){if(null==this)throw new TypeError('"this" is null or not defined');var n=Object(this),o=n.length>>>0;if(0===o)return!1;for(var r=0|e,i=Math.max(r>=0?r:o-Math.abs(r),0);i<o;){if(function(t,e){return t===e||"number"==typeof t&&"number"==typeof e&&isNaN(t)&&isNaN(e)}(n[i],t))return!0;i++}return!1}}),"undefined"!=typeof window&&function(t){t.forEach(function(t){t.hasOwnProperty("remove")||Object.defineProperty(t,"remove",{configurable:!0,enumerable:!0,writable:!0,value:function(){this.parentNode.removeChild(this)}})})}([Element.prototype,CharacterData.prototype,DocumentType.prototype])},function(t,e,n){(function(e){!function(n){function o(){}function r(t,e){return function(){t.apply(e,arguments)}}function i(t){if("object"!=typeof this)throw new TypeError("Promises must be constructed via new");if("function"!=typeof t)throw new TypeError("not a function");this._state=0,this._handled=!1,this._value=void 0,this._deferreds=[],f(t,this)}function a(t,e){for(;3===t._state;)t=t._value;if(0===t._state)return void t._deferreds.push(e);t._handled=!0,i._immediateFn(function(){var n=1===t._state?e.onFulfilled:e.onRejected;if(null===n)return void(1===t._state?s:c)(e.promise,t._value);var o;try{o=n(t._value)}catch(t){return void c(e.promise,t)}s(e.promise,o)})}function s(t,e){try{if(e===t)throw new TypeError("A promise cannot be resolved with itself.");if(e&&("object"==typeof e||"function"==typeof e)){var n=e.then;if(e instanceof i)return t._state=3,t._value=e,void l(t);if("function"==typeof n)return void f(r(n,e),t)}t._state=1,t._value=e,l(t)}catch(e){c(t,e)}}function c(t,e){t._state=2,t._value=e,l(t)}function l(t){2===t._state&&0===t._deferreds.length&&i._immediateFn(function(){t._handled||i._unhandledRejectionFn(t._value)});for(var e=0,n=t._deferreds.length;e<n;e++)a(t,t._deferreds[e]);t._deferreds=null}function u(t,e,n){this.onFulfilled="function"==typeof t?t:null,this.onRejected="function"==typeof e?e:null,this.promise=n}function f(t,e){var n=!1;try{t(function(t){n||(n=!0,s(e,t))},function(t){n||(n=!0,c(e,t))})}catch(t){if(n)return;n=!0,c(e,t)}}var d=setTimeout;i.prototype.catch=function(t){return this.then(null,t)},i.prototype.then=function(t,e){var n=new this.constructor(o);return a(this,new u(t,e,n)),n},i.all=function(t){var e=Array.prototype.slice.call(t);return new i(function(t,n){function o(i,a){try{if(a&&("object"==typeof a||"function"==typeof a)){var s=a.then;if("function"==typeof s)return void s.call(a,function(t){o(i,t)},n)}e[i]=a,0==--r&&t(e)}catch(t){n(t)}}if(0===e.length)return t([]);for(var r=e.length,i=0;i<e.length;i++)o(i,e[i])})},i.resolve=function(t){return t&&"object"==typeof t&&t.constructor===i?t:new i(function(e){e(t)})},i.reject=function(t){return new i(function(e,n){n(t)})},i.race=function(t){return new i(function(e,n){for(var o=0,r=t.length;o<r;o++)t[o].then(e,n)})},i._immediateFn="function"==typeof e&&function(t){e(t)}||function(t){d(t,0)},i._unhandledRejectionFn=function(t){"undefined"!=typeof console&&console&&console.warn("Possible Unhandled Promise Rejection:",t)},i._setImmediateFn=function(t){i._immediateFn=t},i._setUnhandledRejectionFn=function(t){i._unhandledRejectionFn=t},void 0!==t&&t.exports?t.exports=i:n.Promise||(n.Promise=i)}(this)}).call(e,n(18).setImmediate)},function(t,e,n){function o(t,e){this._id=t,this._clearFn=e}var r=Function.prototype.apply;e.setTimeout=function(){return new o(r.call(setTimeout,window,arguments),clearTimeout)},e.setInterval=function(){return new o(r.call(setInterval,window,arguments),clearInterval)},e.clearTimeout=e.clearInterval=function(t){t&&t.close()},o.prototype.unref=o.prototype.ref=function(){},o.prototype.close=function(){this._clearFn.call(window,this._id)},e.enroll=function(t,e){clearTimeout(t._idleTimeoutId),t._idleTimeout=e},e.unenroll=function(t){clearTimeout(t._idleTimeoutId),t._idleTimeout=-1},e._unrefActive=e.active=function(t){clearTimeout(t._idleTimeoutId);var e=t._idleTimeout;e>=0&&(t._idleTimeoutId=setTimeout(function(){t._onTimeout&&t._onTimeout()},e))},n(19),e.setImmediate=setImmediate,e.clearImmediate=clearImmediate},function(t,e,n){(function(t,e){!function(t,n){"use strict";function o(t){"function"!=typeof t&&(t=new Function(""+t));for(var e=new Array(arguments.length-1),n=0;n<e.length;n++)e[n]=arguments[n+1];var o={callback:t,args:e};return l[c]=o,s(c),c++}function r(t){delete l[t]}function i(t){var e=t.callback,o=t.args;switch(o.length){case 0:e();break;case 1:e(o[0]);break;case 2:e(o[0],o[1]);break;case 3:e(o[0],o[1],o[2]);break;default:e.apply(n,o)}}function a(t){if(u)setTimeout(a,0,t);else{var e=l[t];if(e){u=!0;try{i(e)}finally{r(t),u=!1}}}}if(!t.setImmediate){var s,c=1,l={},u=!1,f=t.document,d=Object.getPrototypeOf&&Object.getPrototypeOf(t);d=d&&d.setTimeout?d:t,"[object process]"==={}.toString.call(t.process)?function(){s=function(t){e.nextTick(function(){a(t)})}}():function(){if(t.postMessage&&!t.importScripts){var e=!0,n=t.onmessage;return t.onmessage=function(){e=!1},t.postMessage("","*"),t.onmessage=n,e}}()?function(){var e="setImmediate$"+Math.random()+"$",n=function(n){n.source===t&&"string"==typeof n.data&&0===n.data.indexOf(e)&&a(+n.data.slice(e.length))};t.addEventListener?t.addEventListener("message",n,!1):t.attachEvent("onmessage",n),s=function(n){t.postMessage(e+n,"*")}}():t.MessageChannel?function(){var t=new MessageChannel;t.port1.onmessage=function(t){a(t.data)},s=function(e){t.port2.postMessage(e)}}():f&&"onreadystatechange"in f.createElement("script")?function(){var t=f.documentElement;s=function(e){var n=f.createElement("script");n.onreadystatechange=function(){a(e),n.onreadystatechange=null,t.removeChild(n),n=null},t.appendChild(n)}}():function(){s=function(t){setTimeout(a,0,t)}}(),d.setImmediate=o,d.clearImmediate=r}}("undefined"==typeof self?void 0===t?this:t:self)}).call(e,n(7),n(20))},function(t,e){function n(){throw new Error("setTimeout has not been defined")}function o(){throw new Error("clearTimeout has not been defined")}function r(t){if(u===setTimeout)return setTimeout(t,0);if((u===n||!u)&&setTimeout)return u=setTimeout,setTimeout(t,0);try{return u(t,0)}catch(e){try{return u.call(null,t,0)}catch(e){return u.call(this,t,0)}}}function i(t){if(f===clearTimeout)return clearTimeout(t);if((f===o||!f)&&clearTimeout)return f=clearTimeout,clearTimeout(t);try{return f(t)}catch(e){try{return f.call(null,t)}catch(e){return f.call(this,t)}}}function a(){b&&p&&(b=!1,p.length?m=p.concat(m):v=-1,m.length&&s())}function s(){if(!b){var t=r(a);b=!0;for(var e=m.length;e;){for(p=m,m=[];++v<e;)p&&p[v].run();v=-1,e=m.length}p=null,b=!1,i(t)}}function c(t,e){this.fun=t,this.array=e}function l(){}var u,f,d=t.exports={};!function(){try{u="function"==typeof setTimeout?setTimeout:n}catch(t){u=n}try{f="function"==typeof clearTimeout?clearTimeout:o}catch(t){f=o}}();var p,m=[],b=!1,v=-1;d.nextTick=function(t){var e=new Array(arguments.length-1);if(arguments.length>1)for(var n=1;n<arguments.length;n++)e[n-1]=arguments[n];m.push(new c(t,e)),1!==m.length||b||r(s)},c.prototype.run=function(){this.fun.apply(null,this.array)},d.title="browser",d.browser=!0,d.env={},d.argv=[],d.version="",d.versions={},d.on=l,d.addListener=l,d.once=l,d.off=l,d.removeListener=l,d.removeAllListeners=l,d.emit=l,d.prependListener=l,d.prependOnceListener=l,d.listeners=function(t){return[]},d.binding=function(t){throw new Error("process.binding is not supported")},d.cwd=function(){return"/"},d.chdir=function(t){throw new Error("process.chdir is not supported")},d.umask=function(){return 0}},function(t,e,n){"use strict";n(22).polyfill()},function(t,e,n){"use strict";function o(t,e){if(void 0===t||null===t)throw new TypeError("Cannot convert first argument to object");for(var n=Object(t),o=1;o<arguments.length;o++){var r=arguments[o];if(void 0!==r&&null!==r)for(var i=Object.keys(Object(r)),a=0,s=i.length;a<s;a++){var c=i[a],l=Object.getOwnPropertyDescriptor(r,c);void 0!==l&&l.enumerable&&(n[c]=r[c])}}return n}function r(){Object.assign||Object.defineProperty(Object,"assign",{enumerable:!1,configurable:!0,writable:!0,value:o})}t.exports={assign:o,polyfill:r}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(24),r=n(6),i=n(5),a=n(36),s=function(){for(var t=[],e=0;e<arguments.length;e++)t[e]=arguments[e];if("undefined"!=typeof window){var n=a.getOpts.apply(void 0,t);return new Promise(function(t,e){i.default.promise={resolve:t,reject:e},o.default(n),setTimeout(function(){r.openModal()})})}};s.close=r.onAction,s.getState=r.getState,s.setActionValue=i.setActionValue,s.stopLoading=r.stopLoading,s.setDefaults=a.setDefaults,e.default=s},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(0),i=r.default.MODAL,a=n(4),s=n(34),c=n(35),l=n(1);e.init=function(t){o.getNode(i)||(document.body||l.throwErr("You can only use SweetAlert AFTER the DOM has loaded!"),s.default(),a.default()),a.initModalContent(t),c.default(t)},e.default=e.init},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(0),r=o.default.MODAL;e.modalMarkup='\n <div class="'+r+'" role="dialog" aria-modal="true"></div>',e.default=e.modalMarkup},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(0),r=o.default.OVERLAY,i='<div \n class="'+r+'"\n tabIndex="-1">\n </div>';e.default=i},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(0),r=o.default.ICON;e.errorIconMarkup=function(){var t=r+"--error",e=t+"__line";return'\n <div class="'+t+'__x-mark">\n <span class="'+e+" "+e+'--left"></span>\n <span class="'+e+" "+e+'--right"></span>\n </div>\n '},e.warningIconMarkup=function(){var t=r+"--warning";return'\n <span class="'+t+'__body">\n <span class="'+t+'__dot"></span>\n </span>\n '},e.successIconMarkup=function(){var t=r+"--success";return'\n <span class="'+t+"__line "+t+'__line--long"></span>\n <span class="'+t+"__line "+t+'__line--tip"></span>\n\n <div class="'+t+'__ring"></div>\n <div class="'+t+'__hide-corners"></div>\n '}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(0),r=o.default.CONTENT;e.contentMarkup='\n <div class="'+r+'">\n\n </div>\n'},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(0),r=o.default.BUTTON_CONTAINER,i=o.default.BUTTON,a=o.default.BUTTON_LOADER;e.buttonMarkup='\n <div class="'+r+'">\n\n <button\n class="'+i+'"\n ></button>\n\n <div class="'+a+'">\n <div></div>\n <div></div>\n <div></div>\n </div>\n\n </div>\n'},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(4),r=n(2),i=n(0),a=i.default.ICON,s=i.default.ICON_CUSTOM,c=["error","warning","success","info"],l={error:r.errorIconMarkup(),warning:r.warningIconMarkup(),success:r.successIconMarkup()},u=function(t,e){var n=a+"--"+t;e.classList.add(n);var o=l[t];o&&(e.innerHTML=o)},f=function(t,e){e.classList.add(s);var n=document.createElement("img");n.src=t,e.appendChild(n)},d=function(t){if(t){var e=o.injectElIntoModal(r.iconMarkup);c.includes(t)?u(t,e):f(t,e)}};e.default=d},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(2),r=n(4),i=function(t){navigator.userAgent.includes("AppleWebKit")&&(t.style.display="none",t.offsetHeight,t.style.display="")};e.initTitle=function(t){if(t){var e=r.injectElIntoModal(o.titleMarkup);e.textContent=t,i(e)}},e.initText=function(t){if(t){var e=document.createDocumentFragment();t.split("\n").forEach(function(t,n,o){e.appendChild(document.createTextNode(t)),n<o.length-1&&e.appendChild(document.createElement("br"))});var n=r.injectElIntoModal(o.textMarkup);n.appendChild(e),i(n)}}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(4),i=n(0),a=i.default.BUTTON,s=i.default.DANGER_BUTTON,c=n(3),l=n(2),u=n(6),f=n(5),d=function(t,e,n){var r=e.text,i=e.value,d=e.className,p=e.closeModal,m=o.stringToNode(l.buttonMarkup),b=m.querySelector("."+a),v=a+"--"+t;if(b.classList.add(v),d){(Array.isArray(d)?d:d.split(" ")).filter(function(t){return t.length>0}).forEach(function(t){b.classList.add(t)})}n&&t===c.CONFIRM_KEY&&b.classList.add(s),b.textContent=r;var g={};return g[t]=i,f.setActionValue(g),f.setActionOptionsFor(t,{closeModal:p}),b.addEventListener("click",function(){return u.onAction(t)}),m},p=function(t,e){var n=r.injectElIntoModal(l.footerMarkup);for(var o in t){var i=t[o],a=d(o,i,e);i.visible&&n.appendChild(a)}0===n.children.length&&n.remove()};e.default=p},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(3),r=n(4),i=n(2),a=n(5),s=n(6),c=n(0),l=c.default.CONTENT,u=function(t){t.addEventListener("input",function(t){var e=t.target,n=e.value;a.setActionValue(n)}),t.addEventListener("keyup",function(t){if("Enter"===t.key)return s.onAction(o.CONFIRM_KEY)}),setTimeout(function(){t.focus(),a.setActionValue("")},0)},f=function(t,e,n){var o=document.createElement(e),r=l+"__"+e;o.classList.add(r);for(var i in n){var a=n[i];o[i]=a}"input"===e&&u(o),t.appendChild(o)},d=function(t){if(t){var e=r.injectElIntoModal(i.contentMarkup),n=t.element,o=t.attributes;"string"==typeof n?f(e,n,o):e.appendChild(n)}};e.default=d},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(2),i=function(){var t=o.stringToNode(r.overlayMarkup);document.body.appendChild(t)};e.default=i},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(5),r=n(6),i=n(1),a=n(3),s=n(0),c=s.default.MODAL,l=s.default.BUTTON,u=s.default.OVERLAY,f=function(t){t.preventDefault(),v()},d=function(t){t.preventDefault(),g()},p=function(t){if(o.default.isOpen)switch(t.key){case"Escape":return r.onAction(a.CANCEL_KEY)}},m=function(t){if(o.default.isOpen)switch(t.key){case"Tab":return f(t)}},b=function(t){if(o.default.isOpen)return"Tab"===t.key&&t.shiftKey?d(t):void 0},v=function(){var t=i.getNode(l);t&&(t.tabIndex=0,t.focus())},g=function(){var t=i.getNode(c),e=t.querySelectorAll("."+l),n=e.length-1,o=e[n];o&&o.focus()},h=function(t){t[t.length-1].addEventListener("keydown",m)},w=function(t){t[0].addEventListener("keydown",b)},y=function(){var t=i.getNode(c),e=t.querySelectorAll("."+l);e.length&&(h(e),w(e))},x=function(t){if(i.getNode(u)===t.target)return r.onAction(a.CANCEL_KEY)},_=function(t){var e=i.getNode(u);e.removeEventListener("click",x),t&&e.addEventListener("click",x)},k=function(t){o.default.timer&&clearTimeout(o.default.timer),t&&(o.default.timer=window.setTimeout(function(){return r.onAction(a.CANCEL_KEY)},t))},O=function(t){t.closeOnEsc?document.addEventListener("keyup",p):document.removeEventListener("keyup",p),t.dangerMode?v():g(),y(),_(t.closeOnClickOutside),k(t.timer)};e.default=O},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r=n(3),i=n(37),a=n(38),s={title:null,text:null,icon:null,buttons:r.defaultButtonList,content:null,className:null,closeOnClickOutside:!0,closeOnEsc:!0,dangerMode:!1,timer:null},c=Object.assign({},s);e.setDefaults=function(t){c=Object.assign({},s,t)};var l=function(t){var e=t&&t.button,n=t&&t.buttons;return void 0!==e&&void 0!==n&&o.throwErr("Cannot set both 'button' and 'buttons' options!"),void 0!==e?{confirm:e}:n},u=function(t){return o.ordinalSuffixOf(t+1)},f=function(t,e){o.throwErr(u(e)+" argument ('"+t+"') is invalid")},d=function(t,e){var n=t+1,r=e[n];o.isPlainObject(r)||void 0===r||o.throwErr("Expected "+u(n)+" argument ('"+r+"') to be a plain object")},p=function(t,e){var n=t+1,r=e[n];void 0!==r&&o.throwErr("Unexpected "+u(n)+" argument ("+r+")")},m=function(t,e,n,r){var i=typeof e,a="string"===i,s=e instanceof Element;if(a){if(0===n)return{text:e};if(1===n)return{text:e,title:r[0]};if(2===n)return d(n,r),{icon:e};f(e,n)}else{if(s&&0===n)return d(n,r),{content:e};if(o.isPlainObject(e))return p(n,r),e;f(e,n)}};e.getOpts=function(){for(var t=[],e=0;e<arguments.length;e++)t[e]=arguments[e];var n={};t.forEach(function(e,o){var r=m(0,e,o,t);Object.assign(n,r)});var o=l(n);n.buttons=r.getButtonListOpts(o),delete n.button,n.content=i.getContentOpts(n.content);var u=Object.assign({},s,c,n);return Object.keys(u).forEach(function(t){a.DEPRECATED_OPTS[t]&&a.logDeprecation(t)}),u}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0});var o=n(1),r={element:"input",attributes:{placeholder:""}};e.getContentOpts=function(t){var e={};return o.isPlainObject(t)?Object.assign(e,t):t instanceof Element?{element:t}:"input"===t?r:null}},function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0}),e.logDeprecation=function(t){var n=e.DEPRECATED_OPTS[t],o=n.onlyRename,r=n.replacement,i=n.subOption,a=n.link,s=o?"renamed":"deprecated",c='SweetAlert warning: "'+t+'" option has been '+s+".";if(r){c+=" Please use"+(i?' "'+i+'" in ':" ")+'"'+r+'" instead.'}var l="https://sweetalert.js.org";c+=a?" More details: "+l+a:" More details: "+l+"/guides/#upgrading-from-1x",console.warn(c)},e.DEPRECATED_OPTS={type:{replacement:"icon",link:"/docs/#icon"},imageUrl:{replacement:"icon",link:"/docs/#icon"},customClass:{replacement:"className",onlyRename:!0,link:"/docs/#classname"},imageSize:{},showCancelButton:{replacement:"buttons",link:"/docs/#buttons"},showConfirmButton:{replacement:"button",link:"/docs/#button"},confirmButtonText:{replacement:"button",link:"/docs/#button"},confirmButtonColor:{},cancelButtonText:{replacement:"buttons",link:"/docs/#buttons"},closeOnConfirm:{replacement:"button",subOption:"closeModal",link:"/docs/#button"},closeOnCancel:{replacement:"buttons",subOption:"closeModal",link:"/docs/#buttons"},showLoaderOnConfirm:{replacement:"buttons"},animation:{},inputType:{replacement:"content",link:"/docs/#content"},inputValue:{replacement:"content",link:"/docs/#content"},inputPlaceholder:{replacement:"content",link:"/docs/#content"},html:{replacement:"content",link:"/docs/#content"},allowEscapeKey:{replacement:"closeOnEsc",onlyRename:!0,link:"/docs/#closeonesc"},allowClickOutside:{replacement:"closeOnClickOutside",onlyRename:!0,link:"/docs/#closeonclickoutside"}}}])});
 
includes/user-interface/js/tvc_backup-list.js DELETED
@@ -1,89 +0,0 @@
1
- "use strict";
2
- /*global tvc_backup_list_form_vars */
3
-
4
- function tvc_resetBackupsList() {
5
- var backupListData = null;
6
- var listHtml = '';
7
- var backupListElement = jQuery( '#tvc-backups-list' );
8
-
9
- tvc_getBackupsList(
10
- function( list ) {
11
- if ( '0' !== list ) {
12
- backupListData = JSON.parse( list );
13
-
14
- // convert the data to html code
15
- listHtml = tvc_backupsTable( backupListData );
16
- } else {
17
- listHtml = tvc_emptyBackupsTable();
18
- }
19
-
20
- backupListElement.empty(); // first clear the feedlist
21
-
22
- backupListElement.append( listHtml );
23
- }
24
- );
25
- }
26
-
27
- /**
28
- * Restores the options on the settings page
29
- */
30
- function tvc_resetOptionSettings() {
31
- tvc_getSettingsOptions(
32
- function( optionsString ) {
33
-
34
- if ( optionsString ) {
35
- var options = JSON.parse( optionsString );
36
-
37
- jQuery( '#tvc_auto_feed_fix_mode' ).prop( 'checked', options[ 0 ] === 'true' );
38
- jQuery( '#tvc_background_processing_mode' ).prop( 'checked', options[ 3 ] === 'true' );
39
-
40
- jQuery( '#tvc_third_party_attr_keys' ).val( options[ 1 ] );
41
- jQuery( '#tvc_notice_mailaddress' ).val( options[ 2 ] );
42
- }
43
- }
44
- );
45
- }
46
-
47
- function tvc_backupsTable( list ) {
48
- var htmlCode = '';
49
-
50
- for ( var i = 0; i < list.length; i ++ ) {
51
-
52
- var backup = list[ i ].split( '&&' );
53
- var fileName = backup[ 0 ];
54
- var fileDate = backup[ 1 ];
55
-
56
- htmlCode += '<tr id="feed-row"';
57
- if ( i % 2 === 0 ) {
58
- htmlCode += ' class="alternate"';
59
- } // alternate background color per row
60
- htmlCode += '>';
61
- htmlCode += '<td id="file-name" value="' + fileName + '">' + fileName + '</td>';
62
- htmlCode += '<td id="file-date">' + fileDate + '</td>';
63
- htmlCode += '<td id="actions"><strong><a href="javascript:void(0);" id="tvc-delete-' + fileName.replace('.', '-') + '-backup-action" onclick="tvc_deleteBackupFile(\'' + fileName + '\')">' + tvc_backup_list_form_vars.list_delete + ' </a>';
64
- htmlCode += '| <a href="javascript:void(0);" id="tvc-restore-' + fileName.replace('.', '-') + '-backup-action" onclick="tvc_restoreBackupFile(\'' + fileName + '\')">' + tvc_backup_list_form_vars.list_restore + ' </a>';
65
- htmlCode += '| <a href="javascript:void(0);" id="tvc-duplicate-' + fileName.replace('.', '-') + '-backup-action" onclick="tvc_duplicateBackupFile(\'' + fileName + '\')">' + tvc_backup_list_form_vars.list_duplicate + ' </a></strong></td>';
66
- htmlCode += '</tr>';
67
- }
68
- return htmlCode;
69
- }
70
-
71
- function tvc_emptyBackupsTable() {
72
-
73
- var htmlCode = '';
74
- htmlCode += '<tr>';
75
- htmlCode += '<td colspan = 4>' + tvc_backup_list_form_vars.no_backup + '</td>';
76
- htmlCode += '</tr>';
77
-
78
- return htmlCode;
79
- }
80
-
81
- /**
82
- * Document ready actions
83
- */
84
- jQuery( document ).ready(
85
- function() {
86
- // fill the backups list
87
- tvc_resetBackupsList();
88
- }
89
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_backup-list.min.js DELETED
@@ -1,60 +0,0 @@
1
- function tvc_resetBackupsList() {
2
- var a = null;
3
- var b = "";
4
- var c = jQuery("#tvc-backups-list");
5
- tvc_getBackupsList(function (d) {
6
- if ("0" !== d) {
7
- a = JSON.parse(d);
8
- b = tvc_backupsTable(a)
9
- } else {
10
- b = tvc_emptyBackupsTable()
11
- }
12
- c.empty();
13
- c.append(b)
14
- })
15
- }
16
-
17
- function tvc_resetOptionSettings() {
18
- tvc_getSettingsOptions(function (b) {
19
- if (b) {
20
- var a = JSON.parse(b);
21
- jQuery("#tvc_auto_feed_fix_mode").prop("checked", a[0] === "true");
22
- jQuery("#tvc_background_processing_mode").prop("checked", a[3] === "true");
23
- jQuery("#tvc_third_party_attr_keys").val(a[1]);
24
- jQuery("#tvc_notice_mailaddress").val(a[2])
25
- }
26
- })
27
- }
28
-
29
- function tvc_backupsTable(d) {
30
- var c = "";
31
- for (var b = 0; b < d.length; b++) {
32
- var a = d[b].split("&&");
33
- var f = a[0];
34
- var e = a[1];
35
- c += '<tr id="feed-row"';
36
- if (b % 2 === 0) {
37
- c += ' class="alternate"'
38
- }
39
- c += ">";
40
- c += '<td id="file-name" value="' + f + '">' + f + "</td>";
41
- c += '<td id="file-date">' + e + "</td>";
42
- c += '<td id="actions"><strong><a href="javascript:void(0);" id="tvc-delete-' + f.replace(".", "-") + '-backup-action" onclick="tvc_deleteBackupFile(\'' + f + "')\">" + tvc_backup_list_form_vars.list_delete + " </a>";
43
- c += '| <a href="javascript:void(0);" id="tvc-restore-' + f.replace(".", "-") + '-backup-action" onclick="tvc_restoreBackupFile(\'' + f + "')\">" + tvc_backup_list_form_vars.list_restore + " </a>";
44
- c += '| <a href="javascript:void(0);" id="tvc-duplicate-' + f.replace(".", "-") + '-backup-action" onclick="tvc_duplicateBackupFile(\'' + f + "')\">" + tvc_backup_list_form_vars.list_duplicate + " </a></strong></td>";
45
- c += "</tr>"
46
- }
47
- return c
48
- }
49
-
50
- function tvc_emptyBackupsTable() {
51
- var a = "";
52
- a += "<tr>";
53
- a += "<td colspan = 4>" + tvc_backup_list_form_vars.no_backup + "</td>";
54
- a += "</tr>";
55
- return a
56
- }
57
-
58
- jQuery(document).ready(function () {
59
- tvc_resetBackupsList()
60
- });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-form-events.js DELETED
@@ -1,331 +0,0 @@
1
- "use strict";
2
- jQuery( document ).ready(
3
- function( jQuery ) {
4
- var fileNameElement = jQuery( '#file-name' );
5
- var merchantsElement = jQuery( '#tvc-merchants-selector' );
6
- var countriesElement = jQuery( '#tvc-countries-selector' );
7
- var level0Element = jQuery( '#lvl_0' );
8
-
9
- // monitor the four main feed settings and react when they change
10
- fileNameElement.on(
11
- 'focusout',
12
- function() {
13
- if ( '' !== fileNameElement.val() ) {
14
- countriesElement.prop( 'disabled', false );
15
- level0Element.prop( 'disabled', false );
16
- if ( false === tvc_validateFileName( fileNameElement.val() ) ) {
17
- fileNameElement.val( '' );
18
- }
19
-
20
- if ( '0' !== merchantsElement.val() ) {
21
- tvc_showChannelInputs( merchantsElement.val(), true );
22
- tvc_mainInputChanged( false );
23
- } else {
24
- tvc_hideFeedFormMainInputs();
25
- }
26
- } else {
27
- countriesElement.prop( 'disabled', true );
28
- level0Element.prop( 'disabled', true );
29
- }
30
- }
31
- );
32
-
33
- fileNameElement.on(
34
- 'keyup',
35
- function() {
36
-
37
- if ( '' !== fileNameElement.val() ) {
38
- countriesElement.prop( 'disabled', false );
39
- level0Element.prop( 'disabled', false );
40
- } else {
41
- countriesElement.prop( 'disabled', true );
42
- level0Element.prop( 'disabled', true );
43
- }
44
- }
45
- );
46
-
47
- countriesElement.on(
48
- 'change',
49
- function() {
50
- if ( '0' !== countriesElement.val() ) {
51
- level0Element.prop( 'disabled', false );
52
- }
53
-
54
- tvc_mainInputChanged( false );
55
- }
56
- );
57
-
58
- jQuery( '#tvc-feed-language-selector' ).on(
59
- 'change',
60
- function() {
61
- tvc_setGoogleFeedLanguage( jQuery( '#tvc-feed-language-selector' ).val() );
62
-
63
- if ( tvc_requiresLanguageInput ) {
64
- tvc_mainInputChanged( false );
65
- }
66
- }
67
- );
68
-
69
- jQuery( '#google-feed-title-selector' ).on(
70
- 'change',
71
- function() {
72
- tvc_setGoogleFeedTitle( jQuery( '#google-feed-title-selector' ).val() );
73
- }
74
- );
75
-
76
- jQuery( '#google-feed-description-selector' ).on(
77
- 'change',
78
- function() {
79
- tvc_setGoogleFeedDescription( jQuery( '#google-feed-description-selector' ).val() );
80
- }
81
- );
82
-
83
- merchantsElement.on(
84
- 'change',
85
- function() {
86
- if ( '0' !== merchantsElement.val() && '' !== jQuery( '#file-name' ).val() ) {
87
- tvc_showChannelInputs( jQuery( '#tvc-merchants-selector' ).val(), true );
88
- tvc_mainInputChanged( false );
89
- } else {
90
- tvc_hideFeedFormMainInputs();
91
- }
92
- }
93
- );
94
-
95
- jQuery( '#variations' ).on(
96
- 'change',
97
- function() {
98
- tvc_variation_selection_changed();
99
- }
100
- );
101
-
102
- jQuery( '#aggregator' ).on(
103
- 'change',
104
- function() {
105
- tvc_aggregatorChanged();
106
- tvc_drawAttributeMappingSection(); // reset the attribute mapping
107
- }
108
- );
109
-
110
- level0Element.on(
111
- 'change',
112
- function() {
113
- tvc_mainInputChanged( true );
114
- }
115
- );
116
-
117
- jQuery( '.tvc-cat-selector' ).on(
118
- 'change',
119
- function() {
120
- tvc_nextCategory( this.id );
121
- }
122
- );
123
-
124
- jQuery( '#tvc-generate-feed-button-top' ).on(
125
- 'click',
126
- function() {
127
- tvc_generateFeed();
128
- }
129
- );
130
-
131
- jQuery( '#tvc-generate-feed-button-bottom' ).on(
132
- 'click',
133
- function() {
134
- tvc_generateFeed();
135
- }
136
- );
137
-
138
- jQuery( '#tvc-save-feed-button-top' ).on(
139
- 'click',
140
- function() {
141
- tvc_saveFeedData();
142
- }
143
- );
144
-
145
- jQuery( '#tvc-view-feed-button-top' ).on(
146
- 'click',
147
- function() {
148
- tvc_viewFeed( jQuery( '#tvc-feed-url' ).text() );
149
- }
150
- );
151
-
152
- jQuery( '#tvc-view-feed-button-bottom' ).on(
153
- 'click',
154
- function() {
155
- tvc_viewFeed( jQuery( '#tvc-feed-url' ).text() );
156
- }
157
- );
158
-
159
- jQuery( '#tvc-save-feed-button-bottom' ).on(
160
- 'click',
161
- function() {
162
- tvc_saveFeedData();
163
- }
164
- );
165
-
166
- jQuery( '#days-interval' ).on(
167
- 'change',
168
- function() {
169
- tvc_saveUpdateSchedule();
170
- }
171
- );
172
-
173
- jQuery( '#update-schedule-hours' ).on(
174
- 'change',
175
- function() {
176
- tvc_saveUpdateSchedule();
177
- }
178
- );
179
-
180
- jQuery( '#update-schedule-minutes' ).on(
181
- 'change',
182
- function() {
183
- tvc_saveUpdateSchedule();
184
- }
185
- );
186
-
187
- jQuery( '#update-schedule-frequency' ).on(
188
- 'change',
189
- function() {
190
- tvc_saveUpdateSchedule();
191
- }
192
- );
193
-
194
- jQuery( '#tvc_auto_feed_fix_mode' ).on(
195
- 'change',
196
- function() {
197
- tvc_auto_feed_fix_changed();
198
- }
199
- );
200
-
201
- jQuery( '#tvc_background_processing_mode' ).on(
202
- 'change',
203
- function() {
204
- tvc_clear_feed_process();
205
- tvc_background_processing_mode_changed();
206
- }
207
- );
208
-
209
- jQuery( '#tvc_process_logging_mode' ).on(
210
- 'change',
211
- function() {
212
- tvc_feed_logger_status_changed();
213
- }
214
- );
215
-
216
- jQuery( '#tvc_product_identifiers' ).on(
217
- 'change',
218
- function() {
219
- tvc_show_product_identifiers_changed();
220
- }
221
- );
222
-
223
- jQuery( '#tvc_third_party_attr_keys' ).on(
224
- 'focusout',
225
- function() {
226
- tvc_third_party_attributes_changed();
227
- }
228
- );
229
-
230
- jQuery( '#tvc_notice_mailaddress' ).on(
231
- 'focusout',
232
- function() {
233
- tvc_notice_mailaddress_changed();
234
- }
235
- );
236
-
237
- jQuery( '#tvc-clear-feed-process-button' ).on(
238
- 'click',
239
- function() {
240
- tvc_clear_feed_process();
241
- }
242
- );
243
-
244
- jQuery( '#tvc-reinitiate-plugin-button' ).on(
245
- 'click',
246
- function() {
247
- tvc_reinitiate();
248
- }
249
- );
250
-
251
- jQuery( '.tvc-category-mapping-selector' ).on( // on activation of a category selector in the Category Mapping table
252
- 'change',
253
- function() {
254
- if ( jQuery( this ).is( ':checked' ) ) {
255
- console.log( 'category ' + jQuery( this ).val() + ' selected' );
256
- tvc_activateFeedCategoryMapping( jQuery( this ).val() );
257
- } else {
258
- console.log( 'category ' + jQuery( this ).val() + ' deselected' );
259
- tvc_deactivateFeedCategoryMapping( jQuery( this ).val() );
260
- }
261
- }
262
- );
263
-
264
- jQuery( '.tvc-category-selector' ).on( // on activation of a category selector in the Category Selector table
265
- 'change',
266
- function() {
267
- if ( jQuery( this ).is( ':checked' ) ) {
268
- console.log( 'category ' + jQuery( this ).val() + ' selected' );
269
- tvc_activateFeedCategorySelection( jQuery( this ).val() );
270
- } else {
271
- console.log( 'category ' + jQuery( this ).val() + ' deselected' );
272
- tvc_deactivateFeedCategorySelection( jQuery( this ).val() );
273
- }
274
- }
275
- );
276
-
277
- jQuery( '#tvc-categories-select-all' ).on( // on activation of the 'all' selector in the Category Mapping and Category Selector table
278
- 'change',
279
- function() {
280
- if ( jQuery( this ).is( ':checked' ) ) {
281
- tvc_activateAllFeedCategoryMapping();
282
- } else {
283
- tvc_deactivateAllFeedCategoryMapping();
284
- }
285
- }
286
- );
287
-
288
- jQuery( '#tvc_accept_eula' ).on(
289
- 'change',
290
- function() {
291
- if ( jQuery( this ).is( ':checked' ) ) {
292
- jQuery( '#tvc_license_activate' ).prop( 'disabled', false );
293
- } else {
294
- jQuery( '#tvc_license_activate' ).prop( 'disabled', true );
295
- }
296
- }
297
- );
298
-
299
-
300
- jQuery( '#tvc_prepare_backup' ).on(
301
- 'click',
302
- function() {
303
- jQuery( '#tvc_backup-file-name' ).val( '' );
304
- jQuery( '#tvc_backup-wrapper' ).show();
305
- }
306
- );
307
-
308
- jQuery( '#tvc_make_backup' ).on(
309
- 'click',
310
- function() {
311
- tvc_backup();
312
- }
313
- );
314
-
315
- jQuery( '#tvc_cancel_backup' ).on(
316
- 'click',
317
- function() {
318
- jQuery( '#tvc_backup-wrapper' ).hide();
319
- }
320
- );
321
-
322
- jQuery( '#tvc_backup-file-name' ).on(
323
- 'keyup',
324
- function() {
325
- if ( '' !== jQuery( '#tvc_backup-file-name' ).val ) {
326
- jQuery( '#tvc_make_backup' ).attr( 'disabled', false );
327
- }
328
- }
329
- );
330
- }
331
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-form-events.min.js DELETED
@@ -1 +0,0 @@
1
- jQuery(document).ready(function(c){var d=c("#file-name");var b=c("#tvc-merchants-selector");var a=c("#tvc-countries-selector");var e=c("#lvl_0");d.on("focusout",function(){if(""!==d.val()){a.prop("disabled",false);e.prop("disabled",false);if(false===tvc_validateFileName(d.val())){d.val("")}if("0"!==b.val()){tvc_showChannelInputs(b.val(),true);tvc_mainInputChanged(false)}else{tvc_hideFeedFormMainInputs()}}else{a.prop("disabled",true);e.prop("disabled",true)}});d.on("keyup",function(){if(""!==d.val()){a.prop("disabled",false);e.prop("disabled",false)}else{a.prop("disabled",true);e.prop("disabled",true)}});a.on("change",function(){if("0"!==a.val()){e.prop("disabled",false)}tvc_mainInputChanged(false)});c("#tvc-feed-language-selector").on("change",function(){tvc_setGoogleFeedLanguage(jQuery("#tvc-feed-language-selector").val());if(tvc_requiresLanguageInput){tvc_mainInputChanged(false)}});c("#google-feed-title-selector").on("change",function(){tvc_setGoogleFeedTitle(jQuery("#google-feed-title-selector").val())});c("#google-feed-description-selector").on("change",function(){tvc_setGoogleFeedDescription(jQuery("#google-feed-description-selector").val())});b.on("change",function(){if("0"!==b.val()&&""!==c("#file-name").val()){tvc_showChannelInputs(c("#tvc-merchants-selector").val(),true);tvc_mainInputChanged(false)}else{tvc_hideFeedFormMainInputs()}});c("#variations").on("change",function(){tvc_variation_selection_changed()});c("#aggregator").on("change",function(){tvc_aggregatorChanged();tvc_drawAttributeMappingSection()});e.on("change",function(){tvc_mainInputChanged(true)});c(".tvc-cat-selector").on("change",function(){tvc_nextCategory(this.id)});c("#tvc-generate-feed-button-top").on("click",function(){tvc_generateFeed()});c("#tvc-generate-feed-button-bottom").on("click",function(){tvc_generateFeed()});c("#tvc-save-feed-button-top").on("click",function(){tvc_saveFeedData()});c("#tvc-view-feed-button-top").on("click",function(){tvc_viewFeed(c("#tvc-feed-url").text())});c("#tvc-view-feed-button-bottom").on("click",function(){tvc_viewFeed(c("#tvc-feed-url").text())});c("#tvc-save-feed-button-bottom").on("click",function(){tvc_saveFeedData()});c("#days-interval").on("change",function(){tvc_saveUpdateSchedule()});c("#update-schedule-hours").on("change",function(){tvc_saveUpdateSchedule()});c("#update-schedule-minutes").on("change",function(){tvc_saveUpdateSchedule()});c("#update-schedule-frequency").on("change",function(){tvc_saveUpdateSchedule()});c("#tvc_auto_feed_fix_mode").on("change",function(){tvc_auto_feed_fix_changed()});c("#tvc_background_processing_mode").on("change",function(){tvc_clear_feed_process();tvc_background_processing_mode_changed()});c("#tvc_process_logging_mode").on("change",function(){tvc_feed_logger_status_changed()});c("#tvc_product_identifiers").on("change",function(){tvc_show_product_identifiers_changed()});c("#tvc_third_party_attr_keys").on("focusout",function(){tvc_third_party_attributes_changed()});c("#tvc_notice_mailaddress").on("focusout",function(){tvc_notice_mailaddress_changed()});c("#tvc-clear-feed-process-button").on("click",function(){tvc_clear_feed_process()});c("#tvc-reinitiate-plugin-button").on("click",function(){tvc_reinitiate()});c(".tvc-category-mapping-selector").on("change",function(){if(c(this).is(":checked")){console.log("category "+c(this).val()+" selected");tvc_activateFeedCategoryMapping(c(this).val())}else{console.log("category "+c(this).val()+" deselected");tvc_deactivateFeedCategoryMapping(c(this).val())}});c(".tvc-category-selector").on("change",function(){if(c(this).is(":checked")){console.log("category "+c(this).val()+" selected");tvc_activateFeedCategorySelection(c(this).val())}else{console.log("category "+c(this).val()+" deselected");tvc_deactivateFeedCategorySelection(c(this).val())}});c("#tvc-categories-select-all").on("change",function(){if(c(this).is(":checked")){tvc_activateAllFeedCategoryMapping()}else{tvc_deactivateAllFeedCategoryMapping()}});c("#tvc_accept_eula").on("change",function(){if(c(this).is(":checked")){c("#tvc_license_activate").prop("disabled",false)}else{c("#tvc_license_activate").prop("disabled",true)}});c("#tvc_prepare_backup").on("click",function(){c("#tvc_backup-file-name").val("");c("#tvc_backup-wrapper").show()});c("#tvc_make_backup").on("click",function(){tvc_backup()});c("#tvc_cancel_backup").on("click",function(){c("#tvc_backup-wrapper").hide()});c("#tvc_backup-file-name").on("keyup",function(){if(""!==c("#tvc_backup-file-name").val){c("#tvc_make_backup").attr("disabled",false)}})});
 
includes/user-interface/js/tvc_feed-form.js DELETED
@@ -1,2604 +0,0 @@
1
- "use strict";
2
- /*global tvc_feed_settings_form_vars */
3
- var tvc_backup_list_form_vars = '';
4
- var _mandatoryFields = [];
5
- var _highlyRecommendedFields = [];
6
- var _recommendedFields = [];
7
- var _undefinedRecommendedOutputs = [];
8
- var _definedRecommendedOutputs = [];
9
- var _optionalFields = [];
10
- var _undefinedOptionalOutputs = [];
11
- var _definedOptionalOutputs = [];
12
- var _undefinedCustomOutputs = [];
13
- var _customFields = [];
14
- var _inputFields = [];
15
- var _feedHolder = [];
16
-
17
- /**
18
- * Gets triggered when one of the main inputs on the edit feed page has changed. This function starts a new feed when all
19
- * main inputs are given or updates the existing feed if required, based on the changed main input.
20
- *
21
- * @param {boolean} categoryChanged True if the the Default Category input changed.
22
- */
23
- function tvc_mainInputChanged( categoryChanged ) {
24
- var channel = jQuery( '#tvc-merchants-selector' ).val();
25
- var feedId = _feedHolder[ 'feedId' ];
26
-
27
- tvc_reactOnChannelInputChanged( channel, feedId, categoryChanged );
28
- }
29
-
30
- /**
31
- * Makes sure the feed name does not contain any special characters or already exists.
32
- *
33
- * @param {string} fileNameElement The feed name name.
34
- *
35
- * @return {void|boolean} Returns false when the file name is not valid.
36
- */
37
- function tvc_validateFileName( fileNameElement ) {
38
- if ( ! tvc_contains_special_characters( fileNameElement ) ) {
39
- var existingFileNames = JSON.parse( jQuery( '#tvc-all-feed-names' ).text() );
40
-
41
- // test if file name already exists
42
- if ( -1 === jQuery.inArray( fileNameElement, existingFileNames ) ) {
43
- _feedHolder[ 'title' ] = fileNameElement;
44
- } else {
45
- alert( tvc_feed_settings_form_vars.feed_name_exists );
46
- return false;
47
- }
48
- } else {
49
- alert( tvc_feed_settings_form_vars.prohibited_feed_name_characters );
50
- return false;
51
- }
52
- }
53
-
54
- function tvc_freeCategoryChanged( type, id ) {
55
- if ( type === 'default' ) { // default category selection changed
56
- if ( id ) {
57
- if ( id > 0 ) {
58
- _feedHolder.setCustomCategory( undefined, jQuery( '#free-category-text-input' ).val() );
59
- } else {
60
- tvc_mainInputChanged( true );
61
- }
62
- } else {
63
-
64
- tvc_mainInputChanged( true );
65
- }
66
-
67
- } else { // category mapping selection changed
68
- //tvc_setChildCategories( id, jQuery( '#feed-category-' + id + ' :input' ).val() ); // TODO: would be better if I could reuse this function
69
- _feedHolder.changeCustomFeedCategoryMap( id, jQuery( '#feed-category-' + id + ' :input' ).val() );
70
- }
71
- }
72
-
73
- /**
74
- * Generates a new feed and opens the feed table.
75
- */
76
- function tvc_constructNewFeed() {
77
- var daysIntervalElement = jQuery( '#days-interval' );
78
- var updateScheduleHourElement = jQuery( '#update-schedule-hours' );
79
- var updateScheduleMinutesElement = jQuery( '#update-schedule-minutes' );
80
- var updateScheduleFrequencyElement = jQuery( '#update-schedule-frequency' );
81
-
82
- // get all the data from the input fields
83
- var fileName = jQuery( '#file-name' ).val();
84
- var source = '1';
85
- var mainCategory = jQuery( '#lvl_0 option:selected' ).text();
86
- var categoryMapping = [];
87
- var channel = jQuery( '#tvc-merchants-selector' ).val();
88
- var variations = jQuery( '#variations' ).is( ':checked' ) ? 1 : 0;
89
- var aggregator = jQuery( '#aggregator' ).is( ':checked' ) ? 1 : 0;
90
- var country = jQuery( '#tvc-countries-selector' ).val();
91
- var language = document.getElementById( 'language' ) === null ? '' : jQuery( '#tvc-feed-language-selector' ).val();
92
- var feedTitle = jQuery( '#google-feed-title-selector' ).val();
93
- var feedDescription = jQuery( '#google-feed-description-selector' ).val();
94
- var daysInterval = daysIntervalElement.val() !== '' ? daysIntervalElement.val() : '1';
95
- var hours = updateScheduleHourElement.val() !== '' ? updateScheduleHourElement.val() : '00';
96
- var minutes = updateScheduleMinutesElement.val() !== '' ? updateScheduleMinutesElement.val() : '00';
97
- var frequency = updateScheduleFrequencyElement.val() !== '' ? updateScheduleFrequencyElement.val() : '1';
98
- var feedFilter = [];
99
- var status = 2;
100
- var channelFeedType = tvc_getChannelFeedType( channel );
101
- var feedType = '1';
102
-
103
- // make the url to the feed file
104
- var url = jQuery( '#wp-plugin-url' ).text() + '/tvc-feeds/' + fileName + '.' + channelFeedType;
105
- var updates = daysInterval + ':' + hours + ':' + minutes + ':' + frequency;
106
-
107
- tvc_setScheduleSelector( daysInterval, frequency );
108
-
109
- // make a new feed object
110
- _feedHolder = new Feed( - 1, fileName, variations, aggregator, parseInt( channel ), mainCategory, categoryMapping, url, source, country, language, feedTitle, feedDescription,
111
- updates, feedFilter, status, feedType );
112
- }
113
-
114
- /**
115
- * This function can be used by special feed add-on plugins to handle construction of a new non standard feed.
116
- *
117
- * @param {object} specialFeedFeedHolder
118
- */
119
- function tvc_constructNewSpecialFeed( specialFeedFeedHolder ) {
120
- _feedHolder = specialFeedFeedHolder;
121
- }
122
-
123
- /**
124
- * This function allows to set a feed property that are to be used for special feeds like Google Product Review Feeds.
125
- *
126
- * @param {string} key name of the property
127
- * @param {string|int|array} value value the property should get
128
- * @param {string} type type of the property, like string, int or array
129
- */
130
- function tvc_setSpecialFeedProperty( key, value, type ) {
131
- if ( _feedHolder.hasOwnProperty( key ) ) {
132
- if ( 'object' === typeof _feedHolder[ key ] ) {
133
- _feedHolder[ key ].push( value );
134
- } else {
135
- _feedHolder[ key ] = value;
136
- }
137
- } else {
138
- if ( 'array' === type ) {
139
- _feedHolder[ key ] = [];
140
- _feedHolder[ key ].push( value );
141
- } else {
142
- _feedHolder[ key ] = value;
143
- }
144
- }
145
- }
146
-
147
- /**
148
- * Unset an item from a special feed property of type array or object.
149
- *
150
- * @param {string} key name of the property
151
- * @param {string|int} value value to be removed from the array or object
152
- */
153
- function tvc_unsetSpecialFeedArrayProperty( key, value ) {
154
- if ( _feedHolder.hasOwnProperty( key ) && 'object' === typeof _feedHolder[ key ] ) {
155
- var index = _feedHolder[ key ].indexOf( value );
156
- _feedHolder[ key ].splice( index, 1 );
157
- }
158
- }
159
-
160
- function tvc_finishOrUpdateFeedPage( categoryChanged ) {
161
- var selectedChannelElement = jQuery( '#tvc-merchants-selector' );
162
- var lvl0Element = jQuery( '#lvl_0' );
163
- var selectedChannelValue = selectedChannelElement.val().toString();
164
-
165
- tvc_showFeedSpinner();
166
-
167
- // make sure the data is correct
168
- _feedHolder[ 'title' ] = jQuery( '#file-name' ).val();
169
- _feedHolder[ 'channel' ] = selectedChannelElement.val();
170
- _feedHolder[ 'includeVariations' ] = jQuery( '#variations' ).is( ':checked' ) ? '1' : '0';
171
- _feedHolder[ 'isAggregator' ] = jQuery( '#aggregator' ).is( ':checked' ) ? '1' : '0';
172
- _feedHolder[ 'feedTitle' ] = jQuery( '#google-feed-title-selector' ).val();
173
- _feedHolder[ 'feedDescription' ] = jQuery( '#google-feed-description-selector' ).val();
174
- _feedHolder[ 'language' ] = document.getElementById( 'language' ) === null ? '' : jQuery( '#tvc-feed-language-selector' ).val();
175
-
176
- // get the output fields that can be used with the selected channel
177
- tvc_getFeedAttributes( - 1, selectedChannelValue, function( outputs ) {
178
-
179
- _feedHolder.setUpdateSchedule( jQuery( '#days-interval' ).val(), jQuery( '#update-schedule-hours' ).val(),
180
- jQuery( '#update-schedule-minutes' ).val(), jQuery( '#update-schedule-frequency' ).val() );
181
-
182
- // add the default attributes if attributes are not set
183
- if ( undefined === _feedHolder[ 'attributes' ] || 0 === _feedHolder[ 'attributes' ].length ) {
184
- tvc_addFeedAttributes( outputs, selectedChannelValue, 1 );
185
- }
186
-
187
- tvc_customSourceFields( _feedHolder[ 'dataSource' ], function( customFields ) {
188
-
189
- _feedHolder[ 'country' ] = jQuery( '#tvc-countries-selector' ).val();
190
- _feedHolder[ 'language' ] = jQuery( '#tvc-feed-language-selector' ).val();
191
-
192
- tvc_fillSourcesList( customFields );
193
-
194
- tvc_mainFeedFilters( _feedHolder[ 'feedId' ], function( feedFilters ) {
195
-
196
- // get the master feed filter
197
- var mainFeedFilter = feedFilters !== 1 ? feedFilters : null;
198
- var attributeLevelArgs = '0' !== _feedHolder[ 'country' ] ? _feedHolder[ 'country' ] : _feedHolder[ 'language' ];
199
-
200
- _feedHolder.setFeedFilter( mainFeedFilter );
201
-
202
- // set the correct level of the attributes
203
- _feedHolder = tvc_setOutputAttributeLevels( selectedChannelValue, _feedHolder, attributeLevelArgs );
204
-
205
-
206
-
207
- if ( categoryChanged ) {
208
- _feedHolder[ 'mainCategory' ] = lvl0Element.val() ? lvl0Element.val() : jQuery( '#free-category-text-input' ).val();
209
- _feedHolder.setMainCategory( 'lvl_0', lvl0Element.val(), selectedChannelValue );
210
- }
211
-
212
- // draws the attribute mapping section on the form
213
- tvc_drawAttributeMappingSection();
214
-
215
- if ( _feedHolder !== 0 ) {
216
- var isNew = _feedHolder[ 'feedId' ] === - 1;
217
- tvc_fillFeedFields( isNew, categoryChanged );
218
- }
219
-
220
- console.log(_feedHolder );
221
-
222
- // TODO: somewhere between the initialization of channel in _feedHolder the channel id is changed
223
- // to an integer in stead of the required string. For now I just reset the variable to
224
- // a string again, but I need to figure out why this is happening. Before the tvc_addFeedAttributes
225
- // it is still a string. When it's an int, the static menus of a new feed will not work anymore.
226
- _feedHolder[ 'channel' ] = selectedChannelValue;
227
-
228
- // show the buttons again
229
- jQuery( '#page-center-buttons' ).show();
230
- jQuery( '#page-bottom-buttons' ).show();
231
- jQuery( '#page-bottom-api-buttons' ).show();
232
-
233
- tvc_hideFeedSpinner();
234
- } );
235
- } );
236
- } );
237
- }
238
-
239
- /**
240
- * This function can be used by special feed add-ons to handle special feed updates.
241
- *
242
- * @param {array} specialFeedFeedHolder
243
- */
244
- function tvc_finishOrUpdateSpecialFeedPage( specialFeedFeedHolder ) {
245
- _feedHolder = specialFeedFeedHolder;
246
-
247
- // draws the attribute mapping section on the form
248
- tvc_drawAttributeMappingSection();
249
-
250
- if ( _feedHolder ) {
251
- var isNew = _feedHolder[ 'feedId' ] === - 1;
252
- tvc_fillFeedFields( isNew, false );
253
- }
254
-
255
- // show the buttons again
256
- jQuery( '#page-center-buttons' ).show();
257
- jQuery( '#page-bottom-buttons' ).show();
258
- jQuery( '#page-bottom-api-buttons' ).show();
259
- }
260
-
261
- function tvc_initiateFeed() {
262
-
263
- var feedDataElementValue = jQuery( '#tvc-ajax-feed-data-array' ).text();
264
- var redirectAfterFeedGenerate = jQuery('#tvc-attribute-map-2').trigger('click');
265
-
266
- if ( ! feedDataElementValue ) {
267
- return;
268
- }
269
-
270
- var feedData = JSON.parse( feedDataElementValue ); // get the data from the edit feed form code
271
-
272
- console.log(feedData);
273
-
274
-
275
- // make a _feedHolder
276
- if ( feedData ) {
277
- _feedHolder = new Feed(
278
- feedData['feed_id'],
279
- feedData['feed_file_name'],
280
- feedData['include_variations'],
281
- feedData['is_aggregator'],
282
- feedData['channel_id'],
283
- feedData['main_category'],
284
- feedData['category_mapping'],
285
- feedData['url'],
286
- feedData['source'],
287
- feedData['target_country'],
288
- feedData['language'],
289
- feedData['feed_title'],
290
- feedData['feed_description'],
291
- feedData['schedule'],
292
- [],
293
- feedData['status_id'],
294
- '1'
295
- );
296
-
297
- tvc_addFeedAttributes( feedData['attribute_data'], feedData['channel_id'], 1 );
298
-
299
- _feedHolder.setFeedFilter( feedData['feed_filter'] );
300
-
301
- // _feedHolder.setSourceValue( feedData['source_fields'] );
302
- _feedHolder['source_fields'] = feedData['source_fields'];
303
-
304
- jQuery(document).ready(function(){
305
- jQuery('#tvc-attribute-map-2').trigger('click');
306
- })
307
- }
308
- }
309
-
310
- /**
311
- * Builds up the Edit Feed page for an already existing feed.
312
- *
313
- * @param {string} feedId The id of the feed.
314
- */
315
- function tvc_editExistingFeed( feedId ) {
316
-
317
- // exit if the incorrect data is loaded
318
- if ( feedId !== _feedHolder[ 'feedId' ] ) {
319
- return;
320
- }
321
-
322
- var channel = _feedHolder[ 'channel' ];
323
- var categoryString = _feedHolder[ 'mainCategory' ];
324
- var mainCategory = categoryString && categoryString.indexOf( ' > ' ) > - 1 ? categoryString.substring( 0, categoryString.indexOf( ' > ' ) ) : categoryString;
325
-
326
- tvc_fillCategoryVariables( channel, mainCategory, '0' ); // make sure the category values are set correctly
327
-
328
- tvc_fillSourcesList( _feedHolder[ 'source_fields' ] );
329
-
330
- var attributeLevelArgs = ! tvc_requiresLanguageInput( channel ) ? _feedHolder[ 'country' ] : _feedHolder[ 'language' ];
331
-
332
- // set the correct level of the attributes
333
- _feedHolder = tvc_setOutputAttributeLevels( channel, _feedHolder, attributeLevelArgs );
334
-
335
- // draws the attribute mapping section on the form
336
- tvc_drawAttributeMappingSection();
337
-
338
- if ( _feedHolder !== 0 ) {
339
- tvc_fillFeedFields( false, false );
340
- }
341
-
342
- if ( _feedHolder[ 'categoryMapping' ] ) {
343
- tvc_setCategoryMap( _feedHolder[ 'categoryMapping' ] );
344
- }
345
-
346
- // enable the Generate and Save buttons and the target country selection
347
- tvc_enableFeedActionButtons();
348
-
349
- jQuery( '#tvc-countries-selector' ).prop( 'disabled', false );
350
-
351
- // set the default categories select fields in the background
352
- tvc_fillDefaultCategorySelectors();
353
-
354
- // set the identifier_exists layout
355
- tvc_setIdentifierExistsDependancies();
356
-
357
- // show the buttons again
358
- jQuery( 'div' ).filter( '#page-center-buttons' ).show();
359
- jQuery( '#page-bottom-buttons' ).show();
360
- jQuery( '#page-bottom-api-buttons' ).show();
361
- }
362
-
363
- function tvc_fillSourcesList( customFields ) {
364
- _inputFields = tvc_woocommerceSourceOptions();
365
- tvc_addCustomFieldsToInputFields( _inputFields, customFields );
366
- _inputFields.sort( function( a, b ) {
367
- return (
368
- '' + a.label
369
- ).toUpperCase() < (
370
- '' + b.label
371
- ).toUpperCase() ? - 1 : 1;
372
- }
373
- );
374
- }
375
-
376
- function tvc_saveUpdateSchedule() {
377
-
378
- // get the values
379
- var days = jQuery( '#days-interval' ).val();
380
- var hours = jQuery( '#update-schedule-hours' ).val();
381
- var minutes = jQuery( '#update-schedule-minutes' ).val();
382
- var freq = jQuery( '#update-schedule-frequency' ).val();
383
-
384
- // change the form selector if required
385
- if ( days !== '1' ) {
386
- freq = '1';
387
- }
388
-
389
- if ( freq === 1 ) {
390
- days = '1';
391
- }
392
-
393
- tvc_setScheduleSelector( days, freq );
394
-
395
- // store the selection in the feed
396
- _feedHolder.setUpdateSchedule( days, hours, minutes, freq );
397
- }
398
-
399
- function tvc_setScheduleSelector( days, freq ) {
400
- var updateFrequencyWrapperElement = jQuery( '#tvc-update-frequency-wrapper' );
401
- var updateDayWrapperElement = jQuery( '#tvc-update-day-wrapper' );
402
- var updateEveryDayWrapperElement = jQuery( '#tvc-update-every-day-wrapper' );
403
-
404
- // change the form selector if required
405
- if ( days === '1' ) {
406
- updateFrequencyWrapperElement.show();
407
- } else {
408
- updateFrequencyWrapperElement.hide();
409
- }
410
-
411
- if ( freq > 1 ) {
412
- updateDayWrapperElement.hide();
413
- updateEveryDayWrapperElement.show();
414
- } else {
415
- updateDayWrapperElement.show();
416
- updateEveryDayWrapperElement.hide();
417
- }
418
- }
419
-
420
- function tvc_addCustomFieldsToInputFields( inputFields, customFields ) {
421
-
422
- if ( customFields !== '0' ) {
423
- for ( var i = 0; i < customFields.length; i ++ ) {
424
-
425
- var field = {
426
- value: customFields[ i ].attribute_name,
427
- label: customFields[ i ].attribute_label,
428
- prop: 'custom',
429
- };
430
- inputFields.push( field );
431
- }
432
- }
433
- }
434
-
435
- /**
436
- * Gets the correct categories from the category file and fills the category selector with them
437
- */
438
- function tvc_fillDefaultCategorySelectors() {
439
- var mainCategoriesString = _feedHolder[ 'mainCategory' ];
440
- var channel = _feedHolder[ 'channel' ];
441
- var language = tvc_channelCountryCode( channel );
442
-
443
- tvc_getCategoryListsFromString( channel, mainCategoriesString, language, function( categories ) {
444
- var lists = JSON.parse( categories );
445
-
446
- if ( lists && lists.length > 0 && mainCategoriesString !== undefined ) {
447
- var categoriesArray = mainCategoriesString.split( ' > ' );
448
-
449
- for ( var i = 0; i < lists.length; i ++ ) {
450
- jQuery( '#lvl_' + i ).append( tvc_categorySelectCntrl( lists[ i ] ) );
451
-
452
- var element = document.getElementById( 'lvl_' + i );
453
- element.value = categoriesArray[ i ];
454
- }
455
- } else {
456
- jQuery( '#lvl_0' ).prop( 'disabled', false );
457
- }
458
- } );
459
- }
460
-
461
- function tvc_setGoogleFeedTitle( value ) {
462
- _feedHolder[ 'feedTitle' ] = value;
463
- }
464
-
465
- function tvc_setGoogleFeedDescription( value ) {
466
- _feedHolder[ 'feedDescription' ] = value;
467
- }
468
-
469
- function tvc_setGoogleFeedLanguage( value ) {
470
- _feedHolder[ 'language' ] = value;
471
- }
472
-
473
- function tvc_setCategoryMap( mapping, mode ) {
474
-
475
- if( undefined === mode ) {
476
- mode = 'mapping'; // default setting
477
- }
478
-
479
- var map = JSON.parse( mapping );
480
-
481
- for ( var i = 0; i < map.length; i ++ ) {
482
-
483
- var categoryId = map[ i ].shopCategoryId;
484
- var mapString = '';
485
-
486
- if ( 'mapping' === mode ) { // only show the category mapping column when in mapping mode
487
- switch (map[ i ].feedCategories) {
488
-
489
- case 'wp_mainCategory':
490
- mapString = tvc_mapToDefaultCategoryElement(categoryId, 'default');
491
- break;
492
-
493
- case 'wp_ownCategory':
494
- mapString = tvc_mapToDefaultCategoryElement(categoryId, 'shopCategory');
495
- break;
496
-
497
- default:
498
- mapString = tvc_mapToCategoryElement(categoryId, map[ i ].feedCategories);
499
- break;
500
- }
501
- }
502
-
503
- jQuery( '#feed-selector-' + categoryId ).prop( 'checked', true );
504
- jQuery( '#feed-category-' + categoryId ).html( mapString );
505
- }
506
- }
507
-
508
- function tvc_generateAndSaveFeed() {
509
-
510
- tvc_showFeedSpinner();
511
-
512
- //noinspection JSUnresolvedVariable
513
- _feedHolder[ 'mainCategory' ] = ! tvc_channelUsesOwnCategories(
514
- _feedHolder[ 'channel' ] ) ? _feedHolder[ 'mainCategory' ] : tvc_feed_settings_form_vars.no_category_required;
515
-
516
- // save the feed data to the database
517
- tvc_saveFeedToDb( _feedHolder, function( dbResult ) {
518
-
519
- var newFeed = _feedHolder[ 'feedId' ] === - 1;
520
-
521
- tvc_handleSaveFeedToDbActionResult( dbResult, newFeed );
522
-
523
- // convert the data to xml or csv and save the code to a feed file
524
- tvc_updateFeedFile( _feedHolder[ 'feedId' ], function( xmlResult ) {
525
- tvc_handleUpdateFeedFileActionResult( xmlResult );
526
- } );
527
- jQuery("#tvc-attribute-map-2").trigger("click");
528
- tvc_hideFeedSpinner();
529
- } );
530
- }
531
-
532
- function tvc_handleSaveFeedToDbActionResult( dbResult, newFeed ) {
533
-
534
- // the tvc_saveFeedToDb returns the entered feed id
535
- if ( 0 === dbResult || '0' === dbResult ) {
536
- tvc_handleSaveFeedToDbFailedAction();
537
- } else {
538
-
539
- // insert the feed id in the _feed
540
- _feedHolder[ 'feedId' ] = dbResult;
541
-
542
- if ( newFeed ) {
543
- // reset the url to implement the feed id so the user can reset the form if he wants
544
- var currentUrl = window.location.href;
545
- window.location.href = currentUrl + '&id=' + _feedHolder[ 'feedId' ];
546
- //window.history.replaceState(null, null, "?page=tvc-product-feed-manager&tab=product-feed&id="+ _feedHolder[ 'feedId' ]);
547
- }
548
- }
549
- }
550
-
551
- /**
552
- * Handles a callback error from the function that should save the feed data to the db.
553
- */
554
- function tvc_handleSaveFeedToDbFailedAction() {
555
- console.log( 'Saving the data to the data base has failed!' );
556
- //noinspection JSUnresolvedVariable
557
- //tvc_show_error_message( tvc_feed_settings_form_vars.save_data_failed );
558
- tvc_hideFeedSpinner();
559
- }
560
-
561
- /**
562
- * Handles the callback from the function that updates the feed.
563
- *
564
- * @param {string} xmlResult
565
- */
566
- function tvc_handleUpdateFeedFileActionResult( xmlResult ) {
567
- var errorMessageElement = jQuery( '#error-message' );
568
- tvc_disableViewFeedButtons();
569
- switch ( xmlResult ) {
570
- case 'started_processing':
571
- errorMessageElement.hide();
572
- //noinspection JSUnresolvedVariable
573
- tvc_show_success_message( tvc_feed_settings_form_vars.feed_started );
574
- tvc_alert_update_finished( _feedHolder[ 'feedId' ], 10000 );
575
- break;
576
-
577
- case 'pushed_to_queue':
578
- errorMessageElement.hide();
579
- //noinspection JSUnresolvedVariable
580
- tvc_show_success_message( tvc_feed_settings_form_vars.feed_queued );
581
- tvc_alert_update_finished( _feedHolder[ 'feedId' ], 10000 );
582
- break;
583
-
584
- case 'writing_error':
585
- //noinspection JSUnresolvedVariable
586
- tvc_show_error_message( tvc_feed_settings_form_vars.feed_writing_error );
587
- tvc_hideFeedSpinner();
588
- break;
589
-
590
- case 'foreground_processing_complete':
591
- tvc_alert_update_finished( _feedHolder[ 'feedId' ], 0 );
592
- tvc_hideFeedSpinner();
593
- break;
594
-
595
- case 'activation_error':
596
- //noinspection JSUnresolvedVariable
597
- tvc_show_error_message( tvc_feed_settings_form_vars.feed_initiation_error );
598
- tvc_hideFeedSpinner();
599
- break;
600
-
601
- case '1':
602
- //noinspection JSUnresolvedVariable
603
- tvc_show_error_message( tvc_feed_settings_form_vars.feed_general_error.replace( '%xmlResult%', xmlResult ) );
604
- tvc_hideFeedSpinner();
605
- break;
606
-
607
- default:
608
- tvc_hideFeedSpinner();
609
- }
610
- }
611
-
612
- /**
613
- * Checks the status of the feed generation process every 10 seconds and shows a message when the feed is ready.
614
- *
615
- * @param {int} feedId
616
- * @param {int} repeatTime Time to repeat the status check, default 10.
617
- */
618
- function tvc_alert_update_finished( feedId, repeatTime ) {
619
- if ( undefined === repeatTime || 0 === repeatTime ) {
620
- repeatTime = 5000;
621
- } // default value
622
-
623
- var tvcStatusCheck = window.setInterval( tvc_checkAndSetStatus, repeatTime, feedId );
624
-
625
- var successErrorMessageElement = jQuery( '#success-message' );
626
-
627
- if ( ! feedId ) {
628
- return false;
629
- }
630
-
631
- function tvc_checkAndSetStatus( feedId ) {
632
-
633
- tvc_getCurrentFeedStatus( feedId, function( result ) {
634
- var status = JSON.parse( result );
635
- tvc_enableFeedActionButtons();
636
- switch ( status[ 'status_id' ] ) {
637
- case '0': // unknown
638
- tvc_show_success_message( tvc_feed_settings_form_vars.feed_status_unknown.replace( '%feedname%', status[ 'title' ] ) );
639
- window.clearInterval( tvcStatusCheck );
640
- break;
641
-
642
- case '1': // on hold
643
- case '2': // active
644
- // Get the feed url and store it in the tvc-feed-url storage so the View Feed button gets the correct url to open.
645
- var feedUrlStorageElement = document.getElementById( 'tvc-feed-url' );
646
- feedUrlStorageElement.textContent = status[ 'url' ];
647
-
648
- tvc_show_success_message(
649
- tvc_feed_settings_form_vars.feed_status_ready.replace( '%feedname%', status[ 'title' ] ).replace( '%prodnr%', status[ 'products' ] ) );
650
- window.clearInterval( tvcStatusCheck );
651
- break;
652
-
653
- case '3': // processing
654
- tvc_show_success_message( tvc_feed_settings_form_vars.feed_status_still_processing );
655
- break;
656
-
657
- case '4': // in queue
658
- tvc_show_success_message( tvc_feed_settings_form_vars.feed_status_added_to_queue );
659
- break;
660
-
661
- case '5': // error
662
- successErrorMessageElement.hide();
663
- tvc_show_error_message( tvc_feed_settings_form_vars.feed_status_error.replace( '%feedname%', status[ 'title' ] ) );
664
- window.clearInterval( tvcStatusCheck );
665
- break;
666
-
667
- case '6': // failed
668
- successErrorMessageElement.hide();
669
- tvc_show_error_message( tvc_feed_settings_form_vars.feed_status_failed.replace( '%feedname%', status[ 'title' ] ) );
670
- window.clearInterval( tvcStatusCheck );
671
- break;
672
-
673
- default :
674
- //tvc_hideFeedSpinner();
675
- }
676
- } );
677
- }
678
- }
679
-
680
- function tvc_saveFeed() {
681
-
682
- tvc_showFeedSpinner();
683
-
684
- var newFeed = _feedHolder[ 'feedId' ] === - 1;
685
-
686
- _feedHolder[ 'mainCategory' ] = ! tvc_channelUsesOwnCategories( _feedHolder[ 'channel' ] ) ? _feedHolder[ 'mainCategory' ] : tvc_feed_settings_form_vars.no_category_required;
687
-
688
- if ( newFeed ) {
689
- _feedHolder[ 'url' ] = tvc_feed_settings_form_vars.no_feed_generated;
690
- }
691
-
692
- // save the feed data to the database
693
- tvc_saveFeedToDb( _feedHolder,function( dbResult ) {
694
-
695
- // the tvc_saveFeedToDb returns the entered feed id
696
- if ( dbResult === 0 ) {
697
- console.log( 'Saving the data to the data base has failed!' );
698
- tvc_show_error_message( tvc_feed_settings_form_vars.save_data_failed );
699
- } else {
700
-
701
- // insert the feed id in the _feed
702
- _feedHolder[ 'feedId' ] = dbResult;
703
-
704
- if ( newFeed ) {
705
- // reset the url to implement the feed id so the user can reset the form if he wants
706
- var currentUrl = window.location.href;
707
- window.location.href = currentUrl + '&id=' + _feedHolder[ 'feedId' ];
708
- }
709
- }
710
- }
711
- );
712
- }
713
-
714
- /**
715
- * Gets the next category list and fills the selector with it
716
- *
717
- * @param {string} currentLevelId
718
- */
719
- function tvc_nextCategory( currentLevelId ) {
720
- var nextLevelId = tvc_incrementLast( currentLevelId );
721
- var nextLevel = nextLevelId.match( /(\d+)$/ )[ 0 ]; // get the number on the end of the nextLevelId
722
- var selectedCategory = jQuery( '#' + currentLevelId ).val();
723
- var channel = _feedHolder[ 'channel' ] ? _feedHolder[ 'channel' ].toString() : jQuery( '#tvc-merchants-selector' ).val();
724
- var language = tvc_channelCountryCode( channel );
725
- var nextLevelIdElement = jQuery( '#' + nextLevelId );
726
-
727
- if ( nextLevel > 1 ) {
728
- tvc_showFeedSpinner();
729
- }
730
-
731
- // show the correct sub level selectors, hide the others
732
- tvc_hideSubs( currentLevelId );
733
-
734
- // fill the special filter variables
735
- tvc_fillCategoryVariables( channel, selectedCategory, currentLevelId );
736
-
737
- // get the next level selector
738
- tvc_getNextCategories( channel, nextLevel, selectedCategory, language, function( categories ) {
739
- var list = JSON.parse( categories );
740
-
741
- if ( list.length > 0 ) {
742
- nextLevelIdElement.append( tvc_categorySelectCntrl( list ) );
743
- nextLevelIdElement.show();
744
- }
745
-
746
- if ( currentLevelId.indexOf( 'catmap' ) > - 1 ) { // the selection is from the category map
747
- tvc_setChildCategories( currentLevelId, selectedCategory );
748
- } else { // the selection is from the default category
749
- _feedHolder.setMainCategory( currentLevelId, selectedCategory, channel );
750
-
751
- if ( _feedHolder[ 'attributes' ].length > 0 && _feedHolder[ 'attributes' ][ 3 ][ 'value' ] !== undefined && _feedHolder[ 'attributes' ][ 3 ][ 'value' ] !== '' ) {
752
- jQuery( '#category-source-string' ).html( JSON.parse( _feedHolder[ 'attributes' ][ 3 ][ 'value' ] ).t );
753
- } else {
754
- jQuery( '#category-source-string' ).html( _feedHolder[ 'mainCategory' ] );
755
- }
756
- }
757
-
758
- if ( nextLevel > 1 ) {
759
- tvc_hideFeedSpinner();
760
- }
761
- } );
762
- }
763
-
764
- function tvc_setChildCategories( categorySelectorId, selectedCategory ) {
765
- var selectedLevel = categorySelectorId.match( /(\d+)$/ )[ 0 ]; // next level
766
- var sc = categorySelectorId.replace( '_' + selectedLevel, '' );
767
- var parentCategoryId = sc.match( /(\d+)$/ )[ 0 ];
768
- var children = tvc_getCategoryChildren( parentCategoryId );
769
-
770
- for ( var i = 0; i < children.length; i ++ ) {
771
- tvc_setChildrenToParentCategory( parentCategoryId, children[ i ], selectedLevel, selectedCategory );
772
- }
773
-
774
- _feedHolder.mapCategory( categorySelectorId, selectedCategory );
775
- }
776
-
777
- function tvc_getCategoryChildren( parentCategoryId ) {
778
- var feedSelectorElement = jQuery( '#feed-selector-' + parentCategoryId );
779
-
780
- return feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
781
- }
782
-
783
- function tvc_variation_selection_changed() {
784
- alert( tvc_feed_settings_form_vars.variation_only_for_premium );
785
- _feedHolder.changeIncludeVariations( false );
786
- jQuery( '#variations' ).prop( 'checked', false );
787
- }
788
-
789
- function tvc_aggregatorChanged() {
790
- if ( jQuery( '#aggregator' ).is( ':checked' ) ) {
791
- _feedHolder.changeAggregator( true );
792
- _feedHolder.attributes[ 8 ][ 'fieldLevel' ] = '1';
793
- } else {
794
- _feedHolder.changeAggregator( false );
795
- _feedHolder.attributes[ 8 ][ 'fieldLevel' ] = '0';
796
- _feedHolder.deactivateAttribute( '8' );
797
- }
798
- }
799
-
800
- function tvc_setChildrenToParentCategory( parentId, childId, level, selectedCategory ) {
801
- var currentChildCategory = tvc_getCategorySelectorValue( childId );
802
- var curCatStr = '';
803
- var newCategory = tvc_addNewItemToCategoryString( level, currentChildCategory, selectedCategory, ' > ' );
804
- var categorySelectorId = 'catmap-' + childId + '_' + level;
805
- var catmapTextSpanSelector = jQuery( '#category-text-span-' + childId );
806
-
807
- for ( var i = 0; i < level; i ++ ) {
808
- curCatStr += jQuery( '#catmap-' + parentId + '_' + i ).val() + ' > ';
809
- }
810
-
811
- var preSelectionParentCategory = curCatStr.substring( 0, curCatStr.length - 3 );
812
-
813
- if ( currentChildCategory === preSelectionParentCategory || currentChildCategory === tvc_feed_settings_form_vars.map_to_default_category ) {
814
- if ( catmapTextSpanSelector.length === 0 ) {
815
- tvc_mapToDefaultCategoryElement( childId, newCategory );
816
- }
817
-
818
- catmapTextSpanSelector.text( newCategory );
819
-
820
- var feedSelectorElement = jQuery( '#feed-selector-' + childId );
821
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
822
-
823
- for ( var j = 0; j < children.length; j ++ ) {
824
- tvc_setChildrenToParentCategory( childId, children[ j ], level, selectedCategory );
825
- }
826
-
827
- _feedHolder.mapCategory( categorySelectorId, selectedCategory );
828
- } else if ( catmapTextSpanSelector.length === 0 ) {
829
- jQuery( '#feed-category-' + childId ).html( tvc_mapToDefaultCategoryElement( childId, currentChildCategory ) );
830
- jQuery( '#category-selector-catmap-' + childId ).hide();
831
- }
832
- }
833
-
834
- function tvc_getCategorySelectorValue( selectorId ) {
835
- var val = jQuery( '#category-text-span-' + selectorId ).text();
836
-
837
- if ( val === '' ) {
838
- var catString = '';
839
-
840
- for ( var i = 0; i < 7; i ++ ) {
841
- var catMapSelectorElement = jQuery( '#catmap-' + selectorId + '_' + i );
842
- var cat = catMapSelectorElement.val();
843
-
844
- if ( cat !== null && cat !== '0' ) {
845
- catString += catMapSelectorElement.val() + ' > ';
846
- }
847
- }
848
-
849
- val = catString.substring( 0, catString.length - 3 );
850
- }
851
-
852
- return val;
853
- }
854
-
855
- function tvc_fillFeedFields( isNew, categoryChanged ) {
856
- var langElem = document.getElementById( 'tvc-feed-language-selector' );
857
- var merchantsSelectorElement = jQuery( '#tvc-merchants-selector' );
858
-
859
- // if the category attribute has a value
860
- if ( _feedHolder[ 'mainCategory' ] && isNew === false ) {
861
- // and display the category in the Default Category input field unless only the category has been changed
862
- if ( ! categoryChanged ) {
863
- // make the category string
864
- var categoryString = _feedHolder[ 'mainCategory' ] +
865
- ' (<a class="edit-categories tvc-btn tvc-btn-small" href="javascript:void(0)" ' +
866
- 'id="tvc-edit-categories" onclick="tvc_editCategories()">' + tvc_feed_settings_form_vars.edit + '</a>)';
867
-
868
- jQuery( '#lvl_0' ).hide();
869
- jQuery( '#selected-categories' ).html( categoryString );
870
- jQuery( '#selected-merchant' ).html( jQuery( '#tvc-merchants-selector option[value=\'' + _feedHolder[ 'channel' ] + '\']' ).text() );
871
- merchantsSelectorElement.hide();
872
- }
873
- } else {
874
- jQuery( '#lvl_0' ).css( 'display', 'initial' );
875
- }
876
-
877
- var schedule = _feedHolder[ 'updateSchedule' ] ? _feedHolder[ 'updateSchedule' ].split( ':' ) : [];
878
-
879
- if ( ! isNew ) {
880
- tvc_showChannelInputs( _feedHolder[ 'channel' ], isNew );
881
- } else {
882
- jQuery( '#tvc-category-map' ).show();
883
- }
884
-
885
- jQuery( '#file-name' ).val( _feedHolder[ 'title' ] );
886
- merchantsSelectorElement.val( _feedHolder[ 'channel' ] );
887
- jQuery( '#variations' ).prop( 'checked', _feedHolder[ 'includeVariations' ] > 0 );
888
- jQuery( '#aggregator' ).prop( 'checked', _feedHolder[ 'isAggregator' ] > 0 );
889
- jQuery( '#tvc-countries-selector' ).val( _feedHolder[ 'country' ] );
890
- jQuery( '#google-feed-title-selector' ).val( _feedHolder[ 'feedTitle' ] );
891
- jQuery( '#google-feed-description-selector' ).val( _feedHolder[ 'feedDescription' ] );
892
- jQuery( '#days-interval' ).val( schedule[ 0 ] );
893
-
894
- if ( langElem !== null ) {
895
- var langVal = _feedHolder[ 'language' ] !== '' ? _feedHolder[ 'language' ] : '0';
896
- jQuery( '#tvc-feed-language-selector' ).val( langVal );
897
- }
898
-
899
- // get the link to the update schedule selectors
900
- var hrsSelector = document.getElementById( 'update-schedule-hours' );
901
- var mntsSelector = document.getElementById( 'update-schedule-minutes' );
902
- var freqSelector = document.getElementById( 'update-schedule-frequency' );
903
-
904
- // set the values of the update schedule selectors
905
- hrsSelector.value = schedule[ 1 ];
906
- mntsSelector.value = schedule[ 2 ];
907
- freqSelector.value = schedule[ 3 ] ? schedule[ 3 ] : '1'; // standard setting is once a day
908
-
909
- // set the layout of the update schedule selectors
910
- tvc_setScheduleSelector( schedule[ 0 ], schedule[ 3 ] );
911
- }
912
-
913
- /**
914
- * Category Selector Control.
915
- *
916
- * Generates the html for a category selector.
917
- *
918
- * @since 0.1.1
919
- * @access public
920
- *
921
- * @param {array} categories with strings of categories to be placed in the selector
922
- *
923
- * @returns {string} Html for a category selector
924
- */
925
- function tvc_categorySelectCntrl( categories ) {
926
- var htmlCode = '<option value="0">' + tvc_feed_settings_form_vars.select_a_sub_category + '</option>';
927
-
928
- for ( var i = 0; i < categories.length; i ++ ) {
929
- htmlCode += '<option value="' + categories[ i ] + '">' + categories[ i ] + '</option>';
930
- }
931
-
932
- return htmlCode;
933
- }
934
-
935
- /**
936
- * Edits the mapping of the feed categories to the shop categories
937
- *
938
- * @param {string} id
939
- */
940
- function tvc_editCategoryMapping( id ) {
941
- tvc_showFeedSpinner();
942
- var channel = _feedHolder[ 'channel' ];
943
- var language = tvc_channelCountryCode( channel );
944
- var currentCategoryString = jQuery( '#category-text-span-' + id ).text();
945
- var currentCategoryArray = currentCategoryString.split( ' > ' );
946
-
947
- if ( currentCategoryString && currentCategoryString !== tvc_feed_settings_form_vars.map_to_default_category ) {
948
- // the current Shop Category already has a category set. So keep that category as the default setting
949
- tvc_getCategoryListsFromString( channel, currentCategoryString, language, function( categories ) {
950
- tvc_showCategoryMappingSelectors( id, JSON.parse( categories ), currentCategoryArray );
951
- tvc_hideFeedSpinner();
952
- } );
953
- } else {
954
- if ( ! tvc_isCustomChannel( channel ) ) {
955
- tvc_getCategoryListsFromString( channel, '', language, function( categories ) {
956
- tvc_showCategoryMappingSelectors( id, JSON.parse( categories ), '' );
957
- tvc_hideFeedSpinner();
958
- } );
959
- } else {
960
- jQuery( '#feed-category-' + id ).html( tvc_freeCategoryInputCntrl( 'mapping', id, _feedHolder[ 'mainCategory' ] ) );
961
- jQuery( '#category-selector-catmap-' + id ).hide();
962
- tvc_hideFeedSpinner();
963
- }
964
- }
965
- }
966
-
967
- /**
968
- * Adds category selectors to the Category Mapping section
969
- */
970
- function tvc_showCategoryMappingSelectors( id, catList, currentCategoryArray ) {
971
- for ( var i = 0; i < catList.length; i ++ ) {
972
- var catMapSelectorElement = jQuery( '#catmap-' + id + '_' + i );
973
-
974
- if ( catList[ i ] && catList[ i ].length > 0 ) {
975
- // if no category is the selected category, select the first item in the list
976
- var selectedCategory = currentCategoryArray[ i ] ? currentCategoryArray[ i ] : '0';
977
- // append the category selector code to the select item
978
- catMapSelectorElement.append( tvc_categorySelectCntrl( catList[ i ] ) );
979
- catMapSelectorElement.val( selectedCategory );
980
- catMapSelectorElement.show();
981
- }
982
-
983
- catMapSelectorElement.prop( 'disabled', false );
984
- }
985
-
986
- jQuery( '#feed-category-' + id ).html( '' ); // remove the category string so it can be replaced by the selector
987
- jQuery( '#category-selector-catmap-' + id ).show(); // now show the category selectors
988
- }
989
-
990
- function tvc_activateOptionalFieldRow( level, name ) {
991
- var attributeId = _feedHolder.getAttributeIdByName( name );
992
-
993
- // register the new optional field as an active input
994
- _feedHolder.activateAttribute( attributeId );
995
-
996
- if ( _feedHolder[ 'attributes' ][ attributeId ][ 'advisedSource' ] ) { // when the selected input has an advised value,
997
- _feedHolder.setSourceValue( attributeId, level, _feedHolder[ 'attributes' ][ attributeId ][ 'advisedSource' ] );
998
- }
999
-
1000
- // get the html code for the new source row that needs to be added to the form
1001
- var code = tvc_fieldRow( _feedHolder[ 'attributes' ][ attributeId ], true );
1002
- var ind = - 1;
1003
-
1004
- // find the index of the selected item in the correct undefined outputs list
1005
- if ( level === 3 ) {
1006
- ind = _undefinedRecommendedOutputs.indexOf( name );
1007
- } else if ( level === 4 ) {
1008
- ind = _undefinedOptionalOutputs.indexOf( name );
1009
- }
1010
-
1011
- // if it can not be used more than once, remove it from the undefined output list
1012
- if ( ind > - 1 ) {
1013
- if ( level === 3 ) {
1014
- _undefinedRecommendedOutputs.splice( ind, 1 );
1015
- } else if ( level === 4 ) {
1016
- _undefinedOptionalOutputs.splice( ind, 1 );
1017
- }
1018
- }
1019
-
1020
- // store the removed item in the defined outputs list
1021
- if ( level === 3 ) {
1022
- _definedRecommendedOutputs.push( _feedHolder[ 'attributes' ][ attributeId ][ 'fieldName' ] );
1023
- _definedRecommendedOutputs.sort();
1024
- } else if ( level === 4 ) {
1025
- _definedOptionalOutputs.push( _feedHolder[ 'attributes' ][ attributeId ][ 'fieldName' ] );
1026
- _definedOptionalOutputs.sort();
1027
- }
1028
-
1029
- jQuery( '#output-field-cntrl-' + level + ' option[value=\'' + name + '\']' ).remove();
1030
-
1031
- jQuery( '#output-field-cntrl-' + level ).val( 'no-value' );
1032
-
1033
- if ( level === 3 ) {
1034
- var newRecommendedRowElement = jQuery( '#new-recommended-row' );
1035
- newRecommendedRowElement.append( code );
1036
- newRecommendedRowElement.show();
1037
- } else if ( level === 4 ) {
1038
- jQuery( '#new-optional-row' ).append( code );
1039
- }
1040
- }
1041
-
1042
- function tvc_activateCustomFieldRow( fieldName ) {
1043
- if ( ! _feedHolder.checkIfCustomNameExists( fieldName ) ) { // prevent doubles
1044
- var attributeId = _feedHolder.getAttributeIdByName( fieldName );
1045
- var newCustomRowItem = jQuery( '#new-custom-row' );
1046
-
1047
- // register the new custom field
1048
- _feedHolder.addAttribute( attributeId, fieldName, '', undefined, '5', true, 0, 0, 0, 0 );
1049
-
1050
- newCustomRowItem.append( tvc_fieldRow( _feedHolder[ 'attributes' ][ attributeId ], true ) );
1051
- newCustomRowItem.show();
1052
- } else {
1053
- alert( tvc_feed_settings_form_vars.duplicated_field.replace( '%fieldname%', fieldName ) );
1054
- }
1055
-
1056
- // clear the input field
1057
- jQuery( '#custom-output-title-input' ).val( '' );
1058
- }
1059
-
1060
- function tvc_setStaticValue( attributeId, conditionLevel, combinationLevel ) {
1061
- var staticValue = jQuery( '#static-input-field-' + attributeId + '-' + conditionLevel + '-' + combinationLevel ).val();
1062
-
1063
- if ( staticValue === undefined ) {
1064
-
1065
- //staticValue = jQuery( '#static-condition-input-' + attributeId + '-' + conditionLevel + '-' + combinationLevel + ' option:selected' ).text();
1066
- staticValue = jQuery( '#static-condition-input-' + attributeId + '-' + conditionLevel + '-' + combinationLevel + ' option:selected' ).val();
1067
- }
1068
-
1069
- // store the changed static value in the feed
1070
- _feedHolder.setStaticAttributeValue( attributeId, conditionLevel, combinationLevel, staticValue );
1071
- }
1072
-
1073
- function tvc_setIdentifierExistsDependancies() {
1074
-
1075
- var staticValue = jQuery( '#static-input-field-34-0' ).val();
1076
-
1077
- if ( staticValue === undefined ) {
1078
- staticValue = jQuery( '#static-condition-input-34-0 option:selected' ).val();
1079
- }
1080
-
1081
- switch ( staticValue ) {
1082
-
1083
- case 'true':
1084
- tvc_resetOutputField( 12, 1, true );
1085
- tvc_resetOutputField( 13, 1, true );
1086
- break;
1087
-
1088
- case 'false':
1089
- tvc_resetOutputField( 12, 3, false );
1090
- tvc_resetOutputField( 13, 3, false );
1091
- break;
1092
-
1093
- default:
1094
- break;
1095
- }
1096
- }
1097
-
1098
- function tvc_resetOutputField( fieldId, level, isActive ) {
1099
-
1100
- var oldLevel = _feedHolder[ 'attributes' ][ fieldId ][ 'fieldLevel' ];
1101
-
1102
- // set the attribute status
1103
- _feedHolder[ 'attributes' ][ fieldId ][ 'fieldLevel' ] = level;
1104
- _feedHolder[ 'attributes' ][ fieldId ][ 'isActive' ] = isActive;
1105
-
1106
- //show or hide the output field
1107
- var outputField = tvc_fieldRow( _feedHolder[ 'attributes' ][ fieldId ], false );
1108
- var fieldName = _feedHolder[ 'attributes' ][ fieldId ][ 'fieldName' ];
1109
-
1110
- if ( isActive ) {
1111
-
1112
- jQuery( '#required-field-table' ).append( outputField );
1113
- jQuery( '#output-field-cntrl-' + oldLevel + ' option[value=\'' + fieldName + '\']' ).remove();
1114
- jQuery( '#recommended-field-table #row-' + fieldId ).remove();
1115
-
1116
- } else {
1117
-
1118
- jQuery( '#row-' + fieldId ).replaceWith( '' );
1119
- jQuery( '#output-field-cntrl-' + level ).append( '<option value="' + fieldName + '">' + fieldName + '</option>' );
1120
- }
1121
- }
1122
-
1123
- /**
1124
- * Returns the html code for a single field table row
1125
- *
1126
- * @param {array} attributeData
1127
- * @param {boolean} removable
1128
- * @returns {String} containing the html
1129
- */
1130
- function tvc_fieldRow( attributeData, removable ) {
1131
- var rowId = attributeData[ 'rowId' ];
1132
- var sourceRowsData = _feedHolder.getSourceObject( rowId );
1133
- var nrOfSources = countSources( sourceRowsData.mapping );
1134
-
1135
- // add an extra row when there is a condition in the last source row and an advised source but no user set source
1136
- if ( sourceRowsData.advisedSource && tvc_hasExtraSourceRow( nrOfSources, sourceRowsData.mapping ) ) {
1137
- nrOfSources ++;
1138
- }
1139
-
1140
- // row wrapper
1141
- var htmlCode = '<div class="field-table-row-wrapper tvc-attribute-' + sourceRowsData.fieldName + '-row" id="row-' + rowId + '">';
1142
-
1143
- for ( var i = 0; i < nrOfSources; i ++ ) {
1144
- htmlCode += tvc_addFeedSourceRow( rowId, i, sourceRowsData, _feedHolder.channel, removable );
1145
- }
1146
-
1147
- for ( var j = 0; j < sourceRowsData.changeValues.length; j ++ ) {
1148
- if ( sourceRowsData.changeValues[ 0 ] ) {
1149
- // add the change value editor fields
1150
- htmlCode += tvc_valueEditor( sourceRowsData.rowId, j, j, sourceRowsData.changeValues );
1151
- }
1152
- }
1153
-
1154
- // end the row and start a new one
1155
- htmlCode += tvc_endrow( rowId );
1156
- htmlCode += '</div>';
1157
-
1158
- return htmlCode;
1159
- }
1160
-
1161
- function tvc_addSourceDataAndQueriesColumn( sourceLevel, sourceRowsData ) {
1162
-
1163
- var htmlCode = '';
1164
- var levelString = sourceRowsData.rowId + '-' + sourceLevel;
1165
- var sourceValue = tvc_getMappingSourceValue( sourceRowsData.mapping, sourceLevel );
1166
- var combinedValue = tvc_getMappingCombinedValue( sourceRowsData.mapping, sourceLevel );
1167
- var staticValue = tvc_getMappingStaticValue( sourceRowsData.mapping, sourceLevel );
1168
- var sourceIsCategory = ! ! sourceRowsData.customCondition;
1169
- var sourceMappingHasSourceData = ! ! (
1170
- sourceValue || combinedValue || staticValue
1171
- );
1172
- var channel = _feedHolder[ 'channel' ].toString();
1173
- var conditions = tvc_getMappingConditions( sourceRowsData.mapping, sourceLevel );
1174
- var conditionsCounter = tvc_countObjectItems( conditions );
1175
-
1176
- // wrap the source controls
1177
- htmlCode += '<div class="source-selector colw col30w" id="source-select-' + levelString + '">';
1178
-
1179
- if ( sourceIsCategory ) {
1180
- htmlCode += tvc_categorySource();
1181
- } else if ( (
1182
- sourceRowsData.advisedSource && ! sourceMappingHasSourceData && sourceRowsData.advisedSource !== tvc_feed_settings_form_vars.fill_with_static_value
1183
- )
1184
- || sourceRowsData.advisedSource === sourceValue ) {
1185
-
1186
- // remove underscore where applicable
1187
- //var advisedSourceWithoutUnderscore = sourceRowsData.advisedSource.charAt(0) === '_' ? sourceRowsData.advisedSource.substr(1) : sourceRowsData.advisedSource;
1188
- var advisedSourceLabel = jQuery.grep( _inputFields, function( e ) {
1189
- return e.value === sourceRowsData.advisedSource;
1190
- } );
1191
- advisedSourceLabel = advisedSourceLabel[ 0 ] ? advisedSourceLabel[ 0 ].label : sourceRowsData.advisedSource;
1192
-
1193
- htmlCode += tvc_advisedSourceSelector( sourceRowsData.rowId, sourceLevel, advisedSourceLabel,
1194
- channel, sourceRowsData.mapping );
1195
- } else if ( (
1196
- ! sourceRowsData.advisedSource && ! sourceValue
1197
- )
1198
- || sourceMappingHasSourceData
1199
- || sourceRowsData.advisedSource === tvc_feed_settings_form_vars.fill_with_static_value ) {
1200
-
1201
- htmlCode += tvc_inputFieldCntrl( sourceRowsData.rowId, sourceLevel, sourceValue, staticValue, sourceRowsData.advisedSource, combinedValue,
1202
- tvc_isCustomChannel( channel ) );
1203
-
1204
- if ( staticValue ) {
1205
-
1206
- htmlCode += tvc_feedStaticValueSelector( sourceRowsData.fieldName, sourceRowsData.rowId, sourceLevel, 0,
1207
- staticValue, channel );
1208
- }
1209
-
1210
- if ( combinedValue ) {
1211
-
1212
- htmlCode += tvc_combinedField( sourceRowsData.rowId, sourceLevel, 0, combinedValue, false, channel );
1213
- }
1214
- }
1215
-
1216
- // end the source control wrapper
1217
- htmlCode += '</div>';
1218
-
1219
- htmlCode += '<div class="condition-selector colw" id="condition-data-' + levelString + '">';
1220
-
1221
- // and now fill the condition controls
1222
- if ( ! sourceIsCategory && ! conditions ) {
1223
-
1224
- htmlCode += '<div class="condition-wrapper" id="condition-' + levelString + '-0">';
1225
- htmlCode += tvc_forAllProductsCondition( sourceRowsData.rowId, sourceLevel, 'initial' );
1226
- htmlCode += '</div>';
1227
- } else if ( conditions ) {
1228
- for ( var i = 0; i < conditionsCounter; i ++ ) {
1229
- htmlCode += tvc_conditionSelectorCode( sourceRowsData.rowId, sourceLevel, i, conditionsCounter, conditions[ i ] );
1230
- }
1231
- }
1232
-
1233
- htmlCode += '</div>';
1234
-
1235
- return htmlCode;
1236
- }
1237
-
1238
- function tvc_addCombinedField( id, sourceLevel, combinedLevel ) {
1239
-
1240
- var allFilled = true;
1241
- var combinedFieldsControlElement = jQuery( '#combined-input-field-cntrl-' + id + '-' + sourceLevel + '-' + combinedLevel );
1242
-
1243
- for ( var i = 0; i < combinedLevel; i ++ ) {
1244
-
1245
- // do all fields have a selected value?
1246
- if ( combinedFieldsControlElement.val() === 'select' ) {
1247
-
1248
- allFilled = false;
1249
- i = combinedLevel;
1250
- }
1251
-
1252
- if ( combinedFieldsControlElement.val() === 'static'
1253
- && jQuery( '#static-input-field-' + id + '-' + sourceLevel + '-' + combinedLevel ).val() === '' ) {
1254
-
1255
- allFilled = false;
1256
- i = combinedLevel;
1257
- }
1258
- }
1259
-
1260
- if ( allFilled ) {
1261
- var combinedValueObject = _feedHolder[ 'attributes' ][ id ][ 'value' ] ? JSON.parse( _feedHolder[ 'attributes' ][ id ][ 'value' ] ) : {};
1262
- var combinedValuePart = 'm' in combinedValueObject ? combinedValueObject.m : {};
1263
- var combinedValue = tvc_getMappingCombinedValue( combinedValuePart, sourceLevel );
1264
- var manualAdd = combinedLevel > 0;
1265
-
1266
- jQuery( '#source-select-' + id + '-' + sourceLevel ).append( tvc_combinedField( id, sourceLevel, combinedLevel, combinedValue, manualAdd ) );
1267
-
1268
- jQuery( '#add-combined-field-' + id + '-' + sourceLevel ).hide();
1269
- } else {
1270
- alert( tvc_feed_settings_form_vars.select_all_source_fields_warning );
1271
- }
1272
- }
1273
-
1274
- function tvc_combinedField( rowId, sourceLevel, combinedLevel, fields, manualAdd ) {
1275
-
1276
- jQuery( '#combined-wrapper-' + rowId + '-' + sourceLevel ).remove(); // reset the combined wrapper field
1277
-
1278
- var fieldsArray = tvc_splitCombinedFieldElements( fields );
1279
-
1280
- var fieldsLength = fields ? fieldsArray.length : 2; // if no field data is given, then show two empty input selectors
1281
-
1282
- if ( manualAdd ) {
1283
- fieldsLength ++;
1284
- }
1285
-
1286
- var htmlCode = '<div class="combined-wrapper" id="combined-wrapper-' + rowId + '-' + sourceLevel + '">';
1287
-
1288
- // loop through the field items in the fields string
1289
- for ( var i = 0; i < fieldsLength; i ++ ) {
1290
- var str = fieldsArray[ i ];
1291
- var ind = str ? str.indexOf( '#' ) : 0;
1292
- var fieldSplit;
1293
-
1294
- if ( str ) {
1295
- fieldSplit = str.substr( 0, ind ) !== 'static' ? [ str.substr( 0, ind ), str.substr( ind + 1 ) ]
1296
- : [ '0', fieldsArray[ i ] ];
1297
- } else {
1298
- fieldSplit = [];
1299
- }
1300
-
1301
- htmlCode += tvc_combinedCntrl( rowId, sourceLevel, i + 1, fieldsLength, 'delete', fieldSplit, _feedHolder[ 'channel' ] );
1302
- }
1303
-
1304
- htmlCode += '</div>';
1305
-
1306
- return htmlCode;
1307
- }
1308
-
1309
- function tvc_combinedCntrl( rowId, sourceLevel, combinationLevel, nrQueries, type, valueArray, channel ) {
1310
-
1311
- var htmlCode = '';
1312
- var fieldName = _feedHolder[ 'attributes' ][ rowId ][ 'fieldName' ];
1313
-
1314
- htmlCode += '<span class="combined-field-row" id="combined-field-row-' + rowId + '-' + sourceLevel + '-' + combinationLevel + '">';
1315
-
1316
- if ( combinationLevel > 1 ) {
1317
-
1318
- htmlCode += tvc_combinedSeparatorCntrl( rowId, sourceLevel, combinationLevel, valueArray[ 0 ] );
1319
- }
1320
-
1321
- // draw the control
1322
- htmlCode += tvc_combinedInputFieldCntrl( rowId, sourceLevel, combinationLevel, valueArray[ 1 ], fieldName, channel );
1323
-
1324
- if ( type === 'initialize' ) {
1325
-
1326
- // add an extra control
1327
- htmlCode += '<span class="combined-field-row" id="combined-field-row">';
1328
- htmlCode += tvc_combinedSeparatorCntrl( rowId, sourceLevel, combinationLevel, valueArray[ 0 ] );
1329
- htmlCode += tvc_combinedInputFieldCntrl( rowId, sourceLevel, 2, '', fieldName, channel );
1330
- // htmlCode += '<span id="static-input-combined-field-' + rowId + '-' + sourceLevel + '-2"></span>';
1331
- htmlCode += '<div class="static-value-control" id="static-value-control-' + rowId + '-' + sourceLevel + '-2"></div>';
1332
- }
1333
-
1334
- if ( combinationLevel > 2 ) {
1335
-
1336
- // draw the "remove" button
1337
- htmlCode += '<span id="remove-combined-field-' + rowId + '-' + sourceLevel + '-' + combinationLevel + '" style="display:initial">';
1338
- htmlCode += '(<a class="remove-combined-field tvc-btn tvc-btn-small" href="javascript:void(0)"';
1339
- htmlCode += ' onclick="tvc_removeCombinedField(' + rowId + ', ' + sourceLevel + ', ' + combinationLevel + ')">' + tvc_feed_settings_form_vars.remove + '</a>)</span>';
1340
- }
1341
-
1342
- if ( combinationLevel === 2 || combinationLevel >= nrQueries ) {
1343
-
1344
- if ( combinationLevel === 1 ) {
1345
- combinationLevel ++;
1346
- }
1347
-
1348
- // draw the "add" button
1349
- if ( combinationLevel >= nrQueries ) {
1350
- htmlCode += '<span id="add-combined-field-' + rowId + '-' + sourceLevel + '-' + combinationLevel + '" style="display:initial">';
1351
- htmlCode += '(<a class="add-combined-field tvc-btn tvc-btn-small" href="javascript:void(0)"';
1352
- htmlCode += ' onclick="tvc_addCombinedField(' + rowId + ', ' + sourceLevel + ', ' + combinationLevel + ')">' + tvc_feed_settings_form_vars.add + '</a>)</span>';
1353
- }
1354
- }
1355
-
1356
- htmlCode += '</span>';
1357
-
1358
- return htmlCode;
1359
- }
1360
-
1361
- // TODO: this function looks like the tvc_ifValueQuerySelector() function. Maybe I could combine these two?
1362
- function tvc_ifConditionSelector( rowId, sourceLevel, conditionLevel, numberOfQueries, queryObject ) {
1363
-
1364
- var htmlCode = '';
1365
- var query = tvc_isEmptyQueryObject( queryObject ) ? tvc_makeCleanQueryObject() : queryObject;
1366
- var conditionSelector = tvc_feed_settings_form_vars.if_pref + ' ';
1367
-
1368
- if ( conditionLevel > 1 ) {
1369
-
1370
- conditionSelector = query.preCondition === '1'
1371
- ? '<select id="sub-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '" onchange="tvc_storeCondition(' + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')"><option value="2">' + tvc_feed_settings_form_vars.or + '</option><option value="1" selected>' + tvc_feed_settings_form_vars.and + '</option></select>'
1372
- : '<select id="sub-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '" onchange="tvc_storeCondition(' + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')"><option value="2" selected>' + tvc_feed_settings_form_vars.or + '</option><option value="1">' + tvc_feed_settings_form_vars.and + '</option></select>';
1373
- }
1374
-
1375
- var storeConditionFunctionString = 'tvc_storeCondition(' + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')';
1376
-
1377
- htmlCode += '<div class="condition-wrapper" id="condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '">';
1378
- htmlCode += conditionSelector;
1379
- htmlCode += tvc_conditionFieldCntrl( rowId, sourceLevel, conditionLevel, - 1, 'input-field-cntrl', query.source, storeConditionFunctionString );
1380
- htmlCode += tvc_conditionQueryCntrl( rowId, sourceLevel, conditionLevel, - 1, 'query-condition', 'tvc_queryConditionChanged', query.condition );
1381
-
1382
- htmlCode += '<input type="text" onchange="tvc_storeCondition(' + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')" name="condition-value" id="condition-value-';
1383
- htmlCode += rowId + '-' + sourceLevel + '-' + conditionLevel + '" value="' + query.value + '"';
1384
-
1385
- if ( queryObject.condition !== '4' && queryObject.condition !== '5' ) {
1386
-
1387
- htmlCode += ' style="display:initial">';
1388
- } else {
1389
-
1390
- htmlCode += ' style="display:none;">';
1391
- }
1392
-
1393
- if ( queryObject.condition !== '14' ) {
1394
-
1395
- htmlCode += '<span id="condition-and-value-' + rowId + '-' + sourceLevel + '-' + conditionLevel
1396
- + '" style="display:none;"> ' + tvc_feed_settings_form_vars.and + ' <input type="text" name="condition-and-value" onchange="tvc_storeCondition('
1397
- + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')" id="condition-and-value-input-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '"></span>';
1398
- } else {
1399
-
1400
- htmlCode += '<span id="condition-and-value-' + rowId + '-' + sourceLevel + '-' + conditionLevel
1401
- + '" style="display:initial"> ' + tvc_feed_settings_form_vars.and + ' <input type="text" name="condition-and-value" onchange="tvc_storeCondition('
1402
- + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ')" id="condition-and-value-input-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '" value="' + queryObject.endValue + '"></span>';
1403
- }
1404
-
1405
- htmlCode += '(<a class="remove-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)" id="tvc-remove-attribute-query-' + rowId + '-' + sourceLevel + '-' + conditionLevel;
1406
- htmlCode += '" onclick="tvc_removeCondition(' + rowId + ', ' + sourceLevel + ', ' + (
1407
- conditionLevel - 1
1408
- ) + ')">' + tvc_feed_settings_form_vars.remove + '</a>)';
1409
-
1410
- if ( conditionLevel >= numberOfQueries ) {
1411
-
1412
- htmlCode += '<span id="add-edit-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + '" style="display:initial"> (<a class="add-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)';
1413
- htmlCode += '" id="tvc-add-attribute-query-row-' + rowId +'-' + sourceLevel + '-' + conditionLevel + '" onclick="tvc_addCondition(' + rowId + ', ' + sourceLevel + ', ' + conditionLevel + ', \'\')">' + tvc_feed_settings_form_vars.add + '</a>)</span>';
1414
- }
1415
-
1416
- htmlCode += '</div>';
1417
-
1418
- return htmlCode;
1419
- }
1420
-
1421
- function tvc_orConditionSelector( rowId, inputsObject ) {
1422
- var inputSplit = inputsObject.split( '#' );
1423
- var staticField = '';
1424
- var html = '';
1425
-
1426
- if ( inputSplit[ 0 ] === 'static' ) {
1427
-
1428
- staticField = tvc_displayCorrectStaticField( rowId, '1', '0', _feedHolder[ 'channel' ], _feedHolder[ 'attributes' ][ rowId ][ 'fieldName' ], inputSplit[ 1 ] );
1429
- inputsObject = 'static';
1430
- }
1431
-
1432
- html += 'or ';
1433
- html += tvc_alternativeInputFieldCntrl( rowId, inputsObject );
1434
- html += '<span id="alternative-static-input-' + rowId + '">' + staticField + '</span>';
1435
- html += ' for all other products ';
1436
- html += '(<a class="edit-prod-source tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-prod-source-' + rowId + '" onclick="addSource(' + rowId + ', 0, \'\')">';
1437
- html += tvc_feed_settings_form_vars.edit + '</a>)';
1438
-
1439
- return html;
1440
- }
1441
-
1442
- function tvc_ifValueQuerySelector( rowId, sourceLevel, queryLevel, queryObject, lastValue ) {
1443
-
1444
- var htmlCode = '';
1445
- var query = tvc_isEmptyQueryObject( queryObject ) ? tvc_makeCleanQueryObject() : queryObject;
1446
- var querySelector = 'if ';
1447
- var queryValueConditionChangedFunctionString = 'tvc_queryValueConditionChanged(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ', 0)';
1448
-
1449
- if ( queryLevel > 1 ) {
1450
-
1451
- querySelector = query.preCondition === '1'
1452
- ? '<select id="value-options-sub-query-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" onchange="tvc_storeValueCondition(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')"><option value="2">' + tvc_feed_settings_form_vars.or + '</option><option value="1" selected>' + tvc_feed_settings_form_vars.and + '</option></select>'
1453
- : '<select id="value-options-sub-query-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" onchange="tvc_storeValueCondition(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')"><option value="2" selected>' + tvc_feed_settings_form_vars.or + '</option><option value="1">' + tvc_feed_settings_form_vars.and + '</option></select>';
1454
- }
1455
-
1456
- htmlCode += '<div class="value-options-query-selector" id="value-options-condition-' + rowId + '-' + sourceLevel + '-' + queryLevel + '">';
1457
- htmlCode += querySelector;
1458
- htmlCode += tvc_conditionFieldCntrl( rowId, sourceLevel, queryLevel, - 1, 'value-options-input-field-cntrl', query.source, queryValueConditionChangedFunctionString );
1459
- htmlCode += tvc_conditionQueryCntrl( rowId, sourceLevel, queryLevel, 0, 'value-query-condition', 'tvc_queryValueConditionChanged', query.condition );
1460
-
1461
- if ( queryObject.condition !== '4' && queryObject.condition !== '5' ) {
1462
- htmlCode += '<input type="text" onchange="tvc_storeValueCondition(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')" name="value-options-condition-value" id="value-options-condition-value-';
1463
- htmlCode += rowId + '-' + sourceLevel + '-' + queryLevel + '" value="' + query.value + '" style="display:initial">';
1464
- }
1465
-
1466
- if ( queryObject.condition !== '14' ) {
1467
-
1468
- htmlCode += '<span id="value-options-condition-and-value-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" style="display:none;"> ' + tvc_feed_settings_form_vars.and + ' ';
1469
- htmlCode += '<input id="value-options-condition-and-value-input-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" ';
1470
- htmlCode += 'type="text" onchange="tvc_storeValueCondition(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')" name="value-condition-and-value"></span>';
1471
- } else {
1472
-
1473
- htmlCode += '<span id="value-options-condition-and-value-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" style="display:initial"> ' + tvc_feed_settings_form_vars.and + ' ';
1474
- htmlCode += '<input id="value-options-condition-and-value-input-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" ';
1475
- htmlCode += 'type="text" onchange="tvc_storeValueCondition(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')" name="value-condition-and-value" value="' + queryObject.endValue + '"></span>';
1476
- }
1477
-
1478
- htmlCode += '(<a class="remove-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)" id="tvc-remove-attribute-query-' + rowId + '-' + sourceLevel + '-' + queryLevel;
1479
- htmlCode += '" onclick="tvc_removeValueQuery(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ')">' + tvc_feed_settings_form_vars.remove + '</a>)';
1480
-
1481
- if ( lastValue ) {
1482
-
1483
- htmlCode += '<span id="value-options-add-edit-condition-' + rowId + '-' + sourceLevel + '-' + queryLevel + '" style="display:initial">(<a class="add-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)';
1484
- htmlCode += '" id="tvc-add-attribute-query-row-' + rowId +'-' + sourceLevel + '-' + queryLevel + '" onclick="tvc_addValueQuery(' + rowId + ', ' + sourceLevel + ', ' + queryLevel + ', \'\')">' + tvc_feed_settings_form_vars.add + '</a>)</span>';
1485
- }
1486
-
1487
- htmlCode += '</div>';
1488
-
1489
- return htmlCode;
1490
- }
1491
-
1492
- function tvc_addOptionalFieldRow( level ) {
1493
-
1494
- var htmlCode = '';
1495
- var addRow = false;
1496
-
1497
- if ( level === 3 ) {
1498
-
1499
- addRow = _undefinedRecommendedOutputs.length > 0;
1500
- } else if ( level === 4 ) {
1501
-
1502
- addRow = _undefinedOptionalOutputs.length > 0;
1503
- } else if ( level === 5 ) {
1504
-
1505
- //addRow = _undefinedCustomOutputs.length > 0 ? true : false;
1506
- addRow = true;
1507
- }
1508
-
1509
- if ( addRow === true ) {
1510
-
1511
- if ( level === 3 ) {
1512
- htmlCode += '<div class="field-table-row-wrapper" id="new-recommended-row" style="display:none;"></div>';
1513
- } else if ( level === 4 ) {
1514
- htmlCode += '<div class="field-table-row-wrapper" id="new-optional-row"></div>';
1515
- } else if ( level === 5 ) {
1516
- htmlCode += '<div class="field-table-row-wrapper" id="new-custom-row"></div>';
1517
- }
1518
-
1519
- htmlCode += '<div class="field-table-row-top">';
1520
- htmlCode += '<div class="col2w" id="output-select-' + level;
1521
-
1522
- htmlCode += level !== 5 ? '" onchange="tvc_changedOutputSelection(' + level + ')">' + tvc_outputFieldCntrl( level ) :
1523
- '">' + tvc_customOutputFieldCntrl();
1524
-
1525
- htmlCode += '</div></div>';
1526
- }
1527
-
1528
- return htmlCode;
1529
- }
1530
-
1531
- /**
1532
- * Is called when the user wants to edit an advised source. Changes the advised output string to a source selector
1533
- *
1534
- * @param {string} rowId string containing the id of the feed row
1535
- * @param {string} sourceLevel string containing the source counter
1536
- */
1537
- function tvc_editOutput( rowId, sourceLevel ) {
1538
-
1539
- var htmlCode = '';
1540
-
1541
- htmlCode += tvc_inputFieldCntrl( rowId, sourceLevel, '', '', _feedHolder[ 'attributes' ][ rowId ][ 'advisedSource' ], '', false );
1542
- htmlCode += '<div class="field-table-row-combined-selection" id="combined-selectors-' + rowId + '" style="display:none;"></div>';
1543
-
1544
- jQuery( '#source-select-' + rowId + '-' + sourceLevel ).html( htmlCode );
1545
- }
1546
-
1547
- function tvc_removeCondition( rowId, sourceLevel, conditionLevel ) {
1548
-
1549
- // remove the selected query
1550
- _feedHolder.removeValueConditionValue( rowId, sourceLevel, conditionLevel );
1551
-
1552
- var queries = _feedHolder.getAttributesQueriesObject( rowId, sourceLevel );
1553
-
1554
- var nrQueries = tvc_countObjectItems( queries );
1555
-
1556
- // remove the old condition-wrappers
1557
- for ( var t = 1; t < nrQueries + 2; t ++ ) {
1558
-
1559
- jQuery( '#condition-' + rowId + '-' + sourceLevel + '-' + t ).remove();
1560
- // jQuery( '#dummy-source-' + rowId + '-' + sourceLevel + '-' + t ).remove();
1561
- }
1562
-
1563
- // update the form
1564
- if ( nrQueries > 0 ) {
1565
-
1566
- for ( var i = 0; i < nrQueries; i ++ ) {
1567
-
1568
- tvc_conditionCode( rowId, sourceLevel, i, queries[ i ], nrQueries );
1569
- }
1570
-
1571
- jQuery( '#edit-conditions-' + rowId ).append( tvc_orSelectorCode( rowId, '' ) );
1572
- } else {
1573
-
1574
- var forAllProductsCode = '<div class="condition-wrapper" id="condition-' + rowId + '-' + sourceLevel + '-0">'
1575
- + tvc_forAllProductsCondition( rowId, sourceLevel, 'initial' ) + '</div>';
1576
-
1577
- //jQuery( forAllProductsCode ).insertAfter( '#source-select-' + rowId + '-' + sourceLevel );
1578
- jQuery( '#condition-data-' + rowId + '-' + sourceLevel ).html( forAllProductsCode );
1579
-
1580
- // also remove the for all other products row
1581
- jQuery( '#source-' + rowId + '-' + (
1582
- sourceLevel + 1
1583
- ) ).remove();
1584
- }
1585
- }
1586
-
1587
- function tvc_removeValueQuery( rowId, sourceLevel, queryLevel ) {
1588
-
1589
- // remove the selected query
1590
- _feedHolder.removeValueQueryValue( rowId, sourceLevel, queryLevel );
1591
-
1592
- var queries = _feedHolder.getValueQueryValue( rowId, sourceLevel );
1593
- var editConditionsElement = jQuery( '#edit-conditions-' + rowId );
1594
- var nrQueries = tvc_countObjectItems( queries );
1595
-
1596
- // when the value is fully empty after removing the condition, deactivate the attribute
1597
- if ( ! _feedHolder[ 'attributes' ][ rowId ][ 'value' ] ) {
1598
-
1599
- _feedHolder.deactivateAttribute( rowId );
1600
- }
1601
-
1602
- // clean the old queries html
1603
- jQuery( '#value-editor-queries-' + rowId + '-' + sourceLevel + '-0' ).empty();
1604
- editConditionsElement.empty();
1605
-
1606
- // remove the condition and update the form
1607
- if ( nrQueries > 0 ) {
1608
-
1609
- for ( var i = 0; i < nrQueries; i ++ ) {
1610
-
1611
- tvc_addValueQuery( rowId, sourceLevel, i, queries[ i ] );
1612
- }
1613
-
1614
- editConditionsElement.append( tvc_orSelectorCode( rowId, '' ) );
1615
- } else {
1616
-
1617
- jQuery( '#value-editor-input-query-span-' + rowId + '-' + sourceLevel + '-0' ).show();
1618
-
1619
- // as there are no queries, the other change value needs to be removed from the meta
1620
- _feedHolder.removeEditValueValue( rowId, (
1621
- sourceLevel + 1
1622
- ), 0 );
1623
-
1624
- // also remove the "for all other products" change value line
1625
- jQuery( '#edit-value-span-' + rowId + '-' + (
1626
- sourceLevel + 1
1627
- ) + '-0' ).remove();
1628
- }
1629
- }
1630
-
1631
- function tvc_removeRow( rowId, fieldName ) {
1632
- // find the index of the selected item in the correct undefined outputs list
1633
- var ind = _definedRecommendedOutputs.indexOf( fieldName );
1634
- var level = 3;
1635
-
1636
- if ( ind < 0 ) {
1637
- ind = _definedOptionalOutputs.indexOf( fieldName );
1638
- level = 4;
1639
- }
1640
-
1641
- // deactivate the attribute
1642
- _feedHolder.deactivateAttribute( rowId );
1643
-
1644
- // remove the source row from the form
1645
- jQuery( '#row-' + rowId ).remove();
1646
-
1647
- // reset the lists that contain the selected and non selected output fields
1648
- if ( level === 3 ) {
1649
- _definedRecommendedOutputs.splice( ind, 1 );
1650
- _undefinedRecommendedOutputs.push( fieldName );
1651
- _undefinedRecommendedOutputs.sort();
1652
- } else if ( level === 4 ) {
1653
- _definedOptionalOutputs.splice( ind, 1 );
1654
- _undefinedOptionalOutputs.push( fieldName );
1655
- _undefinedOptionalOutputs.sort();
1656
- }
1657
-
1658
- var outputFieldControlElement = jQuery( '#output-field-cntrl-' + level );
1659
- outputFieldControlElement.empty();
1660
- outputFieldControlElement.html( tvc_outputFieldCntrl( level ) );
1661
- }
1662
-
1663
- /**
1664
- * Adds the condition controls to the attribute mapping rows.
1665
- *
1666
- * @param {int} rowId Id of the row of the attribute.
1667
- * @param {int} sourceLevel Level of the source.
1668
- * @param {int} conditionLevel Level of the condition.
1669
- * @param {string} query String containing the query
1670
- */
1671
- function tvc_addCondition( rowId, sourceLevel, conditionLevel, query ) {
1672
-
1673
- // show the condition controls
1674
- var condition = tvc_conditionCode( rowId, sourceLevel, conditionLevel, query, 0 );
1675
-
1676
- if ( condition ) {
1677
- // and if its the first condition level
1678
- if ( '0' === String( conditionLevel ) ) {
1679
-
1680
- // add a "for all other products" row
1681
- jQuery( tvc_addFeedSourceRow( rowId, sourceLevel + 1, _feedHolder.getSourceObject( rowId ) ) ).insertAfter( '#source-' + rowId + '-' + sourceLevel, false );
1682
- }
1683
-
1684
- // if this input has an advised value, than store this advised value in the meta data
1685
- if ( _feedHolder[ 'attributes' ][ rowId ][ 'advisedSource' ] ) {
1686
-
1687
- _feedHolder.setSourceValue( rowId, (
1688
- sourceLevel + 1
1689
- ), _feedHolder[ 'attributes' ][ rowId ][ 'advisedSource' ] );
1690
- }
1691
- }
1692
- }
1693
-
1694
- function tvc_conditionCode( rowId, sourceLevel, conditionLevel, query, nrQueries ) {
1695
-
1696
- if ( query || tvc_sourceIsFilled( rowId, sourceLevel, conditionLevel ) ) {
1697
-
1698
- // get the data from the selection fields (only used when query is not empty)
1699
- var queryCondition = jQuery( '#query-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
1700
- var inputField = jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
1701
- var conditionValue = jQuery( '#condition-value-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
1702
- var wait = false;
1703
-
1704
- if ( queryCondition !== '4' && queryCondition !== '5' && queryCondition !== '14' ) {
1705
-
1706
- if ( inputField === 'select' || conditionValue === '' ) {
1707
-
1708
- wait = true;
1709
- }
1710
- } else if ( queryCondition === 4 || queryCondition === 5 ) {
1711
-
1712
- if ( inputField === 'select' ) {
1713
-
1714
- wait = true;
1715
- }
1716
- }
1717
-
1718
- if ( wait === false || conditionLevel === 0 ) {
1719
-
1720
- _feedHolder.incrNrQueries( rowId );
1721
-
1722
- var queryObject = tvc_queryStringToQueryObject( query );
1723
-
1724
- if ( conditionLevel === 0 ) {
1725
- jQuery( '#condition-' + rowId + '-' + sourceLevel + '-0' ).remove();
1726
- }
1727
-
1728
- // replaces the "for all products" with a new empty condition row
1729
- jQuery( '#condition-data-' + rowId + '-' + sourceLevel ).append( tvc_ifConditionSelector( rowId, sourceLevel, conditionLevel + 1, nrQueries, queryObject ) );
1730
-
1731
- if ( conditionLevel > 0 ) {
1732
- // remove the "add" button from the previous condition so only the last condition has an "add" button
1733
- jQuery( '#add-edit-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).remove();
1734
- }
1735
-
1736
- return true;
1737
- } else {
1738
- alert( tvc_feed_settings_form_vars.fill_current_condition_warning );
1739
-
1740
- return false;
1741
- }
1742
- } else {
1743
-
1744
- alert( tvc_feed_settings_form_vars.select_a_source_field_warning );
1745
-
1746
- return false;
1747
- }
1748
- }
1749
-
1750
- function tvc_addValueQuery( rowId, sourceLevel, queryLevel, query ) {
1751
-
1752
- if ( tvc_sourceIsFilled( rowId, sourceLevel, queryLevel ) ) {
1753
-
1754
- // get the data from the selection fields (only used when query is not empty)
1755
- var queryCondition = jQuery( '#value-query-condition-' + rowId + '-' + sourceLevel + '-' + queryLevel + '-0' ).val();
1756
- var inputField = jQuery( '#value-options-input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + queryLevel ).val();
1757
- var conditionValue = jQuery( '#value-options-condition-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).val();
1758
- var wait = false;
1759
-
1760
- if ( queryCondition !== '4' && queryCondition !== '5' && queryCondition !== '14' ) {
1761
-
1762
- if ( inputField === 'select' || conditionValue === '' ) {
1763
-
1764
- wait = true;
1765
- }
1766
- } else if ( queryCondition === 4 || queryCondition === 5 ) {
1767
-
1768
- if ( inputField === 'select' ) {
1769
-
1770
- wait = true;
1771
- }
1772
- }
1773
-
1774
- if ( wait === false || sourceLevel === 0 ) {
1775
-
1776
- //_feed.incrNrQueries( id );
1777
-
1778
- var queryArray = tvc_queryStringToQueryObject( query );
1779
-
1780
- jQuery( '#value-options-add-edit-condition-' + rowId + '-' + sourceLevel + '-' + queryLevel ).hide(); // hides the add button on this condition level
1781
- jQuery( '#value-editor-queries-' + rowId + '-' + sourceLevel + '-0' ).append( tvc_ifValueQuerySelector( rowId, sourceLevel, queryLevel + 1, queryArray, true ) );
1782
- } else {
1783
- alert( tvc_feed_settings_form_vars.fill_current_condition_warning );
1784
- }
1785
- } else {
1786
- alert( tvc_feed_settings_form_vars.elect_a_source_field_warning );
1787
- }
1788
- }
1789
-
1790
- function tvc_conditionSelectorCode( id, sourceLevel, level, nrQueries, query ) {
1791
-
1792
- var queryArray = tvc_queryStringToQueryObject( query );
1793
-
1794
- return tvc_ifConditionSelector( id, sourceLevel, level + 1, nrQueries, queryArray );
1795
- }
1796
-
1797
- function tvc_orSelectorRowCode( rowId, sourceLevel, borderStyleClass ) {
1798
- // source wrapper
1799
- var htmlCode = '<div class="feed-source-row" id="source-' + rowId + '-' + sourceLevel + '">';
1800
-
1801
- // first column wrapper
1802
- htmlCode += '<div class="add-to-feed-column colw col20w">&nbsp;</div>';
1803
-
1804
- // the source data and queries wrapper
1805
- htmlCode += '<div class="source-data-column colw col80w' + borderStyleClass + '" id="source-data-' + rowId + '-' + sourceLevel + '">';
1806
-
1807
- htmlCode += '<div class="source-selector colw col30w" id="source-select-' + rowId + '-' + sourceLevel + '"></div>';
1808
- htmlCode += tvc_orSelectorCode( rowId, '' );
1809
- htmlCode += '<div></div>';
1810
-
1811
- htmlCode += tvc_endrow( rowId );
1812
-
1813
- htmlCode += '</div></div>';
1814
-
1815
- return htmlCode;
1816
- }
1817
-
1818
- function tvc_orSelectorCode( id, alternativeInputs ) {
1819
-
1820
- let alternative = '';
1821
-
1822
- if ( alternativeInputs ) {
1823
-
1824
- for ( let altKey in alternativeInputs ) {
1825
-
1826
- alternative = alternativeInputs[ altKey ];
1827
- }
1828
- }
1829
-
1830
- return '<div class="or-selector" id="or-selector-' + id + '">' + tvc_orConditionSelector( id, alternative ) + '</div>';
1831
- }
1832
-
1833
- function tvc_showEditValueQuery( rowId, sourceLevel, queryLevel, query ) {
1834
- var emptyQueryObject = {};
1835
-
1836
- // add a query selector
1837
- jQuery( '#value-editor-queries-' + rowId + '-' + sourceLevel + '-' + queryLevel ).
1838
- html( tvc_ifValueQuerySelector( rowId, sourceLevel, queryLevel + 1, emptyQueryObject, query ) );
1839
-
1840
- // hide the 'for all products' text
1841
- jQuery( '#value-editor-input-query-span-' + rowId + '-' + sourceLevel + '-0' ).hide();
1842
-
1843
- if ( queryLevel === 0 && query ) {
1844
-
1845
- // if it's the first query for this change value, then also add a "for all other products" row
1846
- tvc_addRowValueEditor( rowId, sourceLevel + 1, 0, '' );
1847
- }
1848
- }
1849
-
1850
- /**
1851
- * Gets called when the user selects a source from the source selector
1852
- *
1853
- * @param {string} rowId
1854
- * @param {string} sourceLevel
1855
- * @param {string} advisedSource
1856
- * @returns nothing
1857
- */
1858
- function tvc_changedOutput( rowId, sourceLevel, advisedSource ) {
1859
-
1860
- var selectedValue = jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel ).val();
1861
- var combinationLevel = 0;
1862
- var sourceSelectorElement = jQuery( '#source-select-' + rowId + '-' + sourceLevel );
1863
- var combinedWrapperElement = jQuery( '#combined-wrapper-' + rowId + '-' + sourceLevel );
1864
- var staticInputFieldElement = jQuery( '#static-input-field-' + rowId + '-' + sourceLevel + '-' + combinationLevel );
1865
- var staticConditionInputElement = jQuery( '#static-condition-input-' + rowId + '-' + sourceLevel + '-' + combinationLevel );
1866
-
1867
- switch ( selectedValue ) {
1868
- case 'advised':
1869
-
1870
- if ( rowId !== 3 ) {
1871
-
1872
- var htmlCode = '';
1873
-
1874
- if ( advisedSource !== 'Use the settings in the Merchant Center' ) {
1875
-
1876
- var label = tvc_sourceOptionsConverter( advisedSource );
1877
-
1878
- // reset the row to display an advised input row
1879
- htmlCode = '<div class="advised-source">' + label + tvc_editSourceSelector( rowId, sourceLevel ) + '</div>'; // <span id="static-input-' + id + '"></span>';
1880
- } else {
1881
-
1882
- htmlCode = '<div class="advised-source">Use the settings in the Merchant Center ' + tvc_editSourceSelector( rowId, sourceLevel ) + '</div>';
1883
- }
1884
-
1885
- sourceSelectorElement.html( htmlCode );
1886
-
1887
- // clear the attribute value
1888
- _feedHolder.clearSourceValue( rowId, sourceLevel );
1889
- _feedHolder.deactivateAttribute( rowId );
1890
- } else {
1891
-
1892
- htmlCode = '<span id="category-source-string">' + _feedHolder.mainCategory
1893
- + '</span>' + tvc_editSourceSelector( rowId, sourceLevel );
1894
-
1895
- _feedHolder.setCategoryValue( rowId, _feedHolder.mainCategory );
1896
- sourceSelectorElement.html( htmlCode );
1897
- }
1898
-
1899
- break;
1900
-
1901
- case 'static':
1902
-
1903
- sourceSelectorElement.
1904
- append( tvc_displayCorrectStaticField( rowId, sourceLevel, '0', _feedHolder[ 'channel' ], _feedHolder[ 'attributes' ][ rowId ][ 'fieldName' ], '' ) );
1905
- combinedWrapperElement.remove();
1906
-
1907
- var staticValue = staticInputFieldElement.val() ? staticInputFieldElement.val() :
1908
- jQuery( '#static-condition-input-' + rowId + '-' + sourceLevel + '-' + combinationLevel + ' option:selected' ).val();
1909
-
1910
- // set the attribute value in the feed on the standard value of the input field for when the user leaves it there
1911
- _feedHolder.setStaticAttributeValue( rowId, sourceLevel, combinationLevel, staticValue );
1912
-
1913
- if ( staticValue || sourceLevel > 0 ) {
1914
- _feedHolder.activateAttribute( rowId );
1915
- } else {
1916
- _feedHolder.deactivateAttribute( rowId );
1917
- }
1918
-
1919
- break;
1920
-
1921
- case 'select':
1922
-
1923
- // reset the source value
1924
- _feedHolder.clearSourceValue( rowId, sourceLevel );
1925
- if ( sourceLevel === '0' ) {
1926
- _feedHolder.deactivateAttribute( rowId );
1927
- }
1928
-
1929
- staticInputFieldElement.remove();
1930
- staticConditionInputElement.remove();
1931
- combinedWrapperElement.remove();
1932
-
1933
- tvc_clearStaticField( rowId );
1934
-
1935
- break;
1936
-
1937
- case 'combined':
1938
-
1939
- _feedHolder.setSourceValue( rowId, sourceLevel, selectedValue );
1940
- if ( sourceLevel === '0' ) {
1941
- _feedHolder.deactivateAttribute( rowId );
1942
- }
1943
-
1944
- staticInputFieldElement.remove();
1945
- staticConditionInputElement.remove();
1946
-
1947
- tvc_addCombinedField( rowId, sourceLevel, 0 );
1948
-
1949
- break;
1950
-
1951
- case 'category_mapping':
1952
-
1953
- _feedHolder.setCustomCategory( rowId, _feedHolder.mainCategory );
1954
- // Deze optie geeft een foutmelding!!!!!, maar zou wel de goede optie moeten zijn!!!!
1955
- // _feedHolder.setCategoryValue( rowId, _feedHolder.mainCategory );
1956
- // nieuwe feed maken, aantal outputs invoeren, een van de outputs aan de category map koppelen
1957
- // feed wordt nu wel gemaakt, maar de value van dit attribute wordt geen "t" waarde, maar blijft een
1958
- // een 'm' met 's' waarde
1959
-
1960
- staticInputFieldElement.remove();
1961
- staticConditionInputElement.remove();
1962
- combinedWrapperElement.remove();
1963
-
1964
- // remove the condition and edit values options
1965
- jQuery( '#condition-' + rowId + '-' + sourceLevel + '-0' ).remove();
1966
- jQuery( '#value-editor-input-query-add-span-' + rowId + '-' + sourceLevel + '-0' ).hide();
1967
-
1968
- // display the standard category text message
1969
- sourceSelectorElement.html( tvc_categorySource() );
1970
-
1971
- break;
1972
-
1973
- default:
1974
-
1975
- jQuery( '#static-input-' + rowId ).html( '' );
1976
-
1977
- if ( selectedValue === advisedSource && sourceLevel === '0' && jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel + '-0' ).val() === 'select' ) {
1978
-
1979
- _feedHolder.clearSourceValue( rowId, sourceLevel );
1980
- } else {
1981
-
1982
- _feedHolder.setSourceValue( rowId, sourceLevel, selectedValue );
1983
- }
1984
-
1985
- _feedHolder.activateAttribute( rowId );
1986
- _feedHolder[ 'attributes' ][ rowId ][ 'isActive' ] = true;
1987
-
1988
- staticInputFieldElement.remove();
1989
- staticConditionInputElement.remove();
1990
- combinedWrapperElement.remove();
1991
-
1992
- break;
1993
- }
1994
- }
1995
-
1996
- function tvc_changedAlternativeSource( rowId ) {
1997
- var sourceLevel = '1'; // Only works as long as only the WooCommerce "source" is used by the plugin. Needs to be updated as soon as more sources are added.
1998
- var selectedValue = jQuery( '#alternative-input-field-cntrl-' + rowId ).val();
1999
-
2000
- if ( selectedValue === 'static' ) {
2001
- var htmlCode = tvc_displayCorrectStaticField( rowId, sourceLevel, '0', _feedHolder[ 'channel' ], _feedHolder[ 'attributes' ][ rowId ][ 'fieldName' ], '' );
2002
-
2003
- jQuery( '#alternative-static-input-' + rowId ).html( htmlCode );
2004
-
2005
- } else {
2006
-
2007
- jQuery( '#alternative-static-input-' + rowId ).empty();
2008
-
2009
- if ( selectedValue !== 'select' && selectedValue !== 'empty' ) {
2010
-
2011
- _feedHolder.setAlternativeSourceValue( rowId, sourceLevel, selectedValue );
2012
- } else {
2013
-
2014
- _feedHolder.removeAlternativeSourceValue( rowId, sourceLevel );
2015
- }
2016
- }
2017
- }
2018
-
2019
- function tvc_changedCombinationSeparator( rowId, sourveLevel, combinationLevel ) {
2020
- tvc_changedCombinedOutput( rowId, sourveLevel, combinationLevel );
2021
- }
2022
-
2023
- function tvc_changedCombinedOutput( rowId, sourceLevel, combinationLevel ) {
2024
- var selectedValue = jQuery( '#combined-input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + combinationLevel ).val();
2025
- var staticValueControl = jQuery( '#static-value-control-' + rowId + '-' + sourceLevel + '-' + combinationLevel );
2026
-
2027
- switch ( selectedValue ) {
2028
- case 'static':
2029
- if ( ! jQuery( '#static-input-field-' + rowId + '-' + sourceLevel + '-' + combinationLevel ).val() ) {
2030
- var htmlCode = tvc_displayCorrectStaticField( rowId, sourceLevel, combinationLevel, _feedHolder[ 'channel' ], _feedHolder[ 'attributes' ][ rowId ][ 'fieldName' ],
2031
- '' );
2032
- staticValueControl.html( htmlCode );
2033
- }
2034
-
2035
- break;
2036
-
2037
- default:
2038
- staticValueControl.empty();
2039
-
2040
- break;
2041
- }
2042
-
2043
- var combinedOutput = getCombinedValue( rowId, sourceLevel );
2044
-
2045
- if ( combinedOutput ) {
2046
- _feedHolder.setCombinedOutputValue( rowId, sourceLevel, combinedOutput );
2047
- _feedHolder.activateAttribute( rowId );
2048
- } else {
2049
- _feedHolder.removeCombinedOutputValue( rowId, sourceLevel, combinationLevel );
2050
- if ( sourceLevel === '0' ) {
2051
- _feedHolder.deactivateAttribute( rowId );
2052
- } // only deactivate when when on the first (0) level
2053
- }
2054
- }
2055
-
2056
- function tvc_removeCombinedField( id, sourceLevel, combinedLevel ) {
2057
-
2058
- _feedHolder.removeCombinedOutputValue( id, sourceLevel, combinedLevel );
2059
-
2060
- var combinedValueObject = JSON.parse( _feedHolder[ 'attributes' ][ id ][ 'value' ] );
2061
- var combinedValuePart = 'm' in combinedValueObject ? combinedValueObject.m : {};
2062
- var combinedValue = tvc_getMappingCombinedValue( combinedValuePart, sourceLevel );
2063
-
2064
- jQuery( '#source-select-' + id + '-' + sourceLevel ).append( tvc_combinedField( id, sourceLevel, combinedLevel, combinedValue, false ) );
2065
- }
2066
-
2067
- function tvc_clearStaticField( id ) {
2068
- jQuery( '#static-input-' + id ).html( '' );
2069
- }
2070
-
2071
- function tvc_storeValueCondition( rowId, conditionLevel, queryLevel ) {
2072
-
2073
- var source = jQuery( '#value-options-input-field-cntrl-' + rowId + '-' + conditionLevel + '-' + queryLevel ).val();
2074
-
2075
- if ( source !== 'select' ) {
2076
-
2077
- var doStore;
2078
-
2079
- // get the data required to build the query string
2080
- var subCondition = queryLevel > 1 ? jQuery( '#value-options-sub-query-' + rowId + '-' + conditionLevel + '-' + queryLevel + ' option:selected' ).val() : '0';
2081
- var condition = jQuery( '#value-query-condition-' + rowId + '-' + conditionLevel + '-' + queryLevel + '-0 option:selected' ).val();
2082
- var value = condition !== '4' && condition !== '5' ? jQuery( '#value-options-condition-value-' + rowId + '-' + conditionLevel + '-' + queryLevel ).val() : '';
2083
- var betweenValue = condition === '14' ? jQuery( '#value-options-condition-and-value-input-' + rowId + '-' + conditionLevel + '-' + queryLevel ).val() : '';
2084
-
2085
- if ( condition === '4' || condition === '5' ) {
2086
-
2087
- doStore = true;
2088
- } else if ( condition === '14' ) {
2089
-
2090
- doStore = ! ! (
2091
- value && betweenValue
2092
- );
2093
- } else {
2094
-
2095
- doStore = ! ! value;
2096
- }
2097
-
2098
- if ( doStore === true ) {
2099
-
2100
- var subConditionString = subCondition !== '' ? subCondition + '#' : '0#';
2101
-
2102
- // build the query string
2103
- var query = subConditionString + source + '#' + condition;
2104
-
2105
- if ( value ) {
2106
- query += '#' + value;
2107
- }
2108
-
2109
- if ( betweenValue ) {
2110
- query += '#0#' + betweenValue;
2111
- }
2112
-
2113
- // store the query string in the feed object
2114
- _feedHolder.addValueQueryValue( rowId, conditionLevel, queryLevel, query );
2115
- }
2116
- } else {
2117
- console.log( 'Query ' + rowId + '-' + conditionLevel + '-' + queryLevel + ' removed!' );
2118
-
2119
- _feedHolder.removeValueQueryValue( rowId, conditionLevel, queryLevel );
2120
- }
2121
- }
2122
-
2123
- function tvc_storeCondition( rowId, sourceLevel, conditionLevel ) {
2124
-
2125
- var source = jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
2126
- var result = false;
2127
-
2128
- if ( tvc_validSourceSelected( rowId, sourceLevel ) ) {
2129
-
2130
- // only store the condition if the user has selected a condition option
2131
- if ( source !== 'select' ) {
2132
-
2133
- var doStore;
2134
-
2135
- // get the data from the input fields
2136
- var subCondition = conditionLevel > 1 ? jQuery( '#sub-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + ' option:selected' ).val() : '0';
2137
- var condition = jQuery( '#query-condition-' + rowId + '-' + sourceLevel + '-' + conditionLevel + ' option:selected' ).val();
2138
- var value = condition !== '4' && condition !== '5' ? jQuery( '#condition-value-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val() : '';
2139
- var secondValue = condition === '14' ? jQuery( '#condition-and-value-input-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val() : '';
2140
-
2141
- if ( condition === '4' || condition === '5' ) {
2142
-
2143
- doStore = true;
2144
- } else if ( condition === '14' ) { // is between condition
2145
-
2146
- doStore = ! ! (
2147
- value && secondValue
2148
- );
2149
- } else {
2150
-
2151
- doStore = ! ! (
2152
- value
2153
- );
2154
- }
2155
-
2156
- // only store the data when it is complete
2157
- if ( doStore === true ) {
2158
-
2159
- var subConditionString = subCondition !== '' ? subCondition + '#' : '0#';
2160
-
2161
- // build the query string
2162
- var query = subConditionString + source + '#' + condition;
2163
-
2164
- if ( value ) {
2165
- query += '#' + value;
2166
- }
2167
-
2168
- if ( secondValue ) {
2169
- query += '#0#' + secondValue;
2170
- }
2171
-
2172
- // store the query string in the feed object
2173
- _feedHolder.addConditionValue( rowId, query, sourceLevel, conditionLevel );
2174
-
2175
- result = true;
2176
- }
2177
- } else {
2178
-
2179
- _feedHolder.removeValueConditionValue( rowId, sourceLevel, conditionLevel );
2180
- }
2181
- } else {
2182
-
2183
- jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel + '-1' ).prop( 'selectedIndex', 0 );
2184
- jQuery( '#condition-value-' + rowId + '-' + sourceLevel + '-1' ).val( '' );
2185
-
2186
- alert( tvc_feed_settings_form_vars.select_a_valid_source_warning );
2187
- }
2188
-
2189
- return result;
2190
- }
2191
-
2192
- function tvc_validSourceSelected( rowId, sourceLevel ) {
2193
-
2194
- var mainSelection = jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel ).val();
2195
-
2196
- switch ( mainSelection ) {
2197
-
2198
- case 'select':
2199
- return false;
2200
-
2201
- case 'static':
2202
- var staticConditionInputElement = jQuery( '#static-condition-input-' + rowId + '-' + sourceLevel + '-0' );
2203
- var staticInputFieldElement = jQuery( '#static-input-field-' + rowId + '-' + sourceLevel + '-0' );
2204
-
2205
- // TODO: uitzoeken waarom ik de ene keer een static-condition-input en de ander keer een static-input-field als id gebruik
2206
- if ( staticConditionInputElement.val() ) {
2207
- return ! ! staticConditionInputElement.val();
2208
- } else if ( staticInputFieldElement.val() ) {
2209
- return ! ! staticInputFieldElement.val();
2210
- } else {
2211
- return false;
2212
- }
2213
-
2214
- case 'combined':
2215
- return jQuery( '#combined-input-field-cntrl-' + rowId + '-' + sourceLevel + '-2' ).val() !== 'select';
2216
-
2217
- default:
2218
- return true;
2219
- }
2220
- }
2221
-
2222
- function tvc_valueInputOptionsChanged( rowId, sourceLevel, valueEditorLevel ) {
2223
-
2224
- var option = jQuery( '#value-options-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + ' option:selected' ).text();
2225
- var value = jQuery( '#value-options-input-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel ).val();
2226
- var store = '';
2227
- var pre = sourceLevel > 0 ? 'and' : 'change';
2228
-
2229
- if ( option !== 'replace' && option !== 'recalculate' ) {
2230
-
2231
- store = pre + '#' + option + '#';
2232
- store += option === 'change nothing' ? 'blank' : value;
2233
-
2234
- _feedHolder.addChangeValue( rowId, sourceLevel, valueEditorLevel, store );
2235
- } else if ( option === 'replace' ) {
2236
-
2237
- var withValue = jQuery( '#value-options-input-with-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel ).val();
2238
-
2239
- if ( value && withValue ) {
2240
-
2241
- store = pre + '#' + option + '#' + value + '#' + withValue;
2242
- _feedHolder.addChangeValue( rowId, sourceLevel, valueEditorLevel, store );
2243
- }
2244
-
2245
- } else if ( option === 'recalculate' ) {
2246
-
2247
- var calculation = jQuery( '#value-options-recalculate-options-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + ' option:selected' ).text();
2248
-
2249
- if ( value ) {
2250
-
2251
- store = pre + '#' + option + '#' + calculation + '#' + value;
2252
- _feedHolder.addChangeValue( rowId, sourceLevel, valueEditorLevel, store );
2253
- }
2254
- }
2255
- }
2256
-
2257
- function tvc_removeValueEditor( rowId, sourceLevel, valueEditorLevel ) {
2258
-
2259
- _feedHolder.removeEditValueValue( rowId, sourceLevel, valueEditorLevel );
2260
-
2261
- var values = _feedHolder.getAttributesValueObject( rowId );
2262
- var nrValues = tvc_countObjectItems( values );
2263
-
2264
- // when the value is fully empty after removing the condition, deactivate the attribute
2265
- if ( ! _feedHolder[ 'attributes' ][ rowId ][ 'value' ] ) {
2266
-
2267
- _feedHolder.deactivateAttribute( rowId );
2268
- }
2269
-
2270
- jQuery( '#edit-value-span-' + rowId + '-' + sourceLevel + '-0' ).remove();
2271
-
2272
- if ( nrValues > 0 ) {
2273
-
2274
- for ( var i = 1; i < nrValues; i ++ ) {
2275
-
2276
- tvc_addRowValueEditor( rowId, sourceLevel, i, values[ i ] );
2277
- }
2278
- } else {
2279
-
2280
- jQuery( '#value-editor-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel ).remove();
2281
- jQuery( '#source-' + rowId + '-' + sourceLevel ).append( tvc_editValueSpan( rowId, sourceLevel, valueEditorLevel, 'initial' ) );
2282
- }
2283
- }
2284
-
2285
- function tvc_drawAttributeMappingSection() {
2286
-
2287
- var channel = _feedHolder.channel.toString(); // TODO: Channel is not always a string
2288
-
2289
- // reset the fields
2290
- tvc_resetFields();
2291
-
2292
- for ( var i = 0; i < _feedHolder[ 'attributes' ].length; i ++ ) {
2293
-
2294
- switch ( _feedHolder[ 'attributes' ][ i ][ 'fieldLevel' ] ) {
2295
-
2296
- case '1':
2297
- _mandatoryFields += tvc_fieldRow( _feedHolder[ 'attributes' ][ i ], false );
2298
- break;
2299
-
2300
- case '2':
2301
- _highlyRecommendedFields += tvc_fieldRow( _feedHolder[ 'attributes' ][ i ], false );
2302
- break;
2303
-
2304
- case '3':
2305
- if ( _feedHolder[ 'attributes' ][ i ][ 'isActive' ] ) {
2306
- _recommendedFields += tvc_fieldRow( _feedHolder[ 'attributes' ][ i ], true );
2307
- _definedRecommendedOutputs.push( _feedHolder[ 'attributes' ][ i ][ 'fieldName' ] );
2308
- } else {
2309
- _undefinedRecommendedOutputs.push( _feedHolder[ 'attributes' ][ i ][ 'fieldName' ] );
2310
- }
2311
- break;
2312
-
2313
- case '4':
2314
- if ( _feedHolder[ 'attributes' ][ i ][ 'isActive' ] ) {
2315
- _optionalFields += tvc_fieldRow( _feedHolder[ 'attributes' ][ i ], true );
2316
- _definedOptionalOutputs.push( _feedHolder[ 'attributes' ][ i ][ 'fieldName' ] );
2317
- } else {
2318
- _undefinedOptionalOutputs.push( _feedHolder[ 'attributes' ][ i ][ 'fieldName' ] );
2319
- }
2320
- break;
2321
-
2322
- case '5':
2323
- if ( _feedHolder[ 'attributes' ][ i ][ 'isActive' ] ) {
2324
- _customFields += tvc_fieldRow( _feedHolder[ 'attributes' ][ i ], true );
2325
- } else {
2326
- _undefinedCustomOutputs.push( _feedHolder[ 'attributes' ][ i ][ 'fieldName' ] );
2327
- }
2328
- break;
2329
-
2330
- default:
2331
- break;
2332
- }
2333
- }
2334
-
2335
- _definedRecommendedOutputs.sort();
2336
- _undefinedRecommendedOutputs.sort();
2337
-
2338
- _recommendedFields += tvc_addOptionalFieldRow( 3 );
2339
- _optionalFields += tvc_addOptionalFieldRow( 4 );
2340
-
2341
- if ( tvc_isCustomChannel( channel ) ) { // this means the user has selected a free format feed
2342
- _customFields += tvc_addOptionalFieldRow( 5 );
2343
- }
2344
-
2345
- if ( _mandatoryFields.length > 0 ) {
2346
- jQuery( '#required-field-table' ).html( _mandatoryFields );
2347
- jQuery( '#required-fields' ).show();
2348
- } else {
2349
- jQuery( '#required-fields' ).hide();
2350
- }
2351
-
2352
- if ( _highlyRecommendedFields.length > 0 ) {
2353
- jQuery( '#highly-recommended-field-table' ).html( _highlyRecommendedFields );
2354
- jQuery( '#highly-recommended-fields' ).show();
2355
- } else {
2356
- jQuery( '#highly-recommended-fields' ).hide();
2357
- }
2358
-
2359
- if ( _recommendedFields.length > 0 ) {
2360
- jQuery( '#recommended-field-table' ).html( _recommendedFields );
2361
- jQuery( '#recommended-fields' ).show();
2362
- } else {
2363
- jQuery( '#recommended-fields' ).hide();
2364
- }
2365
-
2366
- if ( _optionalFields.length > 0 ) {
2367
- jQuery( '#optional-field-table' ).html( _optionalFields );
2368
- jQuery( '#optional-fields' ).show();
2369
- } else {
2370
- jQuery( '#optional-fields' ).hide();
2371
- }
2372
-
2373
- if ( _customFields.length > 0 ) {
2374
- jQuery( '#custom-field-table' ).html( _customFields );
2375
- jQuery( '#custom-fields' ).show();
2376
- } else {
2377
- jQuery( '#custom-fields' ).hide();
2378
- }
2379
- tvc_feed_list_tab();
2380
- }
2381
-
2382
- function tvc_saveAndProceed() {
2383
- jQuery(".save-and-proceed").on("click",function(){
2384
- jQuery("#tvc-attribute-map-2").trigger("click");
2385
- });
2386
- }
2387
-
2388
- function tvc_feed_list_tab() {
2389
- var map1 = jQuery('#tvc-attribute-map-1');
2390
- var map2 = jQuery('#tvc-attribute-map-2');
2391
- var _centerbutton = jQuery('#page-center-buttons');
2392
- var _maininputmap = jQuery('#tvc-main-input-map');
2393
- var _catmap = jQuery( '#tvc-category-map' );
2394
- var _filterwrapper = jQuery('#main-product-filter-wrapper');
2395
- var _attributemap = jQuery( '#tvc-attribute-map' );
2396
-
2397
- _attributemap.hide();
2398
- map1.addClass('nav-tab-active');
2399
- map2.on('click',function () {
2400
- _centerbutton.hide();
2401
- map1.removeClass('nav-tab-active');
2402
- map2.addClass('nav-tab-active');
2403
- _maininputmap.hide();
2404
- _filterwrapper.hide();
2405
- _attributemap.show();
2406
- jQuery( '#tvc-category-map' ).hide();
2407
- jQuery(this).css("background-color:white");
2408
- });
2409
- map1.on('click',function () {
2410
- map2.removeClass('nav-tab-active');
2411
- map1.addClass('nav-tab-active');
2412
- _maininputmap.show();
2413
- _catmap.show();
2414
- _filterwrapper.show();
2415
- _attributemap.hide();
2416
- _centerbutton.show();
2417
- jQuery(this).css("background-color:white");
2418
- });
2419
- }
2420
-
2421
- function tvc_resetFields() {
2422
-
2423
- _mandatoryFields = [];
2424
- _highlyRecommendedFields = [];
2425
- _recommendedFields = [];
2426
- _undefinedRecommendedOutputs = [];
2427
- _optionalFields = [];
2428
- _undefinedOptionalOutputs = [];
2429
- _customFields = [];
2430
- _undefinedCustomOutputs = [];
2431
- }
2432
-
2433
- function tvc_queryConditionChanged( id, sourceLevel, conditionLevel ) {
2434
-
2435
- // TODO: tvc_queryConditionChanged en tvc_queryValueConditionChanged en andere functies die aan de conditions zijn
2436
- // gerelateerd kunnen volgens mij samengevoegd worden door in de query-condition niveaus toch een unieke subQuery
2437
- // nummer toe te voegen (bijvoorbeeld een lettercombinatie) waardoor ze van de value-query-condition niveaus
2438
- // kunnen worden gescheiden. Daarna is het combineren van beide condition opties mogelijk.
2439
-
2440
- // get the selected query option
2441
- var value = jQuery( '#query-condition-' + id + '-' + sourceLevel + '-' + conditionLevel ).val();
2442
-
2443
- // if the "is empty" or "is not empty" condition is selected
2444
- if ( value === '4' || value === '5' ) {
2445
-
2446
- jQuery( '#condition-value-' + id + '-' + sourceLevel + '-' + conditionLevel ).hide();
2447
- } else {
2448
-
2449
- jQuery( '#condition-value-' + id + '-' + sourceLevel + '-' + conditionLevel ).show();
2450
- }
2451
-
2452
- // if the "is between" condition is selected
2453
- if ( value === '14' ) {
2454
-
2455
- jQuery( '#condition-value-' + id + '-' + sourceLevel + '-' + conditionLevel ).show();
2456
- jQuery( '#condition-and-value-' + id + '-' + sourceLevel + '-' + conditionLevel ).show();
2457
- } else {
2458
-
2459
- jQuery( '#condition-and-value-' + id + '-' + sourceLevel + '-' + conditionLevel ).hide();
2460
- }
2461
-
2462
- var conditionStored = tvc_storeCondition( id, sourceLevel, conditionLevel );
2463
-
2464
- if ( conditionStored && ! jQuery( '#source-' + id + '-' + (
2465
- sourceLevel + 1
2466
- ) ).length ) {
2467
-
2468
- // add a new source row to the fieldRow
2469
- jQuery( tvc_addFeedSourceRow( id, sourceLevel + 1, _feedHolder.getSourceObject( id ) ) ).insertAfter( '#source-' + id + '-' + sourceLevel, false );
2470
- }
2471
- }
2472
-
2473
- function tvc_queryValueConditionChanged( rowId, sourceLevel, queryLevel, querySublevel ) {
2474
-
2475
- var value = jQuery( '#value-query-condition-' + rowId + '-' + sourceLevel + '-' + queryLevel + '-' + querySublevel ).val();
2476
-
2477
- if ( value === '4' || value === '5' ) {
2478
-
2479
- jQuery( '#value-options-condition-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).hide();
2480
- } else {
2481
-
2482
- jQuery( '#value-options-condition-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).show();
2483
- }
2484
-
2485
- if ( value === '14' ) {
2486
-
2487
- jQuery( '#value-options-condition-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).show();
2488
- jQuery( '#value-options-condition-and-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).show();
2489
- } else {
2490
-
2491
- jQuery( '#value-options-condition-and-value-' + rowId + '-' + sourceLevel + '-' + queryLevel ).hide();
2492
- }
2493
-
2494
- tvc_storeValueCondition( rowId, sourceLevel, queryLevel );
2495
- }
2496
-
2497
- function tvc_getOutputFieldsList( level ) {
2498
- var htmlCode = '';
2499
- var list = [];
2500
-
2501
- switch ( level ) {
2502
- case 3:
2503
- list = _undefinedRecommendedOutputs;
2504
- break;
2505
-
2506
- case 4:
2507
- list = _undefinedOptionalOutputs;
2508
- break;
2509
-
2510
- default:
2511
- break;
2512
- }
2513
-
2514
- list.sort();
2515
- for ( var i = 0; i < list.length; i ++ ) {
2516
- htmlCode += '<option value="' + list[ i ] + '">' + list[ i ] + '</option>';
2517
- }
2518
-
2519
- return htmlCode;
2520
- }
2521
-
2522
- function tvc_fixedSourcesList( selectedValue ) {
2523
-
2524
- var htmlCode = '';
2525
- var selectStatus = '';
2526
-
2527
- for ( var i = 0; i < _inputFields.length; i ++ ) {
2528
-
2529
- selectStatus = selectedValue === _inputFields[ i ].value ? ' selected' : '';
2530
-
2531
- htmlCode += '<option value = "' + _inputFields[ i ].value + '" itemprop="' + _inputFields[ i ].prop + '" ' + selectStatus + '>' + _inputFields[ i ].label + '</option>';
2532
- }
2533
-
2534
- return htmlCode;
2535
- }
2536
-
2537
- function tvc_hideFeedFormMainInputs() {
2538
-
2539
- //jQuery( '#country-list-row' ).hide();
2540
- jQuery( '#category-list-row' ).hide();
2541
- jQuery( '#aggregator-selector-row' ).hide();
2542
- jQuery( '#add-product-variations-row' ).hide();
2543
- }
2544
-
2545
- function tvc_getCombinedSeparatorList( selectedValue ) {
2546
-
2547
- // ALERT These options have to be the same as in the make_combined_result_string() array
2548
- var separatorOptions = {
2549
- '0': '-- ' + tvc_feed_settings_form_vars.no_separator + ' --',
2550
- '1': tvc_feed_settings_form_vars.space,
2551
- '2': tvc_feed_settings_form_vars.comma,
2552
- '3': tvc_feed_settings_form_vars.point,
2553
- '4': tvc_feed_settings_form_vars.semicolon,
2554
- '5': tvc_feed_settings_form_vars.colon,
2555
- '6': tvc_feed_settings_form_vars.dash,
2556
- '7': tvc_feed_settings_form_vars.slash,
2557
- '8': tvc_feed_settings_form_vars.backslash,
2558
- '9': tvc_feed_settings_form_vars.double_pipe,
2559
- '10': tvc_feed_settings_form_vars.underscore,
2560
- };
2561
-
2562
- var htmlCode = '';
2563
-
2564
- for ( var field in separatorOptions ) {
2565
-
2566
- if ( field !== selectedValue ) {
2567
-
2568
- htmlCode += '<option value="' + field + '">' + separatorOptions[ field ] + '</option>';
2569
- } else {
2570
-
2571
- htmlCode += '<option value="' + field + '" selected>' + separatorOptions[ field ] + '</option>';
2572
-
2573
- }
2574
- }
2575
-
2576
- return htmlCode;
2577
- }
2578
-
2579
- function updateFeedFormAfterInputChanged( feedId, categoryChanged ) {
2580
-
2581
- // enable the Generate and Save button
2582
- tvc_enableFeedActionButtons();
2583
- tvc_finishOrUpdateFeedPage( categoryChanged );
2584
-
2585
- // make a new feed object if it has not been already
2586
- if ( feedId === undefined || feedId < 1 ) {
2587
- tvc_constructNewFeed();
2588
- }
2589
- }
2590
-
2591
- /**
2592
- * hook the document actions
2593
- */
2594
- jQuery( document ).ready( function() {
2595
- var feedId = tvc_getUrlVariable( 'id' );
2596
- var tabId = tvc_getUrlVariable( 'tab' );
2597
-
2598
- if ( '' !== feedId && 'product-feed' === tabId ) {
2599
- tvc_showFeedSpinner();
2600
- tvc_initiateFeed();
2601
- tvc_editExistingFeed( feedId );
2602
- tvc_hideFeedSpinner()
2603
- }
2604
- } );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-form.min.js DELETED
@@ -1,1770 +0,0 @@
1
- "use strict";
2
- var _mandatoryFields = [];
3
- var _highlyRecommendedFields = [];
4
- var _recommendedFields = [];
5
- var _undefinedRecommendedOutputs = [];
6
- var _definedRecommendedOutputs = [];
7
- var _optionalFields = [];
8
- var _undefinedOptionalOutputs = [];
9
- var _definedOptionalOutputs = [];
10
- var _undefinedCustomOutputs = [];
11
- var _customFields = [];
12
- var _inputFields = [];
13
- var _feedHolder = [];
14
-
15
- function tvc_mainInputChanged(c) {
16
- var b = jQuery("#tvc-merchants-selector").val();
17
- var a = _feedHolder.feedId;
18
- tvc_reactOnChannelInputChanged(b, a, c)
19
- }
20
-
21
- function tvc_validateFileName(b) {
22
- if (!tvc_contains_special_characters(b)) {
23
- var a = JSON.parse(jQuery("#tvc-all-feed-names").text());
24
- if (-1 === jQuery.inArray(b, a)) {
25
- _feedHolder.title = b
26
- } else {
27
- alert(tvc_feed_settings_form_vars.feed_name_exists);
28
- return false
29
- }
30
- } else {
31
- alert(tvc_feed_settings_form_vars.prohibited_feed_name_characters);
32
- return false
33
- }
34
- }
35
-
36
- function tvc_freeCategoryChanged(a, b) {
37
- if (a === "default") {
38
- if (b) {
39
- if (b > 0) {
40
- _feedHolder.setCustomCategory(undefined, jQuery("#free-category-text-input").val())
41
- } else {
42
- tvc_mainInputChanged(true)
43
- }
44
- } else {
45
- tvc_mainInputChanged(true)
46
- }
47
- } else {
48
- _feedHolder.changeCustomFeedCategoryMap(b, jQuery("#feed-category-" + b + " :input").val())
49
- }
50
- }
51
-
52
- function tvc_constructNewFeed() {
53
- var h = jQuery("#days-interval");
54
- var t = jQuery("#update-schedule-hours");
55
- var f = jQuery("#update-schedule-minutes");
56
- var g = jQuery("#update-schedule-frequency");
57
- var x = jQuery("#file-name").val();
58
- var k = "1";
59
- var c = jQuery("#lvl_0 option:selected").text();
60
- var v = [];
61
- var y = jQuery("#tvc-merchants-selector").val();
62
- var d = jQuery("#variations").is(":checked") ? 1 : 0;
63
- var l = jQuery("#aggregator").is(":checked") ? 1 : 0;
64
- var o = jQuery("#tvc-countries-selector").val();
65
- var n = document.getElementById("language") === null ? "" : jQuery("#tvc-feed-language-selector").val();
66
- var w = jQuery("#google-feed-title-selector").val();
67
- var j = jQuery("#google-feed-description-selector").val();
68
- var i = h.val() !== "" ? h.val() : "1";
69
- var r = t.val() !== "" ? t.val() : "00";
70
- var q = f.val() !== "" ? f.val() : "00";
71
- var e = g.val() !== "" ? g.val() : "1";
72
- var p = [];
73
- var m = 2;
74
- var s = tvc_getChannelFeedType(y);
75
- var u = "1";
76
- var a = jQuery("#wp-plugin-url").text() + "/tvc-feeds/" + x + "." + s;
77
- var b = i + ":" + r + ":" + q + ":" + e;
78
- tvc_setScheduleSelector(i, e);
79
- _feedHolder = new Feed(-1, x, d, l, parseInt(y), c, v, a, k, o, n, w, j, b, p, m, u)
80
- }
81
-
82
- function tvc_constructNewSpecialFeed(a) {
83
- _feedHolder = a
84
- }
85
-
86
- function tvc_setSpecialFeedProperty(a, c, b) {
87
- if (_feedHolder.hasOwnProperty(a)) {
88
- if ("object" === typeof _feedHolder[a]) {
89
- _feedHolder[a].push(c)
90
- } else {
91
- _feedHolder[a] = c
92
- }
93
- } else {
94
- if ("array" === b) {
95
- _feedHolder[a] = [];
96
- _feedHolder[a].push(c)
97
- } else {
98
- _feedHolder[a] = c
99
- }
100
- }
101
- }
102
-
103
- function tvc_unsetSpecialFeedArrayProperty(b, c) {
104
- if (_feedHolder.hasOwnProperty(b) && "object" === typeof _feedHolder[b]) {
105
- var a = _feedHolder[b].indexOf(c);
106
- _feedHolder[b].splice(a, 1)
107
- }
108
- }
109
-
110
- function tvc_finishOrUpdateFeedPage(d) {
111
- var c = jQuery("#tvc-merchants-selector");
112
- var b = jQuery("#lvl_0");
113
- var a = c.val().toString();
114
- tvc_showFeedSpinner();
115
- _feedHolder.title = jQuery("#file-name").val();
116
- _feedHolder.channel = c.val();
117
- _feedHolder.includeVariations = jQuery("#variations").is(":checked") ? "1" : "0";
118
- _feedHolder.isAggregator = jQuery("#aggregator").is(":checked") ? "1" : "0";
119
- _feedHolder.feedTitle = jQuery("#google-feed-title-selector").val();
120
- _feedHolder.feedDescription = jQuery("#google-feed-description-selector").val();
121
- _feedHolder.language = document.getElementById("language") === null ? "" : jQuery("#tvc-feed-language-selector").val();
122
- tvc_getFeedAttributes(-1, a, function(e) {
123
- _feedHolder.setUpdateSchedule(jQuery("#days-interval").val(), jQuery("#update-schedule-hours").val(), jQuery("#update-schedule-minutes").val(), jQuery("#update-schedule-frequency").val());
124
- if (undefined === _feedHolder.attributes || 0 === _feedHolder.attributes.length) {
125
- tvc_addFeedAttributes(e, a, 1)
126
- }
127
- tvc_customSourceFields(_feedHolder.dataSource, function(f) {
128
- _feedHolder.country = jQuery("#tvc-countries-selector").val();
129
- _feedHolder.language = jQuery("#tvc-feed-language-selector").val();
130
- tvc_fillSourcesList(f);
131
- tvc_mainFeedFilters(_feedHolder.feedId, function(j) {
132
- var i = j !== 1 ? j : null;
133
- var h = "0" !== _feedHolder.country ? _feedHolder.country : _feedHolder.language;
134
- _feedHolder.setFeedFilter(i);
135
- _feedHolder = tvc_setOutputAttributeLevels(a, _feedHolder, h);
136
-
137
- if (d) {
138
- _feedHolder.mainCategory = b.val() ? b.val() : jQuery("#free-category-text-input").val();
139
- _feedHolder.setMainCategory("lvl_0", b.val(), a)
140
- }
141
- tvc_drawAttributeMappingSection();
142
- if (_feedHolder !== 0) {
143
- var g = _feedHolder.feedId === -1;
144
- tvc_fillFeedFields(g, d)
145
- }
146
- console.log(_feedHolder);
147
- _feedHolder.channel = a;
148
- jQuery("#page-center-buttons").show();
149
- jQuery("#page-bottom-buttons").show();
150
- jQuery( '#page-bottom-api-buttons' ).show();
151
- tvc_hideFeedSpinner()
152
- })
153
- })
154
- })
155
- }
156
-
157
- function tvc_finishOrUpdateSpecialFeedPage(b) {
158
- _feedHolder = b;
159
- tvc_drawAttributeMappingSection();
160
- if (_feedHolder) {
161
- var a = _feedHolder.feedId === -1;
162
- tvc_fillFeedFields(a, false)
163
- }
164
- jQuery("#page-center-buttons").show();
165
- jQuery("#page-bottom-buttons").show();
166
- jQuery( '#page-bottom-api-buttons' ).show();
167
- }
168
-
169
- function tvc_initiateFeed() {
170
- var b = jQuery("#tvc-ajax-feed-data-array").text();
171
- if (!b) {
172
- return
173
- }
174
- var a = JSON.parse(b);
175
- console.log(a);
176
- if (a) {
177
- _feedHolder = new Feed(a.feed_id, a.feed_file_name, a.include_variations, a.is_aggregator, a.channel_id, a.main_category, a.category_mapping, a.url, a.source, a.target_country, a.language, a.feed_title, a.feed_description, a.schedule, [], a.status_id, "1");
178
- tvc_addFeedAttributes(a.attribute_data, a.channel_id, 1);
179
- _feedHolder.setFeedFilter(a.feed_filter);
180
- _feedHolder.source_fields = a.source_fields
181
- }
182
- }
183
-
184
- function tvc_editExistingFeed(c) {
185
- if (c !== _feedHolder.feedId) {
186
- return
187
- }
188
- var d = _feedHolder.channel;
189
- var a = _feedHolder.mainCategory;
190
- var e = a && a.indexOf(" > ") > -1 ? a.substring(0, a.indexOf(" > ")) : a;
191
- tvc_fillCategoryVariables(d, e, "0");
192
- tvc_fillSourcesList(_feedHolder.source_fields);
193
- var b = !tvc_requiresLanguageInput(d) ? _feedHolder.country : _feedHolder.language;
194
- _feedHolder = tvc_setOutputAttributeLevels(d, _feedHolder, b);
195
- tvc_drawAttributeMappingSection();
196
- if (_feedHolder !== 0) {
197
- tvc_fillFeedFields(false, false)
198
- }
199
- if (_feedHolder.categoryMapping) {
200
- tvc_setCategoryMap(_feedHolder.categoryMapping)
201
- }
202
- tvc_enableFeedActionButtons();
203
- jQuery("#tvc-countries-selector").prop("disabled", false);
204
- tvc_fillDefaultCategorySelectors();
205
- tvc_setIdentifierExistsDependancies();
206
- jQuery("div").filter("#page-center-buttons").show();
207
- jQuery("#page-bottom-buttons").show();
208
- jQuery( '#page-bottom-api-buttons' ).show();
209
- }
210
-
211
- function tvc_fillSourcesList(a) {
212
- _inputFields = tvc_woocommerceSourceOptions();
213
- tvc_addCustomFieldsToInputFields(_inputFields, a);
214
- _inputFields.sort(function(d, c) {
215
- return ("" + d.label).toUpperCase() < ("" + c.label).toUpperCase() ? -1 : 1
216
- })
217
- }
218
-
219
- function tvc_saveUpdateSchedule() {
220
- var d = jQuery("#days-interval").val();
221
- var a = jQuery("#update-schedule-hours").val();
222
- var b = jQuery("#update-schedule-minutes").val();
223
- var c = jQuery("#update-schedule-frequency").val();
224
- if (d !== "1") {
225
- c = "1"
226
- }
227
- if (c === 1) {
228
- d = "1"
229
- }
230
- tvc_setScheduleSelector(d, c);
231
- _feedHolder.setUpdateSchedule(d, a, b, c)
232
- }
233
-
234
- function tvc_setScheduleSelector(e, d) {
235
- var c = jQuery("#tvc-update-frequency-wrapper");
236
- var b = jQuery("#tvc-update-day-wrapper");
237
- var a = jQuery("#tvc-update-every-day-wrapper");
238
- if (e === "1") {
239
- c.show()
240
- } else {
241
- c.hide()
242
- }
243
- if (d > 1) {
244
- b.hide();
245
- a.show()
246
- } else {
247
- b.show();
248
- a.hide()
249
- }
250
- }
251
-
252
- function tvc_addCustomFieldsToInputFields(b, d) {
253
- if (d !== "0") {
254
- for (var a = 0; a < d.length; a++) {
255
- var c = {
256
- value: d[a].attribute_name,
257
- label: d[a].attribute_label,
258
- prop: "custom"
259
- };
260
- b.push(c)
261
- }
262
- }
263
- }
264
-
265
- function tvc_fillDefaultCategorySelectors() {
266
- var b = _feedHolder.mainCategory;
267
- var a = _feedHolder.channel;
268
- var c = tvc_channelCountryCode(a);
269
- tvc_getCategoryListsFromString(a, b, c, function(f) {
270
- var d = JSON.parse(f);
271
- if (d && d.length > 0 && b !== undefined) {
272
- var e = b.split(" > ");
273
- for (var h = 0; h < d.length; h++) {
274
- jQuery("#lvl_" + h).append(tvc_categorySelectCntrl(d[h]));
275
- var g = document.getElementById("lvl_" + h);
276
- g.value = e[h]
277
- }
278
- } else {
279
- jQuery("#lvl_0").prop("disabled", false)
280
- }
281
- })
282
- }
283
-
284
- function tvc_setGoogleFeedTitle(a) {
285
- _feedHolder.feedTitle = a
286
- }
287
-
288
- function tvc_setGoogleFeedDescription(a) {
289
- _feedHolder.feedDescription = a
290
- }
291
-
292
- function tvc_setGoogleFeedLanguage(a) {
293
- _feedHolder.language = a
294
- }
295
-
296
- function tvc_setCategoryMap(a, f) {
297
- if (undefined === f) {
298
- f = "mapping"
299
- }
300
- var d = JSON.parse(a);
301
- for (var b = 0; b < d.length; b++) {
302
- var c = d[b].shopCategoryId;
303
- var e = "";
304
- if ("mapping" === f) {
305
- switch (d[b].feedCategories) {
306
- case "wp_mainCategory":
307
- e = tvc_mapToDefaultCategoryElement(c, "default");
308
- break;
309
- case "wp_ownCategory":
310
- e = tvc_mapToDefaultCategoryElement(c, "shopCategory");
311
- break;
312
- default:
313
- e = tvc_mapToCategoryElement(c, d[b].feedCategories);
314
- break
315
- }
316
- }
317
- jQuery("#feed-selector-" + c).prop("checked", true);
318
- jQuery("#feed-category-" + c).html(e)
319
- }
320
- }
321
-
322
- function tvc_generateAndSaveFeed() {
323
- tvc_showFeedSpinner();
324
- _feedHolder.mainCategory = !tvc_channelUsesOwnCategories(_feedHolder.channel) ? _feedHolder.mainCategory : tvc_feed_settings_form_vars.no_category_required;
325
- tvc_saveFeedToDb(_feedHolder, function(b) {
326
- var a = _feedHolder.feedId === -1;
327
- tvc_handleSaveFeedToDbActionResult(b, a);
328
- tvc_updateFeedFile(_feedHolder.feedId, function(c) {
329
- tvc_handleUpdateFeedFileActionResult(c);
330
- if (!a) {
331
- tvc_hideFeedSpinner();
332
- jQuery("button.feedModel").trigger("click");
333
- jQuery("#attribute_mapping_button").css("display","none");
334
- jQuery(".feed-push-button").css("display","block");
335
- }
336
- })
337
- })
338
- }
339
-
340
- function tvc_handleSaveFeedToDbActionResult(b, a) {
341
- if (0 === b || "0" === b) {
342
- tvc_handleSaveFeedToDbFailedAction()
343
- } else {
344
- _feedHolder.feedId = b;
345
- if (a) {
346
- var c = window.location.href;
347
- window.location.href = c + "&id=" + _feedHolder.feedId + "&show=1"
348
- }
349
- }
350
- }
351
-
352
- function tvc_handleSaveFeedToDbFailedAction() {
353
- console.log("Saving the data to the data base has failed!");
354
- tvc_show_error_message(tvc_feed_settings_form_vars.save_data_failed);
355
- tvc_hideFeedSpinner()
356
- }
357
-
358
- function tvc_handleUpdateFeedFileActionResult(a) {
359
- var b = jQuery("#error-message");
360
- tvc_disableViewFeedButtons();
361
- console.log(a);
362
- switch (a) {
363
- case "started_processing":
364
- b.hide();
365
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_started);
366
- tvc_alert_update_finished(_feedHolder.feedId, 10000);
367
- break;
368
- case "pushed_to_queue":
369
- b.hide();
370
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_queued);
371
- tvc_alert_update_finished(_feedHolder.feedId, 10000);
372
- break;
373
- case "writing_error":
374
- tvc_show_error_message(tvc_feed_settings_form_vars.feed_writing_error);
375
- tvc_hideFeedSpinner();
376
- break;
377
- case "foreground_processing_complete":
378
- tvc_alert_update_finished(_feedHolder.feedId, 0);
379
- tvc_hideFeedSpinner();
380
- break;
381
- case "activation_error":
382
- tvc_show_error_message(tvc_feed_settings_form_vars.feed_initiation_error);
383
- tvc_hideFeedSpinner();
384
- break;
385
- case "1":
386
- tvc_show_error_message(tvc_feed_settings_form_vars.feed_general_error.replace("%xmlResult%", a));
387
- tvc_hideFeedSpinner();
388
- break;
389
- default:
390
- tvc_hideFeedSpinner()
391
- }
392
- }
393
-
394
- function setCookie(key, value, expiry) {
395
- var expires = new Date();
396
- expires.setTime(expires.getTime() + (expiry * 1 * 60 * 60 * 1000));
397
- document.cookie = key + '=' + value + ';expires=' + expires.toUTCString();
398
- }
399
-
400
- function tvc_alert_update_finished(b, c) {
401
- if (undefined === c || 0 === c) {
402
- c = 10000
403
- }
404
- var e = window.setInterval(d, c, b);
405
- var a = jQuery("#success-message");
406
- if (!b) {
407
- return false
408
- }
409
-
410
- function d(f) {
411
- tvc_getCurrentFeedStatus(f, function(g) {
412
- var i = JSON.parse(g);
413
- var feed_id = i.product_feed_id;
414
- var url = i.url;
415
- var feed_name = i.title;
416
-
417
- // Set a cookie
418
- setCookie('feed_id', feed_id,'1');
419
- setCookie('feed_url', url,'1');
420
- setCookie('feed_name', feed_name,'1');
421
-
422
- console.log("Feed status changed to status " + i.status_id);
423
- tvc_enableFeedActionButtons();
424
- switch (i.status_id) {
425
- case "0":
426
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_status_unknown.replace("%feedname%", i.title));
427
- window.clearInterval(e);
428
- break;
429
- case "1":
430
- case "2":
431
- var h = document.getElementById("tvc-feed-url");
432
- h.textContent = i.url;
433
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_status_ready.replace("%feedname%", i.title).replace("%prodnr%", i.products));
434
- window.clearInterval(e);
435
- tvc_hideFeedSpinner();
436
- break;
437
- case "3":
438
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_status_still_processing);
439
- break;
440
- case "4":
441
- tvc_show_success_message(tvc_feed_settings_form_vars.feed_status_added_to_queue);
442
- break;
443
- case "5":
444
- a.hide();
445
- tvc_show_error_message(tvc_feed_settings_form_vars.feed_status_error.replace("%feedname%", i.title));
446
- window.clearInterval(e);
447
- tvc_hideFeedSpinner();
448
- break;
449
- case "6":
450
- a.hide();
451
- tvc_show_error_message(tvc_feed_settings_form_vars.feed_status_failed.replace("%feedname%", i.title));
452
- window.clearInterval(e);
453
- tvc_hideFeedSpinner();
454
- break
455
- }
456
- })
457
- }
458
- }
459
-
460
- function tvc_saveFeed() {
461
- tvc_showFeedSpinner();
462
- var a = _feedHolder.feedId === -1;
463
- _feedHolder.mainCategory = !tvc_channelUsesOwnCategories(_feedHolder.channel) ? _feedHolder.mainCategory : tvc_feed_settings_form_vars.no_category_required;
464
- if (a) {
465
- _feedHolder.url = tvc_feed_settings_form_vars.no_feed_generated
466
- }
467
- tvc_saveFeedToDb(_feedHolder, function(b) {
468
- if (b === 0) {
469
- console.log("Saving the data to the data base has failed!");
470
- tvc_show_error_message(tvc_feed_settings_form_vars.save_data_failed)
471
- } else {
472
- _feedHolder.feedId = b;
473
- if (a) {
474
- var c = window.location.href;
475
- window.location.href = c + "&id=" + _feedHolder.feedId
476
- }
477
- }
478
- })
479
- }
480
-
481
- function tvc_nextCategory(b) {
482
- var c = tvc_incrementLast(b);
483
- var f = c.match(/(\d+)$/)[0];
484
- var e = jQuery("#" + b).val();
485
- var d = _feedHolder.channel ? _feedHolder.channel.toString() : jQuery("#tvc-merchants-selector").val();
486
- var g = tvc_channelCountryCode(d);
487
- var a = jQuery("#" + c);
488
- if (f > 1) {
489
- tvc_showFeedSpinner()
490
- }
491
- tvc_hideSubs(b);
492
- tvc_fillCategoryVariables(d, e, b);
493
- tvc_getNextCategories(d, f, e, g, function(h) {
494
- var i = JSON.parse(h);
495
- if (i.length > 0) {
496
- a.append(tvc_categorySelectCntrl(i));
497
- a.show()
498
- }
499
- if (b.indexOf("catmap") > -1) {
500
- tvc_setChildCategories(b, e)
501
- } else {
502
- _feedHolder.setMainCategory(b, e, d);
503
- if (_feedHolder.attributes.length > 0 && _feedHolder.attributes[3]["value"] !== undefined && _feedHolder.attributes[3]["value"] !== "") {
504
- jQuery("#category-source-string").html(JSON.parse(_feedHolder.attributes[3]["value"]).t)
505
- } else {
506
- jQuery("#category-source-string").html(_feedHolder.mainCategory)
507
- }
508
- }
509
- if (f > 1) {
510
- tvc_hideFeedSpinner()
511
- }
512
- })
513
- }
514
-
515
- function tvc_setChildCategories(c, f) {
516
- var e = c.match(/(\d+)$/)[0];
517
- var g = c.replace("_" + e, "");
518
- var d = g.match(/(\d+)$/)[0];
519
- var b = tvc_getCategoryChildren(d);
520
- for (var a = 0; a < b.length; a++) {
521
- tvc_setChildrenToParentCategory(d, b[a], e, f)
522
- }
523
- _feedHolder.mapCategory(c, f)
524
- }
525
-
526
- function tvc_getCategoryChildren(a) {
527
- var b = jQuery("#feed-selector-" + a);
528
- return b.attr("data-children") ? JSON.parse(b.attr("data-children")) : []
529
- }
530
-
531
- function tvc_variation_selection_changed() {
532
- alert(tvc_feed_settings_form_vars.variation_only_for_premium);
533
- _feedHolder.changeIncludeVariations(false);
534
- jQuery("#variations").prop("checked", false)
535
- }
536
-
537
- function tvc_aggregatorChanged() {
538
- if (jQuery("#aggregator").is(":checked")) {
539
- _feedHolder.changeAggregator(true);
540
- _feedHolder.attributes[8]["fieldLevel"] = "1"
541
- } else {
542
- _feedHolder.changeAggregator(false);
543
- _feedHolder.attributes[8]["fieldLevel"] = "0";
544
- _feedHolder.deactivateAttribute("8")
545
- }
546
- }
547
-
548
- function tvc_setChildrenToParentCategory(l, f, a, d) {
549
- var m = tvc_getCategorySelectorValue(f);
550
- var c = "";
551
- var o = tvc_addNewItemToCategoryString(a, m, d, " > ");
552
- var p = "catmap-" + f + "_" + a;
553
- var h = jQuery("#category-text-span-" + f);
554
- for (var k = 0; k < a; k++) {
555
- c += jQuery("#catmap-" + l + "_" + k).val() + " > "
556
- }
557
- var n = c.substring(0, c.length - 3);
558
- if (m === n || m === tvc_feed_settings_form_vars.map_to_default_category) {
559
- if (h.length === 0) {
560
- tvc_mapToDefaultCategoryElement(f, o)
561
- }
562
- h.text(o);
563
- var e = jQuery("#feed-selector-" + f);
564
- var b = e.attr("data-children") ? JSON.parse(e.attr("data-children")) : [];
565
- for (var g = 0; g < b.length; g++) {
566
- tvc_setChildrenToParentCategory(f, b[g], a, d)
567
- }
568
- _feedHolder.mapCategory(p, d)
569
- } else {
570
- if (h.length === 0) {
571
- jQuery("#feed-category-" + f).html(tvc_mapToDefaultCategoryElement(f, m));
572
- jQuery("#category-selector-catmap-" + f).hide()
573
- }
574
- }
575
- }
576
-
577
- function tvc_getCategorySelectorValue(c) {
578
- var f = jQuery("#category-text-span-" + c).text();
579
- if (f === "") {
580
- var d = "";
581
- for (var b = 0; b < 7; b++) {
582
- var e = jQuery("#catmap-" + c + "_" + b);
583
- var a = e.val();
584
- if (a !== null && a !== "0") {
585
- d += e.val() + " > "
586
- }
587
- }
588
- f = d.substring(0, d.length - 3)
589
- }
590
- return f
591
- }
592
-
593
- function tvc_fillFeedFields(f, c) {
594
- var g = document.getElementById("tvc-feed-language-selector");
595
- var j = jQuery("#tvc-merchants-selector");
596
- if (_feedHolder.mainCategory && f === false) {
597
- if (!c) {
598
- var h = _feedHolder.mainCategory + ' (<a class="edit-categories tvc-btn tvc-btn-small" href="javascript:void(0)" id="tvc-edit-categories" onclick="tvc_editCategories()">' + tvc_feed_settings_form_vars.edit + "</a>)";
599
- jQuery("#lvl_0").hide();
600
- jQuery("#selected-categories").html(h);
601
- jQuery("#selected-merchant").html(jQuery("#tvc-merchants-selector option[value='" + _feedHolder.channel + "']").text());
602
- j.hide()
603
- }
604
- } else {
605
- jQuery("#lvl_0").css("display", "initial")
606
- }
607
- var e = _feedHolder.updateSchedule ? _feedHolder.updateSchedule.split(":") : [];
608
- if (!f) {
609
- tvc_showChannelInputs(_feedHolder.channel, f)
610
- } else {
611
- jQuery("#tvc-category-map").show()
612
- }
613
- jQuery("#file-name").val(_feedHolder.title);
614
- j.val(_feedHolder.channel);
615
- jQuery("#variations").prop("checked", _feedHolder.includeVariations > 0);
616
- jQuery("#aggregator").prop("checked", _feedHolder.isAggregator > 0);
617
- jQuery("#tvc-countries-selector").val(_feedHolder.country);
618
- jQuery("#google-feed-title-selector").val(_feedHolder.feedTitle);
619
- jQuery("#google-feed-description-selector").val(_feedHolder.feedDescription);
620
- jQuery("#days-interval").val(e[0]);
621
- if (g !== null) {
622
- var a = _feedHolder.language !== "" ? _feedHolder.language : "0";
623
- jQuery("#tvc-feed-language-selector").val(a)
624
- }
625
- var d = document.getElementById("update-schedule-hours");
626
- var b = document.getElementById("update-schedule-minutes");
627
- var i = document.getElementById("update-schedule-frequency");
628
- d.value = e[1];
629
- b.value = e[2];
630
- i.value = e[3] ? e[3] : "1";
631
- tvc_setScheduleSelector(e[0], e[3])
632
- }
633
-
634
- function tvc_categorySelectCntrl(a) {
635
- var c = '<option value="0">' + tvc_feed_settings_form_vars.select_a_sub_category + "</option>";
636
- for (var b = 0; b < a.length; b++) {
637
- c += '<option value="' + a[b] + '">' + a[b] + "</option>"
638
- }
639
- return c
640
- }
641
-
642
- function tvc_editCategoryMapping(e) {
643
- tvc_showFeedSpinner();
644
- var c = _feedHolder.channel;
645
- var d = tvc_channelCountryCode(c);
646
- var b = jQuery("#category-text-span-" + e).text();
647
- var a = b.split(" > ");
648
- if (b && b !== tvc_feed_settings_form_vars.map_to_default_category) {
649
- tvc_getCategoryListsFromString(c, b, d, function(f) {
650
- tvc_showCategoryMappingSelectors(e, JSON.parse(f), a);
651
- tvc_hideFeedSpinner()
652
- })
653
- } else {
654
- if (!tvc_isCustomChannel(c)) {
655
- tvc_getCategoryListsFromString(c, "", d, function(f) {
656
- tvc_showCategoryMappingSelectors(e, JSON.parse(f), "");
657
- tvc_hideFeedSpinner()
658
- })
659
- } else {
660
- jQuery("#feed-category-" + e).html(tvc_freeCategoryInputCntrl("mapping", e, _feedHolder.mainCategory));
661
- jQuery("#category-selector-catmap-" + e).hide();
662
- tvc_hideFeedSpinner()
663
- }
664
- }
665
- }
666
-
667
- function tvc_showCategoryMappingSelectors(f, c, a) {
668
- for (var b = 0; b < c.length; b++) {
669
- var e = jQuery("#catmap-" + f + "_" + b);
670
- if (c[b] && c[b].length > 0) {
671
- var d = a[b] ? a[b] : "0";
672
- e.append(tvc_categorySelectCntrl(c[b]));
673
- e.val(d);
674
- e.show()
675
- }
676
- e.prop("disabled", false)
677
- }
678
- jQuery("#feed-category-" + f).html("");
679
- jQuery("#category-selector-catmap-" + f).show()
680
- }
681
-
682
- function tvc_activateOptionalFieldRow(f, a) {
683
- var c = _feedHolder.getAttributeIdByName(a);
684
- _feedHolder.activateAttribute(c);
685
- if (_feedHolder.attributes[c]["advisedSource"]) {
686
- _feedHolder.setSourceValue(c, f, _feedHolder.attributes[c]["advisedSource"])
687
- }
688
- var b = tvc_fieldRow(_feedHolder.attributes[c], true);
689
- var d = -1;
690
- if (f === 3) {
691
- d = _undefinedRecommendedOutputs.indexOf(a)
692
- } else {
693
- if (f === 4) {
694
- d = _undefinedOptionalOutputs.indexOf(a)
695
- }
696
- }
697
- if (d > -1) {
698
- if (f === 3) {
699
- _undefinedRecommendedOutputs.splice(d, 1)
700
- } else {
701
- if (f === 4) {
702
- _undefinedOptionalOutputs.splice(d, 1)
703
- }
704
- }
705
- }
706
- if (f === 3) {
707
- _definedRecommendedOutputs.push(_feedHolder.attributes[c]["fieldName"]);
708
- _definedRecommendedOutputs.sort()
709
- } else {
710
- if (f === 4) {
711
- _definedOptionalOutputs.push(_feedHolder.attributes[c]["fieldName"]);
712
- _definedOptionalOutputs.sort()
713
- }
714
- }
715
- jQuery("#output-field-cntrl-" + f + " option[value='" + a + "']").remove();
716
- jQuery("#output-field-cntrl-" + f).val("no-value");
717
- if (f === 3) {
718
- var e = jQuery("#new-recommended-row");
719
- e.append(b);
720
- e.show()
721
- } else {
722
- if (f === 4) {
723
- jQuery("#new-optional-row").append(b)
724
- }
725
- }
726
- }
727
-
728
- function tvc_activateCustomFieldRow(c) {
729
- if (!_feedHolder.checkIfCustomNameExists(c)) {
730
- var b = _feedHolder.getAttributeIdByName(c);
731
- var a = jQuery("#new-custom-row");
732
- _feedHolder.addAttribute(b, c, "", undefined, "5", true, 0, 0, 0, 0);
733
- a.append(tvc_fieldRow(_feedHolder.attributes[b], true));
734
- a.show()
735
- } else {
736
- alert(tvc_feed_settings_form_vars.duplicated_field.replace("%fieldname%", c))
737
- }
738
- jQuery("#custom-output-title-input").val("")
739
- }
740
-
741
- function tvc_setStaticValue(b, a, d) {
742
- var c = jQuery("#static-input-field-" + b + "-" + a + "-" + d).val();
743
- if (c === undefined) {
744
- c = jQuery("#static-condition-input-" + b + "-" + a + "-" + d + " option:selected").val()
745
- }
746
- _feedHolder.setStaticAttributeValue(b, a, d, c)
747
- }
748
-
749
- function tvc_setIdentifierExistsDependancies() {
750
- var a = jQuery("#static-input-field-34-0").val();
751
- if (a === undefined) {
752
- a = jQuery("#static-condition-input-34-0 option:selected").val()
753
- }
754
- switch (a) {
755
- case "true":
756
- tvc_resetOutputField(12, 1, true);
757
- tvc_resetOutputField(13, 1, true);
758
- break;
759
- case "false":
760
- tvc_resetOutputField(12, 3, false);
761
- tvc_resetOutputField(13, 3, false);
762
- break;
763
- default:
764
- break
765
- }
766
- }
767
-
768
- function tvc_resetOutputField(b, f, c) {
769
- var d = _feedHolder.attributes[b]["fieldLevel"];
770
- _feedHolder.attributes[b]["fieldLevel"] = f;
771
- _feedHolder.attributes[b]["isActive"] = c;
772
- var a = tvc_fieldRow(_feedHolder.attributes[b], false);
773
- var e = _feedHolder.attributes[b]["fieldName"];
774
- if (c) {
775
- jQuery("#required-field-table").append(a);
776
- jQuery("#output-field-cntrl-" + d + " option[value='" + e + "']").remove();
777
- jQuery("#recommended-field-table #row-" + b).remove()
778
- } else {
779
- jQuery("#row-" + b).replaceWith("");
780
- jQuery("#output-field-cntrl-" + f).append('<option value="' + e + '">' + e + "</option>")
781
- }
782
- }
783
-
784
- function tvc_fieldRow(g, a) {
785
- var h = g.rowId;
786
- var e = _feedHolder.getSourceObject(h);
787
- var c = countSources(e.mapping);
788
- if (e.advisedSource && tvc_hasExtraSourceRow(c, e.mapping)) {
789
- c++
790
- }
791
- var f = '<div class="field-table-row-wrapper tvc-attribute-' + e.fieldName + '-row" id="row-' + h + '">';
792
- for (var d = 0; d < c; d++) {
793
- f += tvc_addFeedSourceRow(h, d, e, _feedHolder.channel, a)
794
- }
795
- for (var b = 0; b < e.changeValues.length; b++) {
796
- if (e.changeValues[0]) {
797
- f += tvc_valueEditor(e.rowId, b, b, e.changeValues)
798
- }
799
- }
800
- f += tvc_endrow(h);
801
- f += "</div>";
802
- return f
803
- }
804
-
805
- function tvc_addSourceDataAndQueriesColumn(c, o) {
806
- var k = "";
807
- var d = o.rowId + "-" + c;
808
- var m = tvc_getMappingSourceValue(o.mapping, c);
809
- var f = tvc_getMappingCombinedValue(o.mapping, c);
810
- var h = tvc_getMappingStaticValue(o.mapping, c);
811
- var b = !!o.customCondition;
812
- var a = !!(m || f || h);
813
- var g = _feedHolder.channel.toString();
814
- var l = tvc_getMappingConditions(o.mapping, c);
815
- var n = tvc_countObjectItems(l);
816
- k += '<div class="source-selector colw col30w" id="source-select-' + d + '">';
817
- if (b) {
818
- k += tvc_categorySource()
819
- } else {
820
- if ((o.advisedSource && !a && o.advisedSource !== tvc_feed_settings_form_vars.fill_with_static_value) || o.advisedSource === m) {
821
- var j = jQuery.grep(_inputFields, function(i) {
822
- return i.value === o.advisedSource
823
- });
824
- j = j[0] ? j[0].label : o.advisedSource;
825
- k += tvc_advisedSourceSelector(o.rowId, c, j, g, o.mapping)
826
- } else {
827
- if ((!o.advisedSource && !m) || a || o.advisedSource === tvc_feed_settings_form_vars.fill_with_static_value) {
828
- k += tvc_inputFieldCntrl(o.rowId, c, m, h, o.advisedSource, f, tvc_isCustomChannel(g));
829
- if (h) {
830
- k += tvc_feedStaticValueSelector(o.fieldName, o.rowId, c, 0, h, g)
831
- }
832
- if (f) {
833
- k += tvc_combinedField(o.rowId, c, 0, f, false, g)
834
- }
835
- }
836
- }
837
- }
838
- k += "</div>";
839
- k += '<div class="condition-selector colw" id="condition-data-' + d + '">';
840
- if (!b && !l) {
841
- k += '<div class="condition-wrapper" id="condition-' + d + '-0">';
842
- k += tvc_forAllProductsCondition(o.rowId, c, "initial");
843
- k += "</div>"
844
- } else {
845
- if (l) {
846
- for (var e = 0; e < n; e++) {
847
- k += tvc_conditionSelectorCode(o.rowId, c, e, n, l[e])
848
- }
849
- }
850
- }
851
- k += "</div>";
852
- return k
853
- }
854
-
855
- function tvc_addCombinedField(b, a, j) {
856
- var c = true;
857
- var g = jQuery("#combined-input-field-cntrl-" + b + "-" + a + "-" + j);
858
- for (var e = 0; e < j; e++) {
859
- if (g.val() === "select") {
860
- c = false;
861
- e = j
862
- }
863
- if (g.val() === "static" && jQuery("#static-input-field-" + b + "-" + a + "-" + j).val() === "") {
864
- c = false;
865
- e = j
866
- }
867
- }
868
- if (c) {
869
- var f = _feedHolder.attributes[b]["value"] ? JSON.parse(_feedHolder.attributes[b]["value"]) : {};
870
- var h = "m" in f ? f.m : {};
871
- var d = tvc_getMappingCombinedValue(h, a);
872
- var k = j > 0;
873
- jQuery("#source-select-" + b + "-" + a).append(tvc_combinedField(b, a, j, d, k));
874
- jQuery("#add-combined-field-" + b + "-" + a).hide()
875
- } else {
876
- alert(tvc_feed_settings_form_vars.select_all_source_fields_warning)
877
- }
878
- }
879
-
880
- function tvc_combinedField(c, a, j, e, l) {
881
- jQuery("#combined-wrapper-" + c + "-" + a).remove();
882
- var f = tvc_splitCombinedFieldElements(e);
883
- var k = e ? f.length : 2;
884
- if (l) {
885
- k++
886
- }
887
- var h = '<div class="combined-wrapper" id="combined-wrapper-' + c + "-" + a + '">';
888
- for (var d = 0; d < k; d++) {
889
- var g = f[d];
890
- var b = g ? g.indexOf("#") : 0;
891
- var m;
892
- if (g) {
893
- m = g.substr(0, b) !== "static" ? [g.substr(0, b), g.substr(b + 1)] : ["0", f[d]]
894
- } else {
895
- m = []
896
- }
897
- h += tvc_combinedCntrl(c, a, d + 1, k, "delete", m, _feedHolder.channel)
898
- }
899
- h += "</div>";
900
- return h
901
- }
902
-
903
- function tvc_combinedCntrl(b, a, d, c, g, h, e) {
904
- var f = "";
905
- var i = _feedHolder.attributes[b]["fieldName"];
906
- f += '<span class="combined-field-row" id="combined-field-row-' + b + "-" + a + "-" + d + '">';
907
- if (d > 1) {
908
- f += tvc_combinedSeparatorCntrl(b, a, d, h[0])
909
- }
910
- f += tvc_combinedInputFieldCntrl(b, a, d, h[1], i, e);
911
- if (g === "initialize") {
912
- f += '<span class="combined-field-row" id="combined-field-row">';
913
- f += tvc_combinedSeparatorCntrl(b, a, d, h[0]);
914
- f += tvc_combinedInputFieldCntrl(b, a, 2, "", i, e);
915
- f += '<div class="static-value-control" id="static-value-control-' + b + "-" + a + '-2"></div>'
916
- }
917
- if (d > 2) {
918
- f += '<span id="remove-combined-field-' + b + "-" + a + "-" + d + '" style="display:initial">';
919
- f += '(<a class="remove-combined-field tvc-btn tvc-btn-small" href="javascript:void(0)"';
920
- f += ' onclick="tvc_removeCombinedField(' + b + ", " + a + ", " + d + ')">' + tvc_feed_settings_form_vars.remove + "</a>)</span>"
921
- }
922
- if (d === 2 || d >= c) {
923
- if (d === 1) {
924
- d++
925
- }
926
- if (d >= c) {
927
- f += '<span id="add-combined-field-' + b + "-" + a + "-" + d + '" style="display:initial">';
928
- f += '(<a class="add-combined-field tvc-btn tvc-btn-small" href="javascript:void(0)"';
929
- f += ' onclick="tvc_addCombinedField(' + b + ", " + a + ", " + d + ')">' + tvc_feed_settings_form_vars.add + "</a>)</span>"
930
- }
931
- }
932
- f += "</span>";
933
- return f
934
- }
935
-
936
- function tvc_ifConditionSelector(c, b, h, a, g) {
937
- var d = "";
938
- var e = tvc_isEmptyQueryObject(g) ? tvc_makeCleanQueryObject() : g;
939
- var i = tvc_feed_settings_form_vars.if_pref + " ";
940
- if (h > 1) {
941
- i = e.preCondition === "1" ? '<select id="sub-condition-' + c + "-" + b + "-" + h + '" onchange="tvc_storeCondition(' + c + ", " + b + ", " + h + ')"><option value="2">' + tvc_feed_settings_form_vars.or + '</option><option value="1" selected>' + tvc_feed_settings_form_vars.and + "</option></select>" : '<select id="sub-condition-' + c + "-" + b + "-" + h + '" onchange="tvc_storeCondition(' + c + ", " + b + ", " + h + ')"><option value="2" selected>' + tvc_feed_settings_form_vars.or + '</option><option value="1">' + tvc_feed_settings_form_vars.and + "</option></select>"
942
- }
943
- var f = "tvc_storeCondition(" + c + ", " + b + ", " + h + ")";
944
- d += '<div class="condition-wrapper" id="condition-' + c + "-" + b + "-" + h + '">';
945
- d += i;
946
- d += tvc_conditionFieldCntrl(c, b, h, -1, "input-field-cntrl", e.source, f);
947
- d += tvc_conditionQueryCntrl(c, b, h, -1, "query-condition", "tvc_queryConditionChanged", e.condition);
948
- d += '<input type="text" onchange="tvc_storeCondition(' + c + ", " + b + ", " + h + ')" name="condition-value" id="condition-value-';
949
- d += c + "-" + b + "-" + h + '" value="' + e.value + '"';
950
- if (g.condition !== "4" && g.condition !== "5") {
951
- d += ' style="display:initial">'
952
- } else {
953
- d += ' style="display:none;">'
954
- }
955
- if (g.condition !== "14") {
956
- d += '<span id="condition-and-value-' + c + "-" + b + "-" + h + '" style="display:none;"> ' + tvc_feed_settings_form_vars.and + ' <input type="text" name="condition-and-value" onchange="tvc_storeCondition(' + c + ", " + b + ", " + h + ')" id="condition-and-value-input-' + c + "-" + b + "-" + h + '"></span>'
957
- } else {
958
- d += '<span id="condition-and-value-' + c + "-" + b + "-" + h + '" style="display:initial"> ' + tvc_feed_settings_form_vars.and + ' <input type="text" name="condition-and-value" onchange="tvc_storeCondition(' + c + ", " + b + ", " + h + ')" id="condition-and-value-input-' + c + "-" + b + "-" + h + '" value="' + g.endValue + '"></span>'
959
- }
960
- d += '(<a class="remove-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)" id="tvc-remove-attribute-query-' + c + "-" + b + "-" + h;
961
- d += '" onclick="tvc_removeCondition(' + c + ", " + b + ", " + (h - 1) + ')">' + tvc_feed_settings_form_vars.remove + "</a>)";
962
- if (h >= a) {
963
- d += '<span id="add-edit-condition-' + c + "-" + b + "-" + h + '" style="display:initial"> (<a class="add-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)';
964
- d += '" id="tvc-add-attribute-query-row-' + c + "-" + b + "-" + h + '" onclick="tvc_addCondition(' + c + ", " + b + ", " + h + ", '')\">" + tvc_feed_settings_form_vars.add + "</a>)</span>"
965
- }
966
- d += "</div>";
967
- return d
968
- }
969
-
970
- function tvc_orConditionSelector(d, b) {
971
- var c = b.split("#");
972
- var e = "";
973
- var a = "";
974
- if (c[0] === "static") {
975
- e = tvc_displayCorrectStaticField(d, "1", "0", _feedHolder.channel, _feedHolder.attributes[d]["fieldName"], c[1]);
976
- b = "static"
977
- }
978
- a += "or ";
979
- a += tvc_alternativeInputFieldCntrl(d, b);
980
- a += '<span id="alternative-static-input-' + d + '">' + e + "</span>";
981
- a += " for all other products ";
982
- a += '(<a class="edit-prod-source tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-prod-source-' + d + '" onclick="addSource(' + d + ", 0, '')\">";
983
- a += tvc_feed_settings_form_vars.edit + "</a>)";
984
- return a
985
- }
986
-
987
- function tvc_ifValueQuerySelector(b, a, d, h, g) {
988
- var e = "";
989
- var f = tvc_isEmptyQueryObject(h) ? tvc_makeCleanQueryObject() : h;
990
- var c = "if ";
991
- var i = "tvc_queryValueConditionChanged(" + b + ", " + a + ", " + d + ", 0)";
992
- if (d > 1) {
993
- c = f.preCondition === "1" ? '<select id="value-options-sub-query-' + b + "-" + a + "-" + d + '" onchange="tvc_storeValueCondition(' + b + ", " + a + ", " + d + ')"><option value="2">' + tvc_feed_settings_form_vars.or + '</option><option value="1" selected>' + tvc_feed_settings_form_vars.and + "</option></select>" : '<select id="value-options-sub-query-' + b + "-" + a + "-" + d + '" onchange="tvc_storeValueCondition(' + b + ", " + a + ", " + d + ')"><option value="2" selected>' + tvc_feed_settings_form_vars.or + '</option><option value="1">' + tvc_feed_settings_form_vars.and + "</option></select>"
994
- }
995
- e += '<div class="value-options-query-selector" id="value-options-condition-' + b + "-" + a + "-" + d + '">';
996
- e += c;
997
- e += tvc_conditionFieldCntrl(b, a, d, -1, "value-options-input-field-cntrl", f.source, i);
998
- e += tvc_conditionQueryCntrl(b, a, d, 0, "value-query-condition", "tvc_queryValueConditionChanged", f.condition);
999
- if (h.condition !== "4" && h.condition !== "5") {
1000
- e += '<input type="text" onchange="tvc_storeValueCondition(' + b + ", " + a + ", " + d + ')" name="value-options-condition-value" id="value-options-condition-value-';
1001
- e += b + "-" + a + "-" + d + '" value="' + f.value + '" style="display:initial">'
1002
- }
1003
- if (h.condition !== "14") {
1004
- e += '<span id="value-options-condition-and-value-' + b + "-" + a + "-" + d + '" style="display:none;"> ' + tvc_feed_settings_form_vars.and + " ";
1005
- e += '<input id="value-options-condition-and-value-input-' + b + "-" + a + "-" + d + '" ';
1006
- e += 'type="text" onchange="tvc_storeValueCondition(' + b + ", " + a + ", " + d + ')" name="value-condition-and-value"></span>'
1007
- } else {
1008
- e += '<span id="value-options-condition-and-value-' + b + "-" + a + "-" + d + '" style="display:initial"> ' + tvc_feed_settings_form_vars.and + " ";
1009
- e += '<input id="value-options-condition-and-value-input-' + b + "-" + a + "-" + d + '" ';
1010
- e += 'type="text" onchange="tvc_storeValueCondition(' + b + ", " + a + ", " + d + ')" name="value-condition-and-value" value="' + h.endValue + '"></span>'
1011
- }
1012
- e += '(<a class="remove-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)" id="tvc-remove-attribute-query-' + b + "-" + a + "-" + d;
1013
- e += '" onclick="tvc_removeValueQuery(' + b + ", " + a + ", " + d + ')">' + tvc_feed_settings_form_vars.remove + "</a>)";
1014
- if (g) {
1015
- e += '<span id="value-options-add-edit-condition-' + b + "-" + a + "-" + d + '" style="display:initial">(<a class="add-edit-condition tvc-btn tvc-btn-small" href="javascript:void(0)';
1016
- e += '" id="tvc-add-attribute-query-row-' + b + "-" + a + "-" + d + '" onclick="tvc_addValueQuery(' + b + ", " + a + ", " + d + ", '')\">" + tvc_feed_settings_form_vars.add + "</a>)</span>"
1017
- }
1018
- e += "</div>";
1019
- return e
1020
- }
1021
-
1022
- function tvc_addOptionalFieldRow(c) {
1023
- var b = "";
1024
- var a = false;
1025
- if (c === 3) {
1026
- a = _undefinedRecommendedOutputs.length > 0
1027
- } else {
1028
- if (c === 4) {
1029
- a = _undefinedOptionalOutputs.length > 0
1030
- } else {
1031
- if (c === 5) {
1032
- a = true
1033
- }
1034
- }
1035
- }
1036
- if (a === true) {
1037
- if (c === 3) {
1038
- b += '<div class="field-table-row-wrapper" id="new-recommended-row" style="display:none;"></div>'
1039
- } else {
1040
- if (c === 4) {
1041
- b += '<div class="field-table-row-wrapper" id="new-optional-row"></div>'
1042
- } else {
1043
- if (c === 5) {
1044
- b += '<div class="field-table-row-wrapper" id="new-custom-row"></div>'
1045
- }
1046
- }
1047
- }
1048
- b += '<div class="field-table-row-top">';
1049
- b += '<div class="col2w" id="output-select-' + c;
1050
- b += c !== 5 ? '" onchange="tvc_changedOutputSelection(' + c + ')">' + tvc_outputFieldCntrl(c) : '">' + tvc_customOutputFieldCntrl();
1051
- b += "</div></div>"
1052
- }
1053
- return b
1054
- }
1055
-
1056
- function tvc_editOutput(c, b) {
1057
- var a = "";
1058
- a += tvc_inputFieldCntrl(c, b, "", "", _feedHolder.attributes[c]["advisedSource"], "", false);
1059
- a += '<div class="field-table-row-combined-selection" id="combined-selectors-' + c + '" style="display:none;"></div>';
1060
- jQuery("#source-select-" + c + "-" + b).html(a)
1061
- }
1062
-
1063
- function tvc_removeCondition(g, f, a) {
1064
- _feedHolder.removeValueConditionValue(g, f, a);
1065
- var b = _feedHolder.getAttributesQueriesObject(g, f);
1066
- var e = tvc_countObjectItems(b);
1067
- for (var d = 1; d < e + 2; d++) {
1068
- jQuery("#condition-" + g + "-" + f + "-" + d).remove()
1069
- }
1070
- if (e > 0) {
1071
- for (var c = 0; c < e; c++) {
1072
- tvc_conditionCode(g, f, c, b[c], e)
1073
- }
1074
- jQuery("#edit-conditions-" + g).append(tvc_orSelectorCode(g, ""))
1075
- } else {
1076
- var h = '<div class="condition-wrapper" id="condition-' + g + "-" + f + '-0">' + tvc_forAllProductsCondition(g, f, "initial") + "</div>";
1077
- jQuery("#condition-data-" + g + "-" + f).html(h);
1078
- jQuery("#source-" + g + "-" + (f + 1)).remove()
1079
- }
1080
- }
1081
-
1082
- function tvc_removeValueQuery(f, e, d) {
1083
- _feedHolder.removeValueQueryValue(f, e, d);
1084
- var a = _feedHolder.getValueQueryValue(f, e);
1085
- var g = jQuery("#edit-conditions-" + f);
1086
- var c = tvc_countObjectItems(a);
1087
- if (!_feedHolder.attributes[f]["value"]) {
1088
- _feedHolder.deactivateAttribute(f)
1089
- }
1090
- jQuery("#value-editor-queries-" + f + "-" + e + "-0").empty();
1091
- g.empty();
1092
- if (c > 0) {
1093
- for (var b = 0; b < c; b++) {
1094
- tvc_addValueQuery(f, e, b, a[b])
1095
- }
1096
- g.append(tvc_orSelectorCode(f, ""))
1097
- } else {
1098
- jQuery("#value-editor-input-query-span-" + f + "-" + e + "-0").show();
1099
- _feedHolder.removeEditValueValue(f, (e + 1), 0);
1100
- jQuery("#edit-value-span-" + f + "-" + (e + 1) + "-0").remove()
1101
- }
1102
- }
1103
-
1104
- function tvc_removeRow(c, e) {
1105
- var b = _definedRecommendedOutputs.indexOf(e);
1106
- var d = 3;
1107
- if (b < 0) {
1108
- b = _definedOptionalOutputs.indexOf(e);
1109
- d = 4
1110
- }
1111
- _feedHolder.deactivateAttribute(c);
1112
- jQuery("#row-" + c).remove();
1113
- if (d === 3) {
1114
- _definedRecommendedOutputs.splice(b, 1);
1115
- _undefinedRecommendedOutputs.push(e);
1116
- _undefinedRecommendedOutputs.sort()
1117
- } else {
1118
- if (d === 4) {
1119
- _definedOptionalOutputs.splice(b, 1);
1120
- _undefinedOptionalOutputs.push(e);
1121
- _undefinedOptionalOutputs.sort()
1122
- }
1123
- }
1124
- var a = jQuery("#output-field-cntrl-" + d);
1125
- a.empty();
1126
- a.html(tvc_outputFieldCntrl(d))
1127
- }
1128
-
1129
- function tvc_addCondition(d, c, a, b) {
1130
- var e = tvc_conditionCode(d, c, a, b, 0);
1131
- if (e) {
1132
- if ("0" === String(a)) {
1133
- jQuery(tvc_addFeedSourceRow(d, c + 1, _feedHolder.getSourceObject(d))).insertAfter("#source-" + d + "-" + c, false)
1134
- }
1135
- if (_feedHolder.attributes[d]["advisedSource"]) {
1136
- _feedHolder.setSourceValue(d, (c + 1), _feedHolder.attributes[d]["advisedSource"])
1137
- }
1138
- }
1139
- }
1140
-
1141
- function tvc_conditionCode(c, a, i, g, d) {
1142
- if (g || tvc_sourceIsFilled(c, a, i)) {
1143
- var j = jQuery("#query-condition-" + c + "-" + a + "-" + i).val();
1144
- var b = jQuery("#input-field-cntrl-" + c + "-" + a + "-" + i).val();
1145
- var f = jQuery("#condition-value-" + c + "-" + a + "-" + i).val();
1146
- var e = false;
1147
- if (j !== "4" && j !== "5" && j !== "14") {
1148
- if (b === "select" || f === "") {
1149
- e = true
1150
- }
1151
- } else {
1152
- if (j === 4 || j === 5) {
1153
- if (b === "select") {
1154
- e = true
1155
- }
1156
- }
1157
- }
1158
- if (e === false || i === 0) {
1159
- _feedHolder.incrNrQueries(c);
1160
- var h = tvc_queryStringToQueryObject(g);
1161
- if (i === 0) {
1162
- jQuery("#condition-" + c + "-" + a + "-0").remove()
1163
- }
1164
- jQuery("#condition-data-" + c + "-" + a).append(tvc_ifConditionSelector(c, a, i + 1, d, h));
1165
- if (i > 0) {
1166
- jQuery("#add-edit-condition-" + c + "-" + a + "-" + i).remove()
1167
- }
1168
- return true
1169
- } else {
1170
- alert(tvc_feed_settings_form_vars.fill_current_condition_warning);
1171
- return false
1172
- }
1173
- } else {
1174
- alert(tvc_feed_settings_form_vars.select_a_source_field_warning);
1175
- return false
1176
- }
1177
- }
1178
-
1179
- function tvc_addValueQuery(d, a, f, h) {
1180
- if (tvc_sourceIsFilled(d, a, f)) {
1181
- var i = jQuery("#value-query-condition-" + d + "-" + a + "-" + f + "-0").val();
1182
- var c = jQuery("#value-options-input-field-cntrl-" + d + "-" + a + "-" + f).val();
1183
- var g = jQuery("#value-options-condition-value-" + d + "-" + a + "-" + f).val();
1184
- var e = false;
1185
- if (i !== "4" && i !== "5" && i !== "14") {
1186
- if (c === "select" || g === "") {
1187
- e = true
1188
- }
1189
- } else {
1190
- if (i === 4 || i === 5) {
1191
- if (c === "select") {
1192
- e = true
1193
- }
1194
- }
1195
- }
1196
- if (e === false || a === 0) {
1197
- var b = tvc_queryStringToQueryObject(h);
1198
- jQuery("#value-options-add-edit-condition-" + d + "-" + a + "-" + f).hide();
1199
- jQuery("#value-editor-queries-" + d + "-" + a + "-0").append(tvc_ifValueQuerySelector(d, a, f + 1, b, true))
1200
- } else {
1201
- alert(tvc_feed_settings_form_vars.fill_current_condition_warning)
1202
- }
1203
- } else {
1204
- alert(tvc_feed_settings_form_vars.elect_a_source_field_warning)
1205
- }
1206
- }
1207
-
1208
- function tvc_conditionSelectorCode(f, d, e, a, c) {
1209
- var b = tvc_queryStringToQueryObject(c);
1210
- return tvc_ifConditionSelector(f, d, e + 1, a, b)
1211
- }
1212
-
1213
- function tvc_orSelectorRowCode(c, b, d) {
1214
- var a = '<div class="feed-source-row" id="source-' + c + "-" + b + '">';
1215
- a += '<div class="add-to-feed-column colw col20w">&nbsp;</div>';
1216
- a += '<div class="source-data-column colw col80w' + d + '" id="source-data-' + c + "-" + b + '">';
1217
- a += '<div class="source-selector colw col30w" id="source-select-' + c + "-" + b + '"></div>';
1218
- a += tvc_orSelectorCode(c, "");
1219
- a += "<div></div>";
1220
- a += tvc_endrow(c);
1221
- a += "</div></div>";
1222
- return a
1223
- }
1224
-
1225
- function tvc_orSelectorCode(b, a) {
1226
- let alternative = "";
1227
- if (a) {
1228
- for (let altKey in a) {
1229
- alternative = a[altKey]
1230
- }
1231
- }
1232
- return '<div class="or-selector" id="or-selector-' + b + '">' + tvc_orConditionSelector(b, alternative) + "</div>"
1233
- }
1234
-
1235
- function tvc_showEditValueQuery(e, d, b, c) {
1236
- var a = {};
1237
- jQuery("#value-editor-queries-" + e + "-" + d + "-" + b).html(tvc_ifValueQuerySelector(e, d, b + 1, a, c));
1238
- jQuery("#value-editor-input-query-span-" + e + "-" + d + "-0").hide();
1239
- if (b === 0 && c) {
1240
- tvc_addRowValueEditor(e, d + 1, 0, "")
1241
- }
1242
- }
1243
-
1244
- function tvc_changedOutput(e, a, l) {
1245
- var g = jQuery("#input-field-cntrl-" + e + "-" + a).val();
1246
- var f = 0;
1247
- var b = jQuery("#source-select-" + e + "-" + a);
1248
- var k = jQuery("#combined-wrapper-" + e + "-" + a);
1249
- var d = jQuery("#static-input-field-" + e + "-" + a + "-" + f);
1250
- var c = jQuery("#static-condition-input-" + e + "-" + a + "-" + f);
1251
- switch (g) {
1252
- case "advised":
1253
- if (e !== 3) {
1254
- var i = "";
1255
- if (l !== "Use the settings in the Merchant Center") {
1256
- var j = tvc_sourceOptionsConverter(l);
1257
- i = '<div class="advised-source">' + j + tvc_editSourceSelector(e, a) + "</div>"
1258
- } else {
1259
- i = '<div class="advised-source">Use the settings in the Merchant Center ' + tvc_editSourceSelector(e, a) + "</div>"
1260
- }
1261
- b.html(i);
1262
- _feedHolder.clearSourceValue(e, a);
1263
- _feedHolder.deactivateAttribute(e)
1264
- } else {
1265
- i = '<span id="category-source-string">' + _feedHolder.mainCategory + "</span>" + tvc_editSourceSelector(e, a);
1266
- _feedHolder.setCategoryValue(e, _feedHolder.mainCategory);
1267
- b.html(i)
1268
- }
1269
- break;
1270
- case "static":
1271
- b.append(tvc_displayCorrectStaticField(e, a, "0", _feedHolder.channel, _feedHolder.attributes[e]["fieldName"], ""));
1272
- k.remove();
1273
- var h = d.val() ? d.val() : jQuery("#static-condition-input-" + e + "-" + a + "-" + f + " option:selected").val();
1274
- _feedHolder.setStaticAttributeValue(e, a, f, h);
1275
- if (h || a > 0) {
1276
- _feedHolder.activateAttribute(e)
1277
- } else {
1278
- _feedHolder.deactivateAttribute(e)
1279
- }
1280
- break;
1281
- case "select":
1282
- _feedHolder.clearSourceValue(e, a);
1283
- if (a === "0") {
1284
- _feedHolder.deactivateAttribute(e)
1285
- }
1286
- d.remove();
1287
- c.remove();
1288
- k.remove();
1289
- tvc_clearStaticField(e);
1290
- break;
1291
- case "combined":
1292
- _feedHolder.setSourceValue(e, a, g);
1293
- if (a === "0") {
1294
- _feedHolder.deactivateAttribute(e)
1295
- }
1296
- d.remove();
1297
- c.remove();
1298
- tvc_addCombinedField(e, a, 0);
1299
- break;
1300
- case "category_mapping":
1301
- _feedHolder.setCustomCategory(e, _feedHolder.mainCategory);
1302
- d.remove();
1303
- c.remove();
1304
- k.remove();
1305
- jQuery("#condition-" + e + "-" + a + "-0").remove();
1306
- jQuery("#value-editor-input-query-add-span-" + e + "-" + a + "-0").hide();
1307
- b.html(tvc_categorySource());
1308
- break;
1309
- default:
1310
- jQuery("#static-input-" + e).html("");
1311
- if (g === l && a === "0" && jQuery("#input-field-cntrl-" + e + "-" + a + "-0").val() === "select") {
1312
- _feedHolder.clearSourceValue(e, a)
1313
- } else {
1314
- _feedHolder.setSourceValue(e, a, g)
1315
- }
1316
- _feedHolder.activateAttribute(e);
1317
- _feedHolder.attributes[e]["isActive"] = true;
1318
- d.remove();
1319
- c.remove();
1320
- k.remove();
1321
- break
1322
- }
1323
- }
1324
-
1325
- function tvc_changedAlternativeSource(d) {
1326
- var c = "1";
1327
- var a = jQuery("#alternative-input-field-cntrl-" + d).val();
1328
- if (a === "static") {
1329
- var b = tvc_displayCorrectStaticField(d, c, "0", _feedHolder.channel, _feedHolder.attributes[d]["fieldName"], "");
1330
- jQuery("#alternative-static-input-" + d).html(b)
1331
- } else {
1332
- jQuery("#alternative-static-input-" + d).empty();
1333
- if (a !== "select" && a !== "empty") {
1334
- _feedHolder.setAlternativeSourceValue(d, c, a)
1335
- } else {
1336
- _feedHolder.removeAlternativeSourceValue(d, c)
1337
- }
1338
- }
1339
- }
1340
-
1341
- function tvc_changedCombinationSeparator(b, a, c) {
1342
- tvc_changedCombinedOutput(b, a, c)
1343
- }
1344
-
1345
- function tvc_changedCombinedOutput(f, e, g) {
1346
- var c = jQuery("#combined-input-field-cntrl-" + f + "-" + e + "-" + g).val();
1347
- var a = jQuery("#static-value-control-" + f + "-" + e + "-" + g);
1348
- switch (c) {
1349
- case "static":
1350
- if (!jQuery("#static-input-field-" + f + "-" + e + "-" + g).val()) {
1351
- var d = tvc_displayCorrectStaticField(f, e, g, _feedHolder.channel, _feedHolder.attributes[f]["fieldName"], "");
1352
- a.html(d)
1353
- }
1354
- break;
1355
- default:
1356
- a.empty();
1357
- break
1358
- }
1359
- var b = getCombinedValue(f, e);
1360
- if (b) {
1361
- _feedHolder.setCombinedOutputValue(f, e, b);
1362
- _feedHolder.activateAttribute(f)
1363
- } else {
1364
- _feedHolder.removeCombinedOutputValue(f, e, g);
1365
- if (e === "0") {
1366
- _feedHolder.deactivateAttribute(f)
1367
- }
1368
- }
1369
- }
1370
-
1371
- function tvc_removeCombinedField(f, d, c) {
1372
- _feedHolder.removeCombinedOutputValue(f, d, c);
1373
- var b = JSON.parse(_feedHolder.attributes[f]["value"]);
1374
- var e = "m" in b ? b.m : {};
1375
- var a = tvc_getMappingCombinedValue(e, d);
1376
- jQuery("#source-select-" + f + "-" + d).append(tvc_combinedField(f, d, c, a, false))
1377
- }
1378
-
1379
- function tvc_clearStaticField(a) {
1380
- jQuery("#static-input-" + a).html("")
1381
- }
1382
-
1383
- function tvc_storeValueCondition(d, k, f) {
1384
- var a = jQuery("#value-options-input-field-cntrl-" + d + "-" + k + "-" + f).val();
1385
- if (a !== "select") {
1386
- var i;
1387
- var j = f > 1 ? jQuery("#value-options-sub-query-" + d + "-" + k + "-" + f + " option:selected").val() : "0";
1388
- var c = jQuery("#value-query-condition-" + d + "-" + k + "-" + f + "-0 option:selected").val();
1389
- var h = c !== "4" && c !== "5" ? jQuery("#value-options-condition-value-" + d + "-" + k + "-" + f).val() : "";
1390
- var e = c === "14" ? jQuery("#value-options-condition-and-value-input-" + d + "-" + k + "-" + f).val() : "";
1391
- if (c === "4" || c === "5") {
1392
- i = true
1393
- } else {
1394
- if (c === "14") {
1395
- i = !!(h && e)
1396
- } else {
1397
- i = !!h
1398
- }
1399
- }
1400
- if (i === true) {
1401
- var b = j !== "" ? j + "#" : "0#";
1402
- var g = b + a + "#" + c;
1403
- if (h) {
1404
- g += "#" + h
1405
- }
1406
- if (e) {
1407
- g += "#0#" + e
1408
- }
1409
- _feedHolder.addValueQueryValue(d, k, f, g)
1410
- }
1411
- } else {
1412
- console.log("Query " + d + "-" + k + "-" + f + " removed!");
1413
- _feedHolder.removeValueQueryValue(d, k, f)
1414
- }
1415
- }
1416
-
1417
- function tvc_storeCondition(e, c, k) {
1418
- var a = jQuery("#input-field-cntrl-" + e + "-" + c + "-" + k).val();
1419
- var l = false;
1420
- if (tvc_validSourceSelected(e, c)) {
1421
- if (a !== "select") {
1422
- var i;
1423
- var j = k > 1 ? jQuery("#sub-condition-" + e + "-" + c + "-" + k + " option:selected").val() : "0";
1424
- var d = jQuery("#query-condition-" + e + "-" + c + "-" + k + " option:selected").val();
1425
- var h = d !== "4" && d !== "5" ? jQuery("#condition-value-" + e + "-" + c + "-" + k).val() : "";
1426
- var f = d === "14" ? jQuery("#condition-and-value-input-" + e + "-" + c + "-" + k).val() : "";
1427
- if (d === "4" || d === "5") {
1428
- i = true
1429
- } else {
1430
- if (d === "14") {
1431
- i = !!(h && f)
1432
- } else {
1433
- i = !!(h)
1434
- }
1435
- }
1436
- if (i === true) {
1437
- var b = j !== "" ? j + "#" : "0#";
1438
- var g = b + a + "#" + d;
1439
- if (h) {
1440
- g += "#" + h
1441
- }
1442
- if (f) {
1443
- g += "#0#" + f
1444
- }
1445
- _feedHolder.addConditionValue(e, g, c, k);
1446
- l = true
1447
- }
1448
- } else {
1449
- _feedHolder.removeValueConditionValue(e, c, k)
1450
- }
1451
- } else {
1452
- jQuery("#input-field-cntrl-" + e + "-" + c + "-1").prop("selectedIndex", 0);
1453
- jQuery("#condition-value-" + e + "-" + c + "-1").val("");
1454
- alert(tvc_feed_settings_form_vars.select_a_valid_source_warning)
1455
- }
1456
- return l
1457
- }
1458
-
1459
- function tvc_validSourceSelected(d, c) {
1460
- var a = jQuery("#input-field-cntrl-" + d + "-" + c).val();
1461
- switch (a) {
1462
- case "select":
1463
- return false;
1464
- case "static":
1465
- var e = jQuery("#static-condition-input-" + d + "-" + c + "-0");
1466
- var b = jQuery("#static-input-field-" + d + "-" + c + "-0");
1467
- if (e.val()) {
1468
- return !!e.val()
1469
- } else {
1470
- if (b.val()) {
1471
- return !!b.val()
1472
- } else {
1473
- return false
1474
- }
1475
- }
1476
- case "combined":
1477
- return jQuery("#combined-input-field-cntrl-" + d + "-" + c + "-2").val() !== "select";
1478
- default:
1479
- return true
1480
- }
1481
- }
1482
-
1483
- function tvc_valueInputOptionsChanged(d, b, g) {
1484
- var f = jQuery("#value-options-" + d + "-" + b + "-" + g + " option:selected").text();
1485
- var h = jQuery("#value-options-input-" + d + "-" + b + "-" + g).val();
1486
- var i = "";
1487
- var e = b > 0 ? "and" : "change";
1488
- if (f !== "replace" && f !== "recalculate") {
1489
- i = e + "#" + f + "#";
1490
- i += f === "change nothing" ? "blank" : h;
1491
- _feedHolder.addChangeValue(d, b, g, i)
1492
- } else {
1493
- if (f === "replace") {
1494
- var a = jQuery("#value-options-input-with-" + d + "-" + b + "-" + g).val();
1495
- if (h && a) {
1496
- i = e + "#" + f + "#" + h + "#" + a;
1497
- _feedHolder.addChangeValue(d, b, g, i)
1498
- }
1499
- } else {
1500
- if (f === "recalculate") {
1501
- var c = jQuery("#value-options-recalculate-options-" + d + "-" + b + "-" + g + " option:selected").text();
1502
- if (h) {
1503
- i = e + "#" + f + "#" + c + "#" + h;
1504
- _feedHolder.addChangeValue(d, b, g, i)
1505
- }
1506
- }
1507
- }
1508
- }
1509
- }
1510
-
1511
- function tvc_removeValueEditor(e, d, f) {
1512
- _feedHolder.removeEditValueValue(e, d, f);
1513
- var a = _feedHolder.getAttributesValueObject(e);
1514
- var c = tvc_countObjectItems(a);
1515
- if (!_feedHolder.attributes[e]["value"]) {
1516
- _feedHolder.deactivateAttribute(e)
1517
- }
1518
- jQuery("#edit-value-span-" + e + "-" + d + "-0").remove();
1519
- if (c > 0) {
1520
- for (var b = 1; b < c; b++) {
1521
- tvc_addRowValueEditor(e, d, b, a[b])
1522
- }
1523
- } else {
1524
- jQuery("#value-editor-" + e + "-" + d + "-" + f).remove();
1525
- jQuery("#source-" + e + "-" + d).append(tvc_editValueSpan(e, d, f, "initial"))
1526
- }
1527
- }
1528
-
1529
- function tvc_drawAttributeMappingSection() {
1530
- var b = _feedHolder.channel.toString();
1531
- tvc_resetFields();
1532
- for (var a = 0; a < _feedHolder.attributes.length; a++) {
1533
- switch (_feedHolder.attributes[a]["fieldLevel"]) {
1534
- case "1":
1535
- _mandatoryFields += tvc_fieldRow(_feedHolder.attributes[a], false);
1536
- break;
1537
- case "2":
1538
- _highlyRecommendedFields += tvc_fieldRow(_feedHolder.attributes[a], false);
1539
- break;
1540
- case "3":
1541
- if (_feedHolder.attributes[a]["isActive"]) {
1542
- _recommendedFields += tvc_fieldRow(_feedHolder.attributes[a], true);
1543
- _definedRecommendedOutputs.push(_feedHolder.attributes[a]["fieldName"])
1544
- } else {
1545
- _undefinedRecommendedOutputs.push(_feedHolder.attributes[a]["fieldName"])
1546
- }
1547
- break;
1548
- case "4":
1549
- if (_feedHolder.attributes[a]["isActive"]) {
1550
- _optionalFields += tvc_fieldRow(_feedHolder.attributes[a], true);
1551
- _definedOptionalOutputs.push(_feedHolder.attributes[a]["fieldName"])
1552
- } else {
1553
- _undefinedOptionalOutputs.push(_feedHolder.attributes[a]["fieldName"])
1554
- }
1555
- break;
1556
- case "5":
1557
- if (_feedHolder.attributes[a]["isActive"]) {
1558
- _customFields += tvc_fieldRow(_feedHolder.attributes[a], true)
1559
- } else {
1560
- _undefinedCustomOutputs.push(_feedHolder.attributes[a]["fieldName"])
1561
- }
1562
- break;
1563
- default:
1564
- break
1565
- }
1566
- }
1567
- _definedRecommendedOutputs.sort();
1568
- _undefinedRecommendedOutputs.sort();
1569
- _recommendedFields += tvc_addOptionalFieldRow(3);
1570
- _optionalFields += tvc_addOptionalFieldRow(4);
1571
- if (tvc_isCustomChannel(b)) {
1572
- _customFields += tvc_addOptionalFieldRow(5)
1573
- }
1574
- if (_mandatoryFields.length > 0) {
1575
- jQuery("#required-field-table").html(_mandatoryFields);
1576
- jQuery("#required-fields").show()
1577
- } else {
1578
- jQuery("#required-fields").hide()
1579
- }
1580
- if (_highlyRecommendedFields.length > 0) {
1581
- jQuery("#highly-recommended-field-table").html(_highlyRecommendedFields);
1582
- jQuery("#highly-recommended-fields").show()
1583
- } else {
1584
- jQuery("#highly-recommended-fields").hide()
1585
- }
1586
- if (_recommendedFields.length > 0) {
1587
- jQuery("#recommended-field-table").html(_recommendedFields);
1588
- jQuery("#recommended-fields").show()
1589
- } else {
1590
- jQuery("#recommended-fields").hide()
1591
- }
1592
- if (_optionalFields.length > 0) {
1593
- jQuery("#optional-field-table").html(_optionalFields);
1594
- jQuery("#optional-fields").show()
1595
- } else {
1596
- jQuery("#optional-fields").hide()
1597
- }
1598
- if (_customFields.length > 0) {
1599
- jQuery("#custom-field-table").html(_customFields);
1600
- jQuery("#custom-fields").show()
1601
- } else {
1602
- jQuery("#custom-fields").hide()
1603
- }
1604
- tvc_feed_list_tab();
1605
- }
1606
-
1607
- function tvc_saveAndProceed() {
1608
- jQuery(".save-and-proceed").on("click",function(){
1609
- jQuery("#tvc-attribute-map-2").trigger("click");
1610
- });
1611
- }
1612
-
1613
- function tvc_feed_list_tab() {
1614
- var map1 = jQuery('#tvc-attribute-map-1');
1615
- var map2 = jQuery('#tvc-attribute-map-2');
1616
- var _centerbutton = jQuery('#page-center-buttons');
1617
- var _maininputmap = jQuery('#tvc-main-input-map');
1618
- var _catmap = jQuery( '#tvc-category-map' );
1619
- var _filterwrapper = jQuery('#main-product-filter-wrapper');
1620
- var _attributemap = jQuery( '#tvc-attribute-map' );
1621
-
1622
- _attributemap.hide();
1623
- map1.addClass('nav-tab-active');
1624
- map2.on('click',function () {
1625
- _centerbutton.hide();
1626
- map1.removeClass('nav-tab-active');
1627
- map2.addClass('nav-tab-active');
1628
- _maininputmap.hide();
1629
- _filterwrapper.hide();
1630
- _attributemap.show();
1631
- jQuery( '#tvc-category-map' ).hide();
1632
- jQuery(this).css("background-color:white");
1633
- });
1634
- map1.on('click',function () {
1635
- map2.removeClass('nav-tab-active');
1636
- map1.addClass('nav-tab-active');
1637
- _maininputmap.show();
1638
- _catmap.show();
1639
- _filterwrapper.show();
1640
- _attributemap.hide();
1641
- _centerbutton.show();
1642
- jQuery(this).css("background-color:white");
1643
- });
1644
- }
1645
-
1646
- function tvc_resetFields() {
1647
- _mandatoryFields = [];
1648
- _highlyRecommendedFields = [];
1649
- _recommendedFields = [];
1650
- _undefinedRecommendedOutputs = [];
1651
- _optionalFields = [];
1652
- _undefinedOptionalOutputs = [];
1653
- _customFields = [];
1654
- _undefinedCustomOutputs = []
1655
- }
1656
-
1657
- function tvc_queryConditionChanged(e, d, a) {
1658
- var c = jQuery("#query-condition-" + e + "-" + d + "-" + a).val();
1659
- if (c === "4" || c === "5") {
1660
- jQuery("#condition-value-" + e + "-" + d + "-" + a).hide()
1661
- } else {
1662
- jQuery("#condition-value-" + e + "-" + d + "-" + a).show()
1663
- }
1664
- if (c === "14") {
1665
- jQuery("#condition-value-" + e + "-" + d + "-" + a).show();
1666
- jQuery("#condition-and-value-" + e + "-" + d + "-" + a).show()
1667
- } else {
1668
- jQuery("#condition-and-value-" + e + "-" + d + "-" + a).hide()
1669
- }
1670
- var b = tvc_storeCondition(e, d, a);
1671
- if (b && !jQuery("#source-" + e + "-" + (d + 1)).length) {
1672
- jQuery(tvc_addFeedSourceRow(e, d + 1, _feedHolder.getSourceObject(e))).insertAfter("#source-" + e + "-" + d, false)
1673
- }
1674
- }
1675
-
1676
- function tvc_queryValueConditionChanged(e, c, a, d) {
1677
- var b = jQuery("#value-query-condition-" + e + "-" + c + "-" + a + "-" + d).val();
1678
- if (b === "4" || b === "5") {
1679
- jQuery("#value-options-condition-value-" + e + "-" + c + "-" + a).hide()
1680
- } else {
1681
- jQuery("#value-options-condition-value-" + e + "-" + c + "-" + a).show()
1682
- }
1683
- if (b === "14") {
1684
- jQuery("#value-options-condition-value-" + e + "-" + c + "-" + a).show();
1685
- jQuery("#value-options-condition-and-value-" + e + "-" + c + "-" + a).show()
1686
- } else {
1687
- jQuery("#value-options-condition-and-value-" + e + "-" + c + "-" + a).hide()
1688
- }
1689
- tvc_storeValueCondition(e, c, a)
1690
- }
1691
-
1692
- function tvc_getOutputFieldsList(d) {
1693
- var c = "";
1694
- var b = [];
1695
- switch (d) {
1696
- case 3:
1697
- b = _undefinedRecommendedOutputs;
1698
- break;
1699
- case 4:
1700
- b = _undefinedOptionalOutputs;
1701
- break;
1702
- default:
1703
- break
1704
- }
1705
- b.sort();
1706
- for (var a = 0; a < b.length; a++) {
1707
- c += '<option value="' + b[a] + '">' + b[a] + "</option>"
1708
- }
1709
- return c
1710
- }
1711
-
1712
- function tvc_fixedSourcesList(b) {
1713
- var d = "";
1714
- var c = "";
1715
- for (var a = 0; a < _inputFields.length; a++) {
1716
- c = b === _inputFields[a].value ? " selected" : "";
1717
- d += '<option value = "' + _inputFields[a].value + '" itemprop="' + _inputFields[a].prop + '" ' + c + ">" + _inputFields[a].label + "</option>"
1718
- }
1719
- return d
1720
- }
1721
-
1722
- function tvc_hideFeedFormMainInputs() {
1723
- jQuery("#category-list-row").hide();
1724
- jQuery("#aggregator-selector-row").hide();
1725
- jQuery("#add-product-variations-row").hide()
1726
- }
1727
-
1728
-
1729
- function tvc_getCombinedSeparatorList(b) {
1730
- var a = {
1731
- "0": "-- " + tvc_feed_settings_form_vars.no_separator + " --",
1732
- "1": tvc_feed_settings_form_vars.space,
1733
- "2": tvc_feed_settings_form_vars.comma,
1734
- "3": tvc_feed_settings_form_vars.point,
1735
- "4": tvc_feed_settings_form_vars.semicolon,
1736
- "5": tvc_feed_settings_form_vars.colon,
1737
- "6": tvc_feed_settings_form_vars.dash,
1738
- "7": tvc_feed_settings_form_vars.slash,
1739
- "8": tvc_feed_settings_form_vars.backslash,
1740
- "9": tvc_feed_settings_form_vars.double_pipe,
1741
- "10": tvc_feed_settings_form_vars.underscore
1742
- };
1743
- var c = "";
1744
- for (var d in a) {
1745
- if (d !== b) {
1746
- c += '<option value="' + d + '">' + a[d] + "</option>"
1747
- } else {
1748
- c += '<option value="' + d + '" selected>' + a[d] + "</option>"
1749
- }
1750
- }
1751
- return c
1752
- }
1753
-
1754
- function updateFeedFormAfterInputChanged(a, b) {
1755
- tvc_enableFeedActionButtons();
1756
- tvc_finishOrUpdateFeedPage(b);
1757
- if (a === undefined || a < 1) {
1758
- tvc_constructNewFeed()
1759
- }
1760
- }
1761
- jQuery(document).ready(function() {
1762
- var a = tvc_getUrlVariable("id");
1763
- var b = tvc_getUrlVariable("tab");
1764
- if ("" !== a && "product-feed" === b) {
1765
- tvc_showFeedSpinner();
1766
- tvc_initiateFeed();
1767
- tvc_editExistingFeed(a);
1768
- tvc_hideFeedSpinner()
1769
- }
1770
- });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-html.js DELETED
@@ -1,513 +0,0 @@
1
- "use strict";
2
- /*global tvc_feed_settings_form_vars */
3
- /**
4
- * Returns the html code for a static input field
5
- *
6
- * @param {string} rowId to which attribute row the field belongs
7
- * @param {string} queryLevel to which query level the field belongs
8
- * @param {string} combinationLevel in combined sources, to which combination level the field belongs
9
- * @param {string} selectedValue the value of the field
10
- * @returns {string} the html code
11
- */
12
- function tvc_staticInputField( rowId, queryLevel, combinationLevel, selectedValue ) {
13
-
14
- selectedValue = tvc_escapeHtml( selectedValue );
15
-
16
- return '<input type="text" name="static-input-field" id="static-input-field-' + rowId + '-' + queryLevel + '-' + combinationLevel
17
- + '" class="static-input-field" value="' + selectedValue + '" onchange="tvc_staticValueChanged('
18
- + rowId + ', ' + queryLevel + ', ' + combinationLevel + ')">';
19
- }
20
-
21
- function tvc_feedStaticValueSelector( fieldName, rowId, sourceLevel, level, value, channel ) {
22
-
23
- var restrictedFields = tvc_restrictedStaticFields( channel, fieldName );
24
-
25
- if ( restrictedFields.length > 0 ) {
26
-
27
- return tvc_displayCorrectStaticField( rowId, sourceLevel, level, channel, fieldName, value );
28
- } else {
29
-
30
- return tvc_staticInputField( rowId, sourceLevel, level, value );
31
- }
32
- }
33
-
34
- function tvc_staticInputSelect( rowId, level, combinationLevel, options, selected ) {
35
-
36
- var htmlCode = '<div class="static-value-control" id="static-value-control-' + rowId + '-' + level + '-' + combinationLevel + '">';
37
-
38
- htmlCode += '<select class="static-select-control input-select" id="static-condition-input-' + rowId + '-' + level + '-' + combinationLevel
39
- + '" onchange="tvc_staticValueChanged(' + rowId + ', ' + level + ', ' + combinationLevel + ')">';
40
-
41
- for ( var i = 0; i < options.length; i ++ ) {
42
-
43
- // some channels use a key and value combination for the static values
44
- var key = typeof options[ i ] !== 'object' ? options[ i ] : options[ i ][ 'id' ];
45
- var value = typeof options[ i ] !== 'object' ? options[ i ] : options[ i ][ 'value' ];
46
-
47
- if ( key !== selected ) {
48
- htmlCode += '<option value="' + key + '">' + value.replace( '_', ' ' ) + '</option>';
49
- } else {
50
- htmlCode += '<option value="' + key + '" selected>' + value.replace( '_', ' ' ) + '</option>';
51
- }
52
- }
53
-
54
- htmlCode += '</select></div>';
55
-
56
- return htmlCode;
57
- }
58
-
59
- function tvc_advisedSourceSelector( rowId, sourceCounter, advisedSource ) {
60
-
61
-
62
- return '<div class="advised-source">' + advisedSource + tvc_editSourceSelector( rowId, sourceCounter ) + '</div>';
63
- }
64
-
65
- function tvc_editSourceSelector( rowId, sourceCounter ) {
66
-
67
- var onClickString = 'tvc_editOutput( ' + rowId + ', ' + sourceCounter + ' )';
68
-
69
- return ' (<a class="edit-output tvc-btn tvc-btn-small" href="javascript:void(0)" onclick="' + onClickString + '">' + tvc_feed_settings_form_vars.edit + '</a>)';
70
- }
71
-
72
- function tvc_forAllProductsCondition( rowId, level, isVisible ) {
73
-
74
- var other_val = level > 0 ? tvc_feed_settings_form_vars.other + ' ' : '';
75
-
76
- return '<div class="colw col40w allproducts" id="condition-col-' + rowId + '-' + level + '" style="display:' + isVisible + '"> '
77
- + tvc_feed_settings_form_vars.all_other_products.replace( '%other%', other_val )
78
- + ' (<a class="edit-prod-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-prod-query-' + rowId + '" '
79
- + 'onclick="tvc_addCondition(' + rowId + ', ' + level + ', 0, \'\')">'
80
- + tvc_feed_settings_form_vars.edit + '</a>)'
81
- + '</div>';
82
- }
83
-
84
- function tvc_editValueSpan( rowId, sourceLevel, valueEditorLevel, displayStyle ) {
85
-
86
- return '<div class="edit-value-control" id="value-editor-input-query-add-span-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '" style="display:' + displayStyle + '"><p>'
87
- + '(<a class="edit-prod-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-row-value-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '" '
88
- + 'onclick="tvc_addRowValueEditor(' + rowId + ', ' + sourceLevel + ', ' + valueEditorLevel + ', \'\')">'
89
- + tvc_feed_settings_form_vars.edit_values + '</a>)'
90
- + '</p></div>';
91
- }
92
-
93
- function tvc_requiresForAllOtherProductsField( mapping ) {
94
- return mapping.hasOwnProperty( 'c' );
95
- }
96
-
97
- function tvc_addFeedSourceRow( rowId, sourceLevel, sourceRowsData, channel, removable ) {
98
-
99
- var borderStyleClass = sourceLevel > 0 ? ' dotted-top-line' : '';
100
- var showEditValuesControl = 'initial';
101
- var deleteValueControl = removable ? tvc_removeOutputCntrl( rowId, sourceRowsData.fieldName ) : '';
102
- var requiresForAllOtherProductsField = sourceLevel + 1 === sourceRowsData.mapping.length ? tvc_requiresForAllOtherProductsField( sourceRowsData.mapping[sourceLevel] ) : false;
103
-
104
- if ( sourceRowsData.customCondition ) { // no edit value control for the Category item
105
- showEditValuesControl = 'none';
106
- }
107
-
108
- // source wrapper
109
- var htmlCode = '<div class="feed-source-row" id="source-' + rowId + '-' + sourceLevel + '">';
110
-
111
- // first column wrapper
112
- htmlCode += '<div class="add-to-feed-column colw col20w">';
113
-
114
- // first column (add to feed column)
115
- htmlCode += sourceLevel === 0 ? '<span class="output-field-label">' + sourceRowsData.fieldName + '</span>' + deleteValueControl : '&nbsp;';
116
-
117
- htmlCode += '</div>';
118
-
119
- // the source data and queries wrapper
120
- htmlCode += '<div class="source-data-column colw col80w' + borderStyleClass + '" id="source-data-' + rowId + '-' + sourceLevel + '">';
121
-
122
- htmlCode += tvc_addSourceDataAndQueriesColumn( sourceLevel, sourceRowsData );
123
-
124
- // close the source data and queries wrapper
125
- htmlCode += '</div>';
126
-
127
- if ( sourceLevel === 0 && sourceRowsData.changeValues.length === 0 ) {
128
- htmlCode += tvc_editValueSpan( sourceRowsData.rowId, sourceLevel, 0, showEditValuesControl );
129
- } else {
130
-
131
- // Aanzetten om fout 73 verder te onderzoeken
132
- // console.log(JSON.stringify(sourceRowsData.changeValues));
133
- // console.log(sourceRowsData.changeValues.length);
134
- // console.log(sourceLevel);
135
-
136
- // for ( var i = 0; i < sourceRowsData.changeValues.length; i++ ) {
137
- //
138
- // if ( sourceRowsData.changeValues[sourceLevel] ) {
139
- //
140
- // // add the change value editor fields
141
- // htmlCode += tvc_valueEditor( sourceRowsData.rowId, sourceLevel, i, sourceRowsData.changeValues );
142
- // }
143
-
144
- // }
145
- }
146
-
147
- // close the source wrapper
148
- htmlCode += '</div>';
149
-
150
- if ( requiresForAllOtherProductsField ) {
151
- htmlCode += tvc_orSelectorRowCode( rowId, sourceLevel + 1, borderStyleClass );
152
- }
153
-
154
- return htmlCode;
155
- }
156
-
157
- function tvc_removeOutputCntrl( rowId, fieldName ) {
158
- var htmlCode = ' (';
159
- htmlCode += '<a class="remove-output tvc-btn tvc-btn-small" href="javascript:void(0)" id="';
160
- htmlCode += rowId + '" onclick="tvc_removeRow(' + rowId + ', \'' + fieldName + '\')">' + tvc_feed_settings_form_vars.remove + '</a>';
161
- htmlCode += ') ';
162
-
163
- return htmlCode;
164
- }
165
-
166
- function tvc_conditionQueryCntrl( id, sourceLevel, conditionLevel, subConditionLevel, identifier, onChangeFunction, selectedValue ) {
167
- var queryOptions = tvc_queryOptionsEng();
168
- var queryLevelString = subConditionLevel !== - 1 ? '-' + subConditionLevel : '';
169
- var queryLevelFunctionString = subConditionLevel !== - 1 ? ', ' + subConditionLevel : '';
170
-
171
- var htmlCode = '<select class="select-control condition-query-select" id="' + identifier + '-'
172
- + id + '-' + sourceLevel + '-' + conditionLevel + queryLevelString + '" onchange="' + onChangeFunction + '(' + id + ', ' + sourceLevel + ', ' + conditionLevel + queryLevelFunctionString + ')"> ';
173
-
174
- for ( var i = 0; i < queryOptions.length; i ++ ) {
175
- htmlCode += parseInt( selectedValue ) !== i ? '<option value = "' + i + '">' + queryOptions[ i ] + '</option>'
176
- : '<option value = "' + i + '" selected>' + queryOptions[ i ] + '</option>';
177
- }
178
-
179
- htmlCode += '</select>';
180
-
181
- return htmlCode;
182
- }
183
-
184
- function tvc_valueEditor( rowId, sourceLevel, valueEditorLevel, valueObject ) {
185
- var valueArray = tvc_valueStringToValueObject( valueObject[ sourceLevel ] );
186
- var queryDisplay = valueObject[ valueEditorLevel ] && valueObject[ valueEditorLevel ].q ? 'none' : 'initial';
187
- var value = tvc_countObjectItems( valueArray ) > 0 ? valueArray : tvc_makeCleanValueObject();
188
- var valueSelector = tvc_feed_settings_form_vars.and_change_values + ' ';
189
- var html = '<div class="change-source-value-wrapper" id="edit-value-span-' + rowId + '-' + sourceLevel + '-0">';
190
- var removeValueEditorSelector = sourceLevel === 0 ? ' (<a class="remove-value-editor-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="remove-value-editor-query-' + rowId + '-' + sourceLevel
191
- + '-' + valueEditorLevel + '" onclick="tvc_removeValueEditor(' + rowId + ', ' + sourceLevel + ', ' + valueEditorLevel + ')">' + tvc_feed_settings_form_vars.remove_value_editor + '</a>)' : '';
192
-
193
- if ( sourceLevel > 0 ) {
194
- valueSelector = tvc_feed_settings_form_vars.and + ' ';
195
- }
196
-
197
- html += valueSelector;
198
- html += tvc_changeValueCntrl( rowId, sourceLevel, valueEditorLevel, value.condition );
199
- html += '<span id="value-editor-input-span-' + rowId + '-' + sourceLevel + '-0">';
200
- html += tvc_getCorrectValueSelector( rowId, sourceLevel, 0, value.condition, value.value, value.endValue );
201
- html += '</span>';
202
- html += '<span id="value-editor-selectors-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '">';
203
- html += tvc_forAllProductsAtChangeValuesSelector( rowId, sourceLevel, valueEditorLevel, queryDisplay );
204
- html += '<span id="value-editor-input-query-remove-span-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '">';
205
- html += removeValueEditorSelector;
206
- html += '</span>';
207
- html += '</span>';
208
- html += '<span id="value-editor-queries-' + rowId + '-' + sourceLevel + '-0">';
209
-
210
- if ( valueObject[ valueEditorLevel ] && valueObject[ valueEditorLevel ].q ) {
211
- for ( var i = 1; i < valueObject[ valueEditorLevel ].q.length + 1; i ++ ) {
212
- var queryArray = tvc_convertQueryStringToQueryObject( valueObject[ valueEditorLevel ].q[ i - 1 ][ i ] );
213
- var lastValue = i >= valueObject[ valueEditorLevel ].q.length ? true : false;
214
-
215
- html += tvc_ifValueQuerySelector( rowId, sourceLevel, i, queryArray, lastValue );
216
- }
217
- }
218
-
219
- html += '</span></div>';
220
-
221
- return html;
222
- }
223
-
224
- function tvc_endrow( rowId ) {
225
- return '<div class="end-row" id="end-row-id-' + rowId + '">&nbsp;</div>';
226
- }
227
-
228
-
229
- function tvc_forAllProductsAtChangeValuesSelector( rowId, sourceLevel, valueEditorLevel, displayStatus ) {
230
- var other_val = sourceLevel > 0 ? tvc_feed_settings_form_vars.other + ' ' : '';
231
-
232
- return '<div class="colw col30w allproducts" id="value-editor-input-query-span-' + rowId + '-' + sourceLevel + '-0" style="display:' + displayStatus + ';float:right;">'
233
- + tvc_feed_settings_form_vars.all_other_products.replace( '%other%', other_val )
234
- + ' (<a class="edit-value-editor-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-value-editor-query-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel
235
- + '" onclick="tvc_addValueEditorQuery(' + rowId + ', ' + sourceLevel + ', 0)">' + tvc_feed_settings_form_vars.edit + '</a>)'
236
- + '</div>';
237
- }
238
-
239
- function tvc_valueOptionsSingleInput( rowId, sourceLevel, valueEditorLevel, value ) {
240
- return ' ' + tvc_feed_settings_form_vars.to + tvc_valueOptionsSingleInputValue( rowId, sourceLevel, valueEditorLevel, value );
241
- }
242
-
243
- function tvc_valueOptionsElementInput( rowId, sourceLevel, valueEditorLevel, value ) {
244
- return ' ' + tvc_feed_settings_form_vars.with_element_name + tvc_valueOptionsSingleInputValue( rowId, sourceLevel, valueEditorLevel, value );
245
- }
246
-
247
- function tvc_valueOptionsSingleInputValue( rowId, sourceLevel, valueEditorLevel, optionsSelectorValue ) {
248
-
249
- optionsSelectorValue = tvc_escapeHtml( optionsSelectorValue );
250
-
251
- return ' <input type="text" onchange="tvc_valueInputOptionsChanged(' + rowId + ', ' + sourceLevel
252
- + ', ' + valueEditorLevel + ')" id="value-options-input-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '" value="' + optionsSelectorValue + '">';
253
- }
254
-
255
- function tvc_addFeedStatusChecker( feedId ) {
256
- return '<script type="text/javascript">var tvcStatusCheck_' + feedId + ' = null; '
257
- + '(function(){ tvcStatusCheck_' + feedId + ' = window.setInterval( tvc_checkAndSetStatus_' + feedId + ', 10000, ' + feedId + ' ); })(); '
258
- + 'function tvc_checkAndSetStatus_' + feedId + '( feedId ) {'
259
- + 'tvc_getCurrentFeedStatus( feedId, function( result ) {'
260
- + 'var data = JSON.parse( result );'
261
- + 'tvc_resetFeedStatus( data );'
262
- + 'if( data["status_id"] !== "3" && data["status_id"] !== "4" ) {' // status is not in processing or in queue
263
- + 'window.clearInterval( tvcStatusCheck_' + feedId + ' );'
264
- + '}'
265
- + '} );'
266
- + '}</script>';
267
- }
268
-
269
- function tvc_valueOptionsReplaceInput( rowId, sourceLevel, valueEditorLevel, startValue, endValue ) {
270
-
271
- startValue = tvc_escapeHtml( startValue );
272
-
273
- return '<input type="text" onchange="tvc_valueInputOptionsChanged(' + rowId + ', ' + sourceLevel + ', '
274
- + valueEditorLevel + ' )" id="value-options-input-' + rowId + '-' + sourceLevel + '-' + valueEditorLevel
275
- + '" value="' + startValue + '"> with <input type="text" onchange="tvc_valueInputOptionsChanged('
276
- + rowId + ', ' + sourceLevel + ', ' + valueEditorLevel + ')" id="value-options-input-with-' + rowId + '-'
277
- + sourceLevel + '-' + valueEditorLevel + '" value="' + endValue + '">';
278
- }
279
-
280
- function tvc_valueOptionsRecalculate( rowId, sourceLevel, valueEditorLevel, selectedValue, recalculateValue ) {
281
- var valueOptions = tvc_changeValuesRecalculateOptions();
282
-
283
- var htmlCode = '<select class="select-value-options" id="value-options-recalculate-options-' + rowId + '-' + sourceLevel + '-0">';
284
-
285
- for ( var i = 0; i < valueOptions.length; i ++ ) {
286
-
287
- htmlCode += valueOptions[ i ] !== selectedValue ? '<option value = "' + i + '">' + valueOptions[ i ] + '</option>'
288
- : '<option value = "' + i + '" selected>' + valueOptions[ i ] + '</option>';
289
- }
290
-
291
- htmlCode += '</select>';
292
- htmlCode += ' <input type="text" onchange="tvc_valueInputOptionsChanged(' + rowId + ', ' + sourceLevel + ', ' + valueEditorLevel + ')" id="value-options-input-'
293
- + rowId + '-' + sourceLevel + '-' + valueEditorLevel + '" value="' + recalculateValue + '">';
294
-
295
- return htmlCode;
296
- }
297
-
298
- function tvc_changeValueCntrl( rowId, conditionLevel, valueEditorLevel, selectedValue ) {
299
- var valueOptions = tvc_changeValuesOptions();
300
-
301
- var htmlCode = '<select class="select-value-options" id="value-options-'
302
- + rowId + '-' + conditionLevel + '-0" onchange="tvc_valueOptionChanged(' + rowId + ', ' + conditionLevel + ', 0)"> ';
303
-
304
- for ( var i = 0; i < valueOptions.length; i ++ ) {
305
-
306
- htmlCode += valueOptions[ i ] !== selectedValue ? '<option value = "' + i + '">' + valueOptions[ i ] + '</option>'
307
- : '<option value = "' + i + '" selected>' + valueOptions[ i ] + '</option>';
308
- }
309
-
310
- htmlCode += '</select>';
311
-
312
- return htmlCode;
313
- }
314
-
315
- function tvc_mapToDefaultCategoryElement( categoryId, category ) {
316
- var categoryText = '';
317
- var editable = '';
318
-
319
- switch ( category ) {
320
- case 'default':
321
- categoryText = tvc_feed_settings_form_vars.map_to_default_category;
322
- break;
323
-
324
- case 'shopCategory':
325
- categoryText = tvc_feed_settings_form_vars.use_shop_category;
326
- break;
327
-
328
- default:
329
- categoryText = category;
330
- break;
331
- }
332
-
333
- if ( category !== 'shopCategory' ) {
334
- editable = ' (<a class="edit-feed-mapping tvc-btn tvc-btn-small" '
335
- + 'href="javascript:void(0)" data-id="' + categoryId + '" id="edit-feed-mapping-' + categoryId
336
- + '" onclick="tvc_editCategoryMapping(' + categoryId + ')">' + tvc_feed_settings_form_vars.edit + '</a>)';
337
- }
338
-
339
- return '<div class="feed-category-map-to-default" id="feed-category-map-to-default-' + categoryId
340
- + '" style="display:initial"><span id="category-text-span-' + categoryId + '">' + categoryText
341
- + '</span>' + editable + '</div>';
342
- }
343
-
344
- function tvc_mapToCategoryElement( categoryId, categoryString ) {
345
-
346
- return '<div class="feed-category-map" id="feed-category-map-' + categoryId
347
- + '" style="display:initial"><span id="category-text-span-' + categoryId + '">' + categoryString
348
- + '</span> (<a class="edit-feed-mapping tvc-btn tvc-btn-small" '
349
- + 'href="javascript:void(0)" data-id="' + categoryId + '" id="edit-feed-mapping-' + categoryId
350
- + '" onclick="tvc_editCategoryMapping(' + categoryId + ')">' + tvc_feed_settings_form_vars.edit + '</a>)</div>';
351
- }
352
-
353
- //function tvc_categorySource( rowId, sourceValue ) {
354
- function tvc_categorySource() {
355
- return '<span id="category-source-string">' + tvc_feed_settings_form_vars.defined_by_category_mapping_tble + '</span>';
356
- }
357
-
358
- function tvc_freeCategoryInputCntrl( type, id, value ) {
359
- var valueString = value ? ' value="' + value + '"' : '';
360
-
361
- return '<input type="text" name="free-category" class="free-category-text-input custom-category-'
362
- + type + '" id="free-category-text-input" onchange="tvc_freeCategoryChanged(\''
363
- + type + '\', \'' + id + '\')"' + valueString + '>';
364
- }
365
-
366
- function tvc_inputFieldCntrl( rowId, sourceLevel, sourceValue, staticValue, advisedSource, combinedValue, isCustom ) {
367
-
368
- var hasAdvisedValueHtml = advisedSource ? '<option value="advised" itemprop="basic">' + tvc_feed_settings_form_vars.use_advised_source + '</option>' : '';
369
- var staticSelectedHtml = staticValue ? ' selected' : '';
370
- var prefix = sourceLevel > 0 ? tvc_feed_settings_form_vars.or + ' ' : '';
371
- var hasCombinedOptionHtml = ! combinedValue ? '<option value="combined" itemprop="basic">' + tvc_feed_settings_form_vars.combined_source_fields + '</option>'
372
- : '<option value="combined" selected>' + tvc_feed_settings_form_vars.combined_source_fields + '</option>';
373
- var customCategoryMapping = isCustom ? '<option value="category_mapping" itemprop="basic">' + tvc_feed_settings_form_vars.category_mapping + '</option>' : '';
374
-
375
- return '<div class="select-control">' + prefix + '<select class="select-control input-select" id="input-field-cntrl-' + rowId + '-' + sourceLevel
376
- + '" onchange="tvc_changedOutput(' + rowId + ', ' + sourceLevel + ', \'' + advisedSource + '\')"> '
377
- + '<option value="select" itemprop="basic">-- ' + tvc_feed_settings_form_vars.select_a_source_field + ' --</option>'
378
- + hasAdvisedValueHtml
379
- + '<option value="static" itemprop="basic"'
380
- + staticSelectedHtml
381
- + '>' + tvc_feed_settings_form_vars.fill_with_static_value + '</option>'
382
- + customCategoryMapping
383
- + hasCombinedOptionHtml
384
- + tvc_fixedSourcesList( sourceValue ) + '</select></div>';
385
- }
386
-
387
- function tvc_combinedInputFieldCntrl( rowId, sourceLevel, combinedLevel, selectedValue, fieldName, channel ) {
388
-
389
- var isStatic = selectedValue && selectedValue.startsWith( 'static#' );
390
- var staticSelectedHtml = isStatic ? ' selected' : '';
391
- var staticInputHtml = isStatic ? tvc_feedStaticValueSelector( fieldName, rowId, sourceLevel, combinedLevel, selectedValue.substring( 7 ), channel ) : '';
392
-
393
- return '<select class="select-control input-select align-left" id="combined-input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + combinedLevel
394
- + '" onchange="tvc_changedCombinedOutput(' + rowId + ', ' + sourceLevel + ', ' + combinedLevel + ')"> '
395
- + '<option value="select" itemprop="basic">-- ' + tvc_feed_settings_form_vars.select_a_source_field + ' --</option>'
396
- + '<option value="static" itemprop="basic"'
397
- + staticSelectedHtml
398
- + '>' + tvc_feed_settings_form_vars.fill_with_static_value + '</option>'
399
- + tvc_fixedSourcesList( selectedValue ) + '</select>'
400
- + '<div class="static-value-control" id="static-value-control-' + rowId + '-' + sourceLevel + '-' + combinedLevel + '">'
401
- + staticInputHtml
402
- + '</div>';
403
- }
404
-
405
- function tvc_combinedSeparatorCntrl( rowId, sourceLevel, combinedLevel, selectedValue ) {
406
-
407
- return '<select class="select-control input-select align-left" id="combined-separator-cntrl-' + rowId + '-' + sourceLevel + '-' + combinedLevel
408
- + '" onchange="tvc_changedCombinationSeparator(' + rowId + ', ' + sourceLevel + ', ' + combinedLevel + ')"> '
409
- + tvc_getCombinedSeparatorList( selectedValue )
410
- + '</select>';
411
- }
412
-
413
- function tvc_alternativeInputFieldCntrl( id, selectedValue ) {
414
-
415
- var selectedValueHtml = selectedValue === 'static' ? ' selected' : '';
416
-
417
- return '<select class="select-control alternative-input-select" id="alternative-input-field-cntrl-' + id
418
- + '" onchange="tvc_changedAlternativeSource(' + id + ')"> '
419
- + '<option value="select">-- ' + tvc_feed_settings_form_vars.select_a_source_field + ' --</option>'
420
- + '<option value="empty">-- ' + tvc_feed_settings_form_vars.an_empty_field + ' --</option>'
421
- + '<option value="static"'
422
- + selectedValueHtml
423
- + '>' + tvc_feed_settings_form_vars.fill_with_static_value + '</option>'
424
- + tvc_fixedSourcesList( selectedValue ) + '</select>';
425
- }
426
-
427
- function tvc_outputFieldCntrl( level ) {
428
-
429
- var outputLevelHtml = level === 3 ? '<option value="no-value">-- ' + tvc_feed_settings_form_vars.add_recommended_output + ' --</option>' :
430
- '<option value="no-value">-- ' + tvc_feed_settings_form_vars.add_optional_output + ' --</option>';
431
-
432
- return '<select class="select-control input-select" id="output-field-cntrl-' + level + '"> '
433
- + outputLevelHtml
434
- + tvc_getOutputFieldsList( level )
435
- + '</select>';
436
- }
437
-
438
- function tvc_customOutputFieldCntrl() {
439
- return '<input type="text" name="custom-output-title" id="custom-output-title-input" placeholder="Enter an output title" onfocusout="tvc_changedCustomOutputTitle()">';
440
- }
441
-
442
- function tvc_conditionFieldCntrl( id, sourceLevel, conditionLevel, subConditionLevel, identifier, selectedValue, onChange ) {
443
-
444
- var subConditionLevelString = subConditionLevel !== - 1 ? '-' + subConditionLevel : '';
445
- var emptyOption = identifier === 'or-field-cntrl' ? '<option value="empty">-- ' + tvc_feed_settings_form_vars.an_empty_field + ' --</option>' : '';
446
- var onChangeFunction = onChange ? ' onchange="' + onChange + '"' : '';
447
-
448
- return '<select class="select-control input-select" id="' + identifier + '-' + id + '-' + sourceLevel + '-' + conditionLevel + subConditionLevelString + '"' + onChangeFunction + '> '
449
- + '<option value="select">-- ' + tvc_feed_settings_form_vars.select_a_source_field + ' --</option>'
450
- + emptyOption
451
- + tvc_fixedSourcesList( selectedValue )
452
- + '</select>';
453
- }
454
-
455
- function tvc_filterPreCntrl( feedId, filterLevel, selectedValue ) {
456
-
457
- var preString = '<select id="filter-pre-control-' + feedId + '-' + filterLevel + '" onchange="tvc_filterChanged(' + feedId + ', ' + filterLevel + ')">';
458
-
459
- if ( filterLevel > 1 ) {
460
-
461
- return selectedValue === '1'
462
- ? preString + '<option value="2">' + tvc_feed_settings_form_vars.or + '</option><option value="1" selected>' + tvc_feed_settings_form_vars.and + '</option></select>'
463
- : preString + '<option value="2" selected>' + tvc_feed_settings_form_vars.or + '</option><option value="1">' + tvc_feed_settings_form_vars.and + '</option></select>';
464
- } else {
465
-
466
- return '';
467
- }
468
-
469
- }
470
-
471
- function tvc_filterSourceCntrl( feedId, filterLevel, selectedValue ) {
472
-
473
- return '<select class="select-control input-select" id="filter-source-control-' + feedId + '-' + filterLevel + '" onchange="tvc_filterChanged(' + feedId + ', ' + filterLevel + ')">'
474
- + '<option value="select">-- ' + tvc_feed_settings_form_vars.select_a_source_field + ' --</option>'
475
- + tvc_fixedSourcesList( selectedValue )
476
- + '</select>';
477
- }
478
-
479
- function tvc_filterOptionsCntrl( feedId, filterLevel, selectedValue ) {
480
-
481
- var filterOptions = tvc_queryOptionsEng();
482
-
483
- var htmlCode = '<select class="select-control condition-query-select" id="filter-options-control-' + feedId + '-' + filterLevel;
484
- htmlCode += '" onchange="tvc_filterChanged(' + feedId + ', ' + filterLevel + ')">';
485
-
486
- for ( var i = 0; i < filterOptions.length; i ++ ) {
487
-
488
- htmlCode += parseInt( selectedValue ) !== i ? '<option value = "' + i + '">' + filterOptions[ i ] + '</option>'
489
- : '<option value = "' + i + '" selected>' + filterOptions[ i ] + '</option>';
490
- }
491
-
492
- htmlCode += '</select>';
493
-
494
- return htmlCode;
495
- }
496
-
497
- function tvc_filterInputCntrl( feedId, filterLevel, inputLevel, value ) {
498
- var identString = feedId + '-' + filterLevel + '-' + inputLevel;
499
- var andString = inputLevel > 1 ? ' ' + tvc_feed_settings_form_vars.and + ' ' : '';
500
- var splitPosition = inputLevel === 1 ? 1 : 3;
501
- var splitValue = '';
502
-
503
- if ( inputLevel > 1 ) {
504
- splitValue = value && value.includes( '#' ) ? value.split( '#' )[ splitPosition ] : '';
505
- } else {
506
- splitValue = value ? value : '';
507
- }
508
-
509
- var style = ! splitValue ? 'style="display:none"' : 'style="display:initial"';
510
-
511
- return '<span id="filter-input-span-' + identString + '"' + style + '>' + andString + '<input type="text" name="filter-value" id="filter-input-control-' + identString
512
- + '" onchange="tvc_filterChanged(' + feedId + ', ' + filterLevel + ', ' + inputLevel + ')" value="' + splitValue + '"></span>';
513
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-html.min.js DELETED
@@ -1 +0,0 @@
1
- function tvc_staticInputField(e,t,p,n){return'<input type="text" name="static-input-field" id="static-input-field-'+e+"-"+t+"-"+p+'" class="static-input-field" value="'+(n=tvc_escapeHtml(n))+'" onchange="tvc_staticValueChanged('+e+", "+t+", "+p+')">'}function tvc_feedStaticValueSelector(e,t,p,n,i,o){return tvc_restrictedStaticFields(o,e).length>0?tvc_displayCorrectStaticField(t,p,n,o,e,i):tvc_staticInputField(t,p,n,i)}function tvc_staticInputSelect(e,t,p,n,i){var o='<div class="static-value-control" id="static-value-control-'+e+"-"+t+"-"+p+'">';o+='<select class="static-select-control input-select" id="static-condition-input-'+e+"-"+t+"-"+p+'" onchange="tvc_staticValueChanged('+e+", "+t+", "+p+')">';for(var a=0;a<n.length;a++){var s="object"!=typeof n[a]?n[a]:n[a].id,r="object"!=typeof n[a]?n[a]:n[a].value;o+=s!==i?'<option value="'+s+'">'+r.replace("_"," ")+"</option>":'<option value="'+s+'" selected>'+r.replace("_"," ")+"</option>"}return o+="</select></div>"}function tvc_advisedSourceSelector(e,t,p){return'<div class="advised-source">'+p+tvc_editSourceSelector(e,t)+"</div>"}function tvc_editSourceSelector(e,t){return' (<a class="edit-output tvc-btn tvc-btn-small" href="javascript:void(0)" onclick="'+("tvc_editOutput( "+e+", "+t+" )")+'">'+tvc_feed_settings_form_vars.edit+"</a>)"}function tvc_forAllProductsCondition(e,t,p){var n=t>0?tvc_feed_settings_form_vars.other+" ":"";return'<div class="colw col40w allproducts" id="condition-col-'+e+"-"+t+'" style="display:'+p+'"> '+tvc_feed_settings_form_vars.all_other_products.replace("%other%",n)+' &nbsp;<a class="edit-prod-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-prod-query-'+e+'" onclick="tvc_addCondition('+e+", "+t+", 0, '')\"><i class='fas fa-edit'></i></a></div>"}function tvc_editValueSpan(e,t,p,n){return'<div class="edit-value-control" id="value-editor-input-query-add-span-'+e+"-"+t+"-"+p+'" style="display:'+n+'"><p><a class="edit-prod-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-row-value-'+e+"-"+t+"-"+p+'" onclick="tvc_addRowValueEditor('+e+", "+t+", "+p+", '')\"><i class='fas fa-edit'></i></a></p></div>"}function tvc_requiresForAllOtherProductsField(e){return e.hasOwnProperty("c")}function tvc_addFeedSourceRow(e,t,p,n,i){var o=t>0?" dotted-top-line":"",a="initial",s=i?tvc_removeOutputCntrl(e,p.fieldName):"",r=t+1===p.mapping.length&&tvc_requiresForAllOtherProductsField(p.mapping[t]);p.customCondition&&(a="none");var l='<div class="feed-source-row" id="source-'+e+"-"+t+'">';return l+='<div class="add-to-feed-column colw col20w">',l+=0===t?'<span class="output-field-label">'+p.fieldName+"</span>"+s:"&nbsp;",l+="</div>",l+='<div class="source-data-column colw col80w'+o+'" id="source-data-'+e+"-"+t+'">',l+=tvc_addSourceDataAndQueriesColumn(t,p),l+="</div>",0===t&&0===p.changeValues.length&&(l+=tvc_editValueSpan(p.rowId,t,0,a)),l+="</div>",r&&(l+=tvc_orSelectorRowCode(e,t+1,o)),l}function tvc_removeOutputCntrl(e,t){var p=" (";return p+='<a class="remove-output tvc-btn tvc-btn-small" href="javascript:void(0)" id="',p+=e+'" onclick="tvc_removeRow('+e+", '"+t+"')\">"+tvc_feed_settings_form_vars.remove+"</a>",p+=") "}function tvc_conditionQueryCntrl(e,t,p,n,i,o,a){for(var s=tvc_queryOptionsEng(),r='<select class="select-control condition-query-select" id="'+i+"-"+e+"-"+t+"-"+p+(-1!==n?"-"+n:"")+'" onchange="'+o+"("+e+", "+t+", "+p+(-1!==n?", "+n:"")+')"> ',l=0;l<s.length;l++)r+=parseInt(a)!==l?'<option value = "'+l+'">'+s[l]+"</option>":'<option value = "'+l+'" selected>'+s[l]+"</option>";return r+="</select>"}function tvc_valueEditor(e,t,p,n){var i=tvc_valueStringToValueObject(n[t]),o=n[p]&&n[p].q?"none":"initial",a=tvc_countObjectItems(i)>0?i:tvc_makeCleanValueObject(),s=tvc_feed_settings_form_vars.and_change_values+" ",r='<div class="change-source-value-wrapper" id="edit-value-span-'+e+"-"+t+'-0">',l=0===t?' (<a class="remove-value-editor-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="remove-value-editor-query-'+e+"-"+t+"-"+p+'" onclick="tvc_removeValueEditor('+e+", "+t+", "+p+')">'+tvc_feed_settings_form_vars.remove_value_editor+"</a>)":"";if(t>0&&(s=tvc_feed_settings_form_vars.and+" "),r+=s,r+=tvc_changeValueCntrl(e,t,p,a.condition),r+='<span id="value-editor-input-span-'+e+"-"+t+'-0">',r+=tvc_getCorrectValueSelector(e,t,0,a.condition,a.value,a.endValue),r+="</span>",r+='<span id="value-editor-selectors-'+e+"-"+t+"-"+p+'">',r+=tvc_forAllProductsAtChangeValuesSelector(e,t,p,o),r+='<span id="value-editor-input-query-remove-span-'+e+"-"+t+"-"+p+'">',r+=l,r+="</span>",r+="</span>",r+='<span id="value-editor-queries-'+e+"-"+t+'-0">',n[p]&&n[p].q)for(var c=1;c<n[p].q.length+1;c++){var u=tvc_convertQueryStringToQueryObject(n[p].q[c-1][c]),f=c>=n[p].q.length;r+=tvc_ifValueQuerySelector(e,t,c,u,f)}return r+="</span></div>"}function tvc_endrow(e){return'<div class="end-row" id="end-row-id-'+e+'">&nbsp;</div>'}function tvc_forAllProductsAtChangeValuesSelector(e,t,p,n){var i=t>0?tvc_feed_settings_form_vars.other+" ":"";return'<div class="colw col30w allproducts" id="value-editor-input-query-span-'+e+"-"+t+'-0" style="display:'+n+';float:right;">'+tvc_feed_settings_form_vars.all_other_products.replace("%other%",i)+' (<a class="edit-value-editor-query tvc-btn tvc-btn-small" href="javascript:void(0)" id="edit-value-editor-query-'+e+"-"+t+"-"+p+'" onclick="tvc_addValueEditorQuery('+e+", "+t+', 0)">'+tvc_feed_settings_form_vars.edit+"</a>)</div>"}function tvc_valueOptionsSingleInput(e,t,p,n){return" "+tvc_feed_settings_form_vars.to+tvc_valueOptionsSingleInputValue(e,t,p,n)}function tvc_valueOptionsElementInput(e,t,p,n){return" "+tvc_feed_settings_form_vars.with_element_name+tvc_valueOptionsSingleInputValue(e,t,p,n)}function tvc_valueOptionsSingleInputValue(e,t,p,n){return' <input type="text" onchange="tvc_valueInputOptionsChanged('+e+", "+t+", "+p+')" id="value-options-input-'+e+"-"+t+"-"+p+'" value="'+(n=tvc_escapeHtml(n))+'">'}function tvc_addFeedStatusChecker(e){return'<script type="text/javascript">var tvcStatusCheck_'+e+" = null; (function(){ tvcStatusCheck_"+e+" = window.setInterval( tvc_checkAndSetStatus_"+e+", 10000, "+e+" ); })(); function tvc_checkAndSetStatus_"+e+'( feedId ) {tvc_getCurrentFeedStatus( feedId, function( result ) {var data = JSON.parse( result );tvc_resetFeedStatus( data );if( data["status_id"] !== "3" && data["status_id"] !== "4" ) {window.clearInterval( tvcStatusCheck_'+e+" );}} );}<\/script>"}function tvc_valueOptionsReplaceInput(e,t,p,n,i){return'<input type="text" onchange="tvc_valueInputOptionsChanged('+e+", "+t+", "+p+' )" id="value-options-input-'+e+"-"+t+"-"+p+'" value="'+(n=tvc_escapeHtml(n))+'"> with <input type="text" onchange="tvc_valueInputOptionsChanged('+e+", "+t+", "+p+')" id="value-options-input-with-'+e+"-"+t+"-"+p+'" value="'+i+'">'}function tvc_valueOptionsRecalculate(e,t,p,n,i){for(var o=tvc_changeValuesRecalculateOptions(),a='<select class="select-value-options" id="value-options-recalculate-options-'+e+"-"+t+'-0">',s=0;s<o.length;s++)a+=o[s]!==n?'<option value = "'+s+'">'+o[s]+"</option>":'<option value = "'+s+'" selected>'+o[s]+"</option>";return a+="</select>",a+=' <input type="text" onchange="tvc_valueInputOptionsChanged('+e+", "+t+", "+p+')" id="value-options-input-'+e+"-"+t+"-"+p+'" value="'+i+'">'}function tvc_changeValueCntrl(e,t,p,n){for(var i=tvc_changeValuesOptions(),o='<select class="select-value-options" id="value-options-'+e+"-"+t+'-0" onchange="tvc_valueOptionChanged('+e+", "+t+', 0)"> ',a=0;a<i.length;a++)o+=i[a]!==n?'<option value = "'+a+'">'+i[a]+"</option>":'<option value = "'+a+'" selected>'+i[a]+"</option>";return o+="</select>"}function tvc_mapToDefaultCategoryElement(e,t){var p="",n="";switch(t){case"default":p=tvc_feed_settings_form_vars.map_to_default_category;break;case"shopCategory":p=tvc_feed_settings_form_vars.use_shop_category;break;default:p=t}return"shopCategory"!==t&&(n=' (<a class="edit-feed-mapping tvc-btn tvc-btn-small" href="javascript:void(0)" data-id="'+e+'" id="edit-feed-mapping-'+e+'" onclick="tvc_editCategoryMapping('+e+')">'+tvc_feed_settings_form_vars.edit+"</a>)"),'<div class="feed-category-map-to-default" id="feed-category-map-to-default-'+e+'" style="display:initial"><span id="category-text-span-'+e+'">'+p+"</span>"+n+"</div>"}function tvc_mapToCategoryElement(e,t){return'<div class="feed-category-map" id="feed-category-map-'+e+'" style="display:initial"><span id="category-text-span-'+e+'">'+t+'</span> (<a class="edit-feed-mapping tvc-btn tvc-btn-small" href="javascript:void(0)" data-id="'+e+'" id="edit-feed-mapping-'+e+'" onclick="tvc_editCategoryMapping('+e+')">'+tvc_feed_settings_form_vars.edit+"</a>)</div>"}function tvc_categorySource(){return'<span id="category-source-string">'+tvc_feed_settings_form_vars.defined_by_category_mapping_tble+"</span>"}function tvc_freeCategoryInputCntrl(e,t,p){return'<input type="text" name="free-category" class="free-category-text-input custom-category-'+e+'" id="free-category-text-input" onchange="tvc_freeCategoryChanged(\''+e+"', '"+t+"')\""+(p?' value="'+p+'"':"")+">"}function tvc_inputFieldCntrl(e,t,p,n,i,o,a){var s=i?'<option value="advised" itemprop="basic">'+tvc_feed_settings_form_vars.use_advised_source+"</option>":"",r=n?" selected":"",l=t>0?tvc_feed_settings_form_vars.or+" ":"",c=o?'<option value="combined" selected>'+tvc_feed_settings_form_vars.combined_source_fields+"</option>":'<option value="combined" itemprop="basic">'+tvc_feed_settings_form_vars.combined_source_fields+"</option>",u=a?'<option value="category_mapping" itemprop="basic">'+tvc_feed_settings_form_vars.category_mapping+"</option>":"";return'<div class="select-control">'+l+'<select class="select-control input-select" id="input-field-cntrl-'+e+"-"+t+'" onchange="tvc_changedOutput('+e+", "+t+", '"+i+'\')"> <option value="select" itemprop="basic">-- '+tvc_feed_settings_form_vars.select_a_source_field+" --</option>"+s+'<option value="static" itemprop="basic"'+r+">"+tvc_feed_settings_form_vars.fill_with_static_value+"</option>"+u+c+tvc_fixedSourcesList(p)+"</select></div>"}function tvc_combinedInputFieldCntrl(e,t,p,n,i,o){var a=n&&n.startsWith("static#"),s=a?" selected":"",r=a?tvc_feedStaticValueSelector(i,e,t,p,n.substring(7),o):"";return'<select class="select-control input-select align-left" id="combined-input-field-cntrl-'+e+"-"+t+"-"+p+'" onchange="tvc_changedCombinedOutput('+e+", "+t+", "+p+')"> <option value="select" itemprop="basic">-- '+tvc_feed_settings_form_vars.select_a_source_field+' --</option><option value="static" itemprop="basic"'+s+">"+tvc_feed_settings_form_vars.fill_with_static_value+"</option>"+tvc_fixedSourcesList(n)+'</select><div class="static-value-control" id="static-value-control-'+e+"-"+t+"-"+p+'">'+r+"</div>"}function tvc_combinedSeparatorCntrl(e,t,p,n){return'<select class="select-control input-select align-left" id="combined-separator-cntrl-'+e+"-"+t+"-"+p+'" onchange="tvc_changedCombinationSeparator('+e+", "+t+", "+p+')"> '+tvc_getCombinedSeparatorList(n)+"</select>"}function tvc_alternativeInputFieldCntrl(e,t){var p="static"===t?" selected":"";return'<select class="select-control alternative-input-select" id="alternative-input-field-cntrl-'+e+'" onchange="tvc_changedAlternativeSource('+e+')"> <option value="select">-- '+tvc_feed_settings_form_vars.select_a_source_field+' --</option><option value="empty">-- '+tvc_feed_settings_form_vars.an_empty_field+' --</option><option value="static"'+p+">"+tvc_feed_settings_form_vars.fill_with_static_value+"</option>"+tvc_fixedSourcesList(t)+"</select>"}function tvc_outputFieldCntrl(e){return'<select class="select-control input-select" id="output-field-cntrl-'+e+'"> '+(3===e?'<option value="no-value">-- '+tvc_feed_settings_form_vars.add_recommended_output+" --</option>":'<option value="no-value">-- '+tvc_feed_settings_form_vars.add_optional_output+" --</option>")+tvc_getOutputFieldsList(e)+"</select>"}function tvc_customOutputFieldCntrl(){return'<input type="text" name="custom-output-title" id="custom-output-title-input" placeholder="Enter an output title" onfocusout="tvc_changedCustomOutputTitle()">'}function tvc_conditionFieldCntrl(e,t,p,n,i,o,a){var s=-1!==n?"-"+n:"",r="or-field-cntrl"===i?'<option value="empty">-- '+tvc_feed_settings_form_vars.an_empty_field+" --</option>":"";return'<select class="select-control input-select" id="'+i+"-"+e+"-"+t+"-"+p+s+'"'+(a?' onchange="'+a+'"':"")+'> <option value="select">-- '+tvc_feed_settings_form_vars.select_a_source_field+" --</option>"+r+tvc_fixedSourcesList(o)+"</select></br>"}function tvc_filterPreCntrl(e,t,p){var n='<select id="filter-pre-control-'+e+"-"+t+'" onchange="tvc_filterChanged('+e+", "+t+')">';return t>1?"1"===p?n+'<option value="2">'+tvc_feed_settings_form_vars.or+'</option><option value="1" selected>'+tvc_feed_settings_form_vars.and+"</option></select>":n+'<option value="2" selected>'+tvc_feed_settings_form_vars.or+'</option><option value="1">'+tvc_feed_settings_form_vars.and+"</option></select>":""}function tvc_filterSourceCntrl(e,t,p){return'<select class="select-control input-select" id="filter-source-control-'+e+"-"+t+'" onchange="tvc_filterChanged('+e+", "+t+')"><option value="select">-- '+tvc_feed_settings_form_vars.select_a_source_field+" --</option>"+tvc_fixedSourcesList(p)+"</select>"}function tvc_filterOptionsCntrl(e,t,p){var n=tvc_queryOptionsEng(),i='<select class="select-control condition-query-select" id="filter-options-control-'+e+"-"+t;i+='" onchange="tvc_filterChanged('+e+", "+t+')">';for(var o=0;o<n.length;o++)i+=parseInt(p)!==o?'<option value = "'+o+'">'+n[o]+"</option>":'<option value = "'+o+'" selected>'+n[o]+"</option>";return i+="</select>"}function tvc_filterInputCntrl(e,t,p,n){var i=e+"-"+t+"-"+p,o=p>1?" "+tvc_feed_settings_form_vars.and+" ":"",a=1===p?1:3,s="";return'<span id="filter-input-span-'+i+'"'+((s=p>1?n&&n.includes("#")?n.split("#")[a]:"":n||"")?'style="display:initial"':'style="display:none"')+">"+o+'<input type="text" name="filter-value" id="filter-input-control-'+i+'" onchange="tvc_filterChanged('+e+", "+t+", "+p+')" value="'+s+'"></span>'}
 
includes/user-interface/js/tvc_feed-list.js DELETED
@@ -1,284 +0,0 @@
1
- "use strict";
2
- /*global tvc_feed_list_form_vars */
3
- function tvc_fillFeedList() {
4
- var listHtml = '';
5
- var feedListSelector = jQuery( '#tvc-feed-list' );
6
-
7
- tvc_getFeedList(
8
- function( result ) {
9
- var feedList = JSON.parse( result );
10
- var list = feedList[ 'list' ];
11
- var specialFeedAddOnsActive = feedList[ 'special_feed_add_ons_active' ];
12
-
13
- if ( '0' !== list ) {
14
- // convert the data to html code
15
- listHtml = tvc_feedListTable( list, specialFeedAddOnsActive );
16
- } else {
17
- listHtml = tvc_emptyListTable();
18
- }
19
-
20
- feedListSelector.empty(); // first clear the feed list
21
-
22
- feedListSelector.append( listHtml );
23
-
24
- console.log( 'Feed List refreshed' );
25
-
26
- parent.location='admin.php?page=tvc-product-feed-manager&tab=feed-list';
27
- }
28
- );
29
- }
30
-
31
- function appendCategoryLists( channelId, language, isNew ) {
32
- var levelZeroSelector = jQuery( '#lvl_0' );
33
- var categoryLevelSelector = jQuery( '#category-selector-lvl' );
34
-
35
- if ( isNew ) {
36
- tvc_getCategoryListsFromString(
37
- channelId,
38
- '',
39
- language,
40
- function( categories ) {
41
-
42
- var list = JSON.parse( categories )[ 0 ];
43
-
44
- if ( list && list.length > 0 ) {
45
- levelZeroSelector.html( tvc_categorySelectCntrl( list ) );
46
- levelZeroSelector.prop( 'disabled', false );
47
- } else {
48
- // as the user selected a free format, just show a text input control
49
- categoryLevelSelector.html( tvc_freeCategoryInputCntrl( 'default', '0', false ) );
50
- categoryLevelSelector.prop( 'disabled', false );
51
- }
52
- }
53
- );
54
- }
55
- }
56
-
57
- function tvc_resetFeedList() {
58
- tvc_fillFeedList();
59
- }
60
-
61
- function tvc_resetFeedStatus( feedData ) {
62
- tvc_checkNextFeedInQueue(
63
- function() {
64
- tvc_updateFeedRowStatus( feedData[ 'product_feed_id' ], parseInt( feedData[ 'status_id' ] ) );
65
- tvc_updateFeedRowData( feedData );
66
- }
67
- );
68
- }
69
-
70
- function tvc_feedListTable( list, specialFeedAddOnsActive ) {
71
- var htmlCode = '';
72
-
73
- if ( ! list ) {
74
- return htmlCode;
75
- }
76
-
77
- for ( var i = 0; i < list.length; i ++ ) {
78
- var status = list [ i ] [ 'status' ];
79
- var feedId = list [ i ] [ 'product_feed_id' ];
80
- var feedUrl = list [ i ] [ 'url' ];
81
- var feedReady = 'on_hold' === status || 'ok' === status;
82
- var nrProducts = '';
83
- var statusString = tvc_list_status_text( status );
84
-
85
- if ( feedReady ) {
86
- nrProducts = list [ i ] [ 'products' ];
87
- } else if ( 'processing' === status ) {
88
- nrProducts = tvc_feed_list_form_vars.processing_the_feed;
89
- } else if ( 'failed_processing' === status || 'in_processing_queue' === status ) {
90
- nrProducts = tvc_feed_list_form_vars.unknown_text;
91
- }
92
-
93
- htmlCode += '<tr id="feed-row"';
94
-
95
- if ( i % 2 === 0 ) {
96
- htmlCode += ' class="alternate"';
97
- } // alternate background color per row
98
-
99
- htmlCode += '>';
100
- htmlCode += '<td id="title">' + list [ i ] [ 'title' ] + '</td>';
101
- htmlCode += '<td id="url">' + feedUrl + '</td>';
102
- htmlCode += '<td id="updated-' + feedId + '">' + list [ i ] [ 'updated' ] + '</td>';
103
- htmlCode += '<td id="products-' + feedId + '">' + nrProducts + '</td>';
104
- htmlCode += specialFeedAddOnsActive ? '<td id="type-' + feedId + '">' + list [ i ] [ 'feed_type_name' ] + '</td>' : '';
105
- htmlCode += '<td id="feed-status-' + feedId + '" value="' + status + '" style="color: ' + list [ i ] [ 'color' ] + '"><strong>';
106
- htmlCode += statusString;
107
- htmlCode += '</strong></td>';
108
- htmlCode += '<td id="actions-' + feedId + '">';
109
-
110
- if ( feedReady ) {
111
- htmlCode += feedReadyActions( feedId, feedUrl, status, list [ i ] [ 'title' ], list [ i ] [ 'feed_type_name' ] );
112
- } else {
113
- htmlCode += feedNotReadyActions( feedId, feedUrl, list [ i ] [ 'title' ], list [ i ] [ 'feed_type_name' ] );
114
- }
115
-
116
- htmlCode += '</td>';
117
- }
118
-
119
-
120
- return htmlCode;
121
- }
122
-
123
- function feedReadyActions( feedId, feedUrl, status, title, feedType ) {
124
- var fileExists = 'No feed generated' !== feedUrl;
125
- var fileName = feedUrl.lastIndexOf( '/' ) > 0 ? feedUrl.slice( feedUrl.lastIndexOf( '/' ) - feedUrl.length + 1 ) : title;
126
- var tabTitle = feedType.replace( / /g, '-' ).toLowerCase();
127
- var actionId = title.replace( / /g, '-' ).toLowerCase();
128
- var changeStatus = 'ok' === status ? tvc_feed_list_form_vars.list_deactivate : tvc_feed_list_form_vars.list_activate;
129
-
130
- var htmlCode = '<strong><a href="javascript:void(0);" id="tvc-edit-' + actionId + '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' + tabTitle + '&id=' + feedId + '\'">' + tvc_feed_list_form_vars.list_edit + ' </a>';
131
- htmlCode += fileExists ? ' | <a href="javascript:void(0);" id="tvc-view-' + actionId + '-action" onclick="tvc_viewFeed(\'' + feedUrl + '\')">' + tvc_feed_list_form_vars.list_view + '</a>' : '';
132
- htmlCode += ' | <a href="javascript:void(0);" id="tvc-delete-' + actionId + '-action" onclick="tvc_deleteSpecificFeed(' + feedId + ', \'' + fileName + '\')">' + tvc_feed_list_form_vars.list_delete + '</a>';
133
- htmlCode += fileExists ? '<a href="javascript:void(0);" id="tvc-deactivate-' + actionId + '-action" onclick="tvc_deactivateFeed(' + feedId + ')" id="feed-status-switch-' + feedId + '"> | ' + changeStatus + '</a>' : '';
134
- htmlCode += tvcEndOfActionsCode( feedId, actionId, feedType, title );
135
- return htmlCode;
136
- }
137
-
138
- function feedNotReadyActions( feedId, feedUrl, title, feedType ) {
139
- var fileName = feedUrl.lastIndexOf( '/' ) > 0 ? feedUrl.slice( feedUrl.lastIndexOf( '/' ) - feedUrl.length + 1 ) : title;
140
- var tabTitle = feedType.replace( / /g, '-' ).toLowerCase();
141
- var actionId = title.replace( / /g, '-' ).toLowerCase();
142
-
143
- var htmlCode = '<strong>';
144
- htmlCode += '<a href="javascript:void(0);" id="tvc-edit-' + actionId + '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' + tabTitle + '&id=' + feedId + '\'">' + tvc_feed_list_form_vars.list_edit + '</a>';
145
- htmlCode += ' | <a href="javascript:void(0);" id="tvc-delete-' + actionId + '-action" onclick="tvc_deleteSpecificFeed(' + feedId + ', \'' + fileName + '\')"> ' + tvc_feed_list_form_vars.list_delete + '</a>';
146
- htmlCode += tvcEndOfActionsCode( feedId, actionId, feedType, title );
147
- htmlCode += tvc_addFeedStatusChecker( feedId );
148
- return htmlCode;
149
- }
150
-
151
- function tvcEndOfActionsCode( feedId, actionId, feedType, title ) {
152
- var htmlCode = ' | <a href="javascript:void(0);" id="tvc-duplicate-' + actionId + '-action" onclick="tvc_duplicateFeed(' + feedId + ', \'' + title + '\')">' + tvc_feed_list_form_vars.list_duplicate + '</a>';
153
- htmlCode += 'Product Feed' === feedType ? ' | <a href="javascript:void(0);" id="tvc-regenerate-' + actionId + '-action" onclick="tvc_regenerateFeed(' + feedId + ')">' + tvc_feed_list_form_vars.list_regenerate + '</a>' : '';
154
- htmlCode += '</strong>';
155
-
156
- return htmlCode;
157
- }
158
-
159
- function tvc_emptyListTable() {
160
- var htmlCode = '';
161
-
162
- htmlCode += '<tr>';
163
- htmlCode += '<td colspan = 4>' + tvc_feed_list_form_vars.no_data_found + '</td>';
164
- htmlCode += '</tr>';
165
-
166
- return htmlCode;
167
- }
168
-
169
- function tvc_updateFeedRowData( rowData ) {
170
- if ( rowData[ 'status_id' ] === '1' || rowData[ 'status_id' ] === '2' ) {
171
- var feedId = rowData[ 'product_feed_id' ];
172
- var status = rowData[ 'status_id' ] === '1' ? tvc_feed_list_form_vars.ok : tvc_feed_list_form_vars.other;
173
-
174
- jQuery( '#updated-' + feedId ).html( rowData[ 'updated' ] );
175
- jQuery( '#products-' + feedId ).html( rowData[ 'products' ] );
176
- jQuery( '#actions-' + feedId ).html( feedReadyActions( feedId, rowData[ 'url' ], status, rowData[ 'title' ], rowData[ 'feed_type_name' ] ) );
177
- }
178
- }
179
-
180
- function tvc_switchStatusAction( feedId, status ) {
181
- var feedName = jQuery( '#title-' + feedId ).html();
182
- var actionText = '';
183
-
184
- feedName = feedName.replace(/\s+/g, '-').toLowerCase();
185
-
186
- switch ( status ) {
187
- case '1':
188
- actionText = ' | Auto-off ';
189
- break;
190
-
191
- case '2':
192
- actionText = ' | Auto-on ';
193
- break;
194
- }
195
-
196
- jQuery( '#tvc-deactivate-' + feedName + '-action' ).html( actionText );
197
- }
198
-
199
- function tvc_list_status_text( status ) {
200
- switch ( status ) {
201
- case 'unknown':
202
- return tvc_feed_list_form_vars.unknown;
203
-
204
- case 'ok':
205
- return tvc_feed_list_form_vars.status_ok;
206
-
207
- case 'on_hold':
208
- return tvc_feed_list_form_vars.on_hold;
209
-
210
- case 'processing':
211
- return tvc_feed_list_form_vars.processing;
212
-
213
- case 'in_processing_queue':
214
- return tvc_feed_list_form_vars.processing_queue;
215
-
216
- case 'has_errors':
217
- return tvc_feed_list_form_vars.has_errors;
218
-
219
- case 'failed_processing':
220
- return tvc_feed_list_form_vars.failed_processing;
221
- }
222
- }
223
-
224
- function tvc_updateFeedRowStatus( feedId, status ) {
225
- var feedStatusSelector = jQuery( '#feed-status-' + feedId );
226
- var feedStatusSwitchSelector = jQuery( '#feed-status-switch-' + feedId );
227
- var productsSelector = jQuery( '#products-' + feedId );
228
-
229
- switch ( status ) {
230
- case 0: // unknown
231
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.unknown + '</strong>' );
232
- feedStatusSelector.css( 'color', '#6549F7' );
233
- feedStatusSwitchSelector.html( '' );
234
- break;
235
-
236
- case 1: // OK
237
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.ok + '</strong>' );
238
- feedStatusSelector.css( 'color', '#0073AA' );
239
- feedStatusSwitchSelector.html( ' | ' + tvc_feed_list_form_vars.list_deactivate + ' ' );
240
- break;
241
-
242
- case 2: // On hold
243
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.on_hold + '</strong>' );
244
- feedStatusSelector.css( 'color', '#0173AA' );
245
- feedStatusSwitchSelector.html( ' | ' + tvc_feed_list_form_vars.list_activate + ' ' );
246
- break;
247
-
248
- case 3: // Processing
249
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.processing + '</strong>' );
250
- feedStatusSelector.css( 'color', '#0000FF' );
251
- feedStatusSwitchSelector.html( '' );
252
- productsSelector.html( tvc_feed_list_form_vars.processing_the_feed );
253
- break;
254
-
255
- case 4: // In queue
256
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.processing_queue + '</strong>' );
257
- feedStatusSelector.css( 'color', '#00CCFF' );
258
- feedStatusSwitchSelector.html( tvc_feed_list_form_vars.list_activate + ' ' );
259
- break;
260
-
261
- case 5: // Has errors
262
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.has_errors + '</strong>' );
263
- feedStatusSelector.css( 'color', '#FF0000' );
264
- productsSelector.html( tvc_feed_list_form_vars.unknown );
265
- feedStatusSwitchSelector.html( tvc_feed_list_form_vars.list_activate + ' ' );
266
- break;
267
-
268
- case 6: // Failed processing
269
- feedStatusSelector.html( '<strong>' + tvc_feed_list_form_vars.processing_failed + '</strong>' );
270
- feedStatusSelector.css( 'color', '#FF3300' );
271
- productsSelector.html( tvc_feed_list_form_vars.unknown );
272
- feedStatusSwitchSelector.html( '' );
273
- break;
274
- }
275
- }
276
-
277
- /**
278
- * Document ready actions
279
- */
280
- jQuery( document ).ready(
281
- function() {
282
- // No actions required at the moment.
283
- }
284
- );
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_feed-list.min.js DELETED
@@ -1,227 +0,0 @@
1
- function tvc_fillFeedList() {
2
- var a = "";
3
- var b = jQuery("#tvc-feed-list");
4
- tvc_getFeedList(function (c) {
5
- var d = JSON.parse(c);
6
- var e = d.list;
7
- var f = d.special_feed_add_ons_active;
8
- if ("0" !== e) {
9
- a = tvc_feedListTable(e, f)
10
- } else {
11
- a = tvc_emptyListTable()
12
- }
13
- b.empty();
14
- b.append(a);
15
- console.log("Feed List refreshed");
16
- parent.location='admin.php?page=tvc-product-feed-manager&tab=feed-list';
17
- })
18
- }
19
-
20
- function appendCategoryLists(d, e, a) {
21
- var b = jQuery("#lvl_0");
22
- var c = jQuery("#category-selector-lvl");
23
- if (a) {
24
- tvc_getCategoryListsFromString(d, "", e, function (f) {
25
- var g = JSON.parse(f)[0];
26
- if (g && g.length > 0) {
27
- b.html(tvc_categorySelectCntrl(g));
28
- b.prop("disabled", false)
29
- } else {
30
- c.html(tvc_freeCategoryInputCntrl("default", "0", false));
31
- c.prop("disabled", false)
32
- }
33
- })
34
- }
35
- }
36
-
37
- function tvc_resetFeedList() {
38
- tvc_fillFeedList()
39
- }
40
-
41
- function tvc_resetFeedStatus(a) {
42
- tvc_checkNextFeedInQueue(function () {
43
- tvc_updateFeedRowStatus(a.product_feed_id, parseInt(a.status_id));
44
- tvc_updateFeedRowData(a)
45
- })
46
- }
47
-
48
- function tvc_feedListTable(g, j) {
49
- var h = "";
50
- if (!g) {
51
- return h
52
- }
53
- for (var e = 0; e < g.length; e++) {
54
- var c = g[e]["status"];
55
- var b = g[e]["product_feed_id"];
56
- var f = g[e]["url"];
57
- var a = "on_hold" === c || "ok" === c;
58
- var k = "";
59
- var d = tvc_list_status_text(c);
60
- if (a) {
61
- k = g[e]["products"]
62
- } else {
63
- if ("processing" === c) {
64
- k = tvc_feed_list_form_vars.processing_the_feed
65
- } else {
66
- if ("failed_processing" === c || "in_processing_queue" === c) {
67
- k = tvc_feed_list_form_vars.unknown_text
68
- }
69
- }
70
- }
71
- h += '<tr id="feed-row"';
72
- if (e % 2 === 0) {
73
- h += ' class="alternate"'
74
- }
75
- h += ">";
76
- h += '<td id="title">' + g[e]["title"] + "</td>";
77
- h += '<td id="url">' + f + "</td>";
78
- h += '<td id="updated-' + b + '">' + g[e]["updated"] + "</td>";
79
- h += '<td id="products-' + b + '">' + k + "</td>";
80
- h += j ? '<td id="type-' + b + '">' + g[e]["feed_type_name"] + "</td>" : "";
81
- h += '<td id="feed-status-' + b + '" value="' + c + '" style="color: ' + g[e]["color"] + '"><strong>';
82
- h += d;
83
- h += "</strong></td>";
84
- h += '<td id="actions-' + b + '">';
85
- if (a) {
86
- h += feedReadyActions(b, f, c, g[e]["title"], g[e]["feed_type_name"])
87
- } else {
88
- h += feedNotReadyActions(b, f, g[e]["title"], g[e]["feed_type_name"])
89
- }
90
- h += "</td>"
91
- }
92
- return h
93
- }
94
-
95
- function feedReadyActions(b, f, e, k, j) {
96
- var h = "No feed generated" !== f;
97
- var c = f.lastIndexOf("/") > 0 ? f.slice(f.lastIndexOf("/") - f.length + 1) : k;
98
- var d = j.replace(/ /g, "-").toLowerCase();
99
- var a = k.replace(/ /g, "-").toLowerCase();
100
- var g = "ok" === e ? tvc_feed_list_form_vars.list_deactivate : tvc_feed_list_form_vars.list_activate;
101
- var i = '<strong><a href="javascript:void(0);" id="tvc-edit-' + a + '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' + d + "&id=" + b + "'\">" + tvc_feed_list_form_vars.list_edit + " </a>";
102
- i += h ? ' | <a href="javascript:void(0);" id="tvc-view-' + a + '-action" onclick="tvc_viewFeed(\'' + f + "')\">" + tvc_feed_list_form_vars.list_view + "</a>" : "";
103
- i += ' | <a href="javascript:void(0);" id="tvc-delete-' + a + '-action" onclick="tvc_deleteSpecificFeed(' + b + ", '" + c + "')\">" + tvc_feed_list_form_vars.list_delete + "</a>";
104
- i += h ? '<a href="javascript:void(0);" id="tvc-deactivate-' + a + '-action" onclick="tvc_deactivateFeed(' + b + ')" id="feed-status-switch-' + b + '"> | ' + g + "</a>" : "";
105
- i += tvcEndOfActionsCode(b, a, j, k);
106
- return i
107
- }
108
-
109
- function feedNotReadyActions(b, h, e, a) {
110
- var g = h.lastIndexOf("/") > 0 ? h.slice(h.lastIndexOf("/") - h.length + 1) : e;
111
- var c = a.replace(/ /g, "-").toLowerCase();
112
- var f = e.replace(/ /g, "-").toLowerCase();
113
- var d = "<strong>";
114
- d += '<a href="javascript:void(0);" id="tvc-edit-' + f + '-action" onclick="parent.location=\'admin.php?page=tvc-product-feed-manager&tab=' + c + "&id=" + b + "'\">" + tvc_feed_list_form_vars.list_edit + "</a>";
115
- d += ' | <a href="javascript:void(0);" id="tvc-delete-' + f + '-action" onclick="tvc_deleteSpecificFeed(' + b + ", '" + g + "')\"> " + tvc_feed_list_form_vars.list_delete + "</a>";
116
- d += tvcEndOfActionsCode(b, f, a, e);
117
- d += tvc_addFeedStatusChecker(b);
118
- return d
119
- }
120
-
121
- function tvcEndOfActionsCode(b, e, a, d) {
122
- var c = ' | <a href="javascript:void(0);" id="tvc-duplicate-' + e + '-action" onclick="tvc_duplicateFeed(' + b + ", '" + d + "')\">" + tvc_feed_list_form_vars.list_duplicate + "</a>";
123
- c += "Product Feed" === a ? ' | <a href="javascript:void(0);" id="tvc-regenerate-' + e + '-action" onclick="tvc_regenerateFeed(' + b + ')">' + tvc_feed_list_form_vars.list_regenerate + "</a>" : "";
124
- c += "</strong>";
125
- return c
126
- }
127
-
128
- function tvc_emptyListTable() {
129
- var a = "";
130
- a += "<tr>";
131
- a += "<td colspan = 4>" + tvc_feed_list_form_vars.no_data_found + "</td>";
132
- a += "</tr>";
133
- return a
134
- }
135
-
136
- function tvc_updateFeedRowData(c) {
137
- if (c.status_id === "1" || c.status_id === "2") {
138
- var b = c.product_feed_id;
139
- var a = c.status_id === "1" ? tvc_feed_list_form_vars.ok : tvc_feed_list_form_vars.other;
140
- jQuery("#updated-" + b).html(c.updated);
141
- jQuery("#products-" + b).html(c.products);
142
- jQuery("#actions-" + b).html(feedReadyActions(b, c.url, a, c.title, c.feed_type_name))
143
- }
144
- }
145
-
146
- function tvc_switchStatusAction(b, a) {
147
- var d = jQuery("#title-" + b).html();
148
- var c = "";
149
- d = d.replace(/\s+/g, "-").toLowerCase();
150
- switch (a) {
151
- case"1":
152
- c = " | Auto-off ";
153
- break;
154
- case"2":
155
- c = " | Auto-on ";
156
- break
157
- }
158
- jQuery("#tvc-deactivate-" + d + "-action").html(c)
159
- }
160
-
161
- function tvc_list_status_text(a) {
162
- switch (a) {
163
- case"unknown":
164
- return tvc_feed_list_form_vars.unknown;
165
- case"ok":
166
- return tvc_feed_list_form_vars.status_ok;
167
- case"on_hold":
168
- return tvc_feed_list_form_vars.on_hold;
169
- case"processing":
170
- return tvc_feed_list_form_vars.processing;
171
- case"in_processing_queue":
172
- return tvc_feed_list_form_vars.processing_queue;
173
- case"has_errors":
174
- return tvc_feed_list_form_vars.has_errors;
175
- case"failed_processing":
176
- return tvc_feed_list_form_vars.failed_processing
177
- }
178
- }
179
-
180
- function tvc_updateFeedRowStatus(c, b) {
181
- var a = jQuery("#feed-status-" + c);
182
- var e = jQuery("#feed-status-switch-" + c);
183
- var d = jQuery("#products-" + c);
184
- switch (b) {
185
- case 0:
186
- a.html("<strong>" + tvc_feed_list_form_vars.unknown + "</strong>");
187
- a.css("color", "#6549F7");
188
- e.html("");
189
- break;
190
- case 1:
191
- a.html("<strong>" + tvc_feed_list_form_vars.ok + "</strong>");
192
- a.css("color", "#0073AA");
193
- e.html(" | " + tvc_feed_list_form_vars.list_deactivate + " ");
194
- break;
195
- case 2:
196
- a.html("<strong>" + tvc_feed_list_form_vars.on_hold + "</strong>");
197
- a.css("color", "#0173AA");
198
- e.html(" | " + tvc_feed_list_form_vars.list_activate + " ");
199
- break;
200
- case 3:
201
- a.html("<strong>" + tvc_feed_list_form_vars.processing + "</strong>");
202
- a.css("color", "#0000FF");
203
- e.html("");
204
- d.html(tvc_feed_list_form_vars.processing_the_feed);
205
- break;
206
- case 4:
207
- a.html("<strong>" + tvc_feed_list_form_vars.processing_queue + "</strong>");
208
- a.css("color", "#00CCFF");
209
- e.html(tvc_feed_list_form_vars.list_activate + " ");
210
- break;
211
- case 5:
212
- a.html("<strong>" + tvc_feed_list_form_vars.has_errors + "</strong>");
213
- a.css("color", "#FF0000");
214
- d.html(tvc_feed_list_form_vars.unknown);
215
- e.html(tvc_feed_list_form_vars.list_activate + " ");
216
- break;
217
- case 6:
218
- a.html("<strong>" + tvc_feed_list_form_vars.processing_failed + "</strong>");
219
- a.css("color", "#FF3300");
220
- d.html(tvc_feed_list_form_vars.unknown);
221
- e.html("");
222
- break
223
- }
224
- }
225
-
226
- jQuery(document).ready(function () {
227
- });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_msg_events.js DELETED
@@ -1,27 +0,0 @@
1
- "use strict";
2
- //shorthand for ready event.
3
- jQuery( function() {
4
- jQuery( 'div[data-dismissible] button.notice-dismiss' ).on("click",
5
- function( event ) {
6
- event.preventDefault();
7
- var $this = jQuery( this );
8
-
9
- var attr_value, option_name, dismissible_length, data;
10
-
11
- attr_value = $this.parent().attr( 'data-dismissible' ).split( '-' );
12
-
13
- // remove the dismissible length from the attribute value and rejoin the array.
14
- dismissible_length = attr_value.pop();
15
-
16
- option_name = attr_value.join( '-' );
17
-
18
- data = {
19
- 'action': 'dismiss_admin_notice',
20
- 'option_name': option_name,
21
- 'dismissible_length': dismissible_length,
22
- };
23
-
24
- // We can also pass the url value separately from ajaxurl for front end AJAX implementations
25
- jQuery.post( ajaxurl, data );
26
- }
27
- ); });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_msg_events.min.js DELETED
@@ -1 +0,0 @@
1
- (function(a){a(function(){a("div[data-dismissible] button.notice-dismiss").on("click",function(c){c.preventDefault();var e=a(this);var b,g,f,d;b=e.parent().attr("data-dismissible").split("-");f=b.pop();g=b.join("-");d={action:"dismiss_admin_notice",option_name:g,dismissible_length:f};a.post(ajaxurl,d)})})}(jQuery));
 
includes/user-interface/js/tvc_setting-form.js DELETED
@@ -1,150 +0,0 @@
1
- "use strict";
2
- /*global tvc_setting_form_vars */
3
- function tvc_auto_feed_fix_changed() {
4
- tvc_auto_feed_fix_mode(
5
- jQuery( '#tvc_auto_feed_fix_mode' ).is( ':checked' ),
6
- function( response ) {
7
- console.log( 'Auto feed fix setting changed to ' + response );
8
- }
9
- );
10
- }
11
-
12
- function tvc_background_processing_mode_changed() {
13
- tvc_background_processing_mode(
14
- jQuery( '#tvc_background_processing_mode' ).is( ':checked' ),
15
- function( response ) {
16
- console.log( 'Background processing setting changed to ' + response );
17
- }
18
- );
19
- }
20
-
21
- function tvc_feed_logger_status_changed() {
22
- tvc_feed_logger_status(
23
- jQuery( '#tvc_process_logging_mode' ).is( ':checked' ),
24
- function( response ) {
25
- console.log( 'Feed process logger status changed to ' + response );
26
- }
27
- );
28
- }
29
-
30
- function tvc_show_product_identifiers_changed() {
31
- tvc_show_pi_status(
32
- jQuery( '#tvc_product_identifiers' ).is( ':checked' ),
33
- function( response ) {
34
- console.log( 'Show Product Identifiers setting changed to ' + response );
35
- }
36
- );
37
- }
38
-
39
- function tvc_third_party_attributes_changed() {
40
- tvc_change_third_party_attribute_keywords(
41
- jQuery( '#tvc_third_party_attr_keys' ).val(),
42
- function( response ) {
43
- console.log( 'Third party attributes changed to ' + response );
44
- }
45
- );
46
- }
47
-
48
- function tvc_notice_mailaddress_changed() {
49
- tvc_change_notice_mailaddress(
50
- jQuery( '#tvc_notice_mailaddress' ).val(),
51
- function( response ) {
52
- console.log( 'Notice recipient setting changed to ' + response );
53
- }
54
- );
55
- }
56
-
57
- function tvc_clear_feed_process() {
58
- tvc_showFeedSpinner();
59
- tvc_clear_feed_process_data(
60
- function( response ) {
61
- console.log( 'Clear feed process activated' );
62
- tvc_hideFeedSpinner();
63
- }
64
- );
65
- }
66
-
67
- function tvc_reinitiate() {
68
- tvc_showFeedSpinner();
69
- tvc_reinitiate_plugin(
70
- function( response ) {
71
- console.log( 'Re-initialization initiated ' + response );
72
- tvc_hideFeedSpinner();
73
- }
74
- );
75
- }
76
-
77
- function tvc_backup() {
78
- var backupFileNameElement = jQuery( '#tvc_backup-file-name' );
79
-
80
- if ( backupFileNameElement.val() !== '' ) {
81
- jQuery( '#tvc_backup-wrapper' ).hide();
82
-
83
- tvc_initiateBackup(
84
- backupFileNameElement.val(),
85
- function( response ) {
86
- tvc_resetBackupsList();
87
-
88
- if ( response !== '1' ) {
89
- tvc_show_error_message( 'New backup file made ' + response );
90
- }
91
- }
92
- );
93
- } else {
94
- alert( tvc_setting_form_vars.first_enter_file_name );
95
- }
96
- }
97
-
98
- function tvc_deleteBackupFile( fileName ) {
99
- var userInput = confirm( tvc_setting_form_vars.confirm_file_deletion.replace( '%backup_file_name%', fileName ) );
100
-
101
- if ( userInput === true ) {
102
- tvc_deleteBackup(
103
- fileName,
104
- function( response ) {
105
- tvc_show_success_message( tvc_setting_form_vars.file_deleted.replace( '%backup_file_name%', fileName ) );
106
- tvc_resetBackupsList();
107
- console.log( 'Backup file deleted ' + response );
108
- }
109
- );
110
- }
111
- }
112
-
113
- function tvc_restoreBackupFile( fileName ) {
114
-
115
- var userInput = confirm( tvc_setting_form_vars.confirm_file_restoring.replace( '%backup_file_name%', fileName ) );
116
-
117
- if ( userInput === true ) {
118
-
119
- tvc_restoreBackup(
120
- fileName,
121
- function( response ) {
122
-
123
- if ( response === '1' ) {
124
- tvc_show_success_message( tvc_setting_form_vars.file_restored.replace( '%backup_file_name%', fileName ) );
125
- tvc_resetOptionSettings();
126
- console.log( 'Backup file restored ' + response );
127
- } else {
128
- tvc_show_error_message( response );
129
- }
130
- }
131
- );
132
- }
133
- }
134
-
135
- function tvc_duplicateBackupFile( fileName ) {
136
-
137
- tvc_duplicateBackup(
138
- fileName,
139
- function( response ) {
140
-
141
- if ( response === '1' ) {
142
- tvc_show_success_message( tvc_setting_form_vars.file_duplicated.replace( '%backup_file_name%', fileName ) );
143
- console.log( 'Backup file duplicated' + response );
144
- } else {
145
- tvc_show_error_message( response );
146
- }
147
- tvc_resetBackupsList();
148
- }
149
- );
150
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_setting-form.min.js DELETED
@@ -1 +0,0 @@
1
- function tvc_auto_feed_fix_changed(){tvc_auto_feed_fix_mode(jQuery("#tvc_auto_feed_fix_mode").is(":checked"),function(a){console.log("Auto feed fix setting changed to "+a)})}function tvc_background_processing_mode_changed(){tvc_background_processing_mode(jQuery("#tvc_background_processing_mode").is(":checked"),function(a){console.log("Background processing setting changed to "+a)})}function tvc_feed_logger_status_changed(){tvc_feed_logger_status(jQuery("#tvc_process_logging_mode").is(":checked"),function(a){console.log("Feed process logger status changed to "+a)})}function tvc_show_product_identifiers_changed(){tvc_show_pi_status(jQuery("#tvc_product_identifiers").is(":checked"),function(a){console.log("Show Product Identifiers setting changed to "+a)})}function tvc_third_party_attributes_changed(){tvc_change_third_party_attribute_keywords(jQuery("#tvc_third_party_attr_keys").val(),function(a){console.log("Third party attributes changed to "+a)})}function tvc_notice_mailaddress_changed(){tvc_change_notice_mailaddress(jQuery("#tvc_notice_mailaddress").val(),function(a){console.log("Notice recipient setting changed to "+a)})}function tvc_clear_feed_process(){tvc_showFeedSpinner();tvc_clear_feed_process_data(function(a){console.log("Clear feed process activated");tvc_hideFeedSpinner()})}function tvc_reinitiate(){tvc_showFeedSpinner();tvc_reinitiate_plugin(function(a){console.log("Re-initialization initiated "+a);tvc_hideFeedSpinner()})}function tvc_backup(){var a=jQuery("#tvc_backup-file-name");if(a.val()!==""){jQuery("#tvc_backup-wrapper").hide();tvc_initiateBackup(a.val(),function(b){tvc_resetBackupsList();if(b!=="1"){tvc_show_error_message("New backup file made "+b)}})}else{alert(tvc_setting_form_vars.first_enter_file_name)}}function tvc_deleteBackupFile(b){var a=confirm(tvc_setting_form_vars.confirm_file_deletion.replace("%backup_file_name%",b));if(a===true){tvc_deleteBackup(b,function(c){tvc_show_success_message(tvc_setting_form_vars.file_deleted.replace("%backup_file_name%",b));tvc_resetBackupsList();console.log("Backup file deleted "+c)})}}function tvc_restoreBackupFile(b){var a=confirm(tvc_setting_form_vars.confirm_file_restoring.replace("%backup_file_name%",b));if(a===true){tvc_restoreBackup(b,function(c){if(c==="1"){tvc_show_success_message(tvc_setting_form_vars.file_restored.replace("%backup_file_name%",b));tvc_resetOptionSettings();console.log("Backup file restored "+c)}else{tvc_show_error_message(c)}})}}function tvc_duplicateBackupFile(a){tvc_duplicateBackup(a,function(b){if(b==="1"){tvc_show_success_message(tvc_setting_form_vars.file_duplicated.replace("%backup_file_name%",a));console.log("Backup file duplicated"+b)}else{tvc_show_error_message(b)}tvc_resetBackupsList()})};
 
includes/user-interface/js/tvc_support.js DELETED
@@ -1,261 +0,0 @@
1
- "use strict";
2
- function tvc_activateFeedCategoryMapping( id ) {
3
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
4
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
5
-
6
- feedSelectorElement.prop( 'checked', true );
7
-
8
- tvc_activateFeedCategorySelector( id );
9
-
10
- for ( var i = 0; i < children.length; i ++ ) {
11
- tvc_activateFeedCategorySelector( children[ i ] );
12
- }
13
- }
14
-
15
- function tvc_activateFeedCategorySelection( id ) {
16
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
17
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
18
-
19
- feedSelectorElement.prop( 'checked', true );
20
-
21
- _feedHolder.activateCategory( id, true );
22
-
23
- for ( var i = 0; i < children.length; i ++ ) {
24
- tvc_activateFeedCategorySelection( children[ i ] );
25
- }
26
- }
27
-
28
- function tvc_activateAllFeedCategoryMapping() {
29
- var tableType = 0 !== document.getElementsByClassName( 'tvc-category-mapping-selector' ).length ? 'category_mapping_table' : 'category_selection_table';
30
- var idCollection = 'category_mapping_table' === tableType
31
- ? document.getElementsByClassName( 'tvc-category-mapping-selector' ) // category mapping table
32
- : document.getElementsByClassName( 'tvc-category-selector' ); // category selection table
33
-
34
- for ( var j = 0; j < idCollection.length; j ++ ) {
35
- if ( 'category_mapping_table' === tableType ) {
36
- tvc_activateFeedCategorySelector(idCollection[ j ].value);
37
- } else {
38
- tvc_activateFeedCategorySelection(idCollection[ j ].value);
39
- }
40
- }
41
- }
42
-
43
- function tvc_activateFeedCategorySelector( id ) {
44
-
45
- // some channels use your own shop's categories
46
- var usesOwnCategories = tvc_channelUsesOwnCategories( _feedHolder[ 'channel' ] );
47
- var feedCategoryText = usesOwnCategories ? 'shopCategory' : 'default';
48
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
49
- var feedCategoryElement = jQuery( '#feed-category-' + id );
50
-
51
- // activate the category in the feedHolder
52
- _feedHolder.activateCategory( id, usesOwnCategories );
53
-
54
- // get the children of this selector if any
55
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
56
-
57
- if ( feedCategoryElement.html() === '' ) {
58
- feedCategoryElement.html( tvc_mapToDefaultCategoryElement( id, feedCategoryText ) );
59
- }
60
-
61
- feedSelectorElement.prop( 'checked', true );
62
-
63
- for ( var i = 0; i < children.length; i ++ ) {
64
- tvc_activateFeedCategorySelector( children[ i ] );
65
- }
66
- }
67
-
68
- function tvc_deactivateFeedCategorySelection( id ) {
69
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
70
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
71
-
72
- feedSelectorElement.prop( 'checked', false );
73
-
74
- _feedHolder.deactivateCategory( id );
75
-
76
- for ( var i = 0; i < children.length; i ++ ) {
77
- tvc_deactivateFeedCategorySelection( children[ i ] );
78
- }
79
- }
80
-
81
- function tvc_deactivateFeedCategoryMapping( id ) {
82
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
83
-
84
- tvc_deactivateFeedCategorySelector( id, true );
85
-
86
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
87
-
88
- for ( var i = 0; i < children.length; i ++ ) {
89
- tvc_deactivateFeedCategorySelector( children[ i ], false );
90
- }
91
- }
92
-
93
- function tvc_deactivateAllFeedCategoryMapping() {
94
- var idCollection = 0 !== document.getElementsByClassName( 'tvc-category-mapping-selector' ).length
95
- ? document.getElementsByClassName( 'tvc-category-mapping-selector' ) // category mapping table
96
- : document.getElementsByClassName( 'tvc-category-selector' ); // category selection table
97
-
98
- for ( var j = 0; j < idCollection.length; j ++ ) {
99
- tvc_deactivateFeedCategorySelector( idCollection[j].value );
100
- }
101
- }
102
-
103
- function tvc_contains_special_characters( string ) {
104
- var specialChars = '%^#<>{}[]\/~`@?:;=&';
105
-
106
- for ( var i = 0; i < specialChars.length; i ++ ) {
107
- if ( string.indexOf( specialChars[ i ] ) > - 1 ) {
108
- return true;
109
- }
110
- }
111
-
112
- return false;
113
- }
114
-
115
- function tvc_feedFileNameExists( fileName ) {
116
- console.log(fileName);
117
-
118
- return false;
119
- }
120
-
121
- function tvc_deactivateFeedCategorySelector( id, parent ) {
122
- var feedSelectorElement = jQuery( '#feed-selector-' + id );
123
-
124
- _feedHolder.deactivateCategory( id );
125
-
126
- jQuery( '#feed-category-' + id ).html( '' );
127
- jQuery( '#category-selector-catmap-' + id ).hide();
128
-
129
- feedSelectorElement.prop( 'checked', false );
130
-
131
- if ( ! parent ) {
132
- var children = feedSelectorElement.attr( 'data-children' ) ? JSON.parse( feedSelectorElement.attr( 'data-children' ) ) : [];
133
- for ( var i = 0; i < children.length; i ++ ) {
134
- tvc_deactivateFeedCategorySelector( children[ i ], false );
135
- }
136
- }
137
- }
138
-
139
- /**
140
- * Shows and hides the category sub level selectors depending on the selected level
141
- *
142
- * @param {string} currentLevelId
143
- */
144
- function tvc_hideSubs( currentLevelId ) {
145
-
146
- // identify the level from the level id
147
- var level = currentLevelId.match( /(\d+)$/ )[ 0 ];
148
- var idString = currentLevelId.substring( 0, currentLevelId.length - level.length );
149
-
150
- // only show sub fields that are at or before the selected level. Hide the rest
151
- for ( var i = 7; i > level; i -- ) {
152
- var categorySubLevelSelector = jQuery( '#' + idString + i );
153
- categorySubLevelSelector.css( 'display', 'none' );
154
- categorySubLevelSelector.empty();
155
- }
156
- }
157
-
158
- /**
159
- * Replaces special html characters to HTML entities.
160
- *
161
- * @param text
162
- * @returns {string}
163
- */
164
- function tvc_escapeHtml( text ) {
165
- text = text || '';
166
- text = text.replace( /&([^#])(?![a-z1-4]{1,8};)/gi, '&#038;$1' );
167
- return text.replace( /</g, '&lt;' ).replace( />/g, '&gt;' ).replace( /"/g, '&quot;' ).replace( /'/g, '&#039;' );
168
- }
169
-
170
- /**
171
- * Takes a field string from a source input string and splits it up even when a pipe character
172
- * is used in a combined source input string
173
- *
174
- * @since 2.3.0
175
- * @param {string} fieldString
176
- * @returns {array}
177
- */
178
- function tvc_splitCombinedFieldElements( fieldString ) {
179
- if ( ! fieldString ) {
180
- return [];
181
- }
182
-
183
- var reg = /\|[0-9]/; // pipe splitter plus a number directly after it
184
- var result = [];
185
- var sliceStart = 0;
186
- var match;
187
-
188
- // fetch the separate field strings and put them in the result array
189
- while (( match = reg.exec(fieldString) ) !== null) {
190
- var ind = match.index;
191
- result.push(fieldString.substring(sliceStart, ind));
192
- fieldString = fieldString.slice(ind + 1);
193
- }
194
-
195
- // then add the final field string to the result array
196
- result.push( fieldString );
197
-
198
- return result;
199
- }
200
-
201
- function tvc_showFeedSpinner() {
202
- jQuery( '#feed-spinner' ).show();
203
- jQuery( 'body' ).css( 'cursor', 'wait' );
204
- }
205
-
206
- function tvc_hideFeedSpinner() {
207
- jQuery( '#feed-spinner' ).hide();
208
- jQuery( 'body' ).css( 'cursor', 'default' );
209
- }
210
-
211
- function tvc_enableFeedActionButtons() {
212
- // enable the Generate and Save button
213
- jQuery( '[name=generate-top]' ).prop( 'disabled', false );
214
- jQuery( '[name=generate-bottom]' ).prop( 'disabled', false );
215
- jQuery( '[name=save-top]' ).prop( 'disabled', false );
216
- jQuery( '[name=save-bottom]' ).prop( 'disabled', false );
217
- jQuery( '[name=new]' ).prop( 'disabled', false );
218
- jQuery( '[name=view-top]' ).prop( 'disabled', false );
219
-
220
- if ( '' !== jQuery( '#tvc-feed-url' ).text() ) {
221
- tvc_enableViewFeedButtons();
222
- }
223
- }
224
-
225
- function disableFeedActionButtons() {
226
- // keep the Generate and Save buttons disabled
227
- jQuery( '[name=generate-top]' ).prop( 'disabled', true );
228
- jQuery( '[name=generate-bottom]' ).prop( 'disabled', true );
229
- jQuery( '[name=save-top]' ).prop( 'disabled', true );
230
- jQuery( '[name=save-bottom]' ).prop( 'disabled', true );
231
- jQuery( '[name=new]' ).prop( 'disabled', true );
232
- tvc_disableViewFeedButtons();
233
- }
234
-
235
- function tvc_enableViewFeedButtons() {
236
- jQuery('[name=view-top]').prop('disabled', false);
237
- jQuery('[name=view-bottom]').prop('disabled', false);
238
- jQuery( '[name=new]' ).prop( 'disabled', false );
239
- jQuery( '[name=open-bottom]' ).prop( 'disabled', false );
240
- }
241
-
242
- function tvc_disableViewFeedButtons() {
243
- jQuery( '[name=view-top]' ).prop( 'disabled', true );
244
- jQuery( '[name=view-bottom]' ).prop( 'disabled', true );
245
- jQuery( '[name=new]' ).prop( 'disabled', true );
246
- jQuery( '[name=open-bottom]' ).prop( 'disabled', true );
247
- }
248
-
249
- function tvc_show_error_message( message ) {
250
- var errorMessageSelector = jQuery( '#error-message' );
251
- errorMessageSelector.empty();
252
- errorMessageSelector.append( '<p>' + message + '</p>' );
253
- errorMessageSelector.show();
254
- }
255
-
256
- function tvc_show_success_message( message ) {
257
- var successMessageSelector = jQuery( '#success-message' );
258
- successMessageSelector.empty();
259
- successMessageSelector.append( '<p>' + message + '</p>' );
260
- successMessageSelector.show();
261
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_support.min.js DELETED
@@ -1,192 +0,0 @@
1
- function tvc_activateFeedCategoryMapping(d) {
2
- var c = jQuery("#feed-selector-" + d);
3
- var b = c.attr("data-children") ? JSON.parse(c.attr("data-children")) : [];
4
- c.prop("checked", true);
5
- tvc_activateFeedCategorySelector(d);
6
- for (var a = 0; a < b.length; a++) {
7
- tvc_activateFeedCategorySelector(b[a])
8
- }
9
- }
10
-
11
- function tvc_activateFeedCategorySelection(d) {
12
- var c = jQuery("#feed-selector-" + d);
13
- var b = c.attr("data-children") ? JSON.parse(c.attr("data-children")) : [];
14
- c.prop("checked", true);
15
- _feedHolder.activateCategory(d, true);
16
- for (var a = 0; a < b.length; a++) {
17
- tvc_activateFeedCategorySelection(b[a])
18
- }
19
- }
20
-
21
- function tvc_activateAllFeedCategoryMapping() {
22
- var b = 0 !== document.getElementsByClassName("tvc-category-mapping-selector").length ? "category_mapping_table" : "category_selection_table";
23
- var c = "category_mapping_table" === b ? document.getElementsByClassName("tvc-category-mapping-selector") : document.getElementsByClassName("tvc-category-selector");
24
- for (var a = 0; a < c.length; a++) {
25
- if ("category_mapping_table" === b) {
26
- tvc_activateFeedCategorySelector(c[a].value)
27
- } else {
28
- tvc_activateFeedCategorySelection(c[a].value)
29
- }
30
- }
31
- }
32
-
33
- function tvc_activateFeedCategorySelector(g) {
34
- var a = tvc_channelUsesOwnCategories(_feedHolder.channel);
35
- var b = a ? "shopCategory" : "default";
36
- var f = jQuery("#feed-selector-" + g);
37
- var e = jQuery("#feed-category-" + g);
38
- _feedHolder.activateCategory(g, a);
39
- var d = f.attr("data-children") ? JSON.parse(f.attr("data-children")) : [];
40
- if (e.html() === "") {
41
- e.html(tvc_mapToDefaultCategoryElement(g, b))
42
- }
43
- f.prop("checked", true);
44
- for (var c = 0; c < d.length; c++) {
45
- tvc_activateFeedCategorySelector(d[c])
46
- }
47
- }
48
-
49
- function tvc_deactivateFeedCategorySelection(d) {
50
- var c = jQuery("#feed-selector-" + d);
51
- var b = c.attr("data-children") ? JSON.parse(c.attr("data-children")) : [];
52
- c.prop("checked", false);
53
- _feedHolder.deactivateCategory(d);
54
- for (var a = 0; a < b.length; a++) {
55
- tvc_deactivateFeedCategorySelection(b[a])
56
- }
57
- }
58
-
59
- function tvc_deactivateFeedCategoryMapping(d) {
60
- var c = jQuery("#feed-selector-" + d);
61
- tvc_deactivateFeedCategorySelector(d, true);
62
- var b = c.attr("data-children") ? JSON.parse(c.attr("data-children")) : [];
63
- for (var a = 0; a < b.length; a++) {
64
- tvc_deactivateFeedCategorySelector(b[a], false)
65
- }
66
- }
67
-
68
- function tvc_deactivateAllFeedCategoryMapping() {
69
- var b = 0 !== document.getElementsByClassName("tvc-category-mapping-selector").length ? document.getElementsByClassName("tvc-category-mapping-selector") : document.getElementsByClassName("tvc-category-selector");
70
- for (var a = 0; a < b.length; a++) {
71
- tvc_deactivateFeedCategorySelector(b[a].value)
72
- }
73
- }
74
-
75
- function tvc_contains_special_characters(b) {
76
- var a = "%^#<>{}[]/~`@?:;=&";
77
- for (var c = 0; c < a.length; c++) {
78
- if (b.indexOf(a[c]) > -1) {
79
- return true
80
- }
81
- }
82
- return false
83
- }
84
-
85
- function tvc_feedFileNameExists(a) {
86
- console.log(a);
87
- return false
88
- }
89
-
90
- function tvc_deactivateFeedCategorySelector(e, c) {
91
- var d = jQuery("#feed-selector-" + e);
92
- _feedHolder.deactivateCategory(e);
93
- jQuery("#feed-category-" + e).html("");
94
- jQuery("#category-selector-catmap-" + e).hide();
95
- d.prop("checked", false);
96
- if (!c) {
97
- var b = d.attr("data-children") ? JSON.parse(d.attr("data-children")) : [];
98
- for (var a = 0; a < b.length; a++) {
99
- tvc_deactivateFeedCategorySelector(b[a], false)
100
- }
101
- }
102
- }
103
-
104
- function tvc_hideSubs(c) {
105
- var e = c.match(/(\d+)$/)[0];
106
- var a = c.substring(0, c.length - e.length);
107
- for (var b = 7; b > e; b--) {
108
- var d = jQuery("#" + a + b);
109
- d.css("display", "none");
110
- d.empty()
111
- }
112
- }
113
-
114
- function tvc_escapeHtml(a) {
115
- a = a || "";
116
- a = a.replace(/&([^#])(?![a-z1-4]{1,8};)/gi, "&#038;$1");
117
- return a.replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;").replace(/'/g, "&#039;")
118
- }
119
-
120
- function tvc_splitCombinedFieldElements(e) {
121
- if (!e) {
122
- return []
123
- }
124
- var d = /\|[0-9]/;
125
- var a = [];
126
- var b = 0;
127
- var c;
128
- while ((c = d.exec(e)) !== null) {
129
- var f = c.index;
130
- a.push(e.substring(b, f));
131
- e = e.slice(f + 1)
132
- }
133
- a.push(e);
134
- return a
135
- }
136
-
137
- function tvc_showFeedSpinner() {
138
- jQuery("#feed-spinner").show();
139
- jQuery("body").css("cursor", "wait")
140
- }
141
-
142
- function tvc_hideFeedSpinner() {
143
- jQuery("#feed-spinner").hide();
144
- jQuery("body").css("cursor", "default")
145
- }
146
-
147
- function tvc_enableFeedActionButtons() {
148
- jQuery("[name=generate-top]").prop("disabled", false);
149
- jQuery("[name=generate-bottom]").prop("disabled", false);
150
- jQuery("[name=save-top]").prop("disabled", false);
151
- jQuery("[name=save-bottom]").prop("disabled", false);
152
- jQuery( '[name=new]' ).prop( 'disabled', false );
153
- jQuery( '[name=view-top]' ).prop( 'disabled', false );
154
- if ("" !== jQuery("#tvc-feed-url").text()) {
155
- tvc_enableViewFeedButtons()
156
- }
157
- }
158
-
159
- function disableFeedActionButtons() {
160
- jQuery("[name=generate-top]").prop("disabled", true);
161
- jQuery("[name=generate-bottom]").prop("disabled", true);
162
- jQuery("[name=save-top]").prop("disabled", true);
163
- jQuery("[name=save-bottom]").prop("disabled", true);
164
- jQuery( '[name=new]' ).prop( 'disabled', true );
165
- tvc_disableViewFeedButtons()
166
- }
167
-
168
- function tvc_enableViewFeedButtons() {
169
- jQuery("[name=view-top]").prop("disabled", false);
170
- jQuery("[name=view-bottom]").prop("disabled", false);
171
- jQuery( '[name=new]' ).prop( 'disabled', false );
172
- }
173
-
174
- function tvc_disableViewFeedButtons() {
175
- jQuery("[name=view-top]").prop("disabled", true);
176
- jQuery("[name=view-bottom]").prop("disabled", true);
177
- jQuery( '[name=new]' ).prop( 'disabled', true );
178
- }
179
-
180
- function tvc_show_error_message(b) {
181
- var a = jQuery("#error-message");
182
- a.empty();
183
- a.append("<p>" + b + "</p>");
184
- a.show()
185
- }
186
-
187
- function tvc_show_success_message(b) {
188
- var a = jQuery("#success-message");
189
- a.empty();
190
- a.append("<p>" + b + "</p>");
191
- a.show()
192
- };
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_verify-inputs.js DELETED
@@ -1,79 +0,0 @@
1
- "use strict";
2
- function tvc_sourceIsFilled( rowId, sourceLevel, conditionLevel ) {
3
- if ( 'select' !== jQuery( '#input-field-cntrl-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val() ) {
4
- return true;
5
- } else {
6
- return false;
7
- }
8
- }
9
-
10
- function tvc_changeValueIsFilled( rowId, sourceLevel, conditionLevel ) {
11
- var result = false;
12
- var changeSelectorValue = jQuery( '#value-options-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
13
- var changeOptionsValue = jQuery( '#value-options-input-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
14
-
15
- if ( changeOptionsValue ) {
16
- if ( '2' === changeSelectorValue ) { // replace
17
- result = ! ! jQuery( '#value-options-input-with-' + rowId + '-' + sourceLevel + '-' + conditionLevel ).val();
18
- } else {
19
- result = true;
20
- }
21
- }
22
-
23
- return result;
24
- }
25
-
26
- function tvc_queryIsFilled( rowId, sourceLevel, queryLevel ) {
27
- var identString = rowId + '-' + sourceLevel + '-' + queryLevel;
28
- var result = false;
29
- var querySourceSelectorValue = jQuery( '#value-options-input-field-cntrl-' + identString ).val();
30
- var querySelectorValue = jQuery( '#value-query-condition-' + identString + '-0' ).val();
31
- var queryValue = jQuery( '#value-options-condition-value-' + identString ).val();
32
-
33
- if ( sourceLevel < 0 ) {
34
- return true; // there is no previous query so accept
35
- }
36
-
37
- if ( 'select' !== querySourceSelectorValue ) {
38
- if ( '4' !== querySelectorValue && '5' !== querySelectorValue ) {
39
- if ( '14' === querySelectorValue ) {
40
- result = ! ! (
41
- jQuery( '#value-options-condition-and-value-input-' + identString ).val() && queryValue
42
- );
43
- } else {
44
- result = ! ! queryValue;
45
- }
46
- } else {
47
- result = true;
48
- }
49
- }
50
-
51
- return result;
52
- }
53
-
54
- function tvc_feedFilterIsFilled( feedId, filterLevel ) {
55
- var identifierString = feedId + '-' + filterLevel;
56
- var result = false;
57
- var querySourceSelectorValue = jQuery( '#filter-source-control-' + identifierString ).val();
58
- var querySelectorValue = jQuery( '#filter-options-control-' + identifierString ).val();
59
- var queryValue = jQuery( '#filter-input-control-' + identifierString + '-1' ).val();
60
-
61
- if ( filterLevel < 0 ) {
62
- return true; // there is no previous filter so accept
63
- }
64
-
65
- if ( 'select' !== querySourceSelectorValue ) {
66
- if ( '4' !== querySelectorValue && '5' !== querySelectorValue ) {
67
- if ( '14' === querySelectorValue ) {
68
- result = ! ! (
69
- jQuery( '#filter-input-control-' + identifierString + '-2' ).val() && queryValue
70
- );
71
- } else {
72
- result = ! ! queryValue;
73
- }
74
- } else {
75
- result = true;
76
- }
77
- }
78
- return result;
79
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
includes/user-interface/js/tvc_verify-inputs.min.js DELETED
@@ -1 +0,0 @@
1
- function tvc_sourceIsFilled(c,b,a){if("select"!==jQuery("#input-field-cntrl-"+c+"-"+b+"-"+a).val()){return true}else{return false}}function tvc_changeValueIsFilled(f,e,c){var a=false;var b=jQuery("#value-options-"+f+"-"+e+"-"+c).val();var d=jQuery("#value-options-input-"+f+"-"+e+"-"+c).val();if(d){if("2"===b){a=!!jQuery("#value-options-input-with-"+f+"-"+e+"-"+c).val()}else{a=true}}return a}function tvc_queryIsFilled(h,f,e){var b=h+"-"+f+"-"+e;var a=false;var c=jQuery("#value-options-input-field-cntrl-"+b).val();var g=jQuery("#value-query-condition-"+b+"-0").val();var d=jQuery("#value-options-condition-value-"+b).val();if(f<0){return true}if("select"!==c){if("4"!==g&&"5"!==g){if("14"===g){a=!!(jQuery("#value-options-condition-and-value-input-"+b).val()&&d)}else{a=!!d}}else{a=true}}return a}function tvc_feedFilterIsFilled(d,c){var f=d+"-"+c;var a=false;var b=jQuery("#filter-source-control-"+f).val();var g=jQuery("#filter-options-control-"+f).val();var e=jQuery("#filter-input-control-"+f+"-1").val();if(c<0){return true}if("select"!==b){if("4"!==g&&"5"!==g){if("14"===g){a=!!(jQuery("#filter-input-control-"+f+"-2").val()&&e)}else{a=!!e}}else{a=true}}return a};
 
includes/user-interface/tvc-admin-menu-functions.php DELETED
@@ -1,92 +0,0 @@
1
- <?php
2
-
3
- /**
4
- * @package WP Product Feed Manager/User Interface/Functions
5
- * @version 1.3.0
6
- */
7
-
8
- if ( ! defined( 'ABSPATH' ) ) {
9
- exit;
10
- }
11
-
12
- function tvc_feed_manager_main_page() {
13
-
14
- global $tvc_tab_data;
15
-
16
- $active_tab = isset( $_GET['tab'] ) ? $_GET['tab'] : 'feed-list';
17
- $page_start_function = 'tvc_main_admin_page'; // default
18
-
19
- $list_tab = new TVC_Tab(
20
- 'feed-list',
21
- 'feed-list' === $active_tab ? true : false,
22
- __( 'All Feeds', 'tvc-product-feed-manager' ),
23
- 'tvc_main_admin_page'
24
- );
25
-
26
- $product_feed_tab = new TVC_Tab(
27
- 'product-feed',
28
- 'product-feed' === $active_tab ? true : false,
29
- __( 'Create Product Feed', 'tvc-product-feed-manager' ),
30
- 'tvc_add_product_feed_page'
31
- );
32
-
33
- $tvc_tab_data = apply_filters( 'tvc_main_form_tabs', array( $list_tab, $product_feed_tab ), $active_tab );
34
-
35
- foreach ( $tvc_tab_data as $tab ) {
36
- if ( $tab->get_page_identifier() === $active_tab ) {
37
- $page_start_function = $tab->get_class_identifier();
38
- break;
39
- }
40
- }
41
-
42
- $page_start_function();
43
- }
44
-
45
- /**
46
- * starts the main admin page
47
- */
48
- function tvc_main_admin_page() {
49
- $start = new TVC_Main_Admin_Page();
50
-
51
- // now let's get things going
52
- $start->show();
53
- }
54
-
55
- function tvc_add_product_feed_page() {
56
- $add_new_feed_page = new TVC_Product_Feed_Page();
57
- $add_new_feed_page->show();
58
- }
59
-
60
- function call_api(){
61
- if(!empty(unserialize(get_option('pfm_purchase_code')))){
62
- tvc_main_admin_page();
63
- }
64
- else{
65
- include(ENHANCAD_PLUGIN_DIR . 'includes/setup/pfm-envato-api.php');
66
- }
67
- }
68
-
69
- /**
70
- * options page
71
- */
72
- function tvc_options_page() {
73
- $add_options_page = new TVC_Add_Options_Page();
74
- $add_options_page->show();
75
- }
76
-
77
- /**
78
- * Returns an array of possible feed types that can be altered using the tvc_feed_types filter.
79
- *
80
- * @return array with possible feed types
81
- */
82
- function tvc_list_feed_type_text() {
83
-
84
- return apply_filters(
85
- 'tvc_feed_types',
86
- array(
87
- '1' => 'Product Feed',
88
- )
89
- );
90
- }
91
-
92
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
index.php CHANGED
File without changes
languages/enhanced-ecommerce-google-analytics.pot CHANGED
File without changes
public/class-enhanced-ecommerce-google-analytics-public.php CHANGED
@@ -28,29 +28,87 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
28
  * @return void
29
  */
30
  //set plugin version
31
- public $tvc_eeVer = '2.3.6.1';
32
-
 
 
33
  protected $tvc_aga;
34
-
 
 
35
  protected $ga_id;
36
-
 
 
37
  protected $ga_LC;
38
-
 
 
39
  protected $ga_ST;
40
-
 
 
41
  protected $ga_gCkout;
42
-
 
 
43
  protected $ga_eeT;
44
-
 
 
45
  protected $ga_DF;
46
-
 
 
47
  protected $ga_imTh;
48
-
 
 
49
  protected $ga_OPTOUT;
50
-
 
 
51
  protected $ga_PrivacyPolicy;
52
-
 
 
53
  protected $ga_IPA;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
54
 
55
  public function __construct($plugin_name, $version) {
56
 
@@ -58,16 +116,31 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
58
  $this->version = $version;
59
  $this->tvc_aga = $this->get_option("tvc_aga");
60
  $this->ga_id = $this->get_option("ga_id");
61
- $this->ga_ST = $this->get_option("ga_ST");
 
 
 
 
 
 
 
 
 
 
62
  $this->ga_gCkout = $this->get_option("ga_gCkout") == "on" ? true : false; //guest checkout
63
  $this->ga_gUser = $this->get_option("ga_gUser") == "on" ? true : false; //guest checkout
64
- $this->ga_eeT = $this->get_option("ga_eeT");
65
  $this->ga_DF = $this->get_option("ga_DF") == "on" ? true : false;
66
  $this->ga_imTh = $this->get_option("ga_Impr") == "" ? 6 : $this->get_option("ga_Impr");
67
  $this->ga_OPTOUT = $this->get_option("ga_OPTOUT") == "on" ? true : false; //Google Analytics Opt Out
68
  $this->ga_PrivacyPolicy = $this->get_option("ga_PrivacyPolicy") == "on" ? true : false;
69
  $this->ga_IPA = $this->get_option("ga_IPA") == "on" ? true : false; //IP Anony.
70
-
 
 
 
 
 
 
71
  if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', get_option( 'active_plugins' ) ) ) ) {
72
  // Put your plugin code here
73
  add_action('woocommerce_init' , function (){
@@ -79,6 +152,7 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
79
  public function get_option($key){
80
  $ee_options = array();
81
  $my_option = get_option( 'ee_options' );
 
82
  if(!empty($my_option)){
83
  $ee_options = unserialize($my_option);
84
  }
@@ -94,7 +168,6 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
94
  function tvc_store_meta_data() {
95
  //only on home page
96
  global $woocommerce;
97
- $tvc_sMetaData = array();
98
 
99
  $tvc_sMetaData = array(
100
  'tvc_wcv' => $woocommerce->version,
@@ -142,7 +215,7 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
142
  * @return bool
143
  */
144
  private function disable_tracking($type) {
145
- if (is_admin() || (!$this->ga_id ) || "" == $type || current_user_can("manage_options")) {
146
  return true;
147
  }
148
  }
@@ -175,11 +248,16 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
175
  if (is_admin() || $this->ga_ST == "" || current_user_can("manage_options")) {
176
  return;
177
  }
 
178
  $tracking_id = $this->ga_id;
 
 
 
179
 
180
- if (!$tracking_id || !$this->ga_PrivacyPolicy) {
181
  return;
182
  }
 
183
  //common validation----end
184
  $set_domain_name = "auto";
185
  // IP Anonymization
@@ -188,6 +266,17 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
188
  } else {
189
  $ga_ip_anonymization ="";
190
  }
 
 
 
 
 
 
 
 
 
 
 
191
  if($this->ga_OPTOUT) {
192
  echo '<script>
193
  // Set to the same value as the web property used on the site
@@ -208,15 +297,51 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
208
  }
209
  </script>';
210
  }
211
- $code = '<script async src="https://www.googletagmanager.com/gtag/js?id='.esc_js($tracking_id).'"></script>
 
 
 
212
  <script>
213
  window.dataLayer = window.dataLayer || [];
214
  function gtag(){dataLayer.push(arguments);}
215
  gtag("js", new Date());
216
  gtag("config", "'.esc_js($tracking_id).'",{'.$ga_ip_anonymization.' "cookie_domain":"'.$set_domain_name.'"});
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
217
  </script>
218
  ';
219
- echo $code;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
220
  }
221
 
222
  /**
@@ -229,12 +354,10 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
229
  function ecommerce_tracking_code($order_id) {
230
 
231
  global $woocommerce;
232
- if ($this->disable_tracking($this->ga_eeT) || current_user_can("manage_options") || get_post_meta($order_id, "_tracked", true) == 1)
233
  return;
 
234
 
235
- $tracking_id = $this->ga_id;
236
- if (!$tracking_id)
237
- return;
238
  // Doing eCommerce tracking so unhook standard tracking from the footer
239
  remove_action("wp_footer", array($this, "ee_settings"));
240
 
@@ -357,38 +480,108 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
357
  //make json for trans data on order page
358
  $this->wc_version_compare("tvc_td=" . json_encode($orderpage_trans_Array) . ";");
359
 
360
- $code ='
361
- var items = [];
362
- //set local currencies
363
- gtag("set", {"currency": tvc_lc});
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
364
  for(var t_item in tvc_oc){
365
  items.push({
366
- "id": tvc_oc[t_item].tvc_i,
367
- "name": tvc_oc[t_item].tvc_n,
368
- "category": tvc_oc[t_item].tvc_c,
369
- "attributes": tvc_oc[t_item].tvc_attr,
 
 
370
  "price": tvc_oc[t_item].tvc_p,
 
371
  "quantity": tvc_oc[t_item].tvc_q,
372
  });
373
 
374
  }
375
  gtag("event", "purchase", {
376
  "transaction_id":tvc_td.id,
 
377
  "affiliation": tvc_td.affiliation,
378
  "value":tvc_td.revenue,
379
- "tax": tvc_td.tax,
380
- "shipping": tvc_td.shipping,
381
  "coupon": tvc_td.coupon,
 
382
  "event_category": "Enhanced-Ecommerce",
383
  "event_label":"order_confirmation",
384
  "non_interaction": true,
385
  "items":items
386
  });
387
- ';
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
388
 
389
- //check woocommerce version
390
- $this->wc_version_compare($code);
391
- update_post_meta($order_id, "_tracked", 1);
 
392
  }
393
 
394
  /**
@@ -418,31 +611,77 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
418
  }
419
  //remove last comma(,) if multiple categories are there
420
  $categories = rtrim($categories, ",");
421
-
422
- $code = '
423
- var items = [];
424
- //set local currencies
425
- gtag("set", {"currency": tvc_lc});
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
426
  jQuery("[class*=single_add_to_cart_button]").click(function() {
427
-
428
- // Enhanced E-commerce Add to cart clicks
429
  gtag("event", "add_to_cart", {
430
  "event_category":"Enhanced-Ecommerce",
431
  "event_label":"add_to_cart_click",
 
432
  "non_interaction": true,
433
  "items": [{
434
- "id" : tvc_po.tvc_i,
435
- "name": tvc_po.tvc_n,
436
- "category" :tvc_po.tvc_c,
437
  "price": tvc_po.tvc_p,
438
  "quantity" :jQuery(this).parent().find("input[name=quantity]").val()
439
  }]
440
- });
441
-
 
 
 
 
 
 
 
 
 
 
 
 
442
  });
443
  ';
444
- //check woocommerce version
445
  $this->wc_version_compare($code);
 
446
  }
447
 
448
  /**
@@ -496,23 +735,71 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
496
  }
497
  //prod page detail view json
498
  $this->wc_version_compare("tvc_po=" . json_encode($prodpage_detail_json) . ";");
499
- $code = '
500
- gtag("event", "view_item", {
501
- "event_category":"Enhanced-Ecommerce",
502
- "event_label":"product_impression_pp",
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
503
  "items": [
504
  {
505
- "id": tvc_po.tvc_i,// Product details are provided in an impressionFieldObject.
506
- "name": tvc_po.tvc_n,
507
- "category":tvc_po.tvc_c,
508
  }
509
  ],
510
  "non_interaction": true
511
- })
512
- ';
513
- //check woocommerce version
514
- if(is_product()){
515
- $this->wc_version_compare($code);
 
 
 
 
 
 
 
 
 
 
 
 
 
516
  }
517
  }
518
 
@@ -524,7 +811,6 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
524
  * @return void
525
  */
526
  public function bind_product_metadata() {
527
-
528
  if ($this->disable_tracking($this->ga_eeT)) {
529
  return;
530
  }
@@ -739,72 +1025,221 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
739
  //category page json
740
  $this->wc_version_compare("tvc_pgc=" . json_encode($catpage_json) . ";");
741
  $this->wc_version_compare("catpage_json_ATC_link=" . json_encode($catpage_json_ATC_link) . ";");
742
-
743
- $hmpg_impressions_jQ = '
744
- var items = [];
745
  //set local currencies
746
- gtag("set", {"currency": tvc_lc});
747
- function t_products_impre_clicks(t_json_name,t_action){
748
- t_send_threshold=0;
749
- t_prod_pos=0;
750
- t_json_length=Object.keys(t_json_name).length;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
751
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
752
  for(var t_item in t_json_name) {
753
  t_send_threshold++;
754
  t_prod_pos++;
755
  items.push({
756
- "id": t_json_name[t_item].tvc_i,
757
- "name": t_json_name[t_item].tvc_n,
758
- "category": t_json_name[t_item].tvc_c,
759
  "price": t_json_name[t_item].tvc_p,
 
760
  });
761
-
762
- if(t_json_length > ' . esc_js($impression_threshold) .' ){
763
-
764
  if((t_send_threshold%' . esc_js($impression_threshold) . ')==0){
765
  t_json_length=t_json_length-' . esc_js($impression_threshold) . ';
766
- gtag("event", "view_item_list", { "event_category":"Enhanced-Ecommerce",
767
- "event_label":"product_impression_"+t_action, "items":items,"non_interaction": true});
768
- items = [];
769
- }
770
- }else{
771
-
772
- t_json_length--;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
773
  if(t_json_length==0){
774
- gtag("event", "view_item_list", { "event_category":"Enhanced-Ecommerce",
775
- "event_label":"product_impression_"+t_action, "items":items,"non_interaction": true});
776
- items = [];
777
- }
778
- }
779
- }
780
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
781
 
782
  //function for comparing urls in json object
783
  function prod_exists_in_JSON(t_url,t_json_name,t_action){
784
- if(t_json_name.hasOwnProperty(t_url)){
785
- t_call_fired=true;
786
- gtag("event", "select_content", {
787
- "event_category":"Enhanced-Ecommerce",
788
- "event_label":"product_click_"+t_action,
789
- "content_type": "product",
790
- "items": [
791
- {
792
- "id":t_json_name[t_url].tvc_i,
793
- "name": t_json_name[t_url].tvc_n,
794
- "category":t_json_name[t_url].tvc_c,
795
- "price": t_json_name[t_url].tvc_p,
796
- }
797
- ],
798
- "non_interaction": true
799
- });
800
- }else{
801
- t_call_fired=false;
802
- }
803
- return t_call_fired;
 
804
  }
805
  function prod_ATC_link_exists(t_url,t_ATC_json_name,t_prod_data_json,t_qty){
806
  t_prod_url_key=t_ATC_json_name[t_url]["ATC-link"];
807
-
808
  if(t_prod_data_json.hasOwnProperty(t_prod_url_key)){
809
  t_call_fired=true;
810
  // Enhanced E-commerce Add to cart clicks
@@ -813,22 +1248,33 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
813
  "event_label":"add_to_cart_click",
814
  "non_interaction": true,
815
  "items": [{
816
- "id" : t_prod_data_json[t_prod_url_key].tvc_i,
817
- "name":t_prod_data_json[t_prod_url_key].tvc_n,
818
- "category" : t_prod_data_json[t_prod_url_key].tvc_c,
819
  "price": t_prod_data_json[t_prod_url_key].tvc_p,
 
820
  "quantity" :t_qty
821
  }]
822
  });
823
-
 
 
 
 
 
 
 
 
 
 
 
824
  }else{
825
- t_call_fired=false;
826
  }
827
  return t_call_fired;
828
-
829
  }
830
-
831
  ';
 
832
  if(is_home() || is_front_page()){
833
  $hmpg_impressions_jQ .='
834
  if(tvc_fp.length !== 0){
@@ -1004,28 +1450,55 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
1004
 
1005
  //Cart Page item Array to Json
1006
  $this->wc_version_compare("tvc_cc=" . json_encode($cartpage_prod_array_main) . ";");
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1007
 
1008
- $code = '
1009
- //set local currencies
1010
- gtag("set", {"currency": tvc_lc});
1011
- $("a[href*=\"?remove_item\"]").click(function(){
1012
- t_url=jQuery(this).attr("href");
1013
- gtag("event", "remove_from_cart", {
1014
- "event_category":"Enhanced-Ecommerce",
1015
- "event_label":"remove_from_cart_click",
1016
- "items": [{
1017
- "id":tvc_cc[t_url].tvc_i,
1018
- "name": tvc_cc[t_url].tvc_n,
1019
- "category":tvc_cc[t_url].tvc_c,
1020
- "price": tvc_cc[t_url].tvc_p,
1021
- "quantity": tvc_cc[t_url].tvc_q
1022
- }],
1023
- "non_interaction": true
1024
- });
1025
- });
1026
- ';
1027
- //check woocommerce version
1028
- $this->wc_version_compare($code);
 
 
 
1029
  }
1030
 
1031
  /**
@@ -1040,25 +1513,52 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
1040
  }
1041
  //call fn to make json
1042
  $this->get_ordered_items();
1043
- $code= '
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1044
  var items = [];
1045
- gtag("set", {"currency": tvc_lc});
1046
  for(var t_item in tvc_ch){
1047
  items.push({
1048
- "id": tvc_ch[t_item].tvc_i,
1049
- "name": tvc_ch[t_item].tvc_n,
1050
- "category": tvc_ch[t_item].tvc_c,
1051
- "attributes": tvc_ch[t_item].tvc_attr,
1052
  "price": tvc_ch[t_item].tvc_p,
1053
  "quantity": tvc_ch[t_item].tvc_q
1054
  });
1055
  }';
1056
 
1057
- $code_step_1 = $code . 'gtag("event", "begin_checkout", {"event_category":"Enhanced-Ecommerce",
1058
- "event_label":"checkout_step_1","items":items,"non_interaction": true });';
 
 
 
 
1059
 
1060
- //check woocommerce version and add code
1061
- $this->wc_version_compare($code_step_1);
 
1062
  }
1063
 
1064
  /**
@@ -1071,32 +1571,34 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
1071
  if ($this->disable_tracking($this->ga_eeT)) {
1072
  return;
1073
  }
1074
- $code= '
1075
- var items = [];
1076
- gtag("set", {"currency": tvc_lc});
1077
- for(var t_item in tvc_ch){
1078
- items.push({
1079
- "id": tvc_ch[t_item].tvc_i,
1080
- "name": tvc_ch[t_item].tvc_n,
1081
- "category": tvc_ch[t_item].tvc_c,
1082
- "attributes": tvc_ch[t_item].tvc_attr,
1083
- "price": tvc_ch[t_item].tvc_p,
1084
- "quantity": tvc_ch[t_item].tvc_q
1085
- });
1086
- }';
1087
-
1088
- $code_step_2 = $code . 'gtag("event", "checkout_progress", {"checkout_step": 2,"event_category":"Enhanced-Ecommerce",
1089
- "event_label":"checkout_step_2","items":items,"non_interaction": true });';
1090
-
1091
- //if logged in and first name is filled - Guest Check out
1092
- if (is_user_logged_in()) {
1093
- $step2_onFocus = 't_tracked_focus=0; if(t_tracked_focus===0){' . $code_step_2 . ' t_tracked_focus++;}';
1094
- } else {
1095
- //first name on focus call fire
1096
- $step2_onFocus = 't_tracked_focus=0; jQuery("input[name=billing_first_name]").on("focus",function(){ if(t_tracked_focus===0){' . $code_step_2 . ' t_tracked_focus++;}});';
 
 
 
 
1097
  }
1098
- //check woocommerce version and add code
1099
- $this->wc_version_compare($step2_onFocus);
1100
  }
1101
 
1102
  /**
@@ -1106,38 +1608,41 @@ class Enhanced_Ecommerce_Google_Analytics_Public {
1106
  * @return void
1107
  */
1108
  public function checkout_step_3_tracking() {
 
1109
  if ($this->disable_tracking($this->ga_eeT)) {
1110
  return;
1111
  }
1112
- $code= '
1113
- var items = [];
1114
- for(var t_item in tvc_ch){
1115
- items.push({
1116
- "id": tvc_ch[t_item].tvc_i,
1117
- "name": tvc_ch[t_ite
28
  * @return void
29
  */
30
  //set plugin version
31
+ public $tvc_eeVer = '2.3.6';
32
+ /**
33
+ * @var mixed $tvc_aga
34
+ */
35
  protected $tvc_aga;
36
+ /**
37
+ * @var mixed $ga_id
38
+ */
39
  protected $ga_id;
40
+ /**
41
+ * @var $ga_LC
42
+ */
43
  protected $ga_LC;
44
+ /**
45
+ * @var mixed $ga_ST
46
+ */
47
  protected $ga_ST;
48
+ /**
49
+ * @var bool $ga_gCkout
50
+ */
51
  protected $ga_gCkout;
52
+ /**
53
+ * @var mixed $ga_eeT
54
+ */
55
  protected $ga_eeT;
56
+ /**
57
+ * @var bool $ga_DF
58
+ */
59
  protected $ga_DF;
60
+ /**
61
+ * @var int|mixed $ga_imTh
62
+ */
63
  protected $ga_imTh;
64
+ /**
65
+ * @var bool $ga_OPTOUT
66
+ */
67
  protected $ga_OPTOUT;
68
+ /**
69
+ * @var bool $ga_PrivacyPolicy
70
+ */
71
  protected $ga_PrivacyPolicy;
72
+ /**
73
+ * @var bool $ga_IPA
74
+ */
75
  protected $ga_IPA;
76
+ /**
77
+ * @var mixed $enhanced_e_commerce_tracking
78
+ */
79
+ protected $enhanced_e_commerce_tracking;
80
+ /**
81
+ * @var mixed $add_gtag_snippet
82
+ */
83
+ protected $add_gtag_snippet;
84
+ /**
85
+ * @var mixed $gm_id
86
+ */
87
+ protected $gm_id;
88
+ /**
89
+ * @var mixed $google_ads_id
90
+ */
91
+ protected $google_ads_id;
92
+ /**
93
+ * @var mixed $ga_excT
94
+ */
95
+ protected $ga_excT;
96
+ protected $exception_tracking;
97
+ protected $ga_elaT;
98
+ protected $google_merchant_id;
99
+ protected $tracking_option;
100
+ protected $ga_gUser;
101
+ protected $plugin_name;
102
+ protected $version;
103
+ protected $ads_ert;
104
+ protected $ads_edrt;
105
+ protected $ads_tracking_id;
106
+
107
+ /**
108
+ * Enhanced_Ecommerce_Google_Analytics_Public constructor.
109
+ * @param $plugin_name
110
+ * @param $version
111
+ */
112
 
113
  public function __construct($plugin_name, $version) {
114
 
116
  $this->version = $version;
117
  $this->tvc_aga = $this->get_option("tvc_aga");
118
  $this->ga_id = $this->get_option("ga_id");
119
+ $this->ga_eeT = $this->get_option("ga_eeT");
120
+ $this->enhanced_e_commerce_tracking = $this->get_option("enhanced_e_commerce_tracking");
121
+ $this->ga_ST = $this->get_option("ga_ST"); //add_gtag_snippet
122
+ $this->add_gtag_snippet = $this->get_option("add_gtag_snippet"); //add_gtag_snippet
123
+ $this->gm_id = $this->get_option("gm_id"); //measurement_id
124
+ $this->google_ads_id = $this->get_option("google_ads_id");
125
+ $this->ga_excT = $this->get_option("ga_excT"); //exception_tracking
126
+ $this->exception_tracking = $this->get_option("exception_tracking"); //exception_tracking
127
+ $this->ga_elaT = $this->get_option("ga_elaT"); //enhanced_link_attribution_tracking
128
+ $this->google_merchant_id = $this->get_option("google_merchant_id");
129
+ $this->tracking_option = $this->get_option("tracking_option");
130
  $this->ga_gCkout = $this->get_option("ga_gCkout") == "on" ? true : false; //guest checkout
131
  $this->ga_gUser = $this->get_option("ga_gUser") == "on" ? true : false; //guest checkout
 
132
  $this->ga_DF = $this->get_option("ga_DF") == "on" ? true : false;
133
  $this->ga_imTh = $this->get_option("ga_Impr") == "" ? 6 : $this->get_option("ga_Impr");
134
  $this->ga_OPTOUT = $this->get_option("ga_OPTOUT") == "on" ? true : false; //Google Analytics Opt Out
135
  $this->ga_PrivacyPolicy = $this->get_option("ga_PrivacyPolicy") == "on" ? true : false;
136
  $this->ga_IPA = $this->get_option("ga_IPA") == "on" ? true : false; //IP Anony.
137
+ $this->ads_ert = get_option('ads_ert'); //Enable remarketing tags
138
+ $this->ads_edrt = get_option('ads_edrt'); //Enable dynamic remarketing tags
139
+ $this->ads_tracking_id = get_option('ads_tracking_id');
140
+ $this->ads_ert = get_option('ads_ert');
141
+ $this->ads_edrt = get_option('ads_edrt');
142
+ //$this->subscription_id = $this->get_option("subscription_id");
143
+ //setcookie('subscription_id', $this->subscription_id);
144
  if ( in_array( 'woocommerce/woocommerce.php', apply_filters( 'active_plugins', get_option( 'active_plugins' ) ) ) ) {
145
  // Put your plugin code here
146
  add_action('woocommerce_init' , function (){
152
  public function get_option($key){
153
  $ee_options = array();
154
  $my_option = get_option( 'ee_options' );
155
+
156
  if(!empty($my_option)){
157
  $ee_options = unserialize($my_option);
158
  }
168
  function tvc_store_meta_data() {
169
  //only on home page
170
  global $woocommerce;
 
171
 
172
  $tvc_sMetaData = array(
173
  'tvc_wcv' => $woocommerce->version,
215
  * @return bool
216
  */
217
  private function disable_tracking($type) {
218
+ if (is_admin() || "" == $type || current_user_can("manage_options")) {
219
  return true;
220
  }
221
  }
248
  if (is_admin() || $this->ga_ST == "" || current_user_can("manage_options")) {
249
  return;
250
  }
251
+
252
  $tracking_id = $this->ga_id;
253
+ $measurment_id = $this->gm_id;
254
+ $tracking_opt = $this->tracking_option;
255
+
256
 
257
+ if(!$this->ga_PrivacyPolicy) {
258
  return;
259
  }
260
+
261
  //common validation----end
262
  $set_domain_name = "auto";
263
  // IP Anonymization
266
  } else {
267
  $ga_ip_anonymization ="";
268
  }
269
+
270
+
271
+ echo '<script>';
272
+ echo 'var track_option = '.json_encode($tracking_opt).';';
273
+ echo 'var ua_track_id = '.json_encode($tracking_id).';';
274
+ echo 'var ga4_measure_id = '.json_encode($measurment_id).';';
275
+ echo 'var adsTringId = '.json_encode($this->ads_tracking_id).';';
276
+ echo 'var ads_ert = '.json_encode($this->ads_ert).';';
277
+ echo 'var ads_edrt = '.json_encode($this->ads_edrt).';';
278
+ echo '</script>';
279
+
280
  if($this->ga_OPTOUT) {
281
  echo '<script>
282
  // Set to the same value as the web property used on the site
297
  }
298
  </script>';
299
  }
300
+
301
+ if(($tracking_opt == "UA" || $tracking_id || $tracking_opt == "") && $tracking_opt != "BOTH"){
302
+ //$id = esc_js($tracking_id);
303
+ echo '<script async src="https://www.googletagmanager.com/gtag/js?id='.esc_js($tracking_id).'"></script>
304
  <script>
305
  window.dataLayer = window.dataLayer || [];
306
  function gtag(){dataLayer.push(arguments);}
307
  gtag("js", new Date());
308
  gtag("config", "'.esc_js($tracking_id).'",{'.$ga_ip_anonymization.' "cookie_domain":"'.$set_domain_name.'"});
309
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
310
+ gtag("config", "AW-' . esc_js($this->ads_tracking_id) . '");
311
+ }
312
+ </script>
313
+ ';
314
+ //echo $code;
315
+ }
316
+
317
+ if($tracking_opt == "GA4"){
318
+ echo '<script async src="https://www.googletagmanager.com/gtag/js?id='.esc_js($measurment_id).'"></script>
319
+ <script>
320
+ window.dataLayer = window.dataLayer || [];
321
+ function gtag(){dataLayer.push(arguments);}
322
+ gtag("js", new Date());
323
+ gtag("config", "'.esc_js($measurment_id).'",{'.$ga_ip_anonymization.' "cookie_domain":"'.$set_domain_name.'"});
324
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
325
+ gtag("config", "AW-' . esc_js($this->ads_tracking_id) . '");
326
+ }
327
  </script>
328
  ';
329
+
330
+ }
331
+ if($tracking_opt == "BOTH"){
332
+ echo '<script async src="https://www.googletagmanager.com/gtag/js?id='.esc_js($measurment_id).'"></script>
333
+ <script>
334
+ window.dataLayer = window.dataLayer || [];
335
+ function gtag(){dataLayer.push(arguments);}
336
+ gtag("js", new Date());
337
+ gtag("config", "'.esc_js($measurment_id).'",{'.$ga_ip_anonymization.' "cookie_domain":"'.$set_domain_name.'"});
338
+ gtag("config", "'.esc_js($tracking_id).'");
339
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
340
+ gtag("config", "AW-' . esc_js($this->ads_tracking_id) . '");
341
+ }
342
+ </script>
343
+ ';
344
+ }
345
  }
346
 
347
  /**
354
  function ecommerce_tracking_code($order_id) {
355
 
356
  global $woocommerce;
357
+ if ($this->disable_tracking($this->ga_eeT) || current_user_can("manage_options") || get_post_meta($order_id, "_tracked", true) == 1){
358
  return;
359
+ }
360
 
 
 
 
361
  // Doing eCommerce tracking so unhook standard tracking from the footer
362
  remove_action("wp_footer", array($this, "ee_settings"));
363
 
480
  //make json for trans data on order page
481
  $this->wc_version_compare("tvc_td=" . json_encode($orderpage_trans_Array) . ";");
482
 
483
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH") {
484
+ $code ='
485
+ var items = [];
486
+ //set local currencies
487
+ gtag("set", {"currency": tvc_lc});
488
+ for(var t_item in tvc_oc){
489
+ items.push({
490
+ "id": tvc_oc[t_item].tvc_i,
491
+ "name": tvc_oc[t_item].tvc_n,
492
+ "category": tvc_oc[t_item].tvc_c,
493
+ "attributes": tvc_oc[t_item].tvc_attr,
494
+ "price": tvc_oc[t_item].tvc_p,
495
+ "quantity": tvc_oc[t_item].tvc_q,
496
+ });
497
+
498
+ }
499
+ gtag("event", "purchase", {
500
+ "transaction_id":tvc_td.id,
501
+ "affiliation": tvc_td.affiliation,
502
+ "value":tvc_td.revenue,
503
+ "tax": tvc_td.tax,
504
+ "shipping": tvc_td.shipping,
505
+ "coupon": tvc_td.coupon,
506
+ "event_category": "Enhanced-Ecommerce",
507
+ "event_label":"order_confirmation",
508
+ "non_interaction": true,
509
+ "items":items
510
+ });
511
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
512
+ var ads_items = [];
513
+ var ads_value=0;
514
+ for(var t_item in tvc_oc){
515
+ ads_value=ads_value + parseFloat(tvc_oc[t_item].tvc_p);
516
+ ads_items.push({
517
+ item_id: tvc_oc[t_item].tvc_i,
518
+ google_business_vertical: "retail"
519
+ });
520
+ }
521
+ gtag("event","purchase", {
522
+ "value": ads_value,
523
+ "items": ads_items
524
+ });
525
+ }
526
+ ';
527
+
528
+ //check woocommerce version
529
+ $this->wc_version_compare($code);
530
+ update_post_meta($order_id, "_tracked", 1);
531
+ }
532
+ // start GA4 or Both
533
+ if( $this->gm_id && $this->tracking_option == "GA4") {
534
+ $code = '
535
+ var items = [];
536
  for(var t_item in tvc_oc){
537
  items.push({
538
+ "item_id": tvc_oc[t_item].tvc_i,
539
+ "item_name": tvc_oc[t_item].tvc_n,
540
+ "coupon": tvc_td.coupon,
541
+ "affiliation": tvc_td.affiliation,
542
+ "item_category": tvc_oc[t_item].tvc_c,
543
+ "item_variant": tvc_oc[t_item].tvc_attr,
544
  "price": tvc_oc[t_item].tvc_p,
545
+ "currency": tvc_lc,
546
  "quantity": tvc_oc[t_item].tvc_q,
547
  });
548
 
549
  }
550
  gtag("event", "purchase", {
551
  "transaction_id":tvc_td.id,
552
+ "shipping": tvc_td.shipping,
553
  "affiliation": tvc_td.affiliation,
554
  "value":tvc_td.revenue,
555
+ "currency": tvc_lc,
 
556
  "coupon": tvc_td.coupon,
557
+ "tax": tvc_td.tax,
558
  "event_category": "Enhanced-Ecommerce",
559
  "event_label":"order_confirmation",
560
  "non_interaction": true,
561
  "items":items
562
  });
563
+
564
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
565
+ var ads_items = [];
566
+ var ads_value=0;
567
+ for(var t_item in tvc_oc){
568
+ ads_value=ads_value + parseFloat(tvc_oc[t_item].tvc_p);
569
+ ads_items.push({
570
+ item_id: tvc_oc[t_item].tvc_i,
571
+ google_business_vertical: "retail"
572
+ });
573
+ }
574
+ gtag("event","purchase", {
575
+ "value": ads_value,
576
+ "items": ads_items
577
+ });
578
+ }
579
+ ';
580
 
581
+ //check woocommerce version
582
+ $this->wc_version_compare($code);
583
+ update_post_meta($order_id, "_tracked", 1);
584
+ }
585
  }
586
 
587
  /**
611
  }
612
  //remove last comma(,) if multiple categories are there
613
  $categories = rtrim($categories, ",");
614
+ if($this->ga_id || ($this->tracking_option == "UA" || $this->tracking_option == "BOTH")) {
615
+ $code = '
616
+ var items = [];
617
+ //set local currencies
618
+ gtag("set", {"currency": tvc_lc});
619
+ jQuery("[class*=single_add_to_cart_button]").click(function() {
620
+ // Enhanced E-commerce Add to cart clicks
621
+ gtag("event", "add_to_cart", {
622
+ "event_category":"Enhanced-Ecommerce",
623
+ "event_label":"add_to_cart_click",
624
+ "non_interaction": true,
625
+ "items": [{
626
+ "id" : tvc_po.tvc_i,
627
+ "name": tvc_po.tvc_n,
628
+ "category" :tvc_po.tvc_c,
629
+ "price": tvc_po.tvc_p,
630
+ "quantity" :jQuery(this).parent().find("input[name=quantity]").val()
631
+ }]
632
+ });
633
+ //add remarketing and dynamicremarketing tags
634
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
635
+ gtag("event","add_to_cart", {
636
+ "value": tvc_po.tvc_p,
637
+ "items": [
638
+ {
639
+ "id": tvc_po.tvc_i,
640
+ "google_business_vertical": "retail"
641
+ }
642
+ ]
643
+ });
644
+ }
645
+ });
646
+
647
+ ';
648
+ //check woocommerce version
649
+ $this->wc_version_compare($code);
650
+ }
651
+ if($this->gm_id && $this->tracking_option == "GA4") {
652
+ $code = '
653
+ var items = [];
654
  jQuery("[class*=single_add_to_cart_button]").click(function() {
 
 
655
  gtag("event", "add_to_cart", {
656
  "event_category":"Enhanced-Ecommerce",
657
  "event_label":"add_to_cart_click",
658
+ "currency": tvc_lc,
659
  "non_interaction": true,
660
  "items": [{
661
+ "item_id" : tvc_po.tvc_i,
662
+ "item_name": tvc_po.tvc_n,
663
+ "item_category" :tvc_po.tvc_c,
664
  "price": tvc_po.tvc_p,
665
  "quantity" :jQuery(this).parent().find("input[name=quantity]").val()
666
  }]
667
+ });
668
+
669
+ //add remarketing and dynamicremarketing tags
670
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
671
+ gtag("event","add_to_cart", {
672
+ "value": tvc_po.tvc_p,
673
+ "items": [
674
+ {
675
+ "id": tvc_po.tvc_i,
676
+ "google_business_vertical": "retail"
677
+ }
678
+ ]
679
+ });
680
+ }
681
  });
682
  ';
 
683
  $this->wc_version_compare($code);
684
+ }
685
  }
686
 
687
  /**
735
  }
736
  //prod page detail view json
737
  $this->wc_version_compare("tvc_po=" . json_encode($prodpage_detail_json) . ";");
738
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH") {
739
+ $code = '
740
+ gtag("event", "view_item", {
741
+ "event_category":"Enhanced-Ecommerce",
742
+ "event_label":"product_impression_pp",
743
+ "items": [
744
+ {
745
+ "id": tvc_po.tvc_i,// Product details are provided in an impressionFieldObject.
746
+ "name": tvc_po.tvc_n,
747
+ "category":tvc_po.tvc_c,
748
+ }
749
+ ],
750
+ "non_interaction": true
751
+ })
752
+ //add remarketing and dynamicremarketing tags
753
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
754
+ gtag("event","view_item", {
755
+ "value": tvc_po.tvc_p,
756
+ "items": [
757
+ {
758
+ "id": tvc_po.tvc_i,
759
+ "google_business_vertical": "retail"
760
+ }
761
+ ]
762
+ });
763
+ }
764
+ ';
765
+ //check woocommerce version
766
+ if(is_product()){
767
+ $this->wc_version_compare($code);
768
+ }
769
+ }
770
+
771
+ if( $this->gm_id && $this->tracking_option == "GA4") {
772
+ $code = '
773
+ gtag("event", "view_item", {
774
+ "event_category":"Enhanced-Ecommerce",
775
+ "event_label":"product_impression_pp",
776
+ "currency": tvc_lc,
777
  "items": [
778
  {
779
+ "item_id": tvc_po.tvc_i,
780
+ "item_name": tvc_po.tvc_n,
781
+ "item_category":tvc_po.tvc_c,
782
  }
783
  ],
784
  "non_interaction": true
785
+ })
786
+ //add remarketing and dynamicremarketing tags
787
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
788
+ gtag("event","view_item", {
789
+ "value": tvc_po.tvc_p,
790
+ "items": [
791
+ {
792
+ "id": tvc_po.tvc_i,
793
+ "google_business_vertical": "retail"
794
+ }
795
+ ]
796
+ });
797
+ }
798
+ ';
799
+ //check woocommerce version
800
+ if (is_product()) {
801
+ $this->wc_version_compare($code);
802
+ }
803
  }
804
  }
805
 
811
  * @return void
812
  */
813
  public function bind_product_metadata() {
 
814
  if ($this->disable_tracking($this->ga_eeT)) {
815
  return;
816
  }
1025
  //category page json
1026
  $this->wc_version_compare("tvc_pgc=" . json_encode($catpage_json) . ";");
1027
  $this->wc_version_compare("catpage_json_ATC_link=" . json_encode($catpage_json_ATC_link) . ";");
1028
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH") {
1029
+ $hmpg_impressions_jQ = '
1030
+ var items = [];
1031
  //set local currencies
1032
+ gtag("set", {"currency": tvc_lc});
1033
+ function t_products_impre_clicks(t_json_name,t_action){
1034
+ t_send_threshold=0;
1035
+ t_prod_pos=0;
1036
+ t_json_length=Object.keys(t_json_name).length;
1037
+
1038
+ for(var t_item in t_json_name) {
1039
+ t_send_threshold++;
1040
+ t_prod_pos++;
1041
+ items.push({
1042
+ "id": t_json_name[t_item].tvc_i,
1043
+ "name": t_json_name[t_item].tvc_n,
1044
+ "category": t_json_name[t_item].tvc_c,
1045
+ "price": t_json_name[t_item].tvc_p,
1046
+ });
1047
+
1048
+ if(t_json_length > ' . esc_js($impression_threshold) .' ){
1049
+
1050
+ if((t_send_threshold%' . esc_js($impression_threshold) . ')==0){
1051
+ t_json_length=t_json_length-' . esc_js($impression_threshold) . ';
1052
+ gtag("event", "view_item_list", { "event_category":"Enhanced-Ecommerce",
1053
+ "event_label":"product_impression_"+t_action, "items":items,"non_interaction": true});
1054
+ items = [];
1055
+ }
1056
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1057
+ gtag("event","view_item_list", {
1058
+ "value": t_json_name[t_item].tvc_p,
1059
+ "items": [
1060
+ {
1061
+ "id": t_json_name[t_item].tvc_i,
1062
+ "google_business_vertical": "retail"
1063
+ }
1064
+ ]
1065
+ });
1066
+ }
1067
+ }else{
1068
+
1069
+ t_json_length--;
1070
+ if(t_json_length==0){
1071
+ gtag("event", "view_item_list", { "event_category":"Enhanced-Ecommerce",
1072
+ "event_label":"product_impression_"+t_action, "items":items,"non_interaction": true});
1073
+ items = [];
1074
+ }
1075
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1076
+ gtag("event","view_item_list", {
1077
+ "value": t_json_name[t_item].tvc_p,
1078
+ "items": [
1079
+ {
1080
+ "id": t_json_name[t_item].tvc_i,
1081
+ "google_business_vertical": "retail"
1082
+ }
1083
+ ]
1084
+ });
1085
+ }
1086
+ }
1087
+ }
1088
+ }
1089
+
1090
+ //function for comparing urls in json object
1091
+ function prod_exists_in_JSON(t_url,t_json_name,t_action){
1092
+ if(t_json_name.hasOwnProperty(t_url)){
1093
+ t_call_fired=true;
1094
+ gtag("event", "select_content", {
1095
+ "event_category":"Enhanced-Ecommerce",
1096
+ "event_label":"product_click_"+t_action,
1097
+ "content_type": "product",
1098
+ "items": [
1099
+ {
1100
+ "id":t_json_name[t_url].tvc_i,
1101
+ "name": t_json_name[t_url].tvc_n,
1102
+ "category":t_json_name[t_url].tvc_c,
1103
+ "price": t_json_name[t_url].tvc_p,
1104
+ }
1105
+ ],
1106
+ "non_interaction": true
1107
+ });
1108
+ }else{
1109
+ t_call_fired=false;
1110
+ }
1111
+ return t_call_fired;
1112
+ }
1113
+ function prod_ATC_link_exists(t_url,t_ATC_json_name,t_prod_data_json,t_qty){
1114
+ t_prod_url_key=t_ATC_json_name[t_url]["ATC-link"];
1115
 
1116
+ if(t_prod_data_json.hasOwnProperty(t_prod_url_key)){
1117
+ t_call_fired=true;
1118
+ // Enhanced E-commerce Add to cart clicks
1119
+ gtag("event", "add_to_cart", {
1120
+ "event_category":"Enhanced-Ecommerce",
1121
+ "event_label":"add_to_cart_click",
1122
+ "non_interaction": true,
1123
+ "items": [{
1124
+ "id" : t_prod_data_json[t_prod_url_key].tvc_i,
1125
+ "name":t_prod_data_json[t_prod_url_key].tvc_n,
1126
+ "category" : t_prod_data_json[t_prod_url_key].tvc_c,
1127
+ "price": t_prod_data_json[t_prod_url_key].tvc_p,
1128
+ "quantity" :t_qty
1129
+ }]
1130
+ });
1131
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1132
+ gtag("event","add_to_cart", {
1133
+ "value": t_prod_data_json[t_prod_url_key].tvc_p,
1134
+ "items": [
1135
+ {
1136
+ "id": t_prod_data_json[t_prod_url_key].tvc_i,
1137
+ "google_business_vertical": "retail"
1138
+ }
1139
+ ]
1140
+ });
1141
+ }
1142
+
1143
+ }else{
1144
+ t_call_fired=false;
1145
+ }
1146
+ return t_call_fired;
1147
+
1148
+ }
1149
+
1150
+ ';
1151
+ }
1152
+ if($this->gm_id && $this->tracking_option == "GA4") {
1153
+ $hmpg_impressions_jQ = '
1154
+ var items = [];
1155
+ function t_products_impre_clicks(t_json_name,t_action){
1156
+ t_send_threshold=0;
1157
+ t_prod_pos=0;
1158
+ t_json_length=Object.keys(t_json_name).length;
1159
  for(var t_item in t_json_name) {
1160
  t_send_threshold++;
1161
  t_prod_pos++;
1162
  items.push({
1163
+ "item_id": t_json_name[t_item].tvc_i,
1164
+ "item_name": t_json_name[t_item].tvc_n,
1165
+ "item_category": t_json_name[t_item].tvc_c,
1166
  "price": t_json_name[t_item].tvc_p,
1167
+ "currency": tvc_lc
1168
  });
1169
+ if(t_json_length > ' . esc_js($impression_threshold) . ' ){
 
 
1170
  if((t_send_threshold%' . esc_js($impression_threshold) . ')==0){
1171
  t_json_length=t_json_length-' . esc_js($impression_threshold) . ';
1172
+ gtag("event", "view_item_list", {
1173
+ "event_category":"Enhanced-Ecommerce",
1174
+ "event_label":"product_impression_"+t_action,
1175
+ "items":items,
1176
+ "non_interaction": true
1177
+ });
1178
+ items = [];
1179
+ }
1180
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1181
+ gtag("event","view_item_list", {
1182
+ "value": t_json_name[t_item].tvc_p,
1183
+ "items": [
1184
+ {
1185
+ "id": t_json_name[t_item].tvc_i,
1186
+ "google_business_vertical": "retail"
1187
+ }
1188
+ ]
1189
+ });
1190
+ }
1191
+ }else{
1192
+ t_json_length--;
1193
  if(t_json_length==0){
1194
+ gtag("event", "view_item_list", {
1195
+ "event_category":"Enhanced-Ecommerce",
1196
+ "event_label":"product_impression_"+t_action,
1197
+ "items":items,
1198
+ "non_interaction": true
1199
+ });
1200
+ items = [];
1201
+ }
1202
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1203
+ gtag("event","view_item_list", {
1204
+ "value": t_json_name[t_item].tvc_p,
1205
+ "items": [
1206
+ {
1207
+ "id": t_json_name[t_item].tvc_i,
1208
+ "google_business_vertical": "retail"
1209
+ }
1210
+ ]
1211
+ });
1212
+ }
1213
+ }
1214
+ }
1215
+ }
1216
 
1217
  //function for comparing urls in json object
1218
  function prod_exists_in_JSON(t_url,t_json_name,t_action){
1219
+ if(t_json_name.hasOwnProperty(t_url)){
1220
+ t_call_fired=true;
1221
+ gtag("event", "select_item", {
1222
+ "event_category":"Enhanced-Ecommerce",
1223
+ "event_label":"product_click_"+t_action,
1224
+ "items": [
1225
+ {
1226
+ "item_id":t_json_name[t_url].tvc_i,
1227
+ "item_name": t_json_name[t_url].tvc_n,
1228
+ "item_category":t_json_name[t_url].tvc_c,
1229
+ "price": t_json_name[t_url].tvc_p,
1230
+ "currency": tvc_lc
1231
+ }
1232
+ ],
1233
+ "non_interaction": true
1234
+ });
1235
+
1236
+ }else{
1237
+ t_call_fired=false;
1238
+ }
1239
+ return t_call_fired;
1240
  }
1241
  function prod_ATC_link_exists(t_url,t_ATC_json_name,t_prod_data_json,t_qty){
1242
  t_prod_url_key=t_ATC_json_name[t_url]["ATC-link"];
 
1243
  if(t_prod_data_json.hasOwnProperty(t_prod_url_key)){
1244
  t_call_fired=true;
1245
  // Enhanced E-commerce Add to cart clicks
1248
  "event_label":"add_to_cart_click",
1249
  "non_interaction": true,
1250
  "items": [{
1251
+ "item_id" : t_prod_data_json[t_prod_url_key].tvc_i,
1252
+ "item_name":t_prod_data_json[t_prod_url_key].tvc_n,
1253
+ "item_category" : t_prod_data_json[t_prod_url_key].tvc_c,
1254
  "price": t_prod_data_json[t_prod_url_key].tvc_p,
1255
+ "currency": tvc_lc,
1256
  "quantity" :t_qty
1257
  }]
1258
  });
1259
+
1260
+ if(adsTringId != "" && ( ads_ert == 1 || ads_edrt == 1)){
1261
+ gtag("event","add_to_cart", {
1262
+ "value": t_prod_data_json[t_prod_url_key].tvc_p,
1263
+ "items": [
1264
+ {
1265
+ "id": t_prod_data_json[t_prod_url_key].tvc_i,
1266
+ "google_business_vertical": "retail"
1267
+ }
1268
+ ]
1269
+ });
1270
+ }
1271
  }else{
1272
+ t_call_fired=false;
1273
  }
1274
  return t_call_fired;
 
1275
  }
 
1276
  ';
1277
+ }
1278
  if(is_home() || is_front_page()){
1279
  $hmpg_impressions_jQ .='
1280
  if(tvc_fp.length !== 0){
1450
 
1451
  //Cart Page item Array to Json
1452
  $this->wc_version_compare("tvc_cc=" . json_encode($cartpage_prod_array_main) . ";");
1453
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH") {
1454
+ $code = '
1455
+ //set local currencies
1456
+ gtag("set", {"currency": tvc_lc});
1457
+ $("a[href*=\"?remove_item\"]").click(function(){
1458
+ t_url=jQuery(this).attr("href");
1459
+ gtag("event", "remove_from_cart", {
1460
+ "event_category":"Enhanced-Ecommerce",
1461
+ "event_label":"remove_from_cart_click",
1462
+ "items": [{
1463
+ "id":tvc_cc[t_url].tvc_i,
1464
+ "name": tvc_cc[t_url].tvc_n,
1465
+ "category":tvc_cc[t_url].tvc_c,
1466
+ "price": tvc_cc[t_url].tvc_p,
1467
+ "quantity": tvc_cc[t_url].tvc_q
1468
+ }],
1469
+ "non_interaction": true
1470
+ });
1471
+ });
1472
+
1473
+ ';
1474
+ //check woocommerce version
1475
+ $this->wc_version_compare($code);
1476
+ }
1477
 
1478
+ if($this->gm_id && $this->tracking_option == "GA4") {
1479
+ $code = '
1480
+ $("a[href*=\"?remove_item\"]").click(function(){
1481
+ t_url=jQuery(this).attr("href");
1482
+ gtag("event", "remove_from_cart", {
1483
+ "event_category":"Enhanced-Ecommerce",
1484
+ "event_label":"remove_from_cart_click",
1485
+ "currency": tvc_lc,
1486
+ "items": [{
1487
+ "item_id":tvc_cc[t_url].tvc_i,
1488
+ "item_name": tvc_cc[t_url].tvc_n,
1489
+ "item_category":tvc_cc[t_url].tvc_c,
1490
+ "price": tvc_cc[t_url].tvc_p,
1491
+ "currency": tvc_lc,
1492
+ "quantity": tvc_cc[t_url].tvc_q
1493
+ }],
1494
+ "non_interaction": true
1495
+ });
1496
+ });
1497
+
1498
+ ';
1499
+ //check woocommerce version
1500
+ $this->wc_version_compare($code);
1501
+ }
1502
  }
1503
 
1504
  /**
1513
  }
1514
  //call fn to make json
1515
  $this->get_ordered_items();
1516
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH") {
1517
+ $code= '
1518
+ var items = [];
1519
+ gtag("set", {"currency": tvc_lc});
1520
+ for(var t_item in tvc_ch){
1521
+ items.push({
1522
+ "id": tvc_ch[t_item].tvc_i,
1523
+ "name": tvc_ch[t_item].tvc_n,
1524
+ "category": tvc_ch[t_item].tvc_c,
1525
+ "attributes": tvc_ch[t_item].tvc_attr,
1526
+ "price": tvc_ch[t_item].tvc_p,
1527
+ "quantity": tvc_ch[t_item].tvc_q
1528
+ });
1529
+ }';
1530
+
1531
+ $code_step_1 = $code . 'gtag("event", "begin_checkout", {"event_category":"Enhanced-Ecommerce",
1532
+ "event_label":"checkout_step_1","items":items,"non_interaction": true });';
1533
+
1534
+ //check woocommerce version and add code
1535
+ $this->wc_version_compare($code_step_1);
1536
+ }
1537
+
1538
+ if( $this->gm_id && $this->tracking_option == "GA4") {
1539
+ $code = '
1540
  var items = [];
 
1541
  for(var t_item in tvc_ch){
1542
  items.push({
1543
+ "item_id": tvc_ch[t_item].tvc_i,
1544
+ "item_name": tvc_ch[t_item].tvc_n,
1545
+ "item_category": tvc_ch[t_item].tvc_c,
1546
+ "item_variant": tvc_ch[t_item].tvc_attr,
1547
  "price": tvc_ch[t_item].tvc_p,
1548
  "quantity": tvc_ch[t_item].tvc_q
1549
  });
1550
  }';
1551
 
1552
+ $code_step_1 = $code . 'gtag("event", "begin_checkout", {
1553
+ "event_category":"Enhanced-Ecommerce",
1554
+ "event_label":"checkout_step_1",
1555
+ "items":items,
1556
+ "non_interaction": true
1557
+ });';
1558
 
1559
+ //check woocommerce version and add code
1560
+ $this->wc_version_compare($code_step_1);
1561
+ }
1562
  }
1563
 
1564
  /**
1571
  if ($this->disable_tracking($this->ga_eeT)) {
1572
  return;
1573
  }
1574
+ if($this->ga_id || $this->tracking_option == "UA" || $this->tracking_option == "BOTH" || $this->gm_id) {
1575
+ $code= '
1576
+ var items = [];
1577
+ gtag("set", {"currency": tvc_lc});
1578
+ for(var t_item in tvc_ch){
1579
+ items.push({
1580
+ "id": tvc_ch[t_item].tvc_i,
1581
+ "name": tvc_ch[t_item].tvc_n,
1582
+ "category": tvc_ch[t_item].tvc_c,
1583
+ "attributes": tvc_ch[t_item].tvc_attr,
1584
+ "price": tvc_ch[t_item].tvc_p,
1585
+ "quantity": tvc_ch[t_item].tvc_q
1586
+ });
1587
+ }';
1588
+
1589
+ $code_step_2 = $code . 'gtag("event", "checkout_progress", {"checkout_step": 2,"event_category":"Enhanced-Ecommerce",
1590
+ "event_label":"checkout_step_2","items":items,"non_interaction": true });';
1591
+
1592
+ //if logged in and first name is filled - Guest Check out
1593
+ if (is_user_logged_in()) {
1594
+ $step2_onFocus = 't_tracked_focus=0; if(t_tracked_focus===0){' . $code_step_2 . ' t_tracked_focus++;}';
1595
+ } else {
1596
+ //first name on focus call fire
1597
+ $step2_onFocus = 't_tracked_focus=0; jQuery("input[name=billing_first_name]").on("focus",function(){ if(t_tracked_focus===0){' . $code_step_2 . ' t_tracked_focus++;}});';
1598
+ }
1599
+ //check woocommerce version and add code
1600
+ $this->wc_version_compare($step2_onFocus);
1601
  }
 
 
1602
  }
1603
 
1604
  /**
1608
  * @return void
1609
  */
1610
  public function checkout_step_3_tracking() {
1611
+
1612
  if ($this->disable_tracking($this->ga_eeT)) {
1613
  return;
1614
  }