vuser: access_log

Sers,

ich beschäftige mich grade mit dem Thema access_log und deren Auswertungsmöglichkeiten bzw. weis ich ja genau was ich will.
Ich habe das LogFormat der access_log so umgebaut, dass ich mit einem PHP Script rein theoretisch alles exploden kann und ich es getrennt von einander in eine DB einlesen könnte..
jetzt kommt auch schon mein Problem:

So wies ausschaut archiviert ein Script jede KW die access_log.
Ich würde mit meinem script aber folgender maßen her gehen:

1. $file = file("access_log");
2. access_log leeren! (nicht löschen sondern leeren)
3. foreach($file as $line) -> exploden und in db speichern

und das in einem bestimmten intervall zb. jede stunde wiederholen (je nach dem wie aktuell man es haben möchte)

was ist aber jetzt wenn ich grade das script ausführe und das andere script möchte archivieren?

und überhaupt doof - der archiviert dann leere dateien...

kann ich nicht irgendwo an meinem vserver einstellen, dass ich gerne eine 2. paralele access_log_for_statisics geschrieben wird? und die normale access_log läuft ganz normal weiter? quasi als doppelter boden!

Außerdem: Könnte mal irgendjemand meine Liste hier ergänzen?
%V:#: = muss drin stehen! mehr hab ich auch nicht rausgefunden :-|
%h = IP-Adresse (Host)
%t = Time ( Gibts das auch als Timestamp? <----- nice2have! )
%l = ?
%u = User (.htaccess)
%t = Time
%r = File
%s = 200/404/303/... (wie nennt man das nochmal :D ? )
%b = ?

