How to schedule a task that runs php using window task scheduler? - php

I've been trying to run a php file using window task scheduler. I've tried using the .bat file, but it won't work.
Here's what I've done:
I've created a task "Download Image"
I've created a .bat file, and the content is:
"C:\xampp\php\php.exe" -f "D:\server\newxml\download.php";
The php file that I want to run is:
ini_set('max_execution_time', 300);
$doc = simplexml_load_file('xml_edit_feeds.xml');
foreach ($doc->xpath("//item") as $item) {
$name = $item->productname;
$realname = preg_replace('/\s/', '',$name);
$url = $item->thumbnail_url;
$img = 'D:/server/newxml/imagethumbnail/'.$realname.'.png';
$filename = 'D:server/newxml/imagethumbnail/'.$realname.'.png';
file_put_contents($img, file_get_contents($url));
}
?>
This is the screen shoot of the windows task scheduler:
Is there something wrong from what I did? Thank you for your help

I didn't try this before, but I think you should use a browser exe program to open your webpage instead of php.exe.

Eureka! I got the answer to this, so, I what I've done is:
Set the Program/Script to: C:\xampp\php\php.exe
Set the arguments to: D:\path\to\php.php (In my case D:\server\newxml\download.php)
Set the start-in to the folder that contains download.php (php file that you want to run). In my case: D:\server\newxml\

Related

Add Pictures to comments in PhpSpreadsheet

I have a comment in PhpSpreadsheet and I want to add a backgroundpicture to it.
The comment is created like this:
$spreadsheet->getActiveSheet()->getComment($cell)->getText()->createTextRun('Test text');
But there is nothing in the documentation about how to add a backgroundpicture to it.
I was able to solve my issue with a (bad, but working) workaround. It seems that PHPSpreadsheet is not able (yet) to create a backgroundpicture to a comment, maybe PHPSpreadsheet can do it in the future.
Workaround:
PHPSpreadsheet is not able to create a comment with backgroundimage, but Powershell is. With the following Powershell script you are adding a background image to a comment in row C2, in worksheet 1.
$excel = new-object -comobject excel.application
$workbook = $excel.workbooks.open("C:\MyExcel.xlsx")
$worksheet = $workbook.worksheets.item(1)
$image = "C:\MyPicture.png"
$worksheet.Range("C2").AddComment(" ")
$worksheet.Range("C2").Comment.Shape.Fill.UserPicture($image)
$workbook.save()
$workbook.close()
Stop-Process -processname powershell*
With that knowledge, you are able to create a dynamically Powershell script inside PHP:
$ps_script=Array();
$ps_script[]='$excel = new-object -comobject excel.application';
$ps_script[]='$workbook = $excel.workbooks.open("'.$excel_output_path.'")';
$ps_script[]='$worksheet = $workbook.worksheets.item('.($sheetindex+1).')';
$ps_script[]='$image = "'.$img_path.'"';
$ps_script[]='$worksheet.Range("'.$cell.'").AddComment(" ")';
$ps_script[]='$worksheet.Range("'.$cell.'").Comment.Shape.Fill.UserPicture($image)';
$ps_script[]='$workbook.save()';
$ps_script[]='$workbook.close()';
$ps_script[]='Stop-Process -processname powershell*';
$ps_script = implode("\r\n", $ps_script);
file_put_contents($powershell_output, $ps_script);
Now we create a CMD script, calling that Powershell script:
$call_powershell_script=Array();
$call_powershell_script[]="TASKKILL /F /IM powershell.exe";
$call_powershell_script[]="TASKKILL /F /IM EXCEL.exe";
$call_powershell_script[]=$powershell_path.'powershell.exe "'.$powershell_output.'"';
$call_powershell_script[]="TASKKILL /F /IM powershell.exe";
$call_powershell_script[]="TASKKILL /F /IM EXCEL.exe";
$call_powershell_script = implode("\r\n", $call_powershell_script);
file_put_contents($call_powershell_script_path, $call_powershell_script);
And finally we call this CMD script inside PHP:
$output = shell_exec($cpowershell_script_path." 2>&1");
echo "<br>";
echo $output;
echo "<br>";
Note:
Normally the Powershell script doesn't need this line:
Stop-Process -processname powershell*
But without it, the PHP script takes forever.
Note2:
I received an error in Powershell, when the script was run by PHP, that my Excel file was not accessable:
Exception calling "Open" with "1" argument(s): "Microsoft Office Excel cannot access the file 'C:\MyExcel.xlsx'. There are several possible reasons: The file name or path does not exist. The file is being used by another program. The workbook you are trying to save has the same name as a currently open workbook.
The solution for this error was found
here.

