Make user preferences accessible by plugins

Add methods to the JavaScript API that allows plugins to get and
refresh the preferences of the currently signed in user.

Change-Id: Icabaf8188ccdd19b877856a23d292493cd50a215
Signed-off-by: Edwin Kempin <edwin.kempin@sap.com>
diff --git a/Documentation/js-api.txt b/Documentation/js-api.txt
index 43e4336..4e10b2b 100644
--- a/Documentation/js-api.txt
+++ b/Documentation/js-api.txt
@@ -65,6 +65,15 @@
 Returns the currently signed in user's AccountInfo data; empty account
 data if no user is currently signed in.
 
+[[Gerrit_getUserPreferences]]
+=== Gerrit.getUserPreferences()
+Returns the preferences of the currently signed in user; the default
+preferences if no user is currently signed in.
+
+[[Gerrit_refreshUserPreferences]]
+=== Gerrit.refreshUserPreferences()
+Refreshes the preferences of the current user.
+
 [[self_getPluginName]]
 === self.getPluginName()
 Returns the name this plugin was installed as by the server
diff --git a/gerrit-gwtui-common/src/main/java/com/google/gerrit/client/info/AccountPreferencesInfo.java b/gerrit-gwtui-common/src/main/java/com/google/gerrit/client/info/AccountPreferencesInfo.java
index a9fb96a..f3cdedf 100644
--- a/gerrit-gwtui-common/src/main/java/com/google/gerrit/client/info/AccountPreferencesInfo.java
+++ b/gerrit-gwtui-common/src/main/java/com/google/gerrit/client/info/AccountPreferencesInfo.java
@@ -30,9 +30,6 @@
   public static AccountPreferencesInfo create(AccountGeneralPreferences in,
       List<TopMenuItem> myMenus) {
     AccountPreferencesInfo p = createObject().cast();
-    if (in == null) {
-      in = AccountGeneralPreferences.createDefault();
-    }
     p.changesPerPage(in.getMaximumPageSize());
     p.showSiteHeader(in.isShowSiteHeader());
     p.useFlashClipboard(in.isUseFlashClipboard());
@@ -47,10 +44,16 @@
     p.muteCommonPathPrefixes(in.isMuteCommonPathPrefixes());
     p.reviewCategoryStrategy(in.getReviewCategoryStrategy());
     p.diffView(in.getDiffView());
-    p.setMyMenus(myMenus);
+    if (myMenus != null) {
+      p.setMyMenus(myMenus);
+    }
     return p;
   }
 
+  public static AccountPreferencesInfo createDefault() {
+    return create(AccountGeneralPreferences.createDefault(), null);
+  }
+
   public final short changesPerPage() {
     return get("changes_per_page", AccountGeneralPreferences.DEFAULT_PAGESIZE);
   }
diff --git a/gerrit-gwtui/src/main/java/com/google/gerrit/client/FormatUtil.java b/gerrit-gwtui/src/main/java/com/google/gerrit/client/FormatUtil.java
index d0294f2..fd1cbe1 100644
--- a/gerrit-gwtui/src/main/java/com/google/gerrit/client/FormatUtil.java
+++ b/gerrit-gwtui/src/main/java/com/google/gerrit/client/FormatUtil.java
@@ -15,8 +15,8 @@
 package com.google.gerrit.client;
 
 import com.google.gerrit.client.info.AccountInfo;
+import com.google.gerrit.client.info.AccountPreferencesInfo;
 import com.google.gerrit.reviewdb.client.Account;
-import com.google.gerrit.reviewdb.client.AccountGeneralPreferences;
 import com.google.gwt.i18n.client.DateTimeFormat;
 
 import java.util.Date;
@@ -31,19 +31,10 @@
   private static DateTimeFormat mDate;
   private static DateTimeFormat dtfmt;
 
