Java - Run & use .bat file - java

I have a file generateK.bat, which generate key randomally.
I have two question:
How can I run .bat file in java enviroment? I saw only instruction of edit the .bat file, but not run it.
I want to use the key in my program. How can I use the output in java?
Thanks.

I would use Runtime.exec to exec an external program :
http://docs.oracle.com/javase/1.4.2/docs/api/java/lang/Runtime.html
You will then have a Process with input and output streams that you can read/write to.
Code will look like this :
public static void main(String Argv[]) {
try {
String ls_str;
Process ls_proc = Runtime.getRuntime().exec("pathtoyourbat/generateK.bat");
// get its output (your input) stream
DataInputStream ls_in = new DataInputStream(
ls_proc.getInputStream());
try {
while ((ls_str = ls_in.readLine()) != null) {
System.out.println(ls_str);
}
} catch (IOException e) {
System.exit(0);
}
} catch (IOException e1) {
System.err.println(e1);
System.exit(1);
}
System.exit(0);
}
=> http://www.ensta-paristech.fr/~diam/java/online/io/javazine.html
There are however plenty of tutorials about running external app inside java

How can I run .bat file in java enviroment? I saw only instruction of edit the .bat file, but not run it.
Use Following piece of code to run your batch file.
Runtime.getRuntime().exec("cmd /c start abc.bat");
Estragon already posted answer for 2 .

From java, Runtime.getRuntime().exec("cmd /c start generateK.bat");

Related

Java CommandBuilder incomplete execution of copy command

