################################################################################ # # # ############################################################################ # # # Title : Data::Logger.pm # # # # Description : A super simple logger, you don't actually need to tell it # # # # a single thing. # # # # Coded by : Justin "I'm Really Tired Now" Lee # # # # Version : 0.5.0-RC0 # # # # Date : Monday, March 3, 2008 # # # # License : GNU General Public License v.2 # # # # Copyright (C) 2008 Justin Lee # # # ############################################################################ # # # # ############################################################################ # # # This program is free software; you can redistribute it and/or # # # # modify it under the terms of the GNU General Public License version 2 # # # # as published by the Free Software Foundation. # # # # # # # # This program is distributed in the hope that it will be useful, # # # # but WITHOUT ANY WARRANTY; without even the implied warranty of # # # # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # # # # GNU General Public License for more details. # # # # # # # # You should have received a copy of the GNU General Public License # # # # along with this program; if not, write to the Free Software # # # # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # # # # 02110-1301, USA. Or, see: # # # ############################################################################ # # # ################################################################################ package Data::Logger; use strict; use warnings; our(@ISA,@EXPORT_OK); BEGIN { require Exporter; @ISA = qw(Exporter); @EXPORT_OK = qw( _skew ); } use Carp; use FileHandle; use File::Basename; use File::Find; use Class::Date qw(now); ####################################### # ## # ################################ ### START OF THE OBJECT INTERFACE sub new { my $class = shift; my $self = { _setup(@_) }; return if exists $self->{ERR}; return bless $self, $class; } ############################# # ## # ###################### ### THE _SETUP FUNCTION sub _setup { my $stp = shift; my %slf = ( stamp => '[%h:%m:%s] (%L)'."\t".'- {[%F]}{ %A}{ [ERROR] %E}', level => 2, lpath => _skew(@{[ fileparse($main::0) ]}[1],'logs'), token => { _have_a_toke_man() } ); unless (defined $stp) { $stp = {}; } unless (ref $stp eq 'HASH') { return ( ERR => 1 ); } if (defined $stp->{Level}) { $slf{level} = int($stp->{Level}); } # I don't even trust my mom if (defined $stp->{String}) { $slf{stamp} = $stp->{String}; } if (defined $stp->{Sectional}) { $slf{token}->{S}->{toe} = 1; } if (defined $stp->{Directory}) { $slf{lpath} = _skew($stp->{Directory}); } if (defined $stp->{To_Keep}) { unless(_housekeep($slf{lpath},int($stp->{To_Keep}))) { return ( ERR => 1 ); } } unless (-d $slf{lpath}) { unless(mkdir($slf{lpath},0777)) { return ( ERR => 1 ); } } if (defined $stp->{Dated_Directories}) { unless (defined $stp->{File_Name}) { $stp->{File_Name} = '%h;%m;%s.log'; } $slf{lpath} = _skew($slf{lpath},_decode('%Y-%M-%D')); unless(mkdir($slf{lpath},0777)) { return ( ERR => 1 ); } } $stp->{File_Name} = defined $stp->{File_Name} ? _decode($stp->{File_Name}) : _decode('%Y-%M-%D %h;%m;%s.log'); $slf{lpath} = _skew($slf{lpath},$stp->{File_Name}); $slf{handle} = new FileHandle; $slf{handle}->open($slf{lpath},'>'); defined($slf{handle}) or return ( ERR => 1 ); return %slf; } ################################## # ## # ########################### ### RANDOM AWESOME FUNCTIONS sub _skew { #murder stupid paths my $skew = join('/',@_); $skew =~ s/(?:\\|\/)+/\//go; return $skew; } ######################### # ## # ################## ### TOKEN FUNCTIONS sub _decode { my $smk = shift; $smk =~ s/(?{$tak} and $tik->{$tak}->{toe}) { # exists & active if (defined $tik->{$tok}->{val}) { # defined if (ref $tik->{$tok}->{val} eq 'CODE') { return &{$tik->{$tok}->{val}}; } else { return $tik->{$tok}->{val}; } } else { return '?'; # active, but no value (suggests problem) } } else { return ''; # doesn't exist or not active } } sub _mk_dt { my $gm = shift or return; return sub { my %dt; @dt{ qw( year month day hour minute second ) } = split(/(?:\s|:|-|;)+/,now); return scalar $dt{lc($gm)}; } } sub _have_a_toke_man { return ( A => { # message val => '', toe => 1 }, F => { # function title val => '', toe => 0 }, S => { # script name val => basename($main::0), #'super cool script.pl', #'fake name', toe => 1 }, L => { # log level val => '', toe => 1 }, E => { # error message val => '', toe => 0 }, Y => { val => _mk_dt('year'), toe => 1 }, M => { val => _mk_dt('month'), toe => 1 }, LETS_GET_DRUGS => { val => 'zeke', toe => 0 }, D => { val => _mk_dt('day'), toe => 1 }, h => { val => _mk_dt('hour'), toe => 1 }, m => { val => _mk_dt('minute'), toe => 1 }, s => { val => _mk_dt('second'), toe => 1 } ) } ################################ # ## # ######################### ### CORE LOGGING FUNCTIONS sub print { } ########################## # ## # ################### ### OBJECT FUNCTIONS sub close { my $log = shift; $log->print({ MSG => shift, LVL => 'INFO' }); $log->{handle}->close; } sub log { #alias for note() note(@_); } sub note { my $log = shift; $log->print({ MSG => shift, LVL => 'INFO' }); } sub debug { my $log = shift; $log->print({ MSG => shift, LVL => 'DEBUG' }); } sub warn { my $log = shift; $log->print({ MSG => shift, LVL => 'WARN', ERR => shift }); carp ''; } sub die { my $log = shift; $log->print({ MSG => shift, LVL => 'FATAL', ERR => shift }); croak ''; } 1;