Bash с использованием сценария Expect выдает ошибку при вызове ssh

В сценарии bash у меня есть сегмент ожидания, в котором он отправляет команды на машину через ssh. У меня там есть bash -c, так как мне нужно установить переменные среды в этой команде. Но я получаю сообщение об ошибке:

extra characters after close-quote
    while executing
"spawn -noecho ssh -t anon@machine  'bash -c "cd /tmp;"'
"

Когда я запускаю эту команду вручную ssh -t anon@machine 'bash -c "cd /tmp;"', она работает нормально. Что здесь не так?

   ssh_param = "-t ${scp_user}${_machine}  'bash -c \"cd /tmp;\"'"

    /usr/bin/expect <<-EOF1
    set timeout 360
    spawn -noecho ssh ${ssh_param}
    expect {
        "password:" { 
             send "${_pass}\r" 
         }
         eof { exit }
    }
    expect {
         eof { exit }
    }
EOF1

Кроме того, если я устанавливаю ssh_param как ssh_param = "-t ${scp_user}${_machine} \"cd /tmp;\"", это работает, так почему же bash -c ... приводит к сбою?

Взгляните на Обмен ключами SSH.

Cyrus 04.09.2024 19:50

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

gunnersFc 04.09.2024 19:54

Взгляните на man sshpass (поставщик неинтерактивных паролей ssh).

Cyrus 04.09.2024 20:03

Ожидание предоставляет возможность включить вывод отладки. Вы можете включить это в свой сценарий, чтобы получить больше информации о том, что делает ожидаемый результат. Добавьте следующую строку в начало сценария ожидания: exp_internal 1

GoinOff 04.09.2024 20:05

Мне нужно, чтобы этот сценарий можно было запускать и на компьютерах с Windows.

gunnersFc 04.09.2024 20:06

Вы можете запустить «expect» с опцией -d, чтобы включить режим подробной отладки из командной строки: «expect -d your_script.exp»

GoinOff 04.09.2024 20:06

Сценарий представляет собой сценарий bash, часть исключений предназначена только для раздела пароля в сценарии bash. Когда я добавил exp_internal 1, он не показывает никаких других результатов, просто та же ошибка.

gunnersFc 04.09.2024 20:14

Вы пытались установить exp_internal 1 в ожидаемом коде? Незадолго до этого set timeout 360

GoinOff 04.09.2024 20:37

Это потому, что tcl (и, следовательно, ожидаемый) не имеет особого значения для одинарных кавычек, но имеет значение для двойных кавычек.

Shawn 04.09.2024 20:48

Я всегда предлагаю писать все это в tcl/expect вместо того, чтобы пытаться вызвать ожидаемый результат из сценария оболочки. Удаляет целый слой проблем с цитатами.

Shawn 04.09.2024 20:50

Я бы избавился от 'bash -c \"cd /tmp;\"' и перешел в /tmp в логике expect {.

GoinOff 04.09.2024 21:30

Я удалил остальную часть команды после cd /tmp; для поста, но мне также нужно установить переменную среды и после этого запускать другие команды. Я не могу удалить компакт-диск /tmp

gunnersFc 04.09.2024 22:03

Я говорю, что нужно поместить cd /tmp в ожидаемый код, а не в логику вашего ssh-соединения. настройку переменных окружения также можно выполнить таким же образом.

GoinOff 04.09.2024 22:20
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
1
13
64
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

После того, как bash выполнит замену параметров в Heredoc, expect запускается с помощью

set timeout 360
spawn -noecho ssh -t XXXYYY 'bash -c "cd /tmp;"'
expect {
    "password:" { 
         send "ZZZ\r" 
     }
     eof { exit }
}
expect {
     eof { exit }
}

Скрипты expect написаны на языке tcl, который в основном работает путем разделения строки на слова и обработки первого слова как команды, которую нужно выполнить, а остальные слова - как аргументы после выполнения замен. Что-то вроде оболочки, но с более разумными правилами. 12 правил синтаксического анализа tcl называются Додекалог.

Одинарные кавычки не используются для группировки нескольких слов в одно — только двойные кавычки, [] (которые указывают на команду и аргументы для оценки) и {} (которые ничего в них не заменяют и не оценивают). Итак, линия

spawn -noecho ssh -t XXXYYY 'bash -c "cd /tmp;"'

делится на spawn, -noecho, ssh, -t, XXXYYY, 'bash, -c и "cd /tmp;"'. Одинарная кавычка в конце после закрывающей двойной кавычки последнего слова является ошибкой. Обычно в tcl вместо этого вы просто заключаете его в фигурные скобки (или двойные кавычки, но тогда вам придется экранировать вложенные):

spawn -noecho ssh -t XXXYYY {bash -c "cd /tmp;"}

это означает, что установленная вами переменная оболочки должна выглядеть примерно так

ssh_param = "-t ${scp_user}${_machine} {bash -c \"cd /tmp;\"}"

Написание всего этого в tcl/expect вместо оболочки, которая создает сценарии ожидания для выполнения, облегчит жизнь, поскольку вам не придется переключаться между различными стилями цитирования, беспокоиться о расширении параметров оболочки, вызывающем создание недопустимого tcl, как в этом примере, и т. д.

Я подумаю над тем, чтобы изменить его, спасибо большое за {bash -c \"cd /tmp;\"} идею, это была именно она.

gunnersFc 05.09.2024 21:17

Другие вопросы по теме

Почему моя программа, запущенная из сценария bash, останавливается, когда сценарий находится в фоновом режиме, но только тогда, когда он получает стандартный ввод из именованного канала?
Когда grep ищет шаблоны в файле с кавычками и/или без кавычек в bash?
Как извлечь столбцы из файла CSV, обработать и создать файл CSV на основе результата извлечения и обработки?
Скрипт Bash, который принимает несколько аргументов пути и проверяет, можно ли там успешно создать файлы
Как мне отслеживать и уничтожать все процессы, порожденные запуском сценария, не зная имен подпроцессов?
Псевдоним Git для извлечения всех удаленных веток
Git sed игнорировать двоичные файлы
Как передать переменную оболочки, возвращаемую из Pythonscript, в другую оболочку для запуска другого Pythonscript в правиле Makefile?
Пользовательский номер строки/префикс для текстового файла с использованием awk/sed
Перемещение launchpad.db с пробелами

Похожие вопросы

Почему моя программа, запущенная из сценария bash, останавливается, когда сценарий находится в фоновом режиме, но только тогда, когда он получает стандартный ввод из именованного канала?
Когда grep ищет шаблоны в файле с кавычками и/или без кавычек в bash?
Как извлечь столбцы из файла CSV, обработать и создать файл CSV на основе результата извлечения и обработки?
Скрипт Bash, который принимает несколько аргументов пути и проверяет, можно ли там успешно создать файлы
Почему bash не завершает выполнение сценария после ошибки внутри скобок?
Как запустить эмулятор терминала во время работы оболочки?
Как мне отслеживать и уничтожать все процессы, порожденные запуском сценария, не зная имен подпроцессов?
Bash: медленнее использовать zcat по сравнению с cat+zcat или cat+pv+zcat
Как передать переменную оболочки, возвращаемую из Pythonscript, в другую оболочку для запуска другого Pythonscript в правиле Makefile?
Правильное использование кавычек при подстановке команд – как?