Сделайте так, чтобы команды WinSCP выполнялись синхронно в PowerShell

442
jpmc26

Я пытаюсь использовать WinSCP для сценария синхронизации каталогов с местоположением WebDAV. Я запускаю это так из PowerShell:

.\WinSCP.exe -log=.\winscp.log -command "open davs://username:password@www.example.com/" "synchronize remote .\test-files /path/to/webdav/test-files" "exit" 

Это отлично работает. Файлы синхронизируются. Я удалил каталог WebDAV и повторно запустил его, чтобы увидеть, что файлы составляют его там.

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

Вот команда PowerShell, которая демонстрирует проблему:

& { .\WinSCP.exe -log=.\winscp.log -command "open davs://username:password@www.example.com/" "synchronize remote .\test-files /path/to/webdav/test-files" "exit" Get-Date Write-Host 'Exit code:' $LASTEXITCODE Start-Sleep -Seconds 30 Get-Content -Tail 6 .\WinSCP.log } 

Выход:

Tuesday, April 17, 2018 20:41:52 Exit code: 0 . 2018-04-17 20:42:15.025 Copying finished: Transferred: 177, Elapsed: 0:00:20, CPS: 9/s > 2018-04-17 20:42:15.025 Script: exit . 2018-04-17 20:42:15.025 Script: Exit code: 0 . 2018-04-17 20:42:15.025 sess: Destroying session. . 2018-04-17 20:42:15.025 sess: Closing connection. . 2018-04-17 20:42:15.025 sess: Connection closed. 

Как видите, WinSCP все еще записывал журнал через 20 секунд после выхода из команды. Это не имеет большого смысла. Как WinSCP может определить, сработала ли команда до ее завершения? Как я могу заставить WinSCP остановиться и дождаться завершения команды до ее выхода и до того, как она сообщит об успехе или неудаче?

1

1 ответ на вопрос

1
Martin Prikryl

PowerShell не ожидает завершения работы приложений с графическим интерфейсом, прежде чем перейти к следующей команде.

Чтобы решить эту проблему, можно использовать трюк с конвейером, как показано в разделе Как заставить PowerShell ждать завершения каждой команды перед началом следующей?

.\WinSCP.exe ... | Out-Null 

Хотя проще использовать интерфейс сценариев WinSCPwinscp.com . Это консольный эквивалентwinscp.exe


Хотя интересно, что ваш синтаксис командной строки не создает winscp.logфайл журнала для меня в любом случае. Кажется, что PowerShell повреждает командную строку, когда -используется для коммутаторов. С /этим работает:

.\WinSCP.com /log=.\winscp.log /command "open davs://username:password@www.example.com/" "synchronize remote .\test-files /path/to/webdav/test-files" "exit" 
Я полагаю, что мог воспроизвести это в командной строке. Я просто выбрал PowerShell для удобства выкладывания метки времени и чтения файла. (Это также сделало вставку всей последовательности команд сразу легче, учитывая сон.) Но мне придется повторить тестирование завтра, так как я сейчас не на той же машине. jpmc26 6 лет назад 0
Когда вы запускаете приложение с графическим интерфейсом из командной строки Windows (`cmd.exe`), оно также не будет блокировать приглашение. Но он будет заблокирован при запуске из файла .bat. Опять же, используйте `winscp.com`, чтобы решить эту проблему. Martin Prikryl 6 лет назад 0
Благодарю. Не уверен, что случилось с проблемой `-` vs.` / `. Я знаю, что в документах в основном написано `/`, но я обычно пробую `-` на всех моих исполняемых вызовах и предпочитаю, когда это работает, из-за использования слешей для других целей (например, разделителей каталогов). Поддержка обоих не является чем-то необычным. Используете ли вы последнюю версию (5.13.1 (сборка 8265))? jpmc26 6 лет назад 0
Дело не в WinSCP. WinSCP доволен `-`. Но если я выполню ваш точный сценарий PowerShell, в диспетчере задач можно увидеть, что PowerShell добавляет пробел между `-log =` и `. \ Winscp.log`. https://i.stack.imgur.com/s1t30.png Что не работает. Это заставляет WinSCP рассматривать `. \ Winscp.log` как имя хоста для подключения, что вызывает ошибку (но файл сценария все равно выполняется, но запись в журнал не происходит). Если я заменю `-` на` / `, пробел не добавляется. Martin Prikryl 6 лет назад 0
Может быть, разница в версии PowerShell? Что-то еще, что может это исправить, - заключить весь аргумент в кавычки, чтобы минимизировать обработку команды PowerShell. Если это работает для вас, я могу обновить вопрос. jpmc26 6 лет назад 0
Это нормально, это не совсем основная часть вопроса. Martin Prikryl 6 лет назад 0