Як я можу передавати змінну середовища за допомогою команди ssh? [дублікат]


42

Як я можу передати значення команді ssh, щоб середовище, що запускається на хост-машині, починалося з певної змінної середовища, встановленої на мій вибір?

EDIT: Метою є передача поточного робочого столу kde (від dcop kwin KWinInterface currentDesktop) до нової створеної оболонки, щоб я міг повернути nfs-місця до мого примірника JEdit на оригінальний сервер, унікальний для кожного робочого столу KDE. (Використання такого механізму, як emacsserver / emacsclient )

Причина, коли декілька екземплярів ssh можуть бути в польоті одночасно, полягає в тому, що, коли я налаштовую своє середовище, я відкриваю купу різних екземплярів ssh для різних машин.

Відповіді:


17

~/.ssh/environmentФайл може бути використаний для установки змінних , які ви хочете зробити доступними для віддалених команд. Вам потрібно буде включити PermitUserEnvironmentв конфігурації sshd.

Змінні, встановлені таким чином, експортуються в дочірні процеси, тож ви можете:

echo "Foo=Bar" > sshenv
echo "Joe=37" >> sshenv
scp sshenv user@server:~/.ssh/environment
ssh user@server myscript

і таємниця буде знати, що Фоо - Бар, а Джо - 37 років.


3
змінна повинна змінити потенційно кожен ssh-виклик
Росс Роджерс,

1
Можливо, краще опишіть, що ви намагаєтеся зробити і чому. Можуть бути й інші рішення. Файл оточення повинен був би динамічно генеруватися при кожному ssh-дзвінку, що неможливо.
EmmEff

Що зміниться? Значення цих змінних або навіть їх назви?
innaM

2
Ця відповідь насправді не відповідає на питання.
інтуїтив

1
Це порушиться, якщо два процеси намагатимуться зробити це з різними наборами значень одночасно
nafg

55

SendEnvВаріант ваш хлопець.

~ / .ssh / config: (локально)

SendEnv MYVAR

/ etc / ssh / sshd_config: (на віддаленому кінці)

AcceptEnv MYVAR

Тепер, незалежно від значення $MYVARлокального значення, воно стає доступним і у віддаленому сеансі.
Якщо ви входите кілька разів, кожен сеанс матиме власну копію з $MYVAR, можливо, різними значеннями.

~/.ssh/environmentпризначений для інших цілей. Цей вид діє як $ENVфайл при віддаленому виконанні команд без оболонок .


6
також можна передавати (більш корисно) через командний рядок як ssh myserver -o SendEnv="MYVAR", так що ви можете зробити це динамічним у сценаріях.
Майк Кемпбелл

31

Ви можете передавати значення за допомогою команди, подібної до наступної:

ssh username@machine VAR=value cmd cmdargs

Ви можете протестувати за допомогою:

ssh machine VAR=hello env

На tcsh, здається, працює наступне:

ssh machine "setenv VAR <value>; printenv"

Виглядає так, що це добре працює в середовищі bash. Шкода, що я в корпоративному середовищі tcsh.
Росс Роджерс

2
Як я можу використовувати сеанс інтерактивно?
luckydonald

1
Зауважте, що перший приклад працює лише для першої команди, якщо ви з'єднуєте команди разом (з &&). Використання bash, export VAR=value;замість setenv в третьому класі працює в цьому випадку.
contrebis

2
Це я і закінчила! Куди б ви не поїхали, візьміть із собою оточення. Ви можете зробити це так: ssh user@host "$(<env_to_source.sh) command ..." . У env до джерела я маю export var=value ; окремі рядки (пам'ятаю крапку з комою).
Томаш Гандор

@TomaszGandor: роками пізніше, все ще ідеально - дозволяє мені навіть передавати складні речі, такі як PROMPT_COMMAND там, без яких потрібно турбуватися про втечу :-) 1000 спасибі.
Червона таблетка

29

Також є жахливий, жахливий злом.

Якщо ваш сценарій споживає змінну на віддаленому кінці (тобто ви можете назвати її все, що завгодно), ви можете зловживати змінними локалі. Будь-яка змінна форми LC_ * буде передана дослівно, без жодних вимог до конфігурації.

Наприклад, у нас є декілька серверів бастіонів у одного з моїх клієнтів. Я ненавиджу підключатися до нього, просто підключатися до іншого сервера ... та іншого сервера ... кожного разу. У мене є сценарій, який поводиться так само, як SSH, за винятком того, що він розумний.

В основному, якщо встановлено LC_BOUNCE_HOSTS, він розбиває його на пробіли і знімає перший хост. Потім він відскакує і запускає той самий сценарій. У вузлі призначення цей список з часом порожній, тому він виконує команду. У мене також є режим налагодження (що чудово під час мережних проблем), який встановлюється LC_BOUNCE_DEBUG. Оскільки ssh магічно передає все це разом, мені не потрібно нічого робити, крім розпізнавання кінця списку хостів (що я роблю з опцією -).

Я відчуваю брудність кожного разу, коли це використовую, але він працює скрізь, де я його пробував.


2
Чому б ви використовували щось подібне замість вбудованої ProxyCommandопції OpenSSH ? Відредагуйте свій ~/.ssh/configі додайте такий блок, як Host *.example.com: ProxyCommand -ssh -W %h:%p bastionhostі дозвольте йому тунель ваших зв’язків.
Кірк Штраузер

1
Для тунелів це не так вже й погано. Для навколишнього середовища дві причини: Перша, PermitUserEnvironment вимагає доступу адміністратора для налаштування на сервері, щоб передавати їх безпосередньо. Передача їх через командний рядок також справді важко отримати правий біг. Два, кілька бастіонів повинні бути відбиті, що робить це трохи складніше - особливо коли з вихідного хоста не зрозуміло, який шлях пройти до певного хоста призначення. Простіше сказати: "bounce-ssh bast1 bast2 nodeX - rm -rf /", ніж підтримувати маршрути для еволюціонуючої сукупності хостів у серії файлів ssh-config.
Джейсон

Гарний улов !! Так чудово і трохи брудно !!
zw963

2
Це жахливо. Браво. 👏
Пі-Дельпорт

1
Це жахливо чудово, дякую! Я використав це для ще одного страшенно приємного злому ! :)
мастило

1
bla="MyEnvSelection=dcop"
ssh user@host "export $bla && ./runProg"

На баші я тестував:

$ echo '#!/bin/sh' > readEnv.sh
$ echo 'echo "MyEnv: "$MyEnvFromSSH' >> readEnv.sh

$ scp readEnv.sh user@host:~/
$ bla="MyEnvFromSSH=qwert"
$ ssh user@host "export $bla && ./readEnv.sh"
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.