Wicket configuration for nashorn - wicket

I recently upgraded my java version from java 1.7 to java 1.8. After the upgrade i am getting this error.
Caused by: ECMAScript Exception: Type Error: Can not find a common class loader for ScriptObject and My Interface.
Which version of wicket do i need to use which supports java 1.8 and nashorn script engine. Also do i need to configure anything related to Script Engine for wicket.
I have tried adding this dependency
<dependency>
<groupId>org.wicketstuff</groupId>
<artifactId>wicketstuff-nashorn</artifactId>
<version>7.4.0</version>
</dependency>
and ScriptEngineManager sem = new ScriptEngineManager();
engine = sem.getEngineByName("nashorn");
but i am still getting the same issue.
Please help me fix this issue.
Below is my method
private final ScriptEngine engine;
ScriptEngineManager sem = new ScriptEngineManager();
engine = sem.getEngineByName("nashorn");
public <K> K getNewInterface(MyScript myScript){
ScriptContext ctx = new SimpleScriptContext();
String script = myScript.getScript();
if(Strings.isEmpty(script)) {markInvalid(myScript, "Script is empty", null); return null;}
script += " (function(){return this;})();";
Object thiz;
try{
thiz = engine.eval(script, ctx);
} catch (ScriptException e){
markInvalid(myScript, "Can't execute script", e);
return null;
}
if(thiz==null) {markInvalid(myScript, "Script executed, but context is null", null); return null;}
K ret = (K) ((Invocable)engine).getInterface(thiz, myScript.getScriptInterfaceClass());
if(ret==null) {
markInvalid(myScript, "Script executed, but it's incompatible with required interface", null);
return null;
}else{
myScript.setValid(true);
return ret;
}
}

Wicket doesn't need Nashorn. You can use Wicket 1.5/6.x/7.x/8.x with Java 8.
wicketstuff-nashorn is definitely not needed to run Wicket application.
Without the actual error it is hard for us to tell why it is failing.
Update: why do you use new ScriptEngineManager(null), i.e. null ClassLoader. Better use new ScriptEngineManager() and it will use the context class loader which most probably knows about both classes. Or use new ScriptEngineManager(YourInterface.class.getClassLoader())

Related

RCP plugin retrieving classpath of the runtime project

I want to develop an editor for eclipse which works with java projects.
The plugin needs to know the resources in the classpath of the project of the open file. Since the question is quite ambigious i always find threads about the classpath of the bundle/plugin not the project edited with. Can someone tell me the right buzzword(runtime project) or share some code/links for that topic?
To be clear. This editor and its auto-completion/validation has to behave different whenever a classpath entry is added/removed same as the standard java-file editor.
With helpful hint of #howgler i figured out how to get the classpath of the IJavaProject and scan it via google reflections. Hope that help somebody in the future.
#Override
public void init(IEditorSite site, IEditorInput input) throws PartInitException {
INSTANCE = this;
super.init(site, input);
FileEditorInput fei = (FileEditorInput) input;
IFile file = fei.getFile();
IProject project = file.getProject();
try {
if (project.hasNature(JavaCore.NATURE_ID)) {
IJavaProject targetProject = JavaCore.create(project);
final IClasspathEntry[] resolvedClasspath = targetProject.getResolvedClasspath(true);
ArrayList<URL> urls = new ArrayList<>();
for (IClasspathEntry classpathEntry : resolvedClasspath) {
if (classpathEntry.getPath().toFile().isAbsolute()) {
urls.add(classpathEntry.getPath().toFile().toURI().toURL());
} else {
urls.add(new File(project.getWorkspace().getRoot().getLocation().toFile(),classpathEntry.getPath().toString()).toURI().toURL());
}
}
URLClassLoader urlCl = new URLClassLoader(urls.toArray(new URL[urls.size()]));
Reflections reflections = new Reflections(urlCl,new TypeAnnotationsScanner(),new SubTypesScanner(true));
Set<Class<?>> classes = reflections.getTypesAnnotatedWith(<???>.class);
System.out.println(classes);
}
} catch (CoreException | IOException e1) {
e1.printStackTrace();
}
}

