PHP中的流(streams)浅析

概述

流(streams)是PHP4.3版本引入的一个特性,主要是为了统一文件、sockets以及其他类似资源的工作方法。PHP4.3距今已经有很长时间了,但是很多程序员似乎都不能正确使用PHP中的流,当然这也包括我。以前也在一些程序中遇到过流的使用,如php://input,但是一直没机会整理,今天就把这部分知识整理下。

流是由PHP提供的资源,可以供我们透明的使用,而且流是一个非常强大的工具。适当的在程序中使用流,可以将我们的程序带到一个新的高度。

PHP手册中对流的描述如下:

代码如下:

Streams were introduced with PHP 4.3.0 as a way of generalizing file, network, data compression, and other operations which share a common set of functions and uses. In its simplest definition, a stream is a resource object which exhibits streamable behavior. That is, it can be read from or written to in a linear fashion, and may be able to fseek() to an arbitrary locations within the stream.

每一种流都实现了一个包装器(wrapper),包装器包含一些额外的代码用来处理特殊的协议和编码。PHP提供了一些内置的包装器,我们也可以很轻松的创建和注册自定义的包装器。我们甚至可以使用上下文(contexts)和过滤器来改变和增强包装器。

流基础知识

PHP中流的形式如:<scheme>://<target>。<scheme>是包装器的名字,<target>的内容取决于不同的包装器语法。
默认的包装器是file://,也就是说每次我们访问文件系统的时候都使用了流。例如,我们可以使用如下两种方式来读取文件:readfile('/path/to/somefile.txt')和readfile('file:///path/to/somefile.txt'),使用这两种方式读取文件,可以得到相同的结果。

正如前面所说,PHP提供了一些内置的包装器、协议和过滤器。查看我们的机器上安装了哪些包装器,可以使用如下几个函数:

代码如下:

<?php
    var_dump(stream_get_transports());
    var_dump(stream_get_wrappers());
    var_dump(stream_get_filters());
?>

我本地的环境输出内容如下:

代码如下:

array (size=8)
  0 => string 'tcp' (length=3)
  1 => string 'udp' (length=3)
  2 => string 'unix' (length=4)
  3 => string 'udg' (length=3)
  4 => string 'ssl' (length=3)
  5 => string 'sslv3' (length=5)
  6 => string 'sslv2' (length=5)
  7 => string 'tls' (length=3)
array (size=12)
  0 => string 'https' (length=5)
  1 => string 'ftps' (length=4)
  2 => string 'compress.zlib' (length=13)
  3 => string 'compress.bzip2' (length=14)
  4 => string 'php' (length=3)
  5 => string 'file' (length=4)
  6 => string 'glob' (length=4)
  7 => string 'data' (length=4)
  8 => string 'http' (length=4)
  9 => string 'ftp' (length=3)
  10 => string 'phar' (length=4)
  11 => string 'zip' (length=3)
array (size=12)
  0 => string 'zlib.*' (length=6)
  1 => string 'bzip2.*' (length=7)
  2 => string 'convert.iconv.*' (length=15)
  3 => string 'string.rot13' (length=12)
  4 => string 'string.toupper' (length=14)
  5 => string 'string.tolower' (length=14)
  6 => string 'string.strip_tags' (length=17)
  7 => string 'convert.*' (length=9)
  8 => string 'consumed' (length=8)
  9 => string 'dechunk' (length=7)
  10 => string 'mcrypt.*' (length=8)
  11 => string 'mdecrypt.*' (length=10)

另外,我们可以自定义或者使用第三方的流。

php://包装器

PHP有它自己的访问输入/输出(I/O)流的包装器。PHP有基本的php://stdin,php://stdout,php://stderr包装器对应默认的I/O资源。还有一个php://input流,它是一个只读的流,流内容是post请求的数据。当我们将数据放在一个post请求的body体内用来请求一个远程服务的时候,这个流特别好用。

因为php://input是最常用到的流,所以这里列出一些知识点:

代码如下:

1.php://input可以读取没有处理过的POST数据。相较于$HTTP_RAW_POST_DATA而言,它给内存带来的压力较小,并且不需要特殊的php.ini设置。php://input不能用于enctype=multipart/form-data
2.仅当Content-Type为application/x-www-form-urlencoded且提交方法是POST方法时,$_POST数据与php://input数据才是”一致”(打上引号,表示它们格式不一致,内容一致)的。其它情况,它们都不一致
3.php://input读取不到GET数据。是因为_GET数据作为query_path写在http请求头部(header)的PATH字段,而不是写在http请求的body部分。

流上下文(Stream Contexts)

这部分内容在编程中几乎没有遇到过,本人研究起来也比较吃力,大家感兴趣的话可以自行百度。

总结

