I have an application using Jython 2.1.
In the app I was using jythonc to convert the python scripts to java classes and then include these classes in my webapp like any other.
So I was able to assign package name to python scripts and access these classes like any other java class.
Now I plan to migrate to Jython 2.5. Jython 2.5 has removed support for jythonc.
So I tried to use
jython -m compileall /path/to/my/python/scripts.
When I do that I get all the compiled bytecode files in the same folder. Each of the files have names like myclass$py.class (where my python file is myclass.py).
My questions -
First of all can I access these classes in another normal java
class?
If so, what is the class name I should use ? When I use it like new
myclass() my code does not compile.
Is there a way, I can assign / force a package name or class name
for the generated bytecode with compileall?
Note -
I need to upgrade to jython 2.5 because I need newer versions of
python that it supports.
I would like to stick with pre-compiling the
python code into bytecode, as I want to do optimizations on the
bytecode. So the recommended object factory method is only a
last resort. I am assuming the object factory approach will not allow
me to process the generated bytecode.
Any help is appreciated.
Related
I'd like to do the following: I have a simple function written in Clojure/ClojureScript:
(defn add
[a b]
(+ a b))
I want to wrap this function into a Java class and put it in a jar so that I can access it in an existing Java/Android project. My previous approach was to use gen-class and create an uberjar. This however leads to some problems.
As an alternative approach I considered compiling the function using ClojureScript (a solution also suggested by Sam Beran).
So far I understand how to:
compile javascript files into Java classes
put them in a .jar
Compile ClojureScript
I'm not struggling to get the ClojureScript output into a format that can be passed on to the Rhino compiler.
Any thoughts?
IMPORTANT NOTE: I do not want to create a class with a main function as is done here!
One general way of going about this would be to:
At build time:
run the ClojureScript compiler to generate a JavaScript file
put the JavaScript file into the resource directory.
compile the Java class that uses it
make a jar file (an Uberjar or a normal Unterjar)
this Java class should:
make a java class that on initialization start up Rhino
on instantiation runs the javascript from the resource.
On a desktop of server you may not get the same awesome startup times My. Beran reported on android because processes on android have the advantage of starting life with a warmed up runtime with Rhino ready to go from the moment they start (they inherit it from the Zygote process)
MATLAB is configured to search its static java class path before searching the user-modifiable dynamic path. Unfortunately, the static path contains quite a number of very old public libraries, so if you are trying to use a new version you may end up loading the wrong implementation and get errors.
For instance, the static path contains an old copy of the google-collections.jar, which has long been supplanted by Google's guava library and which has some of the same class names (e.g. com.google.common.base.Objects). As a result, if you invoke a Guava method that uses a newer method of one of such a class, you will end up getting surprising NoSuchMethodErrors because the google-collections jar is found first.
As of R2012b, MATLAB lets you specify additional jars to add to the static path by putting a javaclasspath.txt file in your preferences folder, but that adds jars to the end of the path, and doesn't let you override jars that are built into MATLAB.
So what is the best way around this?
I got an official response from Mathworks:
As of MATLAB R2013a (also in R2012b), classes can be added to the front of the static Java class path by including the following line in javaclasspath.txt:
<before>
Any directory that is after this line in javaclasspath.txt will be added to the front of the static Java class path. This is an undocumented use of javaclasspath.txt as of R2013a.
But overall in MATLAB, the ability to add classes to the front of the static Java classpath is not available through javaclasspath.txt in MATLAB 8.0 (R2012b).
MATLAB searches for classpath.txt in the following order:
In the startup directory. As of MATLAB 8.0 (R2012b) a warning will be shown if the file is found there and it will be ignored.
In the first directory on the MATLABPATH environment variable. (This environment variable is used in the bin/matlab shell script on Linux and in general is not used by the end-user).
In the toolbox/local directory.
Although the MATLABPATH environment variable of point 2 is normally not used by end-users we can use it in a workaround to allow reading a custom classpath.txt outside of the toolbox/local directory.
On Windows:
You will need to create the MATLABPATH environment variable. The first directory on it should be your directory with the custom classpath.txt AND you will also need to add the toolbox\local directory as second option. So from a cmd prompt you could do:
set MATLABPATH=c:\Users\user\Documents\myMATLABClasspath;c:\Program Files\MATLAB\R2012b
\toolbox\local
matlab.exe
One hack that appears to work is to add the jar to the top of the classpath.txt file that can be found in your MATLAB installations toolbox/local folder. Unfortunately, this is automatically generated and may get rewritten at some unspecified time, such as when you install new toolboxes, so this approach would require you to have some way to notice when this happens and reapply the hack.
If you're distributing a jar that's intended to be used with matlab, it may be better to use proguard as described at http://code.google.com/p/guava-libraries/wiki/UsingProGuardWithGuava.
If you specify that all of your classes and their (public) fields and methods are to be preserved and include guava as a program jar (not a library), then it will rename all of guava's methods and update your compiled bytecode to reference the new names.
It seems a bit hackish, but depending on the audience, it may be significantly easier than teaching your users about static vs. dynamic classpath, and it won't break any matlab code that depends on the old behavior.
Instead of obfuscating the package as suggested by #user2443532, I have found it easier to "shade" the conflicting package instead of obfuscating it - unless you actually need obfuscation. One easy way to do this is to build your package using Maven and use the maven-shade-plugin. Internal calls are modified automatically, so you don't need to modify any of the Java code.
Direct calls from Matlab will need to be modified - for example, calls to com.opensource.Class become shaded.com.opensource.Class.
For more info on shading, see What is the maven-shade-plugin used for, and why would you want to relocate Java packages?
I'm attempting to make a game library in Java that uses Lua for the scripts. The real issue appears when I try to require a Java class (that is inside of a jar), and whenever I try to do so, I get an error much like the one below:
Exception in thread "main" org.luaj.vm2.LuaError: #/C:/xampp/htdocs/LevelDesigner/Projects/Lua Test/bin/levels/Test.lua:2 module
'resources.GameLevel' not found: resources.GameLevel
no field package.preload['resources.GameLevel']
How can I require a Java class that is within a jar? Right now it seems that, with Lua, I can only require .lua files, and not .class files. This is obviously problematic as Java files are compiled down to class files...And that is what I need to require.
The answer to this question is to use luajava.bindClass as opposed to require in all of your Lua scripts.
At the build(compile) time of my project I need to do code-generation for a java class. The generated java class is a java bean class with a set of getters and setters. At the build time I am getting the name of the class and names of variables. So what I need to do is dynamically generate the java bean from the information which I have.
eg. At the compile time I am getting following data.
class-name=Test
variable-name=aaa
So the generate class should look like following.
public class Test {
public String aaa;
public void setVar(String str) {
this.aaa = str;
}
public String getVar(){
return this.aaa;
}
}
When I searched for a tool that I can use, I found Arch4j [1] interesting but the problem with that is it is not compatible with Apache 2.0 license. I am looking for a project/tool that is compatible with Apache 2.0 license.
I would appreciate if someone can give me some insight on how I can do this.
[1] - http://arch4j.sourceforge.net/components/generator/index.html
Why not just generate the .java file during your build, using a custom ant task or Maven plugin? This seems like a rather easy task which doesn't need any complex library. You could even use a template file with placeholders for the class name and the field name, and generate the real .java file using a replace task.
JET from Eclipse can be used:
http://eclipse.org/articles/Article-JET/jet_tutorial1.html
It can be called by ant: http://help.eclipse.org/helios/index.jsp?topic=/org.eclipse.jet.doc/references/ant/antTasks.xhtml
And I think from maven: http://mvnrepository.com/artifact/org.eclipse/jet/0.8.0-v20070605
Take a look at javax.tools package. You can create and load a dynamically generated class only with that package.
Just bear in mind you need the JDK available and that's not re-distributable so your customer would need to downloaded it separately ( just like you do in any IDE today )
http://download.oracle.com/javase/6/docs/api/javax/tools/package-summary.html
For instance, you can invoke the java compiler programatically with:
http://download.oracle.com/javase/6/docs/api/javax/tools/JavaCompiler.html
And you can load it with URLClassLoader
Odd suggestion, but it seems like you want to generate beans. Why not use something like apache common's DynaBean? They allow you to create beans at run time. Here is an example of using DynaBean.
Of course this is at run time and not compile time. For compile time, I would recommend using an ant task to compile your source and add a dependency for compile on generation of your classes. You can handle the classes generation by writing a small java application that uses velocity as the java class template's engine.
So your ant task on compile first calls a small java program that generates the java class files using velocity template (delete the old files in ant if needed). Then compile as normal.
I have a Windows DLL file from .NET, namely "System.Management.dll". I work with it using the code I write below:
ManagementObjectSearcher searcher =
new ManagementObjectSearcher("root\\CIMV2",
"SELECT * FROM Win32_LogicalDisk WHERE Name = 'C:'");
foreach (ManagementObject queryObj in searcher.Get())
{
Console.WriteLine("Win32_LogicalDisk instance: ");
if (queryObj["VolumeSerialNumber"] != null)
{
Console.WriteLine("Drive Name : " + queryObj["Name"]);
Console.WriteLine("VolumeSerialNumber:", queryObj["VolumeSerialNumber"]);
SysdriveSerial = queryObj["VolumeSerialNumber"].ToString();
}
}
Now I need this piece of code to be in Java. So can I do this? Without anything like c++ unmanaged code. I don't want to use c++ unmanaged code to call to this dll.
I want something like this :
public class CallToCsharp {
private static native void ManagementObjectSearcher();
public static void main(String[] args) {
System.loadLibrary("System.Management");
System.out.println("Loaded");
ManagementObjectSearcher searcher =
new ManagementObjectSearcher("root\\CIMV2",
"SELECT * FROM Win32_LogicalDisk WHERE Name = 'C:'");
}
}
Well this last code I have to put it in Java. How can I load this DLL and call the DLL to instantiate the native class in DLL and use its methods?
Update
I saw the thing, it seems it's a lot of work to do in case I have to use that class, like selecting each of them in .net Reflector and converting them to jar files. Now as per that tutorial I saw the jar files don't contain any real code to be used.
How to use it? I mean if I need to generate the jar file actually working with the code enough. How to go about it?
And aren't there any alternatives to this?
This is not an easy road you want to go down but IKVM might be able to help.
Overview
IKVM makes it possible to develop .NET applications using the Java language. Here's how it works:
Identify .NET classes you want to use in your application.
Identify which .NET dll's contain the .NET classes you identified in step 1.
Tip: If you're developing on Windows, the Microsoft .NET SDK Class Reference documentation
identifies the assembly / dll for a .NET class at the bottom of each class overview page.
Use the ikvmstub application to generate a Java jar file for each dll you identified in step 2.
The ikvmstub tool analyzes the .NET classes in the designated dll and generates a jar file
containing Java interfaces and stub classes. This information is needed by the Java source
compiler, which knows nothing about .NET assemblies.
Compile your Java source code using javac or jikes, with the ikvmstub-generated jar files on the
compiler classpath.
Compile the resulting Java classes using ikvmc. Use the -reference option to reference the dll's
containing the .NET classes you used; do not include the ikvmstub-generated jar files on the
compiler classpath.
For an example of this, see the tutorial.