danke vuser

  1. Hi

    %s = 200/404/303/... (wie nennt man das nochmal :D ? )

    HTTP-Statuscode

    mfg
    Genie

  2. Hello,

    1. $file = file("access_log");
    2. access_log leeren! (nicht löschen sondern leeren)
    3. foreach($file as $line) -> exploden und in db speichern

    Da läuft über einen CronJob das Programm LogRotate. Musste mal nach suchen, wie sich das bezüglich der Groß-/Kleinschreibung wirklich schreibt.

    Das ist aus dem von Dir genannten Grund auch gar nicht so unkritisch.
    Der Apache hält nämlich ein Handle auf die Log-Datei.
    Das darf man ihm auch nicht wegnehmen, oder kaputtmachen, sonst logged er nicht mehr weiter.
    Es gibt aber auch keinen Fehler, wenn man ihm die Datei wegnimmt. Die weiteren Logbucheinträge landen dann einach im dev NUL

    Wie logrotate das nun so genau macht, habe ich leider auch noch nicht rausgefunden, bzw. war zu faul dazu, habe es damals einfach aus dem Cron-Job rausgenommen...

    Ich nehme an, dass Logrotate die Datei im Append-Modus hält.
    Dann kann man sie gleichzeitig auslesen.
    Zu untersichenm, wie aber genau der Sperrmechanismus funktioniert, habe ich noch auf dem Zettel.
    Ich stelle mir das so vor:

    zweiter Prozess setzt sich auf die Datei
      Sperrt die Datei mit soft-read-lock
      liest sie aus
      kürzt sie auf 0
      gibt sie wieder frei

    dann müsste logrotate auch mit soft-lock (advisory lock) arbeiten
      die Datei exclusiv sperren
      append ausführen
      die Datei wieder freigeben

    Und  der Append-Mechanismus müsste Rücksicht auf die aktuelle Länge der Datei nehmen.

    Wenn da man nicht noch was anderes dahintersteckt?
    Z.B. dass Appends aus verschiedenen Prozessen automatisch serialisiert werden?
    Wäre zumindest denkbar. Das hat ja schließlich schon funktioniert, als man sich über Locking noch keine weiteren Gedanken gemacht hat.

    Harzliche Grüße vom Berg
    http://www.annerschbarrich.de

    Tom

    --
    Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
    Nur selber lernen macht schlau

    1. uff! da hab ich jetzt nur grob verstanden was du meinst :)
      Ich hätte noch nen anderen Ansatz:

      • access_log auslesen
      • stelle merken biswohin ausgelsen wurde in form von Position des Zeigers oder so ähnlich und dann wie gehabt

      ist nur die Frage wie man das handled.

      vuser

      1. Hello,

        Ich hätte noch nen anderen Ansatz:

        • access_log auslesen
        • stelle merken biswohin ausgelsen wurde in form von Position des Zeigers oder so ähnlich und dann wie gehabt

        Das hat ja keinen Zweck, weil die Datei dann doch immer länger wird.
        Es geht ja darum, die vorhandenen Zeilen zu sichern und auszuwerten und dann zu beseitigen, damm das Log nicht über alle Grenzen wächst.

        Wenn ich Zeit finde, probiere ich das bezüglich append mal aus.
        Der Prozess, der die Datei im Append-Modus geöffnet hat, darf den Dateizeiger jedenfalls nicht mehr selber bewegen. Das hat in alten PHP-Versionen noch funktioniert, ist aber mWn inzwischen geändert.

        Harzliche Grüße vom Berg
        http://www.annerschbarrich.de

        Tom

        --
        Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
        Nur selber lernen macht schlau

        1. ja ich hab mich doof ausgedrückt..

          wenn ich die access_log immer von position x bis zum ende auslese und mir die neue position merke, weiss ich bis wo hin ich daten gespeichert habe und kann das immer wieder wiederholen.

          Ich finde nur keinen weg VON positon auszulesen. Das BIS ist kein Problem.

          die access_log wir doch dann nach wie vor archiviert!

          vuser

          1. Hello,

            ja ich hab mich doof ausgedrückt..

            wenn ich die access_log immer von position x bis zum ende auslese und mir die neue position merke, weiss ich bis wo hin ich daten gespeichert habe und kann das immer wieder wiederholen.

            Ich finde nur keinen weg VON positon auszulesen. Das BIS ist kein Problem.

            die access_log wir doch dann nach wie vor archiviert!

            Ach so...
            Du willst das nicht neu machen, sondern nur was reinschmuddeln.

            Das kann dann aber in die Hose gehen, wenn dir logrotate zuvorkommt oder dazwischenhaut.
            Du müsstest dann besser versuchen, das Trigger-Script für logrotate zu finden, und dort Deine private Auswertung noch reinbauen.

            Jedenfalls könnten Die sonst Daten "unterschlagen" werden.

            Das Lesen von einer Dateiposition macht man, indem man den Dateizeiger bis dahin vorlaufen lässt.

            fseek()  http://www.php.net/manual/en/function.fseek.php

            Wenn Du dein Format vernünftig eingestellt hast, dann kannst Du mit
            fgetcsv()  http://www.php.net/manual/en/function.fgetcsv.php
            die Zeilen auslesen. Das hält ja immer hinter einem "Zeilenende" an.
            Das machst Du solange nicht
            feof()  http://www.php.net/manual/en/function.feof.php
            Nach dem Ende merksts Du dir dann die Stelle in der Datei mittels
            ftell() http://www.php.net/manual/en/function.ftell.php

            Den Wert musst Du Dir irgendwo merken.
            Außerdem musst Du Dir merken, welche Version der Datei es ist.
            Da habe ich noch keine Vorstellung, wie man das herausbekommen soll, außer über den Inhalt.

            Also zuerst die erste Zeiel der Datei auslesen und auswerten
            Wenn deren Datum und Uhrzeit schon in Deiner Kontrollliste stehen, vorspulen mit fseek() bis zur gemerkten Stelle (denk an das n-1 bzw. n+1-Problem...) und bis zum Ende auslesen.
            In der Kontrolldatei eintragen, dass die Datei, die mit xyz anfängt, nun bis Stelle Z gelesen ist.

            So könnte es gehen.

            Kritisch ist nur die Phase, wenn noch logged wurde, Du aber noch nicht gelesen hast und logrotate tätig wird. Dann fehlen Dir ggf. etliche Datensätze.
            Du solltest also dafür sorgen, dass direkt davor Dein Script nochmal ausgeführt wird.

            Die Dateioperationen als solche musst Du so kurz wie möglich halten, damit Du das System nicht aufhältst. Auswerten kannst Du, wenn alles wieder freigegeben ist.

            Und denk an die Sperren für Deinen Prozess.

            Harzliche Grüße vom Berg
            http://www.annerschbarrich.de

            Tom

            --
            Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
            Nur selber lernen macht schlau

            1. Oh mann,

              so hab ich mir das echt nicht vorgestellt. Ich komm durch den kram hier echt in Bedrängnis. Ostern kann ich sowieso vergessen :(

              Hab grad mal versucht auf die Datei zu zugreifen da fängt auch schon die SAFE MODE an zu meckern. Soll ich die jetzt ganz ausschalten oder liegt das dadran das auf die Datei ständig zugegriffen wird?

              Du müsstest dann besser versuchen, das Trigger-Script für logrotate zu finden, und dort Deine private Auswertung noch reinbauen.

              Und das finde ich ums verecken nicht..
              Das logrotate Script war nicht schwer zu finden, aber das ist ja nur für die archivierung zuständig soweit ich das jetzt verstanden hab.

              Jedenfalls könnten Die sonst Daten "unterschlagen" werden.

              Ja klar. Ich dachte auch dadran die access_log vor oder nach dem jeweiligen logging-vorgang zu kopieren um "in ruhe" mit der kopierten file zu arbeiten.

              Ich bin echt ratlos!
              vuser

              1. Hello,

                Hab grad mal versucht auf die Datei zu zugreifen da fängt auch schon der SAFE MODE an zu meckern. Soll ich die jetzt ganz ausschalten oder liegt das dadran das auf die Datei ständig zugegriffen wird?

                Wenn es sich um Deinen Server handelt, und da niemand anderes drauf herumhampelt, dann schalte ihn ab. Wenn er aber von Mehreren (Fremden) genutzt wird, kann man es nicht in drei Sätzen erklären, was zu tun ist.

                Bei mir sieht es z.B. so aus:

                :/etc/cron.daily #>ls -la
                total 24
                drwxr-xr-x    2 root     root         4096 Feb 13  2003 .
                drwxr-x--x   31 root     root         4096 Mar 29 11:48 ..
                -rwxr-xr-x    1 root     root           51 Jun 23  2002 logrotate
                -rwxr-xr-x    1 root     root          418 Sep  3  2002 makewhatis.cron
                -rwxr-xr-x    1 root     root          104 Sep  4  2002 rpm
                -rwxr-xr-x    1 root     root          132 Jun 24  2002 slocate.cron

                und mit 'man' bekommt Du noch mehr Info (auch ohne Google)

                :/usr/sbin #>man crond
                CRON(8)                                                                CRON(8)

                NAME
                       cron - daemon to execute scheduled commands (Vixie Cron)

                SYNOPSIS
                       cron

                DESCRIPTION
                       Cron  should  be started from /etc/rc or /etc/rc.local.  It will return
                       immediately, so you don't need to start it with '&'.

                Cron searches /var/spool/cron for crontab files which are  named  after
                       accounts  in  /etc/passwd; crontabs found are loaded into memory.  Cron
                       also searches for /etc/crontab and the files in the /etc/cron.d/ direc-
                       tory,  which  are  in  a  different format (see crontab(5)).  Cron then
                       wakes up every minute, examining all  stored  crontabs,  checking  each
                       command to see if it should be run in the current minute.  When execut-
                       ing commands, any output is mailed to the owner of the crontab  (or  to
                       the  user  named  in the MAILTO environment variable in the crontab, if
                       such exists).

                Additionally, cron checks each minute to see if its  spool  directory's
                       modtime  (or  the  modtime on /etc/crontab) has changed, and if it has,
                       cron will then examine the modtime on all  crontabs  and  reload  those
                       which have changed.  Thus cron need not be restarted whenever a crontab
                       file is modified.  Note that the Crontab(1) command updates the modtime
                       of the spool directory whenever it changes a crontab.

                SEE ALSO
                       crontab(1), crontab(5)

                AUTHOR
                       Paul Vixie paul@vix.com

                4th Berkeley Distribution      20 December 1993                        CRON(8)

                In /etc/crontab stehen die für den cron-daemon wesentlichen Angaben

                SHELL=/bin/bash
                PATH=/sbin:/bin:/usr/sbin:/usr/bin
                MAILTO=root
                HOME=/

                run-parts

                01 * * * * root run-parts /etc/cron.hourly
                02 4 * * * root run-parts /etc/cron.daily
                22 4 * * 0 root run-parts /etc/cron.weekly
                42 4 1 * * root run-parts /etc/cron.monthly

                Harzliche Grüße vom Berg
                http://www.annerschbarrich.de

                Tom

                --
                Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
                Nur selber lernen macht schlau

    2. Ich grüsse den Cosmos,

      Wie logrotate das nun so genau macht, habe ich leider auch noch nicht rausgefunden, bzw. war zu faul dazu, habe es damals einfach aus dem Cron-Job rausgenommen...

      /var/log/apache2/*.log {
              weekly
              missingok
              rotate 52
              compress
              delaycompress
              notifempty
              create 640 root adm
              sharedscripts
              postrotate
                      if [ -f /var/run/apache2.pid ]; then
                              /etc/init.d/apache2 restart > /dev/null
                      fi
              endscript
      }

      Der Startet nach dem Rotieren und Packen einfach den Apache neu. Dadurch werden die Logs wieder neu angelegt.

      Möge das "Self" mit euch sein

      --
      Neulich dachte ich mir, einmal S/M ausprobieren wäre eine tolle Erfahrung. Also hab ich Windows gebootet ...
      ie:{ br:> fl:| va:| ls:& fo:{ rl:( n4:{ de:] ss:) ch:? js:| mo:) sh:( zu:)
      1. Hello,

        Wie logrotate das nun so genau macht, habe ich leider auch noch nicht rausgefunden, bzw. war zu faul dazu, habe es damals einfach aus dem Cron-Job rausgenommen...

        Der Startet nach dem Rotieren und Packen einfach den Apache neu. Dadurch werden die Logs wieder neu angelegt.

        Danke für den Background...
        Dann könnte das andere Tool das genauso machen.
        Könnten aber trotzdem immer noch einige Log-Einträge verloren gehen, wenn ich das richtig sehe.

        Vielleicht wäre es sowieso insgesamt erquicklicher gleich

        http://bitbrook.de/software/mod_log_mysql/

        zu verwenden. Dann kann man sich das Logrotate, das Neustarten und auch das Schreiben eines Reinbastelscriptes sparen...

        Harzliche Grüße vom Berg
        http://www.annerschbarrich.de

        Tom

        --
        Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
        Nur selber lernen macht schlau

        1. Ich grüsse den Cosmos,

          Vielleicht wäre es sowieso insgesamt erquicklicher gleich
             http://bitbrook.de/software/mod_log_mysql/
          zu verwenden.

          Entweder das, oder, wie oben erwähnt, das Log in ein Script pipen und direkt verarbeiten. Was jetzt performanter ist, weiss ich nicht. Ich glaub, um die Performance zu testen, ist eine Webseite mit vielen tausend Besuchern nötig ;)

          Möge das "Self" mit euch sein

          --
          Neulich dachte ich mir, einmal S/M ausprobieren wäre eine tolle Erfahrung. Also hab ich Windows gebootet ...
          ie:{ br:> fl:| va:| ls:& fo:{ rl:( n4:{ de:] ss:) ch:? js:| mo:) sh:( zu:)
  3. Ich grüsse den Cosmos,

    was ist aber jetzt wenn ich grade das script ausführe und das andere script möchte archivieren?

    Mal ne Alternative zum Logfile. Der Apache unterstützt Logfiles per Pipe. Das heiosst, die kannst das Logfile direkt in eine Scriptdatei schreiben lassen (pipen) und dann sofort auswerten und in die Datenbank schreiben.
    Confixx hat so das interne Rotieren der Logfiles gelöst. Obs Plesk auch macht, weiss ich nicht, da ich mittlerweile auf eine Serveradministration umgestiegen bin, die einfach, schnell und kostenlos ist.

    Nur so als Anregung, weil es den Umweg über ein Logfile und eine ressourcenfressende Auswertung unnötig macht.

    Möge das "Self" mit euch sein

    --
    Neulich dachte ich mir, einmal S/M ausprobieren wäre eine tolle Erfahrung. Also hab ich Windows gebootet ...
    ie:{ br:> fl:| va:| ls:& fo:{ rl:( n4:{ de:] ss:) ch:? js:| mo:) sh:( zu:)