說我想知道傳遞給fopen的字符串是表示文件路徑還是有效包裝(例如"/home/user/example.txt"
vs "php://input"
)。這是爲了創建一個從php://input
中的內容創建一個tmp文件,以解決PHP wrappers的fseek
ing限制。如何確定一個字符串是否指向PHP中的有效文件或包裝?
如下圖所示,file_exists
作品的文件,但不能用於包裝的URI:
var_dump(file_exists("php://input"));
var_dump(file_exists("./exists.txt"));
var_dump(file_exists("./non_existent.txt"));
var_dump(file_exists("php://garbage"));
給
bool(false)
bool(true)
bool(false)
bool(false)
只有一個返回true是文件。我發現stream_get_wrappers(),但我想避免太複雜的檢查(如使用字符串比較來嘗試檢測包裝)。
使用stream_get_meta_data似乎也起作用,但它需要首先調用fopen,這會阻塞錯誤日誌。
var_dump(stream_get_meta_data(fopen("php://input","r+")));
var_dump(stream_get_meta_data(fopen("./exists.txt","r+")));
var_dump(stream_get_meta_data(fopen("./non_existent.txt","r+")));
var_dump(stream_get_meta_data(fopen("php://garbage","r+")));
產生
array(9) {
["timed_out"]=>
bool(false)
["blocked"]=>
bool(true)
["eof"]=>
bool(false)
["wrapper_type"]=>
string(3) "PHP"
["stream_type"]=>
string(5) "Input"
["mode"]=>
string(2) "rb"
["unread_bytes"]=>
int(0)
["seekable"]=>
bool(true)
["uri"]=>
string(11) "php://input"
}
array(9) {
["timed_out"]=>
bool(false)
["blocked"]=>
bool(true)
["eof"]=>
bool(false)
["wrapper_type"]=>
string(9) "plainfile"
["stream_type"]=>
string(5) "STDIO"
["mode"]=>
string(2) "r+"
["unread_bytes"]=>
int(0)
["seekable"]=>
bool(true)
["uri"]=>
string(10) "./exists.txt"
}
NULL
NULL
我可以使用由stream_get_meta_data
返回的數組的wrapper_type
,但它仍然會噴涌到垃圾如果日誌文件或包裝URI不存在,我想避免。
什麼是最好的方法來檢測是否我的輸入字符串(要傳遞給fopen)包含了現有文件或有效的PHP包裝,或既無一個有效的文件路徑?
更新:我找到了解決問題的解決方法,其代價是額外的fopen
調用。我已經在下面回答了這個問題。
似乎並沒有成爲一個東西,至少不是在PHP 7.0,也不是官方文檔: 'PHP -R '的var_dump(function_exists( 「is_stream」));'' '布爾(假) ' –
感謝downvote沒有任何解釋:(先前的研究有多少證據需要顯示在這裏? –