fopen(), fwrite() function is not working in php

Below is my code,
test.php
<?php
$prefixnew = "testnew";
$file1 = fopen("testnew.txt","w");
$content_wr_g = "Test sitest"
fwrite($file1,$content_wr_g);
fclose($file1);
?>
test.bat
#ECHO off
C:\wamp\bin\php\php5.3.13\php.exe -f "C:\...\test.php"
popd
UPDATE
When i run (test.php) directly from browser it is working properly. if i run from scheduled tasks, it is not working.
I know very well about task scheduler steps to create a task. When i run set of update queries or delete queries means, it working nicely.
When i have code like fopen(), fwrite() etc it is not working
Instead of using relative path, use absolute path to the file:
$file1 = fopen(__DIR__.'/testnew.txt', 'w');
I assume you are using >= PHP 5.3, if not try:
$file1 = fopen(dirname(__DIR__).'/testnew.txt', 'w');

Save the console text into a txt file? (PHP)

actual I finished writing my program. Because it is only a plugin and it runs on a external server I still want to see if I get some errors or something else in the console.
I wrote every console input with echo ...;. My question now is if it is possible to get the text of the console?
Because then I could easily safe it in a .txt file and could get access to it from the web :) - Or is there another way to get the console text?
I could probably just say fwrite(...) instand of echo ...;. But this will cost a lot of time...
Greetings and Thank You!
An alternative that could be usefull on windows would be to save all the output buffer to a txt, first check your php configuration for the console app implicit_flush must be off then
<?php
ob_start(); //before any echo
/** YOUR CODE HERE **/
$output = ob_get_contents(); //this variable has all the echoes
file_put_contents('c:\whatever.txt',$output);
ob_flush(); //shows the echoes on console
?>
If your goal is to create a text file to access, then you should create a text file directly.
(do this instead of echoing to console)
$output = $consoleData . "\n";
$output .= $moreConsoleData . "\n";
(Once you've completed that, just create the file:)
$file = fopen('output.txt', 'a');
fwrite($file, $output);
fclose($file);
Of course, this is sparse - you should also check that the file exists, create it if necessary, etc.
For console (commando line interface) you can redirect the output of your script:
php yourscript.php > path-of-your-file.txt
If you haven't access to a command line interface or to edit the cronjob line, you can duplicate the starndar output at the begining of the script:
$fdout = fopen('path-to-your-script.txt', 'wb');
eio_dup2($fdout, STDOUT);
eio_event_loop();
fclose($fdout);
(eio is an pecl extension)
If you are running the script using the console (i.e. php yourscript.php), you can easily save the output my modifying your command to:
php yourscript.php > path/to/log.txt
The above command will capture all output by the script and save it to log.txt. Change the paths for your script / log as required.

How to create a ZIP file using PHP and ZipArchive without sending it to the browser?

My PHP/MySQL web application has a function that combines a set of images for each user into a single PDF using ImageMagick. Each PDF is then placed into a ZIP file. Each image can be up to 5 MB in size. My problem is that the browser times out before the user can download the document.
Any ideas on how to best do this?
I was thinking I could create the ZIP file without sending it to the browser (i.e. remove the "headers" at the end of my code) and then email a link to the file; however, it still requires that the user wait a long time for the ZIP file to be created (it appears as if the browser is just hanging). Could this be done with AJAX behind the scenes or directly on the server somehow?
$tmp_path = sys_get_temp_dir().'/';
$archive_name = "myarchive.zip";
$zip = new ZipArchive();
if($zip->open($archive_name,1 ? ZIPARCHIVE::OVERWRITE : ZIPARCHIVE::CREATE) !== true) {
return false;
}
foreach ($rows AS $row) {
$irows = get_images($row['user_id']);
$images = array();
foreach($irows AS $irow){
$doc = fetch_document_path($irow['id']);
$output_file_name = $tmp_path.$irow['id'].'.jpg';
exec ('convert '.$doc.' '.$output_file_name);
$images[] = $irow['id'].'.jpg';
}
$images = implode(' ', $images);
$output_file_name = $tmp_path.$row['name'].'.pdf';
exec ('convert '.$images.' "'.$output_file_name.'"');
$zip->addFile($output_file_name,basename($output_file_name));
}
$zip->close();
header('Content-type: application/zip');
header('Content-Disposition: attachment; filename="output.zip"');
readfile($archive_name);
IMO you should run some background task that will do the job. Background worker can for example save URL to result file in DB after it'll finished (can also save some more information like current status and job progress), meantime webpage can periodically ask server using AJAX if job is already done or not and finally display link when it'll be available.
Simplest way to achieve that is to run your script as background process:
$arg1 = escapeshellarg($somearg1);
$arg2 = escapeshellarg($somearg1);
exec(sprintf('/usr/bin/php archiver.php %s %s > /dev/null 2>&1 & echo $!', $arg1, $arg2));
archiver.php should begin with following lines:
<?php
ignore_user_abort(true);
set_time_limit(0);
it'll prevent script from being stopped when parent script will finish working.
Second idea I have is more complex - you can write a daemon that will run in background waiting for jobs. To communicate with it you can use queues (like AMQP) or just database. With daemon you'll have more control on what is happening and when - in first approach it can happen that your application will fire too many processes.

Cron jobs help

I am trying to make a cron job via my websites cpanel. I have talked to the support services and they gave me this command to run to execute a php file on my website.
/usr/local/bin/php -q /home/mymcstatus/domains/mymcstatus.net/public_html/redesign/scripts/update.php
This doesnt seem to work though, I have also set the minute interval to every minute using */1.
I am using the code below inside of the file update.php:
<?php
ini_set('display_errors', 1);
ini_set('log_errors', 1);
ini_set('error_log', dirname(__FILE__) . '/error_log.txt');
error_reporting(E_ALL);
require('minequery.class.php');
include('../config/config.php');
$date = date("D-M-Y");
$file = fopen("UPDATE_LOG($date).txt", 'w');
$query = mysql_query("SELECT * FROM servers") or die(mysql_error());
if($query) {
while($row = mysql_fetch_array($query)) {
$ip = $row['ip'];
$port = $row['port'];
$name = $row['name'];
$string = "[UPDATE LOG]: $date - Updated Server $name \n";
fwrite($file, $string);
print("[UPDATE LOG] Updated Server $name </br>");
}
mail("duncan#mymcstatus.net","UPDATED","Server has updated","From: Mymcstatus");
} else {
print("Cant query");
}
?>
When I go to update.php manually through the web browser that code works, but nothing seems to happen with the Cronjob. What am I missing or doing wrong?
There are a few things that could be going on here. The first is to check the file permissions of update.php and make sure it is executable. The cron may be executing as a different user that doesn't have permission to execute update.php. The 2nd thing you can try is including this as the very first line of update.php with no whitespace before it.
#!/usr/local/bin/php
Usually cron jobs aren't run from the same directory where your PHP lives so it's possible that it is running but the output file is being created elsewhere. Try changing the output file path to be the full path to the file, i.e:
$file = fopen("/home/mymcstatus/domains/mymcstatus.net/public_html/redesign/scripts/UPDATE_LOG($date).txt", 'w');
With the help of the above comments I managed to fix the file paths but it also came down to the command. I had put the wrong user path in here is the command that works.
/usr/local/bin/php -q /home/mymcstat/domains/mymcstatus.net/public_html/redesign/scripts/update.php
Thanks for the help
It's always a good idea to cd to your script's path. This way you don't need any change in the name of the include and require files and any other file names engaging in file operations. Your cronjob command could look like this:
cd /home/mymcstatus/domains/mymcstatus.net/public_html/redesign/scripts/; /usr/local/bin/php -q /home/mymcstatus/domains/mymcstatus.net/public_html/redesign/scripts/update.php
You don't need to supply any absolute file paths this way.

Categories