Bash script not navigating to folder, only accepting input when "exit" is typed manually - bash

I have the following bash script I am trying to use so I can speed up updates to my code. For some reason it gets stuck at cd /var/www/myapp/code and only prompts input when I type exit to return to the root user.
#!/bin/bash
# Pulls from remote repo and implements changes
su - rails
cd /var/www/myapp/code
git pull
expect "sername for 'https://bitbucket.org':"
send "myusername"
interact
expect "assword for 'https://username#bitbucket.org':"
send "mypassword"
interact
exit
cd /var/www/myapp/code
RAILS_ENV=production bundle exec rake assets:clobber
RAILS_ENV=production bundle exec rake assets:precompile
nginx -t && sudo nginx -s reload
I tried manually entering cd /var/www/myapp/code but it's still not executing until I type exit.

Well, it's a bit of re-factoring, but a solution is to wrap everything in a single su - (user) -c "bla" call, which will automatically exit the subshell as (user) once the commands are all done.
Syntax:
su - (user) -c "command"
Here's how I'd do it:
Note that we have to break commands up with ';', and escape double-quotes with a '\'.
#!/bin/bash
# Pulls from remote repo and implements changes
su - rails -c "cd /var/www/myapp/code;
git pull;
expect \"sername for 'https://bitbucket.org':\";
send \"myusername\";
interact;
expect \"assword for 'https://bitbucket.org':\";
send \"mypassword\";
interact" # Now that the final command's ran,
# we'll auto - exit the subshell
cd /var/www/myapp/code
RAILS_ENV=production bundle exec rake assets:clobber
RAILS_ENV=production bundle exec rake assets:precompile
nginx -t && sudo nginx -s reload

Related

How can I run one line of bash shell script as a specific user

