I'm trying to trigger a beep on the PC speaker for every unique visitor of a website.
After some brainstorming, it seemed to be possible with one line:
for e in `ssh me@mymachine "tail -n 1 -f /var/log/apache2/test.log | awk '{print $1}' | uniq"`; do beep; done
However uniq doesn't output anything as long as stdin is open (seems to wait for EOF). The same goes for the for loop. If I remove the uniq from the chain, I still get no output with tail keeping the pipe open.
This seems not to be because of buffering. Even if I write >100.000 lines into the test file with this command running, there's no output on the other end.
Is there a way to get that working without completely killing the beauty (simplicity) of the solution?
Update
I solved the first part. uniq is unblocked by prefixing the tail command with stdbuf -oL -eL
(see https://unix.stackexchange.com/a/25378/109296).
The same doesn't work for the loop.
Update 2
I got it working - but not exactly according to my spec and with 2 lines:
while [ 1 -eq 1 ]; do ssh root@speedy "stdbuf -oL -eL tail -n 1 -f /var/log/apache2/www.access.log | stdbuf -oL -eL grep 'GET / '"; sleep 60; done > www.log
awk '{print $1}'
is missing because it didn't work inside this construct (just passed through the whole line). I don't know why. But I can live without, because anyway
uniq
turned out not to be so useful after all, because it only looks at adjacent lines, which means that the requests patterns ip1, ip2, ip1 would still let ip1 through twice.
uniq -u
would do what I expect, but it has the same problem like sort
: doesn't output anything as long as stdin is open (not even with stdbuf -oL
.
This command just writes all requests for the base URL (/) to another file. I wrapped it into a loop (and wait) in order to have it automatically retry if for some reason the pipe or connection interrupts.
while inotifywait -e modify www.log; do beep -f 250; done
makes the sound! I could not get the bash for loop to process line by line unbuffered, also tried while read
with the same result.
Thus I gave up and went on with inotifywait
which however means that I need an intermediate file (maybe a named pipe would also work, didn't try. Doesn't really make a difference for me).
I'd still be thankful to contributions which help to make the filtering of unique visitors work (without escalating complexity).
This will be a nice surprise for my team members when they return to the office :-)
I plan to extend this notification system to monitor several events, using different audio frequencies. That's the best job I've found so far for an old server collecting dust...
ar
.tsort
could be worthwhile as well.MAILFILE=/var/log/apache2/www.access.log%$(beep)
which will get the shell to watch the file for modification and expand the%
user-specified message every time it does.