PageSpeed OptiPic — автоматическая оптимизация сайта для требований Google Pagespeed Insights
JavaScript: Слияние, сжатие, ленивая загрузка. CSS: Сжатие размера и оптимизация загрузки. Оптимизация изображений. Оптимизация сторонних виджетов и систем аналитики.

PageSpeed Insights 99/100 из-за Google Analytics - Как я могу кэшировать GA?

Я на поиске достижения 100/100 на PageSpeed, и я почти там. Я пытаюсь найти хорошее решение для кэширования Google Analytics.

Вот сообщение, которое я получаю:

Оптимизация кэширования браузера: Установка срока действия или максимального возраста в заголовках HTTP для статических ресурсов указывает браузеру загружать ранее скачанные ресурсы с локального диска вместо сети. Кэширование браузера для следующих кэшируемых ресурсов: http://www.google-analytics.com/analytics.js (2 часа).

Единственное решение, которое я нашел, было от 2012 года, и я не думаю, что это хорошее решение. В основном вы копируете код GA и размещаете его на своем сервере. Затем вы запускаете cron-задачу для повторной проверки Google раз в день, чтобы получить последний код GA и заменить его.

http://diywpblog.com/leverage-browser-cache-optimize-google-analytics/

Что еще я могу сделать, чтобы достичь 100/100 и продолжать использовать Google Analytics?

Спасибо.

#1

Ну, если Google обманывает вас, вы можете обмануть Google в ответ:

Вот User-Agent для PageSpeed:

“Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/536.8 (KHTML, like Gecko; Google Page Speed Insights) Chrome/19.0.1084.36 Safari/536.8” 

Вы можете вставить условие, чтобы не отправлять скрипт аналитики в PageSpeed:

<?php if (!isset($_SERVER['HTTP_USER_AGENT']) || stripos($_SERVER['HTTP_USER_AGENT'], 'Speed Insights') === false): ?> // ваш код аналитики здесь <?php endif; ?> 

Очевидно, что это не принесет реального улучшения, но если ваша единственная проблема - получить 100/100, это сработает.

#2

Есть подмножество библиотеки Google Analytics js под названием ga-lite, которую вы можете кэшировать, как вам удобно.

Библиотека использует общедоступный REST API Google Analytics для отправки данных отслеживания пользователей в Google. Вы можете узнать больше из статьи в блоге о ga-lite.

Отказ от ответственности: Я являюсь автором этой библиотеки. Я имел проблемы с этой конкретной проблемой, и лучшим результатом, который я нашел, было реализовать это решение.

#3

Вот очень простое решение с использованием JS для основного отслеживания GA, которое также будет работать для кэшей/прокси-серверов (этот код был преобразован из комментария):

