From bb1b4f1a882179359bf027bdf6acb8e9c40e5ab7 Mon Sep 17 00:00:00 2001
From: kenneth_suter <kenneth_suter@localhost>
Date: Thu, 10 May 2007 14:16:11 +0000
Subject: [PATCH] This commit addresses several issues that Brian brought up regarding the upgrader.

---
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/Upgrader.java                 |  243 +++++++++++++++++-------
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/installer/Installer.java               |   36 +++
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/BuildInformation.java                  |   14 +
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/ButtonsPanel.java                   |   13 
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/uninstaller/Uninstaller.java           |   16 +
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/BuildExtractor.java           |   21 +
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/UserData.java                          |    3 
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/util/HtmlProgressMessageFormatter.java |   33 ++
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/ChooseVersionPanel.java    |   33 ++
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/UpgraderReviewPanel.java   |   65 +++++-
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/QuickSetup.java                     |   12 +
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/resources/Resources.properties         |   64 ++++--
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/Application.java                       |    5 
 opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/GuiApplication.java                 |   26 ++
 14 files changed, 432 insertions(+), 152 deletions(-)

diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/Application.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/Application.java
index 520361f..4a60098 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/Application.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/Application.java
@@ -523,10 +523,7 @@
    * @return <CODE>true</CODE> if the install is finished or <CODE>false
    * </CODE> if not.
    */
-  public boolean isFinished()
-  {
-    return getCurrentProgressStep().isLast();
-  }
+  abstract public boolean isFinished();
 
   /**
    * This class is used to notify the ProgressUpdateListeners of events
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/BuildInformation.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/BuildInformation.java
index 8bd0a57..2f6bb10 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/BuildInformation.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/BuildInformation.java
@@ -28,6 +28,7 @@
 package org.opends.quicksetup;
 
 import org.opends.quicksetup.util.Utils;
+import org.opends.quicksetup.i18n.ResourceProvider;
 
 import java.util.HashMap;
 import java.util.List;
@@ -163,7 +164,18 @@
    * {@inheritDoc}
    */
   public String toString() {
-    return getName() + " rev=" + getRevisionNumber();
+    StringBuilder sb = new StringBuilder();
+    sb.append(getName());
+    String id = getBuildId();
+    if (id != null) {
+      sb.append(" (")
+              .append(ResourceProvider.getInstance().
+                      getMsg("general-build-id"))
+              .append(": ")
+              .append(id)
+              .append(")");
+    }
+    return sb.toString();
   }
 
   /**
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/UserData.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/UserData.java
index e885b16..1c7da78 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/UserData.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/UserData.java
@@ -40,7 +40,7 @@
  * This class is used to provide a data model for the different parameters
  * that the user can provide in the installation wizard.
  *
- * @see DataOptions.
+ * @see org.opends.quicksetup.DataOptions
  *
  */
 public class UserData
@@ -82,7 +82,6 @@
         NewSuffixOptions.Type.CREATE_BASE_ENTRY, "dc=example,dc=com");
     setNewSuffixOptions(defaultNewSuffixOptions);
 
-    setServerLocation(Utils.getDefaultServerLocation());
     // See what we can propose as port
     int defaultPort = getDefaultPort();
     if (defaultPort != -1)
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/installer/Installer.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/installer/Installer.java
index 24b7e7f..8d16787 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/installer/Installer.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/installer/Installer.java
@@ -151,6 +151,15 @@
   /**
    * {@inheritDoc}
    */
+  public UserData createUserData() {
+    UserData ud = new UserData();
+    ud.setServerLocation(Utils.getDefaultServerLocation());
+    return ud;
+  }
+
+  /**
+   * {@inheritDoc}
+   */
   public void forceToDisplay() {
     forceToDisplaySetup = true;
   }
@@ -300,6 +309,15 @@
   /**
    * {@inheritDoc}
    */
+  public boolean isFinished()
+  {
+    return getCurrentProgressStep() == InstallProgressStep.FINISHED_SUCCESSFULLY
+        || getCurrentProgressStep() == InstallProgressStep.FINISHED_WITH_ERROR;
+  }
+
+  /**
+   * {@inheritDoc}
+   */
   public void cancelClicked(WizardStep cStep, QuickSetup qs) {
     // do nothing;
   }
@@ -408,14 +426,21 @@
   /**
    * {@inheritDoc}
    */
