Dear all
I want to execute a EXE file in Java, but I was not able to do it correctly.
Originally, in DOS command prompt, my command is like this:
C:>\crf_test.exe model <inputfile.txt> outputfile.txt
Note: the input file name must be place in the brackets <>. It always gave me good results when run it in DOS window.
When I want my java program to call above command, I do like this:
Process p = Runtime.getRuntime().exec("crf_test.exe model <inputfile.txt> outputfile.txt");
However, the output of this command is "no such file or directory: "
I guest Java doesn't like the brackets <> in DOS command. I also remove <> out, but exe file did not accept that.
So now how can I deal with this problem? Please give me a sollution
Thank you much much
There are potentially two problems. Firstly, the one that others have mentioned - crf_test.exe may not be in your path. It's hard to tell whether your output of "no such file or directory" is from crf_test.exe or from Java trying to find crf_test.exe.
Secondly though, running it from DOS you're not really putting the filename in brackets - you're redirecting system input from the input file to the output file, so the logical grouping is:
crf_test.exe model < inputfile.txt > outputfile.txt
Now when you're running it from Java, it's genuinely trying to pass <inputfile.txt> as a second command-line argument, and outputfile.txt as a third. My guess is that crf_test.exe is then trying to load those as files, and giving "no such file or directory" as an error.
You'll need to load the data from inputfile.txt yourself and pass it in via Process.getOutputStream, and then read the output from Process.getInputStream and write it to outputfile.txt.
Alternatively, you could run cmd.exe and pass in the whole command as an argument - that way the shell will perform the redirection for you as if you were running from a DOS prompt.
The angle brackets are redirection operators: <inputfile.txt causes the input to be read in from inputfile.txt instead of the keyboard, >outputfile.txt causes the output to be written to outputfile.txt instead of the screen. This facility is provided by the shell, however when invoking your program with the Java runtime the shell is not present. Invoke via the shell, like this:
Runtime.getRuntime().exec("cmd /c crf_test.exe model <inputfile.txt> outputfile.txt");
...or redirect input and output using facilities provided by Java; see e.g. this question.
try this
Process p = Runtime.getRuntime().exec("crf_test.exe","/c","model outputfile.txt");
The problem is that the crf_test.ext is missing in your current execution folder. You need either copy the executable or use the absolute path or set the PATH variable to include the necessary path.
If I understand the problem right, you want to call
crf_test.exe model
with input from file inputfile.txt and output to outputfile.txt
You have to redrect in and out and call only crf_test.exe model. How do redirect in and out is described in how to redirect stdin to java Runtime.exec ?
Related
I am a high school student working on a project that will convert the video from a YouTube link into an MP3 and download it. However, the way that the video form YouTube is downloaded and converted is through the Mac OS terminal by using YouTube-dl.
This is what I put into the terminal:
youtube-dl -f bestvideo+bestaudio \"ytsearch:{https://www.youtube.com/watch?v=5X-Mrc2l1d0}\"
This works in terminal, but when I try to use:
Runtime.getRuntime().exec("cd /Users/poppa/Desktop/IA Vids");
and there's an error saying "No such file or directory"
Another Problem that I am having is running the code that is inputted into the Terminal from Java. I'm using IntelliJ IDEA if that helps. Thank You!
You have a space in the directory path. Try putting double quotes around like this:
Runtime.getRuntime().exec("cd \"/Users/zeidakel/Desktop/IA Vids\"");
Also note that executing cd command from JVM may have no effect on current user dir when (for example) creating files with new File("path")
If cd means change directory (and isn't the name of an executable), then it almost certainly won't take effect, even if it is executed correctly. The process spawned by exec() will have a working directory, and it can be changed -- but that change will only affect the spawned process.
In addition, having spaces in arguments to exec() is inherently problematic. exec() is not a shell, and you won't be able to protect the string from being split at the spaces by using shell mechanisms like quotes. Instead, you need to split the command into arguments yourself, knowing where the splits should be, and then use the form of exec() that takes a String[] as input. That is, split the arguments into an array of strings yourself, rather than relying on exec() to do it for you (wrongly).
Runtime.exec() is fraught with difficulties, and needs very careful handling. I've written extensively about this subject here:
http://kevinboone.me/exec.html
I have a shell script which I'm trying to call from Java. The shell script contains:
cat /dev/tty.USB0 > file.txt
In my Java code I am using:
Process p= Runtime.getRuntime().exec("/home/myname/Scrivania/capture.sh");
But it does not work. When I run it from the terminal it works as expected.
You can't directly execute a .sh script like this, since it's not an executable. Instead, you have to run /bin/sh -c /home/myname/Scrivania/capture.sh instead.
First of all, it's not a good style to work with OS-based features in Java code. Instead of that i suggest you to work with system input/output streams only. For example if your program should handle output of your script, you can do something like:
cat /dev/tty.USB0 > java YourMainClass
and then work directly with System.in.
Even if your program is more complicated than script output consumer, you can rewrite it to remove all OS-based parts from your program, it'll make your code more stable and maintainable.
What you are doing works. Well, it should.
My guess as to what is/seems wrong is this: You might be looking for the output file "file.txt" in the wrong place.
Here's a little experiment
System.out.println("Output file - " + new File("file.txt"));
Process p= Runtime.getRuntime().exec("/home/myname/Scrivania/capture.sh");
The first line should tell you where to look for your file.
P.S. Of course, do remember to import java.io.File :)
Curious little issue I am running into here:
I would like a client to be able to do something like:
(1) java -jar myJar.jar inputFile outputFile
or
(2) java -jar myJar.jar text outputFile
outputFile is an optional argument.
Essentially (1) will read input from a file for them, while (2) they provide the input my program will use directly. There is no way to determine whether or not the argument is the input or whether it is the location of the file though that I can think of. For normal command line stuff you would specify a flag like -i inputfile to show you want it to read from a file. What are my options here that maintain ease of use for the client?
Is my only option to create a syntax the client must use for the first argument? i.e.
"-t text" or "-i inputFile"?
I have seen libraries such as commons cli which would enable this, but I would prefer a solution that does not involve using a library.
If I understood the problem correctly, can't you just check the number of arguments instead of explicitly specifying direct input? Like, if one arg is passed the first arg is output, and if 2 args are passed then the first arg is input and the second arg is output?
With that being said - Using a 'option' syntax of the hyphen- kind is probably easiest on most people used to a cli.
I would suggest to read from standard input (System.in) and print to standard out (System.out)
This way, no parameters are required. It's very intuitive for people who work with CLI tools. And you can leave the details of where the input comes from to the OS.
So in a unix OS, you would use your jar something like this:
echo "some test" | java -jar myjar.jar > outfile
or
cat somefile | java -jar myjar.jar > outfile
You can use
input=text or file=inputfile
(with output=outputFile as optional).
In this case, you can treat all your parameters in the same way and split them with the delimiter '=', check the left side of '=' to determine which parameter it is.
I have to execute a xyz.cmd file which is in a directory E:/abc. So the absolute path of the file to be executed is E:/abc/xyz.cmd. When executed, a new window is created by the file itself.
My code snippet is:-
String path = “E:\\abc”;
String cmd = path + “\\xyz.cmd”;
ProcessBuilder processBuilder = new ProcessBuilder(cmd);
processBuilder.redirectErrorStream(true);
processBuilder.directory(new File(path));
processBuilder.start();
This does not work, but gives no error or exception. But the cmd file works fine, it can be executed manually from its directory using explorer or cmd-prompt.
Tried using different versions of jdk, but in vain. I am using windows 7 OS. I do not see the process running in the Task Manager also.
Any idea what is going wrong? The same code works fine in a different computer with the same config.
===EDIT====
Can this be a security issue? Something like the user executing the program is not having enough priveleges to execute a file?
You need to call cmd.exe as first part of your process builder String in order for the command processor to be able to call the .cmd file. This is also true for .bat files, or any OS type command. For example, please look here.
Also, please look here: When Runtime.exec() won't
Edit
You state:
please understand, this is not the problem of not adding cmd.exe in the processbuilder; because of the previous commands, cmd.exe will be taken care.
I see no documentation in your posts so far that this is true, and all my experience strongly suggests otherwise.
You also state:
Can this be a security issue? Something like the user executing the program is not having enough priveleges to execute a file?
No way to know unless you capture and display the process's input stream. In fact if you don't capture this stream, you could prevent your process from functioning at all. Often we have to also capture the error stream as well, but you've combined them with
processBuilder.redirectErrorStream(true)
Please read my "When Runtime.exec() won't" link above for more on the necessity of capturing streams.
I currently have the following batch script I want to run from my Java program:
"C:\Program
Files\Java\jdk1.6.0_25\bin\java.exe"
-classpath "D:..."
Main >
"...\result.out"
Now, I've done a simple
Runtime.getRuntime().exec(command);
where command is that string I have shown above. The problem is that it is simply calling java.exe with the shown arguments, instead of calling the console with the given arguments. The difference is subtle, for if it is calling directly java.exe it will ignore the redirect of the output stream!
Is there a easy way to do this? I've tried prefixing command with "cmd " but that didn't seem to help.
I'd like to stay away from having to read the output stream and then having to manually save this to a file.
Thanks
To solve the issue,
cmd /c "command"
is enough.
Process proc = Runtime.getRuntime().exec("acpi -b");
Now you can use proc.getInputStream() and proc.getOutputStream() like any normal input and output streams.
You can then write the contents to your output file.
This is the method I mostly use.