Java Cannot run program CreateProcess error=2 - java

i'd like to run a command that executes a shell script with the java class "DefaultExecutor", but i get this error:
Cannot run program "get_encrypted_password.sh" (in directory "C:\Temp\scripts"): CreateProcess error=2 specified file not found".
the script works well with git bash.
can someone tell me where i'm doing wrong?
public Entity updateWithEncryptedPassword(Entity entity) throws IOException {
String password = entity.getPwd();
String security_key = "00000000000000000000000000000000";
String path = "C:/Temp/scripts";
CommandLine commandLine = CommandLine.parse("get_encrypted_password.sh");
commandLine.addArgument(password);
commandLine.addArgument(security_key);
String encrypted_password = Utils.runCommandAndGetOutput(commandLine, path);
entity.setNewPwd(encrypted_password);
return super.update(entity);
}
public static String runCommandAndGetOutput(CommandLine commandLine, String path) throws IOException {
DefaultExecutor defaultExecutor = new DefaultExecutor();
defaultExecutor.setExitValue(0);
defaultExecutor.setWorkingDirectory(new File(path));
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
PumpStreamHandler streamHandler = new PumpStreamHandler(outputStream);
defaultExecutor.setStreamHandler(streamHandler);
defaultExecutor.execute(commandLine);
return outputStream.toString();
}

Instead of executing "get_encrypted_password.sh", which cannot be ran under Windows, execute "bash", (probably git bash,) and pass "get_encrypted_password.sh" as a parameter to it, so that bash will execute your script.

Related

Run root command using java.lang.ProcessBuilder

Using java.lang.ProcessBuilder on a Java application running on a Linux machine (Ubuntu 18.04 specifically), what can be done such that the command executed would be able to run and not throw Permission Denied.
Here's the code:
boolean isWindows = System.getProperty("os.name")
.toLowerCase().startsWith("windows");
ProcessBuilder builder = new ProcessBuilder();
if (isWindows) {
builder.directory(new File(System.getProperty("user.home")));
builder.command("cmd.exe", "/c", command);
} else {
builder.directory(new File(System.getenv("HOME")));
builder.command("sh", "-c", command);
}
Process process = builder.start();
Tested on Ubuntu 18.04:
import java.io.File;
public class Application {
public static void main(String[] args) throws Exception{
boolean isWindows = System.getProperty("os.name")
.toLowerCase().startsWith("windows");
ProcessBuilder builder = new ProcessBuilder();
if (isWindows) {
builder.directory(new File(System.getProperty("user.home")));
builder.command("cmd.exe", "/c", "");
} else {
builder.directory(new File(System.getenv("HOME")));
// i used the docker command as an example, because it needs a root access (default configuration of Docker)
builder.command("/bin/bash", "-c", "sudo docker image ls > result.txt 2> errors.txt");
}
Process process = builder.start();
// When running the command java Application in terminal, i noticed that when prompted to type the root password
// the program exits so i decided to make the current thread sleep for 5 seconds, to give me time to type the password
Thread.sleep(5000);
}
}
Hope that will be helpful :)

Command Works Through Command Line, but Not When Using ProcessBuilder

I'm writing a program that includes a feature where the user can type in Java code into a text box and be able to compile and run it. The error I get is:
The two directories shown at the top are correct, and the command works when I do it manually through command prompt from the same working directory. I'm using Windows 10, and also here's the code:
public Process compile() throws IOException {
save(); //saves changes to source file
System.out.println(file.getCanonicalPath());
ProcessBuilder processBuilder = new ProcessBuilder("javac", file.getCanonicalPath());
processBuilder.directory(new File(settingsFile.getJdkPath()));
System.out.println(processBuilder.directory());
Process process = processBuilder.start(); //Throws exception
this.compiledFile = new File(file.getParentFile(), file.getName().replace(".java", ".class"));
return process;
}
File to compile:
Working directory:
Using this code, I was able to compile a Test.java file into a Test.class file on my Desktop.
import java.io.IOException;
public class App {
public static Process compile() throws IOException {
String myFilePath = "C:\\Users\\redacted\\Desktop\\Test.java";
String javacPath = "C:\\Program Files\\Java\\jdk1.8.0_171\\bin\\javac.exe";
ProcessBuilder processBuilder = new ProcessBuilder(javacPath, myFilePath);
return processBuilder.start();
}
public static void main(String[] args) throws IOException {
Process process = compile();
}
}
Using String javacPath = "javac.exe"; also worked, but that could be because my JDK bin is on my PATH variable.
There is something wrong with your paths or permissions in the ProcessBuilder constructor call.

How to start a JavaFX application in a standalone process