-  public String getCloseButtonToolTip() {
+  public String getCloseButtonToolTipKey() {
     return "close-button-install-tooltip";
   }
 
   /**
    * {@inheritDoc}
    */
-  public String getFinishButtonToolTip() {
+  public String getQuitButtonToolTipKey() {
+    return "quit-button-install-tooltip";
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public String getFinishButtonToolTipKey() {
     return "finish-button-install-tooltip";
   }
 
@@ -1938,7 +1963,7 @@
    * Validate the data provided by the user in the create global administrator
    * panel and update the UserInstallData object according to that content.
    *
-   * @throws an
+   * @throws
    *           UserInstallDataException if the data provided by the user is not
    *           valid.
    *
@@ -2010,7 +2035,7 @@
    * Validate the data provided by the user in the replicate suffixes options
    * panel and update the UserInstallData object according to that content.
    *
-   * @throws an
+   * @throws
    *           UserInstallDataException if the data provided by the user is not
    *           valid.
    *
@@ -2072,8 +2097,7 @@
    * Validate the data provided by the user in the new suffix data options panel
    * and update the UserInstallData object according to that content.
    *
-   * @throws an
-   *           UserInstallDataException if the data provided by the user is not
+   * @throws UserInstallDataException if the data provided by the user is not
    *           valid.
    *
    */
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/resources/Resources.properties b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/resources/Resources.properties
index 1e3fa06..387a351 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/resources/Resources.properties
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/resources/Resources.properties
@@ -186,7 +186,7 @@
 #
 frame-install-title=OpenDS QuickSetup
 frame-uninstall-title=OpenDS Uninstall
-frame-upgrade-title=OpenDS Upgrade
+frame-upgrade-title=OpenDS QuickUpgrade
 
 #
 # Wizard buttons (labels and tooltips)
@@ -200,18 +200,20 @@
 finish-button-uninstall-label=Uninstall
 finish-button-install-tooltip=Finish Installation and Setup
 finish-button-uninstall-tooltip=Finish Uninstall
-finish-button-tooltip=Finish QuickSetup
+finish-button-upgrade-tooltip=Finish Upgrade
+finish-button-tooltip=Finish Setup
 close-button-label=Close
-close-button-tooltip=Close QuickSetup Window
-close-button-install-tooltip=Close QuickSetup Window
+close-button-tooltip=Close Setup Window
+close-button-install-tooltip=Close Setup Window
 close-button-uninstall-tooltip=Close Uninstall Window
 quit-button-label=Quit
-quit-button-install-tooltip=Quit QuickSetup Tool
+quit-button-install-tooltip=Quit Setup
+quit-button-upgrade-tooltip=Quit Upgrade
 cancel-button-label=Cancel
 cancel-button-uninstall-tooltip=Cancel Uninstall
 shutdown-button-label=Shutdown
 continue-button-label=Continue
-continue-button-install-tooltip=Continue with the QuickSetup Tool
+continue-button-install-tooltip=Continue with Setup
 ok-button-label=OK
 
 #
@@ -226,6 +228,13 @@
 confirm-close-uninstall-title=Confirmation Required
 confirm-close-uninstall-msg=OpenDS Uninstall has not yet completed.\nAre you \
 sure you want to close the Uninstall Window?
+confirm-close-upgrade-title=Confirmation Required
+confirm-close-upgrade-msg=OpenDS QuickUpgrade has not yet completed.\nIf you \
+  click 'Yes' any changes that have been\nmade to the server being upgraded \
+  will\nbe backed out.\n\nAre you sure you want to close the QuickUpgrade Window?\n
+confirm-quit-upgrade-title=Confirmation Required
+confirm-quit-upgrade-msg=Are you sure you want to quit OpenDS \
+QuickUpgrade?\nIf you click 'Yes' nothing will be upgraded on your system.
 confirm-uninstall-server-not-running-msg=Confirm Uninstall\n\
 All selected files will be permanently deleted, are you sure you\n\
 want to continue?
@@ -288,7 +297,8 @@
 # Data validation errors
 #
 # Server Settings
-empty-server-location=You must provide the installation path.
+empty-server-location=Invalid Directory Selected\nYou must provide a valid \
+  OpenDS root installation directory.
 parent-directory-could-not-be-found=Could not find a parent directory for {0}.
 parent-directory-does-not-exist-confirmation=The parent directory of {0} does \
 not exist.\nWould you like to create this directory?
@@ -801,14 +811,22 @@
 summary-upgrade-verifying=Verifying Upgrade...
 summary-upgrade-history=Recording Upgrade History...
 summary-upgrade-cleanup=Cleaning Up...
-summary-upgrade-abort=Aborting Upgrade...
+summary-upgrade-abort=Canceling Upgrade...
 summary-upgrade-finished-successfully=<b>OpenDS QuickSetup Completed \
   Successfully.</b><br>The OpenDS installation at {0} has now been upgraded \
   to version {1}.
 summary-upgrade-finished-successfully-cli=OpenDS QuickSetup Completed \
   Successfully.  The OpenDS installation at {0} has now been upgraded \
   to version {1}.
-summary-upgrade-finished-with-errors=Upgrade Operation Failed
+summary-upgrade-finished-with-errors=<b>OpenDS QuickUpgrade Failed</b><br>\
+  The upgrade operation could not complete successfully due to errors and \
+  the installation has been restored to the state it was in before the upgrade \
+  operation.  See the 'Details' text for more information on why the upgrade \
+  operation failed.
+summary-upgrade-finished-with-errors-cli=OpenDS QuickUpgrade Failed. \
+  The upgrade operation could not complete successfully due to errors and \
+  the installation has been restored to the state it was in before the upgrade \
+  operation.  See the logs for details on why the upgrade operation failed.
 
 #
 # Progress messages
@@ -917,8 +935,8 @@
 upgrade-hypothetical-reversion-failure=Reversion from version {0} to version \
   {1} is not supported.  To revert versions you must uninstall the current \
   server, install the new server, and manually migrate your data.
-upgrade-hypothetical-versions-the-same=Both \
-  new current and proposed version numbers are the same: {0}
+upgrade-hypothetical-versions-the-same=Both the 'upgrade to' and 'upgrade from' \
+  numbers are the same: {0}
 upgrade-mod-no-schema=Processed server modifications \
   (schema checking disabled): {0}
 upgrade-mod=Processed server modifications: {0}
@@ -936,28 +954,29 @@
 # have to modify it or not: if the server uses the locale of the browser to display
 # a language there is no translation to be done but if we have specific URL for
 # each language the URL must be localized.
-upgrade-welcome-panel-offline-instructions=The OpenDS Upgrade tool will upgrade \
+upgrade-welcome-panel-offline-instructions=The OpenDS QuickUpgrade tool will upgrade \
   an existing build in place.<br><br>You will be prompted to choose among a list \
-  of available builds to which you can upgrade or you can specify an install\
-  package (.zip) file that you have already downloaded.  You can also use this tool to set up a build you have \
-  downloaded manually.<br><br> \
+  of available builds to which you can upgrade or you can specify an install \
+  package (.zip) file that you have already downloaded.  You can also use this tool to upgrade to a build \
+  whose install package you have already downloaded manually.<br><br> \
   Additional information on this tool is available on the <a href="https://www.opends.org/wiki/"> \
   OpenDS documentation wiki</a>.<br><br>\
-  <i>Note:</i> the upgrade tool will be stop and start the OpenDS server
-upgrade-welcome-panel-webstart-instructions=The OpenDS Upgrade tool will upgrade \
+  <b><i>Note:</i></b> the upgrade tool will need to stop and start the OpenDS server
+upgrade-welcome-panel-webstart-instructions=The OpenDS QuickUpgrade tool will upgrade \
   an existing build in place.<br><br>You will be prompted to choose among a list \
   of available builds to which you can upgrade or you can specify an install\
-  package (.zip) file that you have already downloaded.  You can also use this tool to set up a build you have \
-  downloaded manually.<br><br> \
+  package (.zip) file that you have already downloaded.  You can also use this tool to upgrade to a build \
+  whose install package you have already downloaded manually.<br><br> \
   Additional information on this tool is available on the <a href="https://www.opends.org/wiki/"> \
-  OpendS documentation wiki</a>.<br><br>\
-  <i>Note:</i> the upgrade tool will be stop and start the OpenDS server
+  OpenDS documentation wiki</a>.<br><br>\
+  <b><i>Note:</i></b> the upgrade tool will need to stop and start the OpenDS server
 upgrade-location-label=Server to Upgrade:
 upgrade-location-tooltip=File system location of the build that will be upgraded
 upgrade-build-id-label=Build Version:
 upgrade-build-id-tooltip=The ID of the build version installed in the above location
 upgrade-build-id-unknown=Unknown
-error-invalid-server-location=Invalid server location: {0}
+error-invalid-server-location=Invalid Directory Selected\nThe selected directory \
+  {0} is not a valid OpenDS root installation directory.
 
 #
 # Upgrader Choose Version Panel
@@ -1003,3 +1022,4 @@
 
 general-loading=Loading...
 general-see-for-details=See {0} for a detailed log of this operation.
+general-build-id=Build ID
\ No newline at end of file
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/ButtonsPanel.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/ButtonsPanel.java
index 3d44cc9..3c213bb 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/ButtonsPanel.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/ButtonsPanel.java
@@ -47,7 +47,7 @@
  * The layout is updated calling setCurrentStep method.
  *
  */
-class ButtonsPanel extends QuickSetupPanel
+public class ButtonsPanel extends QuickSetupPanel
 {
   private static final long serialVersionUID = -8460400337486357976L;
 
@@ -177,17 +177,18 @@
 
     String tooltip;
 
-    tooltip = "quit-button-install-tooltip";
+    GuiApplication application = getApplication();
+    tooltip = application.getQuitButtonToolTipKey();
     quitButton =
         createButton("quit-button-label", tooltip, ButtonName.QUIT);
 
-    GuiApplication application = getApplication();
 
-    tooltip = application.getCloseButtonToolTip();
+
+    tooltip = application.getCloseButtonToolTipKey();
     closeButton = createButton("close-button-label", tooltip, ButtonName.CLOSE);
 
-    String label = application.getFinishButtonLabel();
-    tooltip = application.getFinishButtonToolTip();
+    String label = application.getFinishButtonLabelKey();
+    tooltip = application.getFinishButtonToolTipKey();
     finishButton = createButton(label, tooltip, ButtonName.FINISH);
 
     cancelButton =
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/GuiApplication.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/GuiApplication.java
index 1411d3d..de7893a 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/GuiApplication.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/GuiApplication.java
@@ -323,21 +323,27 @@
    * @param cStep WizardStep at which the user clicked the close button
    * @param qs QuickSetup controller
    */
-  public abstract void closeClicked(WizardStep cStep, QuickSetup qs);
+  public void closeClicked(WizardStep cStep, QuickSetup qs) {
+    qs.quit();
+  }
 
   /**
    * Called when the user has clicked the 'cancel' button.
    * @param cStep WizardStep at which the user clicked the cancel button
    * @param qs QuickSetup controller
    */
-  public abstract void cancelClicked(WizardStep cStep, QuickSetup qs);
+  public void cancelClicked(WizardStep cStep, QuickSetup qs) {
+    qs.quit();
+  }
 
   /**
    * Called when the user has clicked the 'quit' button.
    * @param step WizardStep at which the user clicked the quit button
    * @param qs QuickSetup controller
    */
-  abstract public void quitClicked(WizardStep step, QuickSetup qs);
+  public void quitClicked(WizardStep step, QuickSetup qs) {
+    qs.quit();
+  }
 
   /**
    * Called whenever this application should update its user data from
@@ -354,15 +360,23 @@
    * Gets the key for the close button's tool tip text.
    * @return String key of the text in the resource bundle
    */
-  public String getCloseButtonToolTip() {
+  public String getCloseButtonToolTipKey() {
     return "close-button-tooltip";
   }
 
   /**
+   * Gets the key for the quit button's tool tip text.
+   * @return String key of the text in the resource bundle
+   */
+  public String getQuitButtonToolTipKey() {
+    return "quit-button-install-tooltip";
+  }
+
+  /**
    * Gets the key for the finish button's tool tip text.
    * @return String key of the text in the resource bundle
    */
-  public String getFinishButtonToolTip() {
+  public String getFinishButtonToolTipKey() {
     return "finish-button-tooltip";
   }
 
@@ -370,7 +384,7 @@
    * Gets the key for the finish button's label.
    * @return String key of the text in the resource bundle
    */
-  public String getFinishButtonLabel() {
+  public String getFinishButtonLabelKey() {
     return "finish-button-label";
   }
 
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/QuickSetup.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/QuickSetup.java
index 4da9398..fd57361 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/QuickSetup.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/ui/QuickSetup.java
@@ -41,6 +41,7 @@
 import javax.swing.*;
 import java.util.logging.Logger;
 import java.util.logging.Level;
+import java.util.logging.Handler;
 import java.util.Map;
 
 /**
@@ -424,9 +425,20 @@
    */
   public void quit()
   {
+    LOG.log(Level.INFO, "quitting application");
+    flushLogs();
     System.exit(0);
   }
 
+  private void flushLogs() {
+    Handler[] handlers = LOG.getHandlers();
+    if (handlers != null) {
+      for (Handler h : handlers) {
+        h.flush();
+      }
+    }
+  }
+
   /**
    * Launch the QuickSetup application Open DS.
    */
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/uninstaller/Uninstaller.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/uninstaller/Uninstaller.java
index f22b29f..0cebc3f 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/uninstaller/Uninstaller.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/uninstaller/Uninstaller.java
@@ -253,21 +253,21 @@
   /**
    * {@inheritDoc}
    */
-  public String getCloseButtonToolTip() {
+  public String getCloseButtonToolTipKey() {
     return "close-button-uninstall-tooltip";
   }
 
   /**
    * {@inheritDoc}
    */
-  public String getFinishButtonToolTip() {
+  public String getFinishButtonToolTipKey() {
     return "finish-button-uninstall-tooltip";
   }
 
   /**
    * {@inheritDoc}
    */
-  public String getFinishButtonLabel() {
+  public String getFinishButtonLabelKey() {
     return "finish-button-uninstall-label";
   }
 
@@ -621,6 +621,16 @@
   /**
    * {@inheritDoc}
    */
+  public boolean isFinished() {
+    return getCurrentProgressStep() ==
+            UninstallProgressStep.FINISHED_SUCCESSFULLY
+    || getCurrentProgressStep() ==
+            UninstallProgressStep.FINISHED_WITH_ERROR;
+  }
+
+  /**
+   * {@inheritDoc}
+   */
   public void windowClosing(QuickSetupDialog dlg, WindowEvent evt) {
     if (dlg.getDisplayedStep() == Step.PROGRESS) {
       // Simulate a close button event
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/BuildExtractor.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/BuildExtractor.java
index 78e3382..b56f22e 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/BuildExtractor.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/BuildExtractor.java
@@ -78,6 +78,8 @@
 
   private String[] args = null;
 
+  private boolean finished = false;
+
   private BuildExtractor(String[] args) {
     this.args = args;
     setProgressMessageFormatter(new PlainTextProgressMessageFormatter());
@@ -140,10 +142,14 @@
 
   private void expandZipFile(File buildFile)
           throws ApplicationException, IOException {
-    LOG.log(Level.INFO, "expanding zip file " + buildFile.getPath());
-    ZipExtractor extractor = new ZipExtractor(buildFile);
-    extractor.extract(getStageDirectory());
-    LOG.log(Level.INFO, "extraction finished");
+    try {
+      LOG.log(Level.INFO, "expanding zip file " + buildFile.getPath());
+      ZipExtractor extractor = new ZipExtractor(buildFile);
+      extractor.extract(getStageDirectory());
+      LOG.log(Level.INFO, "extraction finished");
+    } finally {
+      finished = true;
+    }
   }
 
   private File getStageDirectory() throws ApplicationException {
@@ -191,4 +197,11 @@
   public String getSummary(ProgressStep step) {
     return null;
   }
+
+  /**
+   * {@inheritDoc}
+   */
+  public boolean isFinished() {
+    return finished;
+  }
 }
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/Upgrader.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/Upgrader.java
index a8b5b70..8048941 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/Upgrader.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/Upgrader.java
@@ -28,6 +28,7 @@
 package org.opends.quicksetup.upgrader;
 
 import org.opends.quicksetup.*;
+import static org.opends.quicksetup.Step.PROGRESS;
 import org.opends.quicksetup.upgrader.ui.WelcomePanel;
 import org.opends.quicksetup.upgrader.ui.ChooseVersionPanel;
 import org.opends.quicksetup.upgrader.ui.UpgraderReviewPanel;
@@ -51,6 +52,8 @@
 
 import static org.opends.quicksetup.Installation.*;
 
+import javax.swing.*;
+
 /**
  * QuickSetup application of ugrading the bits of an installation of
  * OpenDS.
@@ -239,6 +242,9 @@
 
   private RemoteBuildManager remoteBuildManager = null;
 
+  /** Set to true if the user decides to close the window while running. */
+  private boolean abort = false;
+
   /**
    * Creates a default instance.
    */
@@ -362,8 +368,7 @@
    * {@inheritDoc}
    */
   public Integer getRatio(ProgressStep step) {
-    return ((UpgradeProgressStep) step).ordinal() /
-            EnumSet.allOf(UpgradeWizardStep.class).size();
+    return ((UpgradeProgressStep) step).getProgress();
   }
 
   /**
@@ -373,7 +378,10 @@
     String txt = null;
     if (step == UpgradeProgressStep.FINISHED) {
       txt = getFinalSuccessMessage();
-    } else {
+    } else if (step == UpgradeProgressStep.FINISHED_WITH_ERRORS) {
+      txt = getFinalErrorMessage();
+    }
+    else {
       txt = getMsg(((UpgradeProgressStep) step).getSummaryMesssageKey());
     }
     return txt;
@@ -451,7 +459,7 @@
   /**
    * {@inheritDoc}
    */
-  public boolean canCancel(WizardStep step) {
+  public boolean canQuit(WizardStep step) {
     return UpgradeWizardStep.WELCOME == step ||
             UpgradeWizardStep.CHOOSE_VERSION == step ||
             UpgradeWizardStep.REVIEW == step;
@@ -460,7 +468,79 @@
   /**
    * {@inheritDoc}
    */
-  public void quitClicked(WizardStep step, QuickSetup qs) {
+  public boolean canClose(WizardStep step) {
+    return step == UpgradeWizardStep.PROGRESS;
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public String getFinishButtonToolTipKey() {
+    return "finish-button-upgrade-tooltip";
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public String getQuitButtonToolTipKey() {
+    return "quit-button-upgrade-tooltip";
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public void closeClicked(WizardStep cStep, final QuickSetup qs) {
+    if (cStep == UpgradeWizardStep.PROGRESS) {
+      if (isFinished()) {
+        qs.quit();
+      } else if (qs.displayConfirmation(getMsg("confirm-close-upgrade-msg"),
+              getMsg("confirm-close-upgrade-title"))) {
+        abort = true;
+        JButton btnClose = qs.getDialog().getButtonsPanel().
+                getButton(ButtonName.CLOSE);
+        btnClose.setEnabled(false);
+        new Thread(new Runnable() {
+          public void run() {
+            while (!isFinished()) {
+              try {
+                Thread.sleep(100);
+              } catch (InterruptedException e) {
+                // do nothing
+              }
+            }
+            qs.quit();
+          }
+        }).start();
+      }
+    } else {
+      throw new IllegalStateException(
+              "Close only can be clicked on PROGRESS step");
+    }
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public boolean isFinished() {
+    return getCurrentProgressStep() ==
+            UpgradeProgressStep.FINISHED
+    || getCurrentProgressStep() ==
+            UpgradeProgressStep.FINISHED_WITH_ERRORS;
+  }
+
+  /**
+   * {@inheritDoc}
+   */
+  public void quitClicked(WizardStep cStep, final QuickSetup qs) {
+    if (cStep == UpgradeWizardStep.PROGRESS) {
+      throw new IllegalStateException(
+              "Cannot click on quit from progress step");
+    } else if (isFinished()) {
+      qs.quit();
+    } else if (qs.displayConfirmation(getMsg("confirm-quit-upgrade-msg"),
+            getMsg("confirm-quit-upgrade-title"))) {
+      qs.quit();
+    }
   }
 
   /**
@@ -507,8 +587,10 @@
             uud.setServerLocation(serverLocationString);
 
           } catch (IllegalArgumentException iae) {
+            LOG.log(Level.INFO,
+                    "illegal OpenDS installation directory selected", iae);
             errorMsgs.add(getMsg("error-invalid-server-location",
-                    iae.getLocalizedMessage()));
+                    serverLocationString));
             qs.displayFieldInvalid(FieldName.SERVER_LOCATION, true);
           }
         }
@@ -568,22 +650,6 @@
   /**
    * {@inheritDoc}
    */
-  public void closeClicked(WizardStep cStep, QuickSetup qs) {
-    // TODO: prompt
-    qs.quit();
-  }
-
-  /**
-   * {@inheritDoc}
-   */
-  public void cancelClicked(WizardStep cStep, QuickSetup qs) {
-    // TODO: confirm cancel
-    System.exit(1);
-  }
-
-  /**
-   * {@inheritDoc}
-   */
   public boolean canFinish(WizardStep step) {
     boolean cf = UpgradeWizardStep.REVIEW.equals(step);
     return cf;
@@ -599,13 +665,6 @@
   /**
    * {@inheritDoc}
    */
-  public boolean canClose(WizardStep step) {
-    return step.equals(UpgradeWizardStep.PROGRESS);
-  }
-
-  /**
-   * {@inheritDoc}
-   */
   public void run() {
     // Reset exception just in case this application is rerun
     // for some reason
@@ -623,6 +682,8 @@
         }
       }
 
+      checkAbort();
+
       File buildZip;
       Build buildToDownload =
               getUpgradeUserData().getInstallPackageToDownload();
@@ -664,6 +725,8 @@
         LOG.log(Level.INFO, "will use local build " + buildZip);
       }
 
+      checkAbort();
+
       if (buildZip != null) {
         LOG.log(Level.INFO, "existing local build file " + buildZip.getName());
         try {
@@ -680,6 +743,8 @@
         }
       }
 
+      checkAbort();
+
       try {
         LOG.log(Level.INFO, "initializing upgrade");
         setCurrentProgressStep(UpgradeProgressStep.INITIALIZING);
@@ -692,6 +757,8 @@
         throw e;
       }
 
+      checkAbort();
+
       try {
         LOG.log(Level.INFO, "checking server health");
         setCurrentProgressStep(UpgradeProgressStep.CHECK_SERVER_HEALTH);
@@ -704,6 +771,8 @@
         throw e;
       }
 
+      checkAbort();
+
       boolean schemaCustomizationPresent = false;
       try {
         LOG.log(Level.INFO, "checking for schema customizations");
@@ -718,6 +787,8 @@
         throw e;
       }
 
+      checkAbort();
+
       boolean configCustimizationPresent = false;
       try {
         LOG.log(Level.INFO, "checking for config customizations");
@@ -733,6 +804,8 @@
         throw e;
       }
 
+      checkAbort();
+
       try {
         LOG.log(Level.INFO, "backing up databases");
         setCurrentProgressStep(UpgradeProgressStep.BACKING_UP_DATABASES);
@@ -745,6 +818,8 @@
         throw e;
       }
 
+      checkAbort();
+
       try {
         LOG.log(Level.INFO, "backing up filesystem");
         setCurrentProgressStep(UpgradeProgressStep.BACKING_UP_FILESYSTEM);
@@ -757,6 +832,8 @@
         throw e;
       }
 
+      checkAbort();
+
       try {
         LOG.log(Level.INFO, "upgrading components");
         setCurrentProgressStep(
@@ -771,6 +848,8 @@
         throw e;
       }
 
+      checkAbort();
+
       //********************************************
       //*  The two steps following this step require
       //*  the server to be started 'in process'.
@@ -791,6 +870,8 @@
           throw e;
         }
 
+        checkAbort();
+
         if (schemaCustomizationPresent) {
           try {
             LOG.log(Level.INFO, "applying schema customizatoin");
@@ -807,6 +888,8 @@
           }
         }
 
+        checkAbort();
+
         if (configCustimizationPresent) {
           try {
             LOG.log(Level.INFO, "applying config customizatoin");
@@ -823,6 +906,8 @@
           }
         }
 
+        checkAbort();
+
         try {
           LOG.log(Level.INFO, "stopping server");
           getServerController().stopServerInProcess();
@@ -834,6 +919,8 @@
         }
       }
 
+      checkAbort();
+
       // This allows you to test whether or not he upgrader can successfully
       // abort an upgrade once changes have been made to the installation
       // path's filesystem.
@@ -905,57 +992,55 @@
         LOG.log(Level.INFO, "history recorded");
         notifyListeners("See '" +
                 Utils.getPath(getInstallation().getHistoryLogFile()) +
-                "' for upgrade history" + formatter.getLineBreak());
+                " for upgrade history" + formatter.getLineBreak());
       } catch (ApplicationException e) {
         System.err.print("Error cleaning up after upgrade: " +
                 e.getLocalizedMessage());
       }
-    }
 
-    // Decide final status based on presense of error
+      // Decide final status based on presense of error
 
-    // It would be nice if this were simpler.
-
-    if (runException == null) {
-      LOG.log(Level.INFO, "upgrade completed successfully");
-      if (!Utils.isCli()) {
-
-        notifyListenersOfLog();
-
-        // This seems to be the preferred way to print
-        // a message to the top of the progress panel without
-        // having it show up in the Details section which we
-        // don't want since it is in HTML
-        this.currentProgressStep = UpgradeProgressStep.FINISHED;
-        notifyListeners(null);
-
+      // WARNING: change this code at your own risk!  The ordering
+      // of these statements is important.  There are differences
+      // in how the CLI and GUI application's processes exit.
+      // Changing the ordering here may result in messages being
+      // skipped because the process has already exited by the time
+      // processing messages has finished.  Need to resolve these
+      // issues.
+      if (runException == null) {
+        LOG.log(Level.INFO, "upgrade completed successfully");
+        if (!Utils.isCli()) {
+          notifyListenersOfLog();
+          this.currentProgressStep = UpgradeProgressStep.FINISHED;
+          notifyListeners(null);
+        } else {
+          notifyListeners(null);
+          this.currentProgressStep = UpgradeProgressStep.FINISHED;
+        }
       } else {
-        notifyListeners(100, getFinalSuccessMessage());
-
-        // Don't do this until we've printed out last message
-        // as doing so tells the CLI that it is finished and
-        // System.exit gets called in QuickSetupCli
-        this.currentProgressStep = UpgradeProgressStep.FINISHED;
-      }
-
-    } else {
-      LOG.log(Level.INFO, "upgrade completed with errors", runException);
-      if (!Utils.isCli()) {
-        notifyListeners(100,
-                getMsg(UpgradeProgressStep.FINISHED_WITH_ERRORS.
-                        getSummaryMesssageKey()),
-                formatter.getFormattedError(runException, true));
-        notifyListenersOfLog();
-        notifyListeners(null);
-        setCurrentProgressStep(UpgradeProgressStep.FINISHED_WITH_ERRORS);
-      } else {
-        runException.printStackTrace();
-        this.currentProgressStep = UpgradeProgressStep.FINISHED_WITH_ERRORS;
+        LOG.log(Level.INFO, "upgrade completed with errors", runException);
+        if (!Utils.isCli()) {
+          notifyListenersOfLog();
+          this.currentProgressStep = UpgradeProgressStep.FINISHED_WITH_ERRORS;
+          notifyListeners(formatter.getFormattedError(runException, true));
+        } else {
+          notifyListeners(formatter.getFormattedError(runException, true) +
+                          formatter.getLineBreak());
+          notifyListeners(formatter.getLineBreak());
+          setCurrentProgressStep(UpgradeProgressStep.FINISHED_WITH_ERRORS);
+          notifyListeners(formatter.getLineBreak());
+        }
       }
     }
 
   }
 
+  private void checkAbort() throws ApplicationException {
+    if (abort) throw new ApplicationException(
+            ApplicationException.Type.APPLICATION,
+            "upgrade canceled by user", null);
+  }
+
   /**
    * Stops and starts the server checking for serious errors.  Also
    * has the side effect of having the server write schema.current
@@ -973,7 +1058,7 @@
       if (errors != null) {
         throw new ApplicationException(
                 ApplicationException.Type.APPLICATION,
-                "The server currently starts with errors with must" +
+                "The server currently starts with errors which must" +
                         "be resolved before an upgrade can occur: " +
                         Utils.listToString(errors, " "),
                 null);
@@ -1513,7 +1598,7 @@
     this.currentProgressStep = step;
     int progress = step.getProgress();
     String msg = getSummary(step);
-    notifyListeners(progress, getFormattedProgress(msg), msg);
+    notifyListeners(progress, msg, getFormattedProgress(msg));
   }
 
   private UpgraderCliHelper getCliHelper() {
@@ -1528,7 +1613,12 @@
     String installPath = Utils.getPath(getInstallation().getRootDirectory());
     String newVersion = null;
     try {
-      newVersion = getInstallation().getBuildInformation().getBuildId();
+      BuildInformation bi = getInstallation().getBuildInformation();
+      if (bi != null) {
+        newVersion = bi.toString();
+      } else {
+        newVersion = getMsg("upgrade-build-id-unknown");
+      }
     } catch (ApplicationException e) {
       newVersion = getMsg("upgrade-build-id-unknown");
     }
@@ -1545,6 +1635,17 @@
     return txt;
   }
 
+  private String getFinalErrorMessage() {
+    String txt;
+    if (Utils.isCli()) {
+      txt = getMsg("summary-upgrade-finished-with-errors-cli");
+    } else {
+      txt = getFormattedError(
+              getMsg("summary-upgrade-finished-with-errors"));
+    }
+    return txt;
+  }
+
   private File getStageDirectory()
           throws ApplicationException, IOException {
     return getInstallation().getTemporaryUpgradeDirectory();
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/ChooseVersionPanel.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/ChooseVersionPanel.java
index 59fef13..b122c00 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/ChooseVersionPanel.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/ChooseVersionPanel.java
@@ -59,7 +59,9 @@
   private JRadioButton rbLocal = null;
   private ButtonGroup grpRemoteLocal = null;
   private JComboBox cboBuild = null;
+  private JLabel lblFile = null;
   private JTextField tfFile = null;
+  private JButton butBrowse = null;
   private boolean loadBuildListAttempted = false;
   private RemoteBuildListComboBoxModelCreator bld = null;
 
@@ -101,7 +103,7 @@
         public void actionPerformed(ActionEvent evt) {
           rbLocal.setSelected(true);
           rbRemote.setEnabled(false);
-          cboBuild.setEnabled(false);
+          setComponentEnablement();
           cboBuild.setRenderer(new BuildListLoadingComboBoxRenderer());
           try {
             loadBuildList();
@@ -164,7 +166,8 @@
     tfFile = new JTextField();
     tfFile.setColumns(20);
 
-    JButton butBrowse = UIFactory.makeJButton(getMsg("browse-button-label"),
+    butBrowse =
+            UIFactory.makeJButton(getMsg("browse-button-label"),
             getMsg("browse-button-tooltip"));
 
     BrowseActionListener l =
@@ -173,13 +176,24 @@
                     getMainWindow());
     butBrowse.addActionListener(l);
 
-    JPanel pnlBrowse = Utilities.createBrowseButtonPanel(
-            UIFactory.makeJLabel(null,
+    lblFile = UIFactory.makeJLabel(null,
                     getMsg("upgrade-choose-version-local-path"),
-                    UIFactory.TextStyle.SECONDARY_FIELD_VALID),
+                    UIFactory.TextStyle.SECONDARY_FIELD_VALID);
+
+    JPanel pnlBrowse = Utilities.createBrowseButtonPanel(
+            lblFile,
             tfFile,
             butBrowse);
 
+    ActionListener radioListener = new ActionListener() {
+      public void actionPerformed(ActionEvent e) {
+        setComponentEnablement();
+      }
+    };
+
+    rbRemote.addActionListener(radioListener);
+    rbLocal.addActionListener(radioListener);
+
     p.setLayout(new GridBagLayout());
     // p.setBorder(BorderFactory.createLineBorder(Color.RED));
     GridBagConstraints gbc = new GridBagConstraints();
@@ -416,6 +430,7 @@
               rbRemote.setSelected(false);
               // grpRemoteLocal.setSelected(rbRemote.getModel(), false);
               rbRemote.setEnabled(false);
+              setComponentEnablement();
             }
           });
         } else {
@@ -433,11 +448,11 @@
             cboBuild.setModel(cbmFinal);
             cboBuild.setRenderer(new DefaultListCellRenderer());
             // Disable the remote widgets
-            cboBuild.setEnabled(true);
             rbLocal.setSelected(false);
             rbRemote.setSelected(true);
             // grpRemoteLocal.setSelected(rbRemote.getModel(), false);
             rbRemote.setEnabled(true);
+            setComponentEnablement();
           }
         });
       }
@@ -452,4 +467,10 @@
     }
   }
 
+  private void setComponentEnablement() {
+    cboBuild.setEnabled(rbRemote.isSelected());
+    lblFile.setEnabled(rbLocal.isSelected());
+    tfFile.setEnabled(rbLocal.isSelected());
+    butBrowse.setEnabled((rbLocal.isSelected()));
+  }
 }
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/UpgraderReviewPanel.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/UpgraderReviewPanel.java
index c7edb7b..ca37042 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/UpgraderReviewPanel.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/upgrader/ui/UpgraderReviewPanel.java
@@ -35,9 +35,9 @@
 import org.opends.quicksetup.upgrader.Build;
 import org.opends.quicksetup.ApplicationException;
 import org.opends.quicksetup.UserData;
+import org.opends.quicksetup.BuildInformation;
 
 import javax.swing.*;
-import javax.swing.text.JTextComponent;
 import java.awt.*;
 import java.util.logging.Level;
 import java.util.logging.Logger;
@@ -53,9 +53,9 @@
 
   private static final long serialVersionUID = 5942916658585976799L;
 
-  JTextComponent tcServerLocation = null;
-  JTextComponent tcOldBuild = null;
-  JTextComponent tcNewBuild = null;
+  JLabel tcServerLocation = null;
+  JLabel tcOldBuild = null;
+  JLabel tcNewBuild = null;
   private JCheckBox checkBox;
 
   /**
@@ -134,6 +134,18 @@
       0
     );
 
+    // Here we use labels instead of calling UIFactory.makeJTextComponent.
+    // which supplies us with a JEditorPane for read-only values.  We don't
+    // know the values of these fields at this time.  If we use JEditorPanes
+    // here when the panel is made visible there is an effect where the text
+    // is seen racing left when first seen.
+    tcServerLocation = UIFactory.makeJLabel(serverDescriptor);
+    UIFactory.setTextStyle(tcServerLocation, UIFactory.TextStyle.READ_ONLY);
+    tcOldBuild = UIFactory.makeJLabel(oldVersionDescriptor);
+    UIFactory.setTextStyle(tcOldBuild, UIFactory.TextStyle.READ_ONLY);
+    tcNewBuild = UIFactory.makeJLabel(newVersionDescriptor);
+    UIFactory.setTextStyle(tcNewBuild, UIFactory.TextStyle.READ_ONLY);
+
     p.setLayout(new GridBagLayout());
     GridBagConstraints gbc = new GridBagConstraints();
 
@@ -149,8 +161,7 @@
     gbc.gridy = 0;
     gbc.weightx = 1.0;
     gbc.fill = GridBagConstraints.HORIZONTAL;
-    p.add(tcServerLocation = UIFactory.makeJTextComponent(serverDescriptor,
-            null), gbc);
+    p.add(tcServerLocation, gbc);
 
     gbc.gridx = 0;
     gbc.gridy = 1;
@@ -160,8 +171,7 @@
     gbc.gridx = 1;
     gbc.gridy = 1;
     gbc.fill = GridBagConstraints.HORIZONTAL;
-    p.add(tcOldBuild = UIFactory.makeJTextComponent(oldVersionDescriptor,
-            null), gbc);
+    p.add(tcOldBuild, gbc);
 
     gbc.gridx = 0;
     gbc.gridy = 2;
@@ -172,8 +182,7 @@
     gbc.gridy = 2;
     gbc.weighty = 1.0;
     gbc.fill = GridBagConstraints.HORIZONTAL;
-    p.add(tcNewBuild = UIFactory.makeJTextComponent(newVersionDescriptor,
-            null), gbc);
+    p.add(tcNewBuild, gbc);
 
     return p;
   }
@@ -183,12 +192,17 @@
   }
 
   private String getOldBuildString() {
-    String oldVersion;
+    String oldVersion = null;
     try {
-      oldVersion = getApplication().getInstallation().
-              getBuildInformation().getBuildId();
+      BuildInformation bi = getApplication().getInstallation().
+              getBuildInformation();
+      if (bi != null) {
+        oldVersion = bi.toString();
+      }
     } catch (ApplicationException e) {
       LOG.log(Level.INFO, "error", e);
+    }
+    if (oldVersion == null) {
       oldVersion = getMsg("upgrade-build-id-unknown");
     }
     return oldVersion;
@@ -210,7 +224,6 @@
       newVersion = getMsg("upgrade-build-id-unknown");
     }
     return newVersion;
-
   }
 
   /**
@@ -227,4 +240,28 @@
     }
     return checkBox;
   }
+
+//  public static void main(String[] args) {
+//    final UserData ud = new UpgradeUserData();
+//    ud.setServerLocation("XXX/XXXXX/XX/XXXXXXXXXXXX/XXXX");
+//    Upgrader app = new Upgrader();
+//    app.setUserData(ud);
+//    final UpgraderReviewPanel p = new UpgraderReviewPanel(app);
+//    p.initialize();
+//    JFrame frame = new JFrame();
+//    frame.getContentPane().add(p);
+//    frame.addComponentListener(new ComponentAdapter() {
+//      public void componentHidden(ComponentEvent componentEvent) {
+//        System.exit(0);
+//      }
+//    });
+//    frame.pack();
+//    frame.setVisible(true);
+//    new Thread(new Runnable() {
+//      public void run() {
+//        p.beginDisplay(ud);
+//      }
+//    }).start();
+//
+//  }
 }
diff --git a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/util/HtmlProgressMessageFormatter.java b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/util/HtmlProgressMessageFormatter.java
index e71a829..6d90d96 100644
--- a/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/util/HtmlProgressMessageFormatter.java
+++ b/opendj-sdk/opends/src/quicksetup/org/opends/quicksetup/util/HtmlProgressMessageFormatter.java
@@ -92,12 +92,18 @@
    */
   public String getFormattedError(String text, boolean applyMargin)
   {
-    String html =
-        UIFactory.getIconHtml(UIFactory.IconType.ERROR_LARGE)
-            + SPACE
-            + SPACE
-            + UIFactory.applyFontToHtml(getHtml(text),
-                UIFactory.PROGRESS_ERROR_FONT);
+    String html;
+    if (!containsHtml(text)) {
+      html = UIFactory.getIconHtml(UIFactory.IconType.ERROR_LARGE)
+          + SPACE
+          + SPACE
+          + UIFactory.applyFontToHtml(getHtml(text),
+              UIFactory.PROGRESS_ERROR_FONT);
+    } else {
+      html =
+          UIFactory.getIconHtml(UIFactory.IconType.ERROR_LARGE) + SPACE
+          + SPACE + UIFactory.applyFontToHtml(text, UIFactory.PROGRESS_FONT);
+    }
 
     String result = UIFactory.applyErrorBackgroundToHtml(html);
     if (applyMargin)
@@ -119,12 +125,19 @@
    */
   public String getFormattedWarning(String text, boolean applyMargin)
   {
-    String html =
+    String html;
+    if (!containsHtml(text)) {
+      html =
         UIFactory.getIconHtml(UIFactory.IconType.WARNING_LARGE)
             + SPACE
             + SPACE
             + UIFactory.applyFontToHtml(getHtml(text),
                 UIFactory.PROGRESS_WARNING_FONT);
+    } else {
+      html =
+          UIFactory.getIconHtml(UIFactory.IconType.WARNING_LARGE) + SPACE
+          + SPACE + UIFactory.applyFontToHtml(text, UIFactory.PROGRESS_FONT);
+    }
 
     String result = UIFactory.applyWarningBackgroundToHtml(html);
     if (applyMargin)
@@ -591,5 +604,11 @@
           closeDiv, inverse);
     }
   }
+
+  private boolean containsHtml(String text) {
+    return (text != null &&
+            text.indexOf('<') != -1 &&
+            text.indexOf('>') != -1);
+  }
 }
 

--
Gitblit v1.10.0