322 lines
12 KiB
PHP
322 lines
12 KiB
PHP
<?php
|
|
/**
|
|
* Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved
|
|
*
|
|
* This source code is licensed under the license found in the
|
|
* LICENSE file in the root directory of this source tree.
|
|
*
|
|
* @package MetaCommerce
|
|
*/
|
|
|
|
namespace WooCommerce\Facebook\Utilities;
|
|
|
|
defined( 'ABSPATH' ) || exit;
|
|
|
|
/**
|
|
* Class for adding diagnostic info to WooCommerce Tracker snapshot.
|
|
*
|
|
* See https://woocommerce.com/usage-tracking/ for more information.
|
|
*
|
|
* @since 2.3.4
|
|
*/
|
|
class Tracker {
|
|
|
|
/**
|
|
* Life time for transients used for temporary caching of values we want to add to tracker snapshot.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_LIFE_TIME = 2 * WEEK_IN_SECONDS;
|
|
|
|
/**
|
|
* Transient key name; how long it took to generate the most recent feed file, or minus one if it failed.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FEED_GENERATION_TIME = 'facebook_for_woocommerce_wctracker_feed_generation_time';
|
|
|
|
/**
|
|
* Transient key name; how long it took to generate already generated batches.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_TIME = 'facebook_for_woocommerce_wctracker_feed_generation_batch_time';
|
|
|
|
/**
|
|
* Transient key name; how much wall ( clock ) time it took to generate the feed file.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_TIME = 'facebook_for_woocommerce_wctracker_feed_generation_batch_wall_time';
|
|
|
|
/**
|
|
* Transient key name; the time when was the batched feed generation started.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_START_TIME = 'facebook_for_woocommerce_wctracker_feed_generation_batch_wall_time';
|
|
|
|
/**
|
|
* Transient key name; true if feed has been requested by Facebook.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FEED_REQUESTED = 'facebook_for_woocommerce_wctracker_feed_requested';
|
|
|
|
/**
|
|
* Transient key name; stores various FBE business settings.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FBE_BUSINESS_CONFIG = 'facebook_for_woocommerce_wctracker_fbe_business_config';
|
|
|
|
/**
|
|
* Transient key name; stores feed (data source) settings for catalog sync.
|
|
*
|
|
* @var string
|
|
*/
|
|
public const TRANSIENT_WCTRACKER_FB_FEED_CONFIG = 'facebook_for_woocommerce_wctracker_fb_feed_config';
|
|
|
|
/**
|
|
* Constructor.
|
|
*
|
|
* @since 2.3.4
|
|
*/
|
|
public function __construct() {
|
|
add_filter(
|
|
'woocommerce_tracker_data',
|
|
[ $this, 'add_tracker_data' ]
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Append our tracker properties.
|
|
*
|
|
* @param array $data The current tracker snapshot data.
|
|
* @return array $data Snapshot updated with our data.
|
|
* @since 2.3.4
|
|
*/
|
|
public function add_tracker_data( array $data = [] ) {
|
|
if ( ! isset( $data['extensions'] ) ) {
|
|
$data['extensions'] = [];
|
|
}
|
|
|
|
/**
|
|
* Is the site connected?
|
|
*
|
|
* @since 2.3.4
|
|
*/
|
|
$connection_is_happy = false;
|
|
$connection_handler = facebook_for_woocommerce()->get_connection_handler();
|
|
if ( $connection_handler ) {
|
|
$connection_is_happy = $connection_handler->is_connected() && ! get_transient( 'wc_facebook_connection_invalid' );
|
|
}
|
|
$data['extensions']['facebook-for-woocommerce']['is-connected'] = wc_bool_to_string( $connection_is_happy );
|
|
|
|
/**
|
|
* Synchronization will always be permitted once we initiate the process of syncing all WooCommerce products.
|
|
*
|
|
* @since 3.5.3
|
|
*/
|
|
|
|
$is_woo_all_products_enabled = facebook_for_woocommerce()->get_integration()->is_woo_all_products_enabled();
|
|
if ( ! $is_woo_all_products_enabled ) {
|
|
$product_sync_enabled = facebook_for_woocommerce()->get_integration()->is_product_sync_enabled();
|
|
$data['extensions']['facebook-for-woocommerce']['product-sync-enabled'] = wc_bool_to_string( $product_sync_enabled );
|
|
} else {
|
|
$data['extensions']['facebook-for-woocommerce']['product-sync-enabled'] = wc_bool_to_string( true );
|
|
}
|
|
|
|
/**
|
|
* How long did the last feed generation take (or did it fail - 0)? This counts just the time when the batches have been generated.
|
|
* It does not take into account the time between the batches.
|
|
*
|
|
* @since 2.6.0
|
|
*/
|
|
$feed_generation_time = get_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_TIME );
|
|
$data['extensions']['facebook-for-woocommerce']['feed-generation-time'] = floatval( $feed_generation_time );
|
|
|
|
/**
|
|
* How long did the last feed generation take in wall time. This is the whole duration. Batches plus time in between.
|
|
*
|
|
* @since 2.6.6
|
|
*/
|
|
if ( facebook_for_woocommerce()->get_integration()->is_new_style_feed_generation_enabled() ) {
|
|
$feed_generation_batch_wall_time = intval( get_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_TIME ) );
|
|
} else {
|
|
// For old feed generator this is the same thing $feed_generation_time because the process is done in one step.
|
|
$feed_generation_batch_wall_time = intval( $feed_generation_time );
|
|
}
|
|
$data['extensions']['facebook-for-woocommerce']['feed-generation-wall-time'] = $feed_generation_batch_wall_time;
|
|
|
|
/**
|
|
* Has the feed file been requested since the last snapshot?
|
|
*
|
|
* @since 2.6.0
|
|
*/
|
|
$feed_file_requested = get_transient( self::TRANSIENT_WCTRACKER_FEED_REQUESTED );
|
|
$data['extensions']['facebook-for-woocommerce']['feed-file-requested'] = wc_bool_to_string( $feed_file_requested );
|
|
// Manually delete the transient. This prop tracks if feed has been requested _since last snapshot_.
|
|
delete_transient( self::TRANSIENT_WCTRACKER_FEED_REQUESTED );
|
|
|
|
/**
|
|
* Miscellaneous Facebook config settings.
|
|
*
|
|
* @since 2.6.0
|
|
*/
|
|
$config = get_transient( self::TRANSIENT_WCTRACKER_FBE_BUSINESS_CONFIG );
|
|
$data['extensions']['facebook-for-woocommerce']['instagram-shopping-enabled'] = wc_bool_to_string( $config ? $config['ig_shopping_enabled'] : false );
|
|
$data['extensions']['facebook-for-woocommerce']['instagram-cta-enabled'] = wc_bool_to_string( $config ? $config['ig_cta_enabled'] : false );
|
|
|
|
/**
|
|
* Feed pull / upload settings configured in Facebook UI.
|
|
*
|
|
* @since 2.6.0
|
|
*/
|
|
$data['extensions']['facebook-for-woocommerce']['product-feed-config'] = get_transient( self::TRANSIENT_WCTRACKER_FB_FEED_CONFIG );
|
|
|
|
/**
|
|
* Detect if the user has enabled the new experimental feed generator feature.
|
|
*
|
|
* @since 2.6.6
|
|
*/
|
|
$data['extensions']['facebook-for-woocommerce']['new-feed-generator-enabled'] = wc_bool_to_string( facebook_for_woocommerce()->get_integration()->is_new_style_feed_generation_enabled() );
|
|
|
|
/**
|
|
* Language override feed tracking (Phase 1 metrics).
|
|
*
|
|
* @since 3.6.0
|
|
*/
|
|
// 1. Language override feed enabled status
|
|
$language_feed_enabled = get_option( \WC_Facebookcommerce_Integration::OPTION_LANGUAGE_OVERRIDE_FEED_GENERATION_ENABLED, 'no' );
|
|
$data['extensions']['facebook-for-woocommerce']['language-override-feeds-enabled'] = wc_bool_to_string( 'yes' === $language_feed_enabled );
|
|
|
|
// 2. Active localization plugin + version
|
|
$integration = \WooCommerce\Facebook\Integrations\IntegrationRegistry::get_active_localization_integration();
|
|
$data['extensions']['facebook-for-woocommerce']['localization-plugin'] = $integration ? $integration->get_plugin_name() : 'none';
|
|
$data['extensions']['facebook-for-woocommerce']['localization-plugin-version'] = $integration ? $integration->get_plugin_version() : '';
|
|
|
|
// 3. Number of available languages
|
|
if ( $integration && method_exists( $integration, 'get_available_languages' ) ) {
|
|
try {
|
|
$feed_data = new \WooCommerce\Facebook\Feed\Localization\LanguageFeedData();
|
|
$languages = $feed_data->get_available_languages();
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-count'] = count( $languages );
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-codes'] = implode( ',', $languages );
|
|
} catch ( \Exception $e ) {
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-count'] = 0;
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-codes'] = '';
|
|
}
|
|
} else {
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-count'] = 0;
|
|
$data['extensions']['facebook-for-woocommerce']['language-feed-codes'] = '';
|
|
}
|
|
|
|
return $data;
|
|
}
|
|
|
|
/**
|
|
* Update transient with feed file generation time.
|
|
*
|
|
* Note this is used to clear the transient (set to -1) to track feed generation failure.
|
|
*
|
|
* @param float $time_in_seconds Time taken to generate feed file (in seconds).
|
|
* @since 2.6.0
|
|
*/
|
|
public function track_feed_file_generation_time( $time_in_seconds ) {
|
|
set_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_TIME, $time_in_seconds, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
}
|
|
|
|
/**
|
|
* Reset the feed generation in batch time counter.
|
|
*
|
|
* @since 2.6.6
|
|
*/
|
|
public function reset_batch_generation_time() {
|
|
// Reset the main counter.
|
|
$this->track_feed_file_generation_time( -1 );
|
|
set_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_TIME, 0, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
set_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_TIME, 0, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
set_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_START_TIME, time(), self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
}
|
|
|
|
/**
|
|
* Add time to batch feed_generation_time.
|
|
* This accumulates time over all of the calculated feed batches.
|
|
*
|
|
* @param float $time_in_seconds Time to add to the generation time(in seconds).
|
|
* @since 2.6.6
|
|
*/
|
|
public function increment_batch_generation_time( $time_in_seconds ) {
|
|
$tracked_generation_time = floatval( get_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_TIME ) );
|
|
set_transient(
|
|
self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_TIME,
|
|
floatval( $time_in_seconds ) + $tracked_generation_time,
|
|
self::TRANSIENT_WCTRACKER_LIFE_TIME
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Save batch generation time.
|
|
*
|
|
* This is the last step in batch feed generation time tracking.
|
|
* The accumulated time value is copied to the main transient
|
|
* that is later used by the tracking code to track feed generation time.
|
|
*
|
|
* @since 2.6.6
|
|
*/
|
|
public function save_batch_generation_time() {
|
|
$this->track_feed_file_generation_time(
|
|
get_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_TIME )
|
|
);
|
|
|
|
$start = intval( get_transient( self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_START_TIME ) );
|
|
$end = time();
|
|
set_transient(
|
|
self::TRANSIENT_WCTRACKER_FEED_GENERATION_BATCH_WALL_TIME,
|
|
$end - $start,
|
|
self::TRANSIENT_WCTRACKER_LIFE_TIME
|
|
);
|
|
}
|
|
|
|
/**
|
|
* Store the fact that the feed has been requested by Facebook in a transient.
|
|
* This will later be added to next tracker snapshot.
|
|
*
|
|
* @since 2.6.0
|
|
*/
|
|
public function track_feed_file_requested() {
|
|
set_transient( self::TRANSIENT_WCTRACKER_FEED_REQUESTED, true, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
}
|
|
|
|
/**
|
|
* Store some Facebook config settings for tracking.
|
|
*
|
|
* @param bool $ig_shopping_enabled True if Instagram Shopping is configured.
|
|
* @param bool $ig_cta_enabled True if `ig_cta` config option is enabled.
|
|
* @since 2.6.0
|
|
*/
|
|
public function track_facebook_business_config(
|
|
bool $ig_shopping_enabled,
|
|
bool $ig_cta_enabled
|
|
) {
|
|
$transient = [
|
|
'ig_shopping_enabled' => $ig_shopping_enabled,
|
|
'ig_cta_enabled' => $ig_cta_enabled,
|
|
];
|
|
set_transient( self::TRANSIENT_WCTRACKER_FBE_BUSINESS_CONFIG, $transient, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
}
|
|
|
|
/**
|
|
* Store Facebook feed config for tracking.
|
|
*
|
|
* @param array $feed_settings Key-value array of settings to add to tracker snapshot.
|
|
* @since 2.6.0
|
|
*/
|
|
public function track_facebook_feed_config(
|
|
array $feed_settings
|
|
) {
|
|
set_transient( self::TRANSIENT_WCTRACKER_FB_FEED_CONFIG, $feed_settings, self::TRANSIENT_WCTRACKER_LIFE_TIME );
|
|
}
|
|
}
|