Ich versuche, Dateien zu finden, die in den letzten x Minuten geändert wurden, beispielsweise in der letzten Stunde. Viele Foren und Tutorials im Internet schlagen vor, den Befehl find mit der Option -mmin wie folgt zu verwenden:
find . -mmin -60 |xargs ls -l
Dieser Befehl hat jedoch nicht wie erwartet für mich funktioniert. Wie Sie der folgenden Auflistung entnehmen können, werden auch Dateien angezeigt, die vor einer Stunde geändert wurden:
-rw------- 1 user user 9065 Oct 28 23:13 1446070435.V902I67a5567M283852.harvester
-rw------- 1 user user 1331 Oct 29 01:10 1446077402.V902I67a5b34M538793.harvester
-rw------- 1 user user 1615 Oct 29 01:36 1446078983.V902I67a5b35M267251.harvester
-rw------- 1 user user 72365 Oct 29 02:27 1446082022.V902I67a5b36M873811.harvester
-rw------- 1 user user 69102 Oct 29 02:27 1446082024.V902I67a5b37M142247.harvester
-rw------- 1 user user 2611 Oct 29 02:34 1446082482.V902I67a5b38M258101.harvester
-rw------- 1 user user 2612 Oct 29 02:34 1446082485.V902I67a5b39M607107.harvester
-rw------- 1 user user 2600 Oct 29 02:34 1446082488.V902I67a5b3aM465574.harvester
-rw------- 1 user user 10779 Oct 29 03:27 1446085622.V902I67a5b3bM110329.harvester
-rw------- 1 user user 5836 Oct 29 03:27 1446085623.V902I67a5b3cM254104.harvester
-rw------- 1 user user 8970 Oct 29 04:27 1446089232.V902I67a5b3dM936339.harvester
-rw------- 1 user user 165393 Oct 29 06:10 1446095400.V902I67a5b3eM290158.harvester
-rw------- 1 user user 105054 Oct 29 06:10 1446095430.V902I67a5b3fM265065.harvester
-rw------- 1 user user 1615 Oct 29 06:24 1446096244.V902I67a5b40M55701.harvester
-rw------- 1 user user 1620 Oct 29 06:24 1446096292.V902I67a5b41M337769.harvester
-rw------- 1 user user 10436 Oct 29 06:36 1446096973.V902I67a5b42M707215.harvester
-rw------- 1 user user 7150 Oct 29 06:36 1446097019.V902I67a5b43M415731.harvester
-rw------- 1 user user 4357 Oct 29 06:39 1446097194.V902I67a5b56M446687.harvester
-rw------- 1 user user 4283 Oct 29 06:39 1446097195.V902I67a5b57M957052.harvester
-rw------- 1 user user 4393 Oct 29 06:39 1446097197.V902I67a5b58M774506.harvester
-rw------- 1 user user 4264 Oct 29 06:39 1446097198.V902I67a5b59M532213.harvester
-rw------- 1 user user 4272 Oct 29 06:40 1446097201.V902I67a5b5aM534679.harvester
-rw------- 1 user user 4274 Oct 29 06:40 1446097228.V902I67a5b5dM363553.harvester
-rw------- 1 user user 20905 Oct 29 06:44 1446097455.V902I67a5b5eM918314.harvester
Tatsächlich wurden nur alle Dateien im aktuellen Verzeichnis aufgeführt. Wir können eine dieser Dateien als Beispiel nehmen und prüfen, ob die Änderungszeit tatsächlich mit dem Befehl ls angezeigt wird:
stat 1446070435.V902I67a5567M283852.harvester
File: ‘1446070435.V902I67a5567M283852.harvester’
Size: 9065 Blocks: 24 IO Block: 4096 regular file
Device: 902h/2306d Inode: 108680551 Links: 1
Access: (0600/-rw-------) Uid: ( 1001/ user) Gid: ( 1027/ user)
Access: 2015-10-28 23:13:55.281515368 +0100
Modify: 2015-10-28 23:13:55.281515368 +0100
Change: 2015-10-28 23:13:55.313515539 +0100
Wie wir sehen können, wurde diese Datei definitiv vor vor 1 Stunde geändert! Ich habe auch find -mmin 60
oder find -mmin +60
ausprobiert, aber es hat auch nicht funktioniert.
Warum geschieht dies und wie wird der Befehl find korrekt verwendet?
Ich kann Ihr Problem reproduzieren, wenn keine Dateien im Verzeichnis vorhanden sind, die in der letzten Stunde geändert wurden. In diesem Fall gibt find . -mmin -60
nichts zurück. Der Befehl find . -mmin -60 |xargs ls -l
gibt jedoch jede Datei im Verzeichnis zurück. Dies ist konsistent mit dem, was passiert, wenn ls -l
ohne Argument ausgeführt wird.
Um sicherzustellen, dass ls -l
nur ausgeführt wird, wenn eine Datei gefunden wird, versuchen Sie Folgendes:
find . -mmin -60 -type f -exec ls -l {} +
Das Problem ist, dass
find . -mmin -60
ausgänge:
.
./file1
./file2
Beachten Sie die Linie mit einem Punkt?
Das macht ls
list das gesamte Verzeichnis genau so, wie wenn ls -l .
ausgeführt wird.
Eine Lösung besteht darin, nur Dateien (keine Verzeichnisse) aufzulisten:
find . -mmin -60 -type f | xargs ls -l
Es ist jedoch besser, direkt die Option -exec von find zu verwenden:
find . -mmin -60 -type f -exec ls -l {} \;
Oder nur:
find . -mmin -60 -type f -ls
Welches ist übrigens auch mit Verzeichnissen sicher:
find . -mmin -60 -ls
So suchen Sie nach Dateien in/target_directory und allen seinen Unterverzeichnissen, die in den letzten 60 Minuten geändert wurden:
$ find /target_directory -type f -mmin -60
So finden Sie die zuletzt geänderten Dateien in der umgekehrten Reihenfolge der Aktualisierungszeit (d. H. Die zuletzt aktualisierten Dateien zuerst):
$ find /etc -type f -printf '%TY-%Tm-%Td %TT %p\n' | sort -r
Ich arbeite durch dasselbe Bedürfnis und ich glaube, Ihr Zeitrahmen ist falsch.
Probiere diese:
Sie sollten 24 Stunden als Basis verwenden. Die Anzahl nach -zeit sollte relativ zu 24 Stunden sein. Somit entspricht -.5 12 Stunden, da 12 Stunden die Hälfte von 24 Stunden sind.
Handbuch von find:
Numeric arguments can be specified as
+n for greater than n,
-n for less than n,
n for exactly n.
-amin n
File was last accessed n minutes ago.
-anewer file
File was last accessed more recently than file was modified. If file is a symbolic link and the -H option or the -L option is in effect, the access time of the file it points to is always
used.
-atime n
File was last accessed n*24 hours ago. When find figures out how many 24-hour periods ago the file was last accessed, any fractional part is ignored, so to match -atime +1, a file has to
have been accessed at least two days ago.
-cmin n
File's status was last changed n minutes ago.
-cnewer file
File's status was last changed more recently than file was modified. If file is a symbolic link and the -H option or the -L option is in effect, the status-change time of the file it points
to is always used.
-ctime n
File's status was last changed n*24 hours ago. See the comments for -atime to understand how rounding affects the interpretation of file status change times.
Beispiel:
find /dir -cmin -60 # creation time
find /dir -mmin -60 # modification time
find /dir -amin -60 # access time
Das kann für Sie arbeiten. Ich habe es zum Bereinigen von Ordnern während der Bereitstellung zum Löschen alter Bereitstellungsdateien verwendet.
clean_anyfolder() {
local temp2="$1/**"; //PATH
temp3=( $(ls -d $temp2 -t | grep "`date | awk '{print $2" "$3}'`") )
j=0;
while [ $j -lt ${#temp3[@]} ]
do
echo "to be removed ${temp3[$j]}"
delete_file_or_folder ${temp3[$j]} 0 //DELETE HERE
fi
j=`expr $j + 1`
done
}
Eigentlich gibt es hier mehr als ein Thema. Die wichtigste ist, dass xargs
standardmäßig den von Ihnen angegebenen Befehl ausführt, auch wenn keine Argumente übergeben wurden. Um dies zu ändern, können Sie eine Erweiterung von GNU für xargs
verwenden:
--no-run-if-empty
-r
Wenn die Standardeingabe keine Nicht-Leerzeichen enthält, führen Sie den Befehl nicht aus. Normalerweise wird der Befehl einmal ausgeführt, auch wenn keine Eingabe erfolgt. Diese Option ist eine Erweiterung von GNU.
Einfaches Beispiel:
find . -mmin -60 | xargs -r ls -l
Dies kann jedoch mit allen Unterverzeichnissen übereinstimmen, einschließlich .
(das aktuelle Verzeichnis), und ls
listet jedes einzeln auf. Die Ausgabe wird also ein Durcheinander sein. Lösung: Übergeben Sie -d
an ls
, wodurch das Auflisten des Verzeichnisinhalts nicht möglich ist:
find . -mmin -60 | xargs -r ls -ld
Jetzt mögen Sie .
(das aktuelle Verzeichnis) nicht in Ihrer Liste? Lösung: Schließen Sie die erste Verzeichnisebene (0
) von der Suchausgabe aus:
find . -mindepth 1 -mmin -60 | xargs -r ls -ld
Jetzt brauchst du nur noch die Dateien in deiner Liste? Lösung: Schließen Sie die Verzeichnisse aus:
find . -type f -mmin -60 | xargs -r ls -l
Nun haben Sie einige Dateien mit Namen, die Leerzeichen, Anführungszeichen oder Backslashes enthalten. Lösung: Verwenden Sie eine nullterminierte Ausgabe (find) und eine Eingabe (xargs) (dies sind auch die Erweiterungen GNU, afaik):
find . -type f -mmin -60 -print0 | xargs -r0 ls -l