web-dev-qa-db-fra.com

Répertoriez tous les fichiers et dossiers d’un répertoire avec PHP fonction récursive

J'essaie de parcourir tous les fichiers d'un répertoire, et s'il y en a un, parcourez tous ses fichiers, etc. jusqu'à ce qu'il n'y ait plus de répertoires. Chaque élément traité sera ajouté à un tableau de résultats dans la fonction ci-dessous. Cela ne fonctionne pas bien que je ne sois pas sûr de ce que je peux faire/ce que j'ai mal fait, mais le navigateur est incroyablement lent lorsque ce code ci-dessous est traité, toute aide est la bienvenue, merci!

Code:

    function getDirContents($dir){
        $results = array();
        $files = scandir($dir);

            foreach($files as $key => $value){
                if(!is_dir($dir. DIRECTORY_SEPARATOR .$value)){
                    $results[] = $value;
                } else if(is_dir($dir. DIRECTORY_SEPARATOR .$value)) {
                    $results[] = $value;
                    getDirContents($dir. DIRECTORY_SEPARATOR .$value);
                }
            }
    }

    print_r(getDirContents('/xampp/htdocs/WORK'));
54
user3412869

Obtenez tous les fichiers et dossiers d’un répertoire, n’appelez pas function quand vous avez . ou ...

Votre code :

<?php
function getDirContents($dir, &$results = array()){
    $files = scandir($dir);

    foreach($files as $key => $value){
        $path = realpath($dir.DIRECTORY_SEPARATOR.$value);
        if(!is_dir($path)) {
            $results[] = $path;
        } else if($value != "." && $value != "..") {
            getDirContents($path, $results);
            $results[] = $path;
        }
    }

    return $results;
}

var_dump(getDirContents('/xampp/htdocs/WORK'));

Sortie (exemple):

array (size=12)
  0 => string '/xampp/htdocs/WORK/iframe.html' (length=30)
  1 => string '/xampp/htdocs/WORK/index.html' (length=29)
  2 => string '/xampp/htdocs/WORK/js' (length=21)
  3 => string '/xampp/htdocs/WORK/js/btwn.js' (length=29)
  4 => string '/xampp/htdocs/WORK/js/qunit' (length=27)
  5 => string '/xampp/htdocs/WORK/js/qunit/qunit.css' (length=37)
  6 => string '/xampp/htdocs/WORK/js/qunit/qunit.js' (length=36)
  7 => string '/xampp/htdocs/WORK/js/unit-test.js' (length=34)
  8 => string '/xampp/htdocs/WORK/xxxxx.js' (length=30)
  9 => string '/xampp/htdocs/WORK/plane.png' (length=28)
  10 => string '/xampp/htdocs/WORK/qunit.html' (length=29)
  11 => string '/xampp/htdocs/WORK/styles.less' (length=30)
99
A-312
$rii = new RecursiveIteratorIterator(new RecursiveDirectoryIterator('path/to/folder'));

$files = array(); 

foreach ($rii as $file) {

    if ($file->isDir()){ 
        continue;
    }

    $files[] = $file->getPathname(); 

}



var_dump($files);

Cela vous apportera tous les fichiers avec des chemins.

74
zkanoca

C'est la version plus courte:

function getDirContents($path) {
    $rii = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($path));

    $files = array(); 
    foreach ($rii as $file)
        if (!$file->isDir())
            $files[] = $file->getPathname();

    return $files;
}

var_dump(getDirContents($path));
19
A-312

Obtenez tous les fichiers avec filter (2nd argument) et les dossiers d'un répertoire, n'appelez pas function lorsque vous avez . ou ...

Votre code :

<?php
function getDirContents($dir, $filter = '', &$results = array()) {
    $files = scandir($dir);

    foreach($files as $key => $value){
        $path = realpath($dir.DIRECTORY_SEPARATOR.$value); 

        if(!is_dir($path)) {
            if(empty($filter) || preg_match($filter, $path)) $results[] = $path;
        } elseif($value != "." && $value != "..") {
            getDirContents($path, $filter, $results);
        }
    }

    return $results;
} 