I'd like to start a JavaFX application, if it isn't already running.
The JavaFX application is packaged in a JAR container, which is in the classpath of the calling application. The calling application should execute the JavaFX app.
The JavaFX application should not terminate if the calling application gets terminated. (therefore it needs to be in a separate process)
I tried the following approach, but even though uiProcess.isAlive() returns true, the JavaFX application is never visible.
// caller main thread
String[] startOptions = new String[]{"java", "-jar", "javafx-ui.jar"};
Process uiProcess = new ProcessBuilder(startOptions).start();
+++++++++++++++++++++++++++++++++++++++
UPDATE:
I created a helper class which takes the JAR name and tries to execute it. Unfortunately this doesn't work. But if I copy the the logged CLI command and execute the command in a terminal, the app is started as expected. If I print System.getProperty("java.class.path") property, I see that my javafx-ui.jar is on the classpath.
Usage:
ProcessExecutor processExecutor = new ProcessExecutor();
processExecutor.executeJarByName("javafx-ui.jar");
Executor:
public class ProcessExecutor {
private List<Process> processes;
private static Logger logger = LoggerFactory.getLogger(ProcessExecutor.class);
/**
* Default constructor
*/
public ProcessExecutor() {
processes = new ArrayList<>();
}
/**
* Executes jar in a standalone process
*
* #param jarName
*/
public Process executeJarByName(String jarName) throws IOException {
String[] command = new String[]{"java", "-jar", jarName};
ProcessBuilder builder = createProcessBuilder(command);
Process process = builder.start();
processes.add(process);
if (process.isAlive()) {
Optional<ProcessHandle> processHandle = ProcessHandle.of(process.pid());
if (processHandle.isPresent()) {
ProcessHandle.Info processInfo = processHandle.get().info();
logger.info("COMMAND: {}", processInfo.command().orElse(""));
logger.info("CLI: {}", processInfo.commandLine().orElse(""));
logger.info("USER: {}", processInfo.user().orElse(""));
logger.info("START TIME: {}", processInfo.startInstant().orElse(null));
logger.info("TOTAL CPU: {}", processInfo.totalCpuDuration().orElse(null));
}
}
return process;
}
private ProcessBuilder createProcessBuilder(String[] command) {
return new ProcessBuilder(command);
}
/**
* Kills all executed processes
*/
public void killAll() {
processes.forEach(p -> p.destroy());
}
}
I got it working, if I execute the following command, using the Java ProcessBuilder. The mainClassName needs to be the fully qualified class name of the class, containing the main() method. (including the package name)
String separator = System.getProperty("file.separator");
String classpath = System.getProperty("java.class.path");
String javaHome = System.getProperty("java.home");
String java = javaHome + separator + "bin" + separator + "java";
String[] command = {java, "-cp", classpath, mainClassName};
ProcessBuilder builder = createProcessBuilder(command);

Unable to get output from Apache Commons Exec

Although the titles are very similar, this questions is NOT a duplicate of Process output from apache-commons exec.
I am trying to get the output of a command by using apache-commons exec. Here is what I am doing
import org.apache.commons.exec.*;
import java.io.ByteArrayOutputStream;
public class Sample {
private static void runCommand(String cmd) throws Exception {
ByteArrayOutputStream stdout = new ByteArrayOutputStream();
PumpStreamHandler psh = new PumpStreamHandler(stdout);
CommandLine cl = CommandLine.parse(cmd);
DefaultExecutor exec = new DefaultExecutor();
exec.setStreamHandler(psh);
exec.execute(cl);
System.out.println(stdout.toString());
}
public static void main(String... args) throws Exception {
String cmd1 = "python -c \"print(10)\"";
String cmd2 = "python -c \"import datetime; print(datetime.datetime.now())\"";
runCommand(cmd1); // prints 10
runCommand(cmd2); // should print the current datetime, but does not!
}
}
The problem is that runCommand(cmd2) does not print anything to the output. When I try running the command on terminal, it works fine.
I have tried this program with and without the IDE so I'm sure this has nothing to do with the IDE console.
Here's a screenshot
Here's a screenshot of the terminal
Python command running on the terminal
It works fine on mine PC from IDEA. Try to recreate the project. Add more information about your environment.
Try to put your python code into .py file and run it like "python test.py".
A colleague was able to come up with a solution to this problem. Changing
CommandLine cl = CommandLine.parse(cmd);
to
CommandLine cl = new CommandLine("/bin/sh");
cl.addArguments("-c");
cl.addArguments("'" + cmd + "'", false);
solved the issue.
The complete code looks as follows:
import org.apache.commons.exec.*;
import java.io.ByteArrayOutputStream;
public class Sample {
private static void runCommand(String cmd) throws Exception {
ByteArrayOutputStream stdout = new ByteArrayOutputStream();
PumpStreamHandler psh = new PumpStreamHandler(stdout);
// CommandLine cl = CommandLine.parse(cmd);
CommandLine cl = new CommandLine("/bin/sh");
cl.addArguments("-c");
cl.addArguments("'" + cmd + "'", false);
DefaultExecutor exec = new DefaultExecutor();
exec.setStreamHandler(psh);
exec.execute(cl);
System.out.println(stdout.toString());
}
public static void main(String[] args) throws Exception {
String cmd1 = "python -c \"print(10)\"";
String cmd2 = "python -c \"import datetime; print(datetime.datetime.now())\"";
runCommand(cmd1); // prints 10
runCommand(cmd2);
}
}

How to run a jar file from the teamcity custom plugin code

I am working on developing a plugin for teamcity . The requirement is to run a jar file from the code which does some custom operation. I tried with the below code, but its not working for me.Any ideas on how to run the jar, links to documentation or sample code will help me a lot to progress further
public class CustomBuildProcess extends BuildProcessAdapter
{
private static final String jarDir = "\\plugins\\teamcity-custom-plugin-agent\\lib\\metrics-17.6.4.4.jar";
#Override
public void start()
{
buildStatus = startProcess();
}
private BuildFinishedStatus startProcess() throws IOException
{
final GeneralCommandLine cmd = new GeneralCommandLine();
cmd.setExePath("java -jar C:\\BuildAgent"+jarDir);
final ExecResult result = SimpleCommandLineProcessRunner.runCommand(cmd, new byte[0]);
}
The following code worked for me.
final Runtime rTime = Runtime.getRuntime();
final Process process = rTime.exec("java -jar
C:\\TeamCity\\BuildAgent\\plugins\\teamcity-cutom-plugin-agent\\lib\\metrics-17.6.4.4.jar");
logger.progressMessage(new String(IOUtils.toByteArray(process.getInputStream())));
PrintStream printStream = new PrintStream(process.getOutputStream());
logger.progressMessage(new String(IOUtils.toByteArray(process.getErrorStream())));

Categories