Impossible classname for ExtensionObjects

I am using Milo to browse the capabilities of servers.
This also involves decoding ExtensionObjects (which works fine for the UnifiedAutomationReadCustomDataTypeExample).
On open62541 and milo servers it fails strangely, as ExtensionObjects cannot be cast to ExtensionObjects - please note the "[L" in the following exception:
java.lang.ClassCastException: [Lorg.eclipse.milo.opcua.stack.core.types.builtin.ExtensionObject; cannot be cast to org.eclipse.milo.opcua.stack.core.types.builtin.ExtensionObject
Is this a bug in Milo or am I missing something?
I am using the latest Eclipse to compile both Server and Client.
I am using Milo 0.2.3 from Maven.
The issue was produced by casting an Object[] to an Object. The code below now works properly.
if(rd.getDisplayName().getText().equals("OutputArguments")) {
DataValue readServiceResult = client.readValue(100, TimestampsToReturn.Both, rd.getNodeId().local().get()).get();
Variant args =readServiceResult.getValue();
NodeId ni = args.getDataType().get();
Object[] oVal = (Object[])args.getValue();
Object val = oVal[0];
if(val instanceof ExtensionObject) {
ExtensionObject eo = (ExtensionObject)oVal[0];
Object o = eo.decode();
System.out.println(o);
}
}

IArtifactRepositoryManager is null with Eclipse Oxygen 4.7.2

The following function worked perfectly in Eclipse Neon 4.6.x target runtime for a very long time:
public static boolean addRepository(IProvisioningAgent agent, String repo) {
Utils.log(String.format("adding repository at %s", repo));
IMetadataRepositoryManager metadataManager = (IMetadataRepositoryManager) agent.getService(IMetadataRepositoryManager.SERVICE_NAME);
IArtifactRepositoryManager artifactManager = (IArtifactRepositoryManager) agent.getService(IArtifactRepositoryManager.SERVICE_NAME);
if (metadataManager == null || artifactManager == null) {
Utils.log("P2Utils.addRepository - missing metadata or artifact manager");
return false;
}
try {
URI uri = new URI(repo);
metadataManager.addRepository(uri);
artifactManager.addRepository(uri);
return true;
} catch (Exception e) {
Utils.log(e);
return false;
}
}
It stopped working with Eclipse Oxygen 4.7.2 target, the artifactManager returned is always null. Does anyone involved knows what was changed and how to fix this? It breaks our updates.., I am at a loss where to look.
Got the response from eclipse forum, there were some plugins missing:
org.eclipse.equinox.p2.artifact.repository
org.eclipse.equinox.p2.transport.ecf

FOP/ikvm: error "Provider com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl not found"

I have produced a fop.dll from fop-1.0 with ikvm:
ikvmc -target:library -reference:IKVM.OpenJDK.Core.dll -recurse:{myPathToJars}\*.jar -version:1.0 -out:{myPathToJars}\fop.dll
If I use my fop.dll in a Windows Application, everything works perfect.
If I use it in a Class Library, I get the following error:
"Provider com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl not found" at javax.xml.transform.TransformerFactory.newInstance()
The code line is: TransformerFactory factory = TransformerFactory.newInstance();
Here is the code of method:
public static void xmlToPDF(String xmlPath, String xslPath, SortedList arguments, String destPdfPath)
{
java.io.File xmlfile = new java.io.File(xmlPath);
java.io.File pdffile = new java.io.File(destPdfPath);
try
{
// configure fopFactory as desired
FopFactory fopFactory = FopFactory.newInstance();
FOUserAgent foUserAgent = fopFactory.newFOUserAgent();
// configure foUserAgent as desired
// Setup output
OutputStream outputStream = new java.io.FileOutputStream(pdffile);
outputStream = new java.io.BufferedOutputStream(outputStream);
try
{
// Construct fop with desired output format
Fop fop = fopFactory.newFop("application/pdf" /*MimeConstants.MIME_PDF*/, foUserAgent, outputStream);
// Setup XSLT
TransformerFactory factory = TransformerFactory.newInstance();
java.io.File xsltfile = new java.io.File(xslPath);
Transformer transformer = factory.newTransformer(new StreamSource(xsltfile.getAbsoluteFile()));
// Set the value of a in the stylesheet
if (arguments != null)
{
IList keys = arguments.GetKeyList();
foreach (var key in keys)
{
Object value = arguments[key];
transformer.setParameter(key.ToString(), value);
}
}
// Setup input for XSLT transformation
Source src = new StreamSource(xmlfile);
// Resulting SAX events (the generated FO) must be piped through to FOP
Result res = new SAXResult(fop.getDefaultHandler());
// Start XSLT transformation and FOP processing
transformer.transform(src, res);
}
catch (Exception e1)
{
System.Console.WriteLine(e1.Message);
}
finally
{
outputStream.close();
}
}
catch (Exception ex)
{
System.Console.WriteLine(ex.Message);
}
}
I used ikvm-0.46.0.1 to make my fop.dll (based on fop 1.0). I included the following jars:
avalon-framework-4.2.0.jar
batik-all-1.7.jar
commons-io-1.3.1.jar
commons-logging-1.0.4.jar
fop.jar
serializer-2.7.0.jar
xalan-2.7.0.jar
xercesImpl-2.7.1.jar
xml-apis-1.3.04.jar
xml-apis-ext-1.3.04.jar
xmlgraphics-commons-1.4.jar
Any idea why this error occurs? Why is the behaviour different between Windows Application and Class Library?
Addition 10/19/11:
I managed to get working the following:
MyMainPrg (a Windows Forms Application)
MyFopWrapper (a Class Library that calls fop.dll)
But for my case this is not the solution, because in my target project, I have the following structure:
MainCmdLinePrg (a Console Application; calls DLL_1)
DLL_1 (calls DLLsharedFop) {there are several DLLs that can call DLLsharedFop}
DLLsharedFop (calls directly fop.dll; or - I don't care - might call MyFopWrapper)
Unfortunately this construct results in the error.
You can shorten to a pair (ACmdLinePrg,MyFopWrapper): already this does not work! But (MyMainPrg,MyFopWrapper) does...
Here is how I got that error and how I resolved:
My solultion looks like this:
ClientApp (references)--> ClassLibrary1
My ClassLibrary1 public functions are using, but not exposing any IKVM related objects, therefore the caller (ClientApp) did not have to add IKVM references. All is good in compile time.
However in runtime, the situation is different. I got the same exception and realized that ClientApp also needed to reference the correct IKVM dll (IKVM.OpenJDK.XML.Transform.dll) that contains "com.sun.org.apache.xalan.#internal.xsltc.trax" namespace.
I resolved a similar problem by adding the following before the problematic line:
var s = new com.sun.org.apache.xerces.#internal.jaxp.SAXParserFactoryImpl();
var t = new com.sun.org.apache.xalan.#internal.xsltc.trax.TransformerFactoryImpl();
As described here
Do you have the dll with the missing class in your working directory?
If you have the dll then it is a classloader problem. Look in the IKVM wiki. Often the BootClassPathAssemby help.
I was using NuGet Packages of FOP.dll v1.1.0 and IKVM pacakges of v7.1.45 in C#.NET app. I got this issue on Windows 2016 x64 server with error messages like:
------------------------------ Fop.cs (111): Provider com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl
not found - at javax.xml.transform.TransformerFactory.newInstance()
Fop.cs (125): Provider
com.sun.org.apache.xerces.internal.jaxp.SAXParserFactoryImpl not found
- at javax.xml.parsers.SAXParserFactory.newInstance()\r\n at org.apache.avalon.framework.configuration.DefaultConfigurationBuilder..ctor(Boolean
enableNamespaces)\r\n at
org.apache.avalon.framework.configuration.DefaultConfigurationBuilder..ctor()\r\n
I resolved the problem by adding those two lines at begins of procedure
com.sun.org.apache.xerces.#internal.jaxp.SAXParserFactoryImpl s = new com.sun.org.apache.xerces.#internal.jaxp.SAXParserFactoryImpl();
com.sun.org.apache.xalan.#internal.xsltc.trax.TransformerFactoryImpl t = new com.sun.org.apache.xalan.#internal.xsltc.trax.TransformerFactoryImpl();
helpful link:
https://github.com/KevM/tikaondotnet/issues/21

OSGI & Apache Commons-DBCP Classloading Issue

I inherited some code that is using the Apache commons-dbcp Connection pools in an OSGi bundle. This code works fine with Eclipse/Equinox OSGi version 3.4.3 (R34x_v20081215), commons-dbcp 1.2.2 and the postgres jdbc3 8.3.603 bundles from springsource.org.
I wanted to modernize, maybe this was my first mistake!
When I use the new version of Felix or Equinox OSGI Cores with the new postgresql JDBC3 or JDBC4 bundles along with the latest version of commons-dbcp (1.4.1), I am getting a classloading issue. I have done numerous searches and found that the commons-dbcp code should have a fix DBCP-214, but it still seems to fail.
I have tried to put the org.postgresql on the commons-dbcp MANIFEST.MF import-package line, but that did not work either.
I wrote a simple test in an activator that first does a basic class.forName() and DriverManager.getConnection(), this works fine, but when I add in BasicDataSource() and setup the connection with BasicDataSource.getConnection(), I get the ClassNotFoundException. See the code example below.
Thanks in Advance for any help, suggestions, ...
Sau!
// This one fails with an exception
public void dsTest() {
BasicDataSource bds = new BasicDataSource();
ClassLoader cl;
try {
logger.debug("ContextClassLoader: {}",
Thread.currentThread().getContextClassLoader().toString());
cl = this.getClass().getClassLoader();
logger.debug("ClassLoader: {}", cl);
if (bds.getDriverClassLoader() != null) {
logger.debug(bds.getDriverClassLoader().toString());
}
// The failure is the same with and with the setDriverClassLoader() line
bds.setDriverClassLoader(cl);
bds.setDriverClassName("org.postgresql.Driver");
bds.setUrl("jdbc:postgresql://127.0.0.1/dbname");
bds.setUsername("user");
bds.setPassword("pword");
Class.forName("org.postgresql.Driver").newInstance();
conn = bds.getConnection();
Statement st = conn.createStatement();
ResultSet rs = st.executeQuery("SELECT COUNT(*) FROM table");
conn.close();
logger.debug("Closed DataSource Test");
} catch (Exception ex) {
ex.printStackTrace();
logger.debug("Exception: {} ", ex.getMessage());
}
}
// This one works
public void managerTest() {
ClassLoader cl;
try {
cl = this.getClass().getClassLoader();
logger.debug("ClassLoader: {}", cl);
Class.forName("org.postgresql.Driver").newInstance();
String url = "jdbc:postgresql://127.0.0.1/dbname";
conn = DriverManager.getConnection(url, "user", "pword");
Statement st = conn.createStatement();
ResultSet rs = st.executeQuery("SELECT COUNT(*) FROM table");
conn.close();
logger.debug("Closed Manger Test");
} catch (Exception ex) {
ex.printStackTrace();
logger.debug("Exception: {} ", ex.getMessage());
}
}
this is due to the fact that the commons-dbcp bundle cannot look at the actual driver class, because of the osgi class loader. The solution to this is to attach a fragment to the commons-dbcp class with Dynamic Import *. The actual headers that you need in your MANIFEST are the following:
Fragment-Host: org.apache.commons.dbcp
DynamicImport-Package: *
After this, the code you mentioned worked. Hope this doesnt come too late.