Bug 1036764 - Add telemetry for flash. r=bsmedberg,snorp data-r?bsmedberg
authornechen <cnevinc@livemail.tw>
Tue, 14 Mar 2017 14:12:26 +0800
changeset 348068 36525c06f5a048ac584c6355d27c5038e441aef5
parent 348067 ad24ad035ca8209b9944681bf04c3d8197c57553
child 348069 3cf7e1e3d9939fded5ba24ea14902f97b9639f68
push id31512
push usercbook@mozilla.com
push dateFri, 17 Mar 2017 13:28:24 +0000
treeherdermozilla-central@9a95ade0ec97 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbsmedberg, snorp
bugs1036764
milestone55.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1036764 - Add telemetry for flash. r=bsmedberg,snorp data-r?bsmedberg MozReview-Commit-ID: 1tsNZlEmx6s
mobile/android/base/java/org/mozilla/gecko/GeckoApp.java
mobile/android/base/java/org/mozilla/gecko/telemetry/pingbuilders/TelemetryCorePingBuilder.java
mobile/android/chrome/content/PluginHelper.js
toolkit/components/telemetry/docs/data/core-ping.rst
--- a/mobile/android/base/java/org/mozilla/gecko/GeckoApp.java
+++ b/mobile/android/base/java/org/mozilla/gecko/GeckoApp.java
@@ -156,16 +156,17 @@ public abstract class GeckoApp
 
     public static final String INTENT_REGISTER_STUMBLER_LISTENER = "org.mozilla.gecko.STUMBLER_REGISTER_LOCAL_LISTENER";
 
     public static final String EXTRA_STATE_BUNDLE          = "stateBundle";
 
     public static final String LAST_SELECTED_TAB           = "lastSelectedTab";
 
     public static final String PREFS_ALLOW_STATE_BUNDLE    = "allowStateBundle";
+    public static final String PREFS_FLASH_USAGE = "playFlashCount";
     public static final String PREFS_VERSION_CODE          = "versionCode";
     public static final String PREFS_WAS_STOPPED           = "wasStopped";
     public static final String PREFS_CRASHED_COUNT         = "crashedCount";
     public static final String PREFS_CLEANUP_TEMP_FILES    = "cleanupTempFiles";
 
     // Originally, this was only used for the telemetry core ping logic. To avoid
     // having to write custom migration logic, we just keep the original pref key.
     public static final String PREFS_IS_FIRST_RUN = "telemetry-isFirstRun";
@@ -819,16 +820,21 @@ public abstract class GeckoApp
         } else if ("Update:Check".equals(event)) {
             UpdateServiceHelper.checkForUpdate(this);
 
         } else if ("Update:Download".equals(event)) {
             UpdateServiceHelper.downloadUpdate(this);
 
         } else if ("Update:Install".equals(event)) {
             UpdateServiceHelper.applyUpdate(this);
+
+        } else if ("PluginHelper:playFlash".equals(event)) {
+            final SharedPreferences prefs = getSharedPreferences();
+            int count = prefs.getInt(PREFS_FLASH_USAGE, 0);
+            prefs.edit().putInt(PREFS_FLASH_USAGE,++count).apply();
         }
     }
 
     /**
      * @param permissions
      *        Array of JSON objects to represent site permissions.
      *        Example: { type: "offline-app", setting: "Store Offline Data", value: "Allow" }
      */
@@ -1240,16 +1246,17 @@ public abstract class GeckoApp
             }
         }
 
         // To prevent races, register startup events before launching the Gecko thread.
         EventDispatcher.getInstance().registerGeckoThreadListener(this,
             "Accessibility:Ready",
             "Gecko:Exited",
             "Gecko:Ready",
+            "PluginHelper:playFlash",
             null);
 
         EventDispatcher.getInstance().registerUiThreadListener(this,
             "Sanitize:Finished",
             null);
 
         GeckoThread.launch();
 
