¿Cómo puedo establecer variables de entorno para un proceso rsync remoto?

12

Cuando uso rsync para copiar archivos de una computadora a otra, se inicia un proceso rsync en ambos extremos. Sin embargo, en el extremo remoto, los archivos de inicialización de shell aparentemente no se leen, por lo que no puedo configurar variables de entorno para el proceso rsync remoto. Desafortunadamente, hay un servidor al que necesito rsync en el que rsync requiere una variable de entorno para funcionar. No soy administrador del servidor, por lo que no puedo cambiar la configuración global. ¿Qué puedo hacer para configurar las variables de entorno para un proceso rsync remoto?

Ryan C. Thompson
fuente
¿Cómo iniciar el proceso rsync en el servidor? ¿Podría activar un script a través de ssh?
Kraftan el
Cuando lo haga rsync localfilename remotehost:remotefilename, se iniciará un proceso rsync en el servidor. No estoy exactamente seguro de cómo, pero no lee ningún archivo de inicialización de shell.
Ryan C. Thompson, el

Respuestas:

20

~/.profilepor lo general, no se lee cuando ejecuta ssh somecommand, a diferencia de una sesión ssh interactiva (u otro método de inicio de sesión donde inicia una sesión interactiva).

Ssh admite el envío de variables de entorno. En OpenSSH, use la SendEnvdirectiva en ~/.ssh/config. Sin embargo, la variable de entorno específica debe habilitarse con una AcceptEnvdirectiva en la configuración del servidor , por lo que es posible que esto no funcione para usted.

OpenSSH también permite configurar variables de entorno en el lado del servidor. Nuevamente, esto debe habilitarse en la configuración del servidor, aquí con la PermitUserEnvironmentdirectiva. Las variables se pueden establecer en el archivo ~/.ssh/environment. Suponiendo que use la autenticación de clave pública, también puede establecer variables por clave en ~/.ssh/authorized_keys: agregar environment="FOO=bar"al comienzo de la línea correspondiente.

Una cosa que creo que siempre funciona (por extraño que parezca) siempre y cuando esté utilizando la autenticación de clave pública es (ab) usar la command=opción en el authorized_keysarchivo. Una clave con una commandopción es buena solo para ejecutar el comando especificado; pero el comando en el authorized_keysarchivo se ejecuta con la variable de entorno SSH_ORIGINAL_COMMANDestablecida en el comando que especificó el usuario (vacío para sesiones interactivas). Por lo tanto, puede usar algo como esto ~/.ssh/authorized_keys(por supuesto, no se aplicará si no usa esta clave para autenticar):

command="export LD_LIBRARY_PATH=\"$HOME\"/lib;
         if [ -n \"$SSH_ORIGINAL_COMMAND\" ]; then
           eval \"$SSH_ORIGINAL_COMMAND\";
         else exec \"$SHELL\"; fi" ssh-rsa …

Tenga en cuenta que puse saltos de línea arriba para la legibilidad, pero en realidad esto debe estar todo en una línea.

Otra posibilidad es escribir un script de envoltura ~/bin/rsync-wrapperen el servidor, algo así como

#!/bin/sh
. ~/.profile
exec rsync "$@"

Luego pase --rsync-path='bin/rsync-wrapper'la rsynclínea de comando. El argumento para --rsync-pathse expande mediante un shell, por lo que si lo prefiere, puede hacer que la línea de comando rsync sea autónoma pasando algo como --rsync-path='. ~/.profile; rsync'.

Hay otra vía que depende de que su shell de inicio de sesión sea bash o zsh. Bash siempre lee ~/.bashrccuando es invocado por rshd o sshd, incluso si no es interactivo (pero no si se llama como sh). Zsh siempre lee ~/.zshenv.

## ~/.bashrc
if [[ $- != *i* ]]; then
  # Either .bashrc was sourced explicitly, or this is an rsh/ssh session.
  . ~/.profile
fi

## ~/.zshenv
if [[ $(ps -p $PPID -o comm=) = [rs]shd && $- != *l* ]]; then
  # Not a login shell, but this is an rsh/ssh session
  . ~/.profile
fi
Gilles 'SO- deja de ser malvado'
fuente
Bueno, eso lo resume bastante bien. Esperaba que hubiera una mejor manera que usar un script de envoltura.
Ryan C. Thompson, el
Pero espera un minuto. Si mis archivos de inicio de shell no se leen, ¿cómo puede incluso encontrar el binario rsync en el servidor? Instalé en ~ / usr, una ubicación no estándar que tengo que agregar a mi $PATHen mis scripts de inicio de shell.
Ryan C. Thompson el
@ Ryan: en realidad había olvidado el método más directo (ver mi edición), pero también requiere que se active una directiva en la configuración del servidor. Si ha encontrado una manera de tenerlo PATHen cuenta, debería poder establecer cualquier otra variable allí. (Si esto no funciona, trate de añadir tantas huellas como sea posible, a partir de set -xcualquier secuencia de comandos shell; reemplazar el rsyncbinario por un guión envoltorio que vuelca el medio ambiente en un archivo binario a continuación, llama a la real.)
Gilles 'SO - deja de ser malvado '
¿Qué hay de ~/.ssh/rc?
Ryan C. Thompson, el
@Ryan: ~/.ssh/rcse ejecuta mediante un proceso de shell separado. Creo que su mejor apuesta es un script de envoltura o --rsync-path='. ~/.profile; rsync'. O recompile rsynccon un rpath adecuado según su otra pregunta.
Gilles 'SO- deja de ser malvado'