3

I am using jenkins to run my builds.

One of my steps is to copy over certain files and place them inside /etc/init using sudo

    <exec command="ssh -A ${host-used} '/etc/init.d/ConvertDaemon stop'" outputProperty="result" escape="false">
    </exec>
    <echo msg="${result}" />

    <exec command="ssh -A ${host-used} 'sudo Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" />
    <echo msg="${result}" />

${host-used} returns www-data@ip-address

The issue is the 2nd command.

When I run the 1st command, i can see my result printed out in the console log in jenkins.

For the 2nd command, I get a no tty present message

So I changed the 2nd command to

    <exec command="ssh -t ${host-used} -A ${host-used} 'sudo Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" />
    <echo msg="${result}" />

I get a

 Pseudo-terminal will not be allocated because stdin is not a terminal

How do I overcome this?

UPDATE:

I tried this as well.

    <exec command="ssh -t -t ${host-used} -A ${host-used} 'sudo Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" />
    <echo msg="${result}" />

I got:

bash: www-data@ipaddress: command not found
Connection to ipaddress closed.

I want to emphasize that the command is correctly used. BUT I cannot read the message.


UPDATE2:

There are times when you ask a question, but then you realize the question you want to ask is not the REAL question you want to solve.

This question is like that.

All I wanted to do is to execute a few commands run by jenkins and see the print out of the commands. These commands happen to require sudo.

Jenkins basically ssh as another user www-data to perform these commands.

I was having trouble with printing out the results in jenkins for those commands requiring sudo.

Having spent a lovely saturday working on this with some very helpful SO answers, I realized that I could simply try to execute those commands without sudo by having jenkins ssh as root instead.

It worked.

I am going to answer this question with that approach instead because that is all I wanted -- execute some commands inside jenkins and see their print out.

Kim Stacks
  • 10,202
  • 35
  • 151
  • 282
  • 2
    Looks like you might need an extra -t argument on your ssh command, per the answer to this question: http://stackoverflow.com/questions/7114990/pseudo-terminal-will-not-be-allocated-because-stdin-is-not-a-terminal – Aaron Golden Sep 20 '13 at 17:31
  • I tried that. It failed. Updated my question, @AaronGolden – Kim Stacks Sep 20 '13 at 17:51

5 Answers5

1

The user that is sshing in does not have the command available.

If you look at error it connected could not run command and disconnected

By this I don't mean sudo I mean what you have done after sudo

Console/cake init_runners copy_runners_into_initd

It may be that if you actually ssh in as the user and run the above command it works but not via your jenkins script because it may be that you are missing some environment variables that is defined when you ssh in as per normal and get a session.

I would suggest using full paths to everything including:

which sudo

sudo is /usr/bin/sudo

The full path to sudo to rest assured its nothing to do with that.

UPDATED

Hi Kimsia

Thanks for commenting back and now confirming you have a fix, I still think there is something missing from what you have done with sudo since the return message clearly states command not found. To me it would appear that although you ran sudo the path you were actually in could not run console/cake i.e. command not found !

A few things to try if you still wanted to go down the sudo route since I do believe security wise its a lot safer than opening root ssh access.

  1. run sudo with -i to take on root's profile and then actually change directory to where Console folder and cake command reside.

<exec command="ssh -t -t -A ${host-used} 'sudo -i cd /path/to/cakephp/app; Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" />

  1. Would it not be possible to write a shell script which sudo's in
#!/bin/bash
function ssh_and_run_cake() { 

 echo "Working on $hostname --- $instance --::"
 $ssh -t $hostname "sudo su -i '
    echo \"CD Folder run cake init -----------------\";
    cd /path/to/cakephp/app; 
    Console/cake init_runners copy_runners_into_initd;
    echo \"All done------------------------\";
 '";

}

function rollout_cake() {

   #for hostname in ${h[@]}; do


        hostname="yourhost"

        ssh_and_run_cake
  # done

}

rollout_cake

and from jenkins web interface use the execute shell script which should then call this script and carry out what you want.

I have seen Jenkins work away fine with this method

Updated the shell script to work so long as you define hostname in 2nd function.

You would then need to use jenkins web front end deploy options to execute shell script and define the fullpath script. The script should be on the local file system of jenkins server

V H
  • 8,382
  • 2
  • 28
  • 48
  • i tried renaming sudo to /usr/bin/sudo. I get back the same result :( – Kim Stacks Sep 21 '13 at 04:58
  • thanks for your answer. but i tried an entirely different approach and i got what i wanted. Cheers! – Kim Stacks Sep 21 '13 at 06:18
  • ssh -t -t -A ${host-used} for some reason this causes my jenkins to hang a long time – Kim Stacks Sep 23 '13 at 06:27
  • A few things to try if you still wanted to go down the sudo route since I do believe security wise its a lot safer than opening root ssh access. <-- I agree with this. But right now, I need something that works. Can you explain your 2nd solution with more detail? I don't understand by write a shell script which sudo's in and from jenkins web interface – Kim Stacks Sep 23 '13 at 06:28
1

I don't think you need to specify your host twice.

<exec command="ssh -t -t -A ${host-used} 'sudo Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" />
<echo msg="${result}" />
konsolebox
  • 72,135
  • 12
  • 99
  • 105
0

Jenkins cannot print out the result of certain commands that are executed using sudo.

Hence the best way is to simply allow jenkins to ssh as root to perform those same commands without sudo.

  1. Allow jenkins user to ssh as root without password required.
  2. Read this on how to have ssh login without password.
  3. Then, write the command like so: <exec command="ssh -A ${root-used} 'Console/cake init_runners copy_runners_into_initd'" outputProperty="result" escape="false" /> <echo msg="${result}" />

Note that ${root-used} should have a value like root@ipaddress

Nux
  • 9,276
  • 5
  • 59
  • 72
Kim Stacks
  • 10,202
  • 35
  • 151
  • 282
0

Jenkins cannot execute sudo command if the user used to connect is interactive account. This can be fixed by making the sudoer ad non-interactive.

Try this command on target linux box:

echo "%sudo ALL=(ALL) NOPASSWD: *command*" >> /etc/sudoers
TLama
  • 75,147
  • 17
  • 214
  • 392
0

Although I know the OP simply wanted to test something, allowing any user passwordless ssh access to root is probably going to be frowned upon by the security conscious. I found that igor-chubin had probably the soundest approach to allowing jenkins to run specific commands/scripts with elevated privileges in this answer.

Community
  • 1
  • 1
GMeister
  • 331
  • 2
  • 15