/** * Send category information from Wordpress to Google Analytics (GA). * * The Wordpress category is passed using the Content Grouping feature of * GA, to the contentGroup1 group. * * If the function is_product() is defined, the script assumes the website * has an ecommerce, and the product category will be transmitted from the * 'product_cat' taxonomy to the contentGroup2 group. * * This script should be placed just before the pageview is transmitted * to GA, ie. before the ga ('send', 'pageview') in the standard tracking * code, lest the grouping data is not transmitted to GA. You can either * copy & paste the script there, or include it as a file with the PHP * function include() or the Wordpress function get_template_part(). * * As an alternative, you could place this script wherever you want and * transmit the data to GA using a non-interaction event. If you do so, * you'll see the content grouping data in the Event -> Pages report * rather than in the Content -> All Pages one. * * This script was improved thanks to the following resources; thanks * to the authors! * - https://www.highposition.com/blog/how-to-send-author-content-groups- * wordpress-google-analytics/ * - http://stackoverflow.com/a/34714363/2972183 * * Created by Guido W. Pettinari on 08.01.2015. * Part of Wordpress Analytics: * https://github.com/coccoinomane/wordpress_analytics */ function wpan_content_grouping() { /* Extract the content grouping options from the database. If these are not properly formatted, nothing will be sent to GA. */ $options = wpan_get_options(); $wordpress_group = isset($options['group_index_wordpress']) ? $options['group_index_wordpress'] : ''; $woocommerce_group = isset($options['group_index_woocommerce']) ? $options['group_index_woocommerce'] : ''; $blog_group = isset($options['group_index_blog']) ? $options['group_index_blog'] : ''; /* Extract the categories of this post, and select from them the top-level category that is first in alphabetical order. Note that in Wordpress it is possible for posts not to have top-level categories; in that case, the category name will be empty and the post will be catalogued as (not set) in GA. */ $categories = get_the_category(); foreach ($categories as $cat) { if ($cat->category_parent == 0) { $category_name = $cat->cat_name; break; } } // ==================================================================================== // = Product page = // ==================================================================================== if (function_exists('is_product') && is_product()) { echo "<script> ga('set', 'contentGroup" . $wordpress_group . "', '" . "Prodotti" . "'); </script>\n"; /* Extract the terms in the product category attached this post, and select from them the top-level term that is first in alphabetical order. Note that in Wordpress it is possible for posts not to have top-level terms; in that case, the category name will be empty and the post will be catalogued as (not set) in GA. */ $terms = get_the_terms(get_the_ID(), 'product_cat'); foreach ($terms as $term) { if ($term->parent == 0) { $term_name = $term->name; break; } } if ($terms && !is_wp_error($terms) && !empty($term_name)) { echo "<script> ga('set', 'contentGroup" . $woocommerce_group . "', '" . $term_name . "'); </script>\n"; } else { echo "<script> ga('set', 'contentGroup" . $woocommerce_group . "', '" . "Undefined Product" . "'); </script>\n"; } } else { if ($categories && !is_wp_error($categories) && !empty($category_name)) { echo "<script> ga('set', 'contentGroup" . $wordpress_group . "', '" . $category_name . "'); </script>\n"; /* Extract content type from custom field */ $content_type = get_post_meta(get_the_ID(), 'analytics_content_type', true); if ($content_type) { echo "<script> ga('set', 'contentGroup" . $blog_group . "', '" . $content_type . "'); </script>\n"; } } } }
function wpan_send_form_tracking_event($entry, $form) { global $post; $msg = "About to send form tracking event to Google Analytics..."; wpan_log_debug($msg); GFCommon::log_debug($msg); /* Extract the plugin options from the database */ $options = wpan_get_options(); $tracking_uid = isset($options['tracking_uid']) ? $options['tracking_uid'] : ''; $debug = isset($options['debug']) ? $options['debug'] : ''; $form_title = $form['title']; /* I have taken the following four lines of code from https://github.com/theiconic/php-ga-measurement-protocol; thank you! */ $document_path = str_replace(home_url(), '', $entry['source_url']); $document_location = 'http' . (isset($_SERVER['HTTPS']) ? 's' : '') . '://' . $_SERVER['HTTP_HOST'] . '/' . $_SERVER['REQUEST_URI']; $document_title = isset($post) && get_the_title($post) ? get_the_title($post) : 'no title'; /* Setup the class */ $ga_options = ['client_create_random_id' => true, 'client_fallback_id' => 555, 'client_id' => null, 'user_id' => null, 'adapter' => ['async' => true, 'ssl' => false]]; /* Connect to tracker */ $gatracking = new \Racecore\GATracking\GATracking($tracking_uid, $ga_options); /* Build GA event */ $event = $gatracking->createTracking('Event'); $event->setAsNonInteractionHit(false); $event->setEventCategory('Contact'); $event->setEventAction($form_title); $event->setEventLabel($document_path); $event->setDocumentPath($document_path); $event->setDocumentLocation($document_location); $event->setDocumentTitle($document_title); /* Send event to GA severs */ $response = $gatracking->sendTracking($event); /* Debug */ if ($debug) { wpan_log_debug("Sent the following event to Google Analytics:"); wpan_log_debug($event); wpan_log_debug("Received the following respons from Google Analytics (ASYNC, so it might be empty): "); wpan_log_debug($response); // wpan_log_debug( "This is the form that triggered the event:" ); // wpan_log_debug( $form ); // wpan_log_debug( "This is the entry of the form in Gravity Forms:" ); // wpan_log_debug( $entry ); } }
/** * PHP wrapper for the call tracking Javascript, suitable for use in * Wordpress. * * Created by Guido W. Pettinari on 02.03.2016. * Part of Wordpress Analytics: * https://github.com/coccoinomane/wordpress_analytics */ function wpan_call_tracking() { /* Extract the call tracking options from the database */ $options = wpan_get_options(); $phone_regex_include_pattern = isset($options['phone_regex_include_pattern']) ? $options['phone_regex_include_pattern'] : ''; $phone_regex_exclude_pattern = isset($options['phone_regex_exclude_pattern']) ? $options['phone_regex_exclude_pattern'] : ''; $detect_phone_numbers = isset($options['detect_phone_numbers']) ? $options['detect_phone_numbers'] : ''; $debug = isset($options['debug']) ? $options['debug'] : ''; /* Script path & url */ $script_path = WPAN_PLUGIN_DIR . 'js/call_tracking.js'; $script_url = WPAN_PLUGIN_URL . 'js/call_tracking.js'; $script_versioned = $script_url . '?ver=' . filemtime($script_path); /* Prevent mobile browsers from detecting phone numbers */ if ($detect_phone_numbers) { echo "<meta name='format-detection' content='telephone=no'>\n"; } /* Load the script */ echo "<script src='{$script_versioned}' " . "regexIncludePattern='{$phone_regex_include_pattern}' " . "regexExcludePattern='{$phone_regex_exclude_pattern}' " . "detectPhoneNumbers='{$detect_phone_numbers}' " . "debug='{$debug}' " . "defer='defer'" . "> " . "</script>\n"; }
/** * PHP wrapper of a slightly modified version of the scroll tracking * javascript by Justin Cutroni, suitable for use in Wordpress. * * The javascript needs to be called scroll_tracking.js and to reside * in the URI specified in the named constant ANALYTICS_URI. * * Created by Guido W. Pettinari on 23.12.2015. * Part of Wordpress Analytics: * https://github.com/coccoinomane/wordpress_analytics */ function wpan_scroll_tracking() { /* Extract the scroll tracking options from the database */ $options = wpan_get_options(); $pixel_threshold = isset($options['pixel_threshold']) ? $options['pixel_threshold'] : ''; $time_threshold = isset($options['time_threshold']) ? $options['time_threshold'] : ''; $debug = isset($options['debug']) ? $options['debug'] : ''; /* Script path & url */ $script_path = WPAN_PLUGIN_DIR . 'js/scroll_tracking.js'; $script_url = WPAN_PLUGIN_URL . 'js/scroll_tracking.js'; /* Add the timestamp as a query string to the script, in order to reload automatically the script when it is changed rather than using the cached version (see http://stackoverflow.com/a/14536240/2972183) */ $script_versioned = $script_url . '?ver=' . filemtime($script_path); /* Load the imagesLoaded javascript library to ensure that scroll tracking works properly with image-rich pages. TODO: we should use wp_enqueue() here. */ echo "<script src='https://unpkg.com/imagesloaded@4.1/imagesloaded.pkgd.js' defer='defer'></script>\n"; /* Load the script. TODO: we should use wp_enqueue() here. */ echo "<script src='{$script_versioned}' " . "timeThreshold='{$time_threshold}' " . "pixelThreshold='{$pixel_threshold}' " . "debug='{$debug}' " . "defer='defer'" . "> " . "</script>\n"; }
* Author: Guido W. Pettinari * Author URI: http://www.guidowalterpettinari.eu * License: GPL3 */ /* Define plugin version */ define("WPAN_VERSION", "alpha_v7"); define("WPAN_URL", "https://github.com/coccoinomane/wordpress_analytics"); /* Define plugin directory & URL */ define("WPAN_PLUGIN_DIR", plugin_dir_path(__FILE__)); define("WPAN_PLUGIN_URL", plugin_dir_url(__FILE__)); /* Include utility functions */ require_once WPAN_PLUGIN_DIR . 'functions.php'; /* Build settings page */ require_once WPAN_PLUGIN_DIR . 'settings/settings.php'; /* Extract plugin options from the database */ $options = wpan_get_options(); /* Stop unless we have a valid tracking ID */ if (isset($options['tracking_uid']) && $options['tracking_uid']) { // ======================== // = Client-side tracking = // ======================== /* Load content grouping function */ if (isset($options['content_grouping']) && $options['content_grouping']) { require_once WPAN_PLUGIN_DIR . 'content_grouping.php'; } /* Load scroll tracking function */ if (isset($options['scroll_tracking']) && $options['scroll_tracking']) { require_once WPAN_PLUGIN_DIR . 'scroll_tracking.php'; } /* Load call tracking function */ if (isset($options['call_tracking']) && $options['call_tracking']) {
/** * Debug function: write to debug.log in plugin directory. */ function wpan_log_debug($log) { $options = wpan_get_options(); $debug = isset($options['debug']) ? $options['debug'] : ''; if ($debug && defined('WPAN_PLUGIN_DIR')) { $debug_file = WPAN_PLUGIN_DIR . 'wpan_debug.txt'; $pre = preg_replace('/.*?public_html/', '', __FILE__) . ':' . __LINE__ . ': '; if (is_array($log) || is_object($log)) { file_put_contents($debug_file, $pre . print_r($log, true) . PHP_EOL, FILE_APPEND); } else { file_put_contents($debug_file, $pre . $log . PHP_EOL, FILE_APPEND); } } }
/** * Insert Google Analytics (GA) tracking code in Javascript * in the . * * Anything echoed by this function will be written in the * head of all pages. * * Created by Guido W. Pettinari on 23.12.2015. * Part of Wordpress Analytics: * https://github.com/coccoinomane/wordpress_analytics */ function wpan_tracking_code() { /* Extract the tracking UID from the database */ $options = wpan_get_options(); $tracking_uid = isset($options['tracking_uid']) ? $options['tracking_uid'] : ''; $content_grouping = is_single() && isset($options['content_grouping']) && $options['content_grouping']; $scroll_tracking = is_single() && isset($options['scroll_tracking']) && $options['scroll_tracking']; $call_tracking = isset($options['call_tracking']) && $options['call_tracking']; $form_tracking = isset($options['form_tracking']) && $options['form_tracking']; $custom_code = isset($options['custom_code']) && $options['custom_code']; $enhanced_link_attribution = isset($options['enhanced_link_attribution']) && $options['enhanced_link_attribution']; $cross_domain_support = isset($options['cross_domain_support']) && $options['cross_domain_support']; /* Execute the script only if the tracking ID exists */ if ($tracking_uid) { echo PHP_EOL . PHP_EOL . "<!-- BEGIN: Tracking code inserted by Wordpress Analytics " . WPAN_VERSION . " - " . WPAN_URL . "-->" . PHP_EOL; ?> <script> /* Generic tracking code for Google Universal Analytics */ (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){ (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o), m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m) })(window,document,'script','//www.google-analytics.com/analytics.js','ga'); /* Pass the tracking UID of the GA property associated to this website */ <?php if (!$cross_domain_support) { echo "ga('create', '" . $tracking_uid . "', 'auto');\n"; } else { /* Alas, the allowLinker field can be passed only within a create command (https://developers.google.com/analytics/devguides/collection/analyticsjs/ field-reference#allowLinker) */ echo "ga('create', '" . $tracking_uid . "', 'auto', {'allowLinker': true});\n"; } ?> </script> <?php /* Scroll tracking script to track reading behaviour */ if ($scroll_tracking) { wpan_scroll_tracking(); } /* Call tracking script to track clicks on phone number links */ if ($call_tracking) { wpan_call_tracking(); } /* Content grouping script to categorise the website content in GA */ if ($content_grouping) { wpan_content_grouping(); } /* Enable Cross Domain support */ if ($cross_domain_support) { echo "<script> ga('require', 'linker'); </script>\n"; echo "<script> ga('require', 'displayfeatures'); </script>\n"; } /* Enable Enhanced Link attribution */ if ($enhanced_link_attribution) { echo "<script> ga('require', 'linkid'); </script>\n"; } /* Execute code specified by the user */ if ($custom_code) { echo wpan_php_eval($options['custom_code']); } ?> <script> /* Send a pageview hit to the GA servers, and transmit any information that was set above in the tracker. This line should be at the end of the script. */ ga('send', 'pageview'); </script> <?php } // if $tracking_uid echo "<!-- END: Tracking code inserted by Wordpress Analytics " . WPAN_VERSION . " - " . WPAN_URL . "-->" . PHP_EOL . PHP_EOL; }