-  public static void setPreferences(AccountGeneralPreferences pref) {
-    if (pref == null) {
-      if (Gerrit.isSignedIn()) {
-        pref = Gerrit.getUserAccount().getGeneralPreferences();
-      } else {
-        pref = new AccountGeneralPreferences();
-        pref.resetToDefaults();
-      }
-    }
-
-    String fmt_sTime = pref.getTimeFormat().getFormat();
-    String fmt_sDate = pref.getDateFormat().getShortFormat();
-    String fmt_mDate = pref.getDateFormat().getLongFormat();
+  public static void setPreferences(AccountPreferencesInfo prefs) {
+    String fmt_sTime = prefs.timeFormat().getFormat();
+    String fmt_sDate = prefs.dateFormat().getShortFormat();
+    String fmt_mDate = prefs.dateFormat().getLongFormat();
 
     sTime = DateTimeFormat.getFormat(fmt_sTime);
     sDate = DateTimeFormat.getFormat(fmt_sDate);
@@ -115,7 +106,7 @@
 
   private static void ensureInited() {
     if (dtfmt == null) {
-      setPreferences(null);
+      setPreferences(Gerrit.getUserPreferences());
     }
   }
 
diff --git a/gerrit-gwtui/src/main/java/com/google/gerrit/client/Gerrit.java b/gerrit-gwtui/src/main/java/com/google/gerrit/client/Gerrit.java
index f6daec5..3521c5c 100644
--- a/gerrit-gwtui/src/main/java/com/google/gerrit/client/Gerrit.java
+++ b/gerrit-gwtui/src/main/java/com/google/gerrit/client/Gerrit.java
@@ -49,7 +49,6 @@
 import com.google.gerrit.extensions.client.GerritTopMenu;
 import com.google.gerrit.reviewdb.client.Account;
 import com.google.gerrit.reviewdb.client.AccountDiffPreference;
-import com.google.gerrit.reviewdb.client.AccountGeneralPreferences;
 import com.google.gerrit.reviewdb.client.Project;
 import com.google.gwt.aria.client.Roles;
 import com.google.gwt.core.client.EntryPoint;
@@ -112,6 +111,7 @@
 
   private static String myHost;
   private static ServerInfo myServerInfo;
+  private static AccountPreferencesInfo myPrefs;
   private static boolean hasDocumentation;
   private static String docUrl;
   private static HostPageData.Theme myTheme;
@@ -316,6 +316,11 @@
     return xGerritAuth;
   }
 
+  /** @return the preferences of the currently signed in user, the default preferences if not signed in */
+  public static AccountPreferencesInfo getUserPreferences() {
+    return myPrefs;
+  }
+
   /** @return the currently signed in users's diff preferences; null if no diff preferences defined for the account */
   public static AccountDiffPreference getAccountDiffPreference() {
     return myAccountDiffPref;
@@ -388,6 +393,7 @@
   static void deleteSessionCookie() {
     myAccount = null;
     myAccountDiffPref = null;
+    myPrefs = AccountPreferencesInfo.createDefault();
     xGerritAuth = null;
     refreshMenuBar();
 
@@ -462,9 +468,20 @@
         }
         if (result.accountDiffPref != null) {
           myAccountDiffPref = result.accountDiffPref;
-          applyUserPreferences();
         }
-        onModuleLoad2(result);
+        if (isSignedIn()) {
+          AccountApi.self().view("preferences")
+              .get(new GerritCallback<AccountPreferencesInfo>() {
+            @Override
+            public void onSuccess(AccountPreferencesInfo prefs) {
+              myPrefs = prefs;
+              onModuleLoad2(result);
+            }
+          });
+        } else {
+          myPrefs = AccountPreferencesInfo.createDefault();
+          onModuleLoad2(result);
+        }
       }
     }));
   }
@@ -581,7 +598,7 @@
 
     applyUserPreferences();
     populateBottomMenu(bottomMenu, hpd);
-    refreshMenuBar(false);
+    refreshMenuBar();
 
     History.addValueChangeHandler(new ValueChangeHandler<String>() {
       @Override
@@ -595,13 +612,9 @@
     if (hpd.messages != null) {
       new MessageOfTheDayBar(hpd.messages).show();
     }
-    CallbackGroup cbg = new CallbackGroup();
-    if (isSignedIn()) {
-      AccountApi.self().view("preferences").get(cbg.add(createMyMenuBarCallback()));
-    }
     PluginLoader.load(hpd.plugins,
         hpd.pluginsLoadTimeout,
-        cbg.addFinal(new GerritCallback<VoidResult>() {
+        new GerritCallback<VoidResult>() {
           @Override
           public void onSuccess(VoidResult result) {
             String token = History.getToken();
@@ -612,7 +625,7 @@
             }
             display(token);
           }
-        }));
+        });
   }
 
   private void saveDefaultTheme() {
@@ -622,10 +635,6 @@
   }
 
   public static void refreshMenuBar() {
-    refreshMenuBar(true);
-  }
-
-  private static void refreshMenuBar(boolean populateMyMenu) {
     menuLeft.clear();
     menuRight.clear();
 
@@ -645,9 +654,22 @@
     if (signedIn) {
       LinkMenuBar myBar = new LinkMenuBar();
       menuBars.put(GerritTopMenu.MY.menuName, myBar);
-      if (populateMyMenu) {
-        AccountApi.self().view("preferences").get(createMyMenuBarCallback());
+
+      if (myPrefs.my() != null) {
+        myBar.clear();
+        String url = null;
+        List<TopMenuItem> myMenuItems = Natives.asList(myPrefs.my());
+        if (!myMenuItems.isEmpty()) {
+          if (myMenuItems.get(0).getUrl().startsWith("#")) {
+            url = myMenuItems.get(0).getUrl().substring(1);
+          }
+          for (TopMenuItem item : myMenuItems) {
+            addExtensionLink(myBar, item);
+          }
+        }
+        defaultScreenToken = url;
       }
+
       menuLeft.add(myBar, C.menuMine());
       menuLeft.selectTab(1);
     } else {
@@ -822,6 +844,37 @@
     });
   }
 
