Using Libraries in Vaadin: com.vaadin.server.ServiceException - java

Iam trying to use the matlabcontrol library in vaadin. I basically want use vaadin as a GUI for better configuration of the variables.
I have a test GUI running, everything works fine, until I try to add matlabcontrol specific variables or calls. I did add the library and the matlab interface works great when testing.
I will show you an abstract example:
public class UI_Matlab extends CustomComponent {
public UI_Matlab{
Label matlabRox = new Label("Matlab rocks!");
setCompositionRoot(matlabRox);
}
}
This works fine as expected!
But when I change it too:
public class UI_Matlab extends CustomComponent {
public UI_Matlab{
MatlabProxyFactory factory = new MatlabProxyFactory();
Label matlabRox = new Label("Matlab rocks!");
setCompositionRoot(matlabRox);
}
}
I already get:
"HTTP Status 500 - com.vaadin.server.ServiceException: java.lang.NoClassDefFoundError: matlabcontrol/MatlabProxyFactory"
Additional Information:
Vaadin 7.0
Tomcat v7.0
Eclipse Kepler
matlabcontrol 4.1.0 (edited)

The widget is trying to load additional classes it is depending on (MatlabProxyFactory) and cannot find them (NoClassDefFoundError is like a ClassNotFoundException, but one level "deeper", like a field or return type of the class you are loading cannot be found).
--> Check your build path or whether what you are deploying is complete wrt. dependencies.

I found the answere in another post:
External project dependency in Vaadin
They describe it a little different, so I will add what I did.
What "hiergiltdiestfu" probably meant worked out well, but I accidently was checking the project classpath.
The solution is to add the libraries to the server classpath, which means you have to add it to the tomcat classpath in my case.
Open the following in eclipse:
Run > Run Configurations > Apache Tomcat > (your Tomcat instance) > Classpath
Then add to user entries the library of your need.

Related

Atmosphere servlet classloading conflict with java

I am not sure how to title this question but I'll try to explain what the issue is.
I am currently testing out Atmosphere framework in a web application. I started by reading the documentation and then testing the chat-multiroom sample. I am running it in eclipse using tomcat 8.5. When the atmosphere servlet initializes it will scan a package for any classes that have certain annotations and if it finds the annothions it will add the class to a map using a path as the key. For this to work it must first scan its own packages looking for what annotations it should use and add them to a map of available annotations. This list has to be populated for the annotated classes to be initialised. The code for this looks like this:
public Class<? extends Processor> handleProcessor(Class<?> clazz) {
if (Processor.class.isAssignableFrom(clazz)) {
Class<Processor> p = (Class<Processor>) clazz;
if (logger.isTraceEnabled()) {
logger.trace("Processor {} associated with {}", p, p.getAnnotation(AtmosphereAnnotation.class).value());
}
annotations.put(p.getAnnotation(AtmosphereAnnotation.class).value(), p);
return p;
}
return null;
}
So it goes though every class it finds and checks if it implements Processor. Processeor is an interface provided by atmosphere imported with import org.atmosphere.annotation.Processor;
However when I debug this code it is instead compareing clazz with the jdk:s interface javax.annotation.processing.Processor instead of org.atmosphere.annotation.Processor. This is causing the map to be empty. This results in the endpoints are not loaded because there are no annotations to look for.
If I download the atmosphere code and copy it to my src folder it works correctly.
I am using Eclipse IDE at the moment and I am wondering if there is a way to configure the project or the tomcat server in some way to make it understand which interface it should use.
[EDIT]
After some more research the problem isn't due to the class comparision instead it is about how tomcat loads classes. Atmosphere relies on that the container loads the annotation classes and passes it into Atmosphere ServletContainerInitializer however tomcat will not pass the classes that exisit in the package jar files under the webapps lib folder. It will only pass in the classes that are in the webapps WEB-INF/classes folder and not the WEB-INF/lib folder. That is why it works if I add the Atmosphere src to the webapps src folder in eclipse.
[EDIT2]
It turns out I had disabled jar scanning in catalina.properties.
Enabling the jar scanning again solved the issue.

How can I perform Hot Code Replace in Tomcat web application running outside eclipse?