// Simple Call: List all files
var_dump(getDirContents('/xampp/htdocs/WORK'));

// Regex Call: List php files only
var_dump(getDirContents('/xampp/htdocs/WORK', '/\.php$/'));

Sortie (exemple):

// Simple Call
array(13) {
  [0]=> string(69) "/xampp/htdocs/WORK.htaccess"
  [1]=> string(73) "/xampp/htdocs/WORKConverter.php"
  [2]=> string(69) "/xampp/htdocs/WORKEvent.php"
  [3]=> string(70) "/xampp/htdocs/WORKdefault_filter.json"
  [4]=> string(68) "/xampp/htdocs/WORKdefault_filter.xml"
  [5]=> string(80) "/xampp/htdocs/WORKCaching/ApcCache.php"
  [6]=> string(84) "/xampp/htdocs/WORKCaching/CacheFactory.php"
}

// Regex Call
array(13) {
  [0]=> string(69) "/xampp/htdocs/WORKEvent.php"
  [1]=> string(73) "/xampp/htdocs/WORKConverter.php"
  [2]=> string(80) "/xampp/htdocs/WORKCaching/ApcCache.php"
  [3]=> string(84) "/xampp/htdocs/WORKCaching/CacheFactory.php"
}

_ {Proposition de James Cameron.} _

7
A-312

Ma proposition sans laide "foreach" structures de contrôle est

$iterator = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($path));
$allFiles = array_filter(iterator_to_array($iterator), function($file) {
    return $file->isFile();
});

Vous voudrez peut-être seulement extraire le chemin du fichier, ce que vous pouvez faire en:

array_keys($allFiles);

Toujours 4 lignes de code, mais plus simple que d'utiliser une boucle ou quelque chose.

3
patriziotomato

Cette solution a fait le travail pour moi. RecursiveIteratorIterator répertorie tous les répertoires et fichiers de manière récursive, mais non triée. Le programme filtre la liste et la trie.

Je suis sûr qu'il existe un moyen d'écrire ceci plus court; n'hésitez pas à l'améliorer ... C'est juste un extrait de code. Vous voudrez peut-être le personnaliser à vos fins.

<?php

$path = '/pth/to/your/directories/and/files';
// an unsorted array of dirs & files
$files_dirs = iterator_to_array( new RecursiveIteratorIterator(new RecursiveDirectoryIterator($path),RecursiveIteratorIterator::SELF_FIRST) );

echo '<html><body><pre>';
// create a new associative multi-dimensional array with dirs as keys and their files
$dirs_files = array();
foreach($files_dirs as $dir){
 if(is_dir($dir) AND preg_match('/\/\.$/',$dir)){
  $d = preg_replace('/\/\.$/','',$dir);
  $dirs_files[$d] = array();
  foreach($files_dirs as $file){
   if(is_file($file) AND $d == dirname($file)){
    $f = basename($file);
    $dirs_files[$d][] = $f;
   }
  }
 }
}
//print_r($dirs_files);

// sort dirs
ksort($dirs_files);

foreach($dirs_files as $dir => $files){
 $c = substr_count($dir,'/');
 echo  str_pad(' ',$c,' ', STR_PAD_LEFT)."$dir\n";
 // sort files
 asort($files);
 foreach($files as $file){
  echo str_pad(' ',$c,' ', STR_PAD_LEFT)."|_$file\n";
 }
}
echo '</pre></body></html>';

?>
2
chrinux

Voici ce que je suis venu avec et c'est avec pas beaucoup de lignes de code

function show_files($start) {
    $contents = scandir($start);
    array_splice($contents, 0,2);
    echo "<ul>";
    foreach ( $contents as $item ) {
        if ( is_dir("$start/$item") && (substr($item, 0,1) != '.') ) {
            echo "<li>$item</li>";
            show_files("$start/$item");
        } else {
            echo "<li>$item</li>";
        }
    }
    echo "</ul>";
}

show_files('./');

Il sort quelque chose comme

..idea
.add.php
.add_task.php
.helpers
 .countries.php
.mysqli_connect.php
.sort.php
.test.js
.test.php
.view_tasks.php

