How to use installed plugin in a java project in Eclipse? - eclipse-plugin

I have created one java project with 'project_p' with three packages a, b and c.
In package 'a', I have class 'A', method 'action' which prints: "inside class A". In package b, class B, method 'boxing' which prints: "inside class B". In package 'c', class 'C', method 'catching' - this prints: "inside class C" and also calls 'action' and 'boxing'. There is no main method in any class.
project_p
|
src
|
|
-> a --> class A --> method action --> System.out.println("inside class A.");
|
|
-> b --> class B --> method boxing --> System.out.println("inside class B.");
|
|
-> c --> class C --> method catching --> System.out.println("inside class C.");
A aobj = new A();
aobj.action();
B.boxing();
Then, I created a jar of 'project_p' with all the three packages.
Used that jar to create a plugin 'project_plugin', created the feature 'project_plugin_feature' and update site 'project_plugin_site' for the plugin.
Then installed that plugin to Eclipse using Help --> Install new software.
Now, I have created another java project 'project_plugin_usage' with one package 'abc', class ABC. There is one main method inside class ABC.
My question is - How can I use that installed plugin in the project 'project_plugin_usage' so that I could call method 'action', 'boxing', and 'catching' in the main method of 'project_plugin_usage'?

A plain Java project cannot use code in a plug-in. Only another plug-in can access the code.
For plug-ins: the plug-in providing the code must declare the packages that it makes available in a Export-Package statement in its MANIFEST.MF.
For example:
Export-Package: greg.music.core.autoclose,
greg.music.core.bool
exports two packages.
If the plug-in wants to export packages from a jar included in the plug-in it must include the jar in the Bundle-ClassPath in the MANIFEST.MF
The plug-in which wants to use the packages must add the source plug-in to the Require-Bundle statement in its MANIFEST.MF
Require-Bundle: pluginid

Related

Proguard does not find basic packages and super class

