分析php://output和php://stdout的区别


Posted in PHP onMay 06, 2018

PHP包含了以php://开头的一系列输出输出流,如php://stdin, php://stdout等。今天查看代码时,忽然想到一个问题:php://output和php://stdout有什么区别?

从PHP的官方文献中找答案,对输入流php://stdin和php://input的解释分别如下(输出流的解释过于简略):

php://stdin

php://stdin, php://stdout and php://stderr allow direct access to the corresponding input or output stream of the PHP process. The stream references a duplicate file descriptor, so if you open php://stdin and later close it, you close only your copy of the descriptor-the actual stream referenced by STDIN is unaffected. Note that PHP exhibited buggy behavior in this regard until PHP 5.2.1. It is recommended that you simply use the constants STDIN, STDOUT and STDERR instead of manually opening streams using these wrappers.

php://stdin is read-only, whereas php://stdout and php://stderr are write-only.

php://input

php://input is a read-only stream that allows you to read raw data from the request body. In the case of POST requests, it is preferable to use php://input instead of $HTTP_RAW_POST_DATA as it does not depend on special php.ini directives. Moreover, for those cases where $HTTP_RAW_POST_DATA is not populated by default, it is a potentially less memory intensive alternative to activating always_populate_raw_post_data. php://input is not available with enctype=”multipart/form-data”.

文档并未直接阐述两者的区别,仔细对比可得出以下信息:1. 均是只读流; 2. php://stdin是PHP进程的标准输入,php://input用来读取请求正文的原始数据。通过这些信息,该如何正确认识两者的本质区别?

顺着php://stdin进程输入的提示,联想PHP进程的执行过程,再结合SAPI的差异,可以得到两者主要区别:php://stdin是PHP进程的输入流,执行生命周期内均可能有数据流入(例如CLI下的交互式输入);php://input是PHP执行时的外部输入流,一般数据只能读一次(具体看SAPI的实现)。同理可得到php://stdout和php://output的区别:php://stdout是PHP进程的标准输出流,php://output是返回的结果数据流。

下面用代码验证结论:

// file: test.php
file_put_contents("php://output", "message sent by output" . PHP_EOL);
file_put_contents("php://stdout", "message sent by stdout" . PHP_EOL);
print("message sent by print" . PHP_EOL);
 
echo "SAPI:" , PHP_SAPI , PHP_EOL;

命令行执行文件,输出如下:

message sent by output
message sent by stdout
message sent by print
SAPI:cli

浏览器端请求,输出如下:

message sent by output
message sent by print
SAPI:fpm-fcgi

在命令行下,PHP进程的标准输出流和结果输出流均指向终端,所有消息都打印出来。在浏览器端,PHP进程的输出流被忽略,只有结果数据流被发送到web服务器。同时,print和echo调用的信息都作为执行结果发往结果输出流,所以都正常显示。

最后再感慨一下PHP内置函数的简洁实用,一个file_put_contents函数就搞定流写入操作,换Java需要stream/writer一堆代码,也省去C风格的fopen/fwrite/fclose的繁琐。

PHP 相关文章推荐
DOMXML函数笔记
Oct 09 PHP
基于mysql的bbs设计(五)
Oct 09 PHP
php ftp文件上传函数(基础版)
Jun 03 PHP
PHP array操作10个小技巧分享
Jun 23 PHP
PHP基础知识回顾
Aug 16 PHP
解析php中的escape函数
Jun 29 PHP
PHP常用的小程序代码段
Nov 14 PHP
PHP多维数组转一维数组的简单实现方法
Dec 23 PHP
轻松实现php文件上传功能
Feb 17 PHP
PHP PDOStatement::rowCount讲解
Feb 01 PHP
通过PHP设置BugFree获取邮箱通知
Apr 25 PHP
PHP封装类似thinkphp连贯操作数据库Db类与简单应用示例
May 08 PHP
PHP 布尔值的自增与自减的实现方法
May 03 #PHP
PHPExcel 修改已存在Excel的方法
May 03 #PHP
PHP中PDO事务处理操作示例
May 02 #PHP
PHP简单实现解析xml为数组的方法
May 02 #PHP
PHP实现动态压缩js与css文件的方法
May 02 #PHP
Yii2框架数据验证操作实例详解
May 02 #PHP
Yii2框架类自动加载机制实例分析
May 02 #PHP
You might like
用PHP编程语言开发动态WAP页面
2006/10/09 PHP
PHP中防止直接访问或查看或下载config.php文件的方法
2012/07/07 PHP
解析dedecms空间迁移步骤详解
2013/05/15 PHP
laravel 实现划分admin和home 模块分组
2019/10/15 PHP
js字符串日期yyyy-MM-dd转化为date示例代码
2014/03/06 Javascript
JS实现的网页倒计时数字时钟效果
2015/03/02 Javascript
谈谈javascript中使用连等赋值操作带来的问题
2015/11/26 Javascript
js判断主流浏览器类型和版本号的简单实现代码
2016/05/26 Javascript
BootStrap中Datepicker控件带中文的js文件
2016/08/10 Javascript
jQuery实现鼠标经过时高亮,同时其他同级元素变暗的效果
2016/09/18 Javascript
BootStrap3中模态对话框的使用
2017/01/06 Javascript
JS实现关键词高亮显示正则匹配
2018/06/22 Javascript
微信小程序项目实践之验证码倒计时功能
2018/07/18 Javascript
nodejs之koa2请求示例(GET,POST)
2018/08/07 NodeJs
Angular使用cli生成自定义文件、组件的方法
2018/09/04 Javascript
Vue 处理表单input单行文本框的实例代码
2019/05/09 Javascript
node.js实现简单的压缩/解压缩功能示例
2019/11/05 Javascript
JS错误处理与调试操作实例分析
2020/04/13 Javascript
详解vue路由
2020/08/05 Javascript
python基础教程之缩进介绍
2014/08/29 Python
Python入门篇之正则表达式
2014/10/20 Python
对Python通过pypyodbc访问Access数据库的方法详解
2018/10/27 Python
Python中numpy模块常见用法demo实例小结
2019/03/16 Python
总结Python图形用户界面和游戏开发知识点
2019/05/22 Python
django中间键重定向实例方法
2019/11/10 Python
PyTorch加载预训练模型实例(pretrained)
2020/01/17 Python
Python3爬虫中Ajax的用法
2020/07/10 Python
Python过滤序列元素的方法
2020/07/31 Python
python matplotlib库的基本使用
2020/09/23 Python
俄罗斯天然和有机产品、健康生活网上商店:Fitomarket.ru
2020/10/09 全球购物
C#中类(class)与结构(struct)的异同
2013/11/03 面试题
《学会待客》教学反思
2014/02/22 职场文书
自强自立美德少年事迹材料
2014/08/16 职场文书
灵山大佛导游词
2015/02/04 职场文书
班主任培训研修日志
2015/11/13 职场文书
vue中三级导航的菜单权限控制
2021/03/31 Vue.js