Question
Yone Moreno · Aug 14, 2020

How could we attach external libraries to generated code with Java Gateway Wizard: %ProcessErrorStatic+4^%Net.Remote.Proxy java.lang.NoClassDefFoundError:

Hello,

We would need some help.

We have a Java project in Eclipse which uses two external libraries, which are referenced as a maven pom.xml dependency.

We created a JAR with all the dependencies included.

We have used the Java Gateway Wizard as follows:

In the image you could see that we have chosen the project's jar, written IP and PORT of Gateway and written all external dependencies' server path separated with semicolons.

It generates the following Ensemble class:

Class radarCovidcrearToken.CCAATokenGeneratorTest Extends java.lang.Object [ ProcedureBlock ]
{

Parameter IMPORTTIMESTAMP As STRING = "1970-01-01 00:00:00.0";

Method %OnNew(ByRef p0 As %ObjectHandle) As %Status
{
    Quit:'$D(p0) $$$OK
    Quit ..%Constructor(p0,"radarCovidcrearToken.CCAATokenGeneratorTest",0)
}

ClassMethod main(ByRef p0 As %ObjectHandle, ByRef p1 As %ObjectHandle)
{
    Do ..%PreInvokeStatic(p0,"radarCovidcrearToken.CCAATokenGeneratorTest")
    Set x=$zobjexport("main",18)
    Set x=$zobjexport(-1,18)
    Do ..%WriteArray(p0,"[Ljava.lang.String;",p1)
    Set x=$zobjexport("Y1",8)
    Set id=$zobjexport(9),fun=$zobjexport(15)
    Do:fun'="Y1" ..%ProcessErrorStatic(p0,fun,id)
    Set:$zobjexport(17) p1=..%ReadArrayArgument(p0)
    Do:fun'="Y5" ..%PostInvokeStatic(p0)
}

}

 

We have written an Operation to call the previous code:

Include (%systemInclude, Ensemble)

Class Operaciones.JAVA.AppSeguimiento Extends EnsLib.JavaGateway.AbstractOperation [ ProcedureBlock ]
{

Parameter INVOCATION = "Queue";

Method generarToken(pRequest As Mensajes.Request.Seguridad.AutenticacionLDAP, Output pResponse As %Library.String(MAXLEN="")) As %Status
{
    try{
        kill %objlasterror
        #dim tSC as %Status
        #dim tJavaGateway as EnsLib.JavaGateway.JavaGateway
         Set tSC = ..GetConnection(.tJavaGateway)
        If $$$ISOK(tSC)
        {
           set echo = ##class(radarCovidcrearToken.CCAATokenGeneratorTest).%New(.tJavaGateway)    
           $$$LOGINFO("echo: "_echo)
           zwrite %objlasterror
           do echo.main(.tJavaGateway,.pResponse)
           zwrite %objlasterror
           $$$LOGINFO("pResponse: "_pResponse)
        }
    }catch ex{
        $$$LOGINFO("%objlasterror: "_%objlasterror)
    }
    
    Quit $$$OK
}

XData MessageMap
{
<MapItems>
    <MapItem MessageType="Mensajes.Request.Seguridad.AutenticacionLDAP">
        <Method>generarToken</Method>
    </MapItem>
</MapItems>
}

}

 

The Operation's configuration in the Production is:

