Edgar Peixoto
Edgar Peixoto

Reputation: 559

Using psql in linux with java to import a sql file

I am using this method to send commands to the linux terminal

public static String execute(String command) {
    StringBuilder sb = new StringBuilder();
    String[] commands = new String[]{"/bin/sh", "-c", command};
    try {
        Process proc = new ProcessBuilder(commands).start();
        BufferedReader stdInput = new BufferedReader(new InputStreamReader(proc.getInputStream()));
        BufferedReader stdError = new BufferedReader(new InputStreamReader(proc.getErrorStream()));

        String s = null;
        while ((s = stdInput.readLine()) != null) {
            sb.append(s);
            sb.append("\n");
        }

        while ((s = stdError.readLine()) != null) {
            sb.append(s);
            sb.append("\n");
        } 
    } catch (IOException e) {
        e.printStackTrace(); 
    }
    return sb.toString();
}   

It works fine with many commands like "ls", "date" etc..

but I wanna use a psql command to import a sql file to postgre like:

psql -h localhost -p 5432 -U postgres -d test -f test.sql

I typed this command by hand in terminal and it works fine but not with the method above (the method works well with date,ls...)

It looks like the method entries in a kind of infinite loop when it calls psql. The method does not end when the method calls the psql.

ps: I used export PGPASSWORD=pass to avoid pass the password.

Upvotes: 1

Views: 424

Answers (2)

Edgar Peixoto
Edgar Peixoto

Reputation: 559

I solved the problem creating a file file.sh with

export PGPASSWORD=pass

psql -h ip -p port -U user -d databaseName -f sqlFilePath

unset PGPASSWORD

then I Use the method execute:

execute("chmod +x file.sh"); //to give permission to file execute

execute ("./file.sh") //to execute the file in terminal

in the end I delete the file.sh with

File file = new File("file.sh"); 
file.delete(); 

Upvotes: 0

ryanp
ryanp

Reputation: 5127

I think your problem here might be that you are trying to consume the input and error streams sequentially, when you must actually do them simultaneously. Consequently your first readLine call is blocking, waiting for the readLine to finish on the other stream.

You can solve this by using multiple threads to read the streams, or by redirecting stderr, or by just ditching all the output. Have a look at these threads:

Upvotes: 1

Related Questions