I built a web crawler that records a livestream. After the recording is finished, the individual *.ts files are to be merged into a video. Since after my research FFMPEG has only a complex procedure over a text file as input parameter, it seems to me clearly eifnacher to use the available functions of the operating system.
I can use cmd.exe /c copy /b *.ts J:\final\output.mp4
to merge my ts files. However, as soon as I execute the command via the CommandBuilder, only the first 5 to 10 files are merged. So the video will be only a few seconds long. If I execute the command manually via Windows, all files are merged correctly. How does this happen? My commandExecture method looks like this:
private int execCommand(String dirPath, String command) {
try {
String[] commandArr = command.split(" ");
ProcessBuilder pb = new ProcessBuilder(commandArr);
pb.directory(new File(dirPath));
pb. redirectErrorStream(true);
Process p = pb.start();
return p.exitValue();
} catch (IOException e) {
e.printStackTrace();
}
return -9999;
}
I suspected that the program exited before the command was fully executed. So I added the following after pb.start() :
while(p.isAlive()) {
try {
Thread.sleep(500);
System.out.println("running");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
also this did not change anything. How does this happen and how can I make it merge automatically?

Java Fails to Run Large Python Files

I have a Python script which I am attempting to run via code in Java.
The Python script runs fine when run through a Linux terminal command on my Ubuntu virtual machine using an identical command to the one being passed through the Java script.
The Java code runs fine when running a different Python script that runs faster than the Python script I'm attempting to run..
However, despite both the Python script running fine and the Java script running fine, somehow, when I put the two together, nothing happens: The .txt file isn't updated, so the Java script prints out whatever old value it contains.
System.out.println("starting...");
try {
Process process = Runtime.getRuntime().exec("python3 /home/.../PycharmProjects/.../fraudanalysis.py abc def");
Thread.sleep(900000);
# Or try System.out.println(process.waitFor());
File file = new File("/home/.../PycharmProjects/.../output.txt");
Scanner newLineReader = new Scanner(file);
System.out.println(newLineReader.nextLine());
} catch(Exception e) {
System.out.println(e);
}
The code above should run the Python3 script at the absolute directory provided, using two arguments. The Python3 script completes after around 13 minutes and updates the output.txt file, which is then read by the Java program after waiting 15 minutes (or you can tell the thread to wait for completion-- process.WaitFor() returns 1).
def testScript():
time.sleep(780)
return_string1 = sys.argv[1]
return_string2 = sys.argv[2]
outputFile = open(os.path.dirname(os.path.abspath(__file__)) + "/output/output.txt", "w+")
outputFile.write(return_string1 + " " + return_string2)
print("Python run complete")
if __name__ == "__main__":
testScript()
The script above is a good stand-in for the Python script. If you lower the sleep time to 10 minutes for the Python script, it runs when Java sends the command. But, at the sleep times shown above, Java apparently fails to run the script, or the script run attempt ends in failure.
Additional info: the Java command is activated using a JavaFX button. The Java script has been developed in IntelliJ IDEA and the Python script was created using PyCharm.
My question is, what are possible causes for this problem, when both scripts work fine on their own?
As a simple suggestion, you should not rely on Thread.sleep method with a fixed parameter such as 15 minutes. Your data may grow or shrink and that way of proceeding is not efficient.
You could try to call the Process.waitFor() method so that when the python process is over, your thread continues.
Moreover, you could try to use ProcessBuilder that sometimes helps when facing buggy System exec cases.
Here is some code. in sub(), you can not change the python program, but for sub2() to work, you have to modify the python program so that its output is on the standard out and Java would do the redirect to the output.txt file.
public void sub() {
System.out.println("startig...");
Scanner newLineReader = null;
try {
Process process = Runtime.getRuntime().exec("python3 /home/.../PycharmProjects/.../fraudanalysis.py /home/.../PycharmProjects/.../fraudAnalysis.db 500");
process.waitFor();
File file = new File("/home/.../PycharmProjects/.../output.txt");
newLineReader = new Scanner(file);
String line;
while((line=newLineReader.nextLine())!=null) {
System.out.println(line);
}
} catch(IOException ioe) {
ioe.printStackTrace();
}catch(InterruptedException ie) {
ie.printStackTrace();
}finally {
newLineReader.close();
}
}
public void sub2() {
ProcessBuilder pb =
new ProcessBuilder("python3",
"/home/.../PycharmProjects/.../fraudanalysis.py",
"/home/.../PycharmProjects/.../fraudAnalysis.db", "500");
File log = new File("/home/.../PycharmProjects/.../output.txt");
pb.redirectErrorStream(true);
pb.redirectOutput(Redirect.appendTo(log));
Process p = null;
try {
p = pb.start();
} catch (IOException e) {
e.printStackTrace();
}
try {
p.waitFor();
} catch (InterruptedException e) {
e.printStackTrace();
}
Scanner newLineReader = null;
try{
newLineReader = new Scanner(log);
String line;
while((line=newLineReader.nextLine())!=null) {
System.out.println(line);
}
}catch(IOException ioe) {
ioe.printStackTrace();
}
}
I was able to get it to work with a small modification. I used relative file locations and TimeUnit.MINUTES.sleep(15);
package org.openjfx;
import java.io.File;
import java.util.Scanner;
import java.util.concurrent.TimeUnit;
public class TestWait {
public static void main(String[] args) {
System.out.println("starting...");
String dir="src/main/resources/org/openjfx/";//location of the python script
try {
System.out.println("Working Directory = " + System.getProperty("user.dir"));
//System.out.println("python3 " + dir+"fraudanalysis.py abc def");
Process process = Runtime.getRuntime().exec("python3 " + dir+"fraudanalysis.py abc def");
System.out.println(process.waitFor());
TimeUnit.MINUTES.sleep(15);
File file = new File("src/main/resources/org/openjfx/output.txt");
Scanner newLineReader = new Scanner(file);
System.out.println(newLineReader.nextLine());
} catch (Exception e) {
System.out.println(e);
}
}
}
Here is the python I used.
import sys
import time
def testScript():
return_string1 = sys.argv[1]
return_string2 = sys.argv[2]
time.sleep(780)
outputFile = open("src/main/resources/org/openjfx/output.txt", "w+")
outputFile.write(return_string1 + " " + return_string2)
print("Python run complete")
if __name__ == "__main__":
testScript()
it's a timeout error. can't be fixed. just pick between Java and Python and write everything in it. no reason to use both.

Running an exe from Java gives different result unlike running from command prompt

I have an executable that generates some file, and I need to call this executable from a Java application. The command goes like this
Generator.exe -outputfile="path/to/file" [some other params]
It works fine on the command prompt, but running it from Java,all steps are executed (which means the executable was called properly), but the file is not created, here is my code:
try {
Runtime.getRuntime().exec(new String[]{"path/to/Generator.exe", "-outputfile=path/to/file", param1, param2,..etc});
}
catch (Exception e) {
e.printStackTrace();
}
I got no errors in the exe log,and I have no way to debug it, but this seems as a problem with my java application, I see that I am trying the same exact command.. what am I missing?
I have a second approach for you. Try with the below. Here you are creating a output.txt file to see the output from the exe file. If successful you can comment out that line. Hope this will help you.
String[] command ={"path/to/Generator.exe", "-outputfile=path/to/file", "param1"};
ProcessBuilder pb = new ProcessBuilder(command);
pb.redirectOutput(new File("C:\\log\\output.txt"));
try {
Process p = pb.start();
p.waitFor();
} catch (InterruptedException e) {
e.printStackTrace();
}catch (Exception e1) {
e1.printStackTrace();
}

Execute commands in CMD on Windows with Java code

I want to write a Java code that would perform commands in Windows CMD.
I looked through the site and found out how to send and work with single request. For example create new Process and in execute ("cmd /c dir") then using input stream I can get the answer that is displayed.
How to open the process of cmd and let the user to enter cmd commands?
For example, I open application and it directly opens cmd process, then user can type "dir" and get the output.
After type "cd ../../"
and after type "dir" again and get the output with new path containment.
If it can be performed then how to do it? Or in order to perform this need to open each time a new process and execute ("cmd /c some_reqests")?
Nice question, you can in fact call cmd as a new process and use standard input and standard output to process data.
The tricky part is knowing when the stream from a command has ended.
To do so I used a string echoed right after the command (dir && echo _end_).
In practice I think it would be better to simply start a process for each task.
public class RunCMD {
public static void main(String[] args) {
try {
Process exec = Runtime.getRuntime().exec("cmd");
OutputStream outputStream = exec.getOutputStream();
InputStream inputStream = exec.getInputStream();
PrintStream printStream = new PrintStream(outputStream);
BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream,"utf-8"));
printStream.println("chcp 65001");
printStream.flush();
printStream.println("dir && echo _end_");
printStream.flush();
for(String line=reader.readLine();line!=null;line=reader.readLine()){
System.out.println(line);
if(line.equals("_end_")){
break;
}
}
printStream.println("exit");
printStream.flush();
for(String line=reader.readLine();line!=null;line=reader.readLine()){
System.out.println(line);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
try this
Process p = Runtime.getRuntime().exec("ps -ef");
found it at http://alvinalexander.com/java/edu/pj/pj010016

Why am I getting the output file as empty when I am redirecting the output from cmd?

I am creating a JAVA Web Application for judging the code online. I am taking the .java file uploaded by user and storing it in C:\uploads. Then using the ProcessBuilder class, I am compiling and executing the java file on the server. While executing, I am redirecting the output of the JAVA program to output.txt.
The program gets compiled alright. But the problem occurring is while executing, though the output.txt file gets created, the file is empty.
Here is the code for execution
public static boolean executeCode(int timeLimit,String fileName)
{
fileName=fileName.substring(0,fileName.length()-5); //to remove .java
String commands[]={"CMD", "/C","cd C:\\uploads && java"+fileName+">output.txt"};
ProcessBuilder p=new ProcessBuilder(commands);
p.redirectErrorStream(true);
Process process=null;
boolean errCode=false;
try {
long start=System.nanoTime();
process=p.start();
errCode=process.waitFor(timeLimit,TimeUnit.MILLISECONDS);
long end=System.nanoTime();
System.out.println("Duration="+(end-start));
} catch (IOException e) {
e.printStackTrace();
}
catch(InterruptedException e)
{
e.printStackTrace();
}
return errCode;
}
P.S. - This problem didn't occur when I created just a JAVA program for doing the same thing.
If you're using jdk 1.7 then you can try something like this:
public static boolean executeCode(int timeLimit,String fileName)
{
String commands[]={"CMD", "/C","cd C:\\uploads && javac " + fileName};
ProcessBuilder p=new ProcessBuilder(commands);
p.redirectErrorStream(true);
File output = new File("C:\\uploads\\output.txt");
p.redirectOutput(output);
...
}
I´m not an advanced console/bash user but aren't you missing a couple of spaces? The line should be like this:
String commands[]={"CMD", "/C","cd C:\\uploads && java "+fileName+" > output.txt"};

Categories