<Item Name="Operaciones.JAVA.AppSeguimiento" Category="AppSeguimiento" ClassName="Operaciones.JAVA.AppSeguimiento" PoolSize="1" Enabled="true" Foreground="false" Comment="" LogTraceEvents="true" Schedule="">
    <Setting Target="Host" Name="Port">19501</Setting>
    <Setting Target="Host" Name="AdditionalPaths">/opt/contenedor/Java/AppSeguimientoAnadidaReferenciaJARSexternos.jar,/opt/contenedor/Java/aether-api-1.7.jar,/opt/contenedor/Java/aether-impl-1.7.jar,/opt/contenedor/Java/aether-spi-1.7.jar,/opt/contenedor/Java/aether-util-1.7.jar,/opt/contenedor/Java/asm-6.2.jar,/opt/contenedor/Java/bcpkix-jdk15on-1.58.jar,/opt/contenedor/Java/bcprov-jdk15on-1.58.jar,/opt/contenedor/Java/classworlds-1.1.jar,/opt/contenedor/Java/commons-cli-1.0.jar,/opt/contenedor/Java/commons-codec-1.14.jar,/opt/contenedor/Java/commons-io-2.5.jar,/opt/contenedor/Java/jackson-annotations-2.10.3.jar,/opt/contenedor/Java/jackson-core-2.10.3.jar,/opt/contenedor/Java/jackson-databind-2.10.3.jar,/opt/contenedor/Java/java-jwt-3.10.3.jar,/opt/contenedor/Java/junit-3.8.1.jar,/opt/contenedor/Java/plexus-build-api-0.0.4.jar,/opt/contenedor/Java/plexus-cipher-1.4.jar,/opt/contenedor/Java/plexus-classworlds-2.2.3.jar,/opt/contenedor/Java/plexus-compiler-api-2.8.4.jar,/opt/contenedor/Java/plexus-compiler-javac-2.8.4.jar,/opt/contenedor/Java/plexus-compiler-manager-2.8.4.jar,/opt/contenedor/Java/plexus-component-annotations-1.7.1.jar,/opt/contenedor/Java/plexus-container-default-1.0-alpha-9-stable-1.jar,/opt/contenedor/Java/plexus-interactivity-api-1.0-alpha-4.jar,/opt/contenedor/Java/plexus-interpolation-1.13.jar,/opt/contenedor/Java/plexus-interpolation-1.14.jar,/opt/contenedor/Java/plexus-java-0.9.10.jar,/opt/contenedor/Java/plexus-sec-dispatcher-1.3.jar,/opt/contenedor/Java/plexus-utils-2.0.4.jar,/opt/contenedor/Java/plexus-utils-2.0.5.jar,/opt/contenedor/Java/qdox-2.0-M9.jar,/opt/contenedor/Java/sisu-guice-2.1.7-noaop.jar,/opt/contenedor/Java/sisu-inject-bean-1.4.2.jar,/opt/contenedor/Java/sisu-inject-plexus-1.4.2.jar</Setting>
  </Item>

 

When we execute the Operation from the Production, we observe the following exception:

%objlasterror: 0 ꟈjava.lang.NoClassDefFoundError: org/bouncycastle/util/io/pem/PemReader
at radarCovidcrearToken.CCAATokenGeneratorTest.loadPrivateKeyFromPem(CCAATokenGeneratorTest.java:76)
at radarCovidcrearToken.CCAATokenGeneratorTest.run(CCAATokenGeneratorTest.java:36)
at radarCovidcrearToken.CCAATokenGeneratorTest.main(CCAATokenGeneratorTest.java:31)
at sun.reflect.GeneratedMethodAccessor2.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at com.intersys.gateway.JavaGateway.executeInstanceMethod(JavaGateway.java:996)
at com.intersys.gateway.JavaGateway.executeMethod(JavaGateway.java:942)
at com.intersys.gateway.JavaGateway.processMessage(JavaGateway.java:559)
at com.intersys.gateway.JavaGateway.run(JavaGateway.java:548)
at com.intersys.gateway.JavaGateway.run(JavaGateway.java:519)
P ESBSSCCB/e^%ProcessErrorStatic+4^%Net.Remote.Proxy.1^1;d^zmain+7^radarCovidcrearToken.CCAATokenGeneratorTest.1^1(d^^Operaciones.JAVA.AppSeguimiento.1^0(e^^Operaciones.JAVA.AppSeguimiento.1^0(e^^Operaciones.JAVA.AppSeguimiento.1^0e^zOnTask+42^En

 

We have also read this topic where Robert Cemper and Eduard Lebedyuk, explain how to show native code's exception:

https://community.intersystems.com/post/processerror6-netremoteproxy1-er...

 

How could we attach external libraries to generated code with Java Gateway Wizard?

 

EDIT: We have add in the Production's Operation's configuration: "/opt/contenedor/Java/AppSeguimientoAnadidaReferenciaJARSexternos.jar
"

00
2 0 5 198
Log in or sign up to continue

What Java version are you using?

Can you provide the output of `jar -tf <name of your jar file>`?

NoClassDefFoundError is usually an indication that the classpath (as defined by the classloading operations performed) is not properly setup.

If your jar file isn't properly structured, that's the problem.

Hello Kevin,

We are using the following Java version:

java version "1.8.0_65"
Java(TM) SE Runtime Environment (build 1.8.0_65-b17)
Java HotSpot(TM) 64-Bit Server VM (build 25.65-b01, mixed mode)

If we execute the command with our jar (which includes the Java program and its dependencies):

jar -tf "AppSeguimientoAnadidaReferenciaJARSexternos.jar"

We see:

META-INF/MANIFEST.MF
org/
org/eclipse/
org/eclipse/jdt/
org/eclipse/jdt/internal/
org/eclipse/jdt/internal/jarinjarloader/
org/eclipse/jdt/internal/jarinjarloader/JIJConstants.class
org/eclipse/jdt/internal/jarinjarloader/JarRsrcLoader$ManifestInfo.class
org/eclipse/jdt/internal/jarinjarloader/JarRsrcLoader.class
org/eclipse/jdt/internal/jarinjarloader/RsrcURLConnection.class
org/eclipse/jdt/internal/jarinjarloader/RsrcURLStreamHandler.class
org/eclipse/jdt/internal/jarinjarloader/RsrcURLStreamHandlerFactory.class
radarCovidcrearToken/
radarCovidcrearToken/CCAATokenGeneratorTest.class
generated_private_base64.pem
aether-api-1.7.jar
aether-impl-1.7.jar
aether-spi-1.7.jar
aether-util-1.7.jar
asm-6.2.jar
bcpkix-jdk15on-1.58.jar
bcprov-jdk15on-1.58.jar
classworlds-1.1.jar
commons-cli-1.0.jar
commons-codec-1.14.jar
commons-io-2.5.jar
jackson-annotations-2.10.3.jar
jackson-core-2.10.3.jar
jackson-databind-2.10.3.jar
java-jwt-3.10.3.jar
junit-3.8.1.jar
plexus-build-api-0.0.4.jar
plexus-cipher-1.4.jar
plexus-classworlds-2.2.3.jar
plexus-compiler-api-2.8.4.jar
plexus-compiler-javac-2.8.4.jar
plexus-compiler-manager-2.8.4.jar
plexus-component-annotations-1.7.1.jar
plexus-container-default-1.0-alpha-9-stable-1.jar
plexus-interactivity-api-1.0-alpha-4.jar
plexus-interpolation-1.13.jar
plexus-interpolation-1.14.jar
plexus-java-0.9.10.jar
plexus-sec-dispatcher-1.3.jar
plexus-utils-2.0.4.jar
plexus-utils-2.0.5.jar
qdox-2.0-M9.jar
sisu-guice-2.1.7-noaop.jar
sisu-inject-bean-1.4.2.jar
sisu-inject-plexus-1.4.2.jar
java-jwt-3.10.3_2.jar
jackson-databind-2.10.3_2.jar
jackson-annotations-2.10.3_2.jar
jackson-core-2.10.3_2.jar
commons-codec-1.14_2.jar
bcpkix-jdk15on-1.58_2.jar
bcprov-jdk15on-1.58_2.jar

If we execute the command to locate the jar where is the class which generates the NoClassDefFoundError :

jar -tf "bcprov-jdk15on-1.58.jar"

We get:

...

org/bouncycastle/util/io/pem/
org/bouncycastle/util/io/pem/PemGenerationException.class
org/bouncycastle/util/io/pem/PemHeader.class
org/bouncycastle/util/io/pem/PemObject.class
org/bouncycastle/util/io/pem/PemObjectGenerator.class
org/bouncycastle/util/io/pem/PemObjectParser.class
org/bouncycastle/util/io/pem/PemReader.class
org/bouncycastle/util/io/pem/PemWriter.class
org/bouncycastle/util/test/

...

As you would notice it outputs the name of the missing class:

org/bouncycastle/util/io/pem/PemReader.class

What could we do?

I want to make sure, AppSeguimientoAnadidaReferenciaJARSexternos.jar  is included on the "Additional Paths".

I searched the Operation's XML definition and I didn't see it there.

Hello Kevin,

Yes you were right we did not include "/opt/contenedor/Java/AppSeguimientoAnadidaReferenciaJARSexternos.jar"

We have just added it and the exception continues.