if(navigator.userAgent.indexOf("Speed Insights") == -1) { (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','https://www.google-analytics.com/analytics.js','ga'); ga('create', 'UA-XXXXXXXXX-X', 'auto'); ga('send', 'pageview'); } 

Примечание: это код по умолчанию для GA. У вас может быть и другие вызовы ga(), и если это так, вам необходимо всегда проверять user agent перед вызовом ga(), в противном случае может возникнуть ошибка.

#4

Не беспокойтесь об этом. Не размещайте его на своем собственном сервере, похоже, это проблема Google, но лучше нет. Помещение файла на свой собственный сервер создаст много новых проблем.

Вероятно, им нужно вызывать файл каждый раз, а не получать его из кэша клиента, поскольку в этом случае вы не будете учитывать посещения.

Если у вас есть проблемы с тем, чтобы чувствовать себя комфортно с этим, запустите URL Google Insights на самом Google Insights, посмейтесь, расслабьтесь и займитесь своей работой.

#5

В документации Google они определили фильтр pagespeed, который загрузит скрипт асинхронно:

ModPagespeedEnableFilters make_google_analytics_async 

Вы можете найти документацию по этому адресу: https://developers.google.com/speed/pagespeed/module/filter-make-google-analytics-async

Одна вещь, которую нужно подчеркнуть, - это то, что фильтр считается высоким риском. Из документации:

Фильтр make_google_analytics_async экспериментальный и не прошел обширное тестирование в реальном мире. Одним из случаев, когда переписывание вызывает ошибки, является пропуск вызовов методов Google Analytics, которые возвращают значения. Если такие методы найдены, переписывание пропускается. Однако, дисквалифицирующие методы будут пропущены, если они возникают перед загрузкой, находятся в атрибутах "onclick" или если они находятся во внешних ресурсах. Ожидается, что такие случаи будут редкими.

#6

Вы можете попробовать хостить analytics.js локально и обновлять его содержимое скриптом кэширования или вручную.

Этот js-файл обновляется только несколько раз в год, и если вам не нужны новые функции отслеживания, обновляйте его вручную.

https://developers.google.com/analytics/devguides/collection/analyticsjs/changelog

#7

Храните analytics.js на локальном устройстве, но Google не рекомендует это делать: https://support.google.com/analytics/answer/1032389?hl=ru

Это не рекомендуется, потому что Google может обновлять скрипт по своему желанию. Просто создайте скрипт, который будет скачивать javascript-код аналитики каждую неделю, и у вас не будет никаких проблем!

Кстати, эта решение предотвращает блокировку скриптов Google Analytics с помощью Adblock

#8

Сайт varvy.com (оценка 100/100 по Google Page Speed Insight) загружает код Google Analytics только после того, как пользователь прокрутил страницу:

var fired = false; window.addEventListener("scroll", function(){ if ((document.documentElement.scrollTop != 0 && fired === false) || (document.body.scrollTop != 0 && fired === false)) { (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'); ga('create', 'UA-XXXXXXXX-X', 'auto'); ga('send', 'pageview'); fired = true; } }, true); 
#9

You can proxy the google analytics script via your own server, save it locally and auto update the file every hour to make sure it's always latest version from google.

I've done this on a couple of sites now and all is working fine.

Google Analytics Proxy Route in NodeJS / MEAN Stack

This is how I implemented it on my blog that's built with the MEAN stack.

router.get('/analytics.js', function (req, res, next) {
    var fileUrl = 'http://www.google-analytics.com/analytics.js';
    var filePath = path.resolve('/content/analytics.js');

    // ensure file exists and is less than 1 hour old
    fs.stat(filePath, function (err, stats) {
        if (err) {
            // file doesn't exist so download and create it
            updateFileAndReturn();
        } else {
            // file exists so ensure it's not stale
            if (moment().diff(stats.mtime, 'minutes') > 60) {
                updateFileAndReturn();
            } else {
                returnFile();
            }
        }
    });

    // update file from remote url then send to client
    function updateFileAndReturn() {
        request(fileUrl, function (error, response, body) {
            fs.writeFileSync(filePath, body);
            returnFile();
        });
    }

    // send file to client
    function returnFile() {
        res.set('Cache-Control', 'public, max-age=' + oneWeekSeconds);
        res.sendFile(filePath);
    }
});

Google Analytics Proxy Action Method in ASP.NET MVC

This is how I implemented it on other sites built with ASP.NET MVC.

public class ProxyController : BaseController
{
    [Compress]
    public ActionResult GoogleAnalytics()
    {
        var fileUrl = "https://ssl.google-analytics.com/ga.js";
        var filePath = Server.MapPath("~/scripts/analytics.js");

        // ensure file exists 
        if (!System.IO.File.Exists(filePath))
            UpdateFile(fileUrl, filePath);

        // ensure file is less than 1 hour old
        var lastModified = System.IO.File.GetLastWriteTime(filePath);
        if((DateTime.Now - lastModified).TotalMinutes > 60)
            UpdateFile(fileUrl, filePath);

        // enable caching for 1 week for page speed score
        Response.AddHeader("Cache-Control", "max-age=604800");

        return JavaScript(System.IO.File.ReadAllText(filePath));
    }

    private void UpdateFile(string fileUrl, string filePath)
    {
        using (var response = WebRequest.Create(fileUrl).GetResponse())
        using (var dataStream = response.GetResponseStream())
        using (var reader = new StreamReader(dataStream))
        {
            var body = reader.ReadToEnd();
            System.IO.File.WriteAllText(filePath, body);
        }
    }
}

This is the CompressAttribute used by the MVC ProxyController for Gzip compression

public class CompressAttribute : ActionFilterAttribute
{
    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {

        var encodingsAccepted = filterContext.HttpContext.Request.Headers["Accept-Encoding"];
        if (string.IsNullOrEmpty(encodingsAccepted)) return;

        encodingsAccepted = encodingsAccepted.ToLowerInvariant();
        var response = filterContext.HttpContext.Response;

        if (encodingsAccepted.Contains("gzip"))
        {
            response.AppendHeader("Content-encoding", "gzip");
            response.Filter = new GZipStream(response.Filter, CompressionMode.Compress);
        }
        else if (encodingsAccepted.Contains("deflate"))
        {
            response.AppendHeader("Content-encoding", "deflate");
            response.Filter = new DeflateStream(response.Filter, CompressionMode.Compress);
        }
    }
}

Updated Google Analytics Script

On the client side I append the analytics path with the current date up to the hour so the browser won't use a cached version more than an hour old.

<!-- analytics -->
<script>
    (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', '/analytics.js?d=' + new Date().toISOString().slice(0, 13), 'ga');
</script>
#10

Для Nginx:

location ~ /analytics.js { proxy_pass https://www.google-analytics.com; expires 31536000s; proxy_set_header Pragma "public"; proxy_set_header Cache-Control "max-age=31536000, public"; } 

Затем измените путь с https://www.google-analytics.com/analytics.js на https://yoursite.com/analytics.js

#11
PHP

Добавьте это в свой HTML или PHP код:

<?php if (!isset($_SERVER['HTTP_USER_AGENT']) || stripos($_SERVER['HTTP_USER_AGENT'], 'Speed Insights') === false): ?> <script> (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','https://www.google-analytics.com/analytics.js','ga'); ga('create', 'UA-ВСТАВЬТЕ ВАШ ИДЕНТИФИКАТОР GOOGLE ANALYTICS ЗДЕСЬ', 'auto'); ga('send', 'pageview'); </script> <?php endif; ?> 
JavaScript

Это работает отлично с JavaScript:

 <script> if(navigator.userAgent.indexOf("Speed Insights") == -1) { (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','https://www.google-analytics.com/analytics.js','ga'); ga('create', 'UA-<ВСТАВЬТЕ ВАШ ИДЕНТИФИКАТОР GOOGLE ANALYTICS ЗДЕСЬ>', 'auto'); ga('send', 'pageview'); } </script> 

NiloVelez уже сказал: Очевидно, что это не принесет реального улучшения, но если ваша единственная забота - получение результатов 100/100, то это подойдет.

#12

попробуйте вставить это перед

<script async='async' src='https://cdn.jsdelivr.net/ga-lite/latest/ga-lite.min.js'></script> <script>var galite=galite||{};galite.UA="xx-xxxxxxx-x";</script> 

Пожалуйста, измените xx-xxxxxxx-x на ваш код, проверьте реализацию здесь http://www.gee.web.id/2016/11/how-to-leverage-browser-caching-for-google-analitycs.html

#13

В 2020 году агенты пользователя Page Speed Insights - это "Chrome-Lighthouse" для мобильных устройств и "Google Page Speed Insights" для настольных компьютеров.

<?php if (!isset($_SERVER['HTTP_USER_AGENT']) || stripos($_SERVER['HTTP_USER_AGENT'], 'Chrome-Lighthouse') === false || stripos($_SERVER['HTTP_USER_AGENT'], 'Google Page Speed Insights') === false): ?> // ваш код Google Analytics и другие внешние скрипты, которые вы хотите скрыть от PageSpeed Insights, размещайте здесь <?php endif; ?> 
#14

Google предупреждает об использовании локальных копий скриптов аналитики. Однако, если вы все равно это делаете, вам, вероятно, захочется использовать локальные копии плагинов и отладочного скрипта.

Вторая проблема с агрессивным кэшированием заключается в том, что вы получите хиты с кэшированных страниц, которые могут измениться или быть удалены с сайта.

#15

Для исправления этой проблемы вам нужно загрузить файл локально и запустить cron-задачу для его обновления. Обратите внимание: это не ускорит ваш веб-сайт, поэтому лучше просто игнорировать это.

Однако, для демонстрационных целей следуйте инструкциям по этой ссылке: http://diywpblog.com/leverage-browser-cache-optimize-google-analytics/

#16

Это может сработать :)

<script> $.ajax({ type: "GET", url: "https://www.google-analytics.com/analytics.js", success: function(){}, dataType: "script", cache: true }); </script> 
#17

В зависимости от использования вами данных Google Analytics, если вам нужна только базовая информация (например, посещения, взаимодействия с пользовательским интерфейсом), вы можете вообще не включать analytics.js, но при этом продолжать собирать данные в GA.

Один из вариантов - использовать протокол измерения в кэшированном скрипте. Google Analytics: Обзор протокола измерения

Если вы явно устанавливаете метод транспортировки на изображение image, вы можете увидеть, как GA создает свои собственные пиксели изображений.

ga('set', 'transport', 'image'); https://www.google-analytics.com/r/collect ?v={protocol-version} &tid={tracking-id} &cid={client-id} &t={hit-type} &dl={location} 

Вы можете создавать GET или POST запросы с необходимой нагрузкой данных.

Однако, если вам нужен более детальный уровень информации, вероятно, это не стоит ваших усилий.

#18

Вы можете настроить дистрибуцию в CloudFront, которая будет иметь www.google-analytics.com в качестве сервера источника и установить более длительный заголовок срока действия в настройках дистрибуции CloudFront. Затем измените этот домен во фрагменте кода Google. Это предотвращает нагрузку на ваш собственный сервер и необходимость постоянного обновления файла в задании cron.

Это настройка и забывание. Поэтому вы можете добавить оповещение о счете в CloudFront, на случай, если кто-то "скопирует" ваш фрагмент и украдет вашу пропускную способность ;-)

Изменение: Я попробовал это, и это не так просто, CloudFront передает заголовок Cache-Control без простого способа его удалить

#19

Откройте файл https://www.google-analytics.com/analytics.js в новой вкладке, скопируйте весь код.

Теперь создайте папку в своем веб-каталоге, переименуйте ее в google-analytics.

Создайте текстовый файл в той же папке и вставьте весь скопированный код.

Переименуйте файл в ga-local.js.

Теперь измените URL, чтобы вызывать файл скрипта аналитики, размещенный у вас на локальном хосте, в вашем коде Google Analytics. Он будет выглядеть примерно так: https://domain.xyz/google-analytics/ga.js

Наконец, разместите ваш НОВЫЙ код аналитики Google в подвале вашей веб-страницы.

Вы готовы к работе. Теперь проверьте свой веб-сайт в Google PageSpeed Insights. Он не будет показывать предупреждение о Leverage Browser Caching Google Analytics. Единственная проблема с этим решением в том, что необходимо регулярно вручную обновлять скрипт аналитики.

#20

Вы можете минимизировать все свои скрипты на странице, включая analytics.js, используя:

  • Некоторую технологию на стороне сервера (https://github.com/matthiasmullie/minify)
  • Внешний сервис (http://www.cloudflare.com)

Не забудьте минимизировать файлы перед использованием. В противном случае это займет больше времени на обработку.

?