How can i invoke batch file without fork in java?
I use NSSM command-line interface to install my product as windows service. I always use Runtime.exec() to operate with command-line. I bypass bytes from new process's streams and periodically check for it finish job. I wonder, if there is easy way to use command line? I don't need forked process, is there a way not to use it? I want just call some exec("command") function, which acts as simple procedure.
You cannot do the equivalent of Unix / Linux exec() syscall or the Posix shell exec command ... without forking ... in Java. It is not supported by the standard Java class libraries.
It may be possible to write a native code method to call the OS-provided native libraries to do an exec or equivalent. However, this could behave in unexpected ways (e.g. no shutdown hooks) and would definitely be non-portable. And in the case of Windows, I don't think it is possible to do the equivalent of UNIX exec without fork: source Wikipedia.
However, you can easily run a batch file from Java:
How do I run a batch file from my Java Application?
But I don't understand the point of doing an exec to run a batch file instead of the normal fork / exec ... which is what Runtime.exec() does under the covers. Perhaps if you explained, we could understand why you need to do it, and offer a suggestion.
Related
I'm looking for a solution capable of doing this on Java:
Spawn a process.
Suspend it (like kill -STOP does in Linux).
Continue a suspended process (like kill -CONT in Linux).
Read/Write their standard input/output pipes at runtime.
Working on (at least) Linux and Windows.
As far as I know, the Java standar only implements first and fourth, but not the second neither the third.
What could I do?
There is no way of doing "directly" from Java.
You will need to do something specific for Windows / Linux, in each case executing an external program, or invoking native code.
On Linux, you can use kill as you suggest.
On Windows, you can call SuspendThread(), or maybe you can launch the SysInternals tool 'PsSuspend'. There is some information that may help you here:
How to pause / resume any external process under Windows?
How to suspend/resume a process in Windows?
If you wish to invoke native code from Java, JNIWrapper may help you.
Also, if you need the PIDs of the spawned processes, then you may need to launch them via native code also, as Java will not give you their PIDs.
Goal: I have client-server program in which client and server runs in different jvms.
To test the same, I want to invoke the Server in a different JVM programatically and then use current jvm to run the client and execute different C/S tests.
Is there any way I can execute a method or run Java commands in different jvm programatically?
1) The most powerful tool in java to run process is ProcessBuilder:
ProcessBuilder pb = new ProcessBuilder("java", "-server", "-jar", "yourJar.jar");
Process p = pb.start();
Than using Process you are able to manipulate child process e.g. read InputStream, destroy e.t.c.
2) If you are able to edit both source code review this question to build efficient communication between JVM on the same host.
If you cannot change code, simply create own loader which load Server and implements inter JVM communication and invoke methods you need, because it in the same JVM space.
You can run virtually any command which you otherwise run manually using
Runtime.getRuntime().exec(command);
For more refer to Runtime.getRuntime().exec(...) documentation.
But also note that running any platform specific command using exec will rob your program its platform independent nature.
Sometime back I saw someone using "mv" to move a file. That made the entire program to Unix-based OS specific. Charm of Java or any virtual machine based language is its platform independent nature.
You can use command line:
Runtime.getRuntime().exec("java -server MyServer")
or if you want to build some more complicated call just use http://commons.apache.org/exec/ to build and run program.
From what I know, this is not possible with plain java. Probably grid enabled frameworks could provide a way of running a java program on multiple JVMs. A similar problem was resolved here:
how-to-run-a-java-file-project-in-remote-jvm-which-is-present-in-other-network
We Have a Multi-threaded Application in JAVA which has multiple threads running in parallel. Now we want to run all these threads on a single core. Currently application is running on a system having more then one Cores.
We know there is a technique available ProcesAffinity in .Net Framework to set process affinity.
But we don't want to depend on .Net Framework, because our application is build in java.
Do we set Process affinity using Bat file and run our application executable jar file through Bat file?
Currently our application is running on Window XP. So we need a solution that should be working fine on XP platform.
EDIT:
It's possible: See Java thread affinity
Pure Java doesn't support running a thread on specific processor. Check the SO question linked above.
Personally, I don't think that the fact that this cannot be set in pure Java is a bad thing, as to me, how an app is run does very much depend on the OS, so therefore a OS-specific solution isn't a bad thing.
You can use the MS psexec utility to set the affinity:
psexec -a 1 java -jar myapplication.jar
Would instruct that all of the threads created by java would be run on the lowest CPU.
And this line would be your .BAT file...
You cannot do it in pure Java. But on some versions of Windows, you can do it via operating system utilities; see https://superuser.com/questions/309617/how-to-limit-a-process-to-a-single-cpu-core ... and you might be able to do this by calling native libraries via JNI.
I have a matlab script that takes an input mat file and produces an output file.
Currently I have a shell script that is able to execute this script.
I am executing this script from Java using ProcessBuilder class and all is working well.
I need to perform the matlab script execution very often from java and each time script executes the mcr process is created, script executes and mcr terminates.
i like to have the MCR process open and have a matlab session open towards java , so that same process is kept alive so i can execute scripts multiple times in the same session.
I find matlabcontrol seems to be suitablefor this.
How to configure the MatlabProxyFactory with the MCR location and LD_LIBRARY_PATH
which i am setting in my shell script and execute my script in a same session?
I also came across a tool MATLAB JA Builder but i cannot use this at the moment as its not Free.
Thanks!
If you are using matlabcontrol I don't think you need the shell script, just tell it the name of the m-file you want to be run. If you want to keep the shell script in conjunction with a ProcessBuilder, you have to start the process once and keep a reference to its input stream. When you want a command executed, you write it that stream. Also, you have to keep a thread alive to empty the output and error streams of Matlab, otherwise they will get full and Matlab will hang. If you want to go with this, I recommend looking at the source of this project (which I am a contributor to). The class you are interested in is RCaller. It does more or less the same, except it invokes R and not matlab.
Just wondering, if there is something better, newer, safer, faster, etc than Runtime.getRuntime().exec().
I want to run another process from my application on linux, and this is the only way i know how. Would be nice to have an alternative.
How about ProcessBuilder?
A bit more:
Introduced in Java 1.5, allows you to gain more control on the process environment - set the working directory, let you redirect the error stream to the input stream (from java POV) and a few more things.
From Oracle's site:
ProcessBuilder - The new ProcessBuilder class provides a more
convenient way to invoke subprocesses than does Runtime.exec. In
particular, ProcessBuilder makes it easy to start a subprocess with a
modified process environment (that is, one based on the parent's
process environment, but with a few changes).