用PHP创建Web服务器(不带Apache)

Yoo*_*one 11 php sockets apache webserver http

我刚试过这段代码:

<?php
set_time_limit(0);

$address = '176.9.117.136';
$port = 9000;

$sock = socket_create(AF_INET, SOCK_STREAM, 0);
socket_bind($sock, $address, $port) or die('Could not bind to address');

while(1)
{
    socket_listen($sock);
    $client = socket_accept($sock);

    $input = socket_read($client, 1024);
    echo $input;

    $output = 'URL: http://ip-of-my-server:9000/
HTTP/1.1 200 OK
Date: Tue, 10 Jul 2012 16:58:23 GMT
Server: TestServer/1.0.0 (PHPServ)
Last-Modified: Fri, 06 Jul 2012 14:29:58 GMT
ETag: "13c008e-1b9-4c42a193de580"
Accept-Ranges: bytes
Content-Length: 441
Vary: Accept-Encoding
Content-Type: text/html

';
    socket_write($client, $output);

    socket_close($client);
}

socket_close($sock);
?>
Run Code Online (Sandbox Code Playgroud)

但有一个问题.Apache没有使用$ output的内容作为标题,而是返回自己的标题...

我不知道为什么,因为我通过这个命令执行脚本:php webserv.php.

但它实际上是有效的,因为当我http://ip-of-my-server:9000/从浏览器加载页面时,它会显示客户端在服务器上发送的标题,并将内容返回$output给客户端(我的浏览器).

如果可能的话,我想只在PHP中创建自己的网络服务器.我只是想知道如何在没有Apache的情况下运行它,所以我可以管理自己的HTTP头.

rod*_*ehm 18

是否有理由在PHP(所有东西)中实现HTTP服务器?没有线程等等.这将是一种痛苦......(除非这是一种学术性的东西......)

PHP 5.4附带内置的Web服务器.也许这就是你要找的......


更新:

虽然我理解你学习这类东西的动机,但我相信你在使用PHP尝试这种东西时走错了路.PHP并不是真正设计用于长时间运行的进程(就像服务器一样),它不适用于并行处理(线程).即使是多处理,也需要PCNTL,特别是pcntl_fork(),并将你的教育步骤限制在基于Unix的系统上(尽管这可能不是问题).

如果您的目标是了解服务器如何处理并发,我建议使用专为此设计的语言(Erlang,Go,Scala,...).或者使用一种至少可以模拟并行处理的语言(Python,Ruby,...... [有点像,因为它们的GIL]).

如果您的目标是了解HTTP(并告诉您HTTP是一个野兽,如果您要经过HTTP/1.0并且想要正确行事),摆弄PHP可能没问题,如果它是您唯一的语言如果是这样的话,请看看这篇(遗憾的德语)关于PHP中的Socket服务器的文章中的示例代码(聊天服务器),以获得专注于实际HTTP的基本套接字.


更新2:

要回答关于标题的问题......我不知道apache如何适合您问题中描述的场景.但是我看到你正在使用换行符来分隔标题,使用双换行符来分隔标题.除非你使用\r\n默认的换行符(windows-style)保存你的php文件,否则你的标题部分是格式错误的,因此会被识别为正文.根据http客户端(用户代理,可能是您的浏览器,或卷曲,或其他),可以使用"插入一些默认标头"来处理.替换您的换行符,\r\n然后重试.

如果您的服务器可以从互联网访问,请尝试使用一些标头测试工具来验证您的HTTP是否合理.如果它只是localhost,请查看curl -I http://ip-of-my-server:9000吐出的内容.