Вопрос или проблема
Я хочу использовать “expect
“, чтобы автоматически нажимать клавишу “<Enter>
“, когда скрипт bash запрашивает “Country Name (2 letter code) [US]:
“.
Вот expect:
/usr/bin/expect << EOF
set timeout -1
spawn /bin/bash /path/to/generate_openssl_certificate.sh
expect {
"Country Name (2 letter code) [US]:" {send "\r" ; exp_continue}
}
EOF
Вот ошибка:
spawn /bin/bash /path/to/generate_openssl_certificate.sh
invalid command name "US"
while executing
"US"
invoked from within
"expect {
"Country Name (2 letter code) [US]:" {send "\r" ; exp_continue}
}"
Когда я пытаюсь использовать “-re
” для соответствия строке, она не совпадает со строкой “Country Name (2 letter code) [US]:
“:
expect {
-re "Country Name \(2 letter code\) \[US\]:" {send "\r" ; exp_continue}
}
Вот вывод, экран ожидает нажатия клавиши “<Enter>
” для продолжения:
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [US]:
Как соответствовать строке “Country Name (2 letter code) [US]:
” без использования “-re
“?
Как соответствовать строке “Country Name (2 letter code) [US]:
” с помощью “-re
“?
Expect является расширением языка Tcl.
Tcl использует квадратные скобки для подстановки команд (так же, как оболочки типа POSIX используют $(...)
).
Подстановка команд будет расширяться в строках с двойными кавычками.
Есть 2 вещи, которые вы можете сделать:
-
экранировать открывающуюся скобку
expect { -ex "Country Name (2 letter code) \[US]:" {send ...
-
использовать механизм цитирования Tcl, не выполняющий интерполяцию, фигурные скобки
expect { -ex {Country Name (2 letter code) [US]:} {send ...
Обратите внимание, что я использую точное совпадение — по умолчанию, expect использует сопоставление с шаблоном, где квадратные скобки обозначают набор символов. В данном случае вы хотите сопоставить буквальный текст в скобках.
Ответ или решение
Для решения задачи по автоматизации ввода клавиши "Enter" в сценарии bash с использованием expect
на Ubuntu, необходимо корректно обрабатывать строки с регулярными выражениями и специальными символами в Tcl. Проблема возникает из-за использования квадратных скобок, которые в Tcl воспринимаются как командная подстановка. Рассмотрим два решения:
Без использования -re
1. Экранирование квадратных скобок:
При использовании режима -ex
(exact), который осуществляет точное совпадение, необходимо экранировать квадратные скобки, чтобы они воспринимались как литералы:
expect {
-ex "Country Name (2 letter code) \\[US\\]:" {send "\r"; exp_continue}
}
2. Использование фигурных скобок:
В Tcl фигурные скобки ({}) используются для заключения строк, которые не должны интерполироваться. Это предотвращает подстановку команд:
expect {
-ex {Country Name (2 letter code) [US]:} {send "\r"; exp_continue}
}
С использованием -re
Если вы хотите использовать регулярные выражения, необходимо соблюдать правила экранирования специальных символов, таких как круглые и квадратные скобки:
expect {
-re "Country Name \\(2 letter code\\) \\[US\\]:" {send "\r"; exp_continue}
}
Причины возникновения ошибки
Ошибка, возникающая при первом выполнении скрипта, связана с неопределённым использованием квадратных скобок в строке ожидания, где Tcl пытается выполнить содержимое в качестве команды из-за отсутствия экранирования.
Оптимизация и рекомендации
- Используйте figurные скобки для строк, содержащих специальные символы.
- Для увеличения эффективности выполнения скрипта, вместо повторного вызова
spawn
можно динамически передавать строки в блок архивованияexpect
таким образом, чтобы избежать ненужных ожиданий. - Всегда тестируйте работу скрипта на небольших задачах для проверки корректности обработки ожидаемых строк.
Заключение
Использование библиотек и утилит таких как expect
может значительно облегчить автоматизацию рутинных задач в администрировании и разработке. Правильная работа со строками, содержащими специальные символы, и регулярными выражениями требует внимания к деталям и понимания особенностей используемых языков и утилит.