merge fx-team to mozilla-central

This commit is contained in:
Carsten "Tomcat" Book 2014-02-05 13:28:00 +01:00
Родитель f2c8d5b7a6 0e25436798
Коммит b377b7d2b5
24 изменённых файлов: 206 добавлений и 98 удалений

Просмотреть файл

@ -213,7 +213,6 @@ let gFxAccounts = {
},
openSignInAgainPage: function () {
// FIXME: This should actually show the pre-filled username version of about:accounts?
switchToTabHavingURI("about:accounts?signin=true", true);
switchToTabHavingURI("about:accounts?action=reauth", true);
}
};

Просмотреть файл

@ -173,6 +173,7 @@ toolbar[customizing] > .overflow-button {
}
%ifdef CAN_DRAW_IN_TITLEBAR
#main-window:not([chromemargin]) > #titlebar,
#main-window[inFullscreen] > #titlebar,
#main-window[inFullscreen] .titlebar-placeholder,
#main-window:not([tabsintitlebar]) .titlebar-placeholder {

Просмотреть файл

@ -4481,6 +4481,9 @@ var TabsInTitlebar = {
// Try to avoid reflows in this code by calculating dimensions first and
// then later set the properties affecting layout together in a batch.
// Get the full height of the tabs toolbar:
let tabsToolbar = $("TabsToolbar");
let fullTabsHeight = rect(tabsToolbar).height;
// Buttons first:
let captionButtonsBoxWidth = rect($("titlebar-buttonbox")).width;
#ifdef XP_MACOSX
@ -4495,11 +4498,9 @@ var TabsInTitlebar = {
let menuHeight = rect(menubar).height;
let menuStyles = window.getComputedStyle(menubar);
let fullMenuHeight = verticalMargins(menuStyles) + menuHeight;
#endif
// Get the full height of the tabs toolbar:
let tabsToolbar = $("TabsToolbar");
let tabsStyles = window.getComputedStyle(tabsToolbar);
let fullTabsHeight = rect(tabsToolbar).height + verticalMargins(tabsStyles);
fullTabsHeight += verticalMargins(tabsStyles);
#endif
// If the navbar overlaps the tabbar using negative margins, we need to take those into
// account so we don't overlap it
@ -4509,16 +4510,6 @@ var TabsInTitlebar = {
// And get the height of what's in the titlebar:
let titlebarContentHeight = rect(titlebarContent).height;
// Padding surrounds the tab-view-deck when we are in customization mode,
// so take that into account:
let areCustomizing = document.documentElement.hasAttribute("customizing") ||
document.documentElement.hasAttribute("customize-exiting");
let customizePadding = 0;
if (areCustomizing) {
let deckStyle = window.getComputedStyle($("tab-view-deck"));
customizePadding = parseFloat(deckStyle.paddingTop);
}
// Begin setting CSS properties which will cause a reflow
// If the menubar is around (menuHeight is non-zero), try to adjust
@ -4551,10 +4542,6 @@ var TabsInTitlebar = {
// Next, we calculate how much we need to stretch the titlebar down to
// go all the way to the bottom of the tab strip, if necessary.
let tabAndMenuHeight = fullTabsHeight + fullMenuHeight;
// Oh, and don't forget customization mode:
if (areCustomizing) {
tabAndMenuHeight += customizePadding;
}
if (tabAndMenuHeight > titlebarContentHeight) {
// We need to increase the titlebar content's outer height (ie including margins)
@ -4566,12 +4553,6 @@ var TabsInTitlebar = {
// On non-OSX, we can just use bottom margin:
#ifndef XP_MACOSX
titlebarContent.style.marginBottom = extraMargin + "px";
#else
// Otherwise, center the content. This means taking the titlebar's
// padding into account:
let halfMargin = (extraMargin - titlebarPadding) / 2;
titlebarContent.style.marginTop = halfMargin + "px";
titlebarContent.style.marginBottom = (titlebarPadding + halfMargin) + "px";
#endif
titlebarContentHeight += extraMargin;
}
@ -4606,6 +4587,7 @@ var TabsInTitlebar = {
updateTitlebarDisplay();
// Reset the margins and padding that might have been modified:
titlebarContent.style.marginTop = "";
titlebarContent.style.marginBottom = "";
titlebar.style.marginBottom = "";
menubar.style.paddingBottom = "";
@ -4630,16 +4612,37 @@ var TabsInTitlebar = {
#ifdef CAN_DRAW_IN_TITLEBAR
function updateTitlebarDisplay() {
document.getElementById("titlebar").hidden = !TabsInTitlebar.enabled;
#ifdef XP_MACOSX
// OS X and the other platforms differ enough to necessitate this kind of
// special-casing. Like the other platforms where we CAN_DRAW_IN_TITLEBAR,
// we draw in the OS X titlebar when putting the tabs up there. However, OS X
// also draws in the titlebar when a lightweight theme is applied, regardless
// of whether or not the tabs are drawn in the titlebar.
if (TabsInTitlebar.enabled) {
document.documentElement.setAttribute("chromemargin-nonlwtheme", "0,-1,-1,-1");
document.documentElement.setAttribute("chromemargin", "0,-1,-1,-1");
document.documentElement.removeAttribute("drawtitle");
} else {
// We set chromemargin-nonlwtheme to "" instead of removing it as a way of
// making sure that LightweightThemeConsumer doesn't take it upon itself to
// detect this value again if and when we do a lwtheme state change.
document.documentElement.setAttribute("chromemargin-nonlwtheme", "");
let isCustomizing = document.documentElement.hasAttribute("customizing");
let hasLWTheme = document.documentElement.hasAttribute("lwtheme");
if (!hasLWTheme || isCustomizing) {
document.documentElement.removeAttribute("chromemargin");
}
document.documentElement.setAttribute("drawtitle", "true");
}
#else
if (TabsInTitlebar.enabled)
#ifdef XP_WIN
document.documentElement.setAttribute("chromemargin", "0,2,2,2");
#else
document.documentElement.setAttribute("chromemargin", "0,-1,-1,-1");
#endif
else
document.documentElement.removeAttribute("chromemargin");
#endif
}
#endif

Просмотреть файл

@ -313,7 +313,8 @@ skip-if = true # disabled until the tree view is added
[browser_tab_dragdrop.js]
[browser_tab_dragdrop2.js]
[browser_tabbar_big_widgets.js]
skip-if = os == "linux" # No tabs in titlebar on linux
skip-if = os == "linux" || os == "mac" # No tabs in titlebar on linux
# Disabled on OS X because of bug 967917
[browser_tabfocus.js]
[browser_tabopen_reflows.js]
[browser_tabs_isActive.js]

Просмотреть файл

@ -123,9 +123,6 @@ const CustomizableWidgets = [{
item.setAttribute("label", title || uri);
item.setAttribute("targetURI", uri);
item.setAttribute("class", "subviewbutton");
item.addEventListener("command", function (aEvent) {
onHistoryVisit(uri, aEvent, item);
});
item.addEventListener("click", function (aEvent) {
onHistoryVisit(uri, aEvent, item);
});

Просмотреть файл

@ -13,6 +13,8 @@ support-files =
# Bug 916763 - too many intermittent failures
skip-if = true
[browser_inspector_markup_edit.js]
# Bug 904953 - too many intermittent failures on Linux
skip-if = os == "linux"
[browser_inspector_markup_edit_outerhtml.js]
[browser_inspector_markup_edit_outerhtml2.js]
[browser_inspector_markup_mutation.js]

Просмотреть файл

@ -1143,8 +1143,7 @@ var BrowserUI = {
confirmSanitizeDialog: function () {
let bundle = Services.strings.createBundle("chrome://browser/locale/browser.properties");
let title = bundle.GetStringFromName("clearPrivateData.title2");
let options = bundle.GetStringFromName("optionsCharm");
let message = bundle.GetStringFromName("clearPrivateData.message2").replace("#1", options);
let message = bundle.GetStringFromName("clearPrivateData.message3");
let clearbutton = bundle.GetStringFromName("clearPrivateData.clearButton");
let prefsClearButton = document.getElementById("prefs-clear-data");

Просмотреть файл

@ -9,16 +9,18 @@ function test() {
runTests();
}
function getSimpleMeasurementsFromTelemetryPing() {
function getTelemetryPayload() {
return Cu.import("resource://gre/modules/TelemetryPing.jsm", {}).
TelemetryPing.getPayload().simpleMeasurements;
TelemetryPing.getPayload();
}
gTests.push({
desc: "Test browser-ui telemetry",
run: function testBrowserUITelemetry() {
// startup should have registered simple measures function
let simpleMeasurements = getSimpleMeasurementsFromTelemetryPing();
is(getTelemetryPayload().info.appName, "MetroFirefox");
let simpleMeasurements = getTelemetryPayload().simpleMeasurements;
ok(simpleMeasurements, "simpleMeasurements are truthy");
ok(simpleMeasurements.UITelemetry["metro-ui"]["window-width"], "window-width measurement was captured");
ok(simpleMeasurements.UITelemetry["metro-ui"]["window-height"], "window-height measurement was captured");

Просмотреть файл

@ -39,8 +39,8 @@ contextAppbar2.clear=Clear selection
# Clear private data
clearPrivateData.clearButton=Clear
clearPrivateData.title2=Clear private data
# LOCALIZATION NOTE (clearPrivateData.message2): #1 is optionsCharm
clearPrivateData.message2=This will permanently delete the private data you have selected in #1
# LOCALIZATION NOTE (clearPrivateData.message3): "Options" is the optionsCharm.
clearPrivateData.message3=This will permanently delete the private data you have selected in "Options".
# Settings Charms
aboutCharm1=About

Просмотреть файл

@ -73,6 +73,7 @@ browser.jar:
skin/classic/browser/customizableui/customizeMode-separatorHorizontal.png (customizableui/customizeMode-separatorHorizontal.png)
skin/classic/browser/customizableui/customizeMode-separatorVertical.png (customizableui/customizeMode-separatorVertical.png)
skin/classic/browser/customizableui/customizeFavicon.ico (../shared/customizableui/customizeFavicon.ico)
skin/classic/browser/customizableui/menuPanel-customizeFinish.png (../shared/customizableui/menuPanel-customizeFinish.png)
* skin/classic/browser/customizableui/panelUIOverlay.css (customizableui/panelUIOverlay.css)
skin/classic/browser/customizableui/subView-arrow-back-inverted.png (../shared/customizableui/subView-arrow-back-inverted.png)
skin/classic/browser/downloads/allDownloadsViewOverlay.css (downloads/allDownloadsViewOverlay.css)

Просмотреть файл

@ -59,7 +59,7 @@
}
}
#main-window[chromehidden~="toolbar"] > #titlebar {
#main-window[chromehidden~="toolbar"]:not(:-moz-lwtheme) > #titlebar {
padding-top: 22px;
}
@ -2669,7 +2669,7 @@ toolbarbutton.chevron > .toolbarbutton-menu-dropmarker {
box-shadow: @focusRingShadow@;
}
#titlebar {
#main-window:not(:-moz-lwtheme) > #titlebar {
padding-top: @spaceAboveTabbar@;
min-height: @tabHeight@;
}
@ -4104,13 +4104,26 @@ window > chatbox {
%include ../shared/customizableui/customizeMode.inc.css
#main-window[customize-entered] #titlebar {
#main-window[customize-entered] > #titlebar {
padding-top: 0;
}
#main-window[tabsintitlebar][customize-entered] #titlebar-content {
margin-bottom: 0px !important;
margin-top: 11px !important;
#main-window[tabsintitlebar]:not([customizing]):not(:-moz-lwtheme) > #titlebar > #titlebar-content,
#main-window[tabsintitlebar][customize-entering] > #titlebar > #titlebar-content,
#main-window[tabsintitlebar][customize-exiting] > #titlebar > #titlebar-content {
margin-top: 2px;
margin-bottom: 11px;
}
#main-window[tabsintitlebar][customize-entered] > #titlebar > #titlebar-content,
#main-window:not([tabsintitlebar]):not(:-moz-lwtheme) > #titlebar > #titlebar-content {
margin-top: 11px;
margin-bottom: 0px;
}
#main-window[tabsintitlebar]:-moz-lwtheme > #titlebar > #titlebar-content {
margin-top: 11px;
margin-bottom: 11px;
}
#main-window[customize-entered] #tab-view-deck {
@ -4135,8 +4148,11 @@ window > chatbox {
border-bottom-width: 0;
}
#main-window[customize-entered] #TabsToolbar {
#main-window[tabsintitlebar][customize-entered] #TabsToolbar {
margin-top: 9px;
}
#main-window[customize-entered] #TabsToolbar {
background-clip: padding-box;
border-right: 3px solid transparent;
border-left: 3px solid transparent;

Просмотреть файл

@ -15,6 +15,10 @@
list-style-image: url(chrome://browser/skin/menuPanel-customize@2x.png);
}
#main-window[customize-entered] #PanelUI-customize {
list-style-image: url(chrome://browser/skin/customizableui/menuPanel-customizeFinish@2x.png);
}
#PanelUI-help {
list-style-image: url(chrome://browser/skin/menuPanel-help@2x.png);
}

Просмотреть файл

@ -120,6 +120,8 @@ browser.jar:
skin/classic/browser/customizableui/customizeMode-gridTexture.png (customizableui/customizeMode-gridTexture.png)
skin/classic/browser/customizableui/customizeMode-separatorHorizontal.png (customizableui/customizeMode-separatorHorizontal.png)
skin/classic/browser/customizableui/customizeMode-separatorVertical.png (customizableui/customizeMode-separatorVertical.png)
skin/classic/browser/customizableui/menuPanel-customizeFinish.png (../shared/customizableui/menuPanel-customizeFinish.png)
skin/classic/browser/customizableui/menuPanel-customizeFinish@2x.png (../shared/customizableui/menuPanel-customizeFinish@2x.png)
skin/classic/browser/customizableui/subView-arrow-back-inverted.png (../shared/customizableui/subView-arrow-back-inverted.png)
skin/classic/browser/customizableui/subView-arrow-back-inverted@2x.png (../shared/customizableui/subView-arrow-back-inverted@2x.png)
* skin/classic/browser/customizableui/panelUIOverlay.css (customizableui/panelUIOverlay.css)

Двоичные данные
browser/themes/shared/customizableui/menuPanel-customizeFinish.png Normal file

Двоичный файл не отображается.

После

Ширина:  |  Высота:  |  Размер: 236 B

Двоичный файл не отображается.

После

Ширина:  |  Высота:  |  Размер: 399 B

Просмотреть файл

@ -322,6 +322,10 @@ toolbarpaletteitem[place="palette"] > toolbaritem > toolbarbutton {
list-style-image: url(chrome://browser/skin/menuPanel-customize.png);
}
#customization-panelHolder #PanelUI-customize {
list-style-image: url(chrome://browser/skin/customizableui/menuPanel-customizeFinish.png);
}
#PanelUI-help {
list-style-image: url(chrome://browser/skin/menuPanel-help.png);
}
@ -378,16 +382,15 @@ toolbarpaletteitem[place="palette"] > toolbaritem > toolbarbutton {
background-color: #ad3434;
}
#main-window[customize-entered] #PanelUI-customize {
#customization-panelHolder #PanelUI-customize {
color: white;
background-image: linear-gradient(rgb(41,123,204), rgb(40,133,203));
box-shadow: inset 0 1px 1px rgba(0,0,0,0.5), 0 2px rgba(255,255,255,0.2);
text-shadow: 0 1px 0 rgba(0,0,0,0.4);
background-color: rgb(116,191,67);
text-shadow: none;
}
#main-window[customize-entered] #PanelUI-customize:hover,
#main-window[customize-entered] #PanelUI-customize:hover:active {
background-image: linear-gradient(rgb(38,115,191), rgb(38,125,191));
#customization-panelHolder #PanelUI-customize:hover,
#customization-panelHolder #PanelUI-customize:hover:active {
background-color: rgb(105,173,61);
}
#customization-palette .toolbarbutton-multiline-text,

Просмотреть файл

@ -92,6 +92,7 @@ browser.jar:
skin/classic/browser/customizableui/customizeMode-gridTexture.png (customizableui/customizeMode-gridTexture.png)
skin/classic/browser/customizableui/customizeMode-separatorHorizontal.png (customizableui/customizeMode-separatorHorizontal.png)
skin/classic/browser/customizableui/customizeMode-separatorVertical.png (customizableui/customizeMode-separatorVertical.png)
skin/classic/browser/customizableui/menuPanel-customizeFinish.png (../shared/customizableui/menuPanel-customizeFinish.png)
* skin/classic/browser/customizableui/panelUIOverlay.css (customizableui/panelUIOverlay.css)
skin/classic/browser/customizableui/subView-arrow-back-inverted.png (../shared/customizableui/subView-arrow-back-inverted.png)
* skin/classic/browser/downloads/allDownloadsViewOverlay.css (downloads/allDownloadsViewOverlay.css)
@ -404,6 +405,7 @@ browser.jar:
skin/classic/aero/browser/customizableui/customizeMode-gridTexture.png (customizableui/customizeMode-gridTexture.png)
skin/classic/aero/browser/customizableui/customizeMode-separatorHorizontal.png (customizableui/customizeMode-separatorHorizontal.png)
skin/classic/aero/browser/customizableui/customizeMode-separatorVertical.png (customizableui/customizeMode-separatorVertical.png)
skin/classic/aero/browser/customizableui/menuPanel-customizeFinish.png (../shared/customizableui/menuPanel-customizeFinish.png)
* skin/classic/aero/browser/customizableui/panelUIOverlay.css (customizableui/panelUIOverlay.css)
skin/classic/aero/browser/customizableui/subView-arrow-back-inverted.png (../shared/customizableui/subView-arrow-back-inverted.png)
* skin/classic/aero/browser/downloads/allDownloadsViewOverlay.css (downloads/allDownloadsViewOverlay-aero.css)

Просмотреть файл

@ -538,7 +538,7 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
this.fieldID = integerQuery("named_fields", "field_id",
"measurement_name = ? AND measurement_version = ? AND field_name = ?",
new String[] {measurementName, measurementVersion, fieldName},
-1);
UNKNOWN_TYPE_OR_FIELD_ID);
if (this.fieldID == UNKNOWN_TYPE_OR_FIELD_ID) {
throw new IllegalStateException("No field with name " + fieldName +
" (" + measurementName + ", " + measurementVersion + ")");
@ -552,7 +552,9 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
// store differently stable kinds of data, hence type difference.
// Note that we don't pre-populate the environment cache. We'll typically only
// handle one per session.
private final ConcurrentHashMap<String, Integer> envs = new ConcurrentHashMap<String, Integer>();
//
// protected for testing purposes only.
protected final ConcurrentHashMap<String, Integer> envs = new ConcurrentHashMap<String, Integer>();
/**
* An {@link Environment} that knows how to persist to and from our database.
@ -855,6 +857,12 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
private HashMap<String, Field> fields = new HashMap<String, Field>();
private boolean fieldsCacheUpdated = false;
private void invalidateFieldsCache() {
synchronized (this.fields) {
fieldsCacheUpdated = false;
}
}
private String getFieldKey(String mName, int mVersion, String fieldName) {
return mVersion + "." + mName + "/" + fieldName;
}
@ -1014,9 +1022,7 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
notifyMeasurementVersionUpdated(measurement, version);
// Let's be easy for now.
synchronized (fields) {
fieldsCacheUpdated = false;
}
invalidateFieldsCache();
}
/**
@ -1152,10 +1158,16 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
final SQLiteDatabase db = this.helper.getWritableDatabase();
putValue(v, value);
try {
db.insertOrThrow(table, null, v);
} catch (SQLiteConstraintException e) {
throw new IllegalStateException("Event did not reference existing an environment or field.", e);
// Using SQLiteDatabase.insertOrThrow throws SQLiteConstraintException we cannot catch for
// unknown reasons (bug 961526 comment 13). We believe these are thrown because we attempt to
// record events using environment IDs removed from the database by the prune service. We
// invalidate the currentEnvironment ID after pruning, preventing further propagation,
// however, any event recording waiting for the prune service to complete on the background
// thread may carry an invalid ID: we expect an insertion failure and drop these events here.
final long res = db.insert(table, null, v);
if (res == -1) {
Logger.error(LOG_TAG, "Unable to record daily discrete event. Ignoring.");
}
}
@ -1516,6 +1528,11 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
try {
// Cascade will clear the rest.
db.delete("measurements", null, null);
// Clear measurements and fields cache, because some of their IDs are now invalid.
invalidateFieldsCache(); // Let it repopulate on its own.
populateMeasurementVersionsCache(db); // Performed at Storage init so repopulate now.
db.setTransactionSuccessful();
} finally {
db.endTransaction();
@ -1524,7 +1541,7 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
/**
* Prunes the given number of least-recently used environments. Note that orphaned environments
* are not removed.
* are not removed and the environment cache is cleared.
*/
public void pruneEnvironments(final int numToPrune) {
final SQLiteDatabase db = this.helper.getWritableDatabase();
@ -1538,6 +1555,9 @@ public class HealthReportDatabaseStorage implements HealthReportStorage {
" LIMIT " + numToPrune + ")",
null);
db.setTransactionSuccessful();
// Clear environment cache, because some of their IDs are now invalid.
this.envs.clear();
} finally {
db.endTransaction();
}

Просмотреть файл

@ -43,6 +43,11 @@ public class PrunePolicyDatabaseStorage implements PrunePolicyStorage {
public void pruneEnvironments(final int count) {
getStorage().pruneEnvironments(count);
// Re-populate the DB and environment cache with the current environment in the unlikely event
// that it was deleted.
this.currentEnvironmentID = -1;
getCurrentEnvironmentID();
}
/**

Просмотреть файл

@ -37,9 +37,13 @@ import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStreamWriter;
import java.nio.charset.Charset;
import java.util.Arrays;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Scanner;
import java.util.Set;
import java.util.concurrent.atomic.AtomicBoolean;
/**
@ -758,11 +762,11 @@ public class BrowserHealthRecorder implements GeckoEventListener {
public static final String MEASUREMENT_NAME_SEARCH_COUNTS = "org.mozilla.searches.counts";
public static final int MEASUREMENT_VERSION_SEARCH_COUNTS = 5;
public static final String[] SEARCH_LOCATIONS = {
public static final Set<String> SEARCH_LOCATIONS = Collections.unmodifiableSet(new HashSet<String>(Arrays.asList(new String[] {
"barkeyword",
"barsuggest",
"bartext",
};
})));
private void initializeSearchProvider() {
this.storage.ensureMeasurementInitialized(
@ -771,7 +775,7 @@ public class BrowserHealthRecorder implements GeckoEventListener {
new MeasurementFields() {
@Override
public Iterable<FieldSpec> getFields() {
ArrayList<FieldSpec> out = new ArrayList<FieldSpec>(SEARCH_LOCATIONS.length);
ArrayList<FieldSpec> out = new ArrayList<FieldSpec>(SEARCH_LOCATIONS.size());
for (String location : SEARCH_LOCATIONS) {
// We're not using a counter, because the set of engine
// identifiers is potentially unbounded, and thus our
@ -803,19 +807,31 @@ public class BrowserHealthRecorder implements GeckoEventListener {
return;
}
final int env = this.env;
if (env == -1) {
Log.d(LOG_TAG, "No environment: not recording search.");
return;
}
if (location == null) {
throw new IllegalArgumentException("location must be provided for search.");
}
// Ensure that we don't throw when trying to look up the field for an
// unknown location. If you add a search location, you must extend the
// list of search locations *and update the measurement version*.
if (!SEARCH_LOCATIONS.contains(location)) {
throw new IllegalArgumentException("Unexpected location: " + location);
}
final int day = storage.getDay();
final int env = this.env;
final String key = (engineID == null) ? "other" : engineID;
final BrowserHealthRecorder self = this;
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
final HealthReportDatabaseStorage storage = self.storage;
final HealthReportDatabaseStorage storage = BrowserHealthRecorder.this.storage;
if (storage == null) {
Log.d(LOG_TAG, "No storage: not recording search. Shutting down?");
return;

Просмотреть файл

@ -5,6 +5,7 @@ package org.mozilla.gecko.background.healthreport;
import java.io.File;
import java.util.ArrayList;
import java.util.concurrent.ConcurrentHashMap;
import org.json.JSONObject;
import org.mozilla.gecko.background.common.GlobalConstants;
@ -42,6 +43,10 @@ public class MockHealthReportDatabaseStorage extends HealthReportDatabaseStorage
return now - numDays * GlobalConstants.MILLISECONDS_PER_DAY;
}
public ConcurrentHashMap<String, Integer> getEnvironmentCache() {
return this.envs;
}
public MockHealthReportDatabaseStorage(Context context, File fakeProfileDirectory) {
super(context, fakeProfileDirectory);
}

Просмотреть файл

@ -326,10 +326,6 @@ public class TestHealthReportDatabaseStorage extends FakeProfileTestCase {
storage.incrementDailyCount(nonExistentEnvID, storage.getToday(), counterFieldID);
fail("Should throw - event_integer(env) references environments(id), which is given as a non-existent value.");
} catch (IllegalStateException e) { }
try {
storage.recordDailyDiscrete(nonExistentEnvID, storage.getToday(), discreteFieldID, "iu");
fail("Should throw - event_textual(env) references environments(id), which is given as a non-existent value.");
} catch (IllegalStateException e) { }
try {
storage.recordDailyLast(nonExistentEnvID, storage.getToday(), discreteFieldID, "iu");
fail("Should throw - event_textual(env) references environments(id), which is given as a non-existent value.");
@ -339,14 +335,30 @@ public class TestHealthReportDatabaseStorage extends FakeProfileTestCase {
storage.incrementDailyCount(envID, storage.getToday(), nonExistentFieldID);
fail("Should throw - event_integer(field) references fields(id), which is given as a non-existent value.");
} catch (IllegalStateException e) { }
try {
storage.recordDailyDiscrete(envID, storage.getToday(), nonExistentFieldID, "iu");
fail("Should throw - event_textual(field) references fields(id), which is given as a non-existent value.");
} catch (IllegalStateException e) { }
try {
storage.recordDailyLast(envID, storage.getToday(), nonExistentFieldID, "iu");
fail("Should throw - event_textual(field) references fields(id), which is given as a non-existent value.");
} catch (IllegalStateException e) { }
// Test dropped events due to constraint violations that do not throw (see bug 961526).
final String eventValue = "a value not in the database";
assertFalse(isEventInDB(db, eventValue)); // Better safe than sorry.
storage.recordDailyDiscrete(nonExistentEnvID, storage.getToday(), discreteFieldID, eventValue);
assertFalse(isEventInDB(db, eventValue));
storage.recordDailyDiscrete(envID, storage.getToday(), nonExistentFieldID, "iu");
assertFalse(isEventInDB(db, eventValue));
}
private static boolean isEventInDB(final SQLiteDatabase db, final String value) {
final Cursor c = db.query("events_textual", new String[] {"value"}, "value = ?",
new String[] {value}, null, null, null);
try {
return c.getCount() > 0;
} finally {
c.close();
}
}
// Largely taken from testDeleteEnvAndEventsBefore and testDeleteOrphanedAddons.
@ -553,7 +565,10 @@ public class TestHealthReportDatabaseStorage extends FakeProfileTestCase {
new PrepopulatedMockHealthReportDatabaseStorage(context, fakeProfileDirectory, 2);
final SQLiteDatabase db = storage.getDB();
assertEquals(5, DBHelpers.getRowCount(db, "environments"));
assertEquals(5, storage.getEnvironmentCache().size());
storage.pruneEnvironments(1);
assertEquals(0, storage.getEnvironmentCache().size());
assertTrue(!getEnvAppVersions(db).contains("v3"));
storage.pruneEnvironments(2);
assertTrue(!getEnvAppVersions(db).contains("v2"));

Просмотреть файл

@ -457,6 +457,14 @@ let Impl = {
revision: HISTOGRAMS_FILE_VERSION,
locale: getLocale()
};
// In order to share profile data, the appName used for Metro Firefox is "Firefox",
// (the same as desktop Firefox). We set it to "MetroFirefox" here in order to
// differentiate telemetry pings sent by desktop vs. metro Firefox.
if(Services.metro && Services.metro.immersive) {
ret.appName = "MetroFirefox";
}
if (this._previousBuildID) {
ret.previousBuildID = this._previousBuildID;
}

Просмотреть файл

@ -42,9 +42,7 @@ LightweightThemeConsumer.prototype = {
_lastScreenWidth: null,
_lastScreenHeight: null,
_enabled: true,
#ifdef XP_MACOSX
_chromemarginDefault: undefined,
#endif
_active: false,
enable: function() {
this._enabled = true;
@ -100,8 +98,9 @@ LightweightThemeConsumer.prototype = {
if (!this._enabled)
return;
var root = this._doc.documentElement;
var active = !!aData.headerURL;
let root = this._doc.documentElement;
let active = !!aData.headerURL;
let stateChanging = (active != this._active);
if (active) {
root.style.color = aData.textcolor || "black";
@ -117,6 +116,8 @@ LightweightThemeConsumer.prototype = {
root.removeAttribute("lwtheme");
}
this._active = active;
_setImage(root, active, aData.headerURL);
if (this._footerId) {
let footer = this._doc.getElementById(this._footerId);
@ -129,20 +130,26 @@ LightweightThemeConsumer.prototype = {
}
#ifdef XP_MACOSX
// Sample whether or not we draw in the titlebar by default the first time we update.
// If the root has no chromemargin attribute, getAttribute will return null, and
// we'll remove the attribute when the lw-theme is deactivated.
if (this._chromemarginDefault === undefined)
this._chromemarginDefault = root.getAttribute("chromemargin");
// On OS X, we extend the lightweight theme into the titlebar, which means setting
// the chromemargin attribute. Some XUL applications already draw in the titlebar,
// so we need to save the chromemargin value before we overwrite it with the value
// that lets us draw in the titlebar. We stash this value on the root attribute so
// that XUL applications have the ability to invalidate the saved value.
if (stateChanging) {
if (!root.hasAttribute("chromemargin-nonlwtheme")) {
root.setAttribute("chromemargin-nonlwtheme", root.getAttribute("chromemargin"));
}
if (active) {
root.setAttribute("chromemargin", "0,-1,-1,-1");
}
else {
if (this._chromemarginDefault)
root.setAttribute("chromemargin", this._chromemarginDefault);
else
root.removeAttribute("chromemargin");
if (active) {
root.setAttribute("chromemargin", "0,-1,-1,-1");
} else {
let defaultChromemargin = root.getAttribute("chromemargin-nonlwtheme");
if (defaultChromemargin) {
root.setAttribute("chromemargin", defaultChromemargin);
} else {
root.removeAttribute("chromemargin");
}
}
}
#endif
}