groovy (java): exec() не отсоединяться от процесса (Intellij IDEA vs Maven+TestNG)

У меня есть тестовый проект Groovy Maven2 с включенным плагином TestNG и Surefire.

Я хочу запустить внешний процесс (файл *.cmd, который запускает некоторый файл *.exe) в последнем методе тестирования, завершить мои тесты и оставить процесс запущенным после тестов.

Я пробовал следующие коды, чтобы сделать это:

1 попытка

def builder = new ProcessBuilder('cmd','/c <name>.cmd')
builder.directory( ( new File( <path_to_working_directory> ) ) )
builder.start()

2 попытка (с параметром start cmd и без него)

Runtime.getRuntime().exec( "cmd /c start <name>.cmd", null , ( new File( <path_to_working_directory> ) ) )

3 попытка

( new AntBuilder() ).exec(
    dir: "<path_to_working_directory>",
    executable: "<name>.cmd"
)     

Где .cmd:

set path=<path_to_execFile>;%path%
start <execFileName>.exe

Когда я запускаю каждый из этих кодов из Intellij IDEA с помощью функции «Выполнить» (Alt + Shift + F10), коды выполняются успешно, процесс запускается и запускается после завершения теста.

Когда я запускаю каждый из этих кодов как из задачи Intellij IDEA Maven, процесс чистой установки Maven (и даже задачи Maven из Jenkins) успешно запускается, но тест остается запущенным. Мне нужно убить его вручную. Когда я вручную убиваю тестовый процесс (процесс Maven), мой запущенный внешний процесс продолжает работать так, как я ожидаю.

Этот зависший процесс тестирования - моя головная боль на данный момент.

Я просмотрел множество материалов, но не нашел ни первопричины, ни исправления, ни даже обходного пути для этой проблемы. Я вижу, что все мои попытки (пожалуй, кроме AntBuilder()) создают отсоединенные процессы. Я предполагаю, что это может быть связано с настройками JVM. Но я не нашел к какому.

Кроме того, я пытался

"full command to run my cmd".execute()

но мне тоже не помогло.

Не могли бы вы помочь мне решить проблему?

Заранее спасибо!


person zubactik    schedule 11.06.2013    source источник


Ответы (1)


Итак, я не вижу здесь ответов на свой вопрос. Но у меня есть обновления.

Я обнаружил, что могу использовать инструмент PsExec вместо прямого вызова cmd:

def builder = new ProcessBuilder( 'psexec', 'cmd', '/c', '<name>.cmd' )
builder.directory( ( new File( <path_to_working_directory> ) ) )
builder.start()

И этот код отлично работает, когда я запускаю его только из чистого Maven (не из Jenkins): процесс запущен, задача Maven успешно завершается, процесс продолжает работать.

Но во время выполнения этого кода как части некоторой задачи Maven2 Jenkins я снова столкнулся с проблемой: psexec запущен, но задача Jenkins запущена, и мой процесс не запускается до тех пор, пока я не завершу задачу Jenkins вручную.

Чтобы избежать этой проблемы, я создал простой дополнительный скрипт службы Groovy, который запускаю в режиме прослушиванияЗапись TCP-сервера) на целевой машине вручную во время первоначальной подготовки машины. Этот скрипт работает на машине всегда.

Я отправляю этому слушателю имя командного файла для выполнения из моего теста, который я запускаю из Jenkins, и он успешно выполняет все cmds: процессы запускаются, задача Jenkins успешно завершается, процессы продолжают работать. Я использую ProcessBuilder внутри этого слушателя.

Для отправки имени я использую простой сокет (написание TCP-клиента)

Кроме того, я нашел как отсоединить дочерний элемент от дерева процессов на win32?. Но для меня система по-моему выглядит более заводной, я думаю.

person zubactik    schedule 19.06.2013