How to run shell script in background while start? - shell

I have a shell script contain loop like this:
while true
do
if ... ; then
...
else
...
break
fi
done
I want this script to run backend while OS start. I have try to add this script into /etc/rc.d/local.rc as startup script. But OS start too long, and after OS start up, this script did not exist.
So how to add this script into backend while OS start up? And I need this script also could be start up by hand in backend. Thank you~

If you are scheduling on either Linux or Mac, then you can schedule through crontab.
Open terminal.
$crontab -e #use sudo to run as administrator
#add below line
#reboot sh /absolute_path/script.sh
Give the absolute path of the script, save the crontab and exit.
The script will start running from the next reboot.

Related

Automatically terminate all nodes after calling roslaunch

I am trying to run several roslaunch files, one after the other, from a bash script. However, when the nodes complete execution, they hang with the message:
[grem_node-1] process has finished cleanly
log file: /home/user/.ros/log/956b5e54-75f5-11e9-94f8-a08cfdc04927/grem_node-1*.log
Then I need to Ctrl-C to get killing on exit for all of the nodes launched from the launch file. Is there some way of causing nodes to automatically kill themselves on exit? Because at the moment I need to Ctrl-C every time a node terminates.
My bash script looks like this, by the way:
python /home/user/git/segmentation_plots/scripts/generate_grem_launch.py /home/user/Data2/Coco 0 /home/user/git/Async_CNN/config.txt
source ~/setupgremsim.sh
roslaunch grem_ros grem.launch config:=/home/user/git/Async_CNN/config.txt
source /home/user/catkin_ws/devel/setup.bash
roslaunch rpg_async_cnn_generator conf_coco.launch
The script setupgremsim.sh sources another catkin workspace.
Many thanks!
Thanks all for your advice. What I ended up doing was this; I launched my ROS Nodes from separate python scripts, which I then called from the bash script. In python you are able to terminate child processes with shutdown. So to provide an example for anyone else with this issue:
bash script:
#!/bin/bash
for i in {0..100}
do
echo "========================================================\n"
echo "This is the $i th run\n"
echo "========================================================\n"
source /home/timo/catkin_ws/devel/setup.bash
python planar_launch_generator.py
done
and then inside planar_launch_generator.py:
import roslaunch
import rospy
process_generate_running = True
class ProcessListener(roslaunch.pmon.ProcessListener):
global process_generate_running
def process_died(self, name, exit_code):
global process_generate_running
process_generate_running = False
rospy.logwarn("%s died with code %s", name, exit_code)
def init_launch(launchfile, process_listener):
uuid = roslaunch.rlutil.get_or_generate_uuid(None, False)
roslaunch.configure_logging(uuid)
launch = roslaunch.parent.ROSLaunchParent(
uuid,
[launchfile],
process_listeners=[process_listener],
)
return launch
rospy.init_node("async_cnn_generator")
launch_file = "/home/user/catkin_ws/src/async_cnn_generator/launch/conf_coco.launch"
launch = init_launch(launch_file, ProcessListener())
launch.start()
while process_generate_running:
rospy.sleep(0.05)
launch.shutdown()
Using this method you could source any number of different catkin workspaces and launch any number of launchfiles.
Try to do this
(1) For each launch you put in a separate shell script. So you have N script
In each script, call the launch file in xterm. xterm -e "roslaunch yourfacnylauncher"
(2) Prepare a master script which calling all N child script in the sequence you want it to be and delay you want it to have.
Once it is done, xterm should kill itself.
Edit. You can manually kill one if you know its gonna hang. Eg below
#!/bin/sh
source /opt/ros/kinetic/setup.bash
source ~/catkin_ws/devel/setup.bash
start ROScore using systemd or rc.local using lxtermal or other terminals to avoid accident kill. Then run the part which you think gonna hang or create a problem. Echo->action if necessary
xterm -geometry 80x36+0+0 -e "echo 'uav' | sudo -S dnsmasq -C /dev/null -kd -F 10.5.5.50,10.5.5.100 -i enp59s0 --bind-dynamic" & sleep 15
Stupid OUSTER LIDAR cant auto config like Veloydne and will hang here. other code cant run
killall xterm & sleep 1
Lets just kill it and continuous run other launches
xterm -e "roslaunch '/home/uav/catkin_ws/src/ouster_driver_1.12.0/ouster_ros/os1.launch' os1_hostname:=os1-991907000715.local os1_udp_dest:=10.5.5.1"

How can I return from a shell script and then reboot (to use with VirtualBox)?