流在平时的编程中用到的并不是很多,在使用xml-rpc的时候,server端获取client数据,主要是通过php输入流input,这是一种常用的场景。黑客在入侵网站的时候,也可能会用到这部分内容。

(0)

相关推荐

  • 深入理解PHP中的Streams工具

    Streams 是PHP提供的一个强有力的工具,我们常常在不经意会使用到它,如果善加利用将大大提高PHP的生产力. 驾驭Streams的强大力量后,应用程序将提升到一个新的高度. 下面是PHP手册中对Streams的一段描述: Streams 是在PHP 4.3.0版本被引入的,它被用于统一文件.网络.数据压缩等类文件的操作方式,为这些类文件操作提供了一组通用的函数接口.简而言之,一个stream就是一个具有流式行为的资源对象.也就是说,我们可以用线性的方式来对stream进行读取和写入.并且可

  • PHP中的Streams详细介绍

    Streams 是PHP提供的一个强有力的工具,我们常常在不经意会使用到它,如果善加利用将大大提高PHP的生产力. 驾驭Streams的强大力量后,应用程序将提升到一个新的高度. 下面是PHP手册中对Streams的一段描述: 复制代码 代码如下: Streams 是在PHP 4.3.0版本被引入的,它被用于统一文件.网络.数据压缩等类文件的操作方式,为这些类文件操作提供了一组通用的函数接口.简而言之,一个stream就是一个具有流式行为的资源对象.也就是说,我们可以用线性的方式来对stream

  • Python读写Excel文件的实例

    最近由于经常要用到Excel,需要根据Excel表格中的内容对一些apk进行处理,手动处理很麻烦,于是决定写脚本来处理.首先贴出网上找来的读写Excel的脚本. 1.读取Excel(需要安装xlrd): #-*- coding: utf8 -*- import xlrd fname = "reflect.xls" bk = xlrd.open_workbook(fname) shxrange = range(bk.nsheets) try: sh = bk.sheet_by_name(

  • java 读写文件[多种方法]

    java中多种方式读文件 一.多种方式读文件内容. 1.按字节读取文件内容 2.按字符读取文件内容 3.按行读取文件内容 4.随机读取文件内容 */ import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.FileReader; import java.io.IOException; import java.io.InputStream; import j

  • Node.js Streams文件读写操作详解

    Node.js 天生异步和事件驱动,非常适合处理 I/O 相关的任务.如果你在处理应用中 I/O 相关的操作,你可以利用 Node.js 中的流(stream).因此,我们先具体看看流,理解一下它们是怎么简化 I/O 操作的吧. 流是什么 流是 unix 管道,让你可以很容易地从数据源读取数据,然后流向另一个目的地. 简单来说,流不是什么特别的东西,它只是一个实现了一些方法的 EventEmitter .根据它实现的方法,流可以变成可读流(Readable),可写流(Writable),或者双向

  • Python open读写文件实现脚本

    1.open 使用open打开文件后一定要记得调用文件对象的close()方法.比如可以用try/finally语句来确保最后能关闭文件. file_object = open('thefile.txt') try: all_the_text = file_object.read( ) finally: file_object.close( ) 注:不能把open语句放在try块里,因为当打开文件出现异常时,文件对象file_object无法执行close()方法. 2.读文件 读文本文件 in

  • js读写json文件实例代码

    本节为大家介绍下js如何读写json文件,代码很简练 function funSave() { var id = $('#testText1')[0].value; var name = $('#testText2')[0].value; var str = '{mydata:[' + '{id:' + id + ',name:' + name + '}' + ']}'; str = "{MyData:[{id:'" + id + "',name:'" + name

  • PHP Streams(流)详细介绍及使用

    PHP Streams是内置核心操作,可能一般的开发者很少用,它用于统一文件.网络.数据压缩等类文件操作方式,并为这些类文件操作提供一组通用的函数接口. 一个stream就是一个具有流式行为的资源对象,每个stream对象都有一个包装类.Stream 可以通过<scheme>://<target>方式来引用.其中<scheme>是包装类的名字,<target>中的内容是由包装类的语法指定,不同的包装类的语法会有所不同. 来看看PHP 默认有哪些内置的包装类:

  • Json读写本地文件实现代码

    复制代码 代码如下: import java.io.*; /** * Created by tang on 14-3-1. */public class JsonUtils { //从给定位置读取Json文件    public static String readJson(String path){        //从给定位置获取文件        File file = new File(path);        BufferedReader reader = null;       

  • jscript读写二进制文件的方法

    本文实例讲述了jscript读写二进制文件的方法.分享给大家供大家参考.具体实现方法如下: var bin = new Array(256); for(var i=0;i<256;i++){ bin[i]=String.fromCharCode(i); } function TestWrite(){ var Stream = new ActiveXObject("ADODB.Stream"); var adTypeBinary=1,adTypeText=2; Stream.Typ

随机推荐