127.0.0.1/a.phpset_time_limit(0);while (true) { file_put_contents('./a', "data\r\n", FILE_APPEND); sleep(1);}
我關閉瀏覽器後為什麼發現a檔案還在寫啊,我刪了a檔案還是會繼續產生,不是說關閉串連後PHP預設終止指令碼嗎?
回複內容:
127.0.0.1/a.phpset_time_limit(0);while (true) { file_put_contents('./a', "data\r\n", FILE_APPEND); sleep(1);}
我關閉瀏覽器後為什麼發現a檔案還在寫啊,我刪了a檔案還是會繼續產生,不是說關閉串連後PHP預設終止指令碼嗎?
但是前提是你對ignore_user_abort()
函數是否設定為false
,如果為true
,那麼當使用者關閉瀏覽器後,php頁面還會繼續執行!同時發現你對版面設定了set_time_limit(0),
就是說指令碼不會逾時!只要調整ignore_user_abort()
就好了
瀏覽器發起請求,然後伺服器開始執行,一直執行到伺服器腳步運行完畢或者出現異常或者TIMEOUT。瀏覽器沒法關閉伺服器的運行。
但是……
技術總是不挺發展,RFC HTTP 1.1 定義了 Connection 回應標頭,具體的可以參考 PHP的串連處理。
http的無狀態協議 這個是曆史遺留問題,現在的 HTTP 版本也正在解決這個問題,比如上面提到的長連結。定義在 RFC2616(HTTP 1.1)的 Connection。
https://segmentfault.com/q/1010000000627...
是使用 nginx + php
還是apache + php
,還是其他 webserver + php
nginx + php
,嚴格的說是 phpfpm + php
的確會出現這個情況
PHP在發送資訊給用戶端時,才能檢測串連是否已經中斷.
http://php.net/manual/zh/function.ignore...
php.ini中ignore_user_abort預設是Off,不忽略使用者的中斷,也就是用戶端中斷連線後,指令碼將被中止.
在PHP嘗試發送資訊到用戶端之前,不會檢測到使用者是否已中止串連.
僅使用echo語句不能確保資訊已發送,參見flush()函數.
info.php
測試:
time curl http://127.0.0.1/info.php
Ctrl+C插斷要求(PHP-FPM)最後還是產生了檔案info.txt.
因為該請求沒有輸出,PHP無法檢測使用者是否已中止串連.
PHP在發送資訊給瀏覽器時,才能檢測串連是否已經中斷.
比如執行這段代碼,在5秒內插斷要求,將不會組建檔案info.txt:
for($i=0;$i<5;$i++) { echo $i; ob_flush(); flush(); sleep(1);}file_put_contents('/tmp/info.txt', $i);