2010-04-01 2 views
5

Я хочу выполнить несколько SQL скриптов с использованием метода Runtime.exec в Java. Я намерен вызвать mysql.exe/mysql.sh и перенаправить файл сценария в этот процесс. Из командной строки можно запустить командукак перенаправить стандартный ввод в Java Runtime.exec?

<mysqInstallDir\/bin\mysql.exe -u <userName> -p <password> < scripts\create_tables.sql 

Я могу вызвать mysql.exe с помощью Runtime.exec но как перенаправить данные из SQL файла в mysql.exe?


Я прочитал статью в http://www.javaworld.com/javaworld/jw-12-2000/jw-1229-traps.html?page=4 и используется механизм StreamGobbler для получения ошибок и выходных потоков. Нет проблем. Проблема возникает при чтении файла «сценариев \ create_tables.sql» с помощью BufferedReader и передавая содержимое OutputStream prcess в. Я ожидал, что процесс передаст данные в mysql.exe. Но я вижу, что из этого файла sql считывается только первая строка.

OutputStream outputstream = proc.getOutputStream(); 
OutputStreamWriter outputstreamwriter = new OutputStreamWriter(outputstream); 
BufferedWriter bufferedwriter = new BufferedWriter(outputstreamwriter); 
    while ((line = br.readLine()) != null) 
    { 
bufferedwriter.write(line); 
bufferedwriter.flush(); 
System.out.println(line); 
    } 
    bufferedwriter.flush(); 
    bufferedwriter.close(); 
    proc.waitFor() 

Когда я это делаю, я вижу, что выполняется только первая строка в create_tables.sql. Код выхода для процесса равен 0, и нет другой ошибки или вывода.

ответ

5

Exec возвращает объект процесса к вам.

процесс getInputStream и getOutputStream методы.

Просто используйте те, чтобы захватить входной поток и начать толкаться байтов в него. Не забудьте прочитать выходной поток или процесс может блокироваться.

+0

и поток ошибок, конечно. Или объедините выходные данные и потоки ошибок с помощью метода redirectErrorStream (boolean) ProcessBuilder и прочитайте объединенные потоки. –

1

Переназначение - это функциональность среды OS shell/cmd. Чтобы правильно их вызывать, мы должны использовать Runtime.exec (String []) вместо Runtime.exec (String). Вот код.

public Result executeCmd(String[] cmds, boolean waitForResult) 
{ 
    Result result = new Result(); 
    result.output = ""; 
    try 
    { 
     for(int i=0;i<cmds.length;i++) 
     { 
      System.out.println("CMD["+i+"]::"+cmds[i]); 
     } 
     System.out.println(""); 
     Process process = null; 
     if(cmds.length > 1) 
      process=Runtime.getRuntime().exec(cmds); 
     else 
      process=Runtime.getRuntime().exec(cmds[0]); 
     if (waitForResult) 
     { 
      StreamGobbler errordataReader = new StreamGobbler(process 
        .getErrorStream(), "ERROR"); 

      StreamGobbler outputdataReader = new StreamGobbler(process 
        .getInputStream(), "OUTPUT"); 

      errordataReader.start(); 
      outputdataReader.start(); 

      int exitVal = process.waitFor(); 
      errordataReader.join(); 
      outputdataReader.join(); 
      result.returnCode = exitVal; 
      result.output = outputdataReader.output; 
      result.error = errordataReader.output; 
     } 
    } 
    catch (Exception exp) 
    { 
     result.exp = exp; 
     result.returnCode = -1; 
    } 
    return result; 
} 

И этот метод вызывается с помощью

Result result = executeCmd(cmds, true); 

где

CMD[0]::cmd 
CMD[1]::/c 
CMD[2]::.\mysql\bin\mysql --host=<hostname> --port=<portNum> -u <userName> < .\scripts\create_tables.sql 
Смежные вопросы