首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

PHP 接收二進制流並生成檔案:$GLOBALS['HTTP_RAW_POST_DATA'] 與 php://input 詳解

     編輯:PHP 綜合知識

應用場景

客戶端 (App、IoT 裝置、Webhook) 以原始二進制 POST 送圖片/檔案,非 multipart/form-data,PHP $_POST 無法解析,需讀取 Raw Body。

核心代碼

<?php
/**
 * 將 Raw POST 資料儲存為檔案
 * @param string $file 目標檔案路徑
 * @return bool|int 寫入位元組數或 false
 */
function binary_to_file($file) {
    // 1. 嘗試 $GLOBALS (需 php.ini: always_populate_raw_post_data = On,PHP 5.6+ 棄用)
    $content = $GLOBALS['HTTP_RAW_POST_DATA'] ?? '';

    // 2. 推薦:php://input 流 (不需配置、記憶體效率佳、支援大資料)
    if (empty($content)) {
        $content = file_get_contents('php://input');
    }

    // 3. 寫入檔案
    return file_put_contents($file, $content, LOCK_EX);
}

// 使用範例
binary_to_file('photo/test.png');

兩種讀取方式對比

特性$GLOBALS['HTTP_RAW_POST_DATA']php://input
PHP 版本5.6 棄用,7.0 移除所有版本支援
需配置always_populate_raw_post_data = On無
記憶體完整載入記憶體可流式讀取 (搭配 fopen/fread)
multipart/form-data不支援不支援
建議❌ 棄用✅ 首選

進階:流式處理大檔案

function stream_to_file($file, $chunkSize = 8192) {
    $in = fopen('php://input', 'rb');
    $out = fopen($file, 'wb');
    while (!feof($in)) {
        $data = fread($in, $chunkSize);
        fwrite($out, $data);
    }
    fclose($in); fclose($out);
}

常見坑點

  • Content-Type 錯誤:客戶端需發送 application/octet-stream 或具體 MIME,不可為 multipart/form-data。
  • 重複讀取:php://input 只能讀取一次 (非 seekable),後續再讀將為空。需一次性讀完或暫存。
  • nginx fastcgi_buffering:大請求可能被緩衝至磁碟,導致 php://input 讀取延遲,可關閉 fastcgi_request_buffering off。
  • 安全性:驗證簽名/Token、限制檔案大小 (client_max_body_size)、掃描病毒。

結語

PHP 接收 Raw 二進制流的標準做法是 file_get_contents('php://input') 或流式 fopen('php://input')。棄用 $GLOBALS['HTTP_RAW_POST_DATA'],並注意 multipart/form-data 走 $_FILES 完全不同的處理路徑。掌握此差異,即可正確實現檔案上傳、Webhook 接收、IoT 數據收集等功能。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved