• Willkommen im Linux Club - dem deutschsprachigen Supportforum für GNU/Linux. Registriere dich kostenlos, um alle Inhalte zu sehen und Fragen zu stellen.

Logfiles von 2006 bis ende 2008 finden und zippen

ranganga

Newbie
Hi zusammen,

ich als absoluter Bash/shell Noob steh gerade vor einem größeren Problem ;) (für euch natürlich pillepalle)

Ich habe hier einen Ordner mit logfiles, die mittlerweile 3.2GB haben und seit 2006 aufgelaufen sind.
Da ich diese aber nicht wegputzen darf, möchte ich gerne alles von 2006 bis ende 2008 zippen und diese Dateien
vorerst in einen Ordner verschieben. Nach kontrolle kann ich diese dann löschen.

ich weiß es muss irgendwie über find laufen nur hab ich echt keinen Plan wie ich das ganze verknüpfe bzw der
richtige Befehl aussieht.

Könnt ihr mir da mal helfen? Danke schonmal

Gruß Ranganga
 

abgdf

Guru
Hi,

mit 'find' wohl schwierig. Schätze mal, so:
Code:
#!/usr/bin/perl

use warnings;
use strict;

# checkdate.pl (2006 to 2008):

use Archive::Zip qw( :ERROR_CODES :CONSTANTS );
use POSIX qw(mktime);
use File::Find;
use File::Basename;
use Cwd;

my $zipname = "log2006to2008.zip";

my $t2006 = POSIX::mktime((0, 0, 0, 0, 0, 106, 0, 0, 0));
my $t2009 = POSIX::mktime((0, 0, 0, 0, 0, 109, 0, 0, 0));

my $zip = Archive::Zip->new();

find({ wanted => \&checkDate, no_chdir => 1 }, &getcwd());

sub checkDate {
    my $fname = $_;
    my $bname;
    my @slist = stat($fname);
    my $mtime = $slist[9];
    if ($mtime >= $t2006 && $mtime < $t2009) {
        $bname = &basename($fname);
        print "Adding File: $bname.\n";
        $zip -> addFile($fname, $bname);
    }
}

# Write zip-File:
if ($zip -> numberOfMembers()) {
    die 'write error' unless $zip -> writeToFileNamed($zipname) == AZ_OK;
    print "\n" . $zip -> numberOfMembers(). " files written to '$zipname'.\n\n";
}
else {
    print "\nNo suitable files found: Nothing written.\n\n";
}
:mrgreen: Skript im Verzeichnis mit den Logfiles ausführen :wink:.

Gruß
 

framp

Moderator
Teammitglied
Wenn es auch mit einem tar geht ein Beispiel in Python:
Code:
#!/usr/bin/env python

import os
import tarfile
import sys

if len(sys.argv) < 3:
        print "Usage: " + sys.argv[0] + " [rootDirectory] [resultFile]"
        sys.exit(2)

root = sys.argv[1]
target = sys.argv[2] + ".tar"
try:
        os.remove(target)
except:
        pass

tarFile=tarfile.open(target,mode="w")

files=os.listdir(root)

for file in files:
        inputFile = root + "/" + file
        print "Processing " + inputFile + " ..."
        tarFile.add(inputFile)
 
A

Anonymous

Gast
ranganga schrieb:
Ich weiß es muss irgendwie über find laufen
mit find ist das viel zu einfach ;) und da die anderen auch nicht gerade einfache Scripte geschrieben haben, hier mal eine etwas größeren Einzeiler erstmal zum ausprobieren.
Code:
mkdir -p ./müll;stat -c"%y|%F|%n" * |awk -F"|" '$1~/200[678]-/ && $2~/regular file/ {print $3}' |while read i; do gzip -c "$i" > ./müll/"$i".gz ;done
Erklärung:
arbeitet im lokalem Verzeichnis (nicht rekursiv) und legt im aktuellen Verzeichnis ein Verzeichnis "müll" an, Die Dateien werden direkt über die Jahreszahl des Zeitstempels und nach dem Filetype ausgesucht. Danach werden davon komprimierte Kopien nach "./müll/" erstellt. Eventuell schon komprimierte Dateien werden aber dabei noch einmal komprimiert.

Wenn du die Dateien noch mit Bashmitteln vorauswählen willst, dann hier am "Rotem Stern" ist das möglich.
.....%F|%n" * |awk -F"|".......


