I need my Java console application to do the following:
Open VIM
< the user input multiple lines of words and :wq >
My application should then be able to get the vim input and print it in the terminal.
So far I'm stuck at 1.. It seems impossible to get Java to open VIM!
Here is some non functional code I have been fiddling with:
call system text editor
http://www.linglom.com/2007/06/06/how-to-run-command-line-or-execute-external-application-from-java
Advice much appreciated
EDIT
Ok so the following will open VIM but backgrounded. Any way around this?
String[] command = {"/usr/bin/vim", "test.txt"};
Process vimProcess = Runtime.getRuntime().exec(command);
vimProcess.waitFor();
run vim from java (notice that this will work on gnome, if you use KDE use "konsole"):
Process pr = Runtime.getRuntime().exec("gnome-terminal -e 'vim /tmp/tmpfile'");
wait the user will finish and exit:
int exitVal = pr.waitFor(); //check for the right exitVal
read the input and write to the terminal:
System.out.println(FileUtils.raedFileToString(new File("/tmp/tmpfile")));
Related
I want to execute wsl commands from java.
I'm trying to do this using Process and ProcessBuilder.
As I understand, there are two ways to do this:
Run wsl along with command as argument (for example: wsl ls -l) (do this per-command).
Run wsl, and then execute the commands one by one.
But there are some problems with 1 and 2.
With point 1:
When the command terminates, the process does not stop. So even if i run wsl ls, I can not determine the moment when I can call next command.
wsl does not save the state between such calls, so it's not very convenient
With point 2:
Since wsl does not show bash prompt, I can not track when the command stopped displaying information. For example:
ProcessBuilder pb = new ProcessBuilder("wsl");
pb.redirectErrorStream(true);
Process p = pb.start();
Thread.sleep(1000);
OutputStreamWriter osw = new OutputStreamWriter(p.getOutputStream());
osw.write("ls\n");
osw.flush();
And all I can read is:
build.gradle
gradle
gradlew
gradlew.bat
out
settings.gradle
src
No selya#selya-pc:/mnt/c/Users/selya$ read. So I can't use it as a separator between commands. I think that wsl somehow tracks, in what environment it was launched, for example, through isatty(), and therefore the output is different.
With both:
Аs far as I know, for programs that are running outside the terminal, stdout is not buffered. So there are some problems with, for example, sudo, because it asks fro a password without newline/flush ([sudo] password for selya:), therefore I can't read this line...
I found a solution - pass command as argument to unbuffer util, for example:
wsl unbuffer -p sudo apt-get update
(-p stands for pipeline).
But other problems still remain. Is there any way to do this? Or maybe there is lib for it? Even c or c++ lib will suit my needs...
P.S. I tried to find a solution for several days. Russian-speaking SO didn't help me, that's why I'm here. Sorry for my English...
The problem was solved with the help of pty4j. It works on linux, mac and windows. (It works like pseudo terminal on linux, but have nice java interface).
I am trying to open a vi editor using Java code in an linux env (the java code is executed via shell script). The editor should open in foreground & become active terminal, while the java is should be running at Background.
I tried using both commands using :-
String []command = {"xterm", "vi", "/home/user/test.txt"};
Process pr = Runtime.getRuntime().exec(command);
Process p = new ProcessBuilder("vi", "/home/user/test35.txt").start();
In one of the above code, if check the ps -ef | grep vi, I am able to the process, but its running at background. I want to run it in foreground as an active terminal as user for his type the text into the editor. While the java will be running at the background.
Any suggestion or snippet's.
I have referred this Open VIM with Java application , but still in vain.
If you want to create a new xterm and execute a command in that terminal, you need to pass the command with -e. Try this:
ProcessBuilder pb = new ProcessBuilder("xterm", "-e", "vi", "/home/user/test.txt");
The debug steps I did was I tried opening a terminal via command & use the same command in the Java code. Issue observed that I need to set DISPLAY=:0. if I am running via root user , for other user export DISPLAY was not needed
String []command = {"/usr/bin/xterm","-e", "vi", "/home/hscpe/test.txt"};
Process pr = Runtime.getRuntime().exec(command);
Since I am running the java code via shell script I will be adding export in the shell script i.e export DISPLAY=:0. Now will try to make the editor as editable (Will stimulate by pressing I , i.e Insert by java robot).
I referred here & here
I am trying to make a console-based Java application that starts some batch scripts that do some other irrelevant things. Presently, I just want to find the proof of concept
I have tried to use the following code:
Runtime.getRuntime().exec("cmd /c start pathtomybatch.bat");
This works fine until I turn it into a .jar file and attempt to execute it. Then it opens the batch file in a new command prompt window, which I don't want it to do. I want to open the batch file in the same window that my Java program is running in. I read about the start command on TechNet and SS64 and found out that apparently adding changing start to start /b would open the program in the same command prompt window. However, when I try to run this:
Runtime.getRuntime().exec("cmd /c start /b pathtomybatch.bat");
NetBeans says BUILD SUCCESSFUL for both lines of code, but when I try the second line of code, no command prompt window opens and my batch file doesn't get started.
I want to know how I can make Java open that batch file within the same command prompt window without stopping the Java application or waiting for it to finish.
Also, as a tiny extra request, could someone tell me if I could do the same for an .exe file?
I'm on Windows 7, but I want this app to work for people using Vista or newer.
The extra window is coming from the start command you initiate. See https://www.windows-commandline.com/cmd-start-command/
A better pattern is to use
Process p = Runtime.getRuntime().exec("cmd /c pathtomybatch.bat");
Then make sure you loop until p.exitValue() no longer throws an exception (which means the process has exited), and while looping copy all available bytes from p.getOutputStream() and p.getErrorStream() to System.out and/or System.err.
I am aware that you can pass commands to the Terminal and it returns your result in Java. The problem is for undisclosed reasons I need a Terminal window to open and to have the command in it. This code works to open an empty Terminal window (on mac):
p = Runtime.getRuntime().exec("/usr/bin/open -a Terminal");
And I have seen someone say on a different overflow question that you can do this:
p = Runtime.getRuntime().exec("/usr/bin/open -a Terminal [Put Command to pass through here]");
But it didn't seem to work when I tried to pass the command through to the window.
Any help or suggestions?
You can achieve this by using AppleScript.
Here you can find example how call it from Java:
AppleScript from Java on Mac OS X 10.6?
And script you need will look like this:
tell application "Terminal"
set currentTab to do script ("cd ~/Downloads/")
set currentTab to do script ("ll")
end tell
Each time I use Runtime.exec("cmd /c start....") I am opening a cmd window. I would like to create a more seamless application by closing each previous cmd window. How can I do this?
If anyone knows of a better way to run a series of commands in the same cmd window rather than opening new ones each time I execute a command, please let me know.
Don't use start, that opens another window
Replace:
Runtime.exec("cmd /c start....")
with:
Runtime.exec("cmd /c ....")
Why do you need cmd windows?
I'd run the command directly in Java and capture the output and display it in a local window (if it's needed at all).
Just make sure you consume all the output from the program or it might stall. Also remember to close the stdout, stderr, and stdin streams or some file handles might leak (well, that's true on some JDKs on some Unix OSes... Windows, who knows).
You cannot control the opened windows from Java. But I suggest two solutions for you:
First:
Runtime.exec("cmd /c start /MIN ...")
The /MIN parameter will prevent windows from appearing.
Second: put all the applications you must call inside the same batch file and call it once. :-)