this is my third time trying to post this. I am having some trouble running my Ruby Script using a crontab.
Below is my file tree
rubyUbuntuIssue
├── logFile.txt
├── RubyFile.rb
├── Script_Files
│ ├── logFileTwo.txt
│ ├── scripttwo.sh
│ └── trigger_file.rb
└── trigger.sh
This is my crontab file
SHELL=/bin/bash
PATH=/usr/sbin:/usr/bin:/sbin:/bin
*/1 * * * * sh /home/ubuntumike/Documents/rubyUbuntuIssue/trigger.sh >> /tmp/mybackup.log
This is my trigger.sh file
set -x
set -e
SHELL=/bin/bash
#PATH=/home/ubuntumike/.rvm/gems/ruby-2.1.5/bin:/home/ubuntumike/.rvm/gems/ruby-2.1.5#global/bin:/home/ubuntumike/.rvm/rubies/ruby-2.1.5/bin:/usr/local/sbin:/usr/local/bin:/usr/s$
cd /home/ubuntumike/Documents/rubyUbuntuIssue
[[ -s "$HOME/.rvm/scripts/rvm" ]] && . "$HOME/.rvm/scripts/rvm"
# or use an absolute path instead of $HOME, just make sure the script get sourced
# after that you can choose correct ruby with rvm
rvm use ruby-2.1.5
ruby RubyFile.rb;
ruby Script_Files/trigger_file.rb 2>&1 >> /tmp/errors.txt;
sh Script_Files/scripttwo.sh
echo "The present working directory is `pwd`"
echo "$(date) running trigger.sh file"
echo "`ruby -v`"
When I run trigger.sh directly from terminal everything works perfectly, however when run using crontab only the RubyFile.rb will run which is on the same level as the shell file
Ok so heres what should happen when trigger.sh is executed the 3 scripts
RubyFile.rb,
scripttwo.sh,
trigger_file.rb should run.
When I run this directly from terminal all 3 scripts work as expected.
When I run this using crontab RubyFile.rb and scripttwo.sh will run however trigger_file.rb will not run. I simply don't have a clue what I am doing wrong.
If you want you can have a look at the exact code on GitHub https://github.com/omearamike/rubyUbuntuIssue .
If anyone can offer some guidance it would be much appreciated as I am completely lost and ran out of options.
Current response in terminal when trigger.sh is run.
+ set -e
+ SHELL=/bin/bash
+ cd /home/ubuntumike/Documents/rubyUbuntuIssue
+ [[ -s /home/ubuntumike/.rvm/scripts/rvm ]] trigger.sh: 7: trigger.sh: [[: not found
+ rvm use ruby-2.1.5
RVM is not a function, selecting rubies with 'rvm use ...' will not work.
You need to change your terminal emulator preferences to allow login shell.
Sometimes it is required to use `/bin/bash --login` as the command.
Please visit https://rvm.io/integration/gnome-terminal/ for an example.
+ ruby RubyFile.rb
+ ruby Script_Files/trigger_file.rb
+ sh Script_Files/scripttwo.sh
Script_Files/scripttwo.sh: 10: Script_Files/scripttwo.sh: date: not found
running scripttwo.sh file...........................SUCCESS
+ pwd
+ echo The present working directory is /home/ubuntumike/Documents/rubyUbuntuIssue
The present working directory is /home/ubuntumike/Documents/rubyUbuntuIssue
+ date
+ echo Wed Oct 7 22:10:48 IST 2015 running trigger.sh file
Wed Oct 7 22:10:48 IST 2015 running trigger.sh file
+ ruby -v
+ echo ruby 2.1.5p273 (2014-11-13 revision 48405) [x86_64-linux]
ruby 2.1.5p273 (2014-11-13 revision 48405) [x86_64-linux]
It seems you're using rvm. Instead of setting PATH manually, it's better to delegate this job to rvm. In your trigger.sh:
[[ -s "$HOME/.rvm/scripts/rvm" ]] && . "$HOME/.rvm/scripts/rvm"
# or use an absolute path instead of $HOME, just make sure the script get sourced
# after that you can choose correct ruby with rvm
rvm use ruby-2.1.5
Add to the end of your non-working script 2>&1 >> /tmp/errors.txt, so you can see stdout and stderror in one place, this way you will know what exact errors you experience, like this:
ruby Script_Files/trigger_file.rb 2>&1 >> /tmp/errors.txt
Related
I am trying to run a ruby script as a service on my centos machine. I can run the ruby script direct from the command line and from a bash file without issue.
However, when I try to run it as a service via /etc/init.d I get the error 'require': cannot load such file -- somegem.
#! /home/user/.rvm/rubies/ruby-2.1.5/bin/ruby
# encoding: utf-8
require "somegem"
I have created an init.d script and placed that in /etc/init.d/
#!/bin/sh
# monitor_endpoint
# chkconfig: 2345 20 80
# Source function library.
. /etc/rc.d/init.d/functions
#Define variables
prog="monitor_endpoint"
exec=/home/user/Workspaces/test/bin/test.rb
echo $exec
start() {
echo -n $"Starting $prog: "
# use daemon to start the service
daemon $exec &
retval=$?
echo
return $retval
}
etc...
Would this be a problem with my gems installation path?
Any help would be much appreciated as this is my first attempt at running a ruby script in this way. Thank you.
the problem is in your environment (the env vars).
run
env
in the normal environment and after that run it from the init script and pipe the output to a file.
look at the differences.
GOing to guess you are missing all the ruby specific stuff(GEM_PATH and all)
I have a simple ruby script, hello.rb:
#!/usr/bin/env ruby
puts 'hello'
It runs ok at the command line:
# /usr/local/src/hello/hello.rb
hello
However, if I put it in cron:
* * * * * /usr/local/src/hello/hello.rb >> /usr/local/src/hello/hello.log 2>&1
There are errors in the log file:
/usr/bin/env: ruby: No such file or directory
/usr/bin/env: ruby: No such file or directory
...
/usr/bin/env: ruby: No such file or directory
/usr/bin/env ruby runs ok at command line though:
# /usr/bin/env ruby -v
ruby 1.8.7 (2012-10-12 patchlevel 371) [i686-linux]
How to fix the env error for cron?
The problem is that the environment isn't what you expect.
You don't say whether the cron is running as your user, or as root, but, in either case, you can test to see what the environment looks like by adding another cron entry of:
* * * * * /usr/bin/env > /path/to/your/home/directory/env.txt
Let that run once, then pull it out, and look at the file.
Instead of using /usr/bin/env to try to find a Ruby to run your code, define the Ruby explicitly:
* * * * * /path/to/the/ruby/you/want /usr/local/src/hello/hello.rb >> /usr/local/src/hello/hello.log 2>&1
You can figure out which Ruby you want by using:
which ruby
Alternately, instead of relying on /usr/bin/env in your #! line, define your Ruby there.
Using /usr/bin/env ruby in your code is a convenience when you're using something like RVM or rbenv, and switching between versions of Ruby. It's not a good choice when you're putting something into "production", whether it's on your machine in your own account, or on a production host running as root.
If you are on Linux or Mac OS, try man 5 crontab for more information. Also, "Where can I set environment variables that crontab will use?" should be very useful.
env searches only in the existing PATH variable. crond creates the process that is run as your user name. So the PATH is minimal. You have to set up your environment variables in the script itself
I'm trying to start unicorn_rails in a ruby script, and after executing many commands in the script, when the script gets to the following line
%x[bash -ic "bash <(. ~/.bashrc); cd /home/www-data/rails_app; bundle exec unicorn_rails -p 8000 -E production -c /home/www-data/rails_app/config/unicorn.rb -D"]
the script stops, generating the following output
[1]+ Stopped ./setup_rails.rb
and returns to the Linux prompt. If I type "fg", the script finishes running, the line where the script had stopped gets executed and unicorn gets started as a daemon.
If I run the line in a separate script, the script completes without stopping.
UPDATE_1 -
I source .bashrc because earlier in the script I install rvm and to get it to run with the correct environment I have the following:
%x[echo "[[ -s \"$HOME/.rvm/scripts/rvm\" ]] && source \"$HOME/.rvm/scripts/rvm\"" >> .bashrc]
%x[bash -ic "bash <(. ~/.bashrc); rvm install ruby-1.9.2-p290; rvm 1.9.2-p290 --default;"]
So if I want to run correct version of rvm, ruby and bundle I need to source .bashrc
end UPDATE_1
Does anyone have any idea what could cause a ruby script to halt as if control-Z was pressed?
Not sure why it's stopping, but my general rule of thumb is to never source my .bashrc in a script -- that might be the source of your problem right there, but I can't be sure without seeing what's in it. You should be able to change your script to something like:
$ vi setup_rails.sh
#!/usr/bin/bash
# EDIT from comments below
# expanding from a one liner to a better script...
$RVM_PATH=$HOME/.rvm/scripts
# install 1.9.2-p290 unless it's installed
$RVM_PATH/rvm info 1.9.2-p290 2&>1 >/dev/null || $RVM_SH install 1.9.2-p290
# run startup command inside rvm shell
$RVM_PATH/rvm-shell 1.9.2-p290 -c "cd /home/www-data/rails_app && bundle exec unicorn_rails -p 8000 -E production -c /home/www-data/rails_app/config/unicorn.rb -D"
This should give you the same result.
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}"
My RVM system-wide installation scripts are broken, both in the form of Linode StackScripts and Chef-solo Recipes.
Per the instructions on the RVM website, my scripts execute the following commands as root to install RVM on a system-wide basis:
echo "Installing RVM system-wide" >> $logfile
bash < <( curl -L http://bit.ly/rvm-install-system-wide )
cat >> /etc/profile <<'EOF'
# Load RVM if it is installed,
# first try to load user install
# then try to load root install, if user install is not there.
if [ -s "$HOME/.rvm/scripts/rvm" ] ; then
. "$HOME/.rvm/scripts/rvm"
elif [ -s "/usr/local/rvm/scripts/rvm" ] ; then
. "/usr/local/rvm/scripts/rvm"
fi
EOF
source /etc/profile
The key piece above is the url http://bit.ly/rvm-install-system-wide. As of today, 3/24/2011, this url no longer in service. It results in a GitHub 404 error.
The following url on the RVM website used to contain the instructions for the system-wide install: http://rvm.beginrescueend.com/deployment/system-wide/. However, that url now redirects to the RVM homepage.
In the interests of getting RVM system-wide installation scripts to work again, what are the new instructions?
Here is my fix to install the last working version before he major change:
bash <( curl -L https://github.com/wayneeseguin/rvm/raw/1.3.0/contrib/install-system-wide ) --version '1.3.0'
This is working for me now in production. Good luck!
UPDATE
Also, if you are using the chef cookbook from https://github.com/fnichol/chef-rvm or something similar, you can use the following options:
:rvm => {
:system_installer_url => "https://github.com/wayneeseguin/rvm/raw/1.3.0/contrib/install-system-wide",
:version => "1.3.0"
}
Just received the following answer from the lead developer, wayneeseguin, on #rvm:
[12:53] "the author" merged it into the ain installer
[12:53] so you should be doing
bash < <( curl http://rvm.beginrescueend.com/releases/rvm-install-head )
# http://rvm.beginrescueend.com/rvm/install/
[12:53] the code has just changed and the documentation hasn't caught up
[12:53] for both root and user installs
It is true that RVM 1.5.1 will successfully install into /usr/local/bin just by installing as root. However, for some reason, all the existing Chef and Puppet provisioning scripts that are in use today do not appear to survive this version bump. This is unfortunate, as Wayne E. Seguin has made clear that RVM below version 1.5.0 will not be supported.
That said, we need our systems to work today. In order to continue to use RVM 1.3.0, which the existing scripts support, you need to replace the following line:
bash < <( curl -L http://bit.ly/rvm-install-system-wide )
With the following line (found by phlipper):
bash -c "bash <( curl -L https://github.com/wayneeseguin/rvm/raw/1.3.0/contrib/install-system-wide ) --version '1.3.0'"