Cronjob emailing "command failed with exit status 1" when nothing fails - php

I've been experimenting with cronjobs recently and have it setup like so:
crontab:
SHELL=/bin/sh
MAILTO=me#me.com
26 11 * * * wget http://diruser:pass#domain.com/path/to/file.php
Within the php file it runs is a SQL query which at the moment just runs an insert. This works fine and runs the insert but when I look at the email it produces it says this:
email:
wget http://diruser:pass#domain.com/path/to/file.php:
Command failed with exit status 1
I was just wondering if anyone knows why it would return command failed? It obviously doesn't fail but the email response makes me think I've done something wrong somewhere.
Also, is it good practice to put the file the cron is calling inside a password protected directory or is there a better way around it (such as checking that the request ip is that of the server or something).

Most likely, wget throws an error because it cannot save the result. By default wget will try to store thr result on disk. When running in a cron job, the working directory is (usually) /. You , as a user, probably cannot store a file there.
Instead, tell wget to drop the result, or pipe it to /dev/null. Fox example:
wget -O - -q http://diruser:pass#domain.com/path/to/file.php

I have no idea why error is produced. But in my opinion this is not good practive to call PHP via wget. You can write PHP script which will not be accessible over Apache (or Nginx or other HTTP server) and can be called from cron:
SHELL=/bin/sh
MAILTO=me#me.com
26 11 * * * php /path/to/file.php
And better way is to call it like an separated user, phpuser for example, who will have only permissions that script needs.

Try:
26 11 * * * /usr/local/bin/wget "http://diruser:pass#domain.com/path/to/file.php" > /dev/null 2>&1
Or
26 11 * * * /usr/bin/wget "http://diruser:pass#domain.com/path/to/file.php" > /dev/null 2>&1
1. crontab needs the full path to the command, in order to run it
2. wget will try to save the response of the file.php, if it doesn't have the necessary permissions, it will fail. That's why you should redirect the output somewhere else, other than a file, which is accomplished by > /dev/null.
There are three standard sources of input and output for a program, i.e. STDIN, STDOUT, STDERR, respectively numbered as 0, 1, 2.
When you redirect the output by using the greater-than >, if you don't explicitly mention which one you want to redirect, the default one is STDOUT (1). Thus, we will redirect all STDOUT output to null/trash, and all errors 2>&1 to STDOUT, which in turn will go to trash, as denoted by the previous rule.

Related

Setting up a Cron Job on CPanel to executes a PHP script

As implied in the title, the Cron Job is supposed to execute a php file (update.php, to be specific). The php file then writes to a csv file stored in the same directory.
I have the time set to * * * * * so that it executes every minute. The command is written as follows:
php -q /home//public_html/wallboard/update.php
I don't believe this is causing any errors, though it also doesn't seem to write to the CSV file. When I visit update.php in a browser, however, it executes and writes to the CSV file immediately. I'm not experienced with Cron Jobs and I'm sure there's an issue, but I don't know what exactly that issue is. Let me know if you have suggestions/questions. Any help is appreciated!
Current Command:
* * * * * usr/bin/php -q /home/<user>/public_html/wallboard/update.php
update.php:
<?php
include('lib/HelpDeskView.php');
include('lib/WallboardDisplay.php');
include('helpdesk.csv');
$helpdesk = new HelpDeskView();
$text="\r\ntest,test,test";
file_put_contents( "helpdesk.csv" , $text, FILE_APPEND);
Since your script resides in your public_html directory you can use wget for your Cron Job
wget -O - -q https://yoursite.com/wallboard/update.php
-O - output is written to the standard output in this case it will go to the email address you specify in CPanel
-q quiet mode
IMHO the best way is to contact support and ask them about command line syntax.
This is how I'm doing it at my linux server using cPanel.
This runs script.php which is stored in public root. Course, replace <username> in command line with your username.
At another server I'm using same command line with /usr/bin/php instead of php at the beginning of line, but I'm aware that not all servers use same command line. Some require php-cli in command line instead of php, some don't "like" -f argument, etc. So try various combinations.
To find more suggestions check out this SO topic too: Run a PHP file in a cron job using CPanel
Important thing: When trying different commands wait at least a minute (this case) to see if it works because Cron doesn't fire your script immediately.
Try to execute the same command in PHP CLI and check if it gives you any error, you might be missing some libraries or references required for CLI execution.
/usr/bin/php -d register_argc_argv=On /home/USERNAME/public_html/DOMAIN/artisan AMIR:HOME

How Can I physically see running Cronjobs?

I have cronjobs that execute PHP files at pre-determined times. These scrips can take over an hour to complete. I want to be able to physically monitor the scripts. I have logs, of course, and lots of ways to handle errors, but sometimes I just like to see what's happening.
Previously I did this on Windows where I would schedule a task which would launch in a shell that would remain open while the task ran.
Can I do this on Linux? Using SSH? Something perhaps like using screen with the cron? I'm using the AWS version of Linux.
Thank you.
The easiest (though sligtly dirty) way to do this, is to set an environment variable in crontab:
* * * * * THIS_IS_A_CRON=1 /path/to/script
Then, to see if they're running on your machine:
ps auxe | grep THIS_IS_A_CRON
That'll list all proces (if any) that were started with the THIS_IS_A_CRON environment variable
If all you're after is a window where you can see the output of the script while it's running, it's really nothing too different from having:
* * * * * /path/to/script 2>&1 >> /random/output/file.txt
And opening a terminal that tails the file:
tail -100f /random/output/file.txt
You can pipe output of a cronjob to a logfile, and you can use unix tools (tail, watch, etc) to view all the output as it goes, e.g. the following redirects STDERR as well as STDOUT to a log file:-
/usr/bin/really_long_script.sh > /tmp/script.log 2>&1
tail -f /tmp/script.log
If the script is generating output, that you would like to monitor, let it log this and use tail -f on the log.
Using screen for this is overkill.

Cron running but functionality not working

