20

I have a PHP console script that is called via cron which itself among other things creates a tar file of a directory.

When calling the PHP script via cron the the tar file is not created correctly. The following error is given when viewing the tar file:

gzip: stdin: unexpected end of file
tar: Unexpected EOF in archive
tar: Error is not recoverable: exiting now

When calling the PHP script manually via console the tar file is created correctly. The cron log output shows no errors.

Here the tar call form the PHP script.

 exec("cd $this->backupTempFolderName/$id; tar -czf ../../$this->backupFolderName/$tarFileName $dbDumpFileName documents");

Dose anybody have an idea why the tar is created correctly when manually called and fails when called via cron?

Update: The error given while creating the tar file via cron is:

tar: ../../backup/20150819-060003.tar.gz: Wrote only 4096 of 10240 bytes
tar: Error is not recoverable: exiting now

Sometimes the error is:

tar: ../../backup/20150819-054002.tar.gz: Cannot write: Broken pipe
tar: Error is not recoverable: exiting now

As said before, the when executed via cron the tar file is created, but always 50% of the correct size (when manually executing the script):

-rw-r--r--  1 gtz gtz 1596099468 Aug 19 06:25 20150819-042330.tar.gz <- Manually called skript, working tar
-rw-r--r--  1 gtz gtz  858570752 Aug 19 07:21 20150819-052002.tar.gz <- Script called via cron, broken tar

Update 2

After doing some further research based on the input given here, might should add that the cron called script is running on a virtual private server - I suspect that some limitations may exist for cron jobs that are not documented by the hoster (only limit on minimum repetition time is given in the docs).

wowpatrick
  • 5,082
  • 15
  • 55
  • 86
  • What is the exact crontab entry? What do those variables `$this->backTempFolderName/$id, $this->backupFolderName/$tarFileName, $dbDumpFileName` expand to? – Michael Berkowski Aug 17 '15 at 14:45
  • Variables just extract to strings with folder paths (which work fine, as the script works correctly when called manually) and the corn job entry is `59 23 * * 0 cd path/to/application; /opt/php53/bin/php app/console giz:backup >/paht/to/application/app/logs/backup-output.log`. The `backup-output.log` itself contains no errors as the php script itself seems to work fine. – wowpatrick Aug 17 '15 at 15:10
  • But do the expanded paths have spaces? Are the relative or absolute? Does the crown job run as the same user? Does the crown user have permission to write the file? – Michael Berkowski Aug 17 '15 at 15:27
  • The path that the params expand to are absolute and have no spaces. The file tar file is created even when called via corn, but as said above it incomplete (so I guess there are no problem with permissions. As the cron/PHP script/tar is run on a virtual server and the tar files a rather large (+ 1 GB), there may be some performance limit. – wowpatrick Aug 17 '15 at 16:55
  • 1
    0) check the syslog. The cronjob (does it run via PHP?) is probably terminated because it exceeds some resource limit (time?) – wildplasser Aug 21 '15 at 08:35
  • 2
    Check the disk space just before the `tar` command is ran and log it. I suspect that you might be short of free disk space at the time the cron is running. – VolenD Aug 21 '15 at 09:46
  • Disk space sounds likely. But what about differences in the php.ini? Are you sure it's the same when running directly or with cron, since it could depend on env vars? Try doing a phpinfo() with both cron and in a normal console to check. – M. Ivanov Aug 25 '15 at 02:09
  • Include what server environment this is; I would discourage trying to use cron this way, it's better to have cron call the script instead of trying to script cron. – l'L'l Aug 27 '15 at 16:29
  • @wowpatrick the error occur only when you try to execute the php file right.?? – Nikhil.nj Aug 28 '15 at 05:44
  • Try running with -cjf and with -cf options. Also try error logging a timestamp before and after the exec command. If it's a disk space issue, you should see the created .tar.bz2 and .tar files roughly the same size as your .tgz. If it's a read permission issue, you should see them truncate at roughly the same point in the .tar, If it's a timing issue (PHP script terminating early), you'll never get the error log after the exec. – sibaz Jul 12 '16 at 15:46
  • Could we se the cron configuration how often is running the command? – Michele Carino Jan 10 '17 at 06:35

