PHP delete all subdirectories in a directory having expired date? - php

There is a directory /home/example/public_html/users/files/. Within the directory there are subdirectories with random names like 2378232828923_1298295497.
How do I completely delete the subdirectories which have creation date > 1 month?
There is a good script that I use to delete files, but it don't work with dirs:
$seconds_old = 2629743; //1 month old
$directory = "/home/example/public_html/users/files/";
if( !$dirhandle = #opendir($directory) )
return;
while( false !== ($filename = readdir($dirhandle)) ) {
if( $filename != "." && $filename != ".." ) {
$filename = $directory. "/". $filename;
if( #filectime($filename) < (time()-$seconds_old) )
#unlink($filename); //rmdir maybe?
}
}

you need a recursive function for this.
function remove_dir($dir)
{
chdir($dir);
if( !$dirhandle = #opendir('.') )
return;
while( false !== ($filename = readdir($dirhandle)) ) {
if( $filename == "." || $filename = ".." )
continue;
if( #filectime($filename) < (time()-$seconds_old) ) {
if (is_dir($filename)
remove_dir($filename);
else
#unlink($filename);
}
}
chdir("..");
rmdir($dir);
}

<?php
$dirs = array();
$index = array();
$onemonthback = strtotime('-1 month');
$handle = opendir('relative/path/to/dir');
while($file = readdir($handle){
if(is_dir($file) && $file != '.' && $file != '..'){
$dirs[] = $file;
$index[] = filemtime( 'relative/path/to/dir/'.$file );
}
}
closedir($handle);
asort( $index );
foreach($index as $i => $t) {
if($t < $onemonthback) {
#unlink('relative/path/to/dir/'.$dirs[$i]);
}
}
?>

If PHP runs on a Linux server, you could use a shell command, to improve performance (a recursive PHP function can be inefficient in very large directories):
shell_exec('rm -rf '.$directory);

Related

How to get PHP files and their path changed after a date

I want to get all file names (and path) of files those updated after a date (in directory and subdirectories) using PHP.
like all files updated after 20.08.2017 ,
Below code provide only files from directory, i also need path,
$dir = "opendir(".")";
clearstatcache();
$yesdate = strtotime("-1 days");
while(false != ($file = readdir($dir)))
{
if ( substr($file,-4) == ".php" )
{
if (filemtime($file) >= $yesdate)
{
echo $file;
}
}
}
Thanks
If you're using relative paths like e.g. . or paths that follow a symbolic link, you can get the real path via the function realpath :
$actualDirectory = realpath(".");
$dir = opendir($actualDirectory);
clearstatcache();
$yesdate = strtotime("-1 days");
while(false != ($file = readdir($dir)))
{
if ( substr($file,-4) == ".php" && filemtime($file) >= $yesdate)
{
echo $actualDirectory."/".$file;
}
}
If you want to scan all sub directories until the end of the tree you need to use a recursive function.
function get_updated_files($date, $directory, $result = array())
{
$directory = realpath($directory);
$directory_content = glob($directory.'/*');
foreach($directory_content as $item) {
if(is_dir($item)) {
$result = get_updated_files($date, $item, $result);
} elseif(strtotime($date) < filemtime($item) && pathinfo($item, PATHINFO_EXTENSION) == 'php') {
$result[] = $item;
}
}
return $result;
}
$result = get_updated_files('2017-08-20', '.');
With a specified date:
$dir = opendir(dirname(__FILE__));
clearstatcache();
$dday = "20.08.2017.";
$yesdate = strtotime($dday);
while(false != ($file = readdir($dir))) {
if ( substr($file,-4) == ".php" ) {
if (filemtime($file) >= $yesdate) {
echo $file;
}
}
}
Or with today - 1 day:
$dday = date("d.m.Y", time());
$yesdate = strtotime($dday) - 86400;
You must proceed like this
function get_updated_files($date, $directory,$file_extension='php',$sameday=false, $result = array())
{
if(!$sameday){
/* really worth because actually
your code will return true for your given day and this maybe
is not the goal you are trying to achieve...*/
$date = strtotime($date)+86399;
}else{
$date=strtotime($date);
}
$directory = realpath($directory);
$directory_content = glob($directory.'\\*');
foreach($directory_content as $item) {
if(is_dir($item)) {
$result=get_updated_files($date, $item,$file_extension,$sameday,$result);
} elseif($date < filemtime($item)&& pathinfo($item, PATHINFO_EXTENSION)===$file_extension) {
$result[] = $item;
}
}
return $result;
}
$result = get_updated_files('2017-08-20', '.');

Creating default object from empty value in OT Scroller

I have problem with warning on my Joomla website. More precisely "Warning: Creating default object from empty value in /public_html/modules/mod_ot_scroller/helper.php on line 40"
Here is whole helper.php file:
<?php
defined('_JEXEC') or die;
class modOTScrollerHelper
{
function getImages(&$params, $folder, $type)
{
$files = array();
$images = array();
$dir = JPATH_BASE.DS.$folder;
// check if directory exists
if (is_dir($dir))
{
if ($handle = opendir($dir)) {
while (false !== ($file = readdir($handle))) {
if ($file != '.' && $file != '..' && $file != 'CVS' && $file != 'index.html' && $file != 'Thumbs.db') {
$files[] = $file;
}
}
}
closedir($handle);
foreach($type as $tp){
$tp=trim($tp);
$i = 0;
foreach ($files as $img){
if (!is_dir($dir .DS. $img))
{
if (preg_match("#$tp#i", $img)) {
$images[$i]->name = $img;
$images[$i]->folder = $folder;
++$i;
}
}
}
}
}
return $images;
}
function getFolder(&$params)
{
$folder = $params->get( 'folder' );
$LiveSite = JURI::base();
// if folder includes livesite info, remove
if ( JString::strpos($folder, $LiveSite) === 0 ) {
$folder = str_replace( $LiveSite, '', $folder );
}
// if folder includes absolute path, remove
if ( JString::strpos($folder, JPATH_SITE) === 0 ) {
$folder= str_replace( JPATH_BASE, '', $folder );
}
$folder = str_replace('\\',DS,$folder);
$folder = str_replace('/',DS,$folder);
return $folder;
}
}
?>
Whole website works fine and images shown properly.
What can I do to get rid of it?
Yeah, thats a warning, because you did not specify what $images[$i] should be. If you want to, initialize it using $images[$i] = new \stdClass();

Problems with continue in foreach loop

This is my code:
<?php
function recursive($directory){
$nr = 0;
$files = scandir($directory);
foreach($files as $file){
if($file == '.' || $file == '..') continue;
if(is_dir($file)){
echo $file.'<br>';
continue;
}
echo $file.' ----------<br>';
}
}
recursive('.');
?>
Basically I want the code at the bottom of the loop to be skipped until they are no more files in the directory.
How I want it to look:
How it looks:
A different take on your code but have you looked at the recursiveIterator family of classes? It's part of the php core and is pretty powerful.
$folder='c:/temp';
foreach( new RecursiveIteratorIterator( new RecursiveDirectoryIterator( $folder, RecursiveDirectoryIterator::KEY_AS_PATHNAME ), RecursiveIteratorIterator::CHILD_FIRST ) as $file => $info ) {
if( $info->isFile() && $info->isReadable() && $info->isWritable() ){
echo $info->getFilename().'-------<br />';
} elseif( $info->isDir() ){
echo $info->getPath().'<br />';
}
}
I think you first need to list the directories, then the files. You can do that by changing a bit your function and running it twice:
function recursive($directory, $type){
$nr = 0;
$files = scandir($directory);
foreach($files as $file){
if($file == '.' || $file == '..') continue;
if(is_dir($file) && $type == 'dir'){
echo $file.'<br>';
} else if(!is_dir($file) && $type == 'file'){
echo $file.' ----------<br>';
}
}
}
recursive('.', 'dir');
recursive('.', 'file');
(By the way, although it's called "recursive", it doesn't do recursion)
Like this?
echo $file.'<br>';
if(is_dir($file) === false){
echo $file.' ----------<br>';
}

how to make this find specific extensions and show only the file name

1) how can i make this read only ".txt" files
2) how can i make it show only the file name so i can design it how i'd i like..
(<h1>$file</h1> for example)
$dir = "includes/news";
$dh = opendir($dir);
while (false !== ($filename = readdir($dh)))
{
if ($filename != "." && $filename != ".." && strtolower(substr($filename, strrpos($filename, '.') + 1)) == 'txt')
{
$files[] = $filename;
}
}
sort($files);
echo $files;
what it shows right now is:
Array ( [0] => . [1] => .. [2] => [23.7] Hey.txt [3] => [24.7] New
Website.txt [4] => [25.7] Example.txt )
Now, this is another way i could do it, i like it bit better:
if( $handle = opendir( 'includes/news' ))
{
while( $file = readdir( $handle ))
{
if( strstr( $file, "txt" ) )
{
$addr = strtr($file, array('.txt' => ''));
echo '<h1>» ' . $addr . "</h1>";
}
}
closedir($handle);
}
but the my issue with this one is that there is no Sorting between the files.
everything is ok with the output, just the order of them. so if one of you can figure out how to sort them right, that would be perfect
Okay, try this:
$files = array();
if($handle = opendir( 'includes/news' )) {
while( $file = readdir( $handle )) {
if ($file != '.' && $file != '..') {
// let's check for txt extension
$extension = substr($file, -3);
// filename without '.txt'
$filename = substr($file, 0, -4);
if ($extension == 'txt')
$files[] = $file; // or $filename
}
}
closedir($handle);
}
sort($files);
foreach ($files as $file)
echo '<h1><a href="?module=news&read=' . $file
. '">» ' . $file . "</a></h1>";
I think this should accomplish what you want to do. It uses explode and a negative limit to find only .txt files and returns only the name.
$dir = "includes/news";
$dh = opendir($dir);
while (false !== ($filename = readdir($dh))){
$fileName = explode('.txt', $node, -1)[0];
if(count($fileName) )
$files[] = '<h1>'.$fileName.'</h1>';
}
try to make it as simple as possible
try this
function check_txt($file){
$array = explode(".","$file");
if(count($array)!=1 && $array[count($array)-1]=="txt"){return true;}
return false;
}
if($handle = opendir( 'includes/news' )) {
while( $file = readdir( $handle ))
{
if( check_txt($file) )
{
echo '<h1>» ' . $file . "</h1>";
}
}
closedir($handle);
}

How get first modified file in a folder using PHP?

How get first modified file?
So far I've had:
$dir = $path.'/';
$firstMod = '';
$p = 1;
foreach (scandir($dir) as $file) {
if (is_file($dir.$file) && ... ) {
if($p == 1) break;
}
}
If I would like to get last file but not last modified but last in an folder order what should I use?
you can try to write all the files in the array make key as the date modified than reorder the array based on date and get the first element of array which would first modified.
<?php
$folder = "files/";
$handle = opendir($folder);
$files=array();
while ($file = readdir($handle)){
if( $file != ".." && $file != "." ){
$key = filemtime($file);
$files[$key] = $file ;
}
}
closedir($handle);
ksort($files) ;
echo reset($files);
?>

Categories