I am using Hot Code Replace feature when Tomcat is running from eclipse and it works great.
But, how can I do this manually when Tomcat is running outside eclipse?
After some searching, I have found that I need to use an agent like HotswapAgent. But, they are using this agent with modified JDK called DCEVM. I don't want to use modified JDK. I want to achieve the same thing with OpenJDK.
I know that modification will be limited to method body only but, that's not a problem for me. How can I achieve the exact same thing eclipse is doing for Hot Code Replace for an externally running Tomcat without using IDE?
Edit : Eclipse example is just to clarify what I want to achieve. I do not want to use eclipse at all. I just want to do Hot Code Replace in an application running in Tomcat.
Yes, it's possible to perform Hot Code Replace in a running JVM. This involves several steps.
Prepare (compile) the new version of classes you want to replace. Let's say, you want to replace org.pkg.MyClass, and the new version of this class is located at /new/path/org/pkg/MyClass.class
Create a Java Agent that uses Instrumentation API to redefine the given class. Here is how the simplest agent may look like:
import java.lang.instrument.*;
import java.nio.file.*;
public class HotCodeReplace {
public static void agentmain(String args, Instrumentation instr) throws Exception {
Class oldClass = Class.forName("org.pkg.MyClass");
Path newFile = Paths.get("/new/path/org/pkg/MyClass.class");
byte[] newData = Files.readAllBytes(newFile);
instr.redefineClasses(new ClassDefinition(oldClass, newData));
}
}
Compile the above agent and pack it into .jar with the following MANIFEST.MF
Agent-Class: HotCodeReplace
Can-Redefine-Classes: true
The command to create HotCodeReplace.jar:
jar cvfm HotCodeReplace.jar MANIFEST.MF HotCodeReplace.class
Load the agent .jar into the target JVM. This can be done with Attach API or simply with jattach utility:
jattach <pid> load instrument false /path/to/HotCodeReplace.jar
More about Java agents ยป

Can Play 2.3.x be used without Activator (and with maven)?

I have two related questions here.
In Play 2.2.x, the distribution was bundled as a zip file, and available for download through the maven repository http://downloads.typesafe.com/play/2.2.x/play-2.2.x.zip. This meant that you could use a pom.xml and embed play into your app without needing to use sbt. Given 2.3.x has shifted to the activator model, is it still possible to use it with maven?
And secondly, is it possible to use play 2.3.x without activator at all? (I know they have a sbt plugin for play, but that seems very complex as well).
Thanks!
Activator is only needed to create the empty template project, which you could also do by hand if you know a bit about play. After that empty project is created all you need is sbt (which actually is a pretty central part of activator).
With play 2.3 the distribution model changed from the one big zip-file to regular ivy/maven dependencies, so you could possibly get all dependencies right from a maven project. The problem is that the sbt play setup does so much more: template compilation, routes DSL compilation, hot reloading, asset pipeline stuff, so I don't think maven actually is an option.
Yes.
Example on Github
package io.github.alancnet
import java.io.File
import play.api.{Environment, ApplicationLoader}
object PlayTest {
class Dummy{}
def main(args:Array[String]):Unit = {
def startWebServer = {
val environment = new Environment(
new File("."),
classOf[Dummy].getClassLoader,
play.api.Mode.Dev
)
val context = play.api.ApplicationLoader.createContext(environment)
val application = ApplicationLoader(context).load(context)
play.api.Play.start(application)
play.core.server.NettyServer.fromApplication(
application
)
}
startWebServer
}
}

Added jar in BootStrap location is not reflecting in My Classes using Eclipse

Please help me to understand whats wrong with this.
I added a jar in a BootStrap location of
jdk(C:\Program Files\Java\jdk1.6.0_27\lib\ext) and in jre(C:\Program
Files\Java\jre1.6.0_22\lib\ext)
but jar class is not reflecting while try to invoke methods or classes added by jar in Eclipse.
Also help me to know where I can see the printed things by static block by Logs.......
Below I included the class I used to create the JAR.
package test.classloader;
public class BootStrapTest {
static
{
System.out.println("BootStrap Jar is Loaded....................");
}
public static String checkClassLoader()
{
return "This is BootStrap Class Check ClassLoader";
}
}
I am going to take a stab at the reason behind why you think you need to do this. Excuse me if I am incorrect but you provide vague information and it is unclear what your question is.
If you need missing Java EE libs (or other 3rd party libs) in Eclipse, add one of the sofware REPOs (to your Eclipse software manager) listed on this URL and then install the Java EE libs from it: http://download.eclipse.org/tools/orbit/downloads/
Or, use Maven as a build tool and add the appropriate dependency to download the lib that your project needs.

PlayPlugin onApplicationStart does not work

I try to write a small playframework-module and a plugin in it, and want be sure that it will start when I'm starting up the application.
[myapp] -- uses --> [registration(module)].[plugin(RegistrtionPlugin)]
There is my plugin class I've put to /src/play/modules/registration int he module source
public class RegistrationPlugin extends PlayPlugin {
public void onApplicationStart() {
Logger.info("Yeeha, firstmodule started");
}
}
I have dependency to this module form my application, when i do play deps - it shows me that everything good. Or when i type in console in my app-home folder: play registration:hello - it replies me 'Hello' back.
I've got this code from PlayFramework Cook book (chapter 5), but can not make it working as I expect.
Have you added a play.plugins file to your module src folder configuring the RegistrationPlugin plugin?
The play.plugins of e.g. the spring plugins looks like this:
1000:play.modules.spring.SpringPlugin
You might also take a deeper look at the spring plugin:
At last before the module can be used following command has to be executed:
play build-module
Try to move your RegistrationPlugin to regular /app folder
and don't forget to include path to plugin in /src/play.plugins file.
f.e.
1000:RegistrationPlugin
if RegistrationPlugin is in default package

Categories

Resources