KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > core > startup > NbEvents


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.core.startup;
21
22 // May use core, GUI, ad nauseum.
23

24 import java.awt.Component JavaDoc;
25 import java.awt.Dimension JavaDoc;
26 import java.io.File JavaDoc;
27 import java.util.ArrayList JavaDoc;
28 import java.util.Collection JavaDoc;
29 import java.util.Collections JavaDoc;
30 import java.util.Iterator JavaDoc;
31 import java.util.List JavaDoc;
32 import java.util.Set JavaDoc;
33 import java.util.logging.Level JavaDoc;
34 import java.util.logging.Logger JavaDoc;
35 import javax.swing.JOptionPane JavaDoc;
36 import javax.swing.JTextArea JavaDoc;
37 import org.netbeans.Events;
38 import org.netbeans.Module;
39 import org.netbeans.TopSecurityManager;
40 import org.netbeans.Util;
41 import org.openide.filesystems.FileObject;
42 import org.openide.modules.SpecificationVersion;
43 import org.openide.util.NbBundle;
44 import org.openide.util.NbCollections;
45 import org.openide.util.RequestProcessor;
46
47 /** Report events to the performance logger, status text/splash screen,
48  * console, and so on.
49  * @author Jesse Glick
50  */

51 final class NbEvents extends Events {
52     private Logger JavaDoc logger = Logger.getLogger(NbEvents.class.getName());
53
54     private int moduleCount;
55     
56     private int counter;
57
58     /** Handle a logged event.
59      * CAREFUL that this is called synchronously, usually within a write
60      * mutex or other sensitive environment. So do not call anything
61      * blocking (like TM.notify) directly. TM.setStatusText and printing
62      * to console are fine, as well as performance logging.
63      */

64     protected void logged(final String JavaDoc message, Object JavaDoc[] args) {
65         if (message == PERF_TICK) {
66             StartLog.logProgress( (String JavaDoc)args[0]);
67         } else if (message == PERF_START) {
68             StartLog.logStart( (String JavaDoc)args[0]);
69         } else if (message == PERF_END) {
70             StartLog.logEnd( (String JavaDoc)args[0]);
71         } else if (message == START_CREATE_BOOT_MODULE) {
72             org.netbeans.core.startup.Splash.getInstance().increment(1);
73         } else if (message == START_LOAD_BOOT_MODULES) {
74             setStatusText(
75                 NbBundle.getMessage(NbEvents.class, "MSG_start_load_boot_modules"));
76             StartLog.logStart("ModuleSystem.loadBootModules"); // NOI18N
77
} else if (message == START_LOAD) {
78             StartLog.logStart("NbInstaller.load"); // NOI18N
79
} else if (message == FINISH_LOAD_BOOT_MODULES) {
80             setStatusText(
81                 NbBundle.getMessage(NbEvents.class, "MSG_finish_load_boot_modules"));
82             StartLog.logEnd( "ModuleSystem.loadBootModules" ); // NOI18N
83
} else if (message == FINISH_LOAD) {
84             StartLog.logEnd("NbInstaller.load"); // NOI18N
85
} else if (message == START_AUTO_RESTORE) {
86             Set JavaDoc modules = (Set JavaDoc)args[0];
87             if (! modules.isEmpty()) {
88                 setStatusText(
89                     NbBundle.getMessage(NbEvents.class, "MSG_start_auto_restore"));
90             }
91         } else if (message == FINISH_AUTO_RESTORE) {
92             setStatusText(
93                 NbBundle.getMessage(NbEvents.class, "MSG_finish_auto_restore"));
94         } else if (message == START_ENABLE_MODULES) {
95             setStatusText(
96                 NbBundle.getMessage(NbEvents.class, "MSG_start_enable_modules"));
97         } else if (message == FINISH_ENABLE_MODULES) {
98             List JavaDoc modules = (List JavaDoc)args[0];
99             if (! modules.isEmpty()) {
100                 dumpModulesList(modules);
101             }
102             setStatusText(
103                 NbBundle.getMessage(NbEvents.class, "MSG_finish_enable_modules"));
104             StartLog.logEnd("ModuleManager.enable"); // NOI18N
105
} else if (message == START_DISABLE_MODULES) {
106             setStatusText(
107                 NbBundle.getMessage(NbEvents.class, "MSG_start_disable_modules"));
108         } else if (message == FINISH_DISABLE_MODULES) {
109             List JavaDoc modules = (List JavaDoc)args[0];
110             if (! modules.isEmpty()) {
111                 logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_finish_disable_modules"));
112                 dumpModulesList(modules);
113             }
114             setStatusText(
115                 NbBundle.getMessage(NbEvents.class, "MSG_finish_disable_modules"));
116         } else if (message == START_DEPLOY_TEST_MODULE) {
117             // No need to print anything. ModuleSystem.deployTestModule prints
118
// its own stuff (it needs to be printed synchronously to console
119
// in order to appear in the output window). But status text is OK.
120
// Again no need for I18N as this is only for module developers.
121
setStatusText(
122                 "Deploying test module in " + (File JavaDoc)args[0] + "..."); // NOI18N
123
} else if (message == FINISH_DEPLOY_TEST_MODULE) {
124             setStatusText(
125                 "Finished deploying test module."); // NOI18N
126
} else if (message == FAILED_INSTALL_NEW) {
127             Set JavaDoc<Module> modules = NbCollections.checkedSetByCopy((Set JavaDoc) args[0], Module.class, true);
128             {
129                 StringBuilder JavaDoc buf = new StringBuilder JavaDoc(NbBundle.getMessage(NbEvents.class, "MSG_failed_install_new"));
130                 NbProblemDisplayer.problemMessagesForModules(buf, modules, false);
131                 logger.log(Level.INFO, buf.toString());
132             }
133             {
134                 StringBuilder JavaDoc buf = new StringBuilder JavaDoc(NbBundle.getMessage(NbEvents.class, "MSG_failed_install_new"));
135                 NbProblemDisplayer.problemMessagesForModules(buf, modules, true);
136                 String JavaDoc msg = buf.toString();
137                 notify(msg, true);
138             }
139             setStatusText("");
140         } else if (message == FAILED_INSTALL_NEW_UNEXPECTED) {
141             Module m = (Module)args[0];
142             // ignore args[1]: InvalidException
143
{
144                 StringBuffer JavaDoc buf = new StringBuffer JavaDoc(NbBundle.getMessage(NbEvents.class, "MSG_failed_install_new_unexpected", m.getDisplayName()));
145                 NbProblemDisplayer.problemMessagesForModules(buf, Collections.singleton(m), false);
146                 logger.log(Level.INFO, buf.toString());
147             }
148
149             {
150                 StringBuffer JavaDoc buf = new StringBuffer JavaDoc(NbBundle.getMessage(NbEvents.class, "MSG_failed_install_new_unexpected", m.getDisplayName()));
151                 NbProblemDisplayer.problemMessagesForModules(buf, Collections.singleton(m), true);
152                 notify(buf.toString(), true);
153             }
154             setStatusText("");
155         } else if (message == START_READ) {
156             setStatusText(
157                 NbBundle.getMessage(NbEvents.class, "MSG_start_read"));
158             StartLog.logStart("ModuleList.readInitial"); // NOI18N
159
} else if (message == MODULES_FILE_SCANNED) {
160         moduleCount = (Integer JavaDoc)args[0];
161             Splash.getInstance().addToMaxSteps(Math.max(moduleCount + moduleCount/2 - 100, 0));
162         } else if (message == MODULES_FILE_PROCESSED) {
163             Splash.getInstance().increment(1);
164             if (StartLog.willLog()) {
165                 StartLog.logProgress("file " + ((FileObject)args[0]).getNameExt() + " processed"); // NOI18N
166
}
167         } else if (message == FINISH_READ) {
168         if (moduleCount < 100) {
169         Splash.getInstance().increment(moduleCount - 100);
170         }
171             setStatusText(
172                 NbBundle.getMessage(NbEvents.class, "MSG_finish_read"));
173             StartLog.logEnd("ModuleList.readInitial"); // NOI18N
174
} else if (message == RESTORE) {
175             // Don't look for display name. Just takes too long.
176
setStatusText(
177                 NbBundle.getMessage(NbEvents.class, "MSG_restore"/*, ((Module)args[0]).getDisplayName()*/));
178         if (++counter < moduleCount / 2) {
179         Splash.getInstance().increment(1);
180         }
181         } else if (message == INSTALL) {
182             // Nice to see the real title; not that common, after all.
183
setStatusText(
184                 NbBundle.getMessage(NbEvents.class, "MSG_install", ((Module)args[0]).getDisplayName()));
185             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_install", ((Module)args[0]).getDisplayName()));
186         } else if (message == UPDATE) {
187             setStatusText(
188                 NbBundle.getMessage(NbEvents.class, "MSG_update", ((Module)args[0]).getDisplayName()));
189             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_update", ((Module)args[0]).getDisplayName()));
190         } else if (message == UNINSTALL) {
191             setStatusText(
192                 NbBundle.getMessage(NbEvents.class, "MSG_uninstall", ((Module)args[0]).getDisplayName()));
193         } else if (message == LOAD_SECTION) {
194             // Again avoid finding display name now.
195
setStatusText(
196                 NbBundle.getMessage(NbEvents.class, "MSG_load_section"/*, ((Module)args[0]).getDisplayName()*/));
197         if (++counter < moduleCount / 4) {
198         Splash.getInstance().increment(1);
199         }
200         } else if (message == LOAD_LAYERS) {
201             setStatusText(
202                 NbBundle.getMessage(NbEvents.class, "MSG_load_layers"));
203         } else if (message == WRONG_CLASS_LOADER) {
204             if (! Boolean.getBoolean("netbeans.moduleitem.dontverifyclassloader") && Util.err.isLoggable(Level.WARNING)) { // NOI18N
205
Class JavaDoc clazz = (Class JavaDoc)args[1];
206                 // Message for developers, no need for I18N.
207
StringBuffer JavaDoc b = new StringBuffer JavaDoc();
208                 b.append("The module " + ((Module)args[0]).getDisplayName() + " loaded the class " + clazz.getName() + "\n"); // NOI18N
209
b.append("from the wrong classloader. The expected classloader was " + args[2] + "\n"); // NOI18N
210
b.append("whereas it was actually loaded from " + clazz.getClassLoader() + "\n"); // NOI18N
211
b.append("Usually this means that some classes were in the startup classpath.\n"); // NOI18N
212
b.append("To suppress this message, run with: -J-Dnetbeans.moduleitem.dontverifyclassloader=true"); // NOI18N
213
Util.err.warning(b.toString());
214             }
215         } else if (message == EXTENSION_MULTIPLY_LOADED) {
216             // Developer-oriented message, no need for I18N.
217
logger.log(Level.WARNING, "The extension " + (File JavaDoc)args[0] + " may be multiply loaded by modules: " + (Set JavaDoc/*<File>*/)args[1] + "; see: http://www.netbeans.org/download/dev/javadoc/org-openide-modules/org/openide/modules/doc-files/classpath.html#class-path"); // NOI18N
218
} else if (message == MISSING_JAR_FILE) {
219             File JavaDoc jar = (File JavaDoc)args[0];
220             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_missing_jar_file", jar.getAbsolutePath()));
221         } else if (message == CANT_DELETE_ENABLED_AUTOLOAD) {
222             Module m = (Module)args[0];
223             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_cant_delete_enabled_autoload", m.getDisplayName()));
224         } else if (message == MISC_PROP_MISMATCH) {
225             // XXX does this really need to be logged to the user?
226
// Or should it just be sent quietly to the log file?
227
Module m = (Module)args[0];
228             String JavaDoc prop = (String JavaDoc)args[1];
229             Object JavaDoc onDisk = args[2];
230             Object JavaDoc inMem = args[3];
231             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_misc_prop_mismatch", new Object JavaDoc[] {m.getDisplayName(), prop, onDisk, inMem}));
232         } else if (message == PATCH) {
233             File JavaDoc f = (File JavaDoc)args[0];
234             logger.log(Level.INFO, NbBundle.getMessage(NbEvents.class, "TEXT_patch", f.getAbsolutePath()));
235         }
236         // XXX other messages?
237
}
238
239     /** Print a nonempty list of modules to console (= log file).
240      * @param modules the modules
241      */

242     private void dumpModulesList(Collection JavaDoc modules) {
243         Iterator JavaDoc it = modules.iterator();
244         if (! it.hasNext()) throw new IllegalArgumentException JavaDoc();
245         StringBuilder JavaDoc buf = new StringBuilder JavaDoc(modules.size() * 100 + 1);
246         buf.append(NbBundle.getMessage(NbEvents.class, "TEXT_finish_enable_modules"));
247         String JavaDoc lineSep = System.getProperty("line.separator");
248         buf.append(lineSep);
249         while (it.hasNext()) {
250             Module m = (Module)it.next();
251             buf.append('\t'); // NOI18N
252
buf.append(m.getCodeName());
253             buf.append(" ["); // NOI18N
254
SpecificationVersion sv = m.getSpecificationVersion();
255             if (sv != null) {
256                 buf.append(sv);
257             }
258             String JavaDoc iv = m.getImplementationVersion();
259             if (iv != null) {
260                 buf.append(' '); // NOI18N
261
buf.append(iv);
262             }
263             String JavaDoc bv = m.getBuildVersion();
264             if (bv != null && !bv.equals (iv)) {
265                 buf.append(' '); // NOI18N
266
buf.append(bv);
267             }
268             buf.append(']'); // NOI18N
269
// #32331: use platform-specific newlines
270
buf.append(lineSep);
271         }
272         logger.log(Level.INFO, buf.toString());
273     }
274     
275     private void notify(String JavaDoc text, boolean warn) {
276         if (Boolean.getBoolean("netbeans.full.hack")) { // NOI18N
277
// #21773: interferes with automated GUI testing.
278
logger.log(Level.INFO, text);
279         } else {
280             // Normal - display dialog.
281
new Notifier(text, warn);
282         }
283     }
284     private static final class Notifier implements Runnable JavaDoc {
285         private static int questions;
286         
287         private boolean warn;
288         private String JavaDoc text;
289         private static RequestProcessor RP = new RequestProcessor("Notify About Module System"); // NOI18N
290
private Object JavaDoc[] options;
291         private Object JavaDoc value;
292         
293         public Notifier(String JavaDoc text, boolean type) {
294             this.warn = type;
295             this.text = text;
296             //this.options = options;
297

298             if (questions++ == 0) {
299                 this.options = new String JavaDoc[] {
300                     NbBundle.getMessage(Notifier.class, "MSG_continue"),
301                     NbBundle.getMessage(Notifier.class, "MSG_exit"),
302                 };
303             }
304
305             RequestProcessor.Task t = RP.post(this, 0, Thread.MIN_PRIORITY);
306             
307             if (options != null) {
308                 t.waitFinished();
309             }
310         }
311         
312         public Object JavaDoc getOption() {
313             return value;
314         }
315         public void run() {
316             int type = warn ? JOptionPane.WARNING_MESSAGE : JOptionPane.INFORMATION_MESSAGE;
317             String JavaDoc msg = NbBundle.getMessage(Notifier.class, warn ? "MSG_warning" : "MSG_info"); // NOI18N
318

319             Splash out = Splash.getInstance();
320             Component JavaDoc c = out.getComponent() == null ? null : out.getComponent();
321             
322             JTextArea JavaDoc area = new JTextArea JavaDoc();
323             area.setText(text);
324             area.setEditable(false);
325             area.setEnabled(true);
326             area.setOpaque(false);
327             javax.swing.JScrollPane JavaDoc pane = new javax.swing.JScrollPane JavaDoc(area);
328             pane.setPreferredSize(new Dimension JavaDoc(pane.getPreferredSize().width + 50, area.getFont().getSize() * 15));
329             
330             if (options == null) {
331                 JOptionPane.showMessageDialog(null, pane, msg, type);
332             } else {
333                 int ret = JOptionPane.showOptionDialog(c, pane, msg, 0, type, null, options, options[1]);
334                 if (ret == 1 || ret == -1) { // exit or close
335
TopSecurityManager.exit(1);
336                 }
337             }
338         }
339     }
340
341     private static void setStatusText (String JavaDoc msg) {
342         Main.setStatusText (msg);
343     }
344 }
345
Popular Tags