alle Dateien außer bei bestimmtem Namen löschen

Heute ist Stammtischzeit:
Jeden Donnerstag 20:30 Uhr hier im Chat.
Wer Lust hat, kann sich gerne beteiligen. ;)
  • Moin,

    ich hab hier in den letzten paar Wochen alle 15min das aktuelle Wetter als xml-Datei runtergeladen.
    Jetzt hab ich einen Ordner mit ~1850 Dateien, die nach folgendem Schema benannt sind:

    Code
    2014-04-22-13-00-weather.xml
    2014-04-22-13-15-weather.xml
    2014-04-22-13-30-weather.xml
    2014-04-22-13-45-weather.xml

    usw...
    dazwischen sind von tests aber immer wieder Dateien, die dann z.B. so heißen:

    Code
    2014-04-22-13-21-weather.xml


    Wie kann ich machen, dass per Script alle Dateien, die nicht auf

    Code
    *-00-weather.xml
    *-15-weather.xml
    *-30-weather.xml
    *-45-weather.xml


    enden gelöscht werden?
    Ich kenn mich mit sed und awk leider garnicht aus :(

    Danke :)

    Einmal editiert, zuletzt von LJ Jojo (11. Mai 2014 um 13:00)

  • Womit/Wovon werden die Dateien denn erzeugt?


    Zum Script:
    Ich würd erstmal festlegen welche Maske behalten werden soll, also vermutlich das aktuelle Datum? Oder sollen generell alle Datein behalten werden die auf "alle 15min" zutreffen also auch die vom letzten Monat?

    Zum vorgehen würde ich das für jedes einzelne File abarbeiten, wäre zwar langsamer aber vom Code her einfacher zu verstehen ;)
    Also zunächst eine Liste mit allen Dateien erstellen, dann jede einzelne Datei durch gehen und jene löschen die nicht auf ein bestimmtes Muster zutrifft.

    Zum Beispiel:

    Code
    root@raspberrypi:/tmp/test# ls
    2014-04-22-13-00-weather.xml  2014-04-22-13-21-weather.xml  2014-04-22-13-45-weather.xml
    2014-04-22-13-15-weather.xml  2014-04-22-13-30-weather.xml
    root@raspberrypi:/tmp/test#

    Hier möchtest du also die Dateien mit -00-weather.xml , -15-weather.xml , -30-weather.xml und -45-weather.xml behalten.
    Das entsprechende Bash Script sähe dann zum Beispiel wie folgt aus:

    Die eigentliche Löschaktion habe ich aber noch auskommentiert - damit du es zunächst testen kannst ob das den gewünschten Effekt hat.

    Was das Script macht:
    die erste for Schleife arbeitet alle Dateien nacheinander als $file ab, es wird also eine DateiListe durch ls $CleanDir erstellt.
    Standardmässig wird delete=1 gesetzt. Die zweite for Schleife prüft dann ob das aktuelle $file auf eines der in HoldFiles befindlichen Dateinamen zutrifft und falls das der Fall ist wird delete=0 gesetzt, das file soll also nicht gelöscht werden. Anschließend wird die zweite for Schleife unterbrochen da ja eine Übereinstimmung festgestellt wurde.
    Dann würd geprüft ob delete=1 gesetzt ist, also $file nicht in der HoldFiles Liste vorkam und dann wird die Datei halt gelöscht ;)


    Jenachdem wovon die Dateien erzeugt werden könnte man das aber ggf auch eleganter direkt dort mit einbauen damit nicht zusätzlich ein weiteres Script regelmäßig laufen muss


    /EDIT: korrigiertes Script:

    Spoiler anzeigen
  • Das braucht kein Script. das kann die Shell ganz alleine:

    Code
    rm -i *[1-46-9]-weather.xml

    Das -i fragt nach, ob das File wirklich geloescht werden soll. Fuer den ersten
    Versuch sicher sinnvoll ;)

    Moment, ich muss noch nachbessern:

    Code
    rm  -i  *[1-46-9]-weather.xml  *2?-weather.xml

    Wenn noch welche uebrig bleiben, genau angeben welche ich verpasst habe...

    Zweite Korrektur:

    Code
    rm  -i *[1-46-9]-weather.xml *[25]?-weather.xml *[03]5-weather.xml *[14]0-weather.xml

    Einmal editiert, zuletzt von Tell (11. Mai 2014 um 16:09)

  • Tell:
    deine Zeile hat schon einige gekriegt, aber es sind noch da:

    Code
    2014-04-20-11-35
    2014-04-22-12-40
    2014-04-22-12-50
    2014-04-22-13-05
    2014-04-22-13-10

    usw
    aber es scheinen schonmal alle die nicht auf 0 oder 5 enden weg zu sein :)

    meigrafd:
    Mit dem Script werden per Cronjob alle 15min die Daten von wordlweatheronline geladen:


    mit dem letztem wget werden die aktuelle Temperatur usw. nochmal in eine SQlite Datenbank eingetragen, mit der ich hoffentlich bald die Kurven in der Website darstellen kann :)
    Und dein Script scheint auch noch die restlichen Dateien die das Script von Tell nicht löscht zu löschen :)

    Das Problem ist, wenn ich das direkt in das Download-Skript mit einbaue hab ich ja danach die Testdateien nicht mehr :D also werde ich das vermutlich einfach jede nacht um 3 oder so laufen lassen :)

    Vielen Dank
    Johannes

  • Hm ich versteh nicht ganz wieso das Script die $d-weather.xml Datei nach /usr/share/data/weather kopiert? Anschließend wird /usr/share/data/weather nämlich gar nicht mehr genutzt sondern nur /usr/share/nginx/www/
    Wenn es sich 2x um die selbe Datei handelt belegt das also auch den doppelten Speicherplatz. Sinnvoller wäre, wenn die Datei (in) /usr/share/data/weather wirklich benötigt wird einen Symlink zur /usr/share/nginx/www/weather.xml zu erzeugen.

    Desweiteren fragst du mit dem ersten wget num_of_days=5 ab, scheinst das script aber alle 15min auszuführen. Wieso also dann auch noch die Werte der letzten 5 Tage abfragen? Das vergrößert die Datei bzw später deine SQLite Datenbank doch nur unnötig :huh:

    Um die SD zu entlasten würde ich die Dateien btw lieber in ein tmpfs ablegen und für nginx verlinken - tmpfs ist sowas wie eine ramdisk mit dem Unterschied das nur soviel Ram verbraucht wird wie tatsächlich belegt ist..

  • regex ist sicherlich nicht jedermans Sache, aber wer regex kann wird meinen Vorschlag einfacher finden :cool:

    Es geht aber auch mit

    Code
    find . -not -name "2014*00-weather*" -and -not -name "2014*15-weather*" -and -not -name "2014*30-weather*" -and -not -name "2014*45-weather*" | xargs rm

    Ist vielleicht auf den ersten Blick nicht so ganz einfach - aber dafür excluded man explizit die Dateien mit 00, 15, 30 und 45 und ist sich dann sicher dass da nix schiefgeht. Nicht viele wissen, dass man bei find auch komplexe logische Ausdruecke bauen kann und sogar die Nagation vorhanden ist. Das ist bei regex nicht einfach möglich und deshalb habe ich oben den regex benutzt um die 4 Ausnahmen zu matchen und dann mit -not im find zu negieren.


  • Hm ich versteh nicht ganz wieso das Script die $d-weather.xml Datei nach /usr/share/data/weather kopiert?


    Dort werden sie alle rein gespeichert um etwas datenmüll zu sammeln :thumbs1:
    Und das man da vielleicht mal was nachschauen kann.


    Desweiteren fragst du mit dem ersten wget num_of_days=5 ab, scheinst das script aber alle 15min auszuführen. Wieso also dann auch noch die Werte der letzten 5 Tage abfragen? Das vergrößert die Datei bzw später deine SQLite Datenbank doch nur unnötig :huh:


    Das sind 5 Tage vorhersage und in die SQlite db kommen sowieso nur die aktuellen Daten, dass ich sie hoffentlich bald mit highcharts.js anzeigen kann :)
    Oder wäre es sinnvoller alle daten in die db zu packen und keine inzwischen 2500 XML dateien zu speichern, am tagen kommen 96 dazu :D


    Um die SD zu entlasten würde ich die Dateien btw lieber in ein tmpfs ablegen und für nginx verlinken - tmpfs ist sowas wie eine ramdisk mit dem Unterschied das nur soviel Ram verbraucht wird wie tatsächlich belegt ist..


    für die dateien in /usr/share/data/weather macht das denk ich keinen sinn, aber für die dateien bei nginx die sich alle 15min ändern könnte das schon ganz sinnvoll sein :danke_ATDE: muss ich mir mal genauer anschauen.

    Also ich hab aktuell das Script von meigrafd im einsatz, da mir das am verständlichsten ist :) und das wird auch jede nacht um 3 per cronjob ausgeführt und schickt mir dann die namen der gelöschten dateien per Pushalot.com aufs handy :) nur leider werden die dateien irgendwie nicht gelöscht... kann es sein das der rm befehl per cronjob nicht funktioniert, weil er ist in dem Script nicht mehr auskommentiert:huh:

    Viele Grüße

    Einmal editiert, zuletzt von LJ Jojo (18. Mai 2014 um 17:57)


  • ... dazwischen sind von tests aber immer wieder Dateien, die dann z.B. so heißen:

    Code
    2014-04-22-13-21-weather.xml

    Wenn diese ungewollten Dateien nur bei Tests entstehen, könntest Du ja beim Aufruf Deines Scripts einen Parameter dafür verwenden und dann solche Dateien in ein anderes Verzeichnis (Testverzeichnis) schreiben lassen. Dann brauchst Du diese nachträgliche Prozedur gar nicht.

    Gruß, mmi


  • Über welchen Benutzer lässt du das Script denn laufen? ggf hat der kein Recht die Dateien zu löschen :huh:

    ja per Cronjob. und da kommt man ja nur per

    Code
    sudo crontab -e

    rein.
    Keine Ahnung was das dann für ein benutzer ist.

    Grüße

    • Offizieller Beitrag

    man kommt auch per

    Code
    crontab -e

    ran, dies wäre dann der cronjob für jeweils akuellen user (meistens pi). per sudo läuft der job unter dem user root, welcher eigentlich alles darf.

    Der Unterschied zwischen Genie und Wahnsinn definiert sich im Erfolg.

  • "Eigentlich" :D Es sei denn die Dateirechte verbieten es, sondern erlauben es nur dem Benutzer der die Datei erzeugt hat.

    Kann es vielleicht sein dass das Lösch-Script zu spät ausgeführt wird? Wenn sowohl das erzeugen als auch das löschen um 03:00 ausgeführt wird, könnte es sein das beim ausführen des lösch-Scripts noch keine Dateien zum löschen vorhanden sind...
    Poste mal bitte alle Crontabeinträge die sowohl das Erzeugen/Sammeln als auch das Löschen betreffen

  • also ich hab das jetzt mal so ausprobiert, indem ich jetzt zuerst (ohne sudo) per

    Code
    touch 2014-07-22-31-23-weather.xml


    eine neue Datei hinzugefügt hab.
    Dann bin ich mit

    Code
    sudo -i

    in den Adminbereich (?!) und dort per

    Code
    cd Cronjobs

    in den Ordner wo die ganzen Scripte liegen gegangen. Dort hab ich dann einfach das Script per

    Code
    ./weatherRmTests.sh

    ausgeführt (wurde natürlich vorher schon mit

    Code
    chmod +x

    ausführbar gemacht.
    Und wieder wurde angezeigt, dass die Dateien gelöscht wurden und sie waren noch da.
    (Also die vorher erstellte Datei und das Script w2db.sh, welches die Dateien in die db eingetragen hat.)
    Und das Script zum runterladen wird auch um 3 Uhr ausgeführt (da alle 15min). Aber die Datei sollte ja dann nicht gelöscht werden, da sie ja auf -00-weather.xml endet.

    ....
    mir ist aber grad eben eine Idee gekommen:
    Kann es sein, dass ich bei

    Code
    rm -f $file


    noch den Pfad mit angeben muss, also eine Art

    Code
    rm -f $CleanDir$file


    ? Ich warte mal zuerst eine Antwort ab, da ich leider z.Z. noch kein NAS hab um die Daten zu backupen :/

    Viele Grüße

  • Führ mal bitte folgendes aus und poste die Ausgabe in CODE: bash -x weatherRmTests.sh


    PS: Aber Ja, das könnte helfen ;) Wenn allerdings $CleanDir ohne ' / ' am Ende gesetzt wurde müsste es rm -f $CleanDir/$file lauten

  • Also die ausgaben bei bash -x waren durch die for-Schleife durch 3000 Dateien doch etwas größer und mit

    Code
    bash -x weatherRmTests.sh > /mnt/fritz.nas/ausgabe.txt


    hat er nur die Standardausgabe reingeschrieben, also nicht die extras von bash -x.

    Aber mit dem ganzen Pfad hat es geholfen :) alles unnötige ist gelöscht :)

    Danke :)

  • Dann bitte nicht vergessen den Thread hier als "Erledigt" zu markieren


    PS: Solch eine Umleitung müsste in diesem Fall so lauten:

    Code
    bash -x weatherRmTests.sh > /mnt/fritz.nas/ausgabe.txt 2>&1

    Das leitet den stderr Kanal auf den stdout Kanal um (stderr = 2 , stdout = 1). Siehe dazu auch: http://wiki.ubuntuusers.de/Shell/Umleitungen

Jetzt mitmachen!

Du hast noch kein Benutzerkonto auf unserer Seite? Registriere dich kostenlos und nimm an unserer Community teil!