This Bugzilla instance is a read-only archive of historic NetBeans bug reports. To report a bug in NetBeans please follow the project's instructions for reporting issues.

Bug 177120 - Help viewer does not work in JNLP mode
Summary: Help viewer does not work in JNLP mode
Status: RESOLVED FIXED
Alias: None
Product: platform
Classification: Unclassified
Component: Module System (show other bugs)
Version: 6.x
Hardware: PC Linux
: P1 normal (vote)
Assignee: Jesse Glick
URL:
Keywords:
Depends on:
Blocks: 159586
  Show dependency tree
 
Reported: 2009-11-18 10:38 UTC by Jesse Glick
Modified: 2009-11-22 03:08 UTC (History)
1 user (show)

See Also:
Issue Type: DEFECT
Exception Reporter:


Attachments
Log after launching of the NetBeans application with modified ext-jh-2.0_05.jar (44.00 KB, text/plain)
2009-11-19 20:45 UTC, Victor Vasilyev
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Jesse Glick 2009-11-18 10:38:13 UTC
Create a NetBeans Platform Application. Add a module to it. Add a helpset to the module. Run JNLP and Help > Contents. A 1x1 window appears and the log shows:

INFO [org.netbeans.ui.metrics.javahelp]: Showing help ID: org.netbeans.api.javahelp.MASTER_ID
SEVERE [org.netbeans.modules.javahelp]: Unable to find a JavaHelp Content Viewer component.
SEVERE [org.netbeans.modules.javahelp]: JavaHelp manifest: file:/mysuite/dist/jnlp/local/netbeans/org-netbeans-modules-javahelp/ext-jh-2.0_05.jar/META-INF/MANIFEST.MF
SEVERE [org.netbeans.modules.javahelp]: Current thread: Thread[AWT-EventQueue-2,6,main]
UIDefaults.getUI() failed: no ComponentUI class for: javax.help.JHelpContentViewer[,0,0,0x0,invalid,alignmentX=0.0,alignmentY=0.0,border=,flags=0,maximumSize=,minimumSize=,preferredSize=]
java.lang.Error
        at javax.swing.UIDefaults.getUIError(UIDefaults.java:711)
        at javax.swing.MultiUIDefaults.getUIError(MultiUIDefaults.java:133)
        at javax.swing.UIDefaults.getUI(UIDefaults.java:741)
        at javax.swing.UIManager.getUI(UIManager.java:989)
        at javax.help.JHelpContentViewer.updateUI(JHelpContentViewer.java:140)
        at javax.help.JHelpContentViewer.<init>(JHelpContentViewer.java:87)
        at javax.help.JHelp.<init>(JHelp.java:122)
        at javax.help.JHelp.<init>(JHelp.java:76)
        at org.netbeans.modules.javahelp.JavaHelp.createJHelp(JavaHelp.java:918)
        at org.netbeans.modules.javahelp.JavaHelp.createAndDisplayJHelp(JavaHelp.java:498)
        at org.netbeans.modules.javahelp.JavaHelp.showHelp(JavaHelp.java:477)
        at org.netbeans.modules.javahelp.HelpCtxProcessor$ShortcutAction.actionPerformed(HelpCtxProcessor.java:207)
        at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:1995)
[...]

The URL in the log is wrong, which may or may not be related:

..._05.jar/META...
          ^
          missing '!'
Comment 1 Jesse Glick 2009-11-18 10:46:14 UTC
The bad URL in the log is just a log issue. Should be

                                                     vvvv
            Installer.log.severe("JavaHelp manifest: jar:" +
                                 getCodeLocation(jh.getClass()) +
                                 "!/META-INF/MANIFEST.MF"); // NOI18N
                                  ^
