In Python, we can add the command line log to a file instead of the console using this command:
python script.py >> mylogfile.txt
How can I do it using PHP? I've tried
php script.php >> mylogfile.txt
but it doesn't work.
I use Windows 10.
I finally found the answer. It's based on the article PHP on the Command Line – Part 1 Article
I first used php script.php > mylog.txt which returns some of the log text to the console, so I thought it's not writing to the log, but it does. I wanted php script.php > mylog.txt 2>&1 which will add any log to the file.
The article says it doesn't work in Windows, but I use Windows 10 and it works.
The error messages are mixed with the normal output as before. But by
piping the output from the script, I can split the errors from the
normal output:
php outwitherrors.php 2> errors.log
This time, you’ll only see these messages:
Opening file foobar.log Job finished
But, if you look into the directory in which you ran the script, a new file called errors.log will have been created, containing the error
message. The number 2 is the command line handle used to identify
standard error. Note that 1 is handle for standard output, while 0 is the handle for standard error. Using the > symbol from the command line, you can direct output to a particular location.
Although this may not seem very exciting, it’s a very handy tool for
system administration. A simple application, running some script from
cron, would be the following:
php outwitherrors.php >> transaction.log 2>> errors.log
Using ‘>>‘, I tell the terminal to append new messages to the existing
log (rather than overwrite it). The normal operational messages are
now logged to file transaction.log, which I might peruse once a month, just to check that everything’s OK. Meanwhile, any errors that need a quicker response end up in file errors.log, which some other cron job might email me on a daily basis (or more frequently) as required.
There’s one difference between the Unix and Windows command lines,
when it comes to piping output, of which you should be aware. On Unix,
you can merge the standard output and standard error streams to a single destination,
for example:
php outwitherrors.php > everything.log 2>&1
It reroutes standard error to standard output, meaning that both get
written to log file everything.log.
Related
I have windows batch file and also its scheduled in task scheduler.
task schedule working fine but the windows batch file does not execute
its in an php file. I am learning php and the windows batch file was coded previous employee.
The below code which i took from inside the windows batch file.
The path is correct , what is the purpose of - f ? and can you correct me the code.
List of commandline options can be found here http://php.net/manual/en/features.commandline.options.php
in your case -f stands for Parse and execute File
Change your batch to something like this:
#ECHO ON
echo Before php %TIME% %DATE% >> C:\temp\task.log
C:
Cd \www2
C:\PHP5.3\php.exe -f "C:\www2\cron.php" >> C:\temp\task.log
echo After php %TIME% %DATE% >> C:\temp\task.log
As long as you have the echo command and the call of the php interpreter on a single line this only output a meaningless text to the screen.
The first echo is there to help you diagnose problems: if the scheduled tasks is being called you will see this logged in task.log.
To make sure that the working directory is set to C:\www2 (cron.php will look for files there unless they get addressed with a full path) we change to that directory before running php.
In case php prints any error messages or information we redirect that output to the same log because otherwise you will not see this. You should delete that log from time to time because it can grow considerably. It is up to you to decide which of the logging statements you want to keep or remove ;-)
You can even have the log roll over by size, I bet there are question here on SO that will show you how this can be done ;-)
I am migrating a set of php scripts from Window 2003 / PHP 5.2 to Windows 2012 R2 / PHP 5.6.7
In the scripts exec commands are used, for example to copy files. Commands could look like this:
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\ >> output.log');
You could argue that there are better ways to copy files, but I rather wouldn't like to rebuild these scripts right now.
The problem I have is that when there are no files to copy, the error "The system cannot find the file specified." is now shown, while this wan't the case on the old server.
If you just execute the copy command on the command line, the output looks like this:
The system cannot find the file specified.
0 file(s) copied.
This is the same as what gets written to output.log
So apparently the "0 file(s) copied" is getting suppressed somewhere, but not the error.
So my question is, how do I get rid of the error on the commandline? I thought it would be some configuration in php.ini, but after comparing the php.ini from the old and the new server, I couldn't find any essential differences.
I've tried a few things to suppress the error, but with no success:
Adding a # to the exec command
Adding ob_start() and ob_end_clean() before and after the command
Edit: please do not flag as a duplicate. I did see that question before asking my question. the answers given there do not solve my issue. The main question is, why was it working before, you would think that it should still be possible to get it working the same way without modifications to the scripts.
Try adding "2>&1" to your command.
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\ >> output.log 2>&1');
This should redirect the error output to output.log
I suppose that this string is being printed to stderr.
You could try to replace your STDERR as described in the post https://stackoverflow.com/a/3823015/146003.
The essential part of the post consists of the lines:
fclose(STDERR);
(...)
$STDERR = fopen('error.log', 'wb');
You can then get rid of error.log. Although I didn't try, you could try to open NIL (see https://stackoverflow.com/a/313115/146003)
First of all, you are redirecting the output of the copy command to a text file, so it will not be ouput to console.
Do this way instead:
exec ('copy "C:\ftp\suppliername\upload\*.*" c:\somefolder\', $output);
var_dump ($output);
I have a C++ console application that returns some kind of things, then, I need to show that in a browser. So I tried to write every console.write from C++ to a .txt file for future PHP reading, but no success because it doesn't write the errors!
Then I tried to use exec('program.exe', $output); at PHP but no success too.. :/
Is there another way to do that?
Or any function in C++ that writes to a .txt every single thing that shows up in the console?
Or some function in another Programming Language that catches everything in the console?
You have to understand that cout (standard output) and cerr (standard error output) are two different streams, so probably you forgot to redirect cerr to your text file as well. Here some ideas you can use:
Redirect your streams to a file on your code (see How to redirect cin and cout to files?)
Redirect the output of any console program from the command line (you don't require to change the code and works on windows and unix / linux) by calling it this way executable.exe > out.txt 2>&1 (see Redirect all output to file)
Connect your web application to your console application using TCP sockets (might be an overhead but useful if the application requires some kind of interactive control)
There are three standard file handles known as stdin, stdout, stderr. Looks like you're only fetching stdout right now. Try to redirect stderr to stdout.
exec('program.exe 2>&1', $output);
(works not only on *nix but also win32).
see also: In the shell, what does " 2>&1 " mean?
I have a question regarding running a shell command via PHP. My goal is to successfully run compass compile [project] via PHP. I have tried the following:
echo system('compass compile [project]', $s); // prints [31m[0m
echo $s; // prints 1
echo passthru('compass compile [project]', $p); // prints [31m[0m
echo $p; // prints 1
echo shell_exec('compass compile [project]'); // prints [31m[0m
echo exec('compass compile [project]', $e, $ee);
print_r($e); // Array ( [0] => [31m[0m )
echo $ee; // prints 1
I even tried running a shell command to an executable file that contained compass compile test and I still got the same results as the trials above.
My questions
What does [31m[0m mean? Does this represent binary data? Do these represent bash colors as search engines suggest?
As far as I know, the output should be the following:
For kicks, I tried to execute via system(/usr/local/bin/compass compile [project]); and I got the same result. I double checked my path so I know I can execute these commands as expected. Here is the output from echo $PATH:
/usr/lib/lightdm/lightdm:
/usr/local/sbin:
/usr/local/bin:
/usr/sbin:
/usr/bin:
/sbin:/bin:
/usr/games:
/usr/local/games:
/var/lib/gems/1.9.1/bin
Is there a way to compile compass projects using PHP?
I've seen a similar error before.
Typically it is due to the things being output in the bash startup scripts. For example, I had an echo in one of my bash startups that jacked up a lot of scripts till I realized what was causing the problem.
Or, perhaps the user (www-data ?) doesn't actually have a home dir and appropriate startup scripts in place?
You can try this to get a non interactive shell:
exec("/bin/bash -c \"compass compile [project]\"", $e, $ee);
print_r($e);
echo $ee;
If you still have issues, try redirecting the output to a tmp file, an checking it:
exec("/bin/bash -c \"compass compile [project] > /tmp/compass.compile.output\"", $e, $ee);
print_r($e);
echo $ee;
See also: What's the difference between .bashrc, .bash_profile, and .environment?
The issue was fixed by using sass --compass and redirecting the stderr to stdout via echo shell_exec("sass --compass [project] 2>&1");
It was a pretty long and arduous process figuring this out since it's been awhile since I've dabbled in command line programs. Remember that error streams and output streams might be on different outputs. The easiest way to test this is to shovel the output into a file via:
# do this once with a good file and once with a file that will give errors
sass --poll style.scss > output.txt
If output.txt is empty then the error output is on the stderr stream such as the case above. We can correct this by redirecting the stderr to the srdout. For example:
sass --poll > output.txt 2>&1
#shows results
cat output.txt
I created a simple PHP script that redirects the output from one textarea to the other. The code can be found here.
First guess would be a permissions issue. Odds are the user account running PHP (unless you're running this from the command line, I'm guessing that this is the user that the httpd apache daemon is running under) doesn't have the permissions to do what you're asking. The errors are extremely unhelpful, however.
From what I can tell, it looks like an attempt to have the error show up in red on the command line. My guess is that there are hidden (or somehow never printed out) characters in-between the codes. Check out some of your apache and/or PHP error logs to see if anything helpful is showing up there that never made it into the PHP variable. Or, for kicks, try copy and pasting the output with the bash colors into a basic text editor and first delete each character from the beginning one by one... see if anything magically appears. If that doesn't work, try the same in reverse, backspacing from the end. Either way, there's an error occurring, so important that it must show in bold red letters to you, it's just not getting to you.
If it does in fact turn out to be a permissions issue, and it's one you can't remedy through permissions wrangling, you could create an intermediary file that your Apache user has permissions to write to, and your cron user has permissions to read from. Instead of running the code directly from PHP, put it in the file, then run a cron on a frequent basis looking for anything in that file, CHECKING IT FOR VALIDITY, and then running it through the compiler and removing it from the file.
It'd be ugly, but sometimes pretty things don't work.
You guessed it right it is colors but the way it is defined is not right. For more information regarding using colors in console please refer to this document. Also, for compiling SCSS via compass you can use shell_exec command in linux. For more information regarding shell_exec please refer to this document. Let us know how it goes.
My aim is to create a log file reader using PHP and Shell scripting.
I plan to run the script at intervals in order to detect the last time a particular entry shows up in the logfile.
The way it should work is by calling the PHP script which in turn calls a shell command
tac logfile.log | grep "what i am looking for" | head -n 1
or
tac logfile.log | head -n 1
What this script will do is:
in the case of the first script: scan the log file from the bottom up until it finds what it is looking for and shows me the first line, which is actually the last occurrence of the line in the file.
in the case of the second script: scan only the last line and output it. I am NOT trying to tail the file.
So my intention is to scan the file from the end to the last occurence but I need php to do this because PHP can parse the lines it reads from the shell output and parse them easily.
The issue i am trying to resolve is that once I run the script from PHP using the functions shell_exec, exec, backtick operator, system etc. They all keep the PHP script running or output the result and keeps the first part of the shell running (tac logfile.log).
I dont understand why it works perfectly from CLI but runs indefinitely by trying to tac the whole log file when I run the same script from PHP. Ive noticed that tac and cat give this problem. Sometimes it shows the error "Broken pipe".
What should I be doing? How can I fix this?
You could use pure PHP. Open the the file with fopen, an example how to read a file backwards can be found at Read a file backwards line by line using fseek
than just break the loop after you found your string you search for.