I have several PHP files to be run by cron. I set up the crons using command-
crontab crontab.txt
Inside the crontab.txt file, I have written cron commands like this:-
#(Updating tutor activities) - every minute
* * * * * /usr/bin/wget -O - -q -t 1 http://project/cron/tutor_activities.php
But none of the functionalities are working (database queries, sending reminder mails etc.). Running the URLs manually works.
Then I put my mail address in MAILTO and received the mails. In the mail, I received entire HTML source of the page. What is expected in the mail? Why are my functionalities not working?
Updates
If I change my cron commands to
#(Updating tutor activities) - every minute
* * * * * /usr/bin/wget http://project/cron/tutor_activities.php
Still no success and this comes in my mail -
--15:03:01-- http://project/cron/tutor_activities.php
=> `tutor_activities.php'
Resolving project... IP Address
Connecting to test.project|IP Address|:80... connected.
HTTP request sent, awaiting response... 301 Moved Permanently
Location: http://project./ [following]
--15:03:01-- http://project./
=> `index.html.1'
Resolving project.... IP Address
Connecting to project.|IP Address|:80... connected.
HTTP request sent, awaiting response... 302 Found
Location: http://project/home/ [following]
--15:03:01-- http://project/home/
=> `index.html.1'
Resolving project... IP Address
Connecting to wproject|IP Address|:80... connected.
HTTP request sent, awaiting response... 200 OK
Length: unspecified [text/html]
index.html.1 has sprung into existence.
Retrying.
And lots of index.html.1 , index.html.2 files are accumulating in the root of my project. I do not want these files to be created. Just want the files to execute.
Same results if I use either of the two commands -
* * * * * /usr/bin/wget http://project/cron/tutor_activities.php
* * * * * wget http://project/cron/tutor_activities.php
running php command with MAILTO set sends me this error /bin/sh: php: command not found.
* * * * * php /path/to/test.php
So, I am not able to use php command.
I have written a simple mailto() inside my test.php. The mail does not come when run through cron (using both wget and php fails) but running the URL manually works.
My problem
To make it clear again, my main problem is that the functionality inside the cron files is not running. Creation of files is a secondary issue.
Any help would be appreciated
Thanks,
Sandeepan
if you want to call an url as cronjob, you'll have to use somthing like wget. if it's a php-script on your server it would be easier to use php /...pathtomyscript.../cron/tutor_activities.php
try
which php
The path which is returned should be placed with the command which is passed to run the Cron file.If you are setting up the Cron through Shell,it won't give any problem,but to be assured,try giving absolute path when you are trying to run a php page.
/path/to/php /path/to/cron/script/
Try to give your comand like this,if the problem persists;feel free to discuss.
When you call wget with -O -, it will send the downloaded content to stdout, which cron is sending to you via the email message. In the first case, it's doing exactly what it should.
When you call wget witout the -O parameter, it will try to save the downloaded content as a file of the same name as the web page being downloaded. If it exists, it will add the incrementer to the name, as you saw. In this second case, it's doing exactly what it should.
It's not clear from your question where you want the output to go, but if you want to save the output to the same file each time, use -O myfilename.html.
If your running PHP from cron/command line make sure you put the full path to the php executable
It's entirely possible that PHP's not in the path within the cron environment - it's definitely not going to have the same setup as your regular shell. Try using the absolute path to BOTH the php interpreter AND the php script in the cron command:
* * * * * /path/to/php /path/to/test.php
As for the creation of files, you just have to add a redirect to your wget command:
wget -O - ... http://.... > /dev/null
-O - forces wget to write anything it downloads to standard output, which cron will then happily email to you. By adding the > /dev/null at the end of the command, this output will instead go the Great Bitbucket in the Sky. If you don't want wget's stderr output emailed either, you can also add a 2&>1 after the /dev/null, which further redirects stderr to stdout, which is now going to /dev/null.
I found the problem myself. I did not put the same URL in my crontab file which I was running manually and that was my mistake.
While running manually I was just typing test in the URL, my browsers's list of saved URLs was appearing and I was selecting the URL http://www.test.project.com/cron/tutor_activities.php, but in the crontab file I had put http://test.project.com/cron/tutor_activities.php. I was mistakenly assuming this would run http://www.test.project.com/cron/tutor_activities.php (because we have a rewrite rule present to add www)
But the rewrite rule was redirecting it to http://www.test.project.com/home. That's why the HTML content in the mails.
So, the most important thing to learn here is to make sure we don't miss the minute things and don't assume that we did everything correctly. In my case, better to copy-paste the working URL into the cron file.
An easy and secure (no tmp files) way to do this is to use bash's process substitution:
* * * * * bash -c "/path/to/php <(/usr/bin/wget -O - -q -t 1 http://project/cron/tutor_activities.php)"
Process substitution runs the command within <() and puts the output into a file object that is only visible from the current process. In order to use it from cron, invoke bash directly and pass it as a command string.
And as others have mentioned, use the full path to php which you can find out with which php.

Running CodeIgniter cron on localhost

I'm trying to get a cron job to run every 5 min on my localhost. Using the Cronnix app I entered the following command
0,5 * * * * root curl http://localhost:8888/site/ > /dev/null
The script runs fine when I visit http://localhost:8888/site/ in my browser. I've read some stuff about getting CI to run on Cron, using wget and various other options but none make a lot of sense.
In another SO post I found the following command
wget -O - -q -t 1 http://www.example.com/cron/run
What is the "-O - -q -t 1" syntax exactly?
Are there other options?
-O - Means the output goes to stdout (-O /dev/null) would nullify any output. -q means be quiet (don't print out any progress bars), this would screw up the look of any log files. -t 1 means to only try once. If the connection fails or times out it will not try again.
See http://linux.die.net/man/1/wget for a full manual on the wget command.
Edit: just realised you're piping all this to /dev/null anyway, you may as well either omit the -O parameter or point that to /dev/null and omit the final pipe.
What I always do is use PHP in cli mode. Seems more efficient to me.
first setup a cron entry like :
*/5 * * * * /usr/bin/php /var/www/html/cronnedscript.php
cronnedscript.php should be placed in your root www folder.
then edit cronnedscript.php with:
<?php
$_GET["/mycontroller/index"] = null;
require "index.php";
?>
where mycrontroller is the CI controller you want to fire.
if you want the controller to only be run by crond ,as opposed through public www requests, add the following line to the controller and to the cronnedscript.php :
if (isset($_SERVER['REMOTE_ADDR'])) die('Permission denied');
I realize that this is a reference to Drupal, however they do a very nice job of explaining what each and every parameter is in the wget call.
Drupal Cron Explanation
If you want the more generic explanation, you can find it here.
Try this and save it by making a folder in the C drive with a .bat extension.
Then give the path of this script to task scheduler.
Then run the same.
C:\xampp\php\php-win.exe -fC:\xampp\htdocs\folder name\index.php controllername functionname

Crontab in Plesk

I'm trying to run a test script using crontab within Plesk. The php file simply emails me a message
mail('me#somewhere.com','Cron Test','Test');
My path to php is /user/bin/php
I have entered * in every field, to run the script every minute with the following command:
/usr/bin/php -q /usr/httpdocs/crontest.php
However, the script is not being run.
Can anyone help?
I'm probably missing something simple, I've never used cron before.
Any advice appreciated.
Thanks.
I would start by getting it to write to a log file. eg:
* * * * * /usr/bin/php -q /usr/httpdocs/crontest.php >> /a-location/crontest.log 2>&1
This will at least give you any obvious errors like not being able to find php etc.
I found that when using the user based cron in plesk, there are a number of issues:
first I found that you should reference the script from the virtual domain. If your script has an absolute address of /var/www/vhosts/domain.com/httpdocs/email-this.php, you should reference it as httpdocs/email-this.php in the crontab.
Second, the script has to have very particular permissions, but not sure what they "must be." apache:apache is all that ever worked for me. Even with the group write permission set, user still had to be apache... weird.
Third, the easiest way to do the testing was to edit the crontab directly instead of going back into plesk every time I needed to make a change... Edit your crontab like this:
crontab -u [filesystem-username] -e
Fourth, I could never get the crontab to write to a log file outside of httpdocs (I tried statistics/logs/cron_log every way I could think of... lol... no dice). I ended up just adding the MAILTO directive at the top of the crontab file during testing:
eg:
MAILTO=you#domain.com
## * * * * * php -q httpdocs/cron.php
Also see this if you have Plesk 10 or above: http://shaun.net/2011/09/solving-plesk-10-3-1-cron-issues/
I had to do this
/usr/local/psa/bin/server_pref -u -crontab-secure-shell "/bin/sh"
to get this (example) working: wget -O - http://www.yourdomain.com/cron.php

Categories