I am using the runtime.exec to try and execute a .SQL script into an SQLite database file I have locally. I am currently running this on MacOS.
Runtime runtime = Runtime.getRuntime();
try
{
Process process = runtime.exec("sqlite3 /Users/Documents/Uni/Music\\ Player/src/Common/database.db < /Users/Documents/Uni/Music\\ Player/src/Common/database.sql");
BufferedReader stdError = new BufferedReader(newInputStreamReader(process.getErrorStream()));
try {
if (process.waitFor() != 0) {
String s = "";
System.err.println("exit value = " + process.exitValue());
System.out.println("Here is the standard error of the command (if any):");
while ((s = stdError.readLine()) != null) {
System.out.println(s);
}
}
} catch (InterruptedException e) {
System.err.println(e);
}
This is the code I am currently using. If I were to execute the command through the terminal, it would execute successfully and my database would be updated with the contents of the .SQL script.
However, when I execute this through the code, I get the error:
Error: near "Player": syntax error
along with a process exit
I can't for the life of me find out what is wrong with the String syntax. I've tried multiple different ways to escape the space in the string unsuccessfully. Any ideas?
Instead of trying to generate the path to the file using manual hard-coded
String
, let's make aPath
and have it generate the file path for you. This is much less difficult to use, and it has the benefit of generating the correct file path no matter what the operating system or filesystem happen to be.Replace the current exec command with this to implement that change:
This runs the "sqlite3 database.db < database.sql" command using the environmental variables inherited from the parent process (the JVM) and runs that command from within the directory specified by
parentDirectory
, which happens to be the directory you gave in your question.However, despite fixing the original problem, your code also contains another problem related to the use of file redirection. File redirection via
<
or>
is a shell construct, and won't work outside of the shell. UsingRuntime.exec()
is basically like using theRun...
GUI on Windows, and since file redirection doesn't work there it won't work here. You will need to fix the command used in order to address this problem. Luckily, there is a StackOverflow question addressing this exact problem here.Here is the code with both issues fixed:
This code uses
ProcessBuilder
to set the directory to the same parent directory as before, but the command has been modified to remove the file redirection and instead the file redirection is achieved using theredirectinput()
method. This accomplishes the same things as"sqlite3 database.db < database.sql"
would if executed within a shell, but this code will work within Java.Edit:
The above code is not working, so I have attempted to fix it and have also added debugging statements to help track down the problem:
And here is the same code with the debugging code removed and a slight cleanup: