1 回答

TA貢獻2065條經(jīng)驗 獲得超14個贊
當您單擊一個鏈接時,它會在您的瀏覽器中導(dǎo)航,除非您在服務(wù)器上設(shè)置了 URL 重寫,否則將加載該 URL 上的任何內(nèi)容。您需要使用 GET(查詢)參數(shù)將您選擇的目錄傳遞給您的 PHP 文件,并在顯示錨點時使用它。
我對下面的代碼有一些自由,但我相信它可以滿足您的需求。腳本的名稱是從從任何查詢參數(shù)中剝離的當前 URL 中讀取的,并且dir查詢參數(shù)用于將文件夾名稱傳遞給錨點中的腳本。將這些結(jié)合起來,URL 看起來像這樣,具體取決于您如何運行它:
/folder/script.php?dir=foldername%2Ffolder2
請注意,該值是 URL 編碼的,這通常是一種很好的做法,每當您將任意字符串作為查詢參數(shù)傳遞時。在下面的代碼中,文件名輸出也包含在htmlspecialchars()其中轉(zhuǎn)義瀏覽器可能識別為標記并嘗試解析的任何 HTML 字符,從而導(dǎo)致頁面分崩離析。
為了增加安全性,我調(diào)用了在運行時ini_set將open_basedir設(shè)置更改為當前目錄的調(diào)用,以避免目錄遍歷攻擊,例如?dir=../../../../etc/passwd可用于訪問敏感系統(tǒng)信息的攻擊。雖然不是您最初的要求,但我相信這也應(yīng)該在您的情況下處理,我強烈建議保留此安全措施。
此外,還對點文件(.和..)進行了一些處理,以確保未列出當前目錄,并且您無法從基本目錄向上導(dǎo)航。
我還使用HEREDOC使代碼比多次調(diào)用print. 隨之而來的唯一小不便是您不能在字符串中放入太復(fù)雜的表達式,因此您必須將它們移動到上面的變量中,但我相信這也有助于提高可讀性。
<?php
// Credit to http://jeffreysambells.com/2012/10/25/human-readable-filesize-php
function human_file_size($bytes, $decimals = 2) {
$size = array('B', 'KB', 'MB', 'GB');
$factor = (int)floor((strlen($bytes) - 1) / 3);
return round($bytes / pow(1024, $factor), 2).' '.@$size[$factor];
}
function dirlist() {
// Prevent malicious users from reading files in directories above
ini_set('open_basedir', __DIR__);
$baseDirectory = '.'.DIRECTORY_SEPARATOR;
// Get directory from query parameter
$directoryPath = $baseDirectory.(!empty($_GET['dir']) ? rtrim($_GET['dir'], '\\/').DIRECTORY_SEPARATOR : '');
$myDirectory = opendir($directoryPath);
$isTopLevel = $directoryPath === $baseDirectory;
while ($entry = readdir($myDirectory)){
if ($entry === '.' || ($isTopLevel && $entry === '..')){
continue;
}
$dirListArray[] = $entry;
}
$fileCount = count($dirListArray);
sort($dirListArray);
print <<<HTML
<p class="heading">$fileCount FILES / FOLDER FOUND</p>
<table width="100%" border="1" cellpadding="5" cellspacing="0" class="whitelinks">
<tr>
<th>FILE/FOLDER NAME</th>
<th>FILE TYPE</th>
<th>FILE SIZE</th>
</tr>
HTML;
// Get current URL without query parameters
// Trim everything after and including "?"
$scriptPath = strtok($_SERVER['REQUEST_URI'], '?');
foreach ($dirListArray as $indexValue){
$htmlEncodedIndex = htmlspecialchars($indexValue);
$fileType = filetype($directoryPath.$indexValue);
$fileSize = human_file_size(filesize($directoryPath.$indexValue));
if ($fileType === 'dir'){
if ($indexValue === '..'){
// Link to top level, no rectory separator in string
if (strpos($indexValue, DIRECTORY_SEPARATOR) === false)
$queryParam = '';
// Link to subdirectory
else {
$parts = explode(DIRECTORY_SEPARATOR, $indexValue);
array_pop($parts);
// Assemble query param (make sure to URL encode!)
$queryParam = '?dir='.urlencode(implode(DIRECTORY_SEPARATOR, $parts));
}
}
// Assemble query param (make sure to URL encode!)
else $queryParam = '?dir='.urlencode($indexValue);
$href = $scriptPath.$queryParam;
}
else $href = $directoryPath.$indexValue;
print <<<HTML
<tr>
<td>
<a href='$href'>$htmlEncodedIndex</a>
</td>
<td>$fileType</td>
<td>$fileSize</td>
</tr>
HTML;
}
print '</table>';
}
?>
<!DOCTYPE html>
<html>
<head>
<style type="text/css">
.heading {
color: #CCC;
padding: 0;
margin: 5px;
}
#directory-list-container {
margin: 7px;
padding: 0;
border: 3px solid #000;
outline: 1px solid #666;
}
#directory-list-content {
margin: 0;
padding: 5px;
border: 2px solid #666;
}
#directory-list-content a,
#directory-list-container a:link {
color: #00f;
text-decoration: none !important;
}
#directory-list-container a:hover {
color: #0F0;
}
#directory-list-container a:active {
color: #090;
}
#directory-list-container a:visited {
color: #DDD;
}
</style>
</head>
<body>
<div id="directory-list-container">
<div id="directory-list-content">
<?php dirlist(); ?>
</div>
</div>
</body>
</html>
- 1 回答
- 0 關(guān)注
- 202 瀏覽
添加回答
舉報