标签: php-stream-wrappers

什么是斗式旅?

我真的很想实现一个php_user_filter::filter().但是因此我必须知道斗式旅是什么.这似乎是我可以使用这些stream_bucket_*功能操作的资源.但文档并没有真正的帮助.我能找到的最好的是那些例子stream_filter_register().

我特别好奇这些stream_bucket_new()stream_bucket_make_writeable()能做什么.


更新:似乎PHP暴露了Apache内部数据结构.

php php-stream-wrappers

24
推荐指数
1
解决办法
2329
查看次数

从资源创建流

我知道我可以使用fopen函数从文件名(真实的或URL)创建PHP流:

$stream = fopen('php://temp', 'r');
Run Code Online (Sandbox Code Playgroud)

然后,生成的stream($stream)是从URL创建的"stream"类型的资源.php://temp

但是我如何从资源中创建如上所述的流?


我为什么这么问?

我正在研究PSR-7库,我用类实现了PSR-7 StreamInterfaceStream.为了创建Stream实例,我决定也实现了StreamFactory.其接口StreamFactoryInterfacePSR-17(HTTP工厂)提案中定义.

StreamFactoryInterface定义了一个名为方法createStreamFromResource,其中-符合其官方评论-应该:

从现有资源创建新流.

流必须是可读的并且可以是可写的.

因此工厂方法接收资源作为参数.并且,在其具体实现中,Stream创建了一个新对象 - 它也接收资源作为参数.

这是问题所在:

为简单起见,假设Stream该类仅适用于流,例如使用"stream"类型的资源.如果它收到的资源不属于"stream"类型,则会拒绝它.

那么,如果资源参数createStreamFromResource不是"流"类型的资源呢?如何将其转换为流,例如转换为"stream"类型的资源,以便我可以将其进一步传递给Stream使用它创建新对象的调用?是否有实现此任务的方法(PHP方法,函数或可能的转换函数)?

笔记:

  • 为清楚起见,我准备了一个完整的示例(testStream.php),我Stream用三种方式创建一个流,例如一个实例:一次直接,两次使用流工厂.
  • 我还发布了工厂接口的具体实现:StreamFactory带有方法的类createStreamFromResource.调用此方法应该是我创建流的第四种方法testStream.php.
  • 此外,我目前的课程StreamResponse,这样就可以直接测试所有,如果你想.这两个类是我的真实代码的一个非常简化的版本. …

php fopen stream php-stream-wrappers psr-7

10
推荐指数
1
解决办法
4183
查看次数

php stream_get_contents在流的末尾挂起

问题结束时的解决方案

我正在编写一个PHP应用程序,它将消息发送到服务器,然后在使用时读回响应stream_get_contents.我以相同的方式在Android应用程序中与同一服务器通信.Android应用程序工作正常并快速响应,但是当从服务器读回响应时PHP挂起.

在下面的代码示例中,我设置了一个5字节的微小缓冲区大小来测试理论.如果我删除它的缓冲区大小,它会挂起,但是在5字节大小的情况下,它只会在最后一次循环中挂起:

stream_set_timeout($this->socket, 10); //10 seconds read timeout

while (!feof($this->socket)) {
    $breakOut = false;

    echo 'Reading response'.time().'<br/>';
    $data = stream_get_contents($this->socket, 5);
    echo 'Read response'.time().'<br/>';

    if ($data === false) {
        $this->latestErrStr = "Timed out waiting for a response.";
        return false;
    } else {
        $index = strpos($data, chr(3));

        if ($index !== FALSE){
            $breakOut = true;
            $data = substr($data, 0, $index);
        }

        $response .= $data;
    }

    $stream_meta_data = stream_get_meta_data($this->socket);

    //If we have no EOF marker then break if there are …
Run Code Online (Sandbox Code Playgroud)

php sockets stream php-socket php-stream-wrappers

7
推荐指数
1
解决办法
8267
查看次数

php://输入只能在PHP 5.6.16中读取一次

PHP手册指出使用php://输入支持查找操作打开的流,从PHP 5.6开始可以多次读取,但我无法使其工作.以下示例清楚地显示它不起作用:

<!DOCTYPE html>
<html>
<body>
<form method="post">
<input type="hidden" name="test_name" value="test_value">
<input type="submit">
</form>
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST')
{
    $input = fopen('php://input', 'r');
    echo 'First attempt: ' . fread($input, 1024) . '<br>';
    if (fseek($input, 0) != 0)
        exit('Seek failed');
    echo 'Second attempt: ' . fread($input, 1024) . '<br>';
}
?>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)

输出:

First attempt: test_name=test_value
Second attempt: 
Run Code Online (Sandbox Code Playgroud)

php://输入流是

  1. 成功阅读
  2. 成功回归(fseek成功)
  3. 阅读失败

难道我做错了什么?

php php-stream-wrappers

6
推荐指数
1
解决办法
2136
查看次数

PHP:将 MYSQL 查询写入 CSV

