Kaynak klasöre göre hedef klasöründen istenmeyen dosyaları ve klasörleri silmek

4 Cevap php

Ben PHP kullanıyorum ve ben gibi aşağıda komut bir şey gerekir:

I have to compare two folder structure and with reference of source folder I want to delete all the files/folders present in other destination folder which do not exist in reference source folder, how could i do this?

EDITED:

$original = scan_dir_recursive('/var/www/html/copy2');
$mirror = scan_dir_recursive('/var/www/html/copy1');
function scan_dir_recursive($dir) {

  $all_paths = array();
  $new_paths = scandir($dir);

  foreach ($new_paths as $path) {
    if ($path == '.' || $path == '..') {
      continue;
    }
    $path = $dir . DIRECTORY_SEPARATOR . $path;
    if (is_dir($path)) {
      $all_paths = array_merge($all_paths, scan_dir_recursive($path));
    } else {
      $all_paths[] = $path;
    }
  }

  return $all_paths;

}
foreach($mirror as $mirr)
{
   if($mirr != '.' && $mirr != '..')
   {
     if(!in_array($mirr, $original))
     {
        unlink($mirr);
        // delete the file
     }

   }
}

The above code shows what i did.. Here My copy1 folder contains extra files than copy2 folders hence i need these extra files to be deleted.

EDITED: Below given output is are arrays of original Mirror and of difference of both..

Original Array
(
    [0] => /var/www/html/copy2/Copy (5) of New Text Document.txt
    [1] => /var/www/html/copy2/Copy of New Text Document.txt
)

Mirror Array
(
    [0] => /var/www/html/copy1/Copy (2) of New Text Document.txt
    [1] => /var/www/html/copy1/Copy (3) of New Text Document.txt
    [2] => /var/www/html/copy1/Copy (5) of New Text Document.txt
)

Difference Array
(
    [0] => /var/www/html/copy1/Copy (2) of New Text Document.txt
    [1] => /var/www/html/copy1/Copy (3) of New Text Document.txt
    [2] => /var/www/html/copy1/Copy (5) of New Text Document.txt
)

i fark dizideki tüm dosyaları silmek için bir döngü görüntülenen çıkış başına silinmesi gereken yineleme zaman .. Bunu nasıl düzeltebiliriz .. silinmek için döngü aşağıda verilmiştir.

$dirs_to_delete = array();
foreach ($diff_path as $path) {
    if (is_dir($path)) {
        $dirs_to_delete[] = $path;
    } else {
        unlink($path);
    }
}

while ($dir = array_pop($dirs_to_delete)) {
    rmdir($dir);
}

4 Cevap

Öncelikle her iki dizinde bir özyinelemeli listesini gerekir. Bu gibi basit bir fonksiyon çalışacaktır:

function scan_dir_recursive($dir, $rel = null) {

  $all_paths = array();
  $new_paths = scandir($dir);

  foreach ($new_paths as $path) {

    if ($path == '.' || $path == '..') {
      continue;
    }

    if ($rel === null) {
        $path_with_rel = $path;
    } else {
        $path_with_rel = $rel . DIRECTORY_SEPARATOR . $path;
    }

    $full_path = $dir . DIRECTORY_SEPARATOR . $path;
    $all_paths[] = $path_with_rel;

    if (is_dir($full_path)) {
      $all_paths = array_merge(
        $all_paths, scan_dir_recursive($full_path, $path_with_rel)
      );
    }

  }

  return $all_paths;

}

Sonra array_diff ile farkı hesaplayabiliriz.

$diff_paths = array_diff(
    scan_dir_recursive('/foo/bar/mirror'),
    scan_dir_recursive('/qux/baz/source')
);

Bu dizi üzerinde yineleme, dosyaları silerek başlamak mümkün olacak. Onlar ilk boş olmalı çünkü dizinleri biraz yanıltıcıdır vardır.

// warning: test this code yourself before using on real data!

$dirs_to_delete = array();
foreach ($diff_paths as $path) {
    if (is_dir($path)) {
        $dirs_to_delete[] = $path;
    } else {
        unlink($path);
    }
}

while ($dir = array_pop($dirs_to_delete)) {
    rmdir($dir);
}

Bazı şeyleri test ettik ve şimdi iyi çalışıyor olmalıdır. Tabii ki, bunun için sözümü yapmayız. Gerçek verilerini silmeden önce kurulum kendi güvenli testi emin olun.

Özyinelemeli dizinleri için kullanın lütfen:

$modified_directory = new RecursiveIteratorIterator(
       new RecursiveDirectoryIterator('path/to/modified'), true
);
$modified_files = array();
foreach ($modified_directory as $file)
{
    $modified_files []= $file->getPathname();
}

Sen $ file-> isDot () veya $ dosya-> isFile () gibi diğer şeyler yapabilirsiniz. SPLFileInfo ziyareti ile daha fazla dosya komutları için http://www.php.net/manual/en/class.splfileinfo.php

Teşekkürler tüm Kanunu'nun Aşağıda benim sorun için yaptığı özveri, işimin, erisco Özel Thanks verilen değerli zaman için ben erisco en son düzenlenmiş cevapta küçük bir değişiklik ile, yapmak gerekiyordu görevi başarırsınız için mükemmel bir koddur .. .

$source = '/var/www/html/copy1';
$mirror = '/var/www/html/copy2';

function scan_dir_recursive($dir, $rel = null) {

  $all_paths = array();
  $new_paths = scandir($dir);

  foreach ($new_paths as $path) {

    if ($path == '.' || $path == '..') {
      continue;
    }

    if ($rel === null) {
        $path_with_rel = $path;
    } else {
        $path_with_rel = $rel . DIRECTORY_SEPARATOR . $path;
    }

    $full_path = $dir . DIRECTORY_SEPARATOR . $path;
    $all_paths[] = $path_with_rel;

    if (is_dir($full_path)) {
      $all_paths = array_merge(
        $all_paths, scan_dir_recursive($full_path, $path_with_rel)
      );
    }

  }

  return $all_paths;

}
$diff_paths = array_diff(
    scan_dir_recursive($mirror),
    scan_dir_recursive($source)
);



echo "<pre>Difference ";print_r($diff_paths);

$dirs_to_delete = array();
foreach ($diff_paths as $path) {
    $path = $mirror."/".$path;//added code to unlink.
    if (is_dir($path)) {

        $dirs_to_delete[] = $path;
    } else {

        if(unlink($path))
        {
            echo "File ".$path. "Deleted.";
        }
    }
}

while ($dir = array_pop($dirs_to_delete)) {
    rmdir($dir);
}

First do a scandir() of the original folder,
then do a scandir on mirror folder.
start traversing the mirror folder array and check if that file is present in the scandir() of original folder. something like this


$original = scandir('path/to/original/folder');
$mirror = scandir('path/to/mirror/folder');

foreach($mirror as $mirr)
{
   if($mirr != '.' && $mirr != '..')
   {
     if(in_array($mirr, $original))
     {
        // do not delete the file
     }
     else
     {
        // delete the file
        unlink($mirr);
     }
   }
}

Bu sorunu çözmek gerekir. boş değilse silmek çalıştığınız klasör boş olup olmadığını kontrol etmek için yukarıdaki kodu bazı özyineleme dahil (buna yukarıdaki kodunu değiştirmek gerekir, o zaman önce tüm dosya / klasörleri silmek gerekir ) içinde ve daha sonra üst klasörü silin.