Wenn das in einem Probeverzeichnis dann zur Zufriedenheit funktioniert, dann setzen wir noch einen oben drauf ;) es bleibt aber immer noch ein Einzeiler auch wenn es im Forum eventuell umgebrochen aussieht.
Code:
mkdir -p ./müll;stat -c"%y|%F|%n" * |awk -F"|" '$1~/200[678]-/ && $2~/regular file/ {print $3}' |while read i; do gzip -c "$i" > ./müll/"$i".gz  && (touch -r "$i" ./müll/"$i".gz ;echo "$i")  ;done
jetzt bekommen die komprimierten Dateien im "müll-Verzeichnis" den selben Zeitstempel wie die Orginaldateien und die Orginaldateiennamen werden ausgegeben. Sollte auch das funktionieren dann fast am Ende der Zeile aus dem echo ein rm machen, dann werden die Orginaldateien gelöscht, (soweit die Berechtigung dazu vorhanden ist).

Hoffe mal du hast keine Dateinamen mit Zeilenvorschüben oder mit PIPE-Zeichen im Namen, die würden hier nicht sauber funktionieren und Fehlermeldungen produzieren. ;)


robi
 

abgdf

Guru
@framp: Schön, daß hier auch mal jemand (außer mir) in Python schreibt :wink:.
Aber wo ist die Prüfung, ob das Dateidatum zwischen 2006 und 2008 liegt? (Hatte auch mal was zu Datum und Zeit in Python geschrieben.)
Und dann müßte man wohl noch sowas wie 'find' hinkriegen: Dafür nimmt man meist "os.path.walk()", was ähnlich eigenartig zu verwenden ist wie Perls "&File::Find::find()". Wenn's nur das Ausgangsverzeichnis erfassen soll, reicht aber natürlich auch "os.listdir(os.getcwd())" ...

Gruß
 

framp

Moderator
Teammitglied
abgdf schrieb:
@framp: Schön, daß hier auch mal jemand (außer mir) in Python schreibt :wink:.
Habe gerade vor ein paar Tagen angefangen mich mal mit Python zu befassen. Nette Scriptsprache ...
Aber wo ist die Prüfung, ob das Dateidatum zwischen 2006 und 2008 liegt? (Hatte auch mal was zu Datum und Zeit in Python geschrieben.)
Ist mir erst hinterher aufgefallen, dass das fehlt :eek:ps:
Und dann müßte man wohl noch sowas wie 'find' hinkriegen: Dafür nimmt man meist "os.path.walk()", was ähnlich eigenartig zu verwenden ist wie Perls "&File::Find::find()". Wenn's nur das Ausgangsverzeichnis erfassen soll, reicht aber natürlich auch "os.listdir(os.getcwd())" ...
walk braucht man nicht da TarFile.add ein gesamtes Verzeichnis rekursiv abarbeitet. (Deshalb ja tar als result). Wenn man gzip nehmen will muss man walk anwenden.
 

panamajo

Guru
Ich dachte die Dateien sollen nur komprimiert werden?
Code:
#!/usr/bin/env php
<?php
/**
 * @see	http://www.linux-club.de/viewtopic.php?f=21&t=104243
 */

if($argc < 3) {
	printf("Usage: %s [dir] [dst]\n", $argv[0]);
	exit(2);
}

function in_range($file, $from, $to)
{
	$ts = filemtime($file);
	$rc = (($ts >= $from) and ($ts <= $to));
	
	return $rc;
}

$t2006 = mktime(0, 0, 0, 1, 1, 2006);
$t2008 = mktime(0, 0, 0, 1, 1, 2009) - 1;
$files = glob($argv[1] . DIRECTORY_SEPARATOR . '*');

foreach($files as $file) {
	if(is_file($file) and is_readable($file) and in_range($file, $t2006, $t2008)) {
		$dst = $argv[2] . DIRECTORY_SEPARATOR . basename($file) . '.gz';
		printf("Compressing %s to %s ... ", $file, $dst);
		$src = file_get_contents($file);
		$ok = file_put_contents('compress.zlib://' . $dst, $src);
		if($ok !== FALSE) {
			printf("done\n");
		} else {
			printf("failed\n");
		}
	}
}

?>
 

abgdf

Guru
Übrigens hatten wir schonmal so ein ähnliches Thema (wo jemand sich auch was mit 'find' ausgedacht hat):

http://www.linux-club.de/viewtopic.php?f=21&t=102743

Gruß
 
Oben