Comment 2 Victor Vasilyev 2009-11-19 15:14:50 UTC
(In reply to comment #1)
> The bad URL in the log is just a log issue.

I'm not sure that it is a log issue. 

My original log statement 
http://hg.netbeans.org/main/file/048744607755/javahelp/src/org/netbeans/modules/javahelp/JavaHelp.java#l944
without any predefined protocol prefix and it shows the bad URL too if 
the NetBeans application is started via JNLP. 

The bad URL is obtained via the following expression in the method
getCodeLocation(Class c):

c.getProtectionDomain().getCodeSource().getLocation().toString();

I hope, the expression above is correct.
Comment 3 Victor Vasilyev 2009-11-19 17:06:51 UTC
Please, ignore my comment #2. Draft text has been wrongly committed, sorry. 

The proposed fix in the comment #1 won't work in non-JNLP mode, because the getCodeLocation(Class c) will return a string like this: 
jar:file:/V:/hg.netbeans.org.6.8/main/nbbuild/netbeans/platform11/modules/ext/jh-2.0_05.jar!.
Comment 4 Victor Vasilyev 2009-11-19 20:39:22 UTC
Unfortunately, I've not found a true cause of this issue yet.

I've added some debug info in the code of the JavaHelp and recompiled it. The log of the launching of a NetBeans application with such replacement for the jh-2.0_05.jar is attached.

The log shows the errors "UIDefaults.getUI() failed: no ComponentUI class" for all GUI components of the JavaHelp.
The ComponentUI classes (i.e. like  HelpUI=javax.help.plaf.basic.BasicHelpUI) are accessible via used com.sun.jnlp.JNLPClassLoader. They are installed as the Look And Feel Defaults via the javax.help.SwingHelpUtilities.installUIDefaults() method (see messages with "GUIHelpUtilities:" in the log).
Nevertheless, they are not accessible via the method UIDefaults.getUI() at instantiation of the JavaHelp components if the NetBeans application is launched in the JNLP mode. I don't understand why.

Seems this issue will be fixed if access to the ComponentUI classes will be repaired  in the JNLP mode.
Comment 5 Victor Vasilyev 2009-11-19 20:45:20 UTC
Created attachment 91385 [details]
Log after launching of the NetBeans application with modified ext-jh-2.0_05.jar
Comment 6 Victor Vasilyev 2009-11-20 03:58:48 UTC
In the current implementation in the JNLP mode NB's SystemClassLoader[42 modules] is registered in the javax.swing.UIManager (i.e. AFAIU in the javax.swing.UIDefaults) as the "ClassLoader",
but an actual class loader of the JavaHelp classes is com.sun.jnlp.JNLPClassLoader.

The following lines

           ClassLoader jhClassLoader = JHelp.class.getClassLoader();
           UIManager.put("ClassLoader", jhClassLoader);

before the first instantiating of the JHelp class partly resolve the issue.

At least after such fix I see "normal" JavaHelp window, but the default master help set has been displayed instead of existing help set associated with a NB module that is bundled into the launched NB application.
Comment 7 Jesse Glick 2009-11-20 08:24:33 UTC
UIManager.put("ClassLoader", jhClassLoader) is obviously unacceptable as a workaround since that would affect any Swing component loaded in the app.

The various other exceptions in your log file, e.g. CNFE on NbDocsStreamHandler$Factory, are disturbing - but I cannot reproduce them.
Comment 8 Jesse Glick 2009-11-20 08:42:35 UTC
NbDocsStreamHandler$Factory no longer exists in current sources. Nor does ExceptionVisualizerProvider. Do a clean build of your source tree to get rid of this old junk.
Comment 9 Jesse Glick 2009-11-20 08:59:38 UTC
Something seems to be wrong with class loading of jh.jar in JNLP mode - but only this JAR.

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
public final class DiagAction implements ActionListener {
    public void actionPerformed(ActionEvent e) {
        diagnose("T.cT.cCL", Thread.currentThread().getContextClassLoader());
        diagnose("CL.sCL", ClassLoader.getSystemClassLoader());
    }
    private void diagnose(String what, ClassLoader l) {
        System.err.println(what + "=" + l);
        diagnose2(l, DiagAction.class.getName());
        diagnose2(l, "javax.help.JHelp");
        diagnose2(l, "org.netbeans.modules.javahelp.JavaHelp");
        diagnose2(l, "org.jdesktop.layout.GroupLayout");
    }
    private void diagnose2(ClassLoader l, String clazz) {
        try {
            Class c = l.loadClass(clazz);
            System.err.println("loaded " + clazz + ": " + c.getProtectionDomain().getCodeSource().getLocation());
        } catch (ClassNotFoundException x) {
            x.printStackTrace();
        }
    }
}

run in normal mode shows all four classes being loaded as expected. In JNLP mode, JHelp cannot be loaded but the other three can:

ClassNotFoundException: javax.help.JHelp starting from SystemClassLoader[42 modules] with possible defining loaders null and declared parents []
Comment 10 Jesse Glick 2009-11-20 09:16:01 UTC
Regression due to fix of bug #159586:

  OpenIDE-Module-Hide-Classpath-Packages: javax.help.**, com.sun.java.help.**

causes PCL to refuse to load classes from jh.jar because it thinks these are part of the JRE when in fact they are part of the JNLP app.
Comment 11 Jesse Glick 2009-11-20 10:02:41 UTC
Actually exists in 6.7 too. Not hard to fix once diagnosed: core-main #57bff5dfd9ba
Comment 12 Quality Engineering 2009-11-21 15:44:44 UTC
Integrated into 'main-golden', will be available in build *200911211401* on http://bits.netbeans.org/dev/nightly/ (upload may still be in progress)
Changeset: http://hg.netbeans.org/main/rev/57bff5dfd9ba
User: Jesse Glick <jglick@netbeans.org>
Log: #177120: ignore OpenIDE-Module-Hide-Classpath-Packages in JNLP mode.
Always delegate to the JNLPClassLoader since it probably can load the classes from the module.
("Parent" set and "delegate" starting from "system class loader" are always empty in JNLP mode, since PCL is not used for modules.)
If the classes are in fact present in the JRE, then they will be loaded from there, but not much we can do about that;
running in JNLP mode normally disables the various class loading checks of the NB module system.
If you wanted your jh.jar to override any present in the JRE, you would have to configure this in the JNLP descriptor.
Comment 13 Quality Engineering 2009-11-22 03:08:44 UTC
Integrated into 'main-golden', will be available in build *200911220201* on http://bits.netbeans.org/dev/nightly/ (upload may still be in progress)
Changeset: http://hg.netbeans.org/main/rev/ea7f545a103d
User: Jesse Glick <jglick@netbeans.org>
Log: Simplifying log message mentioned in #177120, since it was often incorrect anyway.
(Technically: JarClassLoader produces jar:file:/.../jh.jar!/ URLs as a codebase location, which is correct.
URLClassLoader as created by JRE code produces either file:/.../jh.jar or jar:file:/.../jh.jar.
The first is a valid URL but not a folder, thus not a codebase; and the second is just wrong.
Similarly with http://.../.../jh.jar and so on.)