如何透過 https 使用 php 代理程式傳輸 http mjpg
P粉835428659
P粉835428659 2023-09-03 20:54:13
0
2
522
<p>我有這個 php 腳本,它應該透過 HTTP 載入 mjpg 流並透過 HTTPS 輸出。然而,它產生的只是一個破碎的圖像:</p> <pre class="brush:php;toolbar:false;"><?php function proxyMjpegStream($url) { $ch = curl_init($url); curl_setopt($ch, CURLOPT_HEADER, false); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); curl_setopt($ch, CURLOPT_TIMEOUT, 30); curl_setopt($ch, CURLOPT_BUFFERSIZE, 8192); header("Content-Type: multipart/x-mixed-replace; boundary=myboundary"); curl_exec($ch); curl_close($ch); } // Get the URL of the MJPEG stream to proxy if (isset($_GET['url'])) { $mjpegUrl = $_GET['url']; // Validate that the URL is a valid HTTP source if (filter_var($mjpegUrl, FILTER_VALIDATE_URL) && strpos($mjpegUrl, 'http://') === 0) { proxyMjpegStream($mjpegUrl); exit; } } // Invalid or missing MJPEG URL parameter header("HTTP/1.0 400 Bad Request"); echo "Invalid MJPEG URL"; ?></pre></p>
P粉835428659
P粉835428659

全部回覆(2)
P粉588152636

這並不是問題的真正答案,Anas 已經涵蓋了這一點,但無論如何還是值得一提,並且不適合在評論中。

寫這樣的程式碼區塊時會遇到麻煩:

 // Get the URL of the MJPEG stream to proxy
 if (isset($_GET['url'])) {
   $mjpegUrl = $_GET['url'];

   // Validate that the URL is a valid HTTP source
   if (filter_var($mjpegUrl, FILTER_VALIDATE_URL) && strpos($mjpegUrl, 'http://') === 0) {
     proxyMjpegStream($mjpegUrl);
     exit;
   }
 }

  // Invalid or missing MJPEG URL parameter
  header("HTTP/1.0 400 Bad Request");
  echo "Invalid MJPEG URL";

如果您繼續將錯誤條件延後到最後,並將非錯誤條件包含在 if(){} 區塊中,則會遇到兩個問題。

  1. 觸發錯誤的條件與產生錯誤訊息的位置越來越脫節。
  2. 您的「幸福之路」程式碼越來越深地埋藏在嵌套 if(){} 區塊中,稱為 箭頭反模式

您可以重新格式化:

if( good ) {
  if( also good ) {
    do_thing();
    exit();
  } else {
    raise_error('also bad');
  }
}
raise_error('bad');

致:

if( ! good ) {
  raise_error('bad');
}
if( ! also good ) {
  raise_error('also bad');
}
do_thing();

這不是一個一成不變的規則,但牢記它可以幫助避免編寫脫節或混亂的程式碼區塊,或最終延伸到頁面右側的程式碼區塊。

P粉523625080

經過一些研究後,您可以使用以下函數在curl中執行流:

curl_setopt($ch, CURLOPT_WRITEFUNCTION, 'streamCallback');

並建立回呼函數:

function streamCallback($curl, $data) {
    // Process the received data
    echo $data;

    // Return the length of the data processed
    return strlen($data);
}

您的程式碼可以正常運作,但 30 秒後您的串流將結束,因為您設定了 curl_setopt($ch, CURLOPT_TIMEOUT, 30);

#我對流 URL 的建議是使用 fopen() 因為 cURL 主要是為發出 HTTP 請求來取得靜態內容而設計的。 MJPEG 串流是動態的並且不斷傳送新影格。

預設情況下,cURL 為每個請求設定了逾時。如果伺服器發送訊框的時間較長,請求可能會逾時,導致串流中斷或錯誤訊息。

您可以使用fopen()函數以獲得最佳體驗。 這是使用串流和 fopen 的範例。

<?php
$videoUrl = 'http://74.142.49.38:8000/axis-cgi/mjpg/video.cgi';

// Set the appropriate headers for MJPG
header('Content-Type: multipart/x-mixed-replace; boundary=myboundary');

// Continuously fetch and display frames
while (true) {
    // Open a connection to the video stream
    $stream = fopen($videoUrl, 'rb');

    // Check if the stream is valid
    if (!$stream) {
        die('Error opening stream');
    }

    // Read and display each frame
    while ($frame = fread($stream, 4096)) {
        // Display the frame
        echo $frame;

        // Flush the output buffer
        ob_flush();
        flush();
    }

    // Close the stream
    fclose($stream);
}
?>
熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板