我正在尝试将 MySQLi 查询写入可下载的 CSV。以下标头为 CSV 打开一个流:

$fileName = ''; //empty file name, file name is cast later
header("Cache=Control: must-revalidate, post-check=0, pre-check=0");
header('Content-Description: File Transfer');
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename={$fileName}");
header("Expires: 0");
header("Pragma: public");
$fh = @fopen( 'php://output', 'w' );
Run Code Online (Sandbox Code Playgroud)

在此之下,我有以下尝试查询并将查询的每一行转换为 CSV 文件中的新行:

if(isset($_POST["Submit"]) && ($_POST['Weight'] == 'Weight')){
    $fileName .= 'OutputWeightNull.csv';
    $query = mysqli_query($conn, 'SELECT * FROM  `Some_Table` WHERE WEIGHT = 0 OR weight IS NULL')or die(mysql_error());
    $result = mysqli_fetch_array($query) or die(mysql_error());
    $headerDisplayed = false;
    foreach ($result as $data){
    if (!headerDisplayed){ …
Run Code Online (Sandbox Code Playgroud)

php mysql csv mysqli php-stream-wrappers

5
推荐指数
1
解决办法
694
查看次数

如何使用 PSR-7 响应?

我的应用程序中的大多数响应要么是视图,要么是 JSON。我不知道如何将它们放入ResponseInterfacePSR-7中实现的对象中。

这是我目前所做的:

// Views
header('Content-Type: text/html; charset=utf-8');
header('Content-Language: en-CA');
echo $twig->render('foo.html.twig', array(
    'param' => 'value'
    /* ... */
));

// JSON
header('Content-Type: application/json; charset=utf-8');
echo json_encode($foo);
Run Code Online (Sandbox Code Playgroud)

这是我试图用 PSR-7 做的事情:

// Views
$response = new Http\Response(200, array(
    'Content-Type' => 'text/html; charset=utf-8',
    'Content-Language' => 'en-CA'
));

// what to do here to put the Twig output in the response??

foreach ($response->getHeaders() as $k => $values) {
    foreach ($values as $v) {
        header(sprintf('%s: %s', $k, $v), false);
    } …
Run Code Online (Sandbox Code Playgroud)

php stream httpresponse php-stream-wrappers psr-7

5
推荐指数
1
解决办法
2445
查看次数

如果没有数据传输,PHP流超时

我目前正在实现一个PHP类,它获取图像文件并在本地缓存它们.这些图像可能来自其他本地来源,通过HTTP或使用Guzzle客户端通过HTTP.使用PHP流包装器,我应该能够以相同的方式处理所有源.

如果没有数据通过流传输,我现在要做的就是实现超时.这应该处理以下情况:

  1. 首先无法建立流.这可能应该在fopen通话时处理,而不是超时.
  2. 流已建立,但未传输任何数据.
  3. 建立流,传输数据但在传输过程中停止一段时间.

我想我可以做到这一切,stream_set_timeout但我不太清楚这实际上是做什么的.如果流上的任何操作花费的时间超过允许的时间,那么超时是否适用,即我可以做一些需要0.5秒并且超时为0.75秒的事情?或者仅在没有数据通过流传输的时间超过允许时间时才适用?

我尝试使用这个简短的脚本测试行为:

<?php

$in = fopen('https://reqres.in/api/users?delay=5', 'r');
$out = fopen('out', 'w');

stream_set_timeout($in, 1);
stream_copy_to_stream($in, $out);

var_dump(stream_get_meta_data($in)['timed_out']);
Run Code Online (Sandbox Code Playgroud)

虽然响应时间reqres.in延迟了5秒,但总是会false超时1秒.请有人解释一下吗?

php php-stream-wrappers

4
推荐指数
1
解决办法
722
查看次数

从URL复制的文件将被截断

我在复制文件时遇到问题.我的代码:

$file = "https://www.ilportaleofferte.it/portaleOfferte/resources/opendata/csv/offerteML/2019_1/PO_Offerte_G_MLIBERO_20190130.xml";

$newfile = $_SERVER['DOCUMENT_ROOT'] . '/input/PO_Offerte_G_MLIBERO_20190130.xml';

if(copy($file, $newfile)) {
    echo "salvato<br>";
} else {
    echo "ERROR inport file PO_Offerte_".$data.".".$ext."<br>";
    die;
}
Run Code Online (Sandbox Code Playgroud)

copy() 如果是,则创建文件但文件末尾的某些行丢失...文件为3.6MB,文件末尾的0.3缺失...

如果我手动下载文件一切都很好,所以源完成...

如果我获得文件内容,我实际上有同样的问题file_get_contents(),我尝试使用文件写入功能将其保存在文件中...

我不认为upload_max_filesize并且post_max_size实际参与其中,copy()但它们是20MB设置

任何提示?

谢谢

php copy file php-stream-wrappers

2
推荐指数
1
解决办法
243
查看次数