I want to concatenate two dos commands in a java program. First I want to change directory then list the files and folders in that. So I wrote that like
try
{
Process process = UI.this.rt.exec("cmd.exe /c cd C:\\Users & start dir");
process.waitFor();
InputStream in = process.getInputStream();
while (in.read() != -1) {}
}
catch (Exception e)
{
System.out.println(e);
}
But this is not working. When I execute this in desktop it is not change the directory and display the files and folders which is in the desktop. Could you please help me to fix this problem? I'm using windows 7 machine.
Thanks
Isuru Liyanage
Write the commands to a batch file on the disk and execute the batch.
If you don't want to have such a batch on the disk, create it on demand and delete it after usage.
Or just use the java build-in features to list files.
EDIT
But your code works. I tried it.
It opens a dos-box an lists the directory after changing the directory.
You can use ProcessBuilder to set the working directory of the Process you exec later.
Or, do as suggested else-thread and use the Java API for listing files in a directory, which is saner.
While creating a process you can pass a string array of commands as below:
String[] command = new String[3];
command[0] = "cmd";
command[1] = "/c";
command[2] = " cd c:\\Users && dir";
Process p = Runtime.getRuntime().exec(command);
Drop the start, it runs files in a new window. Plus as there in no cmd in the NEW command DIR won't be recognised as a command. If you must use start for some reason add cmd /c to the dir part as well.
also dir c:\users is all you actually need to do. No need or reason to change directory.
Related
I have a list of files for which I have to run the vimdiff command and save the output as a html file.I am doing this with Java. Below is the command I am trying to execute
String cmd = "vimdiff -c 'set foldlevel=9999' src/test/resources/testdata/output/html_output_before_changes/file1.html src/test/resources/testdata/output/html_output_after_changes/file2.html -c TOhtml -c 'w! different.html' -c 'qa!'"
When I run the below code, the code is getting executed. But I am not able to see the file getting generated.
Runtime rt = Runtime.getRuntime();
Process process = rt.exec(cmd);
The command is running fine when executed from a terminal. But its not working when executed inside a java program. Can someone help me with this issue? I did a lot of search but not able to proceed with this.
You're using :TOhtml and write the result as different.html. If you're not sure where to locate the file, check the current working directory of the Java process, do a file search of your hard disk, or specify an absolute path in the Vim command to be sure.
You won't see anything from Vim's operation itself. Using process.getInputStream(), you could obtain what Vim wrote to the terminal during its operation, but that would just amount to a garble of characters, as Vim is using special ANSI escape sequences to control the terminal, position the cursor, etc.
To use Vim non-interactively, it is recommended to pass the following options:
-T dumb Avoids errors in case the terminal detection goes wrong.
-n No swapfile.
-i NONE Ignore the |viminfo| file (to avoid disturbing the
user's settings).
-c 'set nomore' Suppress the more-prompt when the screen is filled
with messages or output to avoid blocking.
Without a possibility to interact with Vim (from inside your Java program), a troubleshooting tip is enabling verbose logging: You can capture a full log of a Vim session with -V20vimlog. After quitting Vim, examine the vimlog log file for errors.
After Two days I found the below Solution:
I added the vimdiff command to a shell script and executed it using the following method and it worked like a gem.
Java method
try {
File[] uiDiffDir = getFiles();
for (File file : uiDiffDir) {
String[] cmd = {"sh", shellScriptPath, file1, file2,
outputfile};
Process p = Runtime.getRuntime().exec(cmd);
p.waitFor();
BufferedReader reader = new BufferedReader(new InputStreamReader(
p.getInputStream()));
String line;
while ((line = reader.readLine()) != null) {
System.out.println(line);
}
}
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
shell.sh
vimdiff -c 'set foldlevel=9999' $1 $2 -c TOhtml -c 'w! '"$3"'' -c 'qa!'
Note:
file1 will be passed as a argument in the place of $1
file2 will be passed as a argument in the place of $2
outputfile will be passed as a argument in the place of $3
I want to execute a batch file code from java button click. Also I don't want any command prompt window to be shown all from java code.
I have a code :-
C:\xyz-3.1.1\bin>dita --input=C:/Users/india/Desktop/mobile-phone/m
obilePhone.xyz --format=pdf --output=C:/Users/india/Desktop --logfile=C:/Use
rs/india/Desktop/dofhdif.txt
So I want above code to be run from batch command with C:\xyz-3.1.1\bin> as the parent directory.
Also I want to update --input file path whenever I will choose new file from JFileChooser.
I did this from the java code on button click transform:-
ProcessBuilder pb=new ProcessBuilder("dita --input=C:/Users/india/Desktop/mobile-phone/mobilePhone.xyz --format=pdf --output=C:/Users/india/Desktop --logfile=C:/Users/india/Desktop/dofhdif.txt");
pb.redirectErrorStream(true);
Process process=pb.start();
and getting IOException error.
I get stuck over here for long time , where am I going wrong.
EDIT :- error
java.io.IOException: Cannot run program "dita --input=C:/Users/india/Desktop/mobile-phone/m
obilePhone.xyz --format=pdf --output=C:/Users/india/Desktop --logfile=C:/Use
rs/india/Desktop/dofhdif.txt": CreateProcess error=2, The system cannot find the file specified
at java.lang.ProcessBuilder.start(Unknown Source)
As the Error mentioned, it cannot locate the command because the whole string will be treated as the command by ProcessBuilder.
Try to use Runtime.getRuntime().exec directly, but you have to ensure the command dita can be found.
Process process = Runtime.getRuntime().exec("C:\xyz-3.1.1\bin>dita --input=C:/Users/india/Desktop/mobile-phone/mobilePhone.xyz --format=pdf --output=C:/Users/india/Desktop --logfile=C:/Users/india/Desktop/dofhdif.txt");
process.waitFor();
int exitCode = process.exitValue();
System.out.println(IoHelper.output(process.getInputStream())); // handle the output;
Before JDK 5.0, the only way to start a process and execute it, was to use the exec() method of the java.lang.Runtime class after which ProcessBuilder can be used to help create operating system processes.
The major improvement being that, it also acts as a holder for all those attributes that influence the process. And this is how it should be used:
ProcessBuilder pb = new ProcessBuilder("myCommand", "myArg1", "myArg2");
P.S. Actually Runtime.getRuntime().exec can also be used with String... as:
Runtime.getRuntime().exec(new String[]{"curl", "-v", "--cookie", tokenString, urlString});
My personal preference:
If you have to configure the environment for the command: to control the working directory or environment variables and also you want to execute the commands several times, you'd better use it since the ProcessBuilder will hold the settings and what you need to do is just processBuilder.start() to create another process with the same settings;
If you want to execute a whole long string command as you mentioned, you'd better just use Runtime.getRuntime().exec since you can just execute it right there without any bothering of the parameter format.
Try this:
String inputFile = ...;
String outputFile = ...;
String logFile = ...;
ProcessBuilder pb = new ProcessBuilder(
"dita",
"--input=" + inputFile,
"--format=pdf",
"--output=" + outputFile,
"--logfile=" + logFile)
.directory(new File("C:\\xyz-3.1.1\\bin"))
//.inheritIO();
.redirectErrorStream(true);
Process process = pb.start();
This shows the following points:
The command is separated from the arguments
The argument values can be determined at runtime
The command's default directory (C:\xyz-3.1.1\bin) is set before starting the process
Consider using inheritIO() instead of redirectErrorStream() if you want the process's output to appear as part of your Java application's output.
I try to execute an external jar in my java application. The .jar is in my java-package ("gui").
I tried:
String filepath = this.getClass().getResource("ServerRSS.jar").getPath();
ProcessBuilder pb = new ProcessBuilder("java", filepath);
System.out.println(filepath); results in:
/C:/Users/hox/workspace/PraktikumProg/bin/gui/ServerRSS.jar
My programm doesn't start. Could the problem be the slash before the C: ?
EDIT:
The solution was:
URL filepath = this.getClass().getResource("ServerRSS.jar");
ProcessBuilder pb;
pb = new ProcessBuilder("java", "-jar", new File(filepath.toURI()).toString());
Process p = pb.start();
First get your command working ... simply on the command line.
And only then try to run it from within Java using a ProcessBuilder.
Simple answer is probably: to use -jar when invoking java.
java someJar.jar
does not work!
And yes, that slash matters big time. You simply want a fully correct file path there.
Finally: are you really sure you want to start a new JVM in order to run a main method in some class? You see, you could do that within your current JVM - without the additional performance and complexity cost of using a second JVM!
I need to run executable progam (.exe) in java. This program have two different operating modes: GUI and Command line. The syntax to launch the program from the command line is as follows :
C:\Users\Ermanno\Desktop\ "programFolder"\"program.exe" /stext output.txt
in this way the program store the outoput in the file "output.txt".
I tired it:
Process p = new ProcessBuilder("C:\\Users\\Ermanno\\Desktop\\programFolder\\program.exe" ,"/stext a.txt").start();
does not create the output file.
I also tired to use a file batch that contains the command and run it to java but the result is the same.
You need to pass each argument in a single string:
... program.exe", "/stext", "a.txt")...
Also make sure that you start a background thread which reads the output of the child process. If there is a problem, then the child will print an error message to it's standard output and if you don't actively read it, then this output will be lost.
For this, loop over the streams p.getInputStream() and p.getErrorStream().
The latter is especially important since you say "I also tired to use a file batch". Java doesn't do anything different than a batch script. If you can't run the command from batch, it won't work from Java, either.
My experience was horrible with using the JDK ProcessBuilder and Runtime.getRuntime().exec. I then moved to Apache commons-exec. Here is an example:
String line = "AcroRd32.exe /p /h " + file.getAbsolutePath();
CommandLine cmdLine = CommandLine.parse(line);
DefaultExecutor executor = new DefaultExecutor();
int exitValue = executor.execute(cmdLine);
I solved using file bath. This file contains the command.
String [] _s = {"cmd.exe", "/c", "start", "file.bat"};
Process pr = Runtime.getRuntime().exec(_s);
I'm making an update function for my project, it's working great, until i want it to restart, basically I download the new file and replace it with the old one, and then i want to run it again, now for some reason it doesn't wna run, and i don't get any error...
Here is the complete update class:
http://dl.dropbox.com/u/38414202/Update.txt
Here is the method i'm using to run my .jar file:
String currDir = new File("(CoN).jar").getAbsolutePath();
Process runManager = Runtime.getRuntime().exec("java -jar " + currDir);
It's not clear to me, why do you need to run the jar with a call to exec() . Given that you need to run the code in the .jar file from a Java program, you could simply run the main() method as defined in the jar's manifest, and capture its output - wherever that is.
Using exec() is OK when you need to call a program from the underlying operating system, but there are easier ways to do this if both the caller and the callee are Java programs.
Now, if your jar is gonna change dynamically and you need to update your program according to a new jar, there are mechanisms for reloading its contents, for instance take a look ath this other post.
The JavaDocs for the Process class specifically point out that if you don't capture the output stream of the Process and promptly read it that the process could halt. If this is the case, then you wouldn't see the process that you started run.
I think you have to capture the stream like this :
BufferedReader stdInput = new BufferedReader(new InputStreamReader(runManager.getInputStream()),8*1024);
BufferedReader stdError = new BufferedReader(new InputStreamReader(runManager.getErrorStream()));
// read the output from the command
String s = null;
System.out.println("Here is the standard output of the command:\n");
while ((s = stdInput.readLine()) != null) {
System.out.println(s);
}
The exec function doesn't automatically lookup into the PATH to start a process, so you have to pass the complete path for the java binary.
You can do that by using the java.home system property, see this answer: ProcessBuilder - Start another process / JVM - HowTo?
No one here seemed to help me, so I went to ask my friend and I had it almost right. It abiously required the string to be an array.
solution:
String[] cmd = {"java", "-jar", currDir};
try {
Runtime.getRuntime().exec(cmd);
} catch (IOException e1) {
e1.printStackTrace();
}