** Les points sont les points de la liste non ordonnée.

J'espère que cela t'aides.

1
Koushik Das

C'est une petite modification de la réponse de majick s.
Je viens de changer la structure de tableau retournée par la fonction.

De:

array() => {
    [0] => "test/test.txt"
}

À:

array() => {
    'test/test.txt' => "test.txt"
}

/**
 * @param string $dir
 * @param bool   $recursive
 * @param string $basedir
 *
 * @return array
 */
function getFileListAsArray(string $dir, bool $recursive = true, string $basedir = ''): array {
    if ($dir == '') {
        return array();
    } else {
        $results = array();
        $subresults = array();
    }
    if (!is_dir($dir)) {
        $dir = dirname($dir);
    } // so a files path can be sent
    if ($basedir == '') {
        $basedir = realpath($dir) . DIRECTORY_SEPARATOR;
    }

    $files = scandir($dir);
    foreach ($files as $key => $value) {
        if (($value != '.') && ($value != '..')) {
            $path = realpath($dir . DIRECTORY_SEPARATOR . $value);
            if (is_dir($path)) { // do not combine with the next line or..
                if ($recursive) { // ..non-recursive list will include subdirs
                    $subdirresults = self::getFileListAsArray($path, $recursive, $basedir);
                    $results = array_merge($results, $subdirresults);
                }
            } else { // strip basedir and add to subarray to separate file list
                $subresults[str_replace($basedir, '', $path)] = $value;
            }
        }
    }
    // merge the subarray to give the list of files then subdirectory files
    if (count($subresults) > 0) {
        $results = array_merge($subresults, $results);
    }
    return $results;
}

Cela pourrait aider ceux qui ont exactement les mêmes résultats que moi.

1
Max

Cela affichera le chemin complet de tous les fichiers du répertoire indiqué. Vous pouvez également transmettre d’autres fonctions de rappel à recursiveDir.

function printFunc($path){
    echo $path."<br>";
}

function recursiveDir($path, $fileFunc, $dirFunc){
    $openDir = opendir($path);
    while (($file = readdir($openDir)) !== false) {
        $fullFilePath = realpath("$path/$file");
        if ($file[0] != ".") {
            if (is_file($fullFilePath)){
                if (is_callable($fileFunc)){
                    $fileFunc($fullFilePath);
                }
            } else {
                if (is_callable($dirFunc)){
                    $dirFunc($fullFilePath);
                }
                recursiveDir($fullFilePath, $fileFunc, $dirFunc);
            }
        }
    }
}

recursiveDir($dirToScan, 'printFunc', 'printFunc');
1
Tom Chan

Voici le mien : 

function recScan( $mainDir, $allData = array() ) 
{ 
// hide files 
$hidefiles = array( 
".", 
"..", 
".htaccess", 
".htpasswd", 
"index.php", 
"php.ini", 
"error_log" ) ; 

//start reading directory 
$dirContent = scandir( $mainDir ) ; 

foreach ( $dirContent as $key => $content ) 
{ 
$path = $mainDir . '/' . $content ; 

// if is readable / file 
if ( ! in_array( $content, $hidefiles ) ) 
{ 
if ( is_file( $path ) && is_readable( $path ) ) 
{ 
$allData[] = $path ; 
} 

// if is readable / directory 
// Beware ! recursive scan eats ressources ! 
else 
if ( is_dir( $path ) && is_readable( $path ) ) 
{ 
/*recursive*/ 
$allData = recScan( $path, $allData ) ; 
} 
} 
} 

return $allData ; 
}  
0
Alin Razvan

J'ai amélioré, avec une seule vérification, le bon code de Hors Sujet afin d'éviter d'inclure des dossiers dans le tableau de résultats:

 function getDirContents ($ dir, & $ results = array ()) {

 $ fichiers = scandir ($ dir); 

 foreach ($ fichiers en tant que $ key => $ value) {
 $ path = realpath ($ dir.DIRECTORY_SEPARATOR. $ value); 
 if (is_dir ($ path) == false) {
 $ résultats [] = $ chemin; 
 } 
 else if ($ value! = "." && $ value! = "..") {
 getDirContents ($ path, $ results); 
 if (is_dir ($ path) == false) {
 $ résultats [] = $ chemin; 
 } 
 } 
 } 
 retourne $ résultats; 

} 
0
Roman