+  public static void refreshUserPreferences() {
+    if (isSignedIn()) {
+      AccountApi.self().view("preferences")
+          .get(new GerritCallback<AccountPreferencesInfo>() {
+            @Override
+            public void onSuccess(AccountPreferencesInfo prefs) {
+              setUserPreferences(prefs);
+            }
+          });
+    } else {
+      setUserPreferences(AccountPreferencesInfo.createDefault());
+    }
+  }
+
+  public static void setUserPreferences(AccountPreferencesInfo prefs) {
+    myPrefs = prefs;
+    applyUserPreferences();
+    refreshMenuBar();
+  }
+
+  private static void applyUserPreferences() {
+    CopyableLabel.setFlashEnabled(myPrefs.useFlashClipboard());
+    if (siteHeader != null) {
+      siteHeader.setVisible(myPrefs.showSiteHeader());
+    }
+    if (siteFooter != null) {
+      siteFooter.setVisible(myPrefs.showSiteHeader());
+    }
+    FormatUtil.setPreferences(myPrefs);
+  }
+
   private static void getDocIndex(final AsyncCallback<DocInfo> cb) {
     RequestBuilder req =
         new RequestBuilder(RequestBuilder.HEAD, GWT.getHostPageBaseURL()
@@ -853,41 +906,6 @@
     }
   }
 