@@ -2381,16 +2388,17 @@ public abstract class GeckoApp
             super.onDestroy();
             return;
         }
 
         EventDispatcher.getInstance().unregisterGeckoThreadListener(this,
             "Accessibility:Ready",
             "Gecko:Exited",
             "Gecko:Ready",
+            "PluginHelper:playFlash",
             null);
 
         EventDispatcher.getInstance().unregisterUiThreadListener(this,
             "Sanitize:Finished",
             null);
 
         getAppEventDispatcher().unregisterGeckoThreadListener(this,
             "Accessibility:Event",
--- a/mobile/android/base/java/org/mozilla/gecko/telemetry/pingbuilders/TelemetryCorePingBuilder.java
+++ b/mobile/android/base/java/org/mozilla/gecko/telemetry/pingbuilders/TelemetryCorePingBuilder.java
@@ -11,17 +11,19 @@ import android.content.SharedPreferences
 import android.os.Build;
 import android.support.annotation.NonNull;
 import android.support.annotation.Nullable;
 import android.support.annotation.WorkerThread;
 import android.text.TextUtils;
 
 import android.util.Log;
 import org.mozilla.gecko.AppConstants;
+import org.mozilla.gecko.GeckoApp;
 import org.mozilla.gecko.GeckoProfile;
+import org.mozilla.gecko.GeckoSharedPrefs;
 import org.mozilla.gecko.Locales;
 import org.mozilla.gecko.search.SearchEngine;
 import org.mozilla.gecko.sync.ExtendedJSONObject;
 import org.mozilla.gecko.telemetry.TelemetryPing;
 import org.mozilla.gecko.util.DateUtil;
 import org.mozilla.gecko.Experiments;
 import org.mozilla.gecko.util.StringUtils;
 
@@ -39,17 +41,17 @@ import java.util.concurrent.TimeUnit;
  */
 public class TelemetryCorePingBuilder extends TelemetryPingBuilder {
     private static final String LOGTAG = StringUtils.safeSubstring(TelemetryCorePingBuilder.class.getSimpleName(), 0, 23);
 
     // For legacy reasons, this preference key is not namespaced with "core".
     private static final String PREF_SEQ_COUNT = "telemetry-seqCount";
 
     private static final String NAME = "core";
-    private static final int VERSION_VALUE = 7; // For version history, see toolkit/components/telemetry/docs/core-ping.rst
+    private static final int VERSION_VALUE = 8; // For version history, see toolkit/components/telemetry/docs/core-ping.rst
     private static final String OS_VALUE = "Android";
 
     private static final String ARCHITECTURE = "arch";
     private static final String CAMPAIGN_ID = "campaignId";
     private static final String CLIENT_ID = "clientId";
     private static final String DEFAULT_SEARCH_ENGINE = "defaultSearch";
     private static final String DEVICE = "device";
     private static final String DISTRIBUTION_ID = "distributionId";
@@ -60,16 +62,17 @@ public class TelemetryCorePingBuilder ex
     private static final String PING_CREATION_DATE = "created";
     private static final String PROFILE_CREATION_DATE = "profileDate";
     private static final String SEARCH_COUNTS = "searches";
     private static final String SEQ = "seq";
     private static final String SESSION_COUNT = "sessions";
     private static final String SESSION_DURATION = "durations";
     private static final String TIMEZONE_OFFSET = "tz";
     private static final String VERSION_ATTR = "v";
+    private static final String FLASH_USAGE = "flashUsage";
 
     public TelemetryCorePingBuilder(final Context context) {
         initPayloadConstants(context);
     }
 
     private void initPayloadConstants(final Context context) {
         payload.put(VERSION_ATTR, VERSION_VALUE);
         payload.put(OS_ATTR, OS_VALUE);
@@ -85,16 +88,22 @@ public class TelemetryCorePingBuilder ex
 
         payload.put(ARCHITECTURE, AppConstants.ANDROID_CPU_ARCH);
         payload.put(DEVICE, deviceDescriptor);
         payload.put(LOCALE, Locales.getLanguageTag(Locale.getDefault()));
         payload.put(OS_VERSION, Integer.toString(Build.VERSION.SDK_INT)); // A String for cross-platform reasons.
         payload.put(PING_CREATION_DATE, pingCreationDateFormat.format(nowCalendar.getTime()));
         payload.put(TIMEZONE_OFFSET, DateUtil.getTimezoneOffsetInMinutesForGivenDate(nowCalendar));
         payload.putArray(EXPERIMENTS, Experiments.getActiveExperiments(context));
+        synchronized (this) {
+            SharedPreferences prefs = GeckoSharedPrefs.forApp(context);
+            final int count = prefs.getInt(GeckoApp.PREFS_FLASH_USAGE, 0);
+            payload.put(FLASH_USAGE, count);
+            prefs.edit().putInt(GeckoApp.PREFS_FLASH_USAGE, 0).apply();
+        }
     }
 
     @Override
     public String getDocType() {
         return NAME;
     }
 
     @Override
--- a/mobile/android/chrome/content/PluginHelper.js
+++ b/mobile/android/chrome/content/PluginHelper.js
@@ -1,13 +1,15 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this file,
  * You can obtain one at http://mozilla.org/MPL/2.0/. */
 "use strict";
 
+XPCOMUtils.defineLazyGetter(this, "GlobalEventDispatcher", () => EventDispatcher.instance);
+
 var PluginHelper = {
   showDoorHanger: function(aTab) {
     if (!aTab.browser)
       return;
 
     // Even though we may not end up showing a doorhanger, this flag
     // lets us know that we've tried to show a doorhanger.
     aTab.shouldShowPluginDoorhanger = false;
@@ -78,16 +80,20 @@ var PluginHelper = {
     if (!plugins || !plugins.length)
       return;
 
     plugins.forEach(this.playPlugin);
   },
 
   playPlugin: function(plugin) {
     let objLoadingContent = plugin.QueryInterface(Ci.nsIObjectLoadingContent);
+    let mimeType = objLoadingContent.actualType;
+    if (mimeType) {
+      GlobalEventDispatcher.sendRequest({ type: "PluginHelper:playFlash" });
+    }
     if (!objLoadingContent.activated)
       objLoadingContent.playPlugin();
   },
 
   getPluginPreference: function getPluginPreference() {
     let pluginDisable = Services.prefs.getBoolPref("plugin.disable");
     if (pluginDisable)
       return "0";
--- a/toolkit/components/telemetry/docs/data/core-ping.rst
+++ b/toolkit/components/telemetry/docs/data/core-ping.rst
@@ -50,16 +50,17 @@ Structure:
       "sessions": <integer>, // number of sessions since last upload
       "durations": <integer>, // combined duration, in seconds, of all
                                     // sessions since last upload
       "searches": <object>, // Optional, object of search use counts in the
                             // format: { "engine.source": <pos integer> }
                             // e.g.: { "yahoo.suggestion": 3, "other.listitem": 1 }
       "experiments": [<string>, /* … */], // Optional, array of identifiers
                                     // for the active experiments
+      "flashUsage": <integer>, // number of times flash plugin is played since last upload
     }
 
 Field details
 -------------
 
 device
 ~~~~~~
 The ``device`` field is filled in with information specified by the hardware
@@ -152,16 +153,17 @@ HTTP "Date" header
 This header is used to track the submission date of the core ping in the format
 specified by
 `rfc 2616 sec 14.18 <https://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.18>`_,
 et al (e.g. "Tue, 01 Feb 2011 14:00:00 GMT").
 
 
 Version history
 ---------------
+* v8: added ``flashUsage``
 * v7: added ``sessionCount`` & ``sessionDuration``
 * v6: added ``searches``
 * v5: added ``created`` & ``tz``
 * v4: ``profileDate`` will return package install time when times.json is not available
 * v3: added ``defaultSearch``
 * v2: added ``distributionId``
 * v1: initial version - shipped in `Fennec 45 <https://bugzilla.mozilla.org/show_bug.cgi?id=1205835>`_.