Pour qui a besoin de fichiers de liste en premier lieu que les dossiers (avec alphabétique plus ancien).

Peut utiliser la fonction suivante . Ce n'est pas une fonction auto-appelante. Ainsi, vous aurez la liste des répertoires, la vue des répertoires, la liste des fichiers Et la liste des dossiers comme tableau séparé également.

Je passe deux jours pour cela et je ne veux pas que quelqu'un perd son temps pour cela aussi, j'espère que cela aidera quelqu'un.

function dirlist($dir){
    if(!file_exists($dir)){ return $dir.' does not exists'; }
    $list = array('path' => $dir, 'dirview' => array(), 'dirlist' => array(), 'files' => array(), 'folders' => array());

    $dirs = array($dir);
    while(null !== ($dir = array_pop($dirs))){
        if($dh = opendir($dir)){
            while(false !== ($file = readdir($dh))){
                if($file == '.' || $file == '..') continue;
                $path = $dir.DIRECTORY_SEPARATOR.$file;
                $list['dirlist_natural'][] = $path;
                if(is_dir($path)){
                    $list['dirview'][$dir]['folders'][] = $path;
                    // Bos klasorler while icerisine tekrar girmeyecektir. Klasorun oldugundan emin olalım.
                    if(!isset($list['dirview'][$path])){ $list['dirview'][$path] = array(); }
                    $dirs[] = $path;
                    //if($path == 'D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-content\upgrade'){ press($path); press($list['dirview']); die; }
                }
                else{
                    $list['dirview'][$dir]['files'][] = $path;
                }
            }
            closedir($dh);
        }
    }

    // if(!empty($dirlist['dirlist_natural']))  sort($dirlist['dirlist_natural'], SORT_LOCALE_STRING); // delete safe AMA gerek kalmadı.

    if(!empty($list['dirview'])) ksort($list['dirview']);

    // Dosyaları dogru sıralama yaptırıyoruz. Deniz P. - info[at]netinial.com
    foreach($list['dirview'] as $path => $file){
        if(isset($file['files'])){
            $list['dirlist'][] = $path;
            $list['files'] = array_merge($list['files'], $file['files']);
            $list['dirlist'] = array_merge($list['dirlist'], $file['files']);
        }
        // Add empty folders to the list
        if(is_dir($path) && array_search($path, $list['dirlist']) === false){
            $list['dirlist'][] = $path;
        }
        if(isset($file['folders'])){
            $list['folders'] = array_merge($list['folders'], $file['folders']);
        }
    }

    //press(array_diff($list['dirlist_natural'], $list['dirlist'])); press($list['dirview']); die;

    return $list;
}

va sortir quelque chose comme ça.

[D:\Xampp\htdocs\exclusiveyachtcharter.localhost] => Array
                (
                    [files] => Array
                        (
                            [0] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\.htaccess
                            [1] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\index.php
                            [2] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\license.txt
                            [3] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\php.php
                            [4] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\readme.html
                            [5] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-activate.php
                            [6] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-blog-header.php
                            [7] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-comments-post.php
                            [8] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-config-sample.php
                            [9] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-config.php
                            [10] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-cron.php
                            [11] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-links-opml.php
                            [12] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-load.php
                            [13] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-login.php
                            [14] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-mail.php
                            [15] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-settings.php
                            [16] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-signup.php
                            [17] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-trackback.php
                            [18] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\xmlrpc.php
                        )

                    [folders] => Array
                        (
                            [0] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\exclusiv_excluwlsql
                            [1] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-admin
                            [2] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-content
                            [3] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-includes
                        )

                )