I used to use proguard 5 on java 8, but as I now use Java 11, I've downloaded proguard 6.1.1, but I've encountered issues.
1 - Lot of warnings are generated because proguard does not find basic classes present in java.awt or java.lang:
Warning: ...: can't find referenced class java.awt.image.BufferedImage
Warning: ...: can't find referenced class javax.swing.JPanel
Warning: ...: can't find referenced class java.lang.management.ManagementFactory
I can remove all the warning by adding a global or specifics -dontwarn, but I don't think it's ideal. Is there a better solution?
2 - If I remove the warnings, with the option -dontwarn, an error is generated:
Unexpected error while performing partial evaluation:
Class = [...]
Method = [<init>()V]
Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [softwares/progeria/nuclei/NucleiLabeling] (with 1 known super classes) and [java/lang/InterruptedException] (with 4 known super classes))
Unexpected error while preverifying:
Class = [...]
Method = [<init>()V]
Exception = [java.lang.IllegalArgumentException] (Can't find common super class of [...] (with 1 known super classes) and [java/lang/InterruptedException] (with 4 known super classes))
Error: Can't find common super class of [...] (with 1 known super classes) and [java/lang/InterruptedException] (with 4 known super classes)
The class that generates this error extends a JFrame and runs perfectly. How can I fix this error?
Your application depends on various runtime libraries which you need to tell ProGuard about.
Prior to Java 8, all of the built-in java libraries such as AWT, Swing etc. were bundled together in rt.jar. You would have supplied something like the following parameter to ProGuard:
-libraryjars <java.home>/lib/rt.jar
or if using Ant:
<libraryjar file="${java.home}/jre/lib/rt.jar" />
Since Java 9, these runtime libraries are packaged as a number of jmod files under <java.home>/jmods. As a minimum you will probably need:
-libraryjars <java.home>/jmods/java.base.jmod(!**.jar;!module-info.class)
or if using Ant:
<libraryjar file="${java.home}/jmods/java.base.jmod(!**.jar;!module-info.class)" />
However this will not include AWT or Swing, which are now in java.desktop.jmod. Precisely which of the jmods you need to link will depend on which Java runtime libraries your application makes use of.
In your case it looks like you need
-libraryjars <java.home>/jmods/java.base.jmod(!**.jar;!module-info.class)
-libraryjars <java.home>/jmods/java.destop.jmod(!**.jar;!module-info.class)
-libraryjars <java.home>/jmods/java.management.jmod(!**.jar;!module-info.class)
or
<libraryjar file="${java.home}/jmods/java.base.jmod" jarfilter="!**.jar" filter="!module-info.class" />
<libraryjar file="${java.home}/jmods/java.desktop.jmod" jarfilter="!**.jar" filter="!module-info.class" />
<libraryjar file="${java.home}/jmods/java.management.jmod" jarfilter="!**.jar" filter="!module-info.class" />
A web search for jmod <some class or package> or simply JDK Module Summary should help you identify any others you might need.
Note: If there is no <java.home>/jmods folder, and you use openjdk please note that there's a separate package for it search for java-11-openjdk-jmods to install the right package

Kotlin Script Engine throws "unresolved reference", even if the package and class is valid

When using Kotlin's Script Engine, trying to import packages or use any class throws an "unresolved reference"
javax.script.ScriptException: error: unresolved reference: mrpowergamerbr
fun loritta(context: com.mrpowergamerbr.loritta.commands.CommandContext) {
^
This doesn't happen when running the class within IntelliJ IDEA, however it does happen when running the class on production.
While this YouTrack issue is related to fat JARs, this also can happen if you aren't using fat JARs (loading all the libraries via the startup classpath option or the Class-Path manifest option)
To fix this, or you can all your dependencies on your startup script like this:
-Dkotlin.script.classpath=jar1:jar2:jar3:jar4
Example:
java -Dkotlin.script.classpath=libs/dependency1.jar:libs/dependency2.jar:yourjar.jar -jar yourjar.jar
Or, if you prefer, set the property via code, using your Class-Path manifest option.
val path = this::class.java.protectionDomain.codeSource.location.path
val jar = JarFile(path)
val mf = jar.manifest
val mattr = mf.mainAttributes
// Yes, you SHOULD USE Attributes.Name.CLASS_PATH! Don't try using "Class-Path", it won't work!
val manifestClassPath = mattr[Attributes.Name.CLASS_PATH] as String
// The format within the Class-Path attribute is different than the one expected by the property, so let's fix it!
// By the way, don't forget to append your original JAR at the end of the string!
val propClassPath = manifestClassPath.replace(" ", ":") + ":Loritta-0.0.1-SNAPSHOT.jar"
// Now we set it to our own classpath
System.setProperty("kotlin.script.classpath", propClassPath)
While I didn't test this yet, in another unrelated answer it seems you can also supply your own classpath if you initialize the KotlinJsr223JvmLocalScriptEngine object yourself (as seen here)

NameNotFoundException injecting EJB in JAX-RS Resouce

I've been trying to inject an EJB into a JAX-RS resource via InitialContext()lookup() getting the following exception:
<javax.naming.NameNotFoundException: While trying to look up
comp/env/AServiceLocal
in /app/webapp/wcc/1377099157.; remaining name 'comp/env/AServiceLocal'>
My lookup in resource constructor:
try {
initialContext = new InitialContext();
String jndiSubcontext = "java:comp/env/";
aService = (AServiceLocal) initialContext.lookup(jndiSubcontext+AServiceLocal.class.getSimpleName());
eSService = (ESServiceLocal) initialContext.lookup(jndiSubcontext+ESServiceLocal.class.getSimpleName());
eService = (EServiceLocal) initialContext.lookup(jndiSubcontext+EServiceLocal.class.getSimpleName());
} catch (NamingException e) {
e.printStackTrace();
}
Here's the file structure taking into account that they are all maven projects:
global
|
--shared
|
|---src/main/java/com/x/y/z/AServiceLocal.java (ejb)
|
--war-project
|
|--src/main/java/comm/x/y/z/TheResource.java (jax-rs)
There are more maven projects related and they are all maven-configured through the global project in a hierarchical way.
There is also a resource in the same project as war-project that also performs lookups to the shared project and they do work.
I don't understand what the problem is.
edit
After adding ejb-local-ref to deployment descriptor:
<ejb-local-ref>
<ejb-ref-name>AServiceLocal</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<local>com.x.y.service.AdminXProfileServiceLocal</local>
<ejb-link>shared.jar#AdminXProfileService</ejb-link>
</ejb-local-ref>
I get the following error:
[J2EE:160101]Error: The ejb-link "shared.jar#AService"
declared in the ejb-ref or ejb-local-ref "AServiceLocal"
in the application module "xyz-99.1.0-SNAPSHOT.war" could not be
resolved. The target EJB for the ejb-ref could not be found. Ensure
that the link is correct.
The jar shared.jar is a dependency of the war project, but it seems that location is not correct. Must I add the packages also to the ejb-link ?
Something like: <ejb-link>shared.jar#com.x.y.ServiceImpl</ejb-link>
I aslo need to point out that there is a mix of hk2,cdi and lookups as part of the injection due to the fact the project is quite old and also it was migrated to weblogic 12c version recently so normal #Inject or #EJB don't appear to be working.
If I take into account all the variables I am seeing like Maven, project structure, JNDI lookup etc... the best way is to add an entry in the web.xml of the war project referencing your ejbs.
<ejb-local-ref>
<ejb-ref-name>ejb/adminXProfileService</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<local>com.myapp.ejb.AdminXProfileServiceLocal</local>
<ejb-link>YourEJBLibrary.jar#adminXProfileService</ejb-link>
</ejb-local-ref>
Then in your lookup you simply look for:
contenxt.lookup("java:comp/env/ejb/adminXProfileService");

facing issues while loading bean defined in cache.xml of another .jar file

Background : I have two projects, proj A and proj B. Now, in proj A i have a cache.xml file , a java bean(say customer bean), a repository class(RecordRepository). I am loading the repository class in the cache.xml
Cache.xml
</gfe:client-region>
<!--Scan for annotated GemFire Repositories-->
<gfe-data:repositories base-package="cache.repository" />
In proj B, I import the jar of proj A and then try to load the bean and the repository.
My goal is to create an object of customer bean and then call the repository class to save the customer bean.
Employee emp = (Employee)facilityCacheLoader.getRegionBean();
emp.setRecordId("2001");
emp.setRecordString("record string 2002");
// update the Bean and save
RecordRepository rep = (RecordRepository)facilityCacheLoader.getRepository();
rep.save(emp);
But I am getting the following exception:
Exception in thread "main" org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [cache.repository.RecordRepository] is defined
at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBean(DefaultListableBeanFactory.java:296)
at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:1125)
at com.rxc.cacheclient.CacheLoaderClient.main(CacheLoaderClient.java:40)
What do you mean by?
In proj B, I import the jar of proj A and then try to load the bean and the repository.
And specifically... "I 'import' the jar of proj A"?
Effectively, proj A's JAR file must be on the classpath of the application created by proj B, assuming, of course, cache.repository.RecordRepository is the fully qualified class name (FQCN) of the Repository class defined in proj A, and which you expect to be picked up in Spring's classpath component scanning, used by SD's infrastructure to locate application-defined Repositories (such as your RecordRepository) in proj B's application, i.e. ...
<!--Scan for annotated GemFire Repositories-->
<gfe-data:repositories base-package="cache.repository" />
Perhaps you could share a GitHub project with you application code and configuration
Thanks!
-John

Grails Currencies Plugin: Unable to resolve class Money

I installed the grails currency plugin. I want to use the Money type in my grails domain class as such:
class FOO{
...
Money lunchCost = new Money(amount:0.00, currency:'USD')
Money dinnerCost = new Money(amount:0.00, currency:'USD')
...
}
I get an error when I compile saying "unable to resolve class Money". I traced the package heirchy of the Grails Money Plugin and tried to put in:
cr.co.arquetipos.currencies.Money breakfastCost = new cr.co.arquetipos.currencies.Money(amount:0.00, currency:'USD')
---- That didn't work either.
1) When I generated Foo, grails placed the domain class under "projectName.Foo" as it does for every domain class created.
2) I'm using Grails 1.3.5.
Do you have any ideas as to where the Currencies class is so I can include it in the
"import <....Money> and get rid of this compilation error?
Same here: The plugin does not integrate with the Grails project, at all. Nevertheless, it has been installed to ${user.home}/.grails/1.3.5/projects/${project.name}/plugins/currencies-0.3.
Since the plugin has been last updated in 2008 and doesn't cover too much functionality, I'd suggest to just copy the two domain classes (in the grails-app/domain folder) into your project.
For an evaluation, you may also want to have a brief look at grails-app/conf and test/integration in the plugin's installation folder.
Like ataylor says, don't use this plugin, it's broken. Instead use JScience. Checkout: Best practice to represent Money (value + currency) in Grails