PHP web开发HTTP协议中的KeepAlive_PHP技巧_黑客防线网安服务器维护基地--Powered by WWW.RONGSEN.COM.CN

PHP web开发HTTP协议中的KeepAlive

作者:黑客防线网安PHP教程基地 来源:黑客防线网安PHP教程基地 浏览次数:0

本篇关键词:协议开发line测试
黑客防线网安网讯:  WebjxCom提示:对于本机之间的http通信,在测试过程中发现phttp_get的优势有限,基本合乎逻辑。对于本身处理时间比较长的服务,phttp_get的优势也不明显。综上,phttp_get适用于fastcgi...
  WebjxCom提示:对于本机之间的http通信在测试过程中发现phttp_get的优势有限基本合乎逻辑对于本身处理时间比较长的服务,phttp_get的优势也不明显综上,phttp_get适用于fastcgi模式的web应用调用远程http服务,且此http服务器响应时间比较短的情况。
  
  这篇文章已经写完将近一年了,最近从历史邮件里面翻出来,和大家分享一下。
  
  其中使用PHP实现持久的HTTP连接,让我费了很多心思。
  
  曾经想过使用C语言编写一个PHP的扩展来实现,后来发现pfsockopen这个函数,让我豁然开朗,避免重新发明一个轮子,呵呵。
  
  一,KeepAlive的概念:
  
  参见http://en.wikipedia.org/wiki/HTTP_persistent_connection
  
  二,KeepAlive的客户端实现:
  
  使用了PHP支持的pfsockopen来实现,参见:http://cn.php.net/pfsockopen
  
  KeepAlive必要的Header有:
  
  Connection:Keep-Alive
  
  Content-Length:xxx
  
  三,性能对比测试:
  
  几种对比实现方式:
  
  1,使用fsockopen来实现,读取body内容后,关闭连接,参见测试程序中的ohttp_get实现。
  
  2,使用pfsockopen来实现,读取body内容后,不关闭连接,参见测试程序中的phttp_get实现。
  
  3,php实现的file_get_contents
  
  4,第三方测试工具ab
  
  前三种测试在测试程序中都包含了。
  
  测试用例一:
  
  前三种php实现的客户端单进程单线程请求lighttpd服务器一个16字节的静态文件。顺序请求10000次。
  
  客户端与服务器部署在不同服务器,通过内网请求。
  
  测试结果:
  
  第一次:
  
  [root@localhost~]#/opt/bin/phptp.php
  
  phttp_get:5.3641529083252
  
  ohttp_get:8.1628580093384
  
  file_get_contents:12.217950105667
  
  第二次:
  
  [root@localhost~]#/opt/bin/phptp.php
  
  phttp_get:5.033059835434
  
  ohttp_get:9.589075088501
  
  file_get_contents:12.775387048721
  
  第三次:
  
  [root@localhost~]#/opt/bin/phptp.php
  
  phttp_get:5.0181269645691
  
  ohttp_get:8.2286441326141
  
  file_get_contents:11.089616060257
  
  测试用例二:
  
  使用第三方工具ab来进行测试,-k参数开打开keepalive支持,不做并发测试,顺序请求10000次。
  
  客户端与服务器部署在不同服务器,通过内网请求。
  
  以下测试结果部分省略:
  
  未打开keepalive:
  
  [root@localhost~]#ab-n10000-c1“http://10.69.2.206:8080/sms/ns2/save_msg.txt”
  
  Finished10000requests
  
  ConcurrencyLevel:1
  
  Timetakenfortests:10.410467seconds
  
  Completerequests:10000
  
  Failedrequests:0
  
  Writeerrors:0
  
  Totaltransferred:2480000bytes
  
  HTMLtransferred:160000bytes
  
  Requestspersecond:960.57[#/sec](mean)
  
  Timeperrequest:1.041[ms](mean)
  
  Timeperrequest:1.041[ms](mean,acrossallconcurrentrequests)
  
  Transferrate:232.55[Kbytes/sec]received
  
  ConnectionTimes(ms)
  
  minmean[+/-sd]medianmax
  
  Connect:0030.003002
  
  Processing:000.409
  
  Waiting:000.309
  
  Total:0030.003003
  
  打开keepalive:
  
  [root@localhost~]#ab-k-n10000-c1“http://10.69.2.206:8080/sms/ns2/save_msg.txt”
  
  Finished10000requests
  
  ConcurrencyLevel:1
  
  Timetakenfortests:4.148619seconds
  
  Completerequests:10000
  
  Failedrequests:0
  
  Writeerrors:0
  
  Keep-Aliverequests:9412
  
  Totaltransferred:2527060bytes
  
  HTMLtransferred:160000bytes
  
  Requestspersecond:2410.44[#/sec](mean)
  
  Timeperrequest:0.415[ms](mean)
  
  Timeperrequest:0.415[ms](mean,acrossallconcurrentrequests)
  
  Transferrate:594.66[Kbytes/sec]received
  
  ConnectionTimes(ms)
  
  minmean[+/-sd]medianmax
  
  Connect:000.105
  
  Processing:002.10203
  
  Waiting:002.10203
  
  Total:002.10203
  
  四,在实际中的应用
  
  以上实现的phttp_get和mysqlmemcache的中的“保持连接”概念类似,这种技术一般来说,只适用于fastcgi模式的web服务器。
  
  对于本机之间的http通信,在测试过程中发现phttp_get的优势有限,基本合乎逻辑。
  
  对于本身处理时间比较长的服务,phttp_get的优势也不明显。
  
  综上,phttp_get适用于fastcgi模式的web应用调用远程http服务,且此http服务器响应时间比较短的情况。
  
  五,服务端需要注意的事项
  
  1,http服务器必须支持HTTP/1.1协议
  
  2,php应用必须返回Content-Length:的header,具体实现参见:
  
  http://cn.php.net/manual/en/function.ob-get-length.php
  
  需要在代码中加入:
  
  ob_start();
  
  $size=ob_get_length();
  
  header(”Content-Length:$size”);
  
  ob_end_flush();
  
  最后附上测试代码:
  
  <?php
  
  //$url=http://10.69.2.206:8080/sms/ns2/save_msg.txt
  
  functionohttp_get($host,$port,$query,&$body)
  
  {
  
  $fp=pfsockopen($host,$port,$errno,$errstr,1);
  
  if(!$fp)
  
  {
  
  var_dump($errno,$errstr);
  
  return-1;
  
  }
  
  $out=“GET${query}HTTP/1.1 ”;
  
  $out.=“Host:${host} ”;
  
  $out.=“Connection:close ”;
  
  $out.=“ ”;
  
  fwrite($fp,$out);
  
  $line=trim(fgets($fp));
  
  $header.=$line;
  
  list($proto,$rcode,$result)=explode(”“,$line);
  
  $len=-1;
  
  while(($line=trim(fgets($fp)))!=“”)
  
  {
  
  $header.=$line;
  
  if(strstr($line,”Content-Length:”))
  
  {
  
  list($cl,$len)=explode(”“,$line);
  
  }
  
  if(strstr($line,”Connection:close”))
  
  {
  
  $close=true;
  
  }
  
  }
  
  if($len<0)
  
  {
  
  echo“ohttp_getmustcopewithContent-Lengthheader! ”;
  
  return-1;
  
  }
  
  $body=fread($fp,$len);
  
  if($close)
  
  fclose($fp);
  
  return$rcode;
  
  }
  
  functionphttp_get($host,$port,$query,&$body)
  
  {
  
  $fp=pfsockopen($host,$port,$errno,$errstr,1);
  
  if(!$fp)
  
  {
  
  var_dump($errno,$errstr);
  
  return-1;
  
  }
  
  $out=“GET${query}HTTP/1.1 ”;
  
  $out.=“Host:${host} ”;
  
  $out.=“Connection:Keep-Alive ”;
  
  $out.=“ ”;
  
  fwrite($fp,$out);
  
  $line=trim(fgets($fp));
  
  $header.=$line;
  
  list($proto,$rcode,$result)=explode(”“,$line);
  
  $len=-1;
  
  while(($line=trim(fgets($fp)))!=“”)
  
  {
  
  $header.=$line;
  
  if(strstr($line,”Content-Length:”))
  
  {
  
  list($cl,$len)=explode(”“,$line);
  
  }
  
  if(strstr($line,”Connection:close”))
  
  {
  
  $close=true;
  
  }
  
  }
  
  if($len<0)
  
  {
  
  echo“phttp_getmustcopewithContent-Lengthheader! ”;
  
  return-1;
  
  }
  
  $body=fread($fp,$len);
  
  if($close)
  
  fclose($fp);
  
  return$rcode;
  
  }
  
  $time1=microtime(true);
  
  for($i=0;$i<10000;$i++)
  
  {
  
  $host=”10.69.2.206″;
  
  $port=8080;
  
  $query=”/sms/ns2/save_msg.txt”;
  
  $body=”";
  
  $r=ohttp_get($host,$port,$query,$body);
  
  if($r!=200)
  
  {
  
  echo“returncode:$r ”;
  
  }
  
  }
  
  $time2=microtime(true);
  
  for($i=0;$i<10000;$i++)
  
  {
  
  $url=”http://10.69.2.206:8080/sms/ns2/save_msg.txt”;
  
  $host=”10.69.2.206″;
  
  $port=8080;
  
  $query=”/sms/ns2/save_msg.txt”;
  
  $body=”";
  
  $r=phttp_get($host,$port,$query,$body);
  
  if($r!=200)
  
  {
  
  echo“returncode:$r ”;
  
  }
  
  }
  
  $time3=microtime(true);
  
  for($i=0;$iarray(‘timeout’=>1)
  
  )
  
  );
  
  $body=file_get_contents($url,0,$ctx);
  
  $r=200;
  
  if($r!=200)
  
  {
  
  echo“returncode:$r ”;
  
  }
  
  }
  
  $time4=microtime(true);
  
  echo“phttp_get:“.($time3-$time2).” ”;
  
  echo“ohttp_get:“.($time2-$time1).” ”;
  
  echo“file_get_contents:“.($time4-$time3).” ”;
  
  ?>
  
  
    黑客防线网安服务器维护方案本篇连接:http://www.rongsen.com.cn/show-17538-1.html
网站维护教程更新时间:2012-09-21 05:20:50  【打印此页】  【关闭
我要申请本站N点 | 黑客防线官网 |  
专业服务器维护及网站维护手工安全搭建环境,网站安全加固服务。黑客防线网安服务器维护基地招商进行中!QQ:29769479

footer  footer  footer  footer