将php5_module添加到apache服务器的复杂性

I have a lot of questions regarding the differences between php files on a server and perl files (or any other for that matter). But I'm going to try and start off simple and work up.

First I clean installed OSX Yosemite on my mac. Apache2 comes pre-installed with this OS. I changed nothing in the httpd.conf and my files are located here:

DocumentRoot "/Library/WebServer/Documents"

I have 3 files welcome.pl, welcome.php and welcome.txt all with the same content.

$name="Matt";
$email="foo@bar.com";

print "<!DOCTYPE html>
";
print "<html>
<body>

Welcome " . $name . "<br>
Your email address is: " . $email . "

</body>
</html>";

Except welcome.pl replaces

$email="foo@bar.com";

with

$email="foo\@bar.com";

since perl scripts escape the @ sign other than that the only difference is their extension.

If I start my apache server and open three browser windows and go to their respective pages then they all look the same:

http://localhost/welcome.php

(reproduced in Safari and Chrome)

Likewise if I open three browser windows and go to their respective file system resource then they all look the same:

same output for three file system files

(reproduced in Safari and Chrome)

However, if I then enable php by uncommenting:

#LoadModule php5_module libexec/apache2/libphp5.so

in my httpd.conf file, restart the server and open three browser windows and go to their respective pages then welcome.php changes to:

generic server php enabled

(reproduced in Safari and Chrome)

However, again if I go to their respective file system resource then they all look the same. Why does the server parse things differently for the php file?

Now lets change welcome.php to

<?php
$name="Matt";
$email="foo@bar.com";

print "<!DOCTYPE html>
";
print "<html>
<body>

Welcome " . $name . "<br>
Your email address is: " . $email . "

</body>
</html>";
?>

If I save the file and restart the server then I get:

welcome php file with php tag

(reproduced in Safari and Chrome)

which makes sense, but if I change welcome.pl to:

#!/usr/bin/perl
print "Content-type: text/html

";
$name="Matt";
$email="foo\@bar.com";

print "<!DOCTYPE html>
";
print "<html>
<body>

Welcome " . $name . "<br>
Your email address is: " . $email . "

</body>
</html>";

I still get:

welcome perl file with perl interpreter comment

(reproduced in Safari and Chrome)

However, if I uncomment:

#LoadModule cgi_module libexec/apache2/mod_cgi.so

in the modules section, replace

Options FollowSymLinks Multiviews

with:

Options FollowSymLinks Multiviews ExecCGI

in the "Library/WebServer/Documents" directory directive and add

AddHandler cgi-script .cgi .pl

in the "Library/WebServer/Documents" directory directive then if I restart the server I get:

welcome perl file with ExecCGI enabled and perl CGI handle

(reproduced in Safari and Chrome)

but now if I replace

AddHandler cgi-script .cgi .pl

AddHandler cgi-script .cgi .pl php

restart the server and go to localhost/welcome.php

then I get an internal server error (reproduced in Safari and Chrome)

but then if I replace

<?php
$name="Matt";
$email="foo@bar.com";

print "<!DOCTYPE html>
";
print "<html>
<body>

Welcome " . $name . "<br>
Your email address is: " . $email . "

</body>
</html>";
?>

with

#!/usr/bin/php
<?php
print "Content-type: text/html

";
$name="Matt";
$email="foo@bar.com";

print "<!DOCTYPE html>
";
print "<html>
<body>

Welcome " . $name . "<br>
Your email address is: " . $email . "

</body>
</html>";
?>

then it's fine again (reproduced in Safari and Chrome). I guess my point is there seems to be two types of compilation of php on the server. One for compiling text files with php extensions and another for running php scripts and returning the output to the client.

I would like to know why this is. Is the difference only in the server? Could I pass a php file in the command line as input to the php compiler and get similar results or is the server doing some intermediate work that I'm not seeing?

It seems to me that you have installed both PHP as a CGI, and as an Apache module (mod_php5).

In both cases you need the PHP open tag <?php for a file to "work"; the error is different in the two cases though, CGI giving you an internal server error and the module displaying the file contents as HTML.

You could probably reproduce a similar dual behaviour for Perl files by installing mod_perl.