sortie dirview

    [dirview] => Array
        (
            [0] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\.htaccess
            [1] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\index.php
            [2] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\license.txt
            [3] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\php.php
            [4] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\readme.html
            [5] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-activate.php
            [6] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-blog-header.php
            [7] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-comments-post.php
            [8] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-config-sample.php
            [9] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-config.php
            [10] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-cron.php
            [11] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-links-opml.php
            [12] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-load.php
            [13] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-login.php
            [14] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-mail.php
            [15] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-settings.php
            [16] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-signup.php
            [17] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\wp-trackback.php
            [18] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\xmlrpc.php
            [19] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost
            [20] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\exclusiv_excluwlsql\exclusiv_excluwl.sql
            [21] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\exclusiv_excluwlsql\exclusiv_excluwl.sql.Zip
            [22] => D:\Xampp\htdocs\exclusiveyachtcharter.localhost\exclusiv_excluwlsql
)
0
Deniz Porsuk

Version mise à jour de https://stackoverflow.com/a/24784144/5153116 answer:

function getDirContents($dir, $onlyFiles = false) {
    $results = [];
    $files = scandir($dir);
    foreach($files as $key => $value){
        if ($value === '.' || $value === '..') {
            continue;
        }

        $path = str_replace(DIRECTORY_SEPARATOR, '/', realpath($dir . '/' . $value));
        if (!is_dir($path)) {
            $results[] = $path;
        } else {
            if (!$onlyFiles) {
                $results[] = $path;
            }

            foreach (getDirContents($path, $onlyFiles) as $p) {
                $results[] = $p;
            }
        }
    }

    return $results;
}

Cette version résout/améliore:

  1. avertissements de realpath lorsque PHP open_basedir ne couvre pas le ...
  2. n'utilise pas de référence pour le tableau de résultats
  3. permet de lister uniquement les fichiers
0
Mvorisek

ici j'ai exemple pour ça

Liste tous les fichiers et dossiers d'un répertoire csv (fichier) lu avec la fonction PHP récursive

<?php

/** List all the files and folders in a Directory csv(file) read with PHP recursive function */
function getDirContents($dir, &$results = array()){
    $files = scandir($dir);

    foreach($files as $key => $value){
        $path = realpath($dir.DIRECTORY_SEPARATOR.$value);
        if(!is_dir($path)) {
            $results[] = $path;
        } else if($value != "." && $value != "..") {
            getDirContents($path, $results);
            //$results[] = $path;
        }
    }

    return $results;
}





$files = getDirContents('/xampp/htdocs/medifree/lab');//here folder name where your folders and it's csvfile;


foreach($files as $file){
$csv_file =$file;
$foldername =  explode(DIRECTORY_SEPARATOR,$file);
//using this get your folder name (explode your path);
print_r($foldername);

if (($handle = fopen($csv_file, "r")) !== FALSE) {

fgetcsv($handle); 
while (($data = fgetcsv($handle, 1000, ",")) !== FALSE) {
$num = count($data);
for ($c=0; $c < $num; $c++) {
$col[$c] = $data[$c];
}
}
fclose($handle);
}

}

?>

http://myphpinformation.blogspot.in/2016/05/list-all-files-and-folders-in-directory-csv-file-read-with-php-recursive.html

0
JD The Real Hero

Cela pourrait aider si vous souhaitez obtenir le contenu des répertoires sous forme de tableau, en ignorant les fichiers et répertoires cachés.

function dir_tree($dir_path)
{
    $rdi = new \RecursiveDirectoryIterator($dir_path);

    $rii = new \RecursiveIteratorIterator($rdi);

    $tree = [];

    foreach ($rii as $splFileInfo) {
        $file_name = $splFileInfo->getFilename();

        // Skip hidden files and directories.
        if ($file_name[0] === '.') {
            continue;
        }

        $path = $splFileInfo->isDir() ? array($file_name => array()) : array($file_name);

        for ($depth = $rii->getDepth() - 1; $depth >= 0; $depth--) {
            $path = array($rii->getSubIterator($depth)->current()->getFilename() => $path);
        }

        $tree = array_merge_recursive($tree, $path);
    }

    return $tree;
}

Le résultat serait quelque chose comme:

dir_tree(__DIR__.'/public');

[
    'css' => [
        'style.css',
        'style.min.css',
    ],
    'js' => [
        'style.css',
        'style.min.css',
    ],
    'favicon.ico',
]

La source

0
bmatovu