I have a script I run manually (let's say) mylogin. But there's one line that needs to run as user postgres.
What is a good way to do that?
It's ok if I get a password prompt. I just need it to work somehow.
Here's what I have so far...
~/reload_test_data.sh
#!/bin/bash
# Here's the part that needs to run as user `postgres`...
sudo su postgres
export PGDATA=/Library/PostgreSQL/9.4/data && pg_ctl -m fast restart
# And here we should go back to `mylogin`...
cd ~/projects/my_project
echo 'Dropping database'
bundle exec rake db:drop
# More stuff etc...
I'm using Mac OS 10.12.1.
One of the arguments for sudo is the command so you can do something like:
sudo -u <user> bash -c "command_1; command_2; etc"
where -u <user> change to your target user

Ubuntu start up Rails on boot up

I want to start my Rails server with the following command on boot up:
cd /home/ubuntu/app && bundle exec rails server -p 8080 -e production
I placed it inside the /etc/rc.local, but it never starts up the server. If I remove bundle exec then shell complains about not finding the rails command.
Both variants, with and without bundle exec, work if I log in, and execute it manually.
I am totally lost. Any suggestions?
Try to change a user
su ubuntu && cd /home/ubuntu/app && bundle exec rails server -p 8080 -e production
Running your script as root is not a good idea, so you want to change user before starting your code.
su is indeed the command you want to use, but you need to realise that all arguments are passed to the login shell. So the following won't work (assuming fofox is your username):
su fofox pwd
as you're effectively saying
/bin/bash /bin/pwd
but /bin/pwd does not contain a list of shell commands, so both will give an error message:
/bin/pwd: /bin/pwd: cannot execute binary file
Thus you need to add something to the shell saying you're passing a list of commands, like this:
/bin/bash -c /bin/pwd
The last wrinkle is that you want to pass a number of arguments to the su command but protect them from the shell, as
su fofox -c id && id
will show you that the first bit is executed as fofox and the second part as root again. Single quotes are used to prevent the root shell to see the && characters.
So the final command becomes:
su fofox -c 'cd /home/ubuntu/app && bundle exec rails server -p 8080 -e production'

Why is sudo: bundle command not found?

Why is command "bundle" not found when using sudo:
[root#desktop gitlab]# sudo -u git -H bundle exec rake gitlab:setup RAILS_ENV=production
sudo: bundle: command not found
[root#desktop gitlab]#
but does exist when not using sudo:
[root#desktop gitlab]# bundle exec rake gitlab:setup RAILS_ENV=production
Warning
You are running as user root, we hope you know what you are doing.
Things may work/fail for the wrong reasons.
For correct results you should run this as user git.
This will create the necessary database tables and seed the database.
You will lose any previous data stored in the database.
Do you want to continue (yes/no)? no
Quitting...
[root#desktop gitlab]#
The reason I ask is I am following https://github.com/gitlabhq/gitlab-recipes/tree/master/install/centos, and it states to use sudo.
I've tried adding a -i flag as described by Using $ sudo bundle exec ... raises 'bundle: command not found' error, but get "This account is currently not available.".
Check if the PATH has the same values both with and without sudo. Apparently it cannot find bundle just because it is not listed in PATH
You can compare the outputs of following two lines
$ echo 'echo $PATH' | sh
$ echo 'echo $PATH' | sudo sh
Ideally sudo is supposed to leave PATH untouched. But this might be a side issue of your hosting distribution.
Edit by original poster. Output is:
[root#desktop etc]# echo 'echo $PATH' | sh
/usr/lib64/qt-3.3/bin:/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:/root/bin
[root#desktop etc]# echo 'echo $PATH' | sudo sh
/sbin:/bin:/usr/sbin:/usr/bin:/user/local/bin
[root#desktop etc]#
The user was created without a bash login shell. Change this in centos using system-config-users. Then su git into /home/git and move to gitlab directory. Execute the bundle commands without the sudo tag. The next error you will encounter is the missing database.yml in the config dir. fix this with the correct password (i.e. copy the mysql or postgres sample and edit).
I had this issue I thought that my gitlab installed from source and I got same error. but after try Omnibus method for backup my issue solved
with this command:
sudo gitlab-rake gitlab:backup:create
Try :
sudo -u git -H env PATH=$PATH && bundle exec rake gitlab:check RAILS_ENV=production
to use the same PATH than current user.

Shell script doesn't properly execute from ruby CGI script

I've got a ruby cgi script which calls a shell script.
The shell script does a git pull.
When I run the shell script from the command prompt it works.
But when I run it from the ruby cgi script it executes the script but the git pull doesn't happen.
I'm guessing it's possibly permissions related but I can't quite work out how to fix it.
The ruby script is:
#!/usr/local/rvm/rubies/ruby-1.9.3-p125/bin/ruby
require "cgi"
git_pull = `sh /github/do_git_pull.sh`
move_apanels = `sh /github/move_apanels.sh`
puts "Content-type: text/html\n\n"
puts "<html><body>We've done the following:<ul>"
puts "<li>#{git_pull.to_s}</li>"
puts "<li>#{move_apanels.to_s}</li>"
puts "</ul></body></html>"
And the shell script is:
#!/bin/bash
sudo sh -c cd /github
sudo sh -c git pull origin master
echo "Git Pull Completed"
Both files have chmod 777
Any ideas?
Doing this:
sudo sh -c cd /github
only changes the PWD for the duration of that sh command. It does not affect the current shell. You need to cd and git pull in the same subshell:
sudo sh -c 'cd /github && git pull origin master'
Setting 777 on your scripts won't cut it. Try and find out the user under which your ruby script executes the shell script. Since git uses SSH keys for authentication and normally your SSH keys can only be used by you, then git pull would fail if another user tries to do the git pull.
Check out this question on how to run a shell script as a different user.
Also make sure that the PATH in the target environment is set properly and accessible (if you run the web server chrooted).

Problem deploying Ruby+RVM and daemontools

I am using daemontools in production to keep the services alive and want to run a Ruby server, not Rails, and without RVM it works well but with RVM I have some issues.
My goal is to start a process by root, make it drop root rights to get another user rights and then spawn a Ruby process with RVM and a specified Ruby version.
Here is the run script I was using until now:
#!/bin/sh
exec 2>&1
cd /app/src
. /usr/local/rvm/scripts/rvm
rvm use 1.9.1-p378
exec setuidgid app_user ruby main.rb
This script works but setuidgid has a major problem: the application will be run by user <x> and group <x> and only this group. If the user is in other groups the process will not have their rights.
So it led me to another approach:
#!/bin/sh
exec 2>&1
cd /app
exec sudo -u app_user rvm 1.9.1-p378 exec ruby main.rb
This one works fine except it is the RVM process which is spawned by daemontools and it does not react when it receives a SIGTERM which is not really nice. Basically it means the service cannot be restarted by hand, which is not good.
I found the answer but looking at the rvmsudo script installed with rvm, here is a working run script:
#!/bin/sh
# redirect stderr to stdout
exec 2>&1
cd /app
# load rvm
. /usr/local/rvm/scripts/rvm
# select ruby version for this application
rvm use 1.9.1
# # depending on your configuration you may need to provide the absolute path to rvm, like that:
# /usr/local/bin/rvm use 1.9.1
# build the exec command line preserving the rvm environment
command="exec sudo -u app_user /usr/bin/env PATH='$PATH'"
[[ -n "${GEM_HOME:-}" ]] && command="${command} GEM_HOME='$GEM_HOME' "
[[ -n "${GEM_PATH:-}" ]] && command="${command} GEM_PATH='$GEM_PATH' "
# this is where your real command line goes
command="${command} ruby main.rb"
# run the application
eval "${command}"

Resources