Bug 1435092 - Add a util object to manage preferences; r=bgrins. draft
authorNicolas Chevobbe <nchevobbe@mozilla.com>
Tue, 13 Feb 2018 17:35:32 +0100 (2018-02-13)
changeset 756885 9dc60df24d0514c8bd0aac7655483eb3d026a16a
parent 756852 ad133cd410a719c0b67e61b8d3b1c77a32fd80a9
child 756886 b1b5bc2d35624677fc241194ab1a49502cafe31d
push id99576
push userbmo:nchevobbe@mozilla.com
push dateMon, 19 Feb 2018 07:33:15 +0000 (2018-02-19)
reviewersbgrins
bugs1435092
milestone60.0a1
Bug 1435092 - Add a util object to manage preferences; r=bgrins. This allow us to manage different sets of preferences for the console and the browser console. The util object is passed to the actions through a custom thunk middleware. MozReview-Commit-ID: 6IQLBqX7KMN
devtools/client/preferences/devtools.js
devtools/client/webconsole/new-console-output/actions/filters.js
devtools/client/webconsole/new-console-output/actions/ui.js
devtools/client/webconsole/new-console-output/constants.js
devtools/client/webconsole/new-console-output/store.js
devtools/client/webconsole/new-console-output/utils/moz.build
devtools/client/webconsole/new-console-output/utils/prefs.js
--- a/devtools/client/preferences/devtools.js
+++ b/devtools/client/preferences/devtools.js
@@ -250,17 +250,26 @@ pref("devtools.webconsole.filter.secwarn
 pref("devtools.webconsole.filter.serviceworkers", true);
 pref("devtools.webconsole.filter.sharedworkers", false);
 pref("devtools.webconsole.filter.windowlessworkers", false);
 pref("devtools.webconsole.filter.servererror", false);
 pref("devtools.webconsole.filter.serverwarn", false);
 pref("devtools.webconsole.filter.serverinfo", false);
 pref("devtools.webconsole.filter.serverlog", false);
 
-// Remember the Browser Console filters
+// Browser console filters
+pref("devtools.browserconsole.filter.error", true);
+pref("devtools.browserconsole.filter.warn", true);
+pref("devtools.browserconsole.filter.info", true);
+pref("devtools.browserconsole.filter.log", true);
+pref("devtools.browserconsole.filter.debug", true);
+pref("devtools.browserconsole.filter.css", false);
+pref("devtools.browserconsole.filter.net", false);
+pref("devtools.browserconsole.filter.netxhr", false);
+// Remember the Browser Console filters (old frontend)
 pref("devtools.browserconsole.filter.network", true);
 pref("devtools.browserconsole.filter.networkinfo", false);
 pref("devtools.browserconsole.filter.netwarn", true);
 pref("devtools.browserconsole.filter.netxhr", false);
 pref("devtools.browserconsole.filter.csserror", true);
 pref("devtools.browserconsole.filter.cssparser", false);
 pref("devtools.browserconsole.filter.csslog", false);
 pref("devtools.browserconsole.filter.exception", true);
@@ -275,18 +284,20 @@ pref("devtools.browserconsole.filter.sec
 pref("devtools.browserconsole.filter.serviceworkers", true);
 pref("devtools.browserconsole.filter.sharedworkers", true);
 pref("devtools.browserconsole.filter.windowlessworkers", true);
 pref("devtools.browserconsole.filter.servererror", false);
 pref("devtools.browserconsole.filter.serverwarn", false);
 pref("devtools.browserconsole.filter.serverinfo", false);
 pref("devtools.browserconsole.filter.serverlog", false);
 
-// Web console filter settings bar
+// Web console filter bar settings
 pref("devtools.webconsole.ui.filterbar", false);
+// Browser console filter bar settings
+pref("devtools.browserconsole.ui.filterbar", false);
 
 // Max number of inputs to store in web console history.
 pref("devtools.webconsole.inputHistoryCount", 50);
 
 // Persistent logging: |true| if you want the relevant tool to keep all of the
 // logged messages after reloading the page, |false| if you want the output to
 // be cleared each time page navigation happens.
 pref("devtools.webconsole.persistlog", false);
--- a/devtools/client/webconsole/new-console-output/actions/filters.js
+++ b/devtools/client/webconsole/new-console-output/actions/filters.js
@@ -2,17 +2,16 @@
 /* vim: set ft=javascript ts=2 et sw=2 tw=80: */
 /* 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";
 
 const { getAllFilters } = require("devtools/client/webconsole/new-console-output/selectors/filters");
-const Services = require("Services");
 
 const {
   FILTER_TEXT_SET,
   FILTER_TOGGLE,
   FILTERS_CLEAR,
   DEFAULT_FILTERS_RESET,
   PREFS,
   FILTERS,
@@ -22,60 +21,59 @@ const {
 function filterTextSet(text) {
   return {
     type: FILTER_TEXT_SET,
     text
   };
 }
 
 function filterToggle(filter) {
-  return (dispatch, getState) => {
+  return (dispatch, getState, {prefsService}) => {
     dispatch({
       type: FILTER_TOGGLE,
       filter,
     });
     const filterState = getAllFilters(getState());
-    Services.prefs.setBoolPref(PREFS.FILTER[filter.toUpperCase()],
-      filterState[filter]);
+    prefsService.setBoolPref(PREFS.FILTER[filter.toUpperCase()], filterState[filter]);
   };
 }
 
 function filtersClear() {
-  return (dispatch, getState) => {
+  return (dispatch, getState, {prefsService}) => {
     dispatch({
       type: FILTERS_CLEAR,
     });
 
     const filterState = getAllFilters(getState());
     for (let filter in filterState) {
       if (filter !== FILTERS.TEXT) {
-        Services.prefs.clearUserPref(PREFS.FILTER[filter.toUpperCase()]);
+        prefsService.clearUserPref(PREFS.FILTER[filter.toUpperCase()]);
       }
     }
   };
 }
 
 /**
  * Set the default filters to their original values.
  * This is different than filtersClear where we reset
  * all the filters to their original values. Here we want
  * to keep non-default filters the user might have set.
  */
 function defaultFiltersReset() {
-  return (dispatch, getState) => {
+  return (dispatch, getState, {prefsService}) => {
     // Get the state before dispatching so the action does not alter prefs reset.
     const filterState = getAllFilters(getState());
 
     dispatch({
       type: DEFAULT_FILTERS_RESET,
     });
 
     DEFAULT_FILTERS.forEach(filter => {
       if (filterState[filter] === false) {
-        Services.prefs.clearUserPref(PREFS.FILTER[filter.toUpperCase()]);
+        prefsService.clearUserPref(PREFS.FILTER[filter.toUpperCase()]);
       }
     });
   };
 }
 
 module.exports = {
   filterTextSet,
   filterToggle,
--- a/devtools/client/webconsole/new-console-output/actions/ui.js
+++ b/devtools/client/webconsole/new-console-output/actions/ui.js
@@ -3,46 +3,45 @@
 /* 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";
 
 const { getAllUi } = require("devtools/client/webconsole/new-console-output/selectors/ui");
 const { getMessage } = require("devtools/client/webconsole/new-console-output/selectors/messages");
-const Services = require("Services");
 
 const {
   FILTER_BAR_TOGGLE,
   INITIALIZE,
   PERSIST_TOGGLE,
   PREFS,
   SELECT_NETWORK_MESSAGE_TAB,
   SIDEBAR_CLOSE,
   SHOW_OBJECT_IN_SIDEBAR,
   TIMESTAMPS_TOGGLE,
 } = require("devtools/client/webconsole/new-console-output/constants");
 
 function filterBarToggle(show) {
-  return (dispatch, getState) => {
+  return (dispatch, getState, {prefsService}) => {
     dispatch({
       type: FILTER_BAR_TOGGLE,
     });
-    const uiState = getAllUi(getState());
-    Services.prefs.setBoolPref(PREFS.UI.FILTER_BAR, uiState.filterBarVisible);
+    const {filterBarVisible} = getAllUi(getState());
+    prefsService.setBoolPref(PREFS.UI.FILTER_BAR, filterBarVisible);
   };
 }
 
 function persistToggle(show) {
-  return (dispatch, getState) => {
+  return (dispatch, getState, {prefsService}) => {
     dispatch({
       type: PERSIST_TOGGLE,
     });
     const uiState = getAllUi(getState());
-    Services.prefs.setBoolPref(PREFS.UI.PERSIST, uiState.persistLogs);
+    prefsService.setBoolPref(PREFS.UI.PERSIST, uiState.persistLogs);
   };
 }
 
 function timestampsToggle(visible) {
   return {
     type: TIMESTAMPS_TOGGLE,
     visible,
   };
--- a/devtools/client/webconsole/new-console-output/constants.js
+++ b/devtools/client/webconsole/new-console-output/constants.js
@@ -25,29 +25,35 @@ const actionTypes = {
   SELECT_NETWORK_MESSAGE_TAB: "SELECT_NETWORK_MESSAGE_TAB",
   SIDEBAR_CLOSE: "SIDEBAR_CLOSE",
   SHOW_OBJECT_IN_SIDEBAR: "SHOW_OBJECT_IN_SIDEBAR",
   TIMESTAMPS_TOGGLE: "TIMESTAMPS_TOGGLE",
 };
 
 const prefs = {
   PREFS: {
+    // Filter preferences only have the suffix since they can be used either for the
+    // webconsole or the browser console.
     FILTER: {
-      ERROR: "devtools.webconsole.filter.error",
-      WARN: "devtools.webconsole.filter.warn",
-      INFO: "devtools.webconsole.filter.info",
-      LOG: "devtools.webconsole.filter.log",
-      DEBUG: "devtools.webconsole.filter.debug",
-      CSS: "devtools.webconsole.filter.css",
-      NET: "devtools.webconsole.filter.net",
-      NETXHR: "devtools.webconsole.filter.netxhr",
+      ERROR: "filter.error",
+      WARN: "filter.warn",
+      INFO: "filter.info",
+      LOG: "filter.log",
+      DEBUG: "filter.debug",
+      CSS: "filter.css",
+      NET: "filter.net",
+      NETXHR: "filter.netxhr",
     },
     UI: {
-      FILTER_BAR: "devtools.webconsole.ui.filterbar",
+      // Filter bar UI preference only have the suffix since it can be used either for
+      // the webconsole or the browser console.
+      FILTER_BAR: "ui.filterbar",
+      // Persist is only used by the webconsole.
       PERSIST: "devtools.webconsole.persistlog",
+      // We use the same pref to enable the sidebar on webconsole and browser console.
       SIDEBAR_TOGGLE: "devtools.webconsole.sidebarToggle",
     }
   }
 };
 
 const FILTERS = {
   CSS: "css",
   DEBUG: "debug",
--- a/devtools/client/webconsole/new-console-output/store.js
+++ b/devtools/client/webconsole/new-console-output/store.js
@@ -6,80 +6,92 @@
 const {FilterState} = require("devtools/client/webconsole/new-console-output/reducers/filters");
 const {PrefState} = require("devtools/client/webconsole/new-console-output/reducers/prefs");
 const {UiState} = require("devtools/client/webconsole/new-console-output/reducers/ui");
 const {
   applyMiddleware,
   compose,
   createStore
 } = require("devtools/client/shared/vendor/redux");
-const { thunk } = require("devtools/client/shared/redux/middleware/thunk");
 const {
   BATCH_ACTIONS
 } = require("devtools/client/shared/redux/middleware/debounce");
 const {
   MESSAGE_OPEN,
   MESSAGES_ADD,
   MESSAGES_CLEAR,
   REMOVED_ACTORS_CLEAR,
   NETWORK_MESSAGE_UPDATE,
   PREFS,
 } = require("devtools/client/webconsole/new-console-output/constants");
 const { reducers } = require("./reducers/index");
-const Services = require("Services");
 const {
   getMessage,
   getAllMessagesUiById,
 } = require("devtools/client/webconsole/new-console-output/selectors/messages");
 const DataProvider = require("devtools/client/netmonitor/src/connector/firefox-data-provider");
 const {
   getAllNetworkMessagesUpdateById,
 } = require("devtools/client/webconsole/new-console-output/selectors/messages");
+const {getPrefsService} = require("devtools/client/webconsole/new-console-output/utils/prefs");
 
 /**
  * Create and configure store for the Console panel. This is the place
  * where various enhancers and middleware can be registered.
  */
 function configureStore(hud, options = {}) {
+  const prefsService = getPrefsService(hud);
+  const {
+    getBoolPref,
+    getIntPref,
+  } = prefsService;
+
   const logLimit = options.logLimit
-    || Math.max(Services.prefs.getIntPref("devtools.hud.loglimit"), 1);
-
-  const sidebarToggle = Services.prefs.getBoolPref(PREFS.UI.SIDEBAR_TOGGLE);
+    || Math.max(getIntPref("devtools.hud.loglimit"), 1);
+  const sidebarToggle = getBoolPref(PREFS.UI.SIDEBAR_TOGGLE);
 
   const initialState = {
     prefs: PrefState({ logLimit, sidebarToggle }),
     filters: FilterState({
-      error: Services.prefs.getBoolPref(PREFS.FILTER.ERROR),
-      warn: Services.prefs.getBoolPref(PREFS.FILTER.WARN),
-      info: Services.prefs.getBoolPref(PREFS.FILTER.INFO),
-      debug: Services.prefs.getBoolPref(PREFS.FILTER.DEBUG),
-      log: Services.prefs.getBoolPref(PREFS.FILTER.LOG),
-      css: Services.prefs.getBoolPref(PREFS.FILTER.CSS),
-      net: Services.prefs.getBoolPref(PREFS.FILTER.NET),
-      netxhr: Services.prefs.getBoolPref(PREFS.FILTER.NETXHR),
+      error: getBoolPref(PREFS.FILTER.ERROR),
+      warn: getBoolPref(PREFS.FILTER.WARN),
+      info: getBoolPref(PREFS.FILTER.INFO),
+      debug: getBoolPref(PREFS.FILTER.DEBUG),
+      log: getBoolPref(PREFS.FILTER.LOG),
+      css: getBoolPref(PREFS.FILTER.CSS),
+      net: getBoolPref(PREFS.FILTER.NET),
+      netxhr: getBoolPref(PREFS.FILTER.NETXHR),
     }),
     ui: UiState({
-      filterBarVisible: Services.prefs.getBoolPref(PREFS.UI.FILTER_BAR),
+      filterBarVisible: getBoolPref(PREFS.UI.FILTER_BAR),
       networkMessageActiveTabId: "headers",
-      persistLogs: Services.prefs.getBoolPref(PREFS.UI.PERSIST),
+      persistLogs: getBoolPref(PREFS.UI.PERSIST),
     })
   };
 
   return createStore(
     createRootReducer(),
     initialState,
     compose(
-      applyMiddleware(thunk),
+      applyMiddleware(thunk.bind(null, {prefsService})),
       enableActorReleaser(hud),
       enableBatching(),
       enableNetProvider(hud)
     )
   );
 }
 
+function thunk(options = {}, { dispatch, getState }) {
+  return next => action => {
+    return (typeof action === "function")
+      ? action(dispatch, getState, options)
+      : next(action);
+  };
+}
+
 function createRootReducer() {
   return function rootReducer(state, action) {
     // We want to compute the new state for all properties except "messages".
     const newState = [...Object.entries(reducers)].reduce((res, [key, reducer]) => {
       if (key !== "messages") {
         res[key] = reducer(state[key], action);
       }
       return res;
--- a/devtools/client/webconsole/new-console-output/utils/moz.build
+++ b/devtools/client/webconsole/new-console-output/utils/moz.build
@@ -3,9 +3,10 @@
 # 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/.
 
 DevToolsModules(
     'context-menu.js',
     'id-generator.js',
     'messages.js',
     'object-inspector.js',
+    'prefs.js',
 )
new file mode 100644
--- /dev/null
+++ b/devtools/client/webconsole/new-console-output/utils/prefs.js
@@ -0,0 +1,43 @@
+/* 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";
+const Services = require("Services");
+
+function getPreferenceName(hud, suffix) {
+  if (!suffix) {
+    console.error("Suffix shouldn't be falsy", {suffix});
+    return null;
+  }
+
+  if (!hud) {
+    console.error("hud shouldn't be falsy", {hud});
+    return null;
+  }
+
+  if (suffix.startsWith("devtools.")) {
+    // We don't have a suffix but a full pref name. Let's return it.
+    return suffix;
+  }
+
+  const component = hud.isBrowserConsole
+    ? "browserconsole"
+    : "webconsole";
+  return `devtools.${component}.${suffix}`;
+}
+
+function getPrefsService(hud) {
+  const getPrefName = pref => getPreferenceName(hud, pref);
+
+  return {
+    getBoolPref: (pref, deflt) => Services.prefs.getBoolPref(getPrefName(pref), deflt),
+    getIntPref: (pref, deflt) => Services.prefs.getIntPref(getPrefName(pref), deflt),
+    setBoolPref: (pref, value) => Services.prefs.setBoolPref(getPrefName(pref), value),
+    clearUserPref: pref => Services.prefs.clearUserPref(getPrefName(pref)),
+  };
+}
+
+module.exports = {
+  getPrefsService,
+};