I'm trying to restore a backed up .sql file using Java program. I'm posting the method below. But when I execute this the program halts for a long time. Then I executed same mysql command in command line(Windows) it's works charmingly.
Puzzled where I missed. What do you think ?
File file;
final JFileChooser fc = new JFileChooser();
int returnVal = fc.showOpenDialog(this);
if (returnVal == JFileChooser.APPROVE_OPTION) {
file = fc.getSelectedFile();
try {
System.out.println(file.getCanonicalPath());
String executeCmd = "mysql -u " + username + " -p" + password +" " + dbName+" < "+" \" "+file.getCanonicalPath()+"\" " ;
Process runtimeProcess;
runtimeProcess = Runtime.getRuntime().exec(executeCmd);
int processComplete = runtimeProcess.waitFor();
if (processComplete == 0) {
JOptionPane.showMessageDialog(Interface.mainFrame, "Database Backup restored successfully.", "Netmetering", 1);
} else {
System.out.println("Could not restore the backup");
}
} catch (IOException | InterruptedException ex) {}
...
String executeCmd = "mysql -u " + username + " -p" + password +" " + dbName+" < "+" \" "+file.getCanonicalPath()+"\" " ;
Process runtimeProcess = Runtime.getRuntime().exec(executeCmd);
InputStream is = runtimeProcess.getInputStream();
// Do one OR the other, but not both ;)
// If you don't care about the output, but I think it's a bit of waste personally...
while (is.read() != -1) {}
// I'd at least dump the output to the console...
int byteRead = -1;
while ((byteRead = is.read()) != -1) {
System.out.print((char)byteRead );
}
int processComplete = runtimeProcess.waitFor();
if (processComplete == 0) {...}
I would also recommend using ProcessBuilder over creating the Process manually like this, it handles the parameters better - IMHO
In general the correct way to run an external program is:
build you external program command line
build the ProcessBuilder and Process
build your own StreamRender
execute your external program
check the STDOUT and STDERR of your external program
verify the exit status of your external program
you can achieve this sequence as described following:
String command = "mysql -u... -p... dbname < file.sql";
ProcessBuilder pb = new ProcessBuilder(command);
Process pr;
try {
pr = pb.start();
StreamRender outputStdout = new StreamRender(pr.getInputStream(), StreamRender.STDOUT);
// your STDOUT output here
outputStdout.start();
StreamRender outputStderr = new StreamRender(pr.getErrorStream(), StreamRender.STDERR);
// your STDERR outpu here
outputStderr.start();
pr.waitFor();
if (pr.exitValue() != 0) {
// your external program fails
} else {
// ok, your external program was executed correctly
}
} catch (Exception e) {
// ...
} finally {
// ...
}
StreamRender.java
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
public class StreamRender extends Thread {
public static final String STDOUT = "STDOUT";
public static final String STDERR = "STDERR";
private InputStream inputStream;
private String inputType;
public StreamRender(InputStream inputStream, String inputType) {
this.inputStream = inputStream;
this.inputType = inputType;
}
public void run() {
try {
InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
BufferedReader br = new BufferedReader(inputStreamReader);
String line = null;
while ((line = br.readLine()) != null) {
System.out.println(this.inputType + " > " + line);
}
} catch (IOException ioe) {
ioe.printStackTrace();
}
}
Related
Is it possible in java by using something like ProcessBuilder to open gitbash, write a command (for example git status) and output the results?
I can successfully open git bash by using the following code but i don't know how to write any commands in it.
String[] commands = {"cmd","/C","C:\\Users\\......\\Git\git-bash"};
ProcessBuilder builder = new ProcessBuilder(commands);
builder.redirectErrorStream(true);
Process process = builder.start();
StringBuilder sb = new StringBuilder();
BufferedReader br = null;
try
{
br=new BufferedReader(new InputStreamReader(process.getInputStream()));
String line = null;
while ((line = br.readLine()) != null) {
sb.append(line + System.getProperty("line.seperator"));
}
} finally {
br.close();
}
String outcome = get_output(process.getInputStream());
process.waitFor();
System.out.println("Process finished with outcome = " + outcome);
You just have to change the paths and the git command. But the git-bash output is printed on a separate .txt file because I couldn't read it in any other way.
public class GitBash {
public static final String path_bash = "C:/Program Files/Git/git-bash.exe";
// Create a file Output.txt where git-bash prints the results
public static final String path_file_output_git_bash =
"C:/Users/Utente/Documents/IntelliJ-DOC/IntelliJ_project/Prova/src/main/Git-bash/Output.txt";
public static void main(String[] args) {
// Path to your repository
String path_repository = "cd C:/Users/Utente/Documents/Repository-SVN-Git/Bookkeeper";
// Git command you want to run
String git_command = "git ls-files | grep .java | wc -l";
String command = path_repository + " && " + git_command + " > " + path_file_output_git_bash;
runCommand(command);
}
public static void runCommand(String command) {
try {
ProcessBuilder processBuilder = new ProcessBuilder();
processBuilder.command(path_bash, "-c", command);
Process process = processBuilder.start();
int exitVal = process.waitFor();
if (exitVal == 0) {
System.out.println(" --- Command run successfully");
System.out.println(" --- Output = " + readFileTxt());
} else {
System.out.println(" --- Command run unsuccessfully");
}
} catch (IOException | InterruptedException e) {
System.out.println(" --- Interruption in RunCommand: " + e);
// Restore interrupted state
Thread.currentThread().interrupt();
}
}
public static String readFileTxt() {
String data = null;
try {
File myObj = new File(path_file_output_git_bash);
Scanner myReader = new Scanner(myObj);
while (myReader.hasNextLine()) {
data = myReader.nextLine();
}
myReader.close();
} catch (FileNotFoundException e) {
System.out.println(" --- An error occurred");
e.printStackTrace();
}
return data;
}
}
}
--- EDIT 2021/03/26 ---
Answer without the needs of a .txt file : Read output git-bash with ProcessBuilder in Java
Trying to call a C program using Java's process builder but don't know what to call in the process builder call.
Process p = new ProcessBuilder("myCommand", "myArg").start();
For myCommand and myArg, what values would I replace it with for it to run a C Program? The program I want it to call is shown here:
calculator.c:
#include <stdio.h>
int main ()
{
int a = 4;
int b = 2;
int c = a + b;
printf("Result: %d \n", c);
}
If calculator.c has not been compiled yet, you will want to first compile it:
Process compile = new ProcessBuilder("gcc", "calculator.c").start();
Process execute = new ProcessBuilder("./a.out").start();
Any relevant compiler flags (e.g., -O or -o calculator) should be included in the arguments as well. If you do rename the executable, you'll want to change ./a.out with it.
A better way (in terms of having few hard-coded constants) would be to have some variables like:
String c_file = "calculator.c";
String output_exe = "calculator";
Process compile = new ProcessBuilder("gcc", "-o " + output_exe, c_file).start();
Process execute = new ProcessBuilder("./" + output_exe);
Lastly, you'll probably want to make sure each of your processes are exiting without error:
if (compile.getInputStream().read() == -1) {
// that means something was written to stderr, and you can do something like
System.out.error("ERROR!");
System.exit(-1);
}
As #VinayDandekar pointed out, you can also do this with exitValue.
if (compile.exitValue() == -1) {
// that means something was written to stderr, and you can do something like
System.out.error("ERROR!");
System.exit(-1);
}
At First Set Your Compiler Path On Environment Variable From Windows System Property Otherwise It will not work . Then Set Compile And Run Code
Compile Code: `
JFileChooser fileChooser=new JFileChooser();
if (fileChooser.showSaveDialog(compile.this) != JFileChooser.APPROVE_OPTION)
return;
File file = fileChooser.getSelectedFile();
try {
FileWriter out = new FileWriter(file);
textEditor.write(out);
out.close();
} catch (IOException e1) {
e1.printStackTrace();
}
String filepath = file.getPath();
String filepath2 = filepath.substring(0, filepath.lastIndexOf(File.separator));
System.out.println(filepath);
System.out.println(filepath2);
String name = file.getName();
String name2 = file.getName().substring(0, file.getName().lastIndexOf("."));
String folder = filepath2+"\\";
String exe = folder+name2+".exe";
System.out.println(exe);
ProcessBuilder pb=new ProcessBuilder();
try {
pb = new ProcessBuilder("cmd", "/C", "gcc " + "\"" + filepath2 + "\\" + name + "\"" + " -o \"" + name2+"\"");
pb = new ProcessBuilder("cmd", "/C", "g++ " + "\"" + filepath2 + "\\" + name + "\"" + " -o \"" + name2+"\"");
pb.directory(new File(filepath2));
Process p = pb.start();
p.waitFor();
int x = p.exitValue();
if (x == 0) {
area.setForeground(red);
area.setText(" == 0 error.. Compilation Finished");
} else {
BufferedReader r = new BufferedReader(new InputStreamReader(p.getErrorStream()));
//BufferedWriter rm=new BufferedWriter(new OutputStreamWriter(p.getOutputStream()));
String out;
area.setText("");
while ((out = r.readLine()) != null)
{
area.setForeground(RED);
area.append(out + System.getProperty("line.separator"));
}
}
} catch (Exception ex) {
ex.printStackTrace();
}
`
Run Code: `
JFileChooser fileChooser=new JFileChooser();
if (fileChooser.showSaveDialog(compile.this) != JFileChooser.APPROVE_OPTION)
return;
File file = fileChooser.getSelectedFile();
try {
FileWriter out = new FileWriter(file);
textEditor.write(out);
out.close();
} catch (IOException e1) {
e1.printStackTrace();
}
String filepath = file.getPath();
String filepath2 = filepath.substring(0, filepath.lastIndexOf(File.separator));
System.out.println(filepath);
System.out.println(filepath2);
String name = file.getName();
String name2 = file.getName().substring(0, file.getName().lastIndexOf("."));
String folder = filepath2+"\\";
String exe = folder+name2+".exe";
System.out.println(exe);
ProcessBuilder pb=new ProcessBuilder();
try {
pb = new ProcessBuilder("cmd", "/C", "gcc " + "\"" + filepath2 + "\\" + name + "\"" + " -o \"" + name2+"\"");
pb = new ProcessBuilder("cmd", "/C", "g++ " + "\"" + filepath2 + "\\" + name + "\"" + " -o \"" + name2+"\"");
pb.directory(new File(filepath2));
Process p = pb.start();
p.waitFor();
int x = p.exitValue();
int z=p.exitValue();
if (x == 0) {
Runtime rt = Runtime.getRuntime();
try {
String username = System.getProperty("user.name");
String c = "#echo off\n" + "\"" +
filepath2 + "\\" + name2 + ".exe\"\n" + "echo.\n" + "echo.\n" + "echo Process Terminated\n" +
"pause\n" +
"exit";
File dir = new File("C:\\Users\\" + username + "\\CodeEditor");
dir.mkdir();
try {
File file2 = new File("C:\\Users\\" + username + "\\CodeEditor" + "\\run.bat");
file2.createNewFile();
PrintWriter writer = new PrintWriter(file2);
writer.println(c);
writer.close();
Process p2 = Runtime.getRuntime().exec("cmd /c start run.bat", null, new File("C:\\Users\\" + username + "\\CodeEditor"));
} catch (Exception ex) {
}
} catch (Exception ex) {
}
} else {
JOptionPane.showMessageDialog(compile.this, "Compilation Error", "Error", JOptionPane.ERROR_MESSAGE);
}
} catch (Exception ex) {
ex.printStackTrace();
}
`
Done!!!
Runtime can be used to execute any command line instruction supported by OS.
Example below would be of help.
package com.test;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class CommandExec {
public static void main(String[] args) {
try {
Process pr = Runtime.getRuntime().exec("ls /etc");
BufferedReader read = new BufferedReader(new InputStreamReader(pr.getInputStream()));
String str = read.readLine();
while (str != null){
System.out.println(str);
str = read.readLine();
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
I'm trying to count the number of lines of a text file using a unix command from java code.
My code looks like:
String filePath = "/dir1/testFile.txt";
Runtime rt = Runtime.getRuntime();
Process p;
try {
System.out.println("No: of lines : ");
findLineCount = "cat " + filePath + " | wc -l";
p = rt.exec(findLineCount);
p.waitFor();
} catch (Exception e) {
//code
}
But, nothing is displayed in the console. When I execute the command directly, it works. What could be the issue in the above code?
I suggest you use a ProcessBuilder instead of Runtime.exec. You can also simplify your command by passing the filePath to wc. Please don't swallow Exception(s). Finally, you can use ProcessBuilder.inheritIO() (Sets the source and destination for subprocess standard I/O to be the same as those of the current Java process) like
String filePath = "/dir1/testFile.txt";
try {
System.out.println("No: of lines : ");
ProcessBuilder pb = new ProcessBuilder("wc", "-l", filePath);
pb.inheritIO();
Process p = pb.start();
p.waitFor();
} catch (Exception e) {
e.printStackTrace();
}
Of course, it's more efficient to count the lines in Java without spawning a new process. Perhaps like,
int count = 0;
String filePath = "/dir1/testFile.txt";
try (Scanner sc = new Scanner(new File(filePath));) {
while (sc.hasNextLine()) {
String line = sc.nextLine();
count++;
}
} catch (Exception e) {
e.printStackTrace();
}
System.out.printf("No: of lines : %d%n", count);
When I execute the command directly
I doubt you're execute it "directly". You're probably running it in a shell.
Your code should run that script in a shell too.
rt.exec(new String[]("bash", "-c", findLineCount});
This is how i printed number of lines
public static void main(String[] args) {
try {
Runtime run = Runtime.getRuntime();
String[] env = new String[] { "path=%PATH%;" + "your shell path " }; //path of cigwin bin or any similar application. this is needed only for windows
Process proc = run.exec(new String[] { "bash.exe", "-c", "wc -l < yourfile" }, env);
BufferedReader reader = new BufferedReader(new InputStreamReader(
proc.getInputStream()));
String s;
while ((s = reader.readLine()) != null) {
System.out.println("Number of lines " + s);
}
proc.waitFor();
int exitValue = proc.exitValue();
System.out.println("Status {}" + exitValue);
} catch (IOException | InterruptedException e) {
e.printStackTrace();
}
}
A simple example of using phantomJs in Java will block undefinitely:
public void runPhantomJs(String path, String command) {
Process process;
String outFile = "a11.txt";
try {
process = Runtime.getRuntime().exec(path+ " " + command + " > " +outFile);
int exitStatus = process.waitFor();
//String status = (exitStatus == 0 ? "SUCCESS:" : "ERROR:");
File f = new File(outFile);
if (f.exists()) {
BufferedReader in = new BufferedReader(new InputStreamReader(new FileInputStream(f),"UTF-8"));
String str;
while ((str = in.readLine()) != null) {
System.out.println(str);
}
in.close();
System.out.println(str);
}
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
The script execute is very simple, but it returns a whole page on the console:
var webPage = require('webpage');
var page = webPage.create();
page.open('http://www.google.com/', function(status) {
if (status !== 'success') {
console.log('1');
phantom.exit();
} else {
console.log(page.content);
phantom.exit();
}
});
Note that on the pasted code I've added a "> a11.txt" to see if it worked better to read a file instead of reading the output directly. It should be faster, but for some reason it doesn't work. I suppose the redirection > doesn't work.
So I got my code to work. Apparently the output of phantomjs has to be read or the buffer will fill up completely, blocking further execution.
So I think your code will work if you modify it like so:
process = Runtime.getRuntime().exec(path+ " " + command + " > " +outFile);
BufferedInputStream bis = new BufferedInputStream(process.getInputStream());
bis.close();
process.waitFor();
...
If it doesn't work, try using ProcessBuilder. This is my working code:
try {
String phantomJsExe = configuration.getPhantomJsExe().toString();
String phantomJsScript = configuration.getPhantomJsScript().toString();
String urlsTextFile = configuration.getPhantomJsUrlsTextFile().toString();
Process process = new ProcessBuilder(phantomJsExe, phantomJsScript, urlsTextFile).start();
BufferedInputStream bis = new BufferedInputStream(process.getInputStream());
bis.close();
process.waitFor();
} catch (Exception ex) {
ex.printStackTrace();
}
i wanted to perform rename and delete function and the environment is LINUX.
This is the code which I'm using,
String[] command_ary = { "/usr/bin/sh", "-c", command };
Runtime runtime = Runtime.getRuntime();
Process process = runtime.exec( command_ary );
But Im getting the following error message,
java.io.IOException: Cannot run program "/usr/bin/sh": java.io.IOException: error=2, No such file or directory
Can anybody help me.
Thank-You
As the exception says, there's no file /usr/bin/sh on your system. If you're looking for the Bourne shell, that's /bin/sh.
public void run() {
//log.info("taskDao:{},concurrentHashSet:{},id:{},shellName:{},shellDate:{}", taskDao, concurrentHashSet, id, shellName, shellDate);
log.info("concurrentHashSet:{},param:{}", concurrentHashSet, param);
int exeState = 99999;
// ssh跳转到其他机器去执行脚本,you can add "ssh rd#g1-jg-hadoop-01 \"source ~/.bash_profile ; bash -x %s %s\"" instead of command
String command = "source ~/.bash_profile ; bash -x %s %s";
String commandF = String.format(command, param.getShellName(), param.getRecallDate());
String[] cmdArr = {"/bin/sh", "-c", commandF};
long taskId = param.getTaskId();
Runtime runtime = Runtime.getRuntime();
Process process = null;
try {
process = runtime.exec(cmdArr);
InputStream stderr = process.getErrorStream();
InputStreamReader isr = new InputStreamReader(stderr);
BufferedReader br = new BufferedReader(isr);
String line = null;
StringBuilder sb = new StringBuilder();
while ((line = br.readLine()) != null) {
sb.append(line).append(System.lineSeparator());
}
log.info("exe task thread param:{},commandF:{},execute shell info:{}", param, commandF, sb.toString());
exeState = process.waitFor();
} catch (InterruptedException | IOException e) {
log.error("execute shell error,exeState:{},command:{}", exeState, commandF,e);
} finally {
log.info("execute shell state:{}", exeState);
// 从set中删除 更新表状态 多张表一个脚本,会有问题,其中状态覆盖
if (exeState == 0) {
// 执行成功
taskDao.updateStateByPrimaryKey(taskId, (short) 30, new Date());
// 邮件参数
param.setState(30);
String mailBody = SendMailUtil.beautyMailHtmlLayout(param);
String mailToAddress = param.getMailToUser();
String mailTitle = param.getMailContentTitle();
try {
SendMailUtil.sendMail(mailToAddress, mailTitle, mailBody);
} catch (Exception e) {
e.printStackTrace();
}
}
if (exeState != 0) {
// 执行失败
taskDao.updateStateByPrimaryKey(taskId, (short) 40, new Date());
// 邮件参数
param.setState(40);
String mailBody = SendMailUtil.beautyMailHtmlLayout(param);
String mailToAddress = param.getMailToUser();
try {
SendMailUtil.sendMail(mailToAddress, "回溯任务", mailBody);
} catch (Exception e) {
e.printStackTrace();
}
}
ExecuteTaskModel taskModel = new ExecuteTaskModel();
taskModel.setId(taskId);
log.info("remove task in thread,id:{}", taskId);
boolean remove;
if (concurrentHashSet.contains(taskModel)) {
remove = concurrentHashSet.remove(taskModel);
}
log.info("remove from set success set:{}", concurrentHashSet);
log.info("execute task thread exit!");
System.out.println("Process exitValue: " + exeState);
assert process != null;
process.destroy();
}
}