001/* 002 * The contents of this file are subject to the terms of the Common Development and 003 * Distribution License (the License). You may not use this file except in compliance with the 004 * License. 005 * 006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the 007 * specific language governing permission and limitations under the License. 008 * 009 * When distributing Covered Software, include this CDDL Header Notice in each file and include 010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL 011 * Header, with the fields enclosed by brackets [] replaced by your own identifying 012 * information: "Portions Copyright [year] [name of copyright owner]". 013 * 014 * Copyright 2010 Sun Microsystems, Inc. 015 * Portions Copyright 2013-2016 ForgeRock AS. 016 */ 017package org.opends.quicksetup.installer.ui; 018 019import static org.opends.messages.QuickSetupMessages.*; 020 021import java.awt.Component; 022import java.awt.GridBagConstraints; 023import java.awt.GridBagLayout; 024import java.awt.event.ActionEvent; 025import java.awt.event.ActionListener; 026import java.awt.event.FocusEvent; 027import java.awt.event.FocusListener; 028import java.io.File; 029import java.util.Set; 030 031import javax.swing.Box; 032import javax.swing.JButton; 033import javax.swing.JEditorPane; 034import javax.swing.JFrame; 035import javax.swing.JLabel; 036import javax.swing.JPanel; 037 038import org.opends.admin.ads.ReplicaDescriptor; 039import org.opends.admin.ads.SuffixDescriptor; 040import org.forgerock.i18n.LocalizableMessage; 041import org.opends.quicksetup.JavaArguments; 042import org.opends.quicksetup.UserData; 043import org.opends.quicksetup.installer.DataReplicationOptions; 044import org.opends.quicksetup.installer.NewSuffixOptions; 045import org.opends.quicksetup.installer.SuffixesToReplicateOptions; 046import org.opends.quicksetup.ui.FieldName; 047import org.opends.quicksetup.ui.GuiApplication; 048import org.opends.quicksetup.ui.QuickSetupStepPanel; 049import org.opends.quicksetup.ui.UIFactory; 050import org.opends.quicksetup.util.HtmlProgressMessageFormatter; 051 052/** The panel where the user specifies the runtime settings. */ 053public class RuntimeOptionsPanel extends QuickSetupStepPanel 054{ 055 private static final long serialVersionUID = -8303034619200476754L; 056 057 private JButton bServer; 058 private JButton bImport; 059 private JLabel lServer; 060 private JLabel lImport; 061 private JEditorPane warning; 062 private Component lastFocusComponent; 063 064 private JavaArguments serverJavaArgs; 065 private JavaArguments importJavaArgs; 066 067 private JavaArguments defaultServerJavaArgs; 068 private JavaArguments defaultImportJavaArgs; 069 070 /** 071 * The size of the LDIF file to be imported used as threshold to display 072 * a warning message, telling the user to update the import runtime settings. 073 */ 074 private static final long WARNING_THRESOLD_FOR_IMPORT = 200 * 1024 * 1024; 075 private static final int WARNING_THRESOLD_AUTOMATICALLY_GENERATED_IMPORT 076 = 100000; 077 private static final int WARNING_THRESOLD_REPLICATED_ENTRIES = 100000; 078 079 /** 080 * Constructor of the panel. 081 * @param application Application represented by this panel and used to 082 * initialize the fields of the panel. 083 */ 084 public RuntimeOptionsPanel(GuiApplication application) 085 { 086 super(application); 087 createComponents(); 088 addFocusListeners(); 089 } 090 091 @Override 092 protected Component createInputPanel() 093 { 094 JPanel panel = new JPanel(new GridBagLayout()); 095 panel.setOpaque(false); 096 GridBagConstraints gbc = new GridBagConstraints(); 097 gbc.gridwidth = 4; 098 gbc.fill = GridBagConstraints.HORIZONTAL; 099 gbc.anchor = GridBagConstraints.NORTHWEST; 100 gbc.gridx = 0; 101 gbc.gridy = 0; 102 gbc.insets.top = UIFactory.TOP_INSET_PRIMARY_FIELD; 103 gbc.insets.bottom = UIFactory.TOP_INSET_PRIMARY_FIELD; 104 gbc.weightx = 1.0; 105 panel.add(warning, gbc); 106 warning.setVisible(false); 107 108 gbc.gridy ++; 109 gbc.gridwidth = 1; 110 gbc.weightx = 0.0; 111 gbc.insets.bottom = 0; 112 113 JLabel l = UIFactory.makeJLabel(UIFactory.IconType.NO_ICON, 114 INFO_SERVER_RUNTIME_ARGS_LABEL.get(), 115 UIFactory.TextStyle.PRIMARY_FIELD_VALID); 116 117 gbc.insets.top = Math.abs( 118 bServer.getPreferredSize().height - 119 l.getPreferredSize().height) / 2; 120 panel.add(l, gbc); 121 gbc.gridx ++; 122 gbc.insets.left = UIFactory.LEFT_INSET_PRIMARY_FIELD; 123 gbc.weightx = 0.5; 124 panel.add(lServer, gbc); 125 gbc.gridx ++; 126 gbc.insets.top = 0; 127 gbc.weightx = 0.0; 128 panel.add(bServer, gbc); 129 gbc.gridx ++; 130 gbc.weightx = 1.0; 131 gbc.insets.left = 0; 132 panel.add(Box.createHorizontalGlue(), gbc); 133 134 gbc.gridy++; 135 gbc.gridx = 0; 136 gbc.weightx = 0.0; 137 138 l = UIFactory.makeJLabel(UIFactory.IconType.NO_ICON, 139 INFO_IMPORT_RUNTIME_ARGS_LABEL.get(), 140 UIFactory.TextStyle.PRIMARY_FIELD_VALID); 141 int importInsetsTop = Math.abs( 142 bImport.getPreferredSize().height - 143 l.getPreferredSize().height) / 2; 144 gbc.insets.top = importInsetsTop + UIFactory.TOP_INSET_SECONDARY_FIELD; 145 panel.add(l, gbc); 146 gbc.gridx ++; 147 gbc.insets.left = UIFactory.LEFT_INSET_PRIMARY_FIELD; 148 gbc.weightx = 0.5; 149 panel.add(lImport, gbc); 150 gbc.gridx ++; 151 gbc.insets.top = UIFactory.TOP_INSET_SECONDARY_FIELD; 152 gbc.weightx = 0.0; 153 panel.add(bImport, gbc); 154 gbc.gridx ++; 155 gbc.weightx = 1.0; 156 gbc.insets.left = 0; 157 panel.add(Box.createHorizontalGlue(), gbc); 158 159 gbc.gridx = 0; 160 gbc.gridwidth = 4; 161 gbc.gridy ++; 162 gbc.insets = UIFactory.getEmptyInsets(); 163 gbc.weightx = 1.0; 164 gbc.weighty = 1.0; 165 gbc.fill = GridBagConstraints.VERTICAL; 166 panel.add(Box.createVerticalGlue(), gbc); 167 168 return panel; 169 } 170 171 @Override 172 protected LocalizableMessage getInstructions() 173 { 174 return INFO_JAVA_RUNTIME_OPTIONS_PANEL_INSTRUCTIONS.get(); 175 } 176 177 @Override 178 protected LocalizableMessage getTitle() 179 { 180 return INFO_JAVA_RUNTIME_OPTIONS_PANEL_TITLE.get(); 181 } 182 183 @Override 184 public Object getFieldValue(FieldName fieldName) 185 { 186 Object value = null; 187 if (fieldName == FieldName.SERVER_JAVA_ARGUMENTS) 188 { 189 value = serverJavaArgs; 190 } 191 else if (fieldName == FieldName.IMPORT_JAVA_ARGUMENTS) 192 { 193 value = importJavaArgs; 194 } 195 return value; 196 } 197 198 @Override 199 public void beginDisplay(UserData uData) 200 { 201 if (defaultServerJavaArgs == null) 202 { 203 defaultServerJavaArgs = 204 uData.getDefaultJavaArguments(UserData.SERVER_SCRIPT_NAME); 205 } 206 if (defaultImportJavaArgs == null) 207 { 208 defaultImportJavaArgs = 209 uData.getDefaultJavaArguments(UserData.IMPORT_SCRIPT_NAME); 210 } 211 boolean updatePanel = false; 212 if (serverJavaArgs == null) 213 { 214 serverJavaArgs = uData.getJavaArguments(UserData.SERVER_SCRIPT_NAME); 215 updatePanel = true; 216 } 217 if (importJavaArgs == null) 218 { 219 importJavaArgs = uData.getJavaArguments(UserData.IMPORT_SCRIPT_NAME); 220 updatePanel = true; 221 } 222 if (updatePanel) 223 { 224 lServer.setText(JavaArguments.getMessageForJLabel( 225 serverJavaArgs, defaultServerJavaArgs, 226 UIFactory.SECONDARY_FIELD_VALID_FONT).toString()); 227 lImport.setText(JavaArguments.getMessageForJLabel( 228 importJavaArgs, defaultImportJavaArgs, 229 UIFactory.SECONDARY_FIELD_VALID_FONT).toString()); 230 } 231 232 updateWarningMessage(uData); 233 } 234 235 @Override 236 public void endDisplay() 237 { 238 if (lastFocusComponent != null) 239 { 240 lastFocusComponent.requestFocusInWindow(); 241 } 242 } 243 244 @Override 245 public boolean requiresScroll() 246 { 247 return false; 248 } 249 250 /** Adds the required focus listeners to the fields. */ 251 private void addFocusListeners() 252 { 253 FocusListener l = new FocusListener() 254 { 255 @Override 256 public void focusGained(FocusEvent e) 257 { 258 lastFocusComponent = e.getComponent(); 259 } 260 261 @Override 262 public void focusLost(FocusEvent e) 263 { 264 } 265 }; 266 267 bServer.addFocusListener(l); 268 bImport.addFocusListener(l); 269 lastFocusComponent = bServer; 270 } 271 272 private void changeServerClicked() 273 { 274 JavaArgumentsDialog dlg = new JavaArgumentsDialog( 275 getFrame(), serverJavaArgs, 276 INFO_SERVER_JAVA_ARGUMENTS_TITLE.get(), 277 INFO_SERVER_JAVA_ARGUMENTS_MSG.get()); 278 dlg.pack(); 279 dlg.setModal(true); 280 dlg.setVisible(true); 281 if (!dlg.isCanceled()) 282 { 283 serverJavaArgs = dlg.getJavaArguments(); 284 lServer.setText(JavaArguments.getMessageForJLabel( 285 serverJavaArgs, defaultServerJavaArgs, 286 UIFactory.SECONDARY_FIELD_VALID_FONT).toString()); 287 } 288 } 289 290 private void changeImportClicked() 291 { 292 JavaArgumentsDialog dlg = new JavaArgumentsDialog( 293 getFrame(), importJavaArgs, 294 INFO_IMPORT_JAVA_ARGUMENTS_TITLE.get(), 295 INFO_IMPORT_JAVA_ARGUMENTS_MSG.get()); 296 dlg.pack(); 297 dlg.setModal(true); 298 dlg.setVisible(true); 299 if (!dlg.isCanceled()) 300 { 301 importJavaArgs = dlg.getJavaArguments(); 302 lImport.setText(JavaArguments.getMessageForJLabel( 303 importJavaArgs, defaultImportJavaArgs, 304 UIFactory.SECONDARY_FIELD_VALID_FONT).toString()); 305 } 306 } 307 308 private void createComponents() 309 { 310 warning = UIFactory.makeHtmlPane(LocalizableMessage.EMPTY, 311 UIFactory.INSTRUCTIONS_FONT); 312 warning.setOpaque(false); 313 314 lServer = UIFactory.makeJLabel(UIFactory.IconType.NO_ICON, 315 LocalizableMessage.EMPTY, UIFactory.TextStyle.SECONDARY_FIELD_VALID); 316 bServer = UIFactory.makeJButton(INFO_JAVA_RUNTIME_CHANGE_LABEL.get(), 317 INFO_JAVA_RUNTIME_CHANGE_SERVER_TOOLTIP.get()); 318 bServer.addActionListener(new ActionListener() 319 { 320 @Override 321 public void actionPerformed(ActionEvent ev) 322 { 323 changeServerClicked(); 324 } 325 }); 326 327 lImport = UIFactory.makeJLabel(UIFactory.IconType.NO_ICON, 328 LocalizableMessage.EMPTY, UIFactory.TextStyle.SECONDARY_FIELD_VALID); 329 bImport = UIFactory.makeJButton(INFO_JAVA_RUNTIME_CHANGE_LABEL.get(), 330 INFO_JAVA_RUNTIME_CHANGE_IMPORT_TOOLTIP.get()); 331 bImport.addActionListener(new ActionListener() 332 { 333 @Override 334 public void actionPerformed(ActionEvent ev) 335 { 336 changeImportClicked(); 337 } 338 }); 339 } 340 341 private JFrame getFrame() 342 { 343 Component mainWindow = getMainWindow(); 344 JFrame frame = null; 345 if (mainWindow instanceof JFrame) 346 { 347 frame = (JFrame)mainWindow; 348 } 349 return frame; 350 } 351 352 private void updateWarningMessage(UserData uData) 353 { 354 LocalizableMessage msg = null; 355 356 DataReplicationOptions repl = uData.getReplicationOptions(); 357 SuffixesToReplicateOptions suf = uData.getSuffixesToReplicateOptions(); 358 boolean createSuffix = 359 repl.getType() == DataReplicationOptions.Type.FIRST_IN_TOPOLOGY || 360 repl.getType() == DataReplicationOptions.Type.STANDALONE || 361 suf.getType() == SuffixesToReplicateOptions.Type.NEW_SUFFIX_IN_TOPOLOGY; 362 363 if (createSuffix) 364 { 365 NewSuffixOptions options = uData.getNewSuffixOptions(); 366 367 switch (options.getType()) 368 { 369 case IMPORT_FROM_LDIF_FILE: 370 File ldifFile = new File(options.getLDIFPaths().getFirst()); 371 if (ldifFile.length() > WARNING_THRESOLD_FOR_IMPORT) 372 { 373 msg = INFO_IMPORT_FILE_WARNING_UPDATE_RUNTIME_ARGS.get(); 374 } 375 break; 376 377 case IMPORT_AUTOMATICALLY_GENERATED_DATA: 378 if (options.getNumberEntries() > 379 WARNING_THRESOLD_AUTOMATICALLY_GENERATED_IMPORT) 380 { 381 msg = 382 INFO_AUTOMATICALLY_GENERATED_DATA_WARNING_UPDATE_RUNTIME_ARGS. 383 get(); 384 } 385 break; 386 } 387 } 388 else if (repl.getType() == DataReplicationOptions.Type.IN_EXISTING_TOPOLOGY) 389 { 390 int maxReplicatedEntries = 0; 391 392 Set<SuffixDescriptor> suffixes = suf.getSuffixes(); 393 for (SuffixDescriptor suffix : suffixes) 394 { 395 int suffixEntries = 0; 396 for (ReplicaDescriptor replica : suffix.getReplicas()) 397 { 398 suffixEntries = Math.max(suffixEntries, replica.getEntries()); 399 } 400 maxReplicatedEntries += suffixEntries; 401 } 402 403 if (maxReplicatedEntries > WARNING_THRESOLD_REPLICATED_ENTRIES) 404 { 405 msg = INFO_REPLICATED_ENTRIES_WARNING_UPDATE_RUNTIME_ARGS.get(); 406 } 407 } 408 409 if (msg != null) 410 { 411 HtmlProgressMessageFormatter formatter = 412 new HtmlProgressMessageFormatter(); 413 StringBuilder buf = new StringBuilder(); 414 String space = formatter.getSpace().toString(); 415 String lBreak = formatter.getLineBreak().toString(); 416 String title = UIFactory.applyFontToHtml( 417 INFO_GENERAL_WARNING.get().toString(), 418 UIFactory.TITLE_FONT); 419 String details = UIFactory.applyFontToHtml(msg.toString(), 420 UIFactory.SECONDARY_FIELD_VALID_FONT); 421 buf.append(UIFactory.getIconHtml(UIFactory.IconType.WARNING_LARGE)) 422 .append(space).append(space) 423 .append(title) 424 .append(lBreak).append(lBreak) 425 .append(details); 426 String s = "<form>"+UIFactory.applyErrorBackgroundToHtml(buf.toString())+ 427 "</form>"; 428 429 warning.setText(s); 430 warning.setVisible(true); 431 } 432 else 433 { 434 warning.setText(""); 435 warning.setVisible(false); 436 } 437 } 438}