8 Answers8

1

That error comes usually from lack of disk space.

I would do some more researching on this subject, by adding some logs before and after the tar execution.

Also check what user your configuration is using for the cron job you have running the backup. It can be some quota limit on that user as well, that doesn't happen when you run on the console outside cron.

Ask your provider for quota limits on the VPS for users and for processes... That is what rings the bell here.

prc
  • 860
  • 7
  • 16
  • And if at all possible, check **what user the cron job runs under**, and run from the command line **using that same user**. The cron user might be chroot-jailed into a VFS with very little free space in the temporary directory, or things like that. – LSerni Mar 02 '17 at 19:30
0

I guess that you have a resource limitation As M. Ivanov has said, add this command in your PHP script:

shell_exec("php -info");

and check this parameter both when you execute your script from command line and from cron job

memory_limit => ???

You can also try to run your cron by enhancing the memory limit to 1600M

php -d memory_limit=1600M scriptCompressor.php

Hope that helps :)

Halayem Anis
  • 7,654
  • 2
  • 25
  • 45
  • I modified the backup script as mentioned above and ran it manually via a console call. The memory limit set in the php.ini is `memory_limit => 128M => 128M`. When called via cron, the memory limit is also at 128M. But shouldn't the PHP memory be relevant in this case (http://stackoverflow.com/a/11291704/461992)? – wowpatrick Aug 26 '15 at 15:05
0

cronjobs by themselves usually don't have limits. If you are using shared hosting they may have installed some enforcing scripts but I suspect they would also break your console backups.

If you are running cronjobs from some container, e.g. Drupal, they have special limits.

Also check bash limits with: ulimit -a

Report disk space before backup starts and afterwards just in case. It's usually quite small on VPS.

adam-asdf
  • 646
  • 7
  • 16
Antti Rytsölä
  • 1,485
  • 14
  • 24
0

You may want to try creating the tarball directly from PHP to avoid the exec call. See this answer: https://stackoverflow.com/a/20062628/5260945.

Also, looking at your cron entry, there is no leading slash on your example. I know this could just be a typo for the comment, but make sure you have an absolute path for the cd command. The default environment for a cron job is not the same as for your login shell.

Community
  • 1
  • 1
Nigel Tufnel
  • 418
  • 3
  • 14
0

I am sure its memory or execution time problem. Do one thing run the same script for directory which contains only single test file and check the output, if your script works in this scenario then 100% sure its memory problem.

try to tweak memory parameter and execute your script.

I hope this help you.

Thanks

Anant Waykar
  • 662
  • 2
  • 8
  • 18
0

Looking at the following error.

tar: ../../backup/20150819-054002.tar.gz: Cannot write: Broken pipe
tar: Error is not recoverable: exiting now

I see that as the exec function in the PHP script is not blocking or causing an error prematurely. So the PHP session that get's called during the Cron job exits before the command finishes. This is just a guess but you can try to send this to the background when you run it from Cron.

exec("cd $this->backupTempFolderName/$id; tar -czf ../../$this->backupFolderName/$tarFileName $dbDumpFileName documents &");

This command should be blocking so this is just a shot in the dark.

http://php.net/manual/en/function.exec.php

Melvinchi
  • 51
  • 2
-3

Error occurs when you trying to execute the php file and gives EOF error. It means somewhere in your php file you must check the code of your cron file it may happen that you forget to complete the brackets of the condition or class etc...

Good luck ['}

Nikhil.nj
  • 242
  • 1
  • 11
-3

To write the errors to the log when executed via cron replace >/paht/to/application/app/logs/backup-output.log in the cron line by 2>&1 >/path/to/application/app/logs/backup-output.log Also check the path in the cron line .. maybe the change-dir is not working as you might think. Try printing getcwd() to a log or something, when running the php script from cron.

Edit: I wonder why this was voted not useful. The questioner mentioned that no errors are printed to the log when the cron executes the script. Thats not hard to imagine as > just redirects the STDOUT and not the STDERR (on which php errors would get printed) to the log. So adding 2>&1 might reveal some new informations.

bloodstix
  • 144
  • 5