class-wc-admin-setup-wizard-tracking.php
5 years ago
class-wc-coupon-tracking.php
2 weeks ago
class-wc-coupons-tracking.php
9 months ago
class-wc-extensions-tracking.php
2 years ago
class-wc-importer-tracking.php
2 weeks ago
class-wc-order-tracking.php
6 years ago
class-wc-orders-tracking.php
1 year ago
class-wc-product-collection-block-tracking.php
9 months ago
class-wc-products-tracking.php
2 months ago
class-wc-settings-tracking.php
1 year ago
class-wc-status-tracking.php
9 months ago
class-wc-theme-tracking.php
1 year ago
class-wc-products-tracking.php
608 lines
| 1 | <?php |
| 2 | /** |
| 3 | * WooCommerce Import Tracking |
| 4 | * |
| 5 | * @package WooCommerce\Tracks |
| 6 | */ |
| 7 | |
| 8 | use Automattic\Jetpack\Constants; |
| 9 | use Automattic\WooCommerce\Internal\Admin\WCAdminAssets; |
| 10 | |
| 11 | defined( 'ABSPATH' ) || exit; |
| 12 | |
| 13 | require_once WC_ABSPATH . 'includes/admin/wc-admin-functions.php'; |
| 14 | |
| 15 | /** |
| 16 | * This class adds actions to track usage of WooCommerce Products. |
| 17 | */ |
| 18 | class WC_Products_Tracking { |
| 19 | |
| 20 | /** |
| 21 | * Tracks source. |
| 22 | */ |
| 23 | public const TRACKS_SOURCE = 'product-legacy-editor'; |
| 24 | |
| 25 | /** |
| 26 | * Deferred Tracks callback. |
| 27 | * |
| 28 | * @internal |
| 29 | * @since 10.6.0 |
| 30 | */ |
| 31 | public const TRACK_PRODUCT_PUBLISHED_CALLBACK = 'track_product_published'; |
| 32 | |
| 33 | /** |
| 34 | * Init tracking. |
| 35 | */ |
| 36 | public function init() { |
| 37 | add_action( 'load-edit.php', array( $this, 'track_products_view' ), 10 ); |
| 38 | add_action( 'load-edit-tags.php', array( $this, 'track_categories_and_tags_view' ), 10, 2 ); |
| 39 | add_action( 'edit_post', array( $this, 'track_product_updated' ), 10, 2 ); |
| 40 | add_action( 'wp_after_insert_post', array( $this, 'track_product_published' ), 10, 4 ); |
| 41 | add_action( 'created_product_cat', array( $this, 'track_product_category_created' ) ); |
| 42 | add_action( 'edited_product_cat', array( $this, 'track_product_category_updated' ) ); |
| 43 | add_action( 'add_meta_boxes_product', array( $this, 'track_product_updated_client_side' ), 10 ); |
| 44 | add_action( 'admin_enqueue_scripts', array( $this, 'possibly_add_product_tracking_scripts' ) ); |
| 45 | add_action( 'admin_enqueue_scripts', array( $this, 'possibly_add_product_import_scripts' ) ); |
| 46 | add_action( 'admin_enqueue_scripts', array( $this, 'possibly_add_attribute_tracking_scripts' ) ); |
| 47 | add_action( 'admin_enqueue_scripts', array( $this, 'possibly_add_tag_tracking_scripts' ) ); |
| 48 | add_action( self::TRACK_PRODUCT_PUBLISHED_CALLBACK, array( $this, 'track_product_published_maybe_defer' ), 10, 3 ); |
| 49 | } |
| 50 | |
| 51 | /** |
| 52 | * Send a Tracks event when the Products page is viewed. |
| 53 | */ |
| 54 | public function track_products_view() { |
| 55 | // We only record Tracks event when no `_wp_http_referer` query arg is set, since |
| 56 | // when searching, the request gets sent from the browser twice, |
| 57 | // once with the `_wp_http_referer` and once without it. |
| 58 | // |
| 59 | // Otherwise, we would double-record the view and search events. |
| 60 | |
| 61 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 62 | if ( |
| 63 | isset( $_GET['post_type'] ) |
| 64 | && 'product' === wp_unslash( $_GET['post_type'] ) |
| 65 | && ! isset( $_GET['_wp_http_referer'] ) |
| 66 | ) { |
| 67 | // phpcs:enable |
| 68 | |
| 69 | WC_Tracks::record_event( 'products_view' ); |
| 70 | |
| 71 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 72 | if ( |
| 73 | isset( $_GET['s'] ) |
| 74 | && 0 < strlen( sanitize_text_field( wp_unslash( $_GET['s'] ) ) ) |
| 75 | ) { |
| 76 | // phpcs:enable |
| 77 | |
| 78 | WC_Tracks::record_event( 'products_search' ); |
| 79 | } |
| 80 | } |
| 81 | } |
| 82 | |
| 83 | /** |
| 84 | * Send a Tracks event when the Products Categories and Tags page is viewed. |
| 85 | */ |
| 86 | public function track_categories_and_tags_view() { |
| 87 | // We only record Tracks event when no `_wp_http_referer` query arg is set, since |
| 88 | // when searching, the request gets sent from the browser twice, |
| 89 | // once with the `_wp_http_referer` and once without it. |
| 90 | // |
| 91 | // Otherwise, we would double-record the view and search events. |
| 92 | |
| 93 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 94 | if ( |
| 95 | isset( $_GET['post_type'] ) |
| 96 | && 'product' === wp_unslash( $_GET['post_type'] ) |
| 97 | && isset( $_GET['taxonomy'] ) |
| 98 | && ! isset( $_GET['_wp_http_referer'] ) |
| 99 | ) { |
| 100 | $taxonomy = wp_unslash( $_GET['taxonomy'] ); |
| 101 | // phpcs:enable |
| 102 | |
| 103 | if ( 'product_cat' === $taxonomy ) { |
| 104 | WC_Tracks::record_event( 'categories_view' ); |
| 105 | } elseif ( 'product_tag' === $taxonomy ) { |
| 106 | WC_Tracks::record_event( 'tags_view' ); |
| 107 | } |
| 108 | |
| 109 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 110 | if ( |
| 111 | isset( $_GET['s'] ) |
| 112 | && 0 < strlen( sanitize_text_field( wp_unslash( $_GET['s'] ) ) ) |
| 113 | ) { |
| 114 | // phpcs:enable |
| 115 | |
| 116 | if ( 'product_cat' === $taxonomy ) { |
| 117 | WC_Tracks::record_event( 'categories_search' ); |
| 118 | } elseif ( 'product_tag' === $taxonomy ) { |
| 119 | WC_Tracks::record_event( 'tags_search' ); |
| 120 | } |
| 121 | } |
| 122 | } |
| 123 | } |
| 124 | |
| 125 | /** |
| 126 | * Send a Tracks event when a product is updated. |
| 127 | * |
| 128 | * @param int $product_id Product id. |
| 129 | * @param object $post WordPress post. |
| 130 | */ |
| 131 | public function track_product_updated( $product_id, $post ) { |
| 132 | if ( 'product' !== $post->post_type ) { |
| 133 | return; |
| 134 | } |
| 135 | |
| 136 | /* phpcs:disable WooCommerce.Commenting.CommentHooks.MissingHookComment */ |
| 137 | $source = apply_filters( 'woocommerce_product_source', self::is_importing() ? 'import' : self::TRACKS_SOURCE ); |
| 138 | $properties = array( |
| 139 | 'product_id' => $product_id, |
| 140 | 'source' => $source, |
| 141 | ); |
| 142 | /* phpcs: enable */ |
| 143 | |
| 144 | WC_Tracks::record_event( 'product_edit', $properties ); |
| 145 | } |
| 146 | |
| 147 | /** |
| 148 | * Track the Update button being clicked on the client side. |
| 149 | * This is needed because `track_product_updated` (using the `edit_post` |
| 150 | * hook) is called in response to a number of other triggers. |
| 151 | * |
| 152 | * @param WP_Post $post The post, not used. |
| 153 | */ |
| 154 | public function track_product_updated_client_side( $post ) { |
| 155 | $handle = 'wc-tracks-product-updated-client-side'; |
| 156 | wp_register_script( $handle, '', array( 'jquery' ), WC_VERSION, array( 'in_footer' => true ) ); |
| 157 | wp_enqueue_script( $handle ); |
| 158 | wp_add_inline_script( |
| 159 | $handle, |
| 160 | " |
| 161 | jQuery(function($) { |
| 162 | if ( $( 'h1.wp-heading-inline' ).text().trim() === '" . esc_js( __( 'Edit product', 'woocommerce' ) ) . "') { |
| 163 | var initialStockValue = $( '#_stock' ).val(); |
| 164 | var isBlockEditor = false; |
| 165 | var child_element = '#publish'; |
| 166 | |
| 167 | if ( $( '.block-editor' ).length !== 0 && $( '.block-editor' )[0] ) { |
| 168 | isBlockEditor = true; |
| 169 | } |
| 170 | |
| 171 | if ( isBlockEditor ) { |
| 172 | child_element = '.editor-post-publish-button'; |
| 173 | } |
| 174 | |
| 175 | $( '#wpwrap' ).on( 'click', child_element, function() { |
| 176 | var description_value = ''; |
| 177 | var tagsText = ''; |
| 178 | var currentStockValue = $( '#_stock' ).val(); |
| 179 | |
| 180 | function getProductTypeOptions() { |
| 181 | const productTypeOptionsCheckboxes = $( 'input[type=\"checkbox\"][data-product-type-option-id]' ); |
| 182 | const productTypeOptions = productTypeOptionsCheckboxes.map( function() { |
| 183 | return { |
| 184 | id: $( this ).data( 'product-type-option-id' ), |
| 185 | isEnabled: $( this ).is( ':checked' ), |
| 186 | }; |
| 187 | } ).get(); |
| 188 | return productTypeOptions; |
| 189 | } |
| 190 | |
| 191 | function getProductTypeOptionsString( productTypeOptions ) { |
| 192 | return productTypeOptions |
| 193 | .filter( productTypeOption => productTypeOption.isEnabled ) |
| 194 | .map( productTypeOption => productTypeOption.id ) |
| 195 | .join( ', ' ); |
| 196 | } |
| 197 | |
| 198 | const productTypeOptions = getProductTypeOptions(); |
| 199 | const productTypeOptionsString = getProductTypeOptionsString( productTypeOptions ); |
| 200 | |
| 201 | if ( ! isBlockEditor ) { |
| 202 | tagsText = $( '[name=\"tax_input[product_tag]\"]' ).val(); |
| 203 | if ( $( '#content' ).is( ':visible' ) ) { |
| 204 | description_value = $( '#content' ).val(); |
| 205 | } else if ( typeof tinymce === 'object' && tinymce.get( 'content' ) ) { |
| 206 | description_value = tinymce.get( 'content' ).getContent(); |
| 207 | } |
| 208 | } else { |
| 209 | description_value = $( '.block-editor-rich-text__editable' ).text(); |
| 210 | } |
| 211 | |
| 212 | // We can't just check the number of '.woocommerce_attribute' elements because |
| 213 | // there might be empty ones, which get stripped out when saved. So, we'll check |
| 214 | // whether the name and values have been filled out. |
| 215 | var numberOfAttributes = $( '.woocommerce_attribute' ).filter( function () { |
| 216 | var attributeElement = $( this ); |
| 217 | var attributeName = attributeElement.find( 'input.attribute_name' ).val(); |
| 218 | var attributeValues = attributeElement.find( 'textarea[name^=\"attribute_values\"]' ).val(); |
| 219 | |
| 220 | return attributeName !== '' && attributeValues !== ''; |
| 221 | } ).length; |
| 222 | |
| 223 | var properties = { |
| 224 | attributes: numberOfAttributes, |
| 225 | categories: $( '[name=\"tax_input[product_cat][]\"]:checked' ).length, |
| 226 | cross_sells: $( '#crosssell_ids option' ).length ? 'Yes' : 'No', |
| 227 | description: description_value.trim() !== '' ? 'Yes' : 'No', |
| 228 | enable_reviews: $( '#comment_status' ).is( ':checked' ) ? 'Yes' : 'No', |
| 229 | is_virtual: $( '#_virtual' ).is( ':checked' ) ? 'Yes' : 'No', |
| 230 | is_block_editor: isBlockEditor, |
| 231 | is_downloadable: $( '#_downloadable' ).is( ':checked' ) ? 'Yes' : 'No', |
| 232 | manage_stock: $( '#_manage_stock' ).is( ':checked' ) ? 'Yes' : 'No', |
| 233 | menu_order: parseInt( $( '#menu_order' ).val(), 10 ) !== 0 ? 'Yes' : 'No', |
| 234 | product_gallery: $( '#product_images_container .product_images > li' ).length, |
| 235 | product_image: $( '#_thumbnail_id' ).val() > 0 ? 'Yes' : 'No', |
| 236 | product_type: $( '#product-type' ).val(), |
| 237 | product_type_options_string: productTypeOptionsString, |
| 238 | purchase_note: $( '#_purchase_note' ).val().length ? 'yes' : 'no', |
| 239 | sale_price: $( '#_sale_price' ).val() ? 'yes' : 'no', |
| 240 | short_description: $( '#excerpt' ).val() ? 'yes' : 'no', |
| 241 | stock_quantity_update: ( initialStockValue != currentStockValue ) ? 'Yes' : 'No', |
| 242 | tags: tagsText.length > 0 ? tagsText.split( ',' ).length : 0, |
| 243 | upsells: $( '#upsell_ids option' ).length ? 'Yes' : 'No', |
| 244 | weight: $( '#_weight' ).val() ? 'Yes' : 'No', |
| 245 | }; |
| 246 | if ( window.wcTracks && window.wcTracks.recordEvent ) { |
| 247 | window.wcTracks.recordEvent( 'product_update', properties ); |
| 248 | } |
| 249 | } ); |
| 250 | } |
| 251 | }); |
| 252 | " |
| 253 | ); |
| 254 | } |
| 255 | |
| 256 | /** |
| 257 | * Get the IDs of the possible product type options. |
| 258 | * |
| 259 | * @return array |
| 260 | */ |
| 261 | private static function get_possible_product_type_options_ids() { |
| 262 | $product_type_options_ids = |
| 263 | array_values( |
| 264 | array_map( |
| 265 | function ( $product_type_option ) { |
| 266 | return $product_type_option['id']; |
| 267 | }, |
| 268 | /* phpcs:disable WooCommerce.Commenting.CommentHooks.MissingHookComment */ |
| 269 | apply_filters( |
| 270 | 'product_type_options', |
| 271 | wc_get_default_product_type_options(), |
| 272 | ) |
| 273 | /* phpcs: enable */ |
| 274 | ) |
| 275 | ); |
| 276 | |
| 277 | return $product_type_options_ids; |
| 278 | } |
| 279 | |
| 280 | /** |
| 281 | * Get the product type options for a product. |
| 282 | * |
| 283 | * @param int $post_id The ID of the product. |
| 284 | * |
| 285 | * @return array |
| 286 | */ |
| 287 | private static function get_product_type_options( $post_id ) { |
| 288 | $possible_product_type_options_ids = self::get_possible_product_type_options_ids(); |
| 289 | $post_meta = get_post_meta( $post_id ); |
| 290 | $product_type_options = array(); |
| 291 | |
| 292 | foreach ( $possible_product_type_options_ids as $product_type_option_id ) { |
| 293 | $product_type_options[ $product_type_option_id ] = isset( $post_meta[ $product_type_option_id ] ) ? $post_meta[ $product_type_option_id ][0] : 'no'; |
| 294 | } |
| 295 | |
| 296 | return $product_type_options; |
| 297 | } |
| 298 | |
| 299 | /** |
| 300 | * Get a comma-separated string of the product type options that are enabled. |
| 301 | * |
| 302 | * @param array $product_type_options The product type options. |
| 303 | * |
| 304 | * @return string |
| 305 | */ |
| 306 | private static function get_product_type_options_string( $product_type_options ) { |
| 307 | return implode( |
| 308 | ', ', |
| 309 | array_keys( |
| 310 | array_filter( |
| 311 | $product_type_options, |
| 312 | function ( $is_enabled ) { |
| 313 | return 'yes' === $is_enabled; |
| 314 | } |
| 315 | ) |
| 316 | ) |
| 317 | ); |
| 318 | } |
| 319 | |
| 320 | /** |
| 321 | * Send a Tracks event when a product is published. |
| 322 | * |
| 323 | * @param int $post_id Post ID. |
| 324 | * @param WP_Post $post Post object. |
| 325 | * @param bool $update Whether this is an existing post being updated. |
| 326 | * @param null|WP_Post $post_before Null for new posts, the WP_Post object prior |
| 327 | * to the update for updated posts. |
| 328 | */ |
| 329 | public function track_product_published( $post_id, $post, $update, $post_before ) { |
| 330 | if ( |
| 331 | 'product' !== $post->post_type || |
| 332 | 'publish' !== $post->post_status || |
| 333 | ( $post_before && 'publish' === $post_before->post_status ) |
| 334 | ) { |
| 335 | return; |
| 336 | } |
| 337 | |
| 338 | $product = wc_get_product( $post_id ); |
| 339 | |
| 340 | $product_type_options = self::get_product_type_options( $post_id ); |
| 341 | $product_type_options_string = self::get_product_type_options_string( $product_type_options ); |
| 342 | |
| 343 | $is_importing = self::is_importing(); |
| 344 | $properties = array( |
| 345 | 'attributes' => count( $product->get_attributes() ), |
| 346 | 'categories' => count( $product->get_category_ids() ), |
| 347 | 'cross_sells' => ! empty( $product->get_cross_sell_ids() ) ? 'yes' : 'no', |
| 348 | 'description' => $product->get_description() ? 'yes' : 'no', |
| 349 | 'dimensions' => wc_format_dimensions( $product->get_dimensions( false ) ) !== 'N/A' ? 'yes' : 'no', |
| 350 | 'enable_reviews' => $product->get_reviews_allowed() ? 'yes' : 'no', |
| 351 | 'is_downloadable' => $product->is_downloadable() ? 'yes' : 'no', |
| 352 | 'is_virtual' => $product->is_virtual() ? 'yes' : 'no', |
| 353 | 'manage_stock' => $product->get_manage_stock() ? 'yes' : 'no', |
| 354 | 'menu_order' => $product->get_menu_order() ? 'yes' : 'no', |
| 355 | 'product_id' => $post_id, |
| 356 | 'product_gallery' => count( $product->get_gallery_image_ids() ), |
| 357 | 'product_image' => $product->get_image_id() ? 'yes' : 'no', |
| 358 | 'product_type' => $product->get_type(), |
| 359 | 'product_type_options' => $product_type_options_string, |
| 360 | 'purchase_note' => $product->get_purchase_note() ? 'yes' : 'no', |
| 361 | 'sale_price' => $product->get_sale_price() ? 'yes' : 'no', |
| 362 | 'source' => apply_filters( 'woocommerce_product_source', $is_importing ? 'import' : self::TRACKS_SOURCE ), |
| 363 | 'short_description' => $product->get_short_description() ? 'yes' : 'no', |
| 364 | 'tags' => count( $product->get_tag_ids() ), |
| 365 | 'upsells' => ! empty( $product->get_upsell_ids() ) ? 'yes' : 'no', |
| 366 | 'weight' => $product->get_weight() ? 'yes' : 'no', |
| 367 | 'global_unique_id' => $product->get_global_unique_id() ? 'yes' : 'no', |
| 368 | ); |
| 369 | |
| 370 | $this->track_product_published_maybe_defer( 'product_add_publish', $properties, $is_importing ); |
| 371 | } |
| 372 | |
| 373 | /** |
| 374 | * Tracks the event, allowing deferred/asynchronous event recording. |
| 375 | * |
| 376 | * @internal |
| 377 | * @since 10.6.0 |
| 378 | * |
| 379 | * @param string $event_name The name of the event. |
| 380 | * @param array $event_properties Custom properties to send with the event. |
| 381 | * @param bool $defer Whether to defer the event publishing. |
| 382 | * @return void |
| 383 | */ |
| 384 | public function track_product_published_maybe_defer( string $event_name, array $event_properties, bool $defer = false ): void { |
| 385 | if ( $defer ) { |
| 386 | as_schedule_single_action( |
| 387 | time(), |
| 388 | self::TRACK_PRODUCT_PUBLISHED_CALLBACK, |
| 389 | array( $event_name, $event_properties ), |
| 390 | 'woocommerce-tracks' |
| 391 | ); |
| 392 | } else { |
| 393 | WC_Tracks::record_event( $event_name, $event_properties ); |
| 394 | } |
| 395 | } |
| 396 | |
| 397 | /** |
| 398 | * Send a Tracks event when a product category is created. |
| 399 | * |
| 400 | * @param int $category_id Category ID. |
| 401 | */ |
| 402 | public function track_product_category_created( $category_id ) { |
| 403 | // phpcs:disable WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 404 | // Only track category creation from the edit product screen or the |
| 405 | // category management screen (which both occur via AJAX). |
| 406 | if ( |
| 407 | ! Constants::is_defined( 'DOING_AJAX' ) || |
| 408 | empty( $_POST['action'] ) || |
| 409 | ( |
| 410 | // Product Categories screen. |
| 411 | 'add-tag' !== $_POST['action'] && |
| 412 | // Edit Product screen. |
| 413 | 'add-product_cat' !== $_POST['action'] |
| 414 | ) |
| 415 | ) { |
| 416 | return; |
| 417 | } |
| 418 | |
| 419 | $category = get_term( $category_id, 'product_cat' ); |
| 420 | $parent_category = $category->parent > 0 ? 'Other' : 'None'; |
| 421 | if ( $category->parent > 0 ) { |
| 422 | $parent = get_term( $category_id, 'product_cat' ); |
| 423 | if ( 'uncategorized' === $parent->name ) { |
| 424 | $parent_category = 'Uncategorized'; |
| 425 | } |
| 426 | } |
| 427 | $properties = array( |
| 428 | 'category_id' => $category_id, |
| 429 | 'parent_id' => $category->parent, |
| 430 | 'parent_category' => $parent_category, |
| 431 | 'page' => ( 'add-tag' === $_POST['action'] ) ? 'categories' : 'product', |
| 432 | 'display_type' => isset( $_POST['display_type'] ) ? wp_unslash( $_POST['display_type'] ) : '', |
| 433 | 'image' => isset( $_POST['product_cat_thumbnail_id'] ) && '' !== $_POST['product_cat_thumbnail_id'] ? 'Yes' : 'No', |
| 434 | ); |
| 435 | // phpcs:enable |
| 436 | |
| 437 | WC_Tracks::record_event( 'product_category_add', $properties ); |
| 438 | } |
| 439 | |
| 440 | /** |
| 441 | * Send a Tracks event when a product category is updated. |
| 442 | * |
| 443 | * @param int $category_id Category ID. |
| 444 | */ |
| 445 | public function track_product_category_updated( $category_id ) { |
| 446 | // phpcs:disable WordPress.Security.NonceVerification.Missing |
| 447 | // Only track category creation from the edit product screen or the |
| 448 | // category management screen (which both occur via AJAX). |
| 449 | if ( |
| 450 | empty( $_POST['action'] ) || |
| 451 | ( 'editedtag' !== $_POST['action'] && 'inline-save-tax' !== $_POST['action'] ) |
| 452 | ) { |
| 453 | return; |
| 454 | } |
| 455 | // phpcs:enable |
| 456 | |
| 457 | WC_Tracks::record_event( 'product_category_update' ); |
| 458 | } |
| 459 | |
| 460 | /** |
| 461 | * Adds the tracking scripts for product filtering actions. |
| 462 | * |
| 463 | * @param string $hook Hook of the current page. |
| 464 | * @return string|boolean |
| 465 | */ |
| 466 | protected function get_product_screen( $hook ) { |
| 467 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 468 | if ( |
| 469 | 'edit.php' === $hook && |
| 470 | isset( $_GET['post_type'] ) && |
| 471 | 'product' === wp_unslash( $_GET['post_type'] ) |
| 472 | ) { |
| 473 | return 'list'; |
| 474 | } |
| 475 | |
| 476 | if ( |
| 477 | 'post-new.php' === $hook && |
| 478 | isset( $_GET['post_type'] ) && |
| 479 | 'product' === wp_unslash( $_GET['post_type'] ) |
| 480 | ) { |
| 481 | return 'new'; |
| 482 | } |
| 483 | |
| 484 | if ( |
| 485 | 'post.php' === $hook && |
| 486 | isset( $_GET['post'] ) && |
| 487 | 'product' === get_post_type( intval( $_GET['post'] ) ) |
| 488 | ) { |
| 489 | return 'edit'; |
| 490 | } |
| 491 | |
| 492 | if ( 'product_page_product_importer' === $hook ) { |
| 493 | return 'import'; |
| 494 | } |
| 495 | |
| 496 | // phpcs:enable |
| 497 | |
| 498 | return false; |
| 499 | } |
| 500 | |
| 501 | /** |
| 502 | * Adds the tracking scripts for product filtering actions. |
| 503 | * |
| 504 | * @param string $hook Page hook. |
| 505 | */ |
| 506 | public function possibly_add_product_tracking_scripts( $hook ) { |
| 507 | $product_screen = $this->get_product_screen( $hook ); |
| 508 | if ( ! $product_screen ) { |
| 509 | return; |
| 510 | } |
| 511 | |
| 512 | WCAdminAssets::register_script( 'wp-admin-scripts', 'product-tracking', false ); |
| 513 | wp_localize_script( |
| 514 | 'wc-admin-product-tracking', |
| 515 | 'productScreen', |
| 516 | array( |
| 517 | 'name' => $product_screen, |
| 518 | ) |
| 519 | ); |
| 520 | } |
| 521 | |
| 522 | /** |
| 523 | * Adds the tracking scripts for product setting pages. |
| 524 | * |
| 525 | * @param string $hook Page hook. |
| 526 | */ |
| 527 | public function possibly_add_product_import_scripts( $hook ) { |
| 528 | $product_screen = $this->get_product_screen( $hook ); |
| 529 | |
| 530 | if ( 'import' !== $product_screen ) { |
| 531 | return; |
| 532 | } |
| 533 | |
| 534 | WCAdminAssets::register_script( 'wp-admin-scripts', 'product-import-tracking', false ); |
| 535 | |
| 536 | } |
| 537 | |
| 538 | /** |
| 539 | * Adds the tracking scripts for product attributes filtering actions. |
| 540 | * |
| 541 | * @param string $hook Page hook. |
| 542 | */ |
| 543 | public function possibly_add_attribute_tracking_scripts( $hook ) { |
| 544 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 545 | if ( |
| 546 | 'product_page_product_attributes' !== $hook || |
| 547 | ! isset( $_GET['page'] ) || |
| 548 | 'product_attributes' !== wp_unslash( $_GET['page'] ) |
| 549 | ) { |
| 550 | return; |
| 551 | } |
| 552 | // phpcs:enable |
| 553 | |
| 554 | WCAdminAssets::register_script( 'wp-admin-scripts', 'attributes-tracking', false ); |
| 555 | } |
| 556 | |
| 557 | /** |
| 558 | * Adds the tracking scripts for tags and categories filtering actions. |
| 559 | * |
| 560 | * @param string $hook Page hook. |
| 561 | */ |
| 562 | public function possibly_add_tag_tracking_scripts( $hook ) { |
| 563 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized, WordPress.Security.NonceVerification |
| 564 | if ( |
| 565 | 'edit-tags.php' !== $hook || |
| 566 | ! isset( $_GET['post_type'] ) || |
| 567 | 'product' !== wp_unslash( $_GET['post_type'] ) |
| 568 | ) { |
| 569 | return; |
| 570 | } |
| 571 | // phpcs:enable |
| 572 | |
| 573 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 574 | if ( |
| 575 | isset( $_GET['taxonomy'] ) && |
| 576 | 'product_tag' === wp_unslash( $_GET['taxonomy'] ) |
| 577 | ) { |
| 578 | WCAdminAssets::register_script( 'wp-admin-scripts', 'tags-tracking', false ); |
| 579 | return; |
| 580 | } |
| 581 | |
| 582 | // phpcs:disable WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 583 | if ( |
| 584 | isset( $_GET['taxonomy'] ) && |
| 585 | 'product_cat' === wp_unslash( $_GET['taxonomy'] ) |
| 586 | ) { |
| 587 | WCAdminAssets::register_script( 'wp-admin-scripts', 'category-tracking', false ); |
| 588 | return; |
| 589 | } |
| 590 | WCAdminAssets::register_script( 'wp-admin-scripts', 'add-term-tracking', false ); |
| 591 | } |
| 592 | |
| 593 | /** |
| 594 | * Check if the current process is importing products. |
| 595 | * |
| 596 | * @return bool True if importing, false otherwise. |
| 597 | */ |
| 598 | private function is_importing() { |
| 599 | // phpcs:disable WordPress.Security.NonceVerification.Missing |
| 600 | // Check if the current request is a product import. |
| 601 | if ( isset( $_POST['action'] ) && 'woocommerce_do_ajax_product_import' === $_POST['action'] ) { |
| 602 | return true; |
| 603 | } |
| 604 | return false; |
| 605 | // phpcs:enable |
| 606 | } |
| 607 | } |
| 608 |