I am using guestcontrol with Virtual Box with a Windows host and a Linux (RHEL7) guest. I want to do some config from the host to the guest by running a shell script on the guest (from a .bat on the host). This is fine and the script runs, however, it hangs when I call the reboot (I believe it is because nothing is returned). So when the following .sh is called:
#!/bin/bash
echo "here"
exit
The .bat file shows "here" and then exits (or if I use pause gives the correct message). However, when I add the reboot, the .bat never processes anything past where it calls the script. I think this would be because the guest never tells the host that the script is complete.
I have tried things like:
#!/bin/bash
{ sleep 1; reboot; } >/dev/null &
exit
or even:
#!/bin/bash
do_reboot(){
sleep 1
reboot
}
do_reboot() &
exit
but the .bat never gets past the line where it runs the .sh
How can I tell the host that the .sh script (on the guest) is complete so it can continue with the .bat script?
We need to make sure there are no sub processes running, so we want to do a no heads up using the nohup command. So the script simply becomes this:
#!/bin/bash
nohup reboot &> /tmp/nohup.out </dev/null &
exit
The stdin and stdout were causing the issues, so this just sends them into the void so that the script will not be waiting for any input from any other processes.
If you have any issues with this script, you could do something like:
#!/bin/bash
nohup /path/to/reboot_delay.sh &> /tmp/nohup.out </dev/null &
exit
And then in /path/to/reboot_delay.sh you would have:
#!/bin/bash
sleep 10 # or however many seconds you need to wait for something to happen
reboot
This way you could even allow some time for something to finish etc, yet the host machine (or ssh or wherever you are calling this from) would still know the script had finished and do what it needs to do.
I hope this can help people in future.

Applescript: Making a self-quitting script

I have an applescript which launches an application on computer startup.
The problem is that the script stays open in the background and prevents the machine from restarting, unless I force-quit the said script (The script is saved as an application).
How do I make the script quit itself after performed the actions?
Here is what I have (On OSX 10.8):
on run
do shell script "#!/bin/sh
# luxconsole control
/Applications/LuxRender/LuxRender.app/Contents/MacOS/luxconsole &"
quit
end run
Thanks.
Try this way:
on run
do shell script "/Applications/... > /dev/null 2>&1 &"
quit
end run
Try This;
do shell script "killall -yourapp-"
put that at the end of your script

Simple script run via cronjob doesn't work but works from shell

I am on shared hosting and I'm trying to schedule cronjob to run every now and then. Via cPanel I scheduled to execute my script but even though that according to my host support the cronjob runs, the script doesn't seem as doing anything. The cron job command I set via cPanel is:
/bin/sh /home1/myusername/public_html/somefolder/cronjob2.sh
and the cronjob2.sh
#!/bin/bash
/home1/myusername/public_html/somefolder/node_modules/forever/bin/forever stop 0
when via SSH I execute:
/home1/myusername/public_html/somefolder/cronjob2.sh
it stops forever process as needed. From cronjob doesn't do anything.
How can I get this working?
EDIT:
So I've tried:
/bin/sh /home1/username/public_html/somefolder/cronjob2.sh >> /tmp/mylog 2>&1
and mylog entries say:
/usr/bin/env: node: No such file or directory
It seems that forever needs to run node and this cannot be found. How would I possibly fix this?
EDIT2:
Accepted answer at superuser.com. Thank you all for help
https://superuser.com/questions/763261/simple-script-run-via-cronjob-doesnt-work-but-works-from-shell/763288#763288
For cron job lines in a crontab it's not required to specify kind of shell or e.g. of perl.
It's enough, that your script contains
shebang
line.
Therefore you should remove /bin/sh from your cron job line.
Another aspect, that might cause a different behavior of your script by interactive start and by cron daemon start is possible different environment, first of all the PATH variable. Therefore check, if you script is able to be executed in very restricted environment, that is provided by cron daemon. You can determine your cron job environment experimentally by start of temporary cron job, that executes "env" command and writes its output to a file.
Once more aspect: Have you redirected STDOUT and STDERR of the cron job to a log file and read its content to analyze the issue? You can do it as follows:
your_cron_job >/tmp/any_name.log 2>&1
According to what you wrote, when you run your script via SSH, you are using bash, because this line is the first of your script:
#!/bin/bash
However, in the crontab, you are forcing the use of sh instead of bash. Are you sure your script is fully compatible with sh? Otherwise, simply replace /bin/sh with /bin/bash in your cron command and test again.

Terminal Command: start or stop process if it's running or not

I have a glassfish install and I would like to have a simple terminal command checking if it's running. If it is, it will shutdown the process. Or if it not running, it will start the server.
To start the server I can enter:
/Applications/NetBeans/glassfish-3.1.1/bin/./asadmin start-domain domain
To stop the server I can enter:
/Applications/NetBeans/glassfish-3.1.1/bin/.asadmin stop-domain domain
I will would like to make a simple Alfred.app script than can start this domain if it's not running, or stop it if it's running.
One way to do this is to note in a file the process ID of the server when it starts, and have another script check to see if that process is running.
For example, script A (to run the server unconditionally):
#!/bin/sh
/Applications/NetBeans/glassfish-3.1.1/bin/./asadmin start-domain domain
# file name is arbitrary
pgrep whateverTheProcessNameIs > ~/.glassfish-server.pid
And in script B:
#!/bin/sh
pid=`pgrep -F ~/.glassfish-server.pid` # file chosen in script A
if [ "x$pid" = "x" ] ; then
# process has died; restart by running script A
/path/to/scriptA
fi
Note that only Mac OS X 10.8 (Mountain Lion) installs pgrep by default; otherwise you'd have to use some other method (like parsing ps output) to see what processes are running.
As far as how to run this check periodically, there are various ways. I'm assuming Alfred will run any script that is executable (chmod +x scriptA scriptB) but I don't know for sure.

Resources