[CMD] Как диагностировать проблему или ошибки в синтаксисе, когда Bat-файл "вылетает"?

Dragokas

Angry & Scary Developer
Команда форума
Супер-Модератор
Разработчик
Клуб переводчиков
Сообщения
7,813
Реакции
6,592
Как запустить Batch-файл с протоколированием?
Как диагностировать проблему или ошибки в синтаксисе, когда Bat-файл не работает или "вылетает".


Чтобы увидеть ошибки в синтаксисе, которые приводят к критическому завершению Batch-файла,
необходимо запустить его из CMD.exe (интерпретатора).

Как?
Этап 1. Подготовка:
Если у Вас в скрипте указана директива для скрытия вывода выполняемых команд:
Код:
@echo off
Она обычно идет первой строкой в коде.
- Удалите ее, или закомментируйте:
Код:
::echo off
иначе будет сложно определить, какая команда вызывает "падение" скрипта или ошибку.

Этап 2. Выполнение скрипта с перенаправлением вывода в файл протокола

Вариант 1. Для систем Windows XP и ниже:

ПУСК -> Выполнить (либо Win + R), вводим CMD, нажимаем {ENTER}

Откроется маленькое черное окно - консоль.
В нем Вы увидите путь к каталогу, в котором будут выполняться команды в данный момент.
Вам нужно перейти в каталог, где расположен бат-файл.
Например, Вам нужно запустить Batch-файл с именем script.cmd, расположенном в папке temp на диске C,
тогда вводим команды:

(ввод каждой строки подтверждаем клавишей {ENTER})

Вариант а) С выводом в консоль:

Код:
cd /d "c:\temp"
call script

Вариант б) С логированием во внешний файл

Код:
cd /d "c:\temp"
script > log.txt

После ввода первой строки Вы увидите на экране приглашение вида:
c:\temp>
что свидетельствует об успешном переходе в каталог c:\temp

Вариант 2. Для систем Windows Vista и выше (переход в папку с батником сразу):

1. Перейдите на уровень выше от каталога, где находится Batch-файл
(иными словами: Вам нужно видеть пиктограмму значка папки, в которой находится Batch-файл)
Если Вы видите перед собой сам Batch-файл, достаточно нажать BackSpace (кнопка "стирания").

2. Наведите указатель мыши на папку с Batch-файлом.
Нажмите и удерживайте кнопку "Shift". Вместе с этим нажмите правую кнопку мыши.

3. Выберите пункт "Открыть окно команд".

Comm_Window.png

Например, Вам нужно запустить Batch-файл с именем script.cmd, расположенном в папке temp на диске C,
тогда вводим команду:

Код:
script > log.txt
Нажимаем клавишу {ENTER}

Этап 3. Анализ файла-протокола.

После завершения работы Batch-файла в папке C:\temp будет создан файл log.txt
Передайте его специалистам, либо при наличии достаточного опыта проведите анализ самостоятельно.

Данный файл сохраняется в кодировке OEM-866, поэтому открывать его нужно в соответствующем редакторе: Русский текст в консоли - CMD/BAT - Киберфорум
Как правило, критические ошибки указаны в самом конце протокола и они предваряют команду, которая их вызвала.

Этап 4. (опционально)
Если бат-файл содержит цикл или является очень большим, полезным также будет подготовить лог уже с командой @echo off
Добавьте ее в самое начало кода и повторите всю процедуру.

Альтернатива вызову батника из-под интерпретатора.
В самом начале кода пишем:
Код:
Echo. 1>&3 2>&4 3>>log.txt 4>&3
и запускаем Batch-файл.
Все команды, выводимые на экран будут сразу перенаправляться в файл.
В этом случае на экране Вы не увидите ни выполняемых команд, ни вывода.
Все они будут протоколироваться в файл log.txt.
 
Последнее редактирование:
Альтернатива вызову батника из-под интерпретатора.
Код:
Echo. 1>&3 2>&4 3>>"%~dp0log.txt" 4>&3
Иначе файл лога создается в другой папке если мы предварительно не использовали
Код:
cd /d "%~dp0"
 
Последнее редактирование модератором:
У меня был баг вызванный этим логированием, что и отображалось в логе - то что он логирует цикл меню, а на экран, как вы и обещали, не выводит (то что надо) :LOL::)
 
Да, эта специфическая команда поможет, если Вы доберетесь до вылета скрипта "с закрытыми глазами". :)
У меня был баг вызванный этим логированием
Так я не понял, чем был вызван?
 
Да, интересно. Позже проанализирую.
Вообще, это недокументированная фишка (сам нашел). Она не обязана всегда работать, особенно с меню.

Стандартный способ (добавлю в шапку) - это запустить сначала cmd.exe, а из него батник call start.cmd
или написать в файловом менеджере (думаю, многие пользуются, например Total Copmmander), такую строку:
Код:
cmd /k start.cmd
тогда по завершению работы основного start.cmd окошко батника не закроется.
++ не забыть в батнике закомментировать строку @echo off
В этом способе сложность может быть только, если используется само-перезапуск батника (например, в моей функции само-элевации прав),
тогда консоль с повышенными правами будет создана, как новый процесс.
 
Последнее редактирование:
Console Window Interceptor - перехват вывода чужого консольного окна
Автор: Dragokas
Спасибо The trick за пример работы с буфером консоли.

Сфера применения:
Автоматически подключается к любому всплывающему консольному окну и не дает его закрыть по завершению работы (exit).
Перехватывает текст и выводит его в окне формы.

Будет полезен для получения текста консольных приложений, которые нельзя запустить через cmd /c.

Состав: EXE + VB6 src.

Скриншот 2014-11-21 22.20.39.png
 

Вложения

  • C_Intercept.zip
    21 KB · Просмотры: 18
Последнее редактирование:
Пример перехвата ошибки в выводе команды AVZ ExecuteFile:

1. Запускаем Console Interceptor.
Выставляем интервал поиска окон в 1 мс.
Нажимаем "Искать консольные окна".
2. Запускаем AVZ. Файл -> Выполнить скрипт:
Код:
begin
  ExecuteFile('ipconfig', 'flushdns', 1, 0, false);
end.
Запустить. Результат:

Скриншот 2014-11-22 17.43.12.png


В чем ошибка, думаю, сами должны догадаться.

Примечание по ExecuteFile:
Режим (Mode) должен быть обязательно не 0 (видимое окно).
Terminate = false или WaitTime = 0 необязательно выставлять такими.
AVZ в любом случае получит сигнал о завершении работы процесса,
тем не менее консольное окно не закроется, пока к нему подключено в качестве отладчика другое приложение.

Чтобы не повалить перехватчик, необходимо сперва отключиться от консольного окна ("Deattach") кнопкой "Отключиться от окна".
 
Назад
Сверху Снизу