executa o script como outro usuário a partir de um script raiz sem o tty stdin

4

Usando o CentOs, quero executar um script como 'treinamento' do usuário como um serviço do sistema. Eu uso o daemontools para monitorar o processo, que precisa de um script de inicialização que é executado como root e não tem nenhum padrão tty.

Abaixo, dou minhas cinco tentativas diferentes, todas falharam.

  1. :

    #!/bin/bash
    exec >> /var/log/training_service.log 2>&1
    setuidgid training training_command
    

    Esta última linha não é boa o suficiente, pois para o training_command, precisamos de um ambiente para que o usuário do trash seja configurado.

  2. :

    su - training -c 'training_command' 
    

    Isso parece ( Executar um script de shell como um usuário diferente ) mas dá ' standard in must be tty ' como su certificando-se de que tty esteja presente para potencialmente aceitar senha. Eu sei que eu poderia fazer isso desaparecer, modificando o / etc / sudoers (a la link ), mas estou relutante e inseguro de consequências.

  3. :

    sudo -u training -i bash -c 'source $HOME/.bashrc; training_command'
    

    Uma variação sobre o mesmo tema: ' sudo: sorry, you must have a tty to run sudo '

  4. :

    runuser - training -c 'training_command'  
    

    Este dá runuser: cannot set groups: Connection refused . Não encontrei nenhum sentido ou resolução para este erro.

  5. :

    ssh -p100 training@localhost 'source $HOME/.bashrc; training_command'
    

    Este é mais uma piada para mostrar desespero. Mesmo este falha com Host key verification failed. (a chave do host está em known_hosts, etc).

Nota: todo o 2,3,4 funciona como deveria se eu executar o script wrapper a partir de um shell de raiz. os problemas só ocorrerão se o monitor de serviço do sistema (daemontools) o iniciar (no tty terminal eu acho).

Estou preso. Isso é algo tão difícil de alcançar?

Eu aprecio toda a visão e orientação para as melhores práticas.

(isso também foi postado no superusuário: link )

    
por Viktor Trón 08.06.2012 / 21:17

7 respostas

5

Você precisará desativar a configuração requiretty em /etc/sudoers para root . Adicione a seguinte linha via visudo :

Defaults:root !requiretty

Você também precisará da seguinte linha em /etc/sudoers , então root pode fazer tudo (isso deve ser ativado por padrão, mas verifique se):

root ALL=(ALL) ALL

Então você pode fazer o seguinte:

sudo -u training /path/to/training_command
    
por 04.04.2014 / 23:46
3

Este parece ser essencialmente um caso especial de esta questão ; podemos usar script -c para fingir um tty. O único problema é que, por algum motivo, não consigo usar esse truque para trabalhar diretamente com su , e sudo é um pouco feio se você realmente precisar originar ~/.bashrc antes de training_command . Experimente:

echo password | script -c "sudo su - training -c training_command" 
    
por 02.04.2014 / 11:50
0

Escolha o primeiro e defina as variáveis de ambiente que você precisa.

Se você já usa daemontools, então não crie ou mexa com os arquivos de log manualmente. Daemontools faz esse trabalho para você.

Este é o script para o script de execução do aplicativo

#!/bin/bash
exec 2>&1
exec setuidgid training sh -c 'YOURVARIABLE=yourvalue exec training_command'

Em seguida, você cria um script de execução de diretório log com seu próprio runcript.

Consulte esta entrada para configurar um log: link

    
por 09.06.2012 / 20:56
0

Plagiando minha resposta aqui: Iniciando um script como outro usuário

Você poderia usar o start-stop-daemon assim:

/sbin/start-stop-daemon --background --start --exec /path/to/training.sh --user training --pidfile=/path/to/training.pid --make-pidfile

em que training.sh é algo assim:

#!/bin/sh
exec >> /var/log/training_service.log 2>&1
source /home/training/.bashrc
training_command
    
por 02.04.2014 / 14:19
0

Sob o SSH, você pode executar o comando foo.sh no usuário normal:

$ ssh [email protected] bash /path/to/foo.sh

se um dos comandos foo.sh precisar de privilégios de root, por exemplo, netstat , coloque-o dentro do comando su dessa forma (substitua o original bruto netstat -tunple ):

su -c "netstat -tunpl" root

e execute foo.sh da seguinte forma:

$ ssh -t [email protected] bash /path/to/foo.sh

Isso solicitará a senha de acesso, a primeira será para normal_user e a segunda será para root .

    
por 04.08.2015 / 10:22
0

Execute seu comando com o SSH.

  1. faça a configuração da chave ssh para efetuar login sem senha para outro usuário. Aqui está um tutorial para este propósito: link

  2. Execute o comando com ssh: ssh -l treinamento -i key_file "training_command"

por 13.06.2016 / 15:57
-1

Tente isto:

#!/bin/bash
sudo -u training training_command > /var/log/training_service.log 2>&1

Se isso falhar, poste a saída de /var/log/training_service.log .

    
por 09.06.2012 / 03:46