I want to initialize my external jar library when the JVM starts without a method call. Is there A way I can get a "On JVM Startup" method invoked in an external jar?
There is no way to do it without initializing the class where you have "On JVM Startup". Your best chance to do so is by creating "On JVM Startup" as a static method and calling it from the static block of the class. But static block will be called when the class is first referred, so you need to refer your class at the startup. Otherwise JVM can only load your class but cannot call any of its method without being referred.
But if you are working on a webapp then you can call an init method in a servlet when servlet is configured as load on startup.
Hope it helps!
Related
I am getting following exception when trying to call feature file of another module from different module with logs as,
org.graalvm.polyglot.PolyglotException: TypeError: Access to host class utils.Utils is not allowed or does not exist.
Following is the file which I am trying to run as,
https://github.com/bipin-k/karate-automation/blob/master/sample-automation/src/main/java/sample.feature
https://github.com/bipin-k/karate-automation
karate error description
Please read this answer for hints on how to handle re-use across Java modules: https://stackoverflow.com/a/58339662/143475
Recommendation is to avoid it as far as possible. And things like call read('../../../../core-utilities/src/main/java/java-functions-calls.feature') lead to un-maintainable tests: https://stackoverflow.com/a/54126724/143475
Most likely the problem is because in the project where you make the call - the utils.Utils class is simply not on the Java "classpath". You should probably take the help of someone who knows Java well, or stick to a simpler "single module" Java project.
A related problem: Get the class path from the context class loader (of WebLogic for instance)
This is already solved in How to set up the context class loader's classpath for runtime compilation?.
Current problem: Get the same (proper) class path used to run a web app
Reflectively calling the "getClassPath()" method works but it returns a dirty classpath containing unanted modules from $ORACLE_HOME/oracle_common/modules directory.
Problematic scenario:
Deploy a web app "Parent" in WebLogic // <- works
Get the context class path (it's a String object) by reflexively calling "getClassPath()" // <- works
Fork a process out of the main "Parent" process and run it using the context class path // <- fails
04:36:45,238 [Thread-41] ERROR ChildProcess - Exception in thread "main" java.lang.NoSuchMethodError: com.fasterxml.jackson.databind.ObjectMapp
er.configOverride(Ljava/lang/Class;)Lcom/fasterxml/jackson/databind/cfg/MutableConfigOverride;
Explanation
While the context class path contains the necessary dependencies for the child process to run, they are overshadowed by WebLogic's own dependencies. The result is runtime failures such as the one shown above.
Workaround
a) Use a new version of WebLogic server that hopefully would use newer versions of the artifacts needed by the child process // risky endeavour
b) Manually process the context class path and remove any artifact that would shadow their more-recent counterparts
Solution b) looks more practical, but I don't like it for meany reasons:
The reflexive call to "getClassPath" returns a String, and looking for artifact's names in Strings feels frail and weak
I wouldn't know what shadows what. WebLogic prepends its weird artifacts at the start of the string before listing the web app's own dependencies.
Only weblogic.xml has info on the web app's package preferences. I wish I could mimic how WebLogic processes this file to run the web app (Parent) and use that to properly run the child process
It seems to me that forking a process out from a web app running in WebLogic does not enjoy the same package preferences expressed in "weblogic.xml" that the web app (Parent) enjoyed when it was deployed and started running.
Other than the above suggestions, I am welcoming of any stronger solutions
I am using Java 1.8.0_144, Eclipse (Oxygen) and RunJettyRun plugin on Windows to test my web application. When I modify the Java code in a non-static method (not change to the method signature or adding a new method), the change does not get reflected unless I shut down and resart RunJettyRun. I did some configuration as shown below, but it was not working.
How can I see code change effective without shutting down RunJettyRun?
I'm using play application (using Play version 2.1.0) with RabbitMQ and do not have any view component.
So i would like to invoke this play application without hitting the execution URL (http://localhost:9000/<routing_info>) on server startup.
Would also like to know if there is any way in Play 2.1.0 version to run the application on server startup, i mean bootstrapping. Is this option available in play 2.1.0.
As i've read through the documentation its mentioned only for 1.2 version.
Please help!!
Play allows you to define a 'global' object which will be instantiated automatically by Play when the application starts.
In application.conf you should find the following:
# Global object class
# ~~~~~
# Define the Global object class for this application.
# Default to Global in the root package.
application.global=global.Global
On a new play application, this line is commented out. I've uncommented it and made it point to an object called Global in the global package. You can make it what ever you want.
Your global object should extend GlobalSettings.
In my applications, I use a static initialiser block to run code when that class is loaded:
public class Global extends GlobalSettings
{
static
{
...
}
}
When using JUnit we pass the directory used for logging as a JVM property. This works fine on the command line and in Eclipse. However, it doesn't work when we pass the same property to the Buildr test task.
test.using :properties => { :"server.name" => "tester", :"log.dir" => log_dir}
We know why this happening. The property is being set from inside the JVM rather than outside. This means that at run time (when the static logging class is loaded) the property is not yet set. If we query the property later (say from within a unit test) then we see that it is set correctly.
Does anyone know of a workaround?
BTW, we're using log4J but the question is applicable to any static class that needs access to a JVM property set by Buildr.
Assuming that you are using JUnit, you can ensure that the tests run in a forked JVM via
test.using :fork => :once
However I thought that was the default behaviour? Are you overriding this somehow? (See http://buildr.apache.org/languages.html)
this code defines the log.dir in the log4j.properties file and sets it in the buildfile via
test.using :properties => { :"log.dir" => '/tmp'}
my setup is
buildr 1.4.7
ruby 1.9.3
hth