-  private static AsyncCallback<AccountPreferencesInfo> createMyMenuBarCallback() {
-    return new GerritCallback<AccountPreferencesInfo>() {
-      @Override
-      public void onSuccess(AccountPreferencesInfo prefs) {
-        LinkMenuBar myBar = menuBars.get(GerritTopMenu.MY.menuName);
-        myBar.clear();
-        List<TopMenuItem> myMenuItems = Natives.asList(prefs.my());
-        String url = null;
-        if (!myMenuItems.isEmpty()) {
-          if (myMenuItems.get(0).getUrl().startsWith("#")) {
-            url = myMenuItems.get(0).getUrl().substring(1);
-          }
-          for (TopMenuItem item : myMenuItems) {
-            addExtensionLink(myBar, item);
-          }
-        }
-        defaultScreenToken = url;
-      }
-    };
-  }
-
-  public static void applyUserPreferences() {
-    if (myAccount != null) {
-      final AccountGeneralPreferences p = myAccount.getGeneralPreferences();
-      CopyableLabel.setFlashEnabled(p.isUseFlashClipboard());
-      if (siteHeader != null) {
-        siteHeader.setVisible(p.isShowSiteHeader());
-      }
-      if (siteFooter != null) {
-        siteFooter.setVisible(p.isShowSiteHeader());
-      }
-      FormatUtil.setPreferences(myAccount.getGeneralPreferences());
-    }
-  }
-
   private static void whoAmI(boolean canLogOut) {
     AccountInfo account = getUserAccountInfo();
     final UserPopupPanel userPopup =
diff --git a/gerrit-gwtui/src/main/java/com/google/gerrit/client/account/MyPreferencesScreen.java b/gerrit-gwtui/src/main/java/com/google/gerrit/client/account/MyPreferencesScreen.java
index c5eb27d..5c27eec 100644
--- a/gerrit-gwtui/src/main/java/com/google/gerrit/client/account/MyPreferencesScreen.java
+++ b/gerrit-gwtui/src/main/java/com/google/gerrit/client/account/MyPreferencesScreen.java
@@ -334,7 +334,7 @@
   }
 
   private void doSave() {
-    final AccountGeneralPreferences p = new AccountGeneralPreferences();
+    AccountGeneralPreferences p = new AccountGeneralPreferences();
     p.setShowSiteHeader(showSiteHeader.getValue());
     p.setUseFlashClipboard(useFlashClipboard.getValue());
     p.setCopySelfOnEmails(copySelfOnEmails.getValue());
@@ -369,11 +369,9 @@
             new GerritCallback<AccountPreferencesInfo>() {
           @Override
           public void onSuccess(AccountPreferencesInfo prefs) {
-            Gerrit.getUserAccount().setGeneralPreferences(p);
-            Gerrit.applyUserPreferences();
+            Gerrit.setUserPreferences(prefs);
             enable(true);
             display(prefs);
-            Gerrit.refreshMenuBar();
           }
 
           @Override
diff --git a/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/ApiGlue.java b/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/ApiGlue.java
index b30a1cb..a809a30 100644
--- a/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/ApiGlue.java
+++ b/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/ApiGlue.java
@@ -17,6 +17,7 @@
 import com.google.gerrit.client.ErrorDialog;
 import com.google.gerrit.client.Gerrit;
 import com.google.gerrit.client.info.AccountInfo;
+import com.google.gerrit.client.info.AccountPreferencesInfo;
 import com.google.gwt.core.client.JavaScriptObject;
 import com.google.gwt.core.client.JsArray;
 import com.google.gwt.user.client.History;
@@ -72,6 +73,8 @@
       isSignedIn: @com.google.gerrit.client.api.ApiGlue::isSignedIn(),
       showError: @com.google.gerrit.client.api.ApiGlue::showError(Ljava/lang/String;),
       getCurrentUser: @com.google.gerrit.client.api.ApiGlue::getCurrentUser(),
+      getUserPreferences: @com.google.gerrit.client.api.ApiGlue::getUserPreferences(),
+      refreshUserPreferences: @com.google.gerrit.client.api.ApiGlue::refreshUserPreferences(),
 
       on: function (e,f){(this.events[e] || (this.events[e]=[])).push(f)},
       onAction: function (t,n,c){this._onAction(this.getPluginName(),t,n,c)},
@@ -255,6 +258,14 @@
     return Gerrit.getUserAccountInfo();
   }
 
+  private static final AccountPreferencesInfo getUserPreferences() {
+    return Gerrit.getUserPreferences();
+  }
+
+  private static final void refreshUserPreferences() {
+    Gerrit.refreshUserPreferences();
+  }
+
   private static final void refreshMenuBar() {
     Gerrit.refreshMenuBar();
   }
diff --git a/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/Plugin.java b/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/Plugin.java
index c3b2338..6935d34 100644
--- a/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/Plugin.java
+++ b/gerrit-gwtui/src/main/java/com/google/gerrit/client/api/Plugin.java
@@ -51,6 +51,8 @@
     @com.google.gerrit.client.api.Plugin::TYPE.prototype = {
       getPluginName: function(){return this.name},
       getCurrentUser: @com.google.gerrit.client.api.ApiGlue::getCurrentUser(),
+      getUserPreferences: @com.google.gerrit.client.api.ApiGlue::getUserPreferences(),
+      refreshUserPreferences: @com.google.gerrit.client.api.ApiGlue::refreshUserPreferences(),
       go: @com.google.gerrit.client.api.ApiGlue::go(Ljava/lang/String;),
       refresh: @com.google.gerrit.client.api.ApiGlue::refresh(),
       refreshMenuBar: @com.google.gerrit.client.api.ApiGlue::refreshMenuBar(),
diff --git a/gerrit-plugin-gwtui/src/main/java/com/google/gerrit/plugin/client/Plugin.java b/gerrit-plugin-gwtui/src/main/java/com/google/gerrit/plugin/client/Plugin.java
index 23fa308..ed2f46b 100644
--- a/gerrit-plugin-gwtui/src/main/java/com/google/gerrit/plugin/client/Plugin.java
+++ b/gerrit-plugin-gwtui/src/main/java/com/google/gerrit/plugin/client/Plugin.java
@@ -16,6 +16,7 @@
 
 import com.google.gerrit.client.GerritUiExtensionPoint;
 import com.google.gerrit.client.info.AccountInfo;
+import com.google.gerrit.client.info.AccountPreferencesInfo;
 import com.google.gerrit.plugin.client.extension.Panel;
 import com.google.gerrit.plugin.client.screen.Screen;
 import com.google.gwt.core.client.GWT;
@@ -57,6 +58,14 @@
   public final native void refreshMenuBar()
   /*-{ return this.refreshMenuBar() }-*/;
 
+  /** @return the preferences of the currently signed in user, the default preferences if not signed in */
+  public final native AccountPreferencesInfo getUserPreferences()
+  /*-{ return this.getUserPreferences() }-*/;
+
+  /** Refresh the user preferences of the current user. */
+  public final native void refreshUserPreferences()
+  /*-{ return this.refreshUserPreferences() }-*/;
+
   /** @return the current user */
   public final native AccountInfo getCurrentUser()
   /*-{ return this.getCurrentUser() }-*/;