2
#------------------------------------------------------------------------------
3
# Free realtime web server logfile analyzer to show advanced web statistics.
4
# Works from command line or as a CGI. You must use this script as often as
5
# necessary from your scheduler to update your statistics and from command
6
# line or a browser to read report results.
7
# See AWStats documentation (in docs/ directory) for all setup instructions.
8
#------------------------------------------------------------------------------
9
# $Revision: 1.704 $ - $Author: eldy $ - $Date: 2004/01/25 15:24:13 $
13
#use warnings; # Must be used in test mode only. This reduce a little process speed
14
#use diagnostics; # Must be used in test mode only. This reduce a lot of process speed
15
use strict;no strict "refs";
16
use Time::Local; # use Time::Local 'timelocal_nocheck' is faster but not supported by all Time::Local modules
20
#------------------------------------------------------------------------------
22
#------------------------------------------------------------------------------
23
use vars qw/ $REVISION $VERSION /;
24
$REVISION='$Revision: 1.704 $'; $REVISION =~ /\s(.*)\s/; $REVISION=$1;
25
$VERSION="6.0 (build $REVISION)";
27
# ----- Constants -----
29
$DEBUGFORCED $NBOFLINESFORBENCHMARK $FRAMEWIDTH $NBOFLASTUPDATELOOKUPTOSAVE
30
$LIMITFLUSH $NEWDAYVISITTIMEOUT $VISITTIMEOUT $NOTSORTEDRECORDTOLERANCE $MAXDIFFEXTRA
31
$WIDTHCOLICON $TOOLTIPON
34
$DEBUGFORCED=0; # Force debug level to log lesser level into debug.log file (Keep this value to 0)
35
$NBOFLINESFORBENCHMARK=8192; # Benchmark info are printing every NBOFLINESFORBENCHMARK lines (Must be a power of 2)
36
$FRAMEWIDTH=240; # Width of left frame when UseFramesWhenCGI is on
37
$NBOFLASTUPDATELOOKUPTOSAVE=500; # Nb of records to save in DNS last update cache file
38
$LIMITFLUSH=5000; # Nb of records in data arrays after how we need to flush data on disk
39
$NEWDAYVISITTIMEOUT=764041; # Delay between 01-23:59:59 and 02-00:00:00
40
$VISITTIMEOUT=10000; # Laps of time to consider a page load as a new visit. 10000 = 1 hour (Default = 10000)
41
$NOTSORTEDRECORDTOLERANCE=10000; # Laps of time to accept a record if not in correct order. 10000 = 1 hour (Default = 10000)
44
$TOOLTIPON=0; # Tooltips plugin loaded
45
# ----- Running variables -----
49
$DebugResetDone $DNSLookupAlreadyDone
50
$RunAsCli $UpdateFor $HeaderHTTPComplete $HeaderHTMLComplete
51
$LastLine $LastLineNumber $LastLineOffset $LastLineChecksum $LastUpdate
54
$TotalUnique $TotalVisits $TotalHostsKnown $TotalHostsUnknown
55
$TotalPages $TotalHits $TotalBytes
56
$TotalNotViewedPages $TotalNotViewedHits $TotalNotViewedBytes
57
$TotalEntries $TotalExits $TotalBytesPages $TotalDifferentPages
58
$TotalKeyphrases $TotalKeywords $TotalDifferentKeyphrases $TotalDifferentKeywords
59
$TotalSearchEnginesPages $TotalSearchEnginesHits $TotalRefererPages $TotalRefererHits $TotalDifferentSearchEngines $TotalDifferentReferer
60
$FrameName $Center $FileConfig $FileSuffix $Host $DayRequired $MonthRequired $YearRequired
61
$QueryString $SiteConfig $StaticLinks $PageCode $PageDir $PerlParsingFormat
62
$SiteToAnalyze $SiteToAnalyzeWithoutwww $UserAgent
63
$pos_vh $pos_host $pos_logname $pos_date $pos_tz $pos_method $pos_url $pos_code $pos_size
64
$pos_referer $pos_agent $pos_query $pos_gzipin $pos_gzipout $pos_compratio
65
$pos_cluster $pos_emails $pos_emailr $pos_hostr
67
$DIR=$PROG=$Extension='';
68
$Debug = $ShowSteps = 0;
69
$DebugResetDone = $DNSLookupAlreadyDone = 0;
70
$RunAsCli = $UpdateFor = $HeaderHTTPComplete = $HeaderHTMLComplete = 0;
71
$LastLine = $LastLineNumber = $LastLineOffset = $LastLineChecksum = $LastUpdate = 0;
74
$TotalUnique = $TotalVisits = $TotalHostsKnown = $TotalHostsUnknown = 0;
75
$TotalPages = $TotalHits = $TotalBytes = 0;
76
$TotalNotViewedPages = $TotalNotViewedHits = $TotalNotViewedBytes = 0;
77
$TotalEntries = $TotalExits = $TotalBytesPages = $TotalDifferentPages = 0;
78
$TotalKeyphrases = $TotalKeywords = $TotalDifferentKeyphrases = $TotalDifferentKeywords = 0;
79
$TotalSearchEnginesPages = $TotalSearchEnginesHits = $TotalRefererPages = $TotalRefererHits = $TotalDifferentSearchEngines = $TotalDifferentReferer = 0;
80
($FrameName, $Center, $FileConfig, $FileSuffix, $Host, $DayRequired, $MonthRequired, $YearRequired,
81
$QueryString, $SiteConfig, $StaticLinks, $PageCode, $PageDir, $PerlParsingFormat,
82
$SiteToAnalyze, $SiteToAnalyzeWithoutwww, $UserAgent)=
83
('','','','','','','','','','','','','','','','','');
84
$pos_vh = $pos_host = $pos_logname = $pos_date = $pos_tz = $pos_method = $pos_url = $pos_code = $pos_size = -1;
85
$pos_referer = $pos_agent = $pos_query = $pos_gzipin = $pos_gzipout = $pos_compratio = -1;
86
$pos_cluster = $pos_emails = $pos_emailr = $pos_hostr = -1;
87
# ----- Plugins variable -----
88
use vars qw/ %PluginsLoaded $PluginDir /;
91
# ----- Time vars -----
94
$nowtime $tomorrowtime
95
$nowweekofmonth $nowweekofyear $nowdaymod $nowsmallyear
96
$nowsec $nowmin $nowhour $nowday $nowmonth $nowyear $nowwday $nowyday $nowns
97
$StartSeconds $StartMicroseconds
99
$StartSeconds=$StartMicroseconds=0;
100
# ----- Variables for config file reading -----
102
$FoundNotPageList $FoundValidHTTPCodes $FoundValidSMTPCodes
104
$FoundNotPageList=$FoundValidHTTPCodes=$FoundValidSMTPCodes=0;
105
# ----- Config file variables -----
109
$DNSLastUpdateCacheFile
114
$MaxLengthOfStoredURL
121
$DNSStaticCacheFile='dnscache.txt';
122
$DNSLastUpdateCacheFile='dnscachelastupdate.txt';
123
$MiscTrackerUrl='/js/awstats_misc_tracker.js';
125
$MaxRowsInHTMLOutput=1000;
126
$MaxLengthOfShownURL=64;
127
$MaxLengthOfStoredURL=256; # Note: Apache LimitRequestLine is default to 8190
128
$MaxLengthOfStoredUA=256;
129
%BarPng=('vv'=>'vv.png','vu'=>'vu.png','hu'=>'hu.png','vp'=>'vp.png','hp'=>'hp.png',
130
'he'=>'he.png','hx'=>'hx.png','vh'=>'vh.png','hh'=>'hh.png','vk'=>'vk.png','hk'=>'hk.png');
131
$BuildReportFormat='html';
132
$BuildHistoryFormat='text';
134
$EnableLockForUpdate $DNSLookup $AllowAccessFromWebToAuthenticatedUsersOnly
135
$BarHeight $BarWidth $CreateDirDataIfNotExists $KeepBackupOfHistoricFiles
136
$NbOfLinesParsed $NbOfLinesDropped $NbOfLinesCorrupted $NbOfOldLines $NbOfNewLines
137
$NbOfLinesShowsteps $NewLinePhase $NbOfLinesForCorruptedLog $PurgeLogFile
138
$ShowDropped $ShowCorrupted $ShowUnknownOrigin $ShowLinksToWhoIs
139
$ShowAuthenticatedUsers $ShowFileSizesStats $ShowScreenSizeStats $ShowSMTPErrorsStats
140
$ShowEMailSenders $ShowEMailReceivers $ShowWormsStats $ShowClusterStats
141
$AuthenticatedUsersNotCaseSensitive
142
$Expires $UpdateStats $MigrateStats $URLNotCaseSensitive $URLWithQuery $URLReferrerWithQuery
145
($EnableLockForUpdate, $DNSLookup, $AllowAccessFromWebToAuthenticatedUsersOnly,
146
$BarHeight, $BarWidth, $CreateDirDataIfNotExists, $KeepBackupOfHistoricFiles,
147
$NbOfLinesParsed, $NbOfLinesDropped, $NbOfLinesCorrupted, $NbOfOldLines, $NbOfNewLines,
148
$NbOfLinesShowsteps, $NewLinePhase, $NbOfLinesForCorruptedLog, $PurgeLogFile,
149
$ShowDropped, $ShowCorrupted, $ShowUnknownOrigin, $ShowLinksToWhoIs,
150
$ShowAuthenticatedUsers, $ShowFileSizesStats, $ShowScreenSizeStats, $ShowSMTPErrorsStats,
151
$ShowEMailSenders, $ShowEMailReceivers, $ShowWormsStats, $ShowClusterStats,
152
$AuthenticatedUsersNotCaseSensitive,
153
$Expires, $UpdateStats, $MigrateStats, $URLNotCaseSensitive, $URLWithQuery, $URLReferrerWithQuery,
155
(0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0);
157
$AllowToUpdateStatsFromBrowser
158
$ArchiveLogRecords $DetailedReportsOnNewWindows
159
$FirstDayOfWeek $KeyWordsNotSensitive $SaveDatabaseFilesWithPermissionsForEveryone
160
$WarningMessages $DebugMessages $ShowLinksOnUrl $UseFramesWhenCGI
161
$ShowMenu $ShowMonthStats $ShowDaysOfMonthStats $ShowDaysOfWeekStats
162
$ShowHoursStats $ShowDomainsStats $ShowHostsStats
163
$ShowRobotsStats $ShowSessionsStats $ShowPagesStats $ShowFileTypesStats
164
$ShowOSStats $ShowBrowsersStats $ShowOriginStats
165
$ShowKeyphrasesStats $ShowKeywordsStats $ShowMiscStats $ShowHTTPErrorsStats
166
$AddDataArrayMonthStats $AddDataArrayShowDaysOfMonthStats $AddDataArrayShowDaysOfWeekStats $AddDataArrayShowHoursStats
168
($AllowToUpdateStatsFromBrowser,
169
$ArchiveLogRecords, $DetailedReportsOnNewWindows,
170
$FirstDayOfWeek, $KeyWordsNotSensitive, $SaveDatabaseFilesWithPermissionsForEveryone,
171
$WarningMessages, $DebugMessages, $ShowLinksOnUrl, $UseFramesWhenCGI,
172
$ShowMenu, $ShowMonthStats, $ShowDaysOfMonthStats, $ShowDaysOfWeekStats,
173
$ShowHoursStats, $ShowDomainsStats, $ShowHostsStats,
174
$ShowRobotsStats, $ShowSessionsStats, $ShowPagesStats, $ShowFileTypesStats,
175
$ShowOSStats, $ShowBrowsersStats, $ShowOriginStats,
176
$ShowKeyphrasesStats, $ShowKeywordsStats, $ShowMiscStats, $ShowHTTPErrorsStats,
177
$AddDataArrayMonthStats, $AddDataArrayShowDaysOfMonthStats, $AddDataArrayShowDaysOfWeekStats, $AddDataArrayShowHoursStats
179
(1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1);
182
$LevelForRobotsDetection $LevelForWormsDetection $LevelForBrowsersDetection $LevelForOSDetection $LevelForRefererAnalyze
183
$LevelForFileTypesDetection $LevelForSearchEnginesDetection $LevelForKeywordsDetection
186
$LevelForRobotsDetection, $LevelForWormsDetection, $LevelForBrowsersDetection, $LevelForOSDetection, $LevelForRefererAnalyze,
187
$LevelForFileTypesDetection, $LevelForSearchEnginesDetection, $LevelForKeywordsDetection)=
190
$DirLock $DirCgi $DirConfig $DirData $DirIcons $DirLang $AWScript $ArchiveFileName
191
$AllowAccessFromWebToFollowingIPAddresses $HTMLHeadSection $HTMLEndSection $LinksToWhoIs $LinksToIPWhoIs
192
$LogFile $LogType $LogFormat $LogSeparator $Logo $LogoLink $StyleSheet $WrapperScript $SiteDomain
193
$UseHTTPSLinkForUrl $URLQuerySeparators $URLWithAnchor $ErrorMessages $ShowFlagLinks
195
($DirLock, $DirCgi, $DirConfig, $DirData, $DirIcons, $DirLang, $AWScript, $ArchiveFileName,
196
$AllowAccessFromWebToFollowingIPAddresses, $HTMLHeadSection, $HTMLEndSection, $LinksToWhoIs, $LinksToIPWhoIs,
197
$LogFile, $LogType, $LogFormat, $LogSeparator, $Logo, $LogoLink, $StyleSheet, $WrapperScript, $SiteDomain,
198
$UseHTTPSLinkForUrl, $URLQuerySeparators, $URLWithAnchor, $ErrorMessages, $ShowFlagLinks)=
199
('','','','','','','','','','','','','','','','','','','','','','','','','','','');
201
$color_Background $color_TableBG $color_TableBGRowTitle
202
$color_TableBGTitle $color_TableBorder $color_TableRowTitle $color_TableTitle
203
$color_text $color_textpercent $color_titletext $color_weekend $color_link $color_hover $color_other
204
$color_h $color_k $color_p $color_e $color_x $color_s $color_u $color_v
206
($color_Background, $color_TableBG, $color_TableBGRowTitle,
207
$color_TableBGTitle, $color_TableBorder, $color_TableRowTitle, $color_TableTitle,
208
$color_text, $color_textpercent, $color_titletext, $color_weekend, $color_link, $color_hover, $color_other,
209
$color_h, $color_k, $color_p, $color_e, $color_x, $color_s, $color_u, $color_v)=
210
('','','','','','','','','','','','','','','','','','','','','','');
211
# ---------- Init arrays --------
213
@RobotsSearchIDOrder_list1 @RobotsSearchIDOrder_list2 @RobotsSearchIDOrder_listgen
214
@SearchEnginesSearchIDOrder_list1 @SearchEnginesSearchIDOrder_list2 @SearchEnginesSearchIDOrder_listgen
215
@BrowsersSearchIDOrder @OSSearchIDOrder @WordsToExtractSearchUrl @WordsToCleanSearchUrl
217
@RobotsSearchIDOrder @SearchEnginesSearchIDOrder
219
@_time_p @_time_h @_time_k @_time_nv_p @_time_nv_h @_time_nv_k
220
@DOWIndex @fieldlib @keylist
222
@RobotsSearchIDOrder = @SearchEnginesSearchIDOrder = ();
223
@_from_p = @_from_h = ();
224
@_time_p = @_time_h = @_time_k = @_time_nv_p = @_time_nv_h = @_time_nv_k = ();
225
@DOWIndex = @fieldlib = @keylist = ();
227
@MiscListOrder %MiscListCalc
228
@OSFamily %BrowsersFamily @SessionsRange %SessionsAverage
229
%LangBrowserToLangAwstats %LangAWStatsToCountryAwstats
230
@HostAliases @AllowAccessFromWebToFollowingAuthenticatedUsers
231
@DefaultFile @SkipDNSLookupFor
232
@SkipHosts @SkipUserAgents @SkipFiles
233
@OnlyHosts @OnlyUserAgents @OnlyFiles
234
@URLWithQueryWithOnly @URLWithQueryWithout
235
@ExtraName @ExtraCondition @ExtraStatTypes @MaxNbOfExtra @MinHitExtra
236
@ExtraFirstColumnTitle @ExtraFirstColumnValues @ExtraFirstColumnFormat
237
@ExtraConditionType @ExtraConditionTypeVal
238
@ExtraFirstColumnValuesType @ExtraFirstColumnValuesTypeVal
239
@ExtraAddAverageRow @ExtraAddSumRow
242
@MiscListOrder=('AddToFavourites','JavaEnabled','DirectorSupport','FlashSupport','RealPlayerSupport','QuickTimeSupport','WindowsMediaPlayerSupport','PDFSupport');
243
%MiscListCalc=('TotalMisc'=>'','AddToFavourites'=>'u','JavaEnabled'=>'hm','DirectorSupport'=>'hm','FlashSupport'=>'hm','RealPlayerSupport'=>'hm','QuickTimeSupport'=>'hm','WindowsMediaPlayerSupport'=>'hm','PDFSupport'=>'hm');
244
@OSFamily=('win','mac');
245
#%BrowsersFamily=('msie'=>1,'netscape'=>2,'mozilla'=>3);
246
%BrowsersFamily=('msie'=>1,'netscape'=>2);
247
@SessionsRange=('0s-30s','30s-2mn','2mn-5mn','5mn-15mn','15mn-30mn','30mn-1h','1h+');
248
%SessionsAverage=('0s-30s',15,'30s-2mn',75,'2mn-5mn',210,'5mn-15mn',600,'15mn-30mn',1350,'30mn-1h',2700,'1h+',3600);
249
# Values reported by HTTP-Accept with AWStats code to use
250
%LangBrowserToLangAwstats=('sq'=>'al','ba'=>'ba','bg'=>'bg','zh-tw'=>'tw','zh'=>'cn','cz'=>'cz',
251
'da'=>'dk','nl'=>'nl','en'=>'en','et'=>'et','fi'=>'fi','fr'=>'fr',
252
'de'=>'de','el'=>'gr','hu'=>'hu','is'=>'is','in'=>'id','it'=>'it',
253
'ja'=>'jp','ko'=>'kr','lv'=>'lv','no'=>'nb','nb'=>'nb','nn'=>'nn','pl'=>'pl','pt'=>'pt','pt-br'=>'br',
254
'ro'=>'ro','ru'=>'ru','sr'=>'sr','sk'=>'sk','es'=>'es','eu'=>'es_eu','ca'=>'es_cat','sv'=>'se','tr'=>'tr','uk'=>'ua','wlk'=>'wlk');
255
%LangAWStatsToCountryAwstats=('et'=>'ee','he'=>'il');
256
@HostAliases = @AllowAccessFromWebToFollowingAuthenticatedUsers=();
257
@DefaultFile = @SkipDNSLookupFor = ();
258
@SkipHosts = @SkipUserAgents = @SkipFiles = ();
259
@OnlyHosts = @OnlyUserAgents = @OnlyFiles = ();
260
@URLWithQueryWithOnly = @URLWithQueryWithout = ();
261
@ExtraName = @ExtraCondition = @ExtraStatTypes = @MaxNbOfExtra = @MinHitExtra = ();
262
@ExtraFirstColumnTitle = @ExtraFirstColumnValues = @ExtraFirstColumnFormat = ();
263
@ExtraConditionType = @ExtraConditionTypeVal = ();
264
@ExtraFirstColumnValuesType = @ExtraFirstColumnValuesTypeVal = ();
265
@ExtraAddAverageRow = @ExtraAddSumRow = ();
267
# ---------- Init hash arrays --------
269
%BrowsersHashIDLib %BrowsersHashIcon %BrowsersHereAreGrabbers
271
%MimeHashLib %MimeHashIcon %MimeHashFamily
274
%SearchEnginesHashID %SearchEnginesHashLib %SearchEnginesKnownUrl %NotSearchEnginesKeys
275
%WormsHashID %WormsHashLib
278
%HTMLOutput %NoLoadPlugin %FilterIn %FilterEx
281
%ValidHTTPCodes %ValidSMTPCodes
282
%TrapInfosForHTTPErrorCodes %NotPageList %DayBytes %DayHits %DayPages %DayVisits
284
%ListOfYears %HistoryAlreadyFlushed %PosInFile %ValueInFile
286
%TmpDNSLookup %TmpOS %TmpRefererServer %TmpRobot %TmpBrowser %MyDNSTable
288
%HTMLOutput = %NoLoadPlugin = %FilterIn = %FilterEx = ();
289
%BadFormatWarning = ();
291
%ValidHTTPCodes = %ValidSMTPCodes = ();
292
%TrapInfosForHTTPErrorCodes=(); $TrapInfosForHTTPErrorCodes{404}=1; # TODO Add this in config file
294
%DayBytes = %DayHits = %DayPages = %DayVisits = ();
295
%MaxNbOf = %MinHit = ();
296
%ListOfYears = %HistoryAlreadyFlushed = %PosInFile = %ValueInFile = ();
297
%val = %nextval = %egal = ();
298
%TmpDNSLookup = %TmpOS = %TmpRefererServer = %TmpRobot = %TmpBrowser = %MyDNSTable = ();
301
%MonthHostsKnown %MonthHostsUnknown
302
%MonthUnique %MonthVisits
303
%MonthPages %MonthHits %MonthBytes
304
%MonthNotViewedPages %MonthNotViewedHits %MonthNotViewedBytes
305
%_session %_browser_h
306
%_domener_p %_domener_h %_domener_k %_errors_h %_errors_k
307
%_filetypes_h %_filetypes_k %_filetypes_gz_in %_filetypes_gz_out
308
%_host_p %_host_h %_host_k %_host_l %_host_s %_host_u
309
%_waithost_e %_waithost_l %_waithost_s %_waithost_u
310
%_keyphrases %_keywords %_os_h %_pagesrefs_p %_pagesrefs_h %_robot_h %_robot_k %_robot_l %_robot_r
311
%_worm_h %_worm_k %_worm_l %_login_h %_login_p %_login_k %_login_l %_screensize_h
312
%_misc_p %_misc_h %_misc_k
313
%_cluster_p %_cluster_h %_cluster_k
314
%_se_referrals_p %_se_referrals_h %_sider404_h %_referer404_h %_url_p %_url_k %_url_e %_url_x
315
%_unknownreferer_l %_unknownrefererbrowser_l
316
%_emails_h %_emails_k %_emails_l %_emailr_h %_emailr_k %_emailr_l
320
# ---------- Init Tie::hash arrays --------
321
# Didn't find a tie that increase speed
323
#use Tie::Cache::LRU;
324
#tie %_host_p, 'Tie::StdHash';
325
#tie %TmpOS, 'Tie::Cache::LRU';
328
use vars qw/ %httpcodelib %ftpcodelib %smtpcodelib /;
331
use vars qw/ @Message /;
334
'Unknown (unresolved ip)',
346
'different keywords',
357
'Never updated (See \'Build/Update\' on awstats_setup.html page)',
358
'Visitors domains/countries',
361
'different pages-url',
369
'Connect to site from',
371
'Direct address / Bookmarks',
373
'Links from an Internet Search Engine',
374
'Links from an external page (other web sites except search engines)',
375
'Links from an internal page (other page on same site)',
376
'Keyphrases used on search engines',
377
'Keywords used on search engines',
378
'Unresolved IP Address',
379
'Unknown OS (Referer field)',
380
'Required but not found URLs (HTTP code 404)',
383
'Unknown browsers (Referer field)',
386
'Robots/Spiders visitors',
387
'Free realtime logfile analyzer for advanced web statistics',
411
'dd mmm yyyy - HH:MM',
427
'Authenticated users',
434
'Compression result',
436
'different keyphrases',
440
'Links from a NewsGroup',
453
'Search Keyphrases',
454
'Search Keywords',
455
'different refering search engines',
456
'different refering sites',
458
'Other logins (and/or anonymous users)',
459
'Refering search engines',
462
'Exact value not available in "Year" view',
469
'Worm/Virus attacks',
470
'Add to favorites (estimated)',
473
'Browsers with Java support',
474
'Browsers with Macromedia Director Support',
475
'Browsers with Flash Support',
476
'Browsers with Real audio playing support',
477
'Browsers with Quictime audio playing support',
478
'Browsers with Windows Media audio playing support',
479
'Browsers with PDF support',
487
'Codes shown here gave hits or traffic "not viewed" by visitors, so they are not included in other charts.',
489
'Robots shown here gave hits or traffic "not viewed" by visitors, so they are not included in other charts.',
490
'Numbers after + are successful hits on "robots.txt" files',
491
'Worms shown here gave hits or traffic "not viewed" by visitors, so thay are not included in other charts.',
492
'Not viewed trafic is trafic generated by robots, worms or answers with special HTTP status code',
494
'Traffic not viewed',
502
#------------------------------------------------------------------------------
504
#------------------------------------------------------------------------------
506
#------------------------------------------------------------------------------
507
# Function: Write on ouput header of HTML page
509
# Input: %HTMLOutput $PluginMode $Expires $Lang $StyleSheet $HTMLHeadSection $PageCode $PageDir
510
# Output: $HeaderHTMLComplete=1
512
#------------------------------------------------------------------------------
514
my $dir=$PageDir?'right':'left';
515
if (scalar keys %HTMLOutput || $PluginMode) {
516
my $MetaRobot=0; # meta robots
518
if ($BuildReportFormat eq 'xml') {
519
if ($PageCode) { print "<?xml version=\"1.0\" encoding=\"$PageCode\"?>\n"; }
520
else { print "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n"; };
521
if ($FrameName ne 'index') { print "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">\n"; }
522
else { print "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Frameset//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-frameset.dtd\">\n"; }
523
print "<html xmlns=\"http://www.w3.org/1999/xhtml\" xml:lang=\"$Lang\">\n";
525
if ($FrameName ne 'index') { print "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\">\n\n"; }
526
else { print "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Frameset//EN\">\n\n"; }
527
print "<html lang='$Lang'".($PageDir?" dir='rtl'":"").">\n";
530
if ($MetaRobot) { print "<meta name=\"robots\" content=\"".($FrameName eq 'mainleft'?'no':'')."index,nofollow\" />\n"; }
531
else { print "<meta name=\"robots\" content=\"noindex,nofollow\" />\n"; }
533
# Affiche tag meta content-type
534
if ($BuildReportFormat eq 'xml') { print ($ENV{'HTTP_USER_AGENT'}=~/MSIE|Googlebot/i?"<meta http-equiv=\"content-type\" content=\"text/html; charset=".($PageCode?$PageCode:"iso-8859-1")."\" />\n":"<meta http-equiv=\"content-type\" content=\"text/xml; charset=".($PageCode?$PageCode:"iso-8859-1")."\" />\n"); }
535
else { print "<meta http-equiv=\"content-type\" content=\"text/html; charset=".($PageCode?$PageCode:"iso-8859-1")."\" />\n"; }
537
if ($Expires) { print "<meta http-equiv=\"expires\" content=\"".(gmtime($starttime+$Expires))."\" />\n"; }
538
print "<meta http-equiv=\"description\" content=\"".ucfirst($PROG)." - Advanced Web Statistics for $SiteDomain\" />\n";
539
if ($MetaRobot && $FrameName ne 'mainleft') { print "<meta http-equiv=\"keywords\" content=\"$SiteDomain, free, advanced, realtime, web, server, logfile, log, analyzer, analysis, statistics, stats, perl, analyse, performance, hits, visits\" />\n"; }
540
print "<title>$Message[7] $SiteDomain</title>\n";
541
if ($FrameName ne 'index') {
543
# A STYLE section must be in head section. Do not use " for number in a style section
544
print "<style type=\"text/css\">\n";
545
if ($BuildReportFormat eq 'xml') { print ($ENV{'HTTP_USER_AGENT'}=~/Firebird/i?"<!--\n":"<![CDATA[\n"); }
546
else { print "<!--\n"; }
547
print "body { font: 11px verdana, arial, helvetica, sans-serif; background-color: #$color_Background; margin-top: 0; margin-bottom: 0; }\n";
548
print ".aws_bodyl { }\n";
549
print ".aws_border { background-color: #$color_TableBG; padding: 1px 1px ".($BuildReportFormat eq 'xml'?"2px":"1px")." 1px; margin-top: 0; margin-bottom: 0; }\n";
550
print ".aws_title { font: 13px verdana, arial, helvetica, sans-serif; font-weight: bold; background-color: #$color_TableBGTitle; text-align: center; margin-top: 0; margin-bottom: 0; padding: 1px 1px 1px 1px; }\n";
551
print ".aws_blank { font: 13px verdana, arial, helvetica, sans-serif; background-color: #".($ENV{'HTTP_USER_AGENT'} && $ENV{'HTTP_USER_AGENT'}=~/MSIE/i?$color_Background:$color_TableBG)."; text-align: center; margin-bottom: 0; padding: 1px 1px 1px 1px; }\n";
554
background-color: #$color_Background;
555
border-top-width: 1px;
556
border-left-width: 0px;
557
border-right-width: 0px;
558
border-bottom-width: 0px;
560
.aws_formfield { font: 13px verdana, arial, helvetica; }
562
font-family: arial,verdana,helvetica, sans-serif;
564
border: 1px solid #ccd7e0;
565
background-image : url($DirIcons/other/button.gif);
567
th { border-color: #$color_TableBorder; border-left-width: 0px; border-right-width: 1px; border-top-width: 0px; border-bottom-width: 1px; padding: 1px 2px 1px 1px; font: 11px verdana, arial, helvetica, sans-serif; text-align:center; color: #$color_titletext; }
568
th.aws { border-color: #$color_TableBorder; border-left-width: 0px; border-right-width: 1px; border-top-width: 0px; border-bottom-width: 1px; padding: 1px 2px 1px 1px; font-size: 13px; font-weight: bold; }
569
td { border-color: #$color_TableBorder; border-left-width: 0px; border-right-width: 1px; border-top-width: 0px; border-bottom-width: 1px; padding: 1px 1px 1px 1px; font: 11px verdana, arial, helvetica, sans-serif; text-align:center; color: #$color_text; }
570
td.aws { border-color: #$color_TableBorder; border-left-width: 0px; border-right-width: 1px; border-top-width: 0px; border-bottom-width: 1px; padding: 1px 1px 1px 1px; font: 11px verdana, arial, helvetica, sans-serif; text-align:$dir; color: #$color_text; }
571
td.awsm { border-left-width: 0px; border-right-width: 0px; border-top-width: 0px; border-bottom-width: 0px; padding: 0px 0px 0px 0px; font: 11px verdana, arial, helvetica, sans-serif; text-align:$dir; color: #$color_text; }
572
b { font-weight: bold; }
573
a { font: 11px verdana, arial, helvetica, sans-serif; }
574
a:link { color: #$color_link; text-decoration: none; }
575
a:visited { color: #$color_link; text-decoration: none; }
576
a:hover { color: #$color_hover; text-decoration: underline; }
578
# Call to plugins' function AddHTMLStyles
579
foreach my $pluginname (keys %{$PluginsLoaded{'AddHTMLStyles'}}) {
580
my $function="AddHTMLStyles_$pluginname()";
584
if ($BuildReportFormat eq 'xml') { print ($ENV{'HTTP_USER_AGENT'}=~/Firebird/i?"//-->\n":"]]>\n"); }
585
else { print "//-->\n"; }
589
print "<link rel=\"stylesheet\" href=\"$StyleSheet\" />\n";
593
if ($FrameName ne 'index') {
594
print "<body style=\"margin-top: 0px\"";
595
if ($FrameName eq 'mainleft') { print " class=\"aws_bodyl\""; }
599
$HeaderHTMLComplete=1;
602
#------------------------------------------------------------------------------
603
# Function: Write on ouput end of HTML page
604
# Parameters: 0|1 (0=no list plugins,1=list plugins)
605
# Input: %HTMLOutput $HTMLEndSection $FrameName $BuildReportFormat
608
#------------------------------------------------------------------------------
610
my $listplugins=shift||0;
611
if (scalar keys %HTMLOutput) {
612
if ($FrameName ne 'index' && $FrameName ne 'mainleft') {
613
print "$Center<br /><br />\n";
614
print "<span dir=\"ltr\" style=\"font: 11px verdana, arial, helvetica; color: #$color_text;\">";
615
print "<b>Advanced Web Statistics $VERSION</b> - <a href=\"http://awstats.sourceforge.net\" target=\"awstatshome\">Created by $PROG";
617
my $atleastoneplugin=0;
618
foreach my $pluginname (keys %{$PluginsLoaded{'init'}}) {
619
if (! $atleastoneplugin) { $atleastoneplugin=1; print " (with plugin "; }
623
if ($atleastoneplugin) { print ")"; }
625
print "</a></span><br />\n";
626
if ($HTMLEndSection) { print "<br />\n$HTMLEndSection\n"; }
629
if ($FrameName ne 'index') {
630
if ($FrameName ne 'mainleft' && $BuildReportFormat eq 'html') { print "<br />\n"; }
634
# print "<!-- NEW PAGE --><!-- NEW SHEET -->\n";
638
#------------------------------------------------------------------------------
639
# Function: Print on stdout tab header of a chart
640
# Parameters: $title $tooltip_number [$width percentage of chart title]
644
#------------------------------------------------------------------------------
650
if ($width == 70 && $QueryString =~ /buildpdf/i) { print "<table class=\"aws_border\" border=\"0\" cellpadding=\"2\" cellspacing=\"0\" width=\"800\">\n"; }
651
else { print "<table class=\"aws_border\" border=\"0\" cellpadding=\"2\" cellspacing=\"0\" width=\"100%\">\n"; }
654
print "<tr><td class=\"aws_title\" width=\"$width%\"".($TOOLTIPON?" onmouseover=\"ShowTip($tooltip);\" onmouseout=\"HideTip($tooltip);\"":"").">$title </td>";
657
print "<tr><td class=\"aws_title\" width=\"$width%\">$title </td>";
659
print "<td class=\"aws_blank\"> </td></tr>\n";
660
print "<tr><td colspan=\"2\">\n";
661
if ($width == 70 && $QueryString =~ /buildpdf/i) { print "<table class=\"aws_data $class\" border=\"2\" bordercolor=\"#$color_TableBorder\" cellpadding=\"2\" cellspacing=\"0\" width=\"796\">\n"; }
662
else { print "<table class=\"aws_data $class\" border=\"2\" bordercolor=\"#$color_TableBorder\" cellpadding=\"2\" cellspacing=\"0\" width=\"100%\">\n"; }
665
#------------------------------------------------------------------------------
666
# Function: Print on stdout tab ender of a chart
671
#------------------------------------------------------------------------------
674
print "</table></td></tr></table>";
675
if ($string) { print "<span style=\"font: 11px verdana, arial, helvetica;\">$string</span><br />\n"; }
679
#------------------------------------------------------------------------------
680
# Function: Write error message and exit
681
# Parameters: $message $secondmessage $thirdmessage $donotshowsetupinfo
682
# Input: $HeaderHTTPComplete $HeaderHTMLComplete %HTMLOutput $LogSeparator $LogFormat
685
#------------------------------------------------------------------------------
687
my $message=shift||''; if (scalar keys %HTMLOutput) { $message =~ s/\</</g; $message =~ s/\>/>/g; }
688
my $secondmessage=shift||'';
689
my $thirdmessage=shift||'';
690
my $donotshowsetupinfo=shift||0;
692
if (! $HeaderHTTPComplete && $ENV{'GATEWAY_INTERFACE'}) { print "\n"; $HeaderHTTPComplete=1; }
693
if (! $HeaderHTMLComplete && scalar keys %HTMLOutput) { print "<html><body>\n"; $HeaderHTMLComplete=1; }
694
if ($Debug) { debug("$message $secondmessage $thirdmessage",1); }
695
my $tagbold=''; my $tagunbold=''; my $tagbr=''; my $tagfontred=''; my $tagfontgrey=''; my $tagunfont='';
696
if (scalar keys %HTMLOutput) {
697
$tagbold='<b>'; $tagunbold='</b>'; $tagbr='<br />';
698
$tagfontred='<span style="color: #880000">';
699
$tagfontgrey='<span style="color: #888888">';
700
$tagunfont='</span>';
702
if (! $ErrorMessages && $message =~ /^Format error$/i) {
703
# Files seems to have bad format
704
if (scalar keys %HTMLOutput) { print "<br /><br />\n"; }
705
if ($message !~ $LogSeparator) {
706
# Bad LogSeparator parameter
707
print "${tagfontred}AWStats did not found the ${tagbold}LogSeparator${tagunbold} in your log records.${tagbr}${tagunfont}\n";
710
# Bad LogFormat parameter
711
print "AWStats did not find any valid log lines that match your ${tagbold}LogFormat${tagunbold} parameter, in the ${NbOfLinesForCorruptedLog}th first non commented lines read of your log.${tagbr}\n";
712
print "${tagfontred}Your log file ${tagbold}$thirdmessage${tagunbold} must have a bad format or ${tagbold}LogFormat${tagunbold} parameter setup does not match this format.${tagbr}${tagbr}${tagunfont}\n";
713
print "Your AWStats ${tagbold}LogFormat${tagunbold} parameter is:\n";
714
print "${tagbold}$LogFormat${tagunbold}${tagbr}\n";
715
print "This means each line in your web server log file need to have ";
716
if ($LogFormat == 1) {
717
print "${tagbold}\"combined log format\"${tagunbold} like this:${tagbr}\n";
718
print (scalar keys %HTMLOutput?"$tagfontgrey<i>":"");
719
print "111.22.33.44 - - [10/Jan/2001:02:14:14 +0200] \"GET / HTTP/1.1\" 200 1234 \"http://www.fromserver.com/from.htm\" \"Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)\"\n";
720
print (scalar keys %HTMLOutput?"</i>$tagunfont${tagbr}${tagbr}\n":"");
722
if ($LogFormat == 2) {
723
print "${tagbold}\"MSIE Extended W3C log format\"${tagunbold} like this:${tagbr}\n";
724
print (scalar keys %HTMLOutput?"$tagfontgrey<i>":"");
725
print "date time c-ip c-username cs-method cs-uri-sterm sc-status sc-bytes cs-version cs(User-Agent) cs(Referer)\n";
726
print (scalar keys %HTMLOutput?"</i>$tagunfont${tagbr}${tagbr}\n":"");
728
if ($LogFormat == 3) {
729
print "${tagbold}\"WebStar native log format\"${tagunbold}${tagbr}\n";
731
if ($LogFormat == 4) {
732
print "${tagbold}\"common log format\"${tagunbold} like this:${tagbr}\n";
733
print (scalar keys %HTMLOutput?"$tagfontgrey<i>":"");
734
print "111.22.33.44 - - [10/Jan/2001:02:14:14 +0200] \"GET / HTTP/1.1\" 200 1234\n";
735
print (scalar keys %HTMLOutput?"</i>$tagunfont${tagbr}${tagbr}\n":"");
737
if ($LogFormat == 5) {
738
print "${tagbold}\"ISA native log format\"${tagunbold}${tagbr}\n";
740
if ($LogFormat == 6) {
741
print "${tagbold}\"Lotus Notes/Lotus Domino\"${tagunbold}${tagbr}\n";
742
print (scalar keys %HTMLOutput?"$tagfontgrey<i>":"");
743
print "111.22.33.44 - Firstname Middlename Lastname [10/Jan/2001:02:14:14 +0200] \"GET / HTTP/1.1\" 200 1234 \"http://www.fromserver.com/from.htm\" \"Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)\"\n";
744
print (scalar keys %HTMLOutput?"</i></span>${tagbr}${tagbr}\n":"");
746
if ($LogFormat !~ /^[1-6]$/) {
747
print "the following personalized log format:${tagbr}\n";
748
print (scalar keys %HTMLOutput?"$tagfontgrey<i>":"");
749
print "$LogFormat\n";
750
print (scalar keys %HTMLOutput?"</i>$tagunfont${tagbr}${tagbr}\n":"");
752
print "And this is a sample of records AWStats found in your log file (the record number $NbOfLinesForCorruptedLog in your log):\n";
753
print (scalar keys %HTMLOutput?"<br />$tagfontgrey<i>":"");
754
print "$secondmessage";
755
print (scalar keys %HTMLOutput?"</i>$tagunfont${tagbr}${tagbr}":"");
758
#print "Note: If your $NbOfLinesForCorruptedLog first lines in your log files are wrong because of ";
759
#print "a worm virus attack, you can increase the NbOfLinesForCorruptedLog parameter in config file.\n";
763
print (scalar keys %HTMLOutput?"<br />$tagfontred\n":"");
764
print ($ErrorMessages?"$ErrorMessages":"Error: $message");
765
print (scalar keys %HTMLOutput?"\n</span><br />":"");
768
if (! $ErrorMessages && ! $donotshowsetupinfo) {
769
if ($message =~ /Couldn.t open config file/i) {
771
if ($dir =~ /^\./) { $dir.='/../..'; }
772
else { $dir =~ s/[\\\/]?wwwroot[\/\\]cgi-bin[\\\/]?//; }
774
if ($ENV{'GATEWAY_INTERFACE'}) {
775
print "- ${tagbold}Did you use the correct URL ?${tagunbold}${tagbr}\n";
776
print "Example: http://localhost/awstats/awstats.pl?config=mysite${tagbr}\n";
777
print "Example: http://127.0.0.1/cgi-bin/awstats.pl?config=mysite${tagbr}\n";
779
print "- ${tagbold}Did you use correct config parameter ?${tagunbold}${tagbr}\n";
780
print "Example: If your config file is awstats.mysite.conf, you must use -config=mysite\n";
782
print "- ${tagbold}Did you create your config file 'awstats.$SiteConfig.conf' ?${tagunbold}${tagbr}\n";
783
print "If not, you can run \"$dir/tools/configure.pl\"${tagbr}\n";
786
else { print "${tagbr}${tagbold}Setup (".($FileConfig?"'".$FileConfig."'":"Config")." file, web server or permissions) may be wrong.${tagunbold}${tagbr}\n"; }
787
print "See AWStats documentation in 'docs' directory for informations on how to setup $PROG.\n";
789
# Remove lock if not a lock message
790
if ($EnableLockForUpdate && $message !~ /lock file/) { &Lock_Update(0); }
791
if (scalar keys %HTMLOutput) { print "</body></html>\n"; }
795
#------------------------------------------------------------------------------
796
# Function: Write a warning message
797
# Parameters: $message
798
# Input: $HeaderHTTPComplete $HeaderHTMLComplete $WarningMessage %HTMLOutput
801
#------------------------------------------------------------------------------
803
my $messagestring=shift;
805
if (! $HeaderHTTPComplete && $ENV{'GATEWAY_INTERFACE'}) { print "\n"; $HeaderHTTPComplete=1; }
806
if (! $HeaderHTMLComplete) { html_head(); }
807
if ($Debug) { debug("$messagestring",1); }
808
if ($WarningMessages) {
809
if (scalar keys %HTMLOutput) {
810
$messagestring =~ s/\n/\<br\>/g;
811
print "$messagestring<br />\n";
814
print "$messagestring\n";
819
#------------------------------------------------------------------------------
820
# Function: Write debug message and exit
821
# Parameters: $string $level
822
# Input: %HTMLOutput $Debug=required level $DEBUGFORCED=required level forced
825
#------------------------------------------------------------------------------
827
my $level = $_[1] || 1;
828
if ($level <= $DEBUGFORCED) {
829
my $debugstring = $_[0];
830
if (! $DebugResetDone) { open(DEBUGFORCEDFILE,"debug.log"); close DEBUGFORCEDFILE; chmod 0666,"debug.log"; $DebugResetDone=1; }
831
open(DEBUGFORCEDFILE,">>debug.log");
832
print DEBUGFORCEDFILE localtime(time)." - $$ - DEBUG $level - $debugstring\n";
833
close DEBUGFORCEDFILE;
835
if ($DebugMessages && $level <= $Debug) {
836
my $debugstring = $_[0];
837
if (scalar keys %HTMLOutput) { $debugstring =~ s/^ / /; $debugstring .= "<br />"; }
838
print localtime(time)." - DEBUG $level - $debugstring\n";
842
#------------------------------------------------------------------------------
843
# Function: Optimize an array removing duplicate entries
844
# Parameters: @Array notcasesensitive=0|1
848
#------------------------------------------------------------------------------
851
my @arrayunreg=map{if (/\(\?[-\w]*:(.*)\)/) { $1 } } @$array;
852
my $notcasesensitive=shift;
854
if ($Debug) { debug("OptimizeArray (notcasesensitive=$notcasesensitive)",4); }
855
while ($searchlist>-1 && @arrayunreg) {
858
foreach my $i ($searchlist..(scalar @arrayunreg)-1) {
859
# Search if $i elem is already treated by another elem
860
foreach my $j (0..(scalar @arrayunreg)-1) {
861
if ($i == $j) { next; }
862
my $parami=$notcasesensitive?lc($arrayunreg[$i]):$arrayunreg[$i];
863
my $paramj=$notcasesensitive?lc($arrayunreg[$j]):$arrayunreg[$j];
864
if ($Debug) { debug(" Compare $i ($parami) to $j ($paramj)",4); }
865
if (index($parami,$paramj)>-1) {
866
if ($Debug) { debug(" Elem $i ($arrayunreg[$i]) already treated with elem $j ($arrayunreg[$j])",4); }
872
if ($elemtoremove > -1) {
873
if ($Debug) { debug(" Remove elem $elemtoremove - $arrayunreg[$elemtoremove]",4); }
874
splice @arrayunreg, $elemtoremove, 1;
875
$searchlist=$elemtoremove;
881
if ($notcasesensitive) { return map{qr/$_/i} @arrayunreg; }
882
return map{qr/$_/} @arrayunreg;
885
#------------------------------------------------------------------------------
886
# Function: Check if parameter is in SkipDNSLookupFor array
887
# Parameters: ip @SkipDNSLookupFor (a NOT case sensitive precompiled regex array)
888
# Return: 0 Not found, 1 Found
889
#------------------------------------------------------------------------------
891
foreach (@SkipDNSLookupFor) { if ($_[0] =~ /$_/) { return 1; } }
892
0; # Not in @SkipDNSLookupFor
895
#------------------------------------------------------------------------------
896
# Function: Check if parameter is in SkipHosts array
897
# Parameters: host @SkipHosts (a NOT case sensitive precompiled regex array)
898
# Return: 0 Not found, 1 Found
899
#------------------------------------------------------------------------------
901
foreach (@SkipHosts) { if ($_[0] =~ /$_/) { return 1; } }
902
0; # Not in @SkipHosts
905
#------------------------------------------------------------------------------
906
# Function: Check if parameter is in SkipUserAgents array
907
# Parameters: useragent @SkipUserAgents (a NOT case sensitive precompiled regex array)
908
# Return: 0 Not found, 1 Found
909
#------------------------------------------------------------------------------
911
foreach (@SkipUserAgents) { if ($_[0] =~ /$_/) { return 1; } }
912
0; # Not in @SkipUserAgent
915
#------------------------------------------------------------------------------
916
# Function: Check if parameter is in SkipFiles array
917
# Parameters: url @SkipFiles (a NOT case sensitive precompiled regex array)
918
# Return: 0 Not found, 1 Found
919
#------------------------------------------------------------------------------
921
foreach (@SkipFiles) { if ($_[0] =~ /$_/) { return 1; } }
922
0; # Not in @SkipFiles
925
#------------------------------------------------------------------------------
926
# Function: Check if parameter is in OnlyHosts array
927
# Parameters: host @OnlyHosts (a NOT case sensitive precompiled regex array)
928
# Return: 0 Not found, 1 Found
929
#------------------------------------------------------------------------------
931
foreach (@OnlyHosts) { if ($_[0] =~ /$_/) { return 1; } }
932
0; # Not in @OnlyHosts
935
#------------------------------------------------------------------------------
936
# Function: Check if parameter is in OnlyUserAgents array
937
# Parameters: useragent @OnlyUserAgents (a NOT case sensitive precompiled regex array)
938
# Return: 0 Not found, 1 Found
939
#------------------------------------------------------------------------------
941
foreach (@OnlyUserAgents) { if ($_[0] =~ /$_/) { return 1; } }
942
0; # Not in @OnlyHosts
945
#------------------------------------------------------------------------------
946
# Function: Check if parameter is in OnlyFiles array
947
# Parameters: url @OnlyFiles (a NOT case sensitive precompiled regex array)
948
# Return: 0 Not found, 1 Found
949
#------------------------------------------------------------------------------
951
foreach (@OnlyFiles) { if ($_[0] =~ /$_/) { return 1; } }
952
0; # Not in @OnlyFiles
955
#------------------------------------------------------------------------------
956
# Function: Return day of week of a day
957
# Parameters: $day $month $year
959
#------------------------------------------------------------------------------
961
my ($day, $month, $year) = @_;
962
if ($Debug) { debug("DayOfWeek for $day $month $year",4); }
963
if ($month < 3) { $month += 10; $year--; }
964
else { $month -= 2; }
965
my $cent = sprintf("%1i",($year/100));
966
my $y = ($year % 100);
967
my $dw = (sprintf("%1i",(2.6*$month)-0.2) + $day + $y + sprintf("%1i",($y/4)) + sprintf("%1i",($cent/4)) - (2*$cent)) % 7;
969
if ($Debug) { debug(" is $dw",4); }
973
#------------------------------------------------------------------------------
974
# Function: Return 1 if a date exists
975
# Parameters: $day $month $year
976
# Return: 1 if date exists else 0
977
#------------------------------------------------------------------------------
979
my ($day, $month, $year) = @_;
980
if ($Debug) { debug("DateIsValid for $day $month $year",4); }
981
if ($day < 1) { return 0; }
982
if ($day > 31) { return 0; }
983
if ($month==4 || $month==6 || $month==9 || $month==11) {
984
if ($day > 30) { return 0; }
987
my $leapyear=($year%4==0?1:0); # A leap year every 4 years
988
if ($year%100==0 && $year%400!=0) { $leapyear=0; } # Except if year is 100x and not 400x
989
if ($day > (28+$leapyear)) { return 0; }
994
#------------------------------------------------------------------------------
995
# Function: Return string of visit duration
996
# Parameters: $starttime $endtime
999
# Return: A string that identify the visit duration range
1000
#------------------------------------------------------------------------------
1001
sub GetSessionRange {
1002
my $starttime = my $endtime;
1003
if (shift =~ /(\d\d\d\d)(\d\d)(\d\d)(\d\d)(\d\d)(\d\d)/) { $starttime = Time::Local::timelocal($6,$5,$4,$3,$2-1,$1); }
1004
if (shift =~ /(\d\d\d\d)(\d\d)(\d\d)(\d\d)(\d\d)(\d\d)/) { $endtime = Time::Local::timelocal($6,$5,$4,$3,$2-1,$1); }
1005
my $delay=$endtime-$starttime;
1006
if ($Debug) { debug("GetSessionRange $endtime - $starttime = $delay",4); }
1007
if ($delay <= 30) { return $SessionsRange[0]; }
1008
if ($delay > 30 && $delay <= 120) { return $SessionsRange[1]; }
1009
if ($delay > 120 && $delay <= 300) { return $SessionsRange[2]; }
1010
if ($delay > 300 && $delay <= 900) { return $SessionsRange[3]; }
1011
if ($delay > 900 && $delay <= 1800) { return $SessionsRange[4]; }
1012
if ($delay > 1800 && $delay <= 3600) { return $SessionsRange[5]; }
1013
if ($delay > 3600) { return $SessionsRange[6]; }
1017
#------------------------------------------------------------------------------
1018
# Function: Read config file
1019
# Parameters: None or configdir to scan
1020
# Input: $DIR $PROG $SiteConfig
1021
# Output: Global variables
1023
#------------------------------------------------------------------------------
1025
# Check config file in common possible directories :
1026
# Windows : "$DIR" (same dir than awstats.pl)
1027
# Standard, Mandrake and Debian package : "/etc/awstats"
1028
# Other possible directories : "/usr/local/etc/awstats", "/etc"
1029
# FHS standard, Suse package : "/etc/opt/awstats"
1030
my $configdir=shift;
1031
my @PossibleConfigDir=();
1033
if ($configdir) { @PossibleConfigDir=("$configdir"); }
1034
else { @PossibleConfigDir=("$DIR","/etc/awstats","/usr/local/etc/awstats","/etc","/etc/opt/awstats"); }
1037
$FileConfig=$FileSuffix='';
1038
foreach (@PossibleConfigDir) {
1040
if ($searchdir && $searchdir !~ /[\\\/]$/) { $searchdir .= "/"; }
1041
if (open(CONFIG,"$searchdir$PROG.$SiteConfig.conf")) { $FileConfig="$searchdir$PROG.$SiteConfig.conf"; $FileSuffix=".$SiteConfig"; last; }
1042
if (open(CONFIG,"$searchdir$PROG.conf")) { $FileConfig="$searchdir$PROG.conf"; $FileSuffix=''; last; }
1044
if (! $FileConfig) { error("Couldn't open config file \"$PROG.$SiteConfig.conf\" nor \"$PROG.conf\" after searching in path \"".join(',',@PossibleConfigDir)."\": $!"); }
1046
# Analyze config file content and close it
1047
&Parse_Config( *CONFIG , 1 , $FileConfig);
1050
# If parameter NotPageList not found, init for backward compatibility
1051
if (! $FoundNotPageList) {
1052
$NotPageList{'gif'}=$NotPageList{'jpg'}=$NotPageList{'jpeg'}=$NotPageList{'png'}=$NotPageList{'bmp'}=1;
1054
# If parameter ValidHTTPCodes not found, init for backward compatibility
1055
if (! $FoundValidHTTPCodes) {
1056
$ValidHTTPCodes{"200"}=$ValidHTTPCodes{"304"}=1;
1058
# If parameter ValidSMTPCodes not found, init for backward compatibility
1059
if (! $FoundValidSMTPCodes) {
1060
$ValidSMTPCodes{"1"}=$ValidSMTPCodes{"250"}=1;
1064
#------------------------------------------------------------------------------
1065
# Function: Parse content of a config file
1066
# Parameters: opened file handle, depth level, file name
1068
# Output: Global variables
1070
#------------------------------------------------------------------------------
1072
my ( $confighandle ) = $_[0];
1074
my $configFile = $_[2];
1078
if ($level > 10) { error("$PROG can't read down more than 10 level of includes. Check that no 'included' config files include their parent config file (this cause infinite loop)."); }
1080
while (<$confighandle>) {
1084
# Extract version from first line
1085
if (! $versionnum && $_ =~ /^# AWSTATS CONFIGURE FILE (\d+).(\d+)/i) {
1086
$versionnum=($1*1000)+$2;
1087
#if ($Debug) { debug(" Configure file version is $versionnum",1); }
1091
if ($_ =~ /^\s*$/) { next; }
1094
if ($_ =~ /^Include "([^\"]+)"/ || $_ =~ /^#include "([^\"]+)"/) { # #include kept for backward compatibility
1095
my $includeFile = $1;
1096
if ($Debug) { debug("Found an include : $includeFile",2); }
1097
if ( $includeFile !~ /^[\\\/]/ ) {
1098
# Correct relative include files
1099
if ($FileConfig =~ /^(.*[\\\/])[^\\\/]*$/) { $includeFile = "$1$includeFile"; }
1102
warning("Warning: Perl versions before 5.6 cannot handle nested includes");
1105
if ( open( CONFIG_INCLUDE, $includeFile ) ) {
1106
&Parse_Config( *CONFIG_INCLUDE , $level+1, $includeFile);
1107
close( CONFIG_INCLUDE );
1110
error("Could not open include file: $includeFile" );
1116
if ($_ =~ /^\s*#/) { next; }
1119
# Extract param and value
1120
my ($param,$value)=split(/=/,$_,2);
1121
$param =~ s/^\s+//; $param =~ s/\s+$//;
1123
# If not a param=value, try with next line
1124
if (! $param) { warning("Warning: Syntax error line $conflinenb in file '$configFile'. Config line is ignored."); next; }
1125
if (! defined $value) { warning("Warning: Syntax error line $conflinenb in file '$configFile'. Config line is ignored."); next; }
1128
$value =~ s/^\s+//; $value =~ s/\s+$//;
1129
$value =~ s/^\"//; $value =~ s/\";?$//;
1130
# Replace __MONENV__ with value of environnement variable MONENV
1131
# Must be able to replace __VAR_1____VAR_2__
1132
while ($value =~ /__([^\s_]+(?:_[^\s_]+)*)__/) { my $var=$1; $value =~ s/__${var}__/$ENV{$var}/g; }
1135
# Initialize parameter for (param,value)
1136
if ($param =~ /^LogFile/) {
1137
if ($QueryString !~ /logfile=([^\s&]+)/i) { $LogFile=$value; }
1140
if ($param =~ /^DirIcons/) {
1141
if ($QueryString !~ /diricons=([^\s&]+)/i) { $DirIcons=$value; }
1144
if ($param =~ /^SiteDomain/) {
1145
# No regex test as SiteDomain is always exact value
1149
if ($param =~ /^HostAliases/) {
1150
foreach my $elem (split(/\s+/,$value)) {
1151
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1152
else { $elem='^'.quotemeta($elem).'$'; }
1153
if ($elem) { push @HostAliases, qr/$elem/i; }
1157
# Special optional setup params
1158
if ($param =~ /^SkipDNSLookupFor/) {
1159
foreach my $elem (split(/\s+/,$value)) {
1160
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1161
else { $elem='^'.quotemeta($elem).'$'; }
1162
if ($elem) { push @SkipDNSLookupFor, qr/$elem/i; }
1166
if ($param =~ /^AllowAccessFromWebToFollowingAuthenticatedUsers/) {
1167
foreach (split(/\s+/,$value)) { push @AllowAccessFromWebToFollowingAuthenticatedUsers,$_; }
1170
if ($param =~ /^DefaultFile/) {
1171
foreach my $elem (split(/\s+/,$value)) {
1172
# No REGEX for this option
1173
#if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1174
#else { $elem='^'.quotemeta($elem).'$'; }
1175
if ($elem) { push @DefaultFile,$elem; }
1179
if ($param =~ /^SkipHosts/) {
1180
foreach my $elem (split(/\s+/,$value)) {
1181
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1182
else { $elem='^'.quotemeta($elem).'$'; }
1183
if ($elem) { push @SkipHosts, qr/$elem/i; }
1187
if ($param =~ /^SkipUserAgents/) {
1188
foreach my $elem (split(/\s+/,$value)) {
1189
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1190
else { $elem='^'.quotemeta($elem).'$'; }
1191
if ($elem) { push @SkipUserAgents, qr/$elem/i; }
1195
if ($param =~ /^SkipFiles/) {
1196
foreach my $elem (split(/\s+/,$value)) {
1197
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1198
else { $elem='^'.quotemeta($elem).'$'; }
1199
if ($elem) { push @SkipFiles, qr/$elem/i; }
1203
if ($param =~ /^OnlyHosts/) {
1204
foreach my $elem (split(/\s+/,$value)) {
1205
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1206
else { $elem='^'.quotemeta($elem).'$'; }
1207
if ($elem) { push @OnlyHosts, qr/$elem/i; }
1211
if ($param =~ /^OnlyUserAgents/) {
1212
foreach my $elem (split(/\s+/,$value)) {
1213
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1214
else { $elem='^'.quotemeta($elem).'$'; }
1215
if ($elem) { push @OnlyUserAgents, qr/$elem/i; }
1219
if ($param =~ /^OnlyFiles/) {
1220
foreach my $elem (split(/\s+/,$value)) {
1221
if ($elem =~ /^REGEX\[(.*)\]$/i) { $elem=$1; }
1222
else { $elem='^'.quotemeta($elem).'$'; }
1223
if ($elem) { push @OnlyFiles, qr/$elem/i; }
1227
if ($param =~ /^NotPageList/) {
1228
foreach (split(/\s+/,$value)) { $NotPageList{$_}=1; }
1229
$FoundNotPageList=1;
1232
if ($param =~ /^ValidHTTPCodes/) {
1233
foreach (split(/\s+/,$value)) { $ValidHTTPCodes{$_}=1; }
1234
$FoundValidHTTPCodes=1;
1237
if ($param =~ /^ValidSMTPCodes/) {
1238
foreach (split(/\s+/,$value)) { $ValidSMTPCodes{$_}=1; }
1239
$FoundValidSMTPCodes=1;
1242
if ($param =~ /^URLWithQueryWithOnlyFollowingParameters$/) {
1243
@URLWithQueryWithOnly=split(/\s+/,$value);
1246
if ($param =~ /^URLWithQueryWithoutFollowingParameters$/) {
1247
@URLWithQueryWithout=split(/\s+/,$value);
1251
if ($param =~ /^ExtraSectionName(\d+)/) { $ExtraName[$1]=$value; next; }
1252
if ($param =~ /^ExtraSectionCondition(\d+)/) { $ExtraCondition[$1]=$value; next; }
1253
if ($param =~ /^ExtraSectionStatTypes(\d+)/) { $ExtraStatTypes[$1]=$value; next; }
1254
if ($param =~ /^ExtraSectionFirstColumnTitle(\d+)/) { $ExtraFirstColumnTitle[$1]=$value; next; }
1255
if ($param =~ /^ExtraSectionFirstColumnValues(\d+)/) { $ExtraFirstColumnValues[$1]=$value; next; }
1256
if ($param =~ /^ExtraSectionFirstColumnFormat(\d+)/) { $ExtraFirstColumnFormat[$1]=$value; next; }
1257
if ($param =~ /^ExtraSectionAddAverageRow(\d+)/) { $ExtraAddAverageRow[$1]=$value; next; }
1258
if ($param =~ /^ExtraSectionAddSumRow(\d+)/) { $ExtraAddSumRow[$1]=$value; next; }
1259
if ($param =~ /^MaxNbOfExtra(\d+)/) { $MaxNbOfExtra[$1]=$value; next; }
1260
if ($param =~ /^MinHitExtra(\d+)/) { $MinHitExtra[$1]=$value; next; }
1261
# Special appearance parameters
1262
if ($param =~ /^LoadPlugin/) { push @PluginsToLoad, $value; next; }
1263
# Other that we need to put after MaxNbOfExtra and MinHitExtra
1264
if ($param =~ /^MaxNbOf(\w+)/) { $MaxNbOf{$1}=$value; next; }
1265
if ($param =~ /^MinHit(\w+)/) { $MinHit{$1}=$value; next; }
1266
# Check if this is a known parameter
1267
# if (! $ConfOk{$param}) { error("Unknown config parameter '$param' found line $conflinenb in file \"configFile\""); }
1268
# If parameters was not found previously, defined variable with name of param to value
1272
# For backward compatibility
1273
if ($versionnum < 5001) { $BarHeight=$BarHeight>>1; }
1275
if ($Debug) { debug("Config file read was \"$configFile\" (level $level)"); }
1279
#------------------------------------------------------------------------------
1280
# Function: Load the reference databases
1281
# Parameters: List of files to load
1283
# Output: Arrays and Hash tables are defined
1285
#------------------------------------------------------------------------------
1287
# Check lib files in common possible directories :
1288
# Windows and standard package: "$DIR/lib" (lib in same dir than awstats.pl)
1289
# Debian package : "/usr/share/awstats/lib"
1290
my @PossibleLibDir=("$DIR/lib","/usr/share/awstats/lib");
1291
my %FilePath=(); my %DirAddedInINC=();
1292
my @FileListToLoad=();
1293
while (my $file=shift) { push @FileListToLoad, "$file.pm"; }
1294
if ($Debug) { debug("Call to Read_Ref_Data with files to load: ".(join(',',@FileListToLoad))); }
1295
foreach my $file (@FileListToLoad) {
1296
foreach my $dir (@PossibleLibDir) {
1298
if ($searchdir && (!($searchdir =~ /\/$/)) && (!($searchdir =~ /\\$/)) ) { $searchdir .= "/"; }
1299
if (! $FilePath{$file}) { # To not load twice same file in different path
1300
if (-s "${searchdir}${file}") {
1301
$FilePath{$file}="${searchdir}${file}";
1302
if ($Debug) { debug("Call to Read_Ref_Data [FilePath{$file}=\"$FilePath{$file}\"]"); }
1303
# Note: cygwin perl 5.8 need a push + require file
1304
if (! $DirAddedInINC{"$dir"}) {
1306
$DirAddedInINC{"$dir"}=1;
1308
my $loadret=require "$file";
1309
#my $loadret=(require "$FilePath{$file}"||require "${file}");
1313
if (! $FilePath{$file}) {
1314
my $filetext=$file; $filetext =~ s/\.pm$//; $filetext =~ s/_/ /g;
1315
warning("Warning: Can't read file \"$file\" ($filetext detection will not work correctly).\nCheck if file is in \"".($PossibleLibDir[0])."\" directory and is readable.");
1318
# Sanity check (if loaded)
1319
if ((scalar keys %OSHashID) && @OSSearchIDOrder != scalar keys %OSHashID) { error("Not same number of records of OSSearchIDOrder (".(@OSSearchIDOrder)." entries) and OSHashID (".(scalar keys %OSHashID)." entries) in OS database. Check your file ".$FilePath{"operating_systems.pm"}); }
1320
if ((scalar keys %SearchEnginesHashID) && (@SearchEnginesSearchIDOrder_list1+@SearchEnginesSearchIDOrder_list2+@SearchEnginesSearchIDOrder_listgen) != scalar keys %SearchEnginesHashID) { error("Not same number of records of SearchEnginesSearchIDOrder_listx (total is ".(@SearchEnginesSearchIDOrder_list1+@SearchEnginesSearchIDOrder_list2+@SearchEnginesSearchIDOrder_listgen)." entries) and SearchEnginesHashID (".(scalar keys %SearchEnginesHashID)." entries) in Search Engines database. Check your file ".$FilePath{"search_engines.pm"}); }
1321
if ((scalar keys %BrowsersHashIDLib) && @BrowsersSearchIDOrder != (scalar keys %BrowsersHashIDLib) - 2) { error("Not same number of records of BrowsersSearchIDOrder (".(@BrowsersSearchIDOrder)." entries) and BrowsersHashIDLib (".((scalar keys %BrowsersHashIDLib) - 2)." entries without msie and netscape) in Browsers database. Check your file ".$FilePath{"browsers.pm"}); }
1322
if ((scalar keys %RobotsHashIDLib) && (@RobotsSearchIDOrder_list1+@RobotsSearchIDOrder_list2+@RobotsSearchIDOrder_listgen) != (scalar keys %RobotsHashIDLib) - 1) { error("Not same number of records of RobotsSearchIDOrder_listx (total is ".(@RobotsSearchIDOrder_list1+@RobotsSearchIDOrder_list2+@RobotsSearchIDOrder_listgen)." entries) and RobotsHashIDLib (".((scalar keys %RobotsHashIDLib) - 1)." entries without 'unknown') in Robots database. Check your file ".$FilePath{"robots.pm"}); }
1326
#------------------------------------------------------------------------------
1327
# Function: Get the messages for a specified language
1328
# Parameters: LanguageId
1329
# Input: $DirLang $DIR
1330
# Output: $Message table is defined in memory
1332
#------------------------------------------------------------------------------
1333
sub Read_Language_Data {
1334
# Check lang files in common possible directories :
1335
# Windows and standard package: "$DIR/lang" (lang in same dir than awstats.pl)
1336
# Debian package : "/usr/share/awstats/lang"
1337
my @PossibleLangDir=("$DirLang","$DIR/lang","/usr/share/awstats/lang");
1340
foreach (@PossibleLangDir) {
1342
if ($searchdir && (!($searchdir =~ /\/$/)) && (!($searchdir =~ /\\$/)) ) { $searchdir .= "/"; }
1343
if (open(LANG,"${searchdir}awstats-$_[0].txt")) { $FileLang="${searchdir}awstats-$_[0].txt"; last; }
1345
# If file not found, we try english
1347
foreach (@PossibleLangDir) {
1349
if ($searchdir && (!($searchdir =~ /\/$/)) && (!($searchdir =~ /\\$/)) ) { $searchdir .= "/"; }
1350
if (open(LANG,"${searchdir}awstats-en.txt")) { $FileLang="${searchdir}awstats-en.txt"; last; }
1353
if ($Debug) { debug("Call to Read_Language_Data [FileLang=\"$FileLang\"]"); }
1356
binmode LANG; # Might avoid 'Malformed UTF-8 errors'
1357
my $cregcode=qr/^PageCode=[\t\s\"\']*([\w-]+)/i;
1358
my $cregdir=qr/^PageDir=[\t\s\"\']*([\w-]+)/i;
1359
my $cregmessage=qr/^Message\d+=/i;
1362
if ($_ =~ /$cregcode/o) { $PageCode = $1; }
1363
if ($_ =~ /$cregdir/o) { $PageDir = $1; }
1364
if ($_ =~ s/$cregmessage//o) {
1365
$_ =~ s/#.*//; # Remove comments
1366
$_ =~ tr/\t / /s; # Change all blanks into " "
1367
$_ =~ s/^\s+//; $_ =~ s/\s+$//;
1368
$_ =~ s/^\"//; $_ =~ s/\"$//;
1376
warning("Warning: Can't find language files for \"$_[0]\". English will be used.");
1378
# Some language string changes
1379
if ($LogType eq 'M') { # For mail
1380
$Message[8]=$Message[151];
1381
$Message[9]=$Message[152];
1382
$Message[57]=$Message[149];
1383
$Message[75]=$Message[150];
1385
if ($LogType eq 'F') { # For web
1391
#------------------------------------------------------------------------------
1392
# Function: Check if all parameters are correctly defined. If not set them to default.
1394
# Input: All global variables
1395
# Output: Change on some global variables
1397
#------------------------------------------------------------------------------
1399
if ($Debug) { debug("Call to Check_Config"); }
1401
my %MonthNumLibEn = ("01","Jan","02","Feb","03","Mar","04","Apr","05","May","06","Jun","07","Jul","08","Aug","09","Sep","10","Oct","11","Nov","12","Dec");
1403
# Show initial values of main parameters before check
1405
debug(" LogFile='$LogFile'",2);
1406
debug(" LogType='$LogType'",2);
1407
debug(" LogFormat='$LogFormat'",2);
1408
debug(" LogSeparator='$LogSeparator'",2);
1409
debug(" DNSLookup='$DNSLookup'",2);
1410
debug(" DirData='$DirData'",2);
1411
debug(" DirCgi='$DirCgi'",2);
1412
debug(" DirIcons='$DirIcons'",2);
1413
debug(" NotPageList ".(join(',',keys %NotPageList)),2);
1414
debug(" ValidHTTPCodes ".(join(',',keys %ValidHTTPCodes)),2);
1415
debug(" ValidSMTPCodes ".(join(',',keys %ValidSMTPCodes)),2);
1416
debug(" UseFramesWhenCGI=$UseFramesWhenCGI",2);
1417
debug(" BuildReportFormat=$BuildReportFormat",2);
1418
debug(" BuildHistoryFormat=$BuildHistoryFormat",2);
1419
debug(" URLWithQueryWithOnlyFollowingParameters=".(join(',',@URLWithQueryWithOnly)),2);
1420
debug(" URLWithQueryWithoutFollowingParameters=".(join(',',@URLWithQueryWithout)),2);
1424
while ($LogFile =~ /%([ymdhwYMDHWNSO]+)-(\d+)/) {
1427
if ($Debug) { debug(" Found a time tag '$timetag' with a phase of '$timephase' hour in log file name",1); }
1429
my ($oldersec,$oldermin,$olderhour,$olderday,$oldermonth,$olderyear,$olderwday,$olderyday) = localtime($starttime-($timephase*3600));
1430
my $olderweekofmonth=int($olderday/7);
1431
my $olderweekofyear=int(($olderyday-1+6-($olderwday==0?6:$olderwday-1))/7)+1; if ($olderweekofyear > 52) { $olderweekofyear = 1; }
1432
my $olderdaymod=$olderday%7;
1434
my $olderns=Time::Local::timegm(0,0,0,$olderday,$oldermonth,$olderyear);
1435
if ($olderdaymod <= $olderwday) { if (($olderwday != 7) || ($olderdaymod != 0)) { $olderweekofmonth=$olderweekofmonth+1; } }
1436
if ($olderdaymod > $olderwday) { $olderweekofmonth=$olderweekofmonth+2; }
1437
# Change format of time variables
1438
$olderweekofmonth = "0$olderweekofmonth";
1439
if ($olderweekofyear < 10) { $olderweekofyear = "0$olderweekofyear"; }
1440
if ($olderyear < 100) { $olderyear+=2000; } else { $olderyear+=1900; }
1441
my $oldersmallyear=$olderyear;$oldersmallyear =~ s/^..//;
1442
if (++$oldermonth < 10) { $oldermonth = "0$oldermonth"; }
1443
if ($olderday < 10) { $olderday = "0$olderday"; }
1444
if ($olderhour < 10) { $olderhour = "0$olderhour"; }
1445
if ($oldermin < 10) { $oldermin = "0$oldermin"; }
1446
if ($oldersec < 10) { $oldersec = "0$oldersec"; }
1447
# Replace tag with new value
1448
if ($timetag eq 'YYYY') { $LogFile =~ s/%YYYY-$timephase/$olderyear/ig; next; }
1449
if ($timetag eq 'YY') { $LogFile =~ s/%YY-$timephase/$oldersmallyear/ig; next; }
1450
if ($timetag eq 'MM') { $LogFile =~ s/%MM-$timephase/$oldermonth/ig; next; }
1451
if ($timetag eq 'MO') { $LogFile =~ s/%MO-$timephase/$MonthNumLibEn{$oldermonth}/ig; next; }
1452
if ($timetag eq 'DD') { $LogFile =~ s/%DD-$timephase/$olderday/ig; next; }
1453
if ($timetag eq 'HH') { $LogFile =~ s/%HH-$timephase/$olderhour/ig; next; }
1454
if ($timetag eq 'NS') { $LogFile =~ s/%NS-$timephase/$olderns/ig; next; }
1455
if ($timetag eq 'WM') { $LogFile =~ s/%WM-$timephase/$olderweekofmonth/g; next; }
1456
if ($timetag eq 'Wm') { my $olderweekofmonth0=$olderweekofmonth-1; $LogFile =~ s/%Wm-$timephase/$olderweekofmonth0/g; next; }
1457
if ($timetag eq 'WY') { $LogFile =~ s/%WY-$timephase/$olderweekofyear/g; next; }
1458
if ($timetag eq 'Wy') { my $olderweekofyear0=sprintf("%02d",$olderweekofyear-1); $LogFile =~ s/%Wy-$timephase/$olderweekofyear0/g; next; }
1459
if ($timetag eq 'DW') { $LogFile =~ s/%DW-$timephase/$olderwday/g; next; }
1460
if ($timetag eq 'Dw') { my $olderwday0=$olderwday-1; $LogFile =~ s/%Dw-$timephase/$olderwday0/g; next; }
1462
error("Unknown tag '\%$timetag' in LogFile parameter.");
1464
# Replace %YYYY %YY %MM %DD %HH with current value. Kept for backward compatibility.
1465
$LogFile =~ s/%YYYY/$nowyear/ig;
1466
$LogFile =~ s/%YY/$nowsmallyear/ig;
1467
$LogFile =~ s/%MM/$nowmonth/ig;
1468
$LogFile =~ s/%MO/$MonthNumLibEn{$nowmonth}/ig;
1469
$LogFile =~ s/%DD/$nowday/ig;
1470
$LogFile =~ s/%HH/$nowhour/ig;
1471
$LogFile =~ s/%NS/$nowns/ig;
1472
$LogFile =~ s/%WM/$nowweekofmonth/g;
1473
my $nowweekofmonth0=$nowweekofmonth-1; $LogFile =~ s/%Wm/$nowweekofmonth0/g;
1474
$LogFile =~ s/%WY/$nowweekofyear/g;
1475
my $nowweekofyear0=$nowweekofyear-1; $LogFile =~ s/%Wy/$nowweekofyear0/g;
1476
$LogFile =~ s/%DW/$nowwday/g;
1477
my $nowwday0=$nowwday-1; $LogFile =~ s/%Dw/$nowwday0/g;
1478
if (! $LogFile) { error("LogFile parameter is not defined in config/domain file"); }
1479
if ($LogType !~ /[WSMF]/i) { $LogType='W'; }
1480
$LogFormat =~ s/\\//g;
1481
if (! $LogFormat) { error("LogFormat parameter is not defined in config/domain file"); }
1482
if ($LogFormat =~ /^\d$/ && $LogFormat !~ /[1-6]/) { error("LogFormat parameter is wrong in config/domain file. Value is '$LogFormat' (should be 1,2,3,4,5 or a 'personalized AWStats log format string')"); }
1483
$LogSeparator||="\\s";
1485
$DirCgi||='/cgi-bin';
1486
$DirIcons||='/icon';
1487
if ($DNSLookup !~ /[0-2]/) { error("DNSLookup parameter is wrong in config/domain file. Value is '$DNSLookup' (should be 0 or 1)"); }
1488
if (! $SiteDomain) { error("SiteDomain parameter not defined in your config/domain file. You must add it for using this version of AWStats."); }
1489
if ($AllowToUpdateStatsFromBrowser !~ /[0-1]/) { $AllowToUpdateStatsFromBrowser=0; }
1490
if ($AllowFullYearView !~ /[0-3]/) { $AllowFullYearView=2; }
1491
# Optional setup section
1492
if ($EnableLockForUpdate !~ /[0-1]/) { $EnableLockForUpdate=0; }
1493
$DNSStaticCacheFile||='dnscache.txt';
1494
$DNSLastUpdateCacheFile||='dnscachelastupdate.txt';
1495
if ($DNSStaticCacheFile eq $DNSLastUpdateCacheFile) { error("DNSStaticCacheFile and DNSLastUpdateCacheFile must have different values."); }
1496
if ($AllowAccessFromWebToAuthenticatedUsersOnly !~ /[0-1]/) { $AllowAccessFromWebToAuthenticatedUsersOnly=0; }
1497
if ($CreateDirDataIfNotExists !~ /[0-1]/) { $CreateDirDataIfNotExists=0; }
1498
if ($BuildReportFormat !~ /html|xml/i) { $BuildReportFormat='html'; }
1499
if ($BuildHistoryFormat !~ /text/) { $BuildHistoryFormat='text'; }
1500
if ($SaveDatabaseFilesWithPermissionsForEveryone !~ /[0-1]/) { $SaveDatabaseFilesWithPermissionsForEveryone=1; }
1501
if ($PurgeLogFile !~ /[0-1]/) { $PurgeLogFile=0; }
1502
if ($ArchiveLogRecords !~ /[0-1]/) { $ArchiveLogRecords=1; }
1503
if ($KeepBackupOfHistoricFiles !~ /[0-1]/) { $KeepBackupOfHistoricFiles=0; }
1504
$DefaultFile[0]||='index.html';
1505
if ($AuthenticatedUsersNotCaseSensitive !~ /[0-1]/) { $AuthenticatedUsersNotCaseSensitive=0; }
1506
if ($URLNotCaseSensitive !~ /[0-1]/) { $URLNotCaseSensitive=0; }
1507
if ($URLWithAnchor !~ /[0-1]/) { $URLWithAnchor=0; }
1508
$URLQuerySeparators =~ s/\s//g;
1509
if (! $URLQuerySeparators) { $URLQuerySeparators='?;'; }
1510
if ($URLWithQuery !~ /[0-1]/) { $URLWithQuery=0; }
1511
if ($URLReferrerWithQuery !~ /[0-1]/) { $URLReferrerWithQuery=0; }
1512
if ($WarningMessages !~ /[0-1]/) { $WarningMessages=1; }
1513
if ($DebugMessages !~ /[0-1]/) { $DebugMessages=1; }
1514
if ($NbOfLinesForCorruptedLog !~ /^\d+/ || $NbOfLinesForCorruptedLog<1) { $NbOfLinesForCorruptedLog=50; }
1515
if ($Expires !~ /^\d+/) { $Expires=0; }
1516
if ($DecodeUA !~ /[0-1]/) { $DecodeUA=0; }
1517
$MiscTrackerUrl||='/js/awstats_misc_tracker.js';
1518
# Optional accuracy setup section
1519
if ($LevelForWormsDetection !~ /^\d+/) { $LevelForWormsDetection=0; }
1520
if ($LevelForRobotsDetection !~ /^\d+/) { $LevelForRobotsDetection=2; }
1521
if ($LevelForBrowsersDetection !~ /^\d+/) { $LevelForBrowsersDetection=2; }
1522
if ($LevelForOSDetection !~ /^\d+/) { $LevelForOSDetection=2; }
1523
if ($LevelForRefererAnalyze !~ /^\d+/) { $LevelForRefererAnalyze=2; }
1524
if ($LevelForFileTypesDetection !~ /^\d+/) { $LevelForFileTypesDetection=2; }
1525
if ($LevelForSearchEnginesDetection !~ /^\d+/) { $LevelForSearchEnginesDetection=2; }
1526
if ($LevelForKeywordsDetection !~ /^\d+/) { $LevelForKeywordsDetection=2; }
1527
# Optional extra setup section
1528
foreach my $extracpt (1..@ExtraName-1) {
1529
if ($ExtraStatTypes[$extracpt] !~ /[PHBL]/) { $ExtraStatTypes[$extracpt]='PHBL'; }
1530
if ($MaxNbOfExtra[$extracpt] !~ /^\d+$/ || $MaxNbOfExtra[$extracpt]<1) { $MaxNbOfExtra[$extracpt]=20; }
1531
if ($MinHitExtra[$extracpt] !~ /^\d+$/ || $MinHitExtra[$extracpt]<1) { $MinHitExtra[$extracpt]=1; }
1532
if (! $ExtraFirstColumnValues[$extracpt]) { error("Extra section number $extracpt is defined without ExtraSectionFirstColumnValues$extracpt parameter"); }
1533
if (! $ExtraFirstColumnFormat[$extracpt]) { $ExtraFirstColumnFormat[$extracpt] = '%s'; }
1535
# Optional appearance setup section
1536
if ($MaxRowsInHTMLOutput !~ /^\d+/ || $MaxRowsInHTMLOutput<1) { $MaxRowsInHTMLOutput=1000; }
1537
if ($ShowMenu !~ /[01]/) { $ShowMenu=1; }
1538
if ($ShowMonthStats !~ /[01UVPHB]/) { $ShowMonthStats='UVPHB'; }
1539
if ($ShowDaysOfMonthStats !~ /[01VPHB]/) { $ShowDaysOfMonthStats='VPHB'; }
1540
if ($ShowDaysOfWeekStats !~ /[01PHBL]/) { $ShowDaysOfWeekStats='PHBL'; }
1541
if ($ShowHoursStats !~ /[01PHBL]/) { $ShowHoursStats='PHBL'; }
1542
if ($ShowDomainsStats !~ /[01PHB]/) { $ShowDomainsStats='PHB'; }
1543
if ($ShowHostsStats !~ /[01PHBL]/) { $ShowHostsStats='PHBL'; }
1544
if ($ShowAuthenticatedUsers !~ /[01PHBL]/) { $ShowAuthenticatedUsers=0; }
1545
if ($ShowRobotsStats !~ /[01HBL]/) { $ShowRobotsStats='HBL'; }
1546
if ($ShowWormsStats !~ /[01HBL]/) { $ShowWormsStats='HBL'; }
1547
if ($ShowEMailSenders !~ /[01HBML]/) { $ShowEMailSenders=0; }
1548
if ($ShowEMailReceivers !~ /[01HBML]/) { $ShowEMailReceivers=0; }
1549
if ($ShowSessionsStats !~ /[01]/) { $ShowSessionsStats=1; }
1550
if ($ShowPagesStats !~ /[01PBEX]/i) { $ShowPagesStats='PBEX'; }
1551
if ($ShowFileTypesStats !~ /[01HBC]/) { $ShowFileTypesStats='HB'; }
1552
if ($ShowFileSizesStats !~ /[01]/) { $ShowFileSizesStats=1; }
1553
if ($ShowOSStats !~ /[01]/) { $ShowOSStats=1; }
1554
if ($ShowBrowsersStats !~ /[01]/) { $ShowBrowsersStats=1; }
1555
if ($ShowScreenSizeStats !~ /[01]/) { $ShowScreenSizeStats=0; }
1556
if ($ShowOriginStats !~ /[01PH]/) { $ShowOriginStats='PH'; }
1557
if ($ShowKeyphrasesStats !~ /[01]/) { $ShowKeyphrasesStats=1; }
1558
if ($ShowKeywordsStats !~ /[01]/) { $ShowKeywordsStats=1; }
1559
if ($ShowClusterStats !~ /[01PHB]/) { $ShowClusterStats=0; }
1560
if ($ShowMiscStats !~ /[01ajdfrqwp]/) { $ShowMiscStats='a'; }
1561
if ($ShowHTTPErrorsStats !~ /[01]/) { $ShowHTTPErrorsStats=1; }
1562
if ($ShowSMTPErrorsStats !~ /[01]/) { $ShowSMTPErrorsStats=0; }
1563
if ($AddDataArrayMonthStats !~ /[01]/) { $AddDataArrayMonthStats=1; }
1564
if ($AddDataArrayShowDaysOfMonthStats !~ /[01]/) { $AddDataArrayShowDaysOfMonthStats=1; }
1565
if ($AddDataArrayShowDaysOfWeekStats !~ /[01]/) { $AddDataArrayShowDaysOfWeekStats=1; }
1566
if ($AddDataArrayShowHoursStats !~ /[01]/) { $AddDataArrayShowHoursStats=1; }
1567
my @maxnboflist=('Domain','HostsShown','LoginShown','RobotShown','WormsShown','PageShown','OsShown','BrowsersShown','ScreenSizesShown','RefererShown','KeyphrasesShown','KeywordsShown','EMailsShown');
1568
my @maxnboflistdefaultval=(10,10,10,10,5,10,10,10,5,10,10,10,20);
1569
foreach my $i (0..(@maxnboflist-1)) {
1570
if (! $MaxNbOf{$maxnboflist[$i]} || $MaxNbOf{$maxnboflist[$i]} !~ /^\d+$/ || $MaxNbOf{$maxnboflist[$i]}<1) { $MaxNbOf{$maxnboflist[$i]}=$maxnboflistdefaultval[$i]; }
1572
my @minhitlist=('Domain','Host','Login','Robot','Worm','File','Os','Browser','ScreenSize','Refer','Keyphrase','Keyword','EMail');
1573
my @minhitlistdefaultval=(1,1,1,1,1,1,1,1,1,1,1,1,1);
1574
foreach my $i (0..(@minhitlist-1)) {
1575
if (! $MinHit{$minhitlist[$i]} || $MinHit{$minhitlist[$i]} !~ /^\d+$/ || $MinHit{$minhitlist[$i]}<1) { $MinHit{$minhitlist[$i]}=$minhitlistdefaultval[$i]; }
1577
if ($FirstDayOfWeek !~ /[01]/) { $FirstDayOfWeek=1; }
1578
if ($UseFramesWhenCGI !~ /[01]/) { $UseFramesWhenCGI=1; }
1579
if ($DetailedReportsOnNewWindows !~ /[012]/) { $DetailedReportsOnNewWindows=1; }
1580
if ($ShowLinksOnUrl !~ /[01]/) { $ShowLinksOnUrl=1; }
1581
if ($MaxLengthOfShownURL !~ /^\d+/ || $MaxLengthOfShownURL<1) { $MaxLengthOfShownURL=64; }
1582
if ($ShowLinksToWhoIs !~ /[01]/) { $ShowLinksToWhoIs=0; }
1583
$Logo||='awstats_logo6.png';
1584
$LogoLink||='http://awstats.sourceforge.net';
1585
if ($BarWidth !~ /^\d+/ || $BarWidth<1) { $BarWidth=260; }
1586
if ($BarHeight !~ /^\d+/ || $BarHeight<1) { $BarHeight=90; }
1587
$color_Background =~ s/#//g; if ($color_Background !~ /^[0-9|A-H]+$/i) { $color_Background='FFFFFF'; }
1588
$color_TableBGTitle =~ s/#//g; if ($color_TableBGTitle !~ /^[0-9|A-H]+$/i) { $color_TableBGTitle='CCCCDD'; }
1589
$color_TableTitle =~ s/#//g; if ($color_TableTitle !~ /^[0-9|A-H]+$/i) { $color_TableTitle='000000'; }
1590
$color_TableBG =~ s/#//g; if ($color_TableBG !~ /^[0-9|A-H]+$/i) { $color_TableBG='CCCCDD'; }
1591
$color_TableRowTitle =~ s/#//g; if ($color_TableRowTitle !~ /^[0-9|A-H]+$/i) { $color_TableRowTitle='FFFFFF'; }
1592
$color_TableBGRowTitle =~ s/#//g; if ($color_TableBGRowTitle !~ /^[0-9|A-H]+$/i) { $color_TableBGRowTitle='ECECEC'; }
1593
$color_TableBorder =~ s/#//g; if ($color_TableBorder !~ /^[0-9|A-H]+$/i) { $color_TableBorder='ECECEC'; }
1594
$color_text =~ s/#//g; if ($color_text !~ /^[0-9|A-H]+$/i) { $color_text='000000'; }
1595
$color_textpercent =~ s/#//g; if ($color_textpercent !~ /^[0-9|A-H]+$/i) { $color_textpercent='606060'; }
1596
$color_titletext =~ s/#//g; if ($color_titletext !~ /^[0-9|A-H]+$/i) { $color_titletext='000000'; }
1597
$color_weekend =~ s/#//g; if ($color_weekend !~ /^[0-9|A-H]+$/i) { $color_weekend='EAEAEA'; }
1598
$color_link =~ s/#//g; if ($color_link !~ /^[0-9|A-H]+$/i) { $color_link='0011BB'; }
1599
$color_hover =~ s/#//g; if ($color_hover !~ /^[0-9|A-H]+$/i) { $color_hover='605040'; }
1600
$color_other =~ s/#//g; if ($color_other !~ /^[0-9|A-H]+$/i) { $color_other='666688'; }
1601
$color_u =~ s/#//g; if ($color_u !~ /^[0-9|A-H]+$/i) { $color_u='FFA060'; }
1602
$color_v =~ s/#//g; if ($color_v !~ /^[0-9|A-H]+$/i) { $color_v='F4F090'; }
1603
$color_p =~ s/#//g; if ($color_p !~ /^[0-9|A-H]+$/i) { $color_p='4477DD'; }
1604
$color_h =~ s/#//g; if ($color_h !~ /^[0-9|A-H]+$/i) { $color_h='66EEFF'; }
1605
$color_k =~ s/#//g; if ($color_k !~ /^[0-9|A-H]+$/i) { $color_k='2EA495'; }
1606
$color_s =~ s/#//g; if ($color_s !~ /^[0-9|A-H]+$/i) { $color_s='8888DD'; }
1607
$color_e =~ s/#//g; if ($color_e !~ /^[0-9|A-H]+$/i) { $color_e='CEC2E8'; }
1608
$color_x =~ s/#//g; if ($color_x !~ /^[0-9|A-H]+$/i) { $color_x='C1B2E2'; }
1610
# Correct param if default value is asked
1611
if ($ShowMonthStats eq '1') { $ShowMonthStats = 'UVPHB'; }
1612
if ($ShowDaysOfMonthStats eq '1') { $ShowDaysOfMonthStats = 'VPHB'; }
1613
if ($ShowDaysOfWeekStats eq '1') { $ShowDaysOfWeekStats = 'PHBL'; }
1614
if ($ShowHoursStats eq '1') { $ShowHoursStats = 'PHBL'; }
1615
if ($ShowDomainsStats eq '1') { $ShowDomainsStats = 'PHB'; }
1616
if ($ShowHostsStats eq '1') { $ShowHostsStats = 'PHBL'; }
1617
if ($ShowEMailSenders eq '1') { $ShowEMailSenders = 'HBML'; }
1618
if ($ShowEMailReceivers eq '1') { $ShowEMailReceivers = 'HBML'; }
1619
if ($ShowAuthenticatedUsers eq '1') { $ShowAuthenticatedUsers = 'PHBL'; }
1620
if ($ShowRobotsStats eq '1') { $ShowRobotsStats = 'HBL'; }
1621
if ($ShowWormsStats eq '1') { $ShowWormsStats = 'HBL'; }
1622
if ($ShowPagesStats eq '1') { $ShowPagesStats = 'PBEX'; }
1623
if ($ShowFileTypesStats eq '1') { $ShowFileTypesStats = 'HB'; }
1624
if ($ShowOriginStats eq '1') { $ShowOriginStats = 'PH'; }
1625
if ($ShowClusterStats eq '1') { $ShowClusterStats = 'PHB'; }
1626
if ($ShowMiscStats eq '1') { $ShowMiscStats = 'ajdfrqwp'; }
1628
# Convert extra sections data into @ExtraConditionType, @ExtraConditionTypeVal...
1629
foreach my $extranum (1..@ExtraName-1) {
1631
foreach my $conditioncouple (split(/\s*\|\s*/, $ExtraCondition[$extranum])) {
1632
my ($conditiontype, $conditiontypeval)=split(/,/,$conditioncouple,2);
1633
$ExtraConditionType[$extranum][$part]=$conditiontype;
1634
if ($conditiontypeval =~ /^REGEX\[(.*)\]$/i) { $conditiontypeval=$1; }
1635
#else { $conditiontypeval=quotemeta($conditiontypeval); }
1636
$ExtraConditionTypeVal[$extranum][$part]=qr/$conditiontypeval/i;
1640
foreach my $rowkeycouple (split(/\s*\|\s*/, $ExtraFirstColumnValues[$extranum])) {
1641
my ($rowkeytype, $rowkeytypeval)=split(/,/,$rowkeycouple,2);
1642
$ExtraFirstColumnValuesType[$extranum][$part]=$rowkeytype;
1643
if ($rowkeytypeval =~ /^REGEX\[(.*)\]$/i) { $rowkeytypeval=$1; }
1644
#else { $rowkeytype=quotemeta($rowkeytype); }
1645
$ExtraFirstColumnValuesTypeVal[$extranum][$part]=qr/$rowkeytypeval/i;
1650
# Show definitive value for major parameters
1652
debug(" LogFile='$LogFile'",2);
1653
debug(" LogFormat='$LogFormat'",2);
1654
debug(" LogSeparator='$LogSeparator'",2);
1655
debug(" DNSLookup='$DNSLookup'",2);
1656
debug(" DirData='$DirData'",2);
1657
debug(" DirCgi='$DirCgi'",2);
1658
debug(" DirIcons='$DirIcons'",2);
1659
debug(" SiteDomain='$SiteDomain'",2);
1660
debug(" MiscTrackerUrl='$MiscTrackerUrl'",2);
1661
foreach (keys %MaxNbOf) { debug(" MaxNbOf{$_}=$MaxNbOf{$_}",2); }
1662
foreach (keys %MinHit) { debug(" MinHit{$_}=$MinHit{$_}",2); }
1663
foreach my $extranum (1..@ExtraName-1) {
1664
debug(" ExtraConditionType[$extranum] is array ".join(',',@{$ExtraConditionType[$extranum]}),2);
1665
debug(" ExtraConditionTypeVal[$extranum] is array ".join(',',@{$ExtraConditionTypeVal[$extranum]}),2);
1666
debug(" ExtraFirstColumnValuesType[$extranum] is array ".join(',',@{$ExtraFirstColumnValuesType[$extranum]}),2);
1667
debug(" ExtraFirstColumnValuesTypeVal[$extranum] is array ".join(',',@{$ExtraFirstColumnValuesTypeVal[$extranum]}),2);
1671
# Deny URLWithQueryWithOnlyFollowingParameters and URLWithQueryWithoutFollowingParameters both set
1672
if (@URLWithQueryWithOnly && @URLWithQueryWithout) {
1673
error("URLWithQueryWithOnlyFollowingParameters and URLWithQueryWithoutFollowingParameters can't be both set at the same time");
1675
# Deny $ShowHTTPErrorsStats and $ShowSMTPErrorsStats both set
1676
if ($ShowHTTPErrorsStats && $ShowSMTPErrorsStats) {
1677
error("ShowHTTPErrorsStats and ShowSMTPErrorsStats can't be both set at the same time");
1680
# Deny LogFile if contains a pipe and PurgeLogFile || ArchiveLogRecords set on
1681
if (($PurgeLogFile || $ArchiveLogRecords) && $LogFile =~ /\|\s*$/) {
1682
error("A pipe in log file name is not allowed if PurgeLogFile and ArchiveLogRecords are not set to 0");
1684
# If not a migrate, check if DirData is OK
1685
if (! $MigrateStats && ! -d $DirData) {
1686
if ($CreateDirDataIfNotExists) {
1687
if ($Debug) { debug(" Make directory $DirData",2); }
1688
my $mkdirok=mkdir "$DirData", 0766;
1689
if (! $mkdirok) { error("$PROG failed to create directory DirData (DirData=\"$DirData\", CreateDirDataIfNotExists=$CreateDirDataIfNotExists)."); }
1692
error("AWStats database directory defined in config file by 'DirData' parameter ($DirData) does not exist or is not writable.");
1696
if ($LogType eq 'S') { $NOTSORTEDRECORDTOLERANCE=1000000; }
1700
#------------------------------------------------------------------------------
1701
# Function: Common function used by init function of plugins
1702
# Parameters: AWStats version required by plugin
1705
# Return: '' if ok, "Error: xxx" if error
1706
#------------------------------------------------------------------------------
1707
sub Check_Plugin_Version {
1708
my $PluginNeedAWStatsVersion=shift;
1709
if (! $PluginNeedAWStatsVersion) { return 0; }
1710
$VERSION =~ /^(\d+)\.(\d+)/;
1711
my $numAWStatsVersion=($1*1000)+$2;
1712
$PluginNeedAWStatsVersion =~ /^(\d+)\.(\d+)/;
1713
my $numPluginNeedAWStatsVersion=($1*1000)+$2;
1714
if ($numPluginNeedAWStatsVersion > $numAWStatsVersion) {
1715
return "Error: AWStats version $PluginNeedAWStatsVersion or higher is required. Detected $VERSION.";
1721
#------------------------------------------------------------------------------
1722
# Function: Return a checksum for an array of string
1723
# Parameters: Array of string
1726
# Return: Checksum number
1727
#------------------------------------------------------------------------------
1732
# $checksum = MD5->hexhash($string);
1734
while ($i < length($string)) {
1735
my $c=substr($string,$i,1);
1736
$checksum+=(ord($c)<<(8*$j));
1737
if ($j++ > 3) { $j=0; }
1744
#------------------------------------------------------------------------------
1745
# Function: Load plugins files
1747
# Input: $DIR @PluginsToLoad
1750
#------------------------------------------------------------------------------
1752
# Check plugin files in common possible directories :
1753
# Windows and standard package: "$DIR/plugins" (plugins in same dir than awstats.pl)
1754
# Redhat : "/usr/local/awstats/wwwroot/cgi-bin/plugins"
1755
# Debian package : "/usr/share/awstats/plugins"
1756
my @PossiblePluginsDir=("$DIR/plugins","/usr/local/awstats/wwwroot/cgi-bin/plugins","/usr/share/awstats/plugins");
1757
my %DirAddedInINC=();
1759
foreach my $key (keys %NoLoadPlugin) { if ($NoLoadPlugin{$key} < 0) { push @PluginsToLoad, $key; } }
1760
if ($Debug) { debug("Call to Read_Plugins with list: ".join(',',@PluginsToLoad)); }
1761
foreach my $plugininfo (@PluginsToLoad) {
1762
my @loadplugin=split(/\s+/,$plugininfo,2);
1763
my $pluginfile=$loadplugin[0]; $pluginfile =~ s/\.pm$//i;
1764
# Check if we plugin is not disabled
1765
if ($NoLoadPlugin{$pluginfile} && $NoLoadPlugin{$pluginfile} > 0) {
1766
if ($Debug) { debug(" Plugin load for '$pluginfile' has been disabled from parameters"); }
1769
my $pluginparam=$loadplugin[1]||'';
1770
$pluginfile =~ /([^\/\\]*)$/;
1773
if (! $PluginsLoaded{'init'}{"$pluginname"}) { # Plugin not already loaded
1774
my %pluginisfor=('ipv6'=>'u','hashfiles'=>'u','geoip'=>'u','geoipfree'=>'u','timehires'=>'u','timezone'=>'ou',
1775
'decodeutfkeys'=>'o','hostinfo'=>'o','userinfo'=>'o','urlalias'=>'o','tooltips'=>'o');
1776
if ($pluginisfor{$pluginname}) {
1777
# Do not load "update plugins" if output only
1778
if (! $UpdateStats && scalar keys %HTMLOutput && $pluginisfor{$pluginname} !~ /o/) { $PluginsLoaded{'init'}{"$pluginname"}=1; next; }
1779
# Do not load "output plugins" if update only
1780
if ($UpdateStats && ! scalar keys %HTMLOutput && $pluginisfor{$pluginname} !~ /u/) { $PluginsLoaded{'init'}{"$pluginname"}=1; next; }
1782
else { $PluginsLoaded{'init'}{"$pluginname"}=1; } # Unknown plugins always loaded
1784
foreach my $dir (@PossiblePluginsDir) {
1786
if ($searchdir && (!($searchdir =~ /\/$/)) && (!($searchdir =~ /\\$/)) ) { $searchdir .= "/"; }
1787
my $pluginpath="${searchdir}${pluginfile}.pm";
1788
if (-s "$pluginpath") {
1789
$PluginDir="${searchdir}"; # Set plugin dir
1790
if ($Debug) { debug(" Try to init plugin '$pluginname' ($pluginpath) with param '$pluginparam'",1); }
1791
if (! $DirAddedInINC{"$dir"}) {
1793
$DirAddedInINC{"$dir"}=1;
1796
my $modperl=$ENV{"MOD_PERL"}? eval { require mod_perl; $mod_perl::VERSION >= 1.99 ? 2 : 1 } : 0;
1797
if ($modperl == 2) { $loadret=require "$pluginpath"; }
1798
else { $loadret=require "$pluginfile.pm"; }
1800
if (! $loadret || $loadret =~ /^error/i) {
1801
# Load failed, we stop here
1802
error("Plugin load for plugin '$pluginname' failed with return code: $loadret");
1804
my $ret; # To get init return
1805
my $initfunction="\$ret=Init_$pluginname('$pluginparam')";
1806
my $initret=eval("$initfunction");
1807
if (! $initret || $initret =~ /^error/i) {
1808
# Init function failed, we stop here
1809
error("Plugin init for plugin '$pluginname' failed with return code: ".($initret?"$initret":"$@ (A module required by plugin might be missing)."));
1811
# Plugin load and init successfull
1812
foreach my $elem (split(/\s+/,$initret)) {
1813
# Some functions can only be plugged once
1814
my @UniquePluginsFunctions=('GetCountryCodeByName','GetCountryCodeByAddr','ChangeTime','GetTimeZoneTitle','GetTime','SearchFile','LoadCache','SaveHash','ShowMenu');
1816
foreach my $function (@UniquePluginsFunctions) {
1817
if ("$elem" eq "$function") {
1818
# We try to load a 'unique' function, so we check and stop if already loaded
1819
foreach my $otherpluginname (keys %{$PluginsLoaded{"$elem"}}) {
1820
error("Conflict between plugin '$pluginname' and '$otherpluginname'. They both implements the 'must be unique' function '$elem'.\nYou must choose between one of them. Using together is not possible.");
1826
if ($isuniquefunc) {
1827
# TODO Use $PluginsLoaded{"$elem"}="$pluginname"; for unique func
1828
$PluginsLoaded{"$elem"}{"$pluginname"}=1;
1830
else { $PluginsLoaded{"$elem"}{"$pluginname"}=1; }
1832
$PluginsLoaded{'init'}{"$pluginname"}=1;
1833
if ($Debug) { debug(" Plugin '$pluginname' now hooks functions '$initret'",1); }
1837
if (! $PluginsLoaded{'init'}{"$pluginname"}) {
1838
error("Can't open plugin file \"$pluginfile.pm\" for read.\nCheck if file is in \"".($PossiblePluginsDir[0])."\" directory and is readable.");
1842
warning("Warning: Tried to load plugin \"$pluginname\" twice. Fix config file.");
1846
error("Plugin \"$pluginfile\" is not a valid plugin name.");
1849
# In output, geo ip plugins were not loaded, so message changes can't be done in plugin init function
1850
if ($PluginsLoaded{'init'}{'geoip'} || $PluginsLoaded{'init'}{'geoipfree'}) { $Message[17]=$Message[25]=$Message[148]; }
1853
#------------------------------------------------------------------------------
1854
# Function: Read history file and create/update tmp history file
1855
# Parameters: year,month,withupdate,withpurge,part_to_load[,lastlinenumber,lastlineoffset,lastlinechecksum]
1856
# Input: $DirData $PROG $FileSuffix $LastLine
1858
# Return: Tmp history file name created/updated or '' if withupdate is 0
1859
#------------------------------------------------------------------------------
1860
sub Read_History_With_TmpUpdate {
1862
my $year=sprintf("%04i",shift||0);
1863
my $month=sprintf("%02i",shift||0);
1864
my $withupdate=shift||0;
1865
my $withpurge=shift||0;
1868
my $lastlinenumber=shift||0;
1869
my $lastlineoffset=shift||0;
1870
my $lastlinechecksum=shift||0;
1872
my %allsections=('general'=>1,'misc'=>2,'time'=>3,'visitor'=>4,'day'=>5,
1873
'domain'=>6,'cluster'=>7,'login'=>8,'robot'=>9,'worms'=>10,'emailsender'=>11,'emailreceiver'=>12,
1874
'session'=>13,'sider'=>14,'filetypes'=>15,
1875
'os'=>16,'browser'=>17,'screensize'=>18,'unknownreferer'=>19,'unknownrefererbrowser'=>20,
1876
'origin'=>21,'sereferrals'=>22,'pagerefs'=>23,
1877
'searchwords'=>24,'keywords'=>25,
1879
my $order=(scalar keys %allsections)+1;
1880
foreach (keys %TrapInfosForHTTPErrorCodes) { $allsections{"sider_$_"}=$order++; }
1881
foreach (1..@ExtraName-1) { $allsections{"extra_$_"}=$order++; }
1884
# Variable used to read old format history files
1885
my $readvisitorforbackward=0;
1887
# In standard use of AWStats, the DayRequired variable is always empty
1888
if ($DayRequired) { if ($Debug) { debug("Call to Read_History_With_TmpUpdate [$year,$month,withupdate=$withupdate,withpurge=$withpurge,part=$part,lastlinenumber=$lastlinenumber,lastlineoffset=$lastlineoffset,lastlinechecksum=$lastlinechecksum] ($DayRequired)"); } }
1889
else { if ($Debug) { debug("Call to Read_History_With_TmpUpdate [$year,$month,withupdate=$withupdate,withpurge=$withpurge,part=$part,lastlinenumber=$lastlinenumber,lastlineoffset=$lastlineoffset,lastlinechecksum=$lastlinechecksum]"); } }
1891
# Define SectionsToLoad (which sections to load)
1892
my %SectionsToLoad = ();
1893
if ($part eq 'all') { # Load all needed sections
1895
$SectionsToLoad{'general'}=$order++;
1897
$SectionsToLoad{'time'}=$order++; # Always loaded because needed to count TotalPages, TotalHits, TotalBandwidth
1898
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowHostsStats) || $HTMLOutput{'allhosts'} || $HTMLOutput{'lasthosts'} || $HTMLOutput{'unknownip'}) { $SectionsToLoad{'visitor'}=$order++; } # Must be before day, sider and session section
1899
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && ($ShowDaysOfWeekStats || $ShowDaysOfMonthStats)) || $HTMLOutput{'alldays'}) { $SectionsToLoad{'day'}=$order++; }
1901
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowDomainsStats) || $HTMLOutput{'alldomains'}) { $SectionsToLoad{'domain'}=$order++; }
1902
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowAuthenticatedUsers) || $HTMLOutput{'alllogins'} || $HTMLOutput{'lastlogins'}) { $SectionsToLoad{'login'}=$order++; }
1903
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowRobotsStats) || $HTMLOutput{'allrobots'} || $HTMLOutput{'lastrobots'}) { $SectionsToLoad{'robot'}=$order++; }
1904
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowWormsStats) || $HTMLOutput{'allworms'} || $HTMLOutput{'lastworms'}) { $SectionsToLoad{'worms'}=$order++; }
1905
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowEMailSenders) || $HTMLOutput{'allemails'} || $HTMLOutput{'lastemails'}) { $SectionsToLoad{'emailsender'}=$order++; }
1906
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowEMailReceivers) || $HTMLOutput{'allemailr'} || $HTMLOutput{'lastemailr'}) { $SectionsToLoad{'emailreceiver'}=$order++; }
1908
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowSessionsStats) || $HTMLOutput{'sessions'}) { $SectionsToLoad{'session'}=$order++; }
1909
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowPagesStats) || $HTMLOutput{'urldetail'} || $HTMLOutput{'urlentry'} || $HTMLOutput{'urlexit'}) { $SectionsToLoad{'sider'}=$order++; }
1910
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowFileTypesStats) || $HTMLOutput{'filetypes'}) { $SectionsToLoad{'filetypes'}=$order++; }
1911
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowOSStats) || $HTMLOutput{'osdetail'}) { $SectionsToLoad{'os'}=$order++; }
1912
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowBrowsersStats) || $HTMLOutput{'browserdetail'}) { $SectionsToLoad{'browser'}=$order++; }
1913
if ($UpdateStats || $MigrateStats || $HTMLOutput{'unknownos'}) { $SectionsToLoad{'unknownreferer'}=$order++; }
1914
if ($UpdateStats || $MigrateStats || $HTMLOutput{'unknownbrowser'}) { $SectionsToLoad{'unknownrefererbrowser'}=$order++; }
1915
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowScreenSizeStats)) { $SectionsToLoad{'screensize'}=$order++; }
1917
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowOriginStats) || $HTMLOutput{'origin'}) { $SectionsToLoad{'origin'}=$order++; }
1918
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowOriginStats) || $HTMLOutput{'refererse'}) { $SectionsToLoad{'sereferrals'}=$order++; }
1919
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowOriginStats) || $HTMLOutput{'refererpages'}) { $SectionsToLoad{'pagerefs'}=$order++; }
1920
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowKeyphrasesStats) || $HTMLOutput{'keyphrases'} || $HTMLOutput{'keywords'}) { $SectionsToLoad{'searchwords'}=$order++; }
1921
if (! $withupdate && $HTMLOutput{'main'} && $ShowKeywordsStats) { $SectionsToLoad{'keywords'}=$order++; } # If we update, dont need to load
1923
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowMiscStats)) { $SectionsToLoad{'misc'}=$order++; }
1924
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && ($ShowHTTPErrorsStats || $ShowSMTPErrorsStats)) || $HTMLOutput{'errors'}) { $SectionsToLoad{'errors'}=$order++; }
1925
foreach (keys %TrapInfosForHTTPErrorCodes) {
1926
if ($UpdateStats || $MigrateStats || $HTMLOutput{"errors$_"}) { $SectionsToLoad{"sider_$_"}=$order++; }
1928
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ShowClusterStats)) { $SectionsToLoad{'cluster'}=$order++; }
1929
foreach (1..@ExtraName-1) {
1930
if ($UpdateStats || $MigrateStats || ($HTMLOutput{'main'} && $ExtraStatTypes[$_]) || $HTMLOutput{"extra$_"}) { $SectionsToLoad{"extra_$_"}=$order++; }
1933
else { # Load only required sections
1935
foreach (split(/\s+/,$part)) { $SectionsToLoad{$_}=$order++; }
1938
# Define SectionsToSave (which sections to save)
1939
my %SectionsToSave = ();
1940
if ($withupdate) { %SectionsToSave=%allsections; }
1943
foreach (sort { $SectionsToLoad{$a} <=> $SectionsToLoad{$b} } keys %SectionsToLoad) { debug(" Section '$_' is marked for load",2); }
1944
foreach (sort { $SectionsToSave{$a} <=> $SectionsToSave{$b} } keys %SectionsToSave) { debug(" Section '$_' is marked for save",2); }
1947
# Define value for filetowrite and filetoread (Month before Year kept for backward compatibility)
1950
if ($HistoryAlreadyFlushed{"$year$month"} && -s "$DirData/$PROG$month$year$FileSuffix.tmp.$$") {
1951
# tmp history file was already flushed
1952
$filetoread="$DirData/$PROG$month$year$FileSuffix.tmp.$$";
1953
$filetowrite="$DirData/$PROG$month$year$FileSuffix.tmp.$$.bis";
1956
$filetoread="$DirData/$PROG$DayRequired$month$year$FileSuffix.txt";
1957
$filetowrite="$DirData/$PROG$month$year$FileSuffix.tmp.$$";
1959
if ($Debug) { debug(" History file to read is '$filetoread'",2); }
1961
# Is there an old data file to read or, if migrate, can we open the file for read
1962
if (-s $filetoread || $MigrateStats) { $withread=1; }
1966
open(HISTORY,$filetoread) || error("Couldn't open file \"$filetoread\" for read: $!","","",$MigrateStats);
1967
binmode HISTORY; # Avoid premature EOF due to history files corrupted with \cZ or bin chars
1970
open(HISTORYTMP,">$filetowrite") || error("Couldn't open file \"$filetowrite\" for write: $!");
1972
Save_History("header",$year,$month);
1984
# Ignore lines started by a XML tag
1985
if ($_ =~ /^</) { next; }
1987
# Extract version from first line
1988
if (! $versionnum && $_ =~ /^AWSTATS DATA FILE (\d+).(\d+)/i) {
1989
$versionnum=($1*1000)+$2;
1990
if ($Debug) { debug(" Data file version is $versionnum",1); }
1995
@field=split(/\s+/,$_);
1996
if (! $field[0]) { next; }
1999
if ($field[0] eq 'BEGIN_GENERAL') {
2000
if ($Debug) { debug(" Begin of GENERAL section"); }
2003
if ($field[0] eq 'LastLine') {
2004
if (! $LastLine || $LastLine < int($field[1])) { $LastLine=int($field[1]); };
2005
if ($field[2]) { $LastLineNumber=int($field[2]); }
2006
if ($field[3]) { $LastLineOffset=int($field[3]); }
2007
if ($field[4]) { $LastLineChecksum=int($field[4]); }
2010
if ($field[0] eq 'FirstTime') { if (! $FirstTime{$year.$month} || $FirstTime{$year.$month} > int($field[1])) { $FirstTime{$year.$month}=int($field[1]); }; next; }
2011
if ($field[0] eq 'LastTime') { if (! $LastTime{$year.$month} || $LastTime{$year.$month} < int($field[1])) { $LastTime{$year.$month}=int($field[1]); }; next; }
2012
if ($field[0] eq 'LastUpdate') {
2013
if ($LastUpdate < $field[1]) {
2014
$LastUpdate=int($field[1]);
2015
#$LastUpdateLinesRead=int($field[2]);
2016
#$LastUpdateNewLinesRead=int($field[3]);
2017
#$LastUpdateLinesCorrupted=int($field[4]);
2021
if ($field[0] eq 'TotalVisits') {
2022
if (! $withupdate) { $MonthVisits{$year.$month}+=int($field[1]); }
2023
# Save in MonthVisits also if migrate from a file < 4.x for backward compatibility
2024
if ($MigrateStats && $versionnum < 4000 && ! $MonthVisits{$year.$month}) {
2025
if ($Debug) { debug("File is version < 4000. We save ".int($field[1])." visits in DayXxx arrays",1); }
2026
$DayHits{$year.$month."00"}+=0;
2027
$DayVisits{$year.$month."00"}+=int($field[1]);
2031
if ($field[0] eq 'TotalUnique') { if (! $withupdate) { $MonthUnique{$year.$month}+=int($field[1]); } next; }
2032
if ($field[0] eq 'MonthHostsKnown') { if (! $withupdate) { $MonthHostsKnown{$year.$month}+=int($field[1]); } next; }
2033
if ($field[0] eq 'MonthHostsUnknown') { if (! $withupdate) { $MonthHostsUnknown{$year.$month}+=int($field[1]); } next; }
2035
if ($field[0] eq 'END_GENERAL' # END_GENERAL didn't exist for history files < 5.0
2036
|| ($versionnum < 5000 && $SectionsToLoad{"general"} && $FirstTime{$year.$month} && $LastTime{$year.$month}) ) {
2037
if ($Debug) { debug(" End of GENERAL section"); }
2039
# Show migrate warning for backward compatibility
2040
if ($versionnum < 5000 && ! $MigrateStats && ! $BadFormatWarning{$year.$month}) {
2041
if ($FrameName ne 'mainleft') {
2042
$BadFormatWarning{$year.$month}=1;
2043
my $message="Warning: Data file '$filetoread' has an old history file format (version $versionnum). You should upgrade it...\nFrom command line: $PROG.$Extension -migrate=\"$filetoread\"";
2044
if ($ENV{'GATEWAY_INTERFACE'} && $AllowToUpdateStatsFromBrowser) { $message.="\nFrom your browser with URL: <a href=\"http://".$ENV{"SERVER_NAME"}.$ENV{"SCRIPT_NAME"}."?migrate=$filetoread\">http://".$ENV{"SERVER_NAME"}.$ENV{"SCRIPT_NAME"}."?migrate=$filetoread</a>"; }
2045
warning("$message");
2048
if (! ($versionnum < 5000) && $MigrateStats && ! $BadFormatWarning{$year.$month}) {
2049
$BadFormatWarning{$year.$month}=1;
2050
warning("Warning: You are migrating a file that is already a recent version (migrate not required for files version $versionnum).","","",1);
2052
# If migrate and version < 4.x we need to include BEGIN_UNKNOWNIP into BEGIN_VISITOR for backward compatibility
2053
if ($MigrateStats && $versionnum < 4000) {
2054
if ($Debug) { debug("File is version < 4000. We add UNKNOWNIP in sections to load",1); }
2055
$SectionsToLoad{'unknownip'}=99;
2058
delete $SectionsToLoad{'general'};
2059
if ($SectionsToSave{'general'}) { Save_History('general',$year,$month,$lastlinenumber,$lastlineoffset,$lastlinechecksum); delete $SectionsToSave{'general'}; }
2061
# Test for backward compatibility
2062
if ($versionnum < 5000 && ! $withupdate) {
2063
# We must find another way to init MonthUnique MonthHostsKnown and MonthHostsUnknown
2064
if ($Debug) { debug(" We ask to count MonthUnique, MonthHostsKnown and MonthHostsUnknown in visitor section because they are not stored in general section for this data file (version $versionnum)."); }
2065
$readvisitorforbackward=($SectionsToLoad{"visitor"}?1:2);
2066
$SectionsToLoad{"visitor"}=4;
2069
if (! scalar %SectionsToLoad) {
2070
if ($Debug) { debug(" Stop reading history file. Got all we need."); }
2074
if ($versionnum >= 5000) { next; } # We can forget 'END_GENERAL' line and read next one
2078
if ($field[0] eq 'BEGIN_MISC') {
2079
if ($Debug) { debug(" Begin of MISC section"); }
2081
my $count=0;my $countloaded=0;
2085
if ($SectionsToLoad{'misc'}) {
2087
if ($field[1]) { $_misc_p{$field[0]}+=int($field[1]); }
2088
if ($field[2]) { $_misc_h{$field[0]}+=int($field[2]); }
2089
if ($field[3]) { $_misc_k{$field[0]}+=int($field[3]); }
2094
@field=split(/\s+/,$_); $countlines++;
2096
until ($field[0] eq 'END_MISC' || ! $_);
2097
if ($field[0] ne 'END_MISC') { error("History file \"$filetoread\" is corrupted (End of section MISC not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2098
if ($Debug) { debug(" End of MISC section ($count entries, $countloaded loaded)"); }
2099
delete $SectionsToLoad{'misc'};
2100
if ($SectionsToSave{'misc'}) {
2101
Save_History('misc',$year,$month); delete $SectionsToSave{'misc'};
2102
if ($withpurge) { %_misc_p=(); %_misc_h=(); %_misc_k=(); }
2104
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2109
if ($field[0] eq 'BEGIN_CLUSTER') {
2110
if ($Debug) { debug(" Begin of CLUSTER section"); }
2112
my $count=0;my $countloaded=0;
2116
if ($SectionsToLoad{'cluster'}) {
2118
if ($field[1]) { $_cluster_p{$field[0]}+=int($field[1]); }
2119
if ($field[2]) { $_cluster_h{$field[0]}+=int($field[2]); }
2120
if ($field[3]) { $_cluster_k{$field[0]}+=int($field[3]); }
2125
@field=split(/\s+/,$_); $countlines++;
2127
until ($field[0] eq 'END_CLUSTER' || ! $_);
2128
if ($field[0] ne 'END_CLUSTER') { error("History file \"$filetoread\" is corrupted (End of section CLUSTER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2129
if ($Debug) { debug(" End of CLUSTER section ($count entries, $countloaded loaded)"); }
2130
delete $SectionsToLoad{'cluster'};
2131
if ($SectionsToSave{'cluster'}) {
2132
Save_History('cluster',$year,$month); delete $SectionsToSave{'cluster'};
2133
if ($withpurge) { %_cluster_p=(); %_cluster_h=(); %_cluster_k=(); }
2135
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2140
if ($field[0] eq 'BEGIN_TIME') {
2141
my $monthpages=0;my $monthhits=0;my $monthbytes=0;
2142
my $monthnotviewedpages=0;my $monthnotviewedhits=0;my $monthnotviewedbytes=0;
2143
if ($Debug) { debug(" Begin of TIME section"); }
2145
my $count=0;my $countloaded=0;
2147
if ($field[0] ne '') { # Test on ne '' because field[0] is '0' for hour 0)
2149
if ($SectionsToLoad{'time'}) {
2150
if ($withupdate || $MonthRequired eq 'all' || $MonthRequired eq "$month") { # Still required
2152
if ($field[1]) { $_time_p[$field[0]]+=int($field[1]); }
2153
if ($field[2]) { $_time_h[$field[0]]+=int($field[2]); }
2154
if ($field[3]) { $_time_k[$field[0]]+=int($field[3]); }
2155
if ($field[4]) { $_time_nv_p[$field[0]]+=int($field[4]); }
2156
if ($field[5]) { $_time_nv_h[$field[0]]+=int($field[5]); }
2157
if ($field[6]) { $_time_nv_k[$field[0]]+=int($field[6]); }
2159
$monthpages+=int($field[1]);
2160
$monthhits+=int($field[2]);
2161
$monthbytes+=int($field[3]);
2162
$monthnotviewedpages+=int($field[4]||0);
2163
$monthnotviewedhits+=int($field[5]||0);
2164
$monthnotviewedbytes+=int($field[6]||0);
2169
@field=split(/\s+/,$_); $countlines++;
2171
until ($field[0] eq 'END_TIME' || ! $_);
2172
if ($field[0] ne 'END_TIME') { error("History file \"$filetoread\" is corrupted (End of section TIME not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2173
if ($Debug) { debug(" End of TIME section ($count entries, $countloaded loaded)"); }
2174
$MonthPages{$year.$month}+=$monthpages;
2175
$MonthHits{$year.$month}+=$monthhits;
2176
$MonthBytes{$year.$month}+=$monthbytes;
2177
$MonthNotViewedPages{$year.$month}+=$monthnotviewedpages;
2178
$MonthNotViewedHits{$year.$month}+=$monthnotviewedhits;
2179
$MonthNotViewedBytes{$year.$month}+=$monthnotviewedbytes;
2180
delete $SectionsToLoad{'time'};
2181
if ($SectionsToSave{'time'}) {
2182
Save_History('time',$year,$month); delete $SectionsToSave{'time'};
2183
if ($withpurge) { @_time_p=(); @_time_h=(); @_time_k=(); @_time_nv_p=(); @_time_nv_h=(); @_time_nv_k=(); }
2185
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2190
if ($field[0] eq 'BEGIN_ORIGIN') {
2191
if ($Debug) { debug(" Begin of ORIGIN section"); }
2193
my $count=0;my $countloaded=0;
2197
if ($SectionsToLoad{'origin'}) {
2198
if ($field[0] eq 'From0') { $_from_p[0]+=$field[1]; $_from_h[0]+=$field[2]; }
2199
elsif ($field[0] eq 'From1') { $_from_p[1]+=$field[1]; $_from_h[1]+=$field[2]; }
2200
elsif ($field[0] eq 'From2') { $_from_p[2]+=$field[1]; $_from_h[2]+=$field[2]; }
2201
elsif ($field[0] eq 'From3') { $_from_p[3]+=$field[1]; $_from_h[3]+=$field[2]; }
2202
elsif ($field[0] eq 'From4') { $_from_p[4]+=$field[1]; $_from_h[4]+=$field[2]; }
2203
elsif ($field[0] eq 'From5') { $_from_p[5]+=$field[1]; $_from_h[5]+=$field[2]; }
2208
@field=split(/\s+/,$_); $countlines++;
2210
until ($field[0] eq 'END_ORIGIN' || ! $_);
2211
if ($field[0] ne 'END_ORIGIN') { error("History file \"$filetoread\" is corrupted (End of section ORIGIN not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2212
if ($Debug) { debug(" End of ORIGIN section ($count entries, $countloaded loaded)"); }
2213
delete $SectionsToLoad{'origin'};
2214
if ($SectionsToSave{'origin'}) {
2215
Save_History('origin',$year,$month); delete $SectionsToSave{'origin'};
2216
if ($withpurge) { @_from_p=(); @_from_h=(); }
2218
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2222
if ($field[0] eq 'BEGIN_DAY') {
2223
if ($Debug) { debug(" Begin of DAY section"); }
2225
my $count=0;my $countloaded=0;
2229
if ($SectionsToLoad{'day'}) {
2231
if ($field[1]) { $DayPages{$field[0]}+=int($field[1]); }
2232
$DayHits{$field[0]}+=int($field[2]); # DayHits always load (should be >0 and if not it's a day YYYYMM00 resulting of an old file migration)
2233
if ($field[3]) { $DayBytes{$field[0]}+=int($field[3]); }
2234
if ($field[4]) { $DayVisits{$field[0]}+=int($field[4]); }
2239
@field=split(/\s+/,$_); $countlines++;
2241
until ($field[0] eq 'END_DAY' || ! $_);
2242
if ($field[0] ne 'END_DAY') { error("History file \"$filetoread\" is corrupted (End of section DAY not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2243
if ($Debug) { debug(" End of DAY section ($count entries, $countloaded loaded)"); }
2244
delete $SectionsToLoad{'day'};
2245
# WE DO NOT SAVE SECTION NOW BECAUSE VALUES CAN BE CHANGED AFTER READING VISITOR
2246
#if ($SectionsToSave{'day'}) { # Must be made after read of visitor
2247
# Save_History('day',$year,$month); delete $SectionsToSave{'day'};
2248
# if ($withpurge) { %DayPages=(); %DayHits=(); %DayBytes=(); %DayVisits=(); }
2250
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2254
if ($field[0] eq 'BEGIN_VISITOR') {
2255
if ($Debug) { debug(" Begin of VISITOR section"); }
2257
my $count=0;my $countloaded=0;
2262
# For backward compatibility
2263
if ($readvisitorforbackward) {
2264
if ($field[1]) { $MonthUnique{$year.$month}++; }
2265
if ($MonthRequired ne 'all') {
2266
if ($field[0] !~ /^\d+\.\d+\.\d+\.\d+$/ && $field[0] !~ /^[0-9A-F]*:/i) { $MonthHostsKnown{$year.$month}++; }
2267
else { $MonthHostsUnknown{$year.$month}++; }
2271
# Process data saved in 'wait' arrays
2272
if ($withupdate && $_waithost_e{$field[0]}){
2273
my $timehostl=int($field[4]||0);
2274
my $timehosts=int($field[5]||0);
2275
my $newtimehosts=($_waithost_s{$field[0]}?$_waithost_s{$field[0]}:$_host_s{$field[0]});
2276
my $newtimehostl=($_waithost_l{$field[0]}?$_waithost_l{$field[0]}:$_host_l{$field[0]});
2277
if ($newtimehosts > $timehostl + $VISITTIMEOUT ) {
2278
if ($Debug) { debug(" Visit for $field[0] in 'wait' arrays is a new visit different than last in history",4); }
2279
if ($field[6]) { $_url_x{$field[6]}++; }
2280
$_url_e{$_waithost_e{$field[0]}}++;
2281
$newtimehosts =~ /^(\d\d\d\d\d\d\d\d)/; $DayVisits{$1}++;
2282
if ($timehosts && $timehostl) { $_session{GetSessionRange($timehosts,$timehostl)}++; }
2283
if ($_waithost_s{$field[0]}) {
2284
# First session found in log was followed by another one so it's finished
2285
$_session{GetSessionRange($newtimehosts,$newtimehostl)}++;
2287
# Here $_host_l $_host_s and $_host_u are correctly defined
2290
if ($Debug) { debug(" Visit for $field[0] in 'wait' arrays is following of last visit in history",4); }
2291
if ($_waithost_s{$field[0]}) {
2292
# First session found in log was followed by another one so it's finished
2293
$_session{GetSessionRange(MinimumButNoZero($timehosts,$newtimehosts),$timehostl>$newtimehostl?$timehostl:$newtimehostl)}++;
2294
# Here $_host_l $_host_s and $_host_u are correctly defined
2297
# We correct $_host_l $_host_s and $_host_u
2298
if ($timehostl > $newtimehostl) {
2299
$_host_l{$field[0]}=$timehostl;
2300
$_host_u{$field[0]}=$field[6];
2302
if ($timehosts < $newtimehosts) {
2303
$_host_s{$field[0]}=$timehosts;
2307
delete $_waithost_e{$field[0]};
2308
delete $_waithost_l{$field[0]};
2309
delete $_waithost_s{$field[0]};
2310
delete $_waithost_u{$field[0]};
2314
if ($readvisitorforbackward!=2 && $SectionsToLoad{'visitor'}) { # if readvisitorforbackward==2 we do not load
2320
if ($HTMLOutput{'allhosts'} || $HTMLOutput{'lasthosts'}) {
2321
if ((!$FilterIn{'host'} || $field[0] =~ /$FilterIn{'host'}/)
2322
&& (!$FilterEx{'host'} || $field[0] !~ /$FilterEx{'host'}/)) { $loadrecord=1; }
2324
elsif ($MonthRequired eq 'all' || $field[2] >= $MinHit{'Host'}) {
2325
if ($HTMLOutput{'unknownip'} && ($field[0] =~ /^\d+\.\d+\.\d+\.\d+$/ || $field[0] =~ /^[0-9A-F]*:/i)) { $loadrecord=1; }
2326
elsif ($HTMLOutput{'main'} && ($MonthRequired eq 'all' || $countloaded < $MaxNbOf{'HostsShown'})) { $loadrecord=1; }
2330
if ($field[1]) { $_host_p{$field[0]}+=$field[1]; }
2331
if ($field[2]) { $_host_h{$field[0]}+=$field[2]; }
2332
if ($field[3]) { $_host_k{$field[0]}+=$field[3]; }
2333
if ($field[4] && ! $_host_l{$field[0]}) { # We save last connexion params if not previously defined
2334
$_host_l{$field[0]}=int($field[4]);
2335
if ($withupdate) { # field[5] field[6] are used only for update
2336
if ($field[5] && ! $_host_s{$field[0]}) { $_host_s{$field[0]}=int($field[5]); }
2337
if ($field[6] && ! $_host_u{$field[0]}) { $_host_u{$field[0]}=$field[6]; }
2346
@field=split(/\s+/,$_); $countlines++;
2348
until ($field[0] eq 'END_VISITOR' || ! $_);
2349
if ($field[0] ne 'END_VISITOR') { error("History file \"$filetoread\" is corrupted (End of section VISITOR not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2350
if ($Debug) { debug(" End of VISITOR section ($count entries, $countloaded loaded)"); }
2351
delete $SectionsToLoad{'visitor'};
2352
# WE DO NOT SAVE SECTION NOW TO BE SURE TO HAVE THIS LARGE SECTION NOT AT THE BEGINNING OF FILE
2353
#if ($SectionsToSave{'visitor'}) {
2354
# Save_History('visitor',$year,$month); delete $SectionsToSave{'visitor'};
2355
# if ($withpurge) { %_host_p=(); %_host_h=(); %_host_k=(); %_host_l=(); %_host_s=(); %_host_u=(); }
2357
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2360
# BEGIN_UNKNOWNIP for backward compatibility
2361
if ($field[0] eq 'BEGIN_UNKNOWNIP') {
2363
if ($Debug) { debug(" Begin of UNKNOWNIP section"); }
2365
my $count=0;my $countloaded=0;
2369
if ($SectionsToLoad{'unknownip'}) {
2370
$iptomigrate{$field[0]}=$field[1]||0;
2376
@field=split(/\s+/,$_); $countlines++;
2378
until ($field[0] eq 'END_UNKNOWNIP' || ! $_);
2379
if ($field[0] ne 'END_UNKNOWNIP') { error("History file \"$filetoread\" is corrupted (End of section UNKOWNIP not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2380
if ($Debug) { debug(" End of UNKOWNIP section ($count entries, $countloaded loaded)"); }
2381
delete $SectionsToLoad{'visitor'};
2382
# THIS SECTION IS NEVER SAVED. ONLY READ FOR MIGRATE AND CONVERTED INTO VISITOR SECTION
2383
foreach (keys %iptomigrate) {
2384
$_host_p{$_}+=int($_host_p{'Unknown'}/$countloaded);
2385
$_host_h{$_}+=int($_host_h{'Unknown'}/$countloaded);
2386
$_host_k{$_}+=int($_host_k{'Unknown'}/$countloaded);
2387
if ($iptomigrate{$_} > 0) { $_host_l{$_}=$iptomigrate{$_} };
2389
delete $_host_p{'Unknown'};
2390
delete $_host_h{'Unknown'};
2391
delete $_host_k{'Unknown'};
2392
delete $_host_l{'Unknown'};
2393
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2397
if ($field[0] eq 'BEGIN_LOGIN') {
2398
if ($Debug) { debug(" Begin of LOGIN section"); }
2400
my $count=0;my $countloaded=0;
2404
if ($SectionsToLoad{'login'}) {
2406
if ($field[1]) { $_login_p{$field[0]}+=$field[1]; }
2407
if ($field[2]) { $_login_h{$field[0]}+=$field[2]; }
2408
if ($field[3]) { $_login_k{$field[0]}+=$field[3]; }
2409
if (! $_login_l{$field[0]} && $field[4]) { $_login_l{$field[0]}=int($field[4]); }
2414
@field=split(/\s+/,$_); $countlines++;
2416
until ($field[0] eq 'END_LOGIN' || ! $_);
2417
if ($field[0] ne 'END_LOGIN') { error("History file \"$filetoread\" is corrupted (End of section LOGIN not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2418
if ($Debug) { debug(" End of LOGIN section ($count entries, $countloaded loaded)"); }
2419
delete $SectionsToLoad{'login'};
2420
if ($SectionsToSave{'login'}) {
2421
Save_History('login',$year,$month); delete $SectionsToSave{'login'};
2422
if ($withpurge) { %_login_p=(); %_login_h=(); %_login_k=(); %_login_l=(); }
2424
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2428
if ($field[0] eq 'BEGIN_DOMAIN') {
2429
if ($Debug) { debug(" Begin of DOMAIN section"); }
2431
my $count=0;my $countloaded=0;
2435
if ($SectionsToLoad{'domain'}) {
2437
if ($field[1]) { $_domener_p{$field[0]}+=$field[1]; }
2438
if ($field[2]) { $_domener_h{$field[0]}+=$field[2]; }
2439
if ($field[3]) { $_domener_k{$field[0]}+=$field[3]; }
2444
@field=split(/\s+/,$_); $countlines++;
2446
until ($field[0] eq 'END_DOMAIN' || ! $_);
2447
if ($field[0] ne 'END_DOMAIN') { error("History file \"$filetoread\" is corrupted (End of section DOMAIN not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2448
if ($Debug) { debug(" End of DOMAIN section ($count entries, $countloaded loaded)"); }
2449
delete $SectionsToLoad{'domain'};
2450
if ($SectionsToSave{'domain'}) {
2451
Save_History('domain',$year,$month); delete $SectionsToSave{'domain'};
2452
if ($withpurge) { %_domener_p=(); %_domener_h=(); %_domener_k=(); }
2454
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2458
if ($field[0] eq 'BEGIN_SESSION') {
2459
if ($Debug) { debug(" Begin of SESSION section"); }
2461
my $count=0;my $countloaded=0;
2465
if ($SectionsToLoad{'session'}) {
2467
if ($field[1]) { $_session{$field[0]}+=$field[1]; }
2472
@field=split(/\s+/,$_); $countlines++;
2474
until ($field[0] eq 'END_SESSION' || ! $_);
2475
if ($field[0] ne 'END_SESSION') { error("History file \"$filetoread\" is corrupted (End of section SESSION not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2476
if ($Debug) { debug(" End of SESSION section ($count entries, $countloaded loaded)"); }
2477
delete $SectionsToLoad{'session'};
2478
# WE DO NOT SAVE SECTION NOW BECAUSE VALUES CAN BE CHANGED AFTER READING VISITOR
2479
#if ($SectionsToSave{'session'}) {
2480
# Save_History('session',$year,$month); delete $SectionsToSave{'session'}; }
2481
# if ($withpurge) { %_session=(); }
2483
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2487
if ($field[0] eq 'BEGIN_OS') {
2488
if ($Debug) { debug(" Begin of OS section"); }
2490
my $count=0;my $countloaded=0;
2494
if ($SectionsToLoad{'os'}) {
2496
if ($field[1]) { $_os_h{$field[0]}+=$field[1]; }
2501
@field=split(/\s+/,$_); $countlines++;
2503
until ($field[0] eq 'END_OS' || ! $_);
2504
if ($field[0] ne 'END_OS') { error("History file \"$filetoread\" is corrupted (End of section OS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2505
if ($Debug) { debug(" End of OS section ($count entries, $countloaded loaded)"); }
2506
delete $SectionsToLoad{'os'};
2507
if ($SectionsToSave{'os'}) {
2508
Save_History('os',$year,$month); delete $SectionsToSave{'os'};
2509
if ($withpurge) { %_os_h=(); }
2511
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2515
if ($field[0] eq 'BEGIN_BROWSER') {
2516
if ($Debug) { debug(" Begin of BROWSER section"); }
2518
my $count=0;my $countloaded=0;
2522
if ($SectionsToLoad{'browser'}) {
2524
if ($field[1]) { $_browser_h{$field[0]}+=$field[1]; }
2529
@field=split(/\s+/,$_); $countlines++;
2531
until ($field[0] eq 'END_BROWSER' || ! $_);
2532
if ($field[0] ne 'END_BROWSER') { error("History file \"$filetoread\" is corrupted (End of section BROWSER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2533
if ($Debug) { debug(" End of BROWSER section ($count entries, $countloaded loaded)"); }
2534
delete $SectionsToLoad{'browser'};
2535
if ($SectionsToSave{'browser'}) {
2536
Save_History('browser',$year,$month); delete $SectionsToSave{'browser'};
2537
if ($withpurge) { %_browser_h=(); }
2539
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2542
# BEGIN_UNKNOWNREFERER
2543
if ($field[0] eq 'BEGIN_UNKNOWNREFERER') {
2544
if ($Debug) { debug(" Begin of UNKNOWNREFERER section"); }
2546
my $count=0;my $countloaded=0;
2550
if ($SectionsToLoad{'unknownreferer'}) {
2552
if (! $_unknownreferer_l{$field[0]}) { $_unknownreferer_l{$field[0]}=int($field[1]); }
2557
@field=split(/\s+/,$_); $countlines++;
2559
until ($field[0] eq 'END_UNKNOWNREFERER' || ! $_);
2560
if ($field[0] ne 'END_UNKNOWNREFERER') { error("History file \"$filetoread\" is corrupted (End of section UNKNOWNREFERER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2561
if ($Debug) { debug(" End of UNKNOWNREFERER section ($count entries, $countloaded loaded)"); }
2562
delete $SectionsToLoad{'unknownreferer'};
2563
if ($SectionsToSave{'unknownreferer'}) {
2564
Save_History('unknownreferer',$year,$month); delete $SectionsToSave{'unknownreferer'};
2565
if ($withpurge) { %_unknownreferer_l=(); }
2567
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2570
# BEGIN_UNKNOWNREFERERBROWSER
2571
if ($field[0] eq 'BEGIN_UNKNOWNREFERERBROWSER') {
2572
if ($Debug) { debug(" Begin of UNKNOWNREFERERBROWSER section"); }
2574
my $count=0;my $countloaded=0;
2578
if ($SectionsToLoad{'unknownrefererbrowser'}) {
2580
if (! $_unknownrefererbrowser_l{$field[0]}) { $_unknownrefererbrowser_l{$field[0]}=int($field[1]); }
2585
@field=split(/\s+/,$_); $countlines++;
2587
until ($field[0] eq 'END_UNKNOWNREFERERBROWSER' || ! $_);
2588
if ($field[0] ne 'END_UNKNOWNREFERERBROWSER') { error("History file \"$filetoread\" is corrupted (End of section UNKNOWNREFERERBROWSER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2589
if ($Debug) { debug(" End of UNKNOWNREFERERBROWSER section ($count entries, $countloaded loaded)"); }
2590
delete $SectionsToLoad{'unknownrefererbrowser'};
2591
if ($SectionsToSave{'unknownrefererbrowser'}) {
2592
Save_History('unknownrefererbrowser',$year,$month); delete $SectionsToSave{'unknownrefererbrowser'};
2593
if ($withpurge) { %_unknownrefererbrowser_l=(); }
2595
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2599
if ($field[0] eq 'BEGIN_SCREENSIZE') {
2600
if ($Debug) { debug(" Begin of SCREENSIZE section"); }
2602
my $count=0;my $countloaded=0;
2606
if ($SectionsToLoad{'screensize'}) {
2608
if ($field[1]) { $_screensize_h{$field[0]}+=$field[1]; }
2613
@field=split(/\s+/,$_); $countlines++;
2615
until ($field[0] eq 'END_SCREENSIZE' || ! $_);
2616
if ($field[0] ne 'END_SCREENSIZE') { error("History file \"$filetoread\" is corrupted (End of section SCREENSIZE not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2617
if ($Debug) { debug(" End of SCREENSIZE section ($count entries, $countloaded loaded)"); }
2618
delete $SectionsToLoad{'screensize'};
2619
if ($SectionsToSave{'screensize'}) {
2620
Save_History('screensize',$year,$month); delete $SectionsToSave{'screensize'};
2621
if ($withpurge) { %_screensize_h=(); }
2623
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2627
if ($field[0] eq 'BEGIN_ROBOT') {
2628
if ($Debug) { debug(" Begin of ROBOT section"); }
2630
my $count=0;my $countloaded=0;
2634
if ($SectionsToLoad{'robot'}) {
2636
if ($field[1]) { $_robot_h{$field[0]}+=$field[1]; }
2637
if ($versionnum < 5000 || ! $field[3]) { # For backward compatibility
2638
if (! $_robot_l{$field[0]}) { $_robot_l{$field[0]}=int($field[2]); }
2641
$_robot_k{$field[0]}+=$field[2];
2642
if (! $_robot_l{$field[0]}) { $_robot_l{$field[0]}=int($field[3]); }
2644
if ($field[4]) { $_robot_r{$field[0]}+=$field[4]; }
2649
@field=split(/\s+/,$_); $countlines++;
2651
until ($field[0] eq 'END_ROBOT' || ! $_);
2652
if ($field[0] ne 'END_ROBOT') { error("History file \"$filetoread\" is corrupted (End of section ROBOT not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2653
if ($Debug) { debug(" End of ROBOT section ($count entries, $countloaded loaded)"); }
2654
delete $SectionsToLoad{'robot'};
2655
if ($SectionsToSave{'robot'}) {
2656
Save_History('robot',$year,$month); delete $SectionsToSave{'robot'};
2657
if ($withpurge) { %_robot_h=(); %_robot_k=(); %_robot_l=(); %_robot_r=(); }
2659
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2663
if ($field[0] eq 'BEGIN_WORMS') {
2664
if ($Debug) { debug(" Begin of WORMS section"); }
2666
my $count=0;my $countloaded=0;
2670
if ($SectionsToLoad{'worms'}) {
2672
if ($field[1]) { $_worm_h{$field[0]}+=$field[1]; }
2673
$_worm_k{$field[0]}+=$field[2];
2674
if (! $_worm_l{$field[0]}) { $_worm_l{$field[0]}=int($field[3]); }
2679
@field=split(/\s+/,$_); $countlines++;
2681
until ($field[0] eq 'END_WORMS' || ! $_);
2682
if ($field[0] ne 'END_WORMS') { error("History file \"$filetoread\" is corrupted (End of section WORMS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2683
if ($Debug) { debug(" End of WORMS section ($count entries, $countloaded loaded)"); }
2684
delete $SectionsToLoad{'worms'};
2685
if ($SectionsToSave{'worms'}) {
2686
Save_History('worms',$year,$month); delete $SectionsToSave{'worms'};
2687
if ($withpurge) { %_worm_h=(); %_worm_k=(); %_worm_l=(); }
2689
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2693
if ($field[0] eq 'BEGIN_EMAILSENDER') {
2694
if ($Debug) { debug(" Begin of EMAILSENDER section"); }
2696
my $count=0;my $countloaded=0;
2700
if ($SectionsToLoad{'emailsender'}) {
2702
if ($field[1]) { $_emails_h{$field[0]}+=$field[1]; }
2703
if ($field[2]) { $_emails_k{$field[0]}+=$field[2]; }
2704
if (! $_emails_l{$field[0]}) { $_emails_l{$field[0]}=int($field[3]); }
2709
@field=split(/\s+/,$_); $countlines++;
2711
until ($field[0] eq 'END_EMAILSENDER' || ! $_);
2712
if ($field[0] ne 'END_EMAILSENDER') { error("History file \"$filetoread\" is corrupted (End of section EMAILSENDER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2713
if ($Debug) { debug(" End of EMAILSENDER section ($count entries, $countloaded loaded)"); }
2714
delete $SectionsToLoad{'emailsender'};
2715
if ($SectionsToSave{'emailsender'}) {
2716
Save_History('emailsender',$year,$month); delete $SectionsToSave{'emailsender'};
2717
if ($withpurge) { %_emails_h=(); %_emails_k=(); %_emails_l=(); }
2719
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2723
if ($field[0] eq 'BEGIN_EMAILRECEIVER') {
2724
if ($Debug) { debug(" Begin of EMAILRECEIVER section"); }
2726
my $count=0;my $countloaded=0;
2730
if ($SectionsToLoad{'emailreceiver'}) {
2732
if ($field[1]) { $_emailr_h{$field[0]}+=$field[1]; }
2733
if ($field[2]) { $_emailr_k{$field[0]}+=$field[2]; }
2734
if (! $_emailr_l{$field[0]}) { $_emailr_l{$field[0]}=int($field[3]); }
2739
@field=split(/\s+/,$_); $countlines++;
2741
until ($field[0] eq 'END_EMAILRECEIVER' || ! $_);
2742
if ($field[0] ne 'END_EMAILRECEIVER') { error("History file \"$filetoread\" is corrupted (End of section EMAILRECEIVER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2743
if ($Debug) { debug(" End of EMAILRECEIVER section ($count entries, $countloaded loaded)"); }
2744
delete $SectionsToLoad{'emailreceiver'};
2745
if ($SectionsToSave{'emailreceiver'}) {
2746
Save_History('emailreceiver',$year,$month); delete $SectionsToSave{'emailreceiver'};
2747
if ($withpurge) { %_emailr_h=(); %_emailr_k=(); %_emailr_l=(); }
2749
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2753
if ($field[0] eq 'BEGIN_SIDER') {
2754
if ($Debug) { debug(" Begin of SIDER section"); }
2756
my $count=0;my $countloaded=0;
2760
if ($SectionsToLoad{'sider'}) {
2766
if ($HTMLOutput{'main'}) {
2767
if ($MonthRequired eq 'all') { $loadrecord=1; }
2769
if ($countloaded < $MaxNbOf{'PageShown'} && $field[1] >= $MinHit{'File'}) { $loadrecord=1; }
2770
$TotalDifferentPages++;
2773
else { # This is for $HTMLOutput = urldetail, urlentry or urlexit
2774
if ($MonthRequired eq 'all' ) {
2775
if ((!$FilterIn{'url'} || $field[0] =~ /$FilterIn{'url'}/)
2776
&& (!$FilterEx{'url'} || $field[0] !~ /$FilterEx{'url'}/)) { $loadrecord=1; }
2779
if ((!$FilterIn{'url'} || $field[0] =~ /$FilterIn{'url'}/)
2780
&& (!$FilterEx{'url'} || $field[0] !~ /$FilterEx{'url'}/)
2781
&& $field[1] >= $MinHit{'File'}) { $loadrecord=1; }
2782
$TotalDifferentPages++;
2785
# Posssibilite de mettre if ($FilterIn{'url'} && $field[0] =~ /$FilterIn{'url'}/) mais il faut gerer TotalPages de la meme maniere
2786
if ($versionnum < 4000) { # For history files < 4.0
2787
$TotalEntries+=($field[2]||0);
2790
$TotalBytesPages+=($field[2]||0);
2791
$TotalEntries+=($field[3]||0);
2792
$TotalExits+=($field[4]||0);
2796
if ($field[1]) { $_url_p{$field[0]}+=$field[1]; }
2797
if ($versionnum < 4000) { # For history files < 4.0
2798
if ($field[2]) { $_url_e{$field[0]}+=$field[2]; }
2799
$_url_k{$field[0]}=0;
2802
if ($field[2]) { $_url_k{$field[0]}+=$field[2]; }
2803
if ($field[3]) { $_url_e{$field[0]}+=$field[3]; }
2804
if ($field[4]) { $_url_x{$field[0]}+=$field[4]; }
2812
@field=split(/\s+/,$_); $countlines++;
2814
until ($field[0] eq 'END_SIDER' || ! $_);
2815
if ($field[0] ne 'END_SIDER') { error("History file \"$filetoread\" is corrupted (End of section SIDER not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2816
if ($Debug) { debug(" End of SIDER section ($count entries, $countloaded loaded)"); }
2817
delete $SectionsToLoad{'sider'};
2818
# WE DO NOT SAVE SECTION NOW BECAUSE VALUES CAN BE CHANGED AFTER READING VISITOR
2819
#if ($SectionsToSave{'sider'}) {
2820
# Save_History('sider',$year,$month); delete $SectionsToSave{'sider'};
2821
# if ($withpurge) { %_url_p=(); %_url_k=(); %_url_e=(); %_url_x=(); }
2823
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2827
if ($field[0] eq 'BEGIN_FILETYPES') {
2828
if ($Debug) { debug(" Begin of FILETYPES section"); }
2830
my $count=0;my $countloaded=0;
2834
if ($SectionsToLoad{'filetypes'}) {
2836
if ($field[1]) { $_filetypes_h{$field[0]}+=$field[1]; }
2837
if ($field[2]) { $_filetypes_k{$field[0]}+=$field[2]; }
2838
if ($field[3]) { $_filetypes_gz_in{$field[0]}+=$field[3]; }
2839
if ($field[4]) { $_filetypes_gz_out{$field[0]}+=$field[4]; }
2844
@field=split(/\s+/,$_); $countlines++;
2846
until ($field[0] eq 'END_FILETYPES' || ! $_);
2847
if ($field[0] ne 'END_FILETYPES') { error("History file \"$filetoread\" is corrupted (End of section FILETYPES not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2848
if ($Debug) { debug(" End of FILETYPES section ($count entries, $countloaded loaded)"); }
2849
delete $SectionsToLoad{'filetypes'};
2850
if ($SectionsToSave{'filetypes'}) {
2851
Save_History('filetypes',$year,$month); delete $SectionsToSave{'filetypes'};
2852
if ($withpurge) { %_filetypes_h=(); %_filetypes_k=(); %_filetypes_gz_in=(); %_filetypes_gz_out=(); }
2854
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2858
if ($field[0] eq 'BEGIN_SEREFERRALS') {
2859
if ($Debug) { debug(" Begin of SEREFERRALS section"); }
2861
my $count=0;my $countloaded=0;
2865
if ($SectionsToLoad{'sereferrals'}) {
2867
if ($versionnum < 5004) { # For history files < 5.4
2868
my $se=$field[0]; $se=~s/\./\\./g;
2869
if ($SearchEnginesHashID{$se}) {
2870
$_se_referrals_h{$SearchEnginesHashID{$se}}+=$field[1]||0;
2873
$_se_referrals_h{$field[0]}+=$field[1]||0;
2876
elsif ($versionnum < 5091) { # For history files < 5.91
2877
my $se=$field[0]; $se=~s/\./\\./g;
2878
if ($SearchEnginesHashID{$se}) {
2879
$_se_referrals_p{$SearchEnginesHashID{$se}}+=$field[1]||0;
2880
$_se_referrals_h{$SearchEnginesHashID{$se}}+=$field[2]||0;
2883
$_se_referrals_p{$field[0]}+=$field[1]||0;
2884
$_se_referrals_h{$field[0]}+=$field[2]||0;
2887
if ($field[1]) { $_se_referrals_p{$field[0]}+=$field[1]; }
2888
if ($field[2]) { $_se_referrals_h{$field[0]}+=$field[2]; }
2894
@field=split(/\s+/,$_); $countlines++;
2896
until ($field[0] eq 'END_SEREFERRALS' || ! $_);
2897
if ($field[0] ne 'END_SEREFERRALS') { error("History file \"$filetoread\" is corrupted (End of section SEREFERRALS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2898
if ($Debug) { debug(" End of SEREFERRALS section ($count entries, $countloaded loaded)"); }
2899
delete $SectionsToLoad{'sereferrals'};
2900
if ($SectionsToSave{'sereferrals'}) {
2901
Save_History('sereferrals',$year,$month); delete $SectionsToSave{'sereferrals'};
2902
if ($withpurge) { %_se_referrals_p=(); %_se_referrals_h=(); }
2904
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2908
if ($field[0] eq 'BEGIN_PAGEREFS') {
2909
if ($Debug) { debug(" Begin of PAGEREFS section"); }
2911
my $count=0;my $countloaded=0;
2915
if ($SectionsToLoad{'pagerefs'}) {
2921
if ((!$FilterIn{'refererpages'} || $field[0] =~ /$FilterIn{'refererpages'}/)
2922
&& (!$FilterEx{'refererpages'} || $field[0] !~ /$FilterEx{'refererpages'}/)) { $loadrecord=1; }
2925
if ($versionnum < 5004) { # For history files < 5.4
2926
if ($field[1]) { $_pagesrefs_h{$field[0]}+=int($field[1]); }
2928
if ($field[1]) { $_pagesrefs_p{$field[0]}+=int($field[1]); }
2929
if ($field[2]) { $_pagesrefs_h{$field[0]}+=int($field[2]); }
2937
@field=split(/\s+/,$_); $countlines++;
2939
until ($field[0] eq 'END_PAGEREFS' || ! $_);
2940
if ($field[0] ne 'END_PAGEREFS') { error("History file \"$filetoread\" is corrupted (End of section PAGEREFS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
2941
if ($Debug) { debug(" End of PAGEREFS section ($count entries, $countloaded loaded)"); }
2942
delete $SectionsToLoad{'pagerefs'};
2943
if ($SectionsToSave{'pagerefs'}) {
2944
Save_History('pagerefs',$year,$month); delete $SectionsToSave{'pagerefs'};
2945
if ($withpurge) { %_pagesrefs_p=(); %_pagesrefs_h=(); }
2947
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
2951
if ($field[0] eq 'BEGIN_SEARCHWORDS') {
2952
if ($Debug) { debug(" Begin of SEARCHWORDS section ($MaxNbOf{'KeyphrasesShown'},$MinHit{'Keyphrase'})"); }
2954
my $count=0;my $countloaded=0;
2958
if ($SectionsToLoad{'searchwords'}) {
2964
if ($HTMLOutput{'main'}) {
2965
if ($MonthRequired eq 'all') { $loadrecord=1; }
2967
if ($countloaded < $MaxNbOf{'KeyphrasesShown'} && $field[1] >= $MinHit{'Keyphrase'}) { $loadrecord=1; }
2968
$TotalDifferentKeyphrases++;
2969
$TotalKeyphrases+=($field[1]||0);
2972
elsif ($HTMLOutput{'keyphrases'}) { # Load keyphrases for keyphrases chart
2973
if ($MonthRequired eq 'all' ) { $loadrecord=1; }
2975
if ($field[1] >= $MinHit{'Keyphrase'}) { $loadrecord=1; }
2976
$TotalDifferentKeyphrases++;
2977
$TotalKeyphrases+=($field[1]||0);
2980
if ($HTMLOutput{'keywords'}) { # Load keyphrases for keywords chart
2986
if ($loadrecord==2) {
2987
foreach (split(/\+/,$field[0])) { # field[0] is "val1+val2+..."
2988
$_keywords{$_}+=$field[1];
2992
$_keyphrases{$field[0]}+=$field[1];
3001
@field=split(/\s+/,$_); $countlines++;
3003
until ($field[0] eq 'END_SEARCHWORDS' || ! $_);
3004
if ($field[0] ne 'END_SEARCHWORDS') { error("History file \"$filetoread\" is corrupted (End of section SEARCHWORDS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
3005
if ($Debug) { debug(" End of SEARCHWORDS section ($count entries, $countloaded loaded)"); }
3006
delete $SectionsToLoad{'searchwords'};
3007
if ($SectionsToSave{'searchwords'}) {
3008
Save_History('searchwords',$year,$month); delete $SectionsToSave{'searchwords'}; # This save searwords and keywords sections
3009
if ($withpurge) { %_keyphrases=(); }
3011
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
3015
if ($field[0] eq 'BEGIN_KEYWORDS') {
3016
if ($Debug) { debug(" Begin of KEYWORDS section ($MaxNbOf{'KeywordsShown'},$MinHit{'Keyword'})"); }
3018
my $count=0;my $countloaded=0;
3022
if ($SectionsToLoad{'keywords'}) {
3024
if ($MonthRequired eq 'all') { $loadrecord=1; }
3026
if ($countloaded < $MaxNbOf{'KeywordsShown'} && $field[1] >= $MinHit{'Keyword'}) { $loadrecord=1; }
3027
$TotalDifferentKeywords++;
3028
$TotalKeywords+=($field[1]||0);
3031
if ($field[1]) { $_keywords{$field[0]}+=$field[1]; }
3038
@field=split(/\s+/,$_); $countlines++;
3040
until ($field[0] eq 'END_KEYWORDS' || ! $_);
3041
if ($field[0] ne 'END_KEYWORDS') { error("History file \"$filetoread\" is corrupted (End of section KEYWORDS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
3042
if ($Debug) { debug(" End of KEYWORDS section ($count entries, $countloaded loaded)"); }
3043
delete $SectionsToLoad{'keywords'};
3044
if ($SectionsToSave{'keywords'}) {
3045
Save_History('keywords',$year,$month); delete $SectionsToSave{'keywords'};
3046
if ($withpurge) { %_keywords=(); }
3048
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
3052
if ($field[0] eq 'BEGIN_ERRORS') {
3053
if ($Debug) { debug(" Begin of ERRORS section"); }
3055
my $count=0;my $countloaded=0;
3059
if ($SectionsToLoad{'errors'}) {
3061
if ($field[1]) { $_errors_h{$field[0]}+=$field[1]; }
3062
if ($field[2]) { $_errors_k{$field[0]}+=$field[2]; }
3067
@field=split(/\s+/,$_); $countlines++;
3069
until ($field[0] eq 'END_ERRORS' || ! $_);
3070
if ($field[0] ne 'END_ERRORS') { error("History file \"$filetoread\" is corrupted (End of section ERRORS not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
3071
if ($Debug) { debug(" End of ERRORS section ($count entries, $countloaded loaded)"); }
3072
delete $SectionsToLoad{'errors'};
3073
if ($SectionsToSave{'errors'}) {
3074
Save_History('errors',$year,$month); delete $SectionsToSave{'errors'};
3075
if ($withpurge) { %_errors_h=(); %_errors_k=(); }
3077
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
3081
foreach my $code (keys %TrapInfosForHTTPErrorCodes) {
3082
if ($field[0] eq "BEGIN_SIDER_$code") {
3083
if ($Debug) { debug(" Begin of SIDER_$code section"); }
3085
my $count=0;my $countloaded=0;
3089
if ($SectionsToLoad{"sider_$code"}) {
3091
if ($field[1]) { $_sider404_h{$field[0]}+=$field[1]; }
3092
if ($withupdate || $HTMLOutput{"errors$code"}) {
3093
if ($field[2]) { $_referer404_h{$field[0]}=$field[2]; }
3099
@field=split(/\s+/,$_); $countlines++;
3101
until ($field[0] eq "END_SIDER_$code" || ! $_);
3102
if ($field[0] ne "END_SIDER_$code") { error("History file \"$filetoread\" is corrupted (End of section SIDER_$code not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
3103
if ($Debug) { debug(" End of SIDER_$code section ($count entries, $countloaded loaded)"); }
3104
delete $SectionsToLoad{"sider_$code"};
3105
if ($SectionsToSave{"sider_$code"}) {
3106
Save_History("sider_$code",$year,$month); delete $SectionsToSave{"sider_$code"};
3107
if ($withpurge) { %_sider404_h=(); %_referer404_h=(); }
3109
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
3114
foreach my $extranum (1..@ExtraName-1) {
3115
if ($field[0] eq "BEGIN_EXTRA_$extranum") {
3116
if ($Debug) { debug(" Begin of EXTRA_$extranum"); }
3118
my $count=0;my $countloaded=0;
3120
if ($field[0] ne '') {
3122
if ($SectionsToLoad{"extra_$extranum"}) {
3123
if ($ExtraStatTypes[$extranum] =~ /P/i && $field[1]) { ${'_section_' . $extranum . '_p'}{$field[0]}+=$field[1]; }
3124
${'_section_' . $extranum . '_h'}{$field[0]}+=$field[2];
3125
if ($ExtraStatTypes[$extranum] =~ /B/i && $field[3]) { ${'_section_' . $extranum . '_k'}{$field[0]}+=$field[3]; }
3126
if ($ExtraStatTypes[$extranum] =~ /L/i && ! ${'_section_' . $extranum . '_l'}{$field[0]} && $field[4]) { ${'_section_' . $extranum . '_l'}{$field[0]}=int($field[4]); }
3132
@field=split(/\s+/,$_); $countlines++;
3134
until ($field[0] eq "END_EXTRA_$extranum" || ! $_);
3135
if ($field[0] ne "END_EXTRA_$extranum") { error("History file \"$filetoread\" is corrupted (End of section EXTRA_$extranum not found).\nRestore a recent backup of this file (data for this month will be restored to backup date), remove it (data for month will be lost), or remove the corrupted section in file (data for at least this section will be lost).","","",1); }
3136
if ($Debug) { debug(" End of EXTRA_$extranum section ($count entries, $countloaded loaded)"); }
3137
delete $SectionsToLoad{"extra_$extranum"};
3138
if ($SectionsToSave{"extra_$extranum"}) {
3139
Save_History("extra_$extranum",$year,$month); delete $SectionsToSave{"extra_$extranum"};
3140
if ($withpurge) { %{'_section_' . $extranum . '_p'}=(); %{'_section_' . $extranum . '_h'}=(); %{'_section_' . $extranum . '_b'}=(); %{'_section_' . $extranum . '_l'}=(); }
3142
if (! scalar %SectionsToLoad) { debug(" Stop reading history file. Got all we need."); last; }
3147
# For backward compatibility (ORIGIN section was "HitFromx" in old history files)
3148
if ($SectionsToLoad{'origin'}) {
3149
if ($field[0] eq 'HitFrom0') { $_from_p[0]+=0; $_from_h[0]+=$field[1]; next; }
3150
if ($field[0] eq 'HitFrom1') { $_from_p[1]+=0; $_from_h[1]+=$field[1]; next; }
3151
if ($field[0] eq 'HitFrom2') { $_from_p[2]+=0; $_from_h[2]+=$field[1]; next; }
3152
if ($field[0] eq 'HitFrom3') { $_from_p[3]+=0; $_from_h[3]+=$field[1]; next; }
3153
if ($field[0] eq 'HitFrom4') { $_from_p[4]+=0; $_from_h[4]+=$field[1]; next; }
3154
if ($field[0] eq 'HitFrom5') { $_from_p[5]+=0; $_from_h[5]+=$field[1]; next; }
3160
# Process rest of data saved in 'wait' arrays (data for hosts that are not in history file or no history file found)
3161
# This can change some values for day, sider and session sections
3162
if ($Debug) { debug(" Processing data in 'wait' arrays",3); }
3163
foreach (keys %_waithost_e) {
3164
if ($Debug) { debug(" Visit in 'wait' array for $_ is a new visit",4); }
3165
my $newtimehosts=($_waithost_s{$_}?$_waithost_s{$_}:$_host_s{$_});
3166
my $newtimehostl=($_waithost_l{$_}?$_waithost_l{$_}:$_host_l{$_});
3167
$_url_e{$_waithost_e{$_}}++;
3168
$newtimehosts =~ /^(\d\d\d\d\d\d\d\d)/; $DayVisits{$1}++;
3169
if ($_waithost_s{$_}) {
3170
# There was also a second session in processed log
3171
$_session{GetSessionRange($newtimehosts,$newtimehostl)}++;
3176
# Write all unwrote sections in section order ('general','time', 'day','sider','session' and other...)
3177
foreach my $key (sort { $SectionsToSave{$a} <=> $SectionsToSave{$b} } keys %SectionsToSave) {
3178
Save_History("$key",$year,$month,$lastlinenumber,$lastlineoffset,$lastlinechecksum);
3182
# Update offset in map section and last data in general section then close files
3184
# Update offset of sections in the MAP section
3185
foreach (sort { $PosInFile{$a} <=> $PosInFile{$b} } keys %ValueInFile) {
3186
if ($Debug) { debug(" Update offset of section $_=$ValueInFile{$_} in file at offset $PosInFile{$_}"); }
3187
if ($PosInFile{"$_"}) {
3188
seek(HISTORYTMP,$PosInFile{"$_"},0); print HISTORYTMP $ValueInFile{"$_"};
3191
# Save last data in general sections
3192
if ($Debug) { debug(" Update MonthVisits=$MonthVisits{$year.$month} in file at offset $PosInFile{TotalVisits}"); }
3193
seek(HISTORYTMP,$PosInFile{"TotalVisits"},0); print HISTORYTMP $MonthVisits{$year.$month};
3194
if ($Debug) { debug(" Update MonthUnique=$MonthUnique{$year.$month} in file at offset $PosInFile{TotalUnique}"); }
3195
seek(HISTORYTMP,$PosInFile{"TotalUnique"},0); print HISTORYTMP $MonthUnique{$year.$month};
3196
if ($Debug) { debug(" Update MonthHostsKnown=$MonthHostsKnown{$year.$month} in file at offset $PosInFile{MonthHostsKnown}"); }
3197
seek(HISTORYTMP,$PosInFile{"MonthHostsKnown"},0); print HISTORYTMP $MonthHostsKnown{$year.$month};
3198
if ($Debug) { debug(" Update MonthHostsUnknown=$MonthHostsUnknown{$year.$month} in file at offset $PosInFile{MonthHostsUnknown}"); }
3199
seek(HISTORYTMP,$PosInFile{"MonthHostsUnknown"},0); print HISTORYTMP $MonthHostsUnknown{$year.$month};
3200
close(HISTORYTMP) || error("Failed to write temporary history file");
3203
close(HISTORY) || error("Command for pipe '$filetoread' failed");
3207
if ($withpurge) { &Init_HashArray(); }
3209
# If update, rename tmp file bis into tmp file or set HistoryAlreadyFlushed
3211
if ($HistoryAlreadyFlushed{"$year$month"}) {
3212
if (rename($filetowrite,$filetoread)==0) {
3213
error("Failed to update tmp history file $filetoread");
3217
$HistoryAlreadyFlushed{"$year$month"}=1;
3219
if (! $ListOfYears{"$year"} || $ListOfYears{"$year"} lt "$month") { $ListOfYears{"$year"}="$month"; }
3222
# For backward compatibility, if LastLine does not exist, set to LastTime
3223
$LastLine||=$LastTime{$year.$month};
3225
return ($withupdate?"$filetowrite":"");
3228
#------------------------------------------------------------------------------
3229
# Function: Save a part of history file
3230
# Parameters: sectiontosave,year,month[,lastlinenumber,lastlineoffset,lastlinechecksum]
3231
# Input: $VERSION HISTORYTMP $nowyear $nowmonth $nowday $nowhour $nowmin $nowsec $LastLineNumber $LastLineOffset $LastLineChecksum
3234
#------------------------------------------------------------------------------
3236
my $sectiontosave=shift||'';
3238
my $month=shift||'';
3240
my $lastlinenumber=shift||0;
3241
my $lastlineoffset=shift||0;
3242
my $lastlinechecksum=shift||0;
3243
if (! $lastlinenumber) { # This happens for migrate
3244
$lastlinenumber=$LastLineNumber;
3245
$lastlineoffset=$LastLineOffset;
3246
$lastlinechecksum=$LastLineChecksum;
3249
if ($Debug) { debug(" Save_History [sectiontosave=$sectiontosave,year=$year,month=$month,lastlinenumber=$lastlinenumber,lastlineoffset=$lastlineoffset,lastlinechecksum=$lastlinechecksum]",1); }
3251
my %keysinkeylist=();
3254
if ($sectiontosave eq 'header') {
3255
print HISTORYTMP "AWSTATS DATA FILE $VERSION\n";
3256
print HISTORYTMP "# If you remove this file, all statistics for date $year-$month will be lost/reset.\n";
3257
print HISTORYTMP "\n";
3258
print HISTORYTMP "# Position (offset in bytes) in this file of beginning of each section for\n";
3259
print HISTORYTMP "# direct I/O access. If you made changes somewhere in this file, you should\n";
3260
print HISTORYTMP "# also remove completely the MAP section (AWStats will rewrite it at next\n";
3261
print HISTORYTMP "# update).\n";
3262
print HISTORYTMP "BEGIN_MAP ".(26+(scalar keys %TrapInfosForHTTPErrorCodes)+(scalar @ExtraName?scalar @ExtraName-1:0))."\n";
3263
print HISTORYTMP "POS_GENERAL ";$PosInFile{"general"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3265
print HISTORYTMP "POS_TIME ";$PosInFile{"time"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3266
print HISTORYTMP "POS_VISITOR ";$PosInFile{"visitor"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3267
print HISTORYTMP "POS_DAY ";$PosInFile{"day"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3269
print HISTORYTMP "POS_DOMAIN ";$PosInFile{"domain"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3270
print HISTORYTMP "POS_LOGIN ";$PosInFile{"login"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3271
print HISTORYTMP "POS_ROBOT ";$PosInFile{"robot"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3272
print HISTORYTMP "POS_WORMS ";$PosInFile{"worms"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3273
print HISTORYTMP "POS_EMAILSENDER ";$PosInFile{"emailsender"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3274
print HISTORYTMP "POS_EMAILRECEIVER ";$PosInFile{"emailreceiver"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3276
print HISTORYTMP "POS_SESSION ";$PosInFile{"session"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3277
print HISTORYTMP "POS_SIDER ";$PosInFile{"sider"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3278
print HISTORYTMP "POS_FILETYPES ";$PosInFile{"filetypes"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3279
print HISTORYTMP "POS_OS ";$PosInFile{"os"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3280
print HISTORYTMP "POS_BROWSER ";$PosInFile{"browser"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3281
print HISTORYTMP "POS_SCREENSIZE ";$PosInFile{"screensize"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3282
print HISTORYTMP "POS_UNKNOWNREFERER ";$PosInFile{'unknownreferer'}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3283
print HISTORYTMP "POS_UNKNOWNREFERERBROWSER ";$PosInFile{'unknownrefererbrowser'}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3285
print HISTORYTMP "POS_ORIGIN ";$PosInFile{"origin"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3286
print HISTORYTMP "POS_SEREFERRALS ";$PosInFile{"sereferrals"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3287
print HISTORYTMP "POS_PAGEREFS ";$PosInFile{"pagerefs"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3288
print HISTORYTMP "POS_SEARCHWORDS ";$PosInFile{"searchwords"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3289
print HISTORYTMP "POS_KEYWORDS ";$PosInFile{"keywords"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3291
print HISTORYTMP "POS_MISC ";$PosInFile{"misc"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3292
print HISTORYTMP "POS_ERRORS ";$PosInFile{"errors"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3293
print HISTORYTMP "POS_CLUSTER ";$PosInFile{"cluster"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3294
foreach (keys %TrapInfosForHTTPErrorCodes) {
3295
print HISTORYTMP "POS_SIDER_$_ ";$PosInFile{"sider_$_"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3297
foreach (1..@ExtraName-1) {
3298
print HISTORYTMP "POS_EXTRA_$_ ";$PosInFile{"extra_$_"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3300
print HISTORYTMP "END_MAP\n";
3304
if ($sectiontosave eq 'general') {
3305
if ($LastUpdate < int("$nowyear$nowmonth$nowday$nowhour$nowmin$nowsec")) { $LastUpdate=int("$nowyear$nowmonth$nowday$nowhour$nowmin$nowsec"); }
3306
print HISTORYTMP "\n";
3307
print HISTORYTMP "# LastLine = Date of last record processed - Last record line number in last log - Last record offset in last log - Last record signature value\n";
3308
print HISTORYTMP "# FirstTime = Date of first visit for history file\n";
3309
print HISTORYTMP "# LastTime = Date of last visit for history file\n";
3310
print HISTORYTMP "# LastUpdate = Date of last update - Nb of parsed records - Nb of old records - Nb of new records - Nb of corrupted - Nb of dropped\n";
3311
print HISTORYTMP "# TotalVisits = Number of visits\n";
3312
print HISTORYTMP "# TotalUnique = Number of unique visitors\n";
3313
print HISTORYTMP "# MonthHostsKnown = Number of hosts known\n";
3314
print HISTORYTMP "# MonthHostsUnKnown = Number of hosts unknown\n";
3315
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3316
print HISTORYTMP "BEGIN_GENERAL 8\n";
3317
print HISTORYTMP "LastLine ".($LastLine>0?$LastLine:$LastTime{$year.$month})." $lastlinenumber $lastlineoffset $lastlinechecksum\n";
3318
print HISTORYTMP "FirstTime $FirstTime{$year.$month}\n";
3319
print HISTORYTMP "LastTime $LastTime{$year.$month}\n";
3320
print HISTORYTMP "LastUpdate $LastUpdate $NbOfLinesParsed $NbOfOldLines $NbOfNewLines $NbOfLinesCorrupted $NbOfLinesDropped\n";
3321
print HISTORYTMP "TotalVisits ";$PosInFile{"TotalVisits"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3322
print HISTORYTMP "TotalUnique ";$PosInFile{"TotalUnique"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3323
print HISTORYTMP "MonthHostsKnown ";$PosInFile{"MonthHostsKnown"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3324
print HISTORYTMP "MonthHostsUnknown ";$PosInFile{"MonthHostsUnknown"}=tell HISTORYTMP;print HISTORYTMP "$spacebar\n";
3325
print HISTORYTMP "END_GENERAL\n";
3329
if ($sectiontosave eq 'time') {
3330
print HISTORYTMP "\n";
3331
print HISTORYTMP "# Hour - Pages - Hits - Bandwidth - Not viewed Pages - Not viewed Hits - Not viewed Bandwidth\n";
3332
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3333
print HISTORYTMP "BEGIN_TIME 24\n";
3334
for (my $ix=0; $ix<=23; $ix++) { print HISTORYTMP "$ix ".int($_time_p[$ix])." ".int($_time_h[$ix])." ".int($_time_k[$ix])." ".int($_time_nv_p[$ix])." ".int($_time_nv_h[$ix])." ".int($_time_nv_k[$ix])."\n"; }
3335
print HISTORYTMP "END_TIME\n";
3337
if ($sectiontosave eq 'day') { # This section must be saved after VISITOR section is read
3338
print HISTORYTMP "\n";
3339
print HISTORYTMP "# Date - Pages - Hits - Bandwidth - Visits\n";
3340
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3341
print HISTORYTMP "BEGIN_DAY ".(scalar keys %DayHits)."\n";
3343
foreach (sort keys %DayHits) {
3344
if ($_ =~ /^$year$month/i) { # Found a day entry of the good month
3345
my $page=$DayPages{$_}||0;
3346
my $hits=$DayHits{$_}||0;
3347
my $bytes=$DayBytes{$_}||0;
3348
my $visits=$DayVisits{$_}||0;
3349
print HISTORYTMP "$_ $page $hits $bytes $visits\n";
3350
$monthvisits+=$visits;
3353
$MonthVisits{$year.$month}=$monthvisits;
3354
print HISTORYTMP "END_DAY\n";
3358
if ($sectiontosave eq 'domain') {
3359
print HISTORYTMP "\n";
3360
print HISTORYTMP "# Domain - Pages - Hits - Bandwidth\n";
3361
print HISTORYTMP "# The $MaxNbOf{'Domain'} first Pages must be first (order not required for others)\n";
3362
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3363
print HISTORYTMP "BEGIN_DOMAIN ".(scalar keys %_domener_h)."\n";
3364
# We save page list in score sorted order to get a -output faster and with less use of memory.
3365
&BuildKeyList($MaxNbOf{'Domain'},$MinHit{'Domain'},\%_domener_h,\%_domener_p);
3366
my %keysinkeylist=();
3367
foreach (@keylist) {
3368
$keysinkeylist{$_}=1;
3369
my $page=$_domener_p{$_}||0;
3370
my $bytes=$_domener_k{$_}||0; # ||0 could be commented to reduce history file size
3371
print HISTORYTMP "$_ $page $_domener_h{$_} $bytes\n";
3373
foreach (keys %_domener_h) {
3374
if ($keysinkeylist{$_}) { next; }
3375
my $page=$_domener_p{$_}||0;
3376
my $bytes=$_domener_k{$_}||0; # ||0 could be commented to reduce history file size
3377
print HISTORYTMP "$_ $page $_domener_h{$_} $bytes\n";
3379
print HISTORYTMP "END_DOMAIN\n";
3381
if ($sectiontosave eq 'visitor') {
3382
print HISTORYTMP "\n";
3383
print HISTORYTMP "# Host - Pages - Hits - Bandwidth - Last visit date - [Start of last visit date] - [Last page of last visit]\n";
3384
print HISTORYTMP "# [Start of last visit date] and [Last page of last visit] are saved only if session is not finished\n";
3385
print HISTORYTMP "# The $MaxNbOf{'HostsShown'} first Hits must be first (order not required for others)\n";
3386
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3387
print HISTORYTMP "BEGIN_VISITOR ".(scalar keys %_host_h)."\n";
3388
my $monthhostsknown=0;
3389
# We save page list in score sorted order to get a -output faster and with less use of memory.
3390
&BuildKeyList($MaxNbOf{'HostsShown'},$MinHit{'Host'},\%_host_h,\%_host_p);
3391
my %keysinkeylist=();
3392
foreach my $key (@keylist) {
3393
if ($key !~ /^\d+\.\d+\.\d+\.\d+$/ && $key !~ /^[0-9A-F]*:/i) { $monthhostsknown++; }
3394
$keysinkeylist{$key}=1;
3395
my $page=$_host_p{$key}||0;
3396
my $bytes=$_host_k{$key}||0;
3397
my $timehostl=$_host_l{$key}||0;
3398
my $timehosts=$_host_s{$key}||0;
3399
my $lastpage=$_host_u{$key}||'';
3400
if ($timehostl && $timehosts && $lastpage) {
3401
if (($timehostl+$VISITTIMEOUT) < $LastLine) {
3402
# Session for this user is expired
3403
if ($timehosts) { $_session{GetSessionRange($timehosts,$timehostl)}++; }
3404
if ($lastpage) { $_url_x{$lastpage}++; }
3405
delete $_host_s{$key};
3406
delete $_host_u{$key};
3407
print HISTORYTMP "$key $page $_host_h{$key} $bytes $timehostl\n";
3410
# If this user has started a new session that is not expired
3411
print HISTORYTMP "$key $page $_host_h{$key} $bytes $timehostl $timehosts $lastpage\n";
3415
my $hostl=$timehostl||'';
3416
print HISTORYTMP "$key $page $_host_h{$key} $bytes $hostl\n";
3419
foreach my $key (keys %_host_h) {
3420
if ($keysinkeylist{$key}) { next; }
3421
if ($key !~ /^\d+\.\d+\.\d+\.\d+$/ && $key !~ /^[0-9A-F]*:/i) { $monthhostsknown++; }
3422
my $page=$_host_p{$key}||0;
3423
my $bytes=$_host_k{$key}||0;
3424
my $timehostl=$_host_l{$key}||0;
3425
my $timehosts=$_host_s{$key}||0;
3426
my $lastpage=$_host_u{$key}||'';
3427
if ($timehostl && $timehosts && $lastpage) {
3428
if (($timehostl+$VISITTIMEOUT) < $LastLine) {
3429
# Session for this user is expired
3430
if ($timehosts) { $_session{GetSessionRange($timehosts,$timehostl)}++; }
3431
if ($lastpage) { $_url_x{$lastpage}++; }
3432
delete $_host_s{$key};
3433
delete $_host_u{$key};
3434
print HISTORYTMP "$key $page $_host_h{$key} $bytes $timehostl\n";
3437
# If this user has started a new session that is not expired
3438
print HISTORYTMP "$key $page $_host_h{$key} $bytes $timehostl $timehosts $lastpage\n";
3442
my $hostl=$timehostl||'';
3443
print HISTORYTMP "$key $page $_host_h{$key} $bytes $hostl\n";
3446
$MonthUnique{$year.$month}=(scalar keys %_host_p);
3447
$MonthHostsKnown{$year.$month}=$monthhostsknown;
3448
$MonthHostsUnknown{$year.$month}=(scalar keys %_host_h) - $monthhostsknown;
3449
print HISTORYTMP "END_VISITOR\n";
3451
if ($sectiontosave eq 'login') {
3452
print HISTORYTMP "\n";
3453
print HISTORYTMP "# Login - Pages - Hits - Bandwidth - Last visit\n";
3454
print HISTORYTMP "# The $MaxNbOf{'LoginShown'} first Pages must be first (order not required for others)\n";
3455
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3456
print HISTORYTMP "BEGIN_LOGIN ".(scalar keys %_login_h)."\n";
3457
# We save login list in score sorted order to get a -output faster and with less use of memory.
3458
&BuildKeyList($MaxNbOf{'LoginShown'},$MinHit{'Login'},\%_login_h,\%_login_p);
3459
my %keysinkeylist=();
3460
foreach (@keylist) {
3461
$keysinkeylist{$_}=1;
3462
print HISTORYTMP "$_ ".int($_login_p{$_}||0)." ".int($_login_h{$_}||0)." ".int($_login_k{$_}||0)." ".($_login_l{$_}||'')."\n";
3464
foreach (keys %_login_h) {
3465
if ($keysinkeylist{$_}) { next; }
3466
print HISTORYTMP "$_ ".int($_login_p{$_}||0)." ".int($_login_h{$_}||0)." ".int($_login_k{$_}||0)." ".($_login_l{$_}||'')."\n";
3468
print HISTORYTMP "END_LOGIN\n";
3470
if ($sectiontosave eq 'robot') {
3471
print HISTORYTMP "\n";
3472
print HISTORYTMP "# Robot ID - Hits - Bandwidth - Last visit - Hits on robots.txt\n";
3473
print HISTORYTMP "# The $MaxNbOf{'RobotShown'} first Hits must be first (order not required for others)\n";
3474
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3475
print HISTORYTMP "BEGIN_ROBOT ".(scalar keys %_robot_h)."\n";
3476
# We save robot list in score sorted order to get a -output faster and with less use of memory.
3477
&BuildKeyList($MaxNbOf{'RobotShown'},$MinHit{'Robot'},\%_robot_h,\%_robot_h);
3478
my %keysinkeylist=();
3479
foreach (@keylist) {
3480
$keysinkeylist{$_}=1;
3481
print HISTORYTMP "$_ ".int($_robot_h{$_})." ".int($_robot_k{$_})." $_robot_l{$_} ".int($_robot_r{$_})." \n";
3483
foreach (keys %_robot_h) {
3484
if ($keysinkeylist{$_}) { next; }
3485
print HISTORYTMP "$_ ".int($_robot_h{$_})." ".int($_robot_k{$_})." $_robot_l{$_} ".int($_robot_r{$_})." \n";
3487
print HISTORYTMP "END_ROBOT\n";
3489
if ($sectiontosave eq 'worms') {
3490
print HISTORYTMP "\n";
3491
print HISTORYTMP "# Worm ID - Hits - Bandwidth - Last visit\n";
3492
print HISTORYTMP "# The $MaxNbOf{'WormsShown'} first Hits must be first (order not required for others)\n";
3493
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3494
print HISTORYTMP "BEGIN_WORMS ".(scalar keys %_worm_h)."\n";
3495
# We save worm list in score sorted order to get a -output faster and with less use of memory.
3496
&BuildKeyList($MaxNbOf{'WormsShown'},$MinHit{'Worm'},\%_worm_h,\%_worm_h);
3497
my %keysinkeylist=();
3498
foreach (@keylist) {
3499
$keysinkeylist{$_}=1;
3500
print HISTORYTMP "$_ ".int($_worm_h{$_})." ".int($_worm_k{$_})." $_worm_l{$_}\n";
3502
foreach (keys %_worm_h) {
3503
if ($keysinkeylist{$_}) { next; }
3504
print HISTORYTMP "$_ ".int($_worm_h{$_})." ".int($_worm_k{$_})." $_worm_l{$_}\n";
3506
print HISTORYTMP "END_WORMS\n";
3508
if ($sectiontosave eq 'emailsender') {
3509
print HISTORYTMP "\n";
3510
print HISTORYTMP "# EMail - Hits - Bandwidth - Last visit\n";
3511
print HISTORYTMP "# The $MaxNbOf{'EMailsShown'} first Hits must be first (order not required for others)\n";
3512
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3513
print HISTORYTMP "BEGIN_EMAILSENDER ".(scalar keys %_emails_h)."\n";
3514
# We save sender email list in score sorted order to get a -output faster and with less use of memory.
3515
&BuildKeyList($MaxNbOf{'EMailsShown'},$MinHit{'EMail'},\%_emails_h,\%_emails_h);
3516
my %keysinkeylist=();
3517
foreach (@keylist) {
3518
$keysinkeylist{$_}=1;
3519
print HISTORYTMP "$_ ".int($_emails_h{$_}||0)." ".int($_emails_k{$_}||0)." $_emails_l{$_}\n";
3521
foreach (keys %_emails_h) {
3522
if ($keysinkeylist{$_}) { next; }
3523
print HISTORYTMP "$_ ".int($_emails_h{$_}||0)." ".int($_emails_k{$_}||0)." $_emails_l{$_}\n";
3525
print HISTORYTMP "END_EMAILSENDER\n";
3527
if ($sectiontosave eq 'emailreceiver') {
3528
print HISTORYTMP "\n";
3529
print HISTORYTMP "# EMail - Hits - Bandwidth - Last visit\n";
3530
print HISTORYTMP "# The $MaxNbOf{'EMailsShown'} first hits must be first (order not required for others)\n";
3531
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3532
print HISTORYTMP "BEGIN_EMAILRECEIVER ".(scalar keys %_emailr_h)."\n";
3533
# We save receiver email list in score sorted order to get a -output faster and with less use of memory.
3534
&BuildKeyList($MaxNbOf{'EMailsShown'},$MinHit{'EMail'},\%_emailr_h,\%_emailr_h);
3535
my %keysinkeylist=();
3536
foreach (@keylist) {
3537
$keysinkeylist{$_}=1;
3538
print HISTORYTMP "$_ ".int($_emailr_h{$_}||0)." ".int($_emailr_k{$_}||0)." $_emailr_l{$_}\n";
3540
foreach (keys %_emailr_h) {
3541
if ($keysinkeylist{$_}) { next; }
3542
print HISTORYTMP "$_ ".int($_emailr_h{$_}||0)." ".int($_emailr_k{$_}||0)." $_emailr_l{$_}\n";
3544
print HISTORYTMP "END_EMAILRECEIVER\n";
3548
if ($sectiontosave eq 'session') { # This section must be saved after VISITOR section is read
3549
print HISTORYTMP "\n";
3550
print HISTORYTMP "# Session range - Number of visits\n";
3551
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3552
print HISTORYTMP "BEGIN_SESSION ".(scalar keys %_session)."\n";
3553
foreach (keys %_session) { print HISTORYTMP "$_ ".int($_session{$_})."\n"; }
3554
print HISTORYTMP "END_SESSION\n";
3556
if ($sectiontosave eq 'sider') { # This section must be saved after VISITOR section is read
3557
print HISTORYTMP "\n";
3558
print HISTORYTMP "# URL - Pages - Bandwidth - Entry - Exit\n";
3559
print HISTORYTMP "# The $MaxNbOf{'PageShown'} first Pages must be first (order not required for others)\n";
3560
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3561
print HISTORYTMP "BEGIN_SIDER ".(scalar keys %_url_p)."\n";
3562
# We save page list in score sorted order to get a -output faster and with less use of memory.
3563
&BuildKeyList($MaxNbOf{'PageShown'},$MinHit{'File'},\%_url_p,\%_url_p);
3565
foreach (@keylist) {
3566
$keysinkeylist{$_}=1;
3568
$newkey =~ s/([^:])\/\//$1\//g; # Because some targeted url were taped with 2 / (Ex: //rep//file.htm). We must keep http://rep/file.htm
3569
print HISTORYTMP "$newkey ".int($_url_p{$_}||0)." ".int($_url_k{$_}||0)." ".int($_url_e{$_}||0)." ".int($_url_x{$_}||0)."\n";
3571
foreach (keys %_url_p) {
3572
if ($keysinkeylist{$_}) { next; }
3574
$newkey =~ s/([^:])\/\//$1\//g; # Because some targeted url were taped with 2 / (Ex: //rep//file.htm). We must keep http://rep/file.htm
3575
print HISTORYTMP "$newkey ".int($_url_p{$_}||0)." ".int($_url_k{$_}||0)." ".int($_url_e{$_}||0)." ".int($_url_x{$_}||0)."\n";
3577
print HISTORYTMP "END_SIDER\n";
3579
if ($sectiontosave eq 'filetypes') {
3580
print HISTORYTMP "\n";
3581
print HISTORYTMP "# Files type - Hits - Bandwidth - Bandwidth without compression - Bandwidth after compression\n";
3582
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3583
print HISTORYTMP "BEGIN_FILETYPES ".(scalar keys %_filetypes_h)."\n";
3584
foreach (keys %_filetypes_h) {
3585
my $hits=$_filetypes_h{$_}||0;
3586
my $bytes=$_filetypes_k{$_}||0;
3587
my $bytesbefore=$_filetypes_gz_in{$_}||0;
3588
my $bytesafter=$_filetypes_gz_out{$_}||0;
3589
print HISTORYTMP "$_ $hits $bytes $bytesbefore $bytesafter\n";
3591
print HISTORYTMP "END_FILETYPES\n";
3593
if ($sectiontosave eq 'os') {
3594
print HISTORYTMP "\n";
3595
print HISTORYTMP "# OS ID - Hits\n";
3596
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3597
print HISTORYTMP "BEGIN_OS ".(scalar keys %_os_h)."\n";
3598
foreach (keys %_os_h) { print HISTORYTMP "$_ $_os_h{$_}\n"; }
3599
print HISTORYTMP "END_OS\n";
3601
if ($sectiontosave eq 'browser') {
3602
print HISTORYTMP "\n";
3603
print HISTORYTMP "# Browser ID - Hits\n";
3604
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3605
print HISTORYTMP "BEGIN_BROWSER ".(scalar keys %_browser_h)."\n";
3606
foreach (keys %_browser_h) { print HISTORYTMP "$_ $_browser_h{$_}\n"; }
3607
print HISTORYTMP "END_BROWSER\n";
3609
if ($sectiontosave eq 'screensize') {
3610
print HISTORYTMP "\n";
3611
print HISTORYTMP "# Screen size - Hits\n";
3612
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3613
print HISTORYTMP "BEGIN_SCREENSIZE ".(scalar keys %_screensize_h)."\n";
3614
foreach (keys %_screensize_h) { print HISTORYTMP "$_ $_screensize_h{$_}\n"; }
3615
print HISTORYTMP "END_SCREENSIZE\n";
3619
if ($sectiontosave eq 'unknownreferer') {
3620
print HISTORYTMP "\n";
3621
print HISTORYTMP "# Unknown referer OS - Last visit date\n";
3622
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3623
print HISTORYTMP "BEGIN_UNKNOWNREFERER ".(scalar keys %_unknownreferer_l)."\n";
3624
foreach (keys %_unknownreferer_l) { print HISTORYTMP "$_ $_unknownreferer_l{$_}\n"; }
3625
print HISTORYTMP "END_UNKNOWNREFERER\n";
3627
if ($sectiontosave eq 'unknownrefererbrowser') {
3628
print HISTORYTMP "\n";
3629
print HISTORYTMP "# Unknown referer Browser - Last visit date\n";
3630
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3631
print HISTORYTMP "BEGIN_UNKNOWNREFERERBROWSER ".(scalar keys %_unknownrefererbrowser_l)."\n";
3632
foreach (keys %_unknownrefererbrowser_l) { print HISTORYTMP "$_ $_unknownrefererbrowser_l{$_}\n"; }
3633
print HISTORYTMP "END_UNKNOWNREFERERBROWSER\n";
3635
if ($sectiontosave eq 'origin') {
3636
print HISTORYTMP "\n";
3637
print HISTORYTMP "# Origin - Pages - Hits \n";
3638
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3639
print HISTORYTMP "BEGIN_ORIGIN 6\n";
3640
print HISTORYTMP "From0 ".int($_from_p[0])." ".int($_from_h[0])."\n";
3641
print HISTORYTMP "From1 ".int($_from_p[1])." ".int($_from_h[1])."\n";
3642
print HISTORYTMP "From2 ".int($_from_p[2])." ".int($_from_h[2])."\n";
3643
print HISTORYTMP "From3 ".int($_from_p[3])." ".int($_from_h[3])."\n";
3644
print HISTORYTMP "From4 ".int($_from_p[4])." ".int($_from_h[4])."\n"; # Same site
3645
print HISTORYTMP "From5 ".int($_from_p[5])." ".int($_from_h[5])."\n"; # News
3646
print HISTORYTMP "END_ORIGIN\n";
3648
if ($sectiontosave eq 'sereferrals') {
3649
print HISTORYTMP "\n";
3650
print HISTORYTMP "# Search engine referers ID - Pages - Hits\n";
3651
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3652
print HISTORYTMP "BEGIN_SEREFERRALS ".(scalar keys %_se_referrals_h)."\n";
3653
foreach (keys %_se_referrals_h) { print HISTORYTMP "$_ ".int($_se_referrals_p{$_}||0)." $_se_referrals_h{$_}\n"; }
3654
print HISTORYTMP "END_SEREFERRALS\n";
3656
if ($sectiontosave eq 'pagerefs') {
3657
print HISTORYTMP "\n";
3658
print HISTORYTMP "# External page referers - Pages - Hits\n";
3659
print HISTORYTMP "# The $MaxNbOf{'RefererShown'} first Pages must be first (order not required for others)\n";
3660
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3661
print HISTORYTMP "BEGIN_PAGEREFS ".(scalar keys %_pagesrefs_h)."\n";
3662
# We save page list in score sorted order to get a -output faster and with less use of memory.
3663
&BuildKeyList($MaxNbOf{'RefererShown'},$MinHit{'Refer'},\%_pagesrefs_h,\%_pagesrefs_p);
3665
foreach (@keylist) {
3666
$keysinkeylist{$_}=1;
3668
$newkey =~ s/^http(s|):\/\/([^\/]+)\/$/http$1:\/\/$2/i; # Remove / at end of http://.../ but not at end of http://.../dir/
3669
$newkey =~ s/\s/%20/g;
3670
print HISTORYTMP "$newkey ".int($_pagesrefs_p{$_}||0)." $_pagesrefs_h{$_}\n";
3672
foreach (keys %_pagesrefs_h) {
3673
if ($keysinkeylist{$_}) { next; }
3675
$newkey =~ s/^http(s|):\/\/([^\/]+)\/$/http$1:\/\/$2/i; # Remove / at end of http://.../ but not at end of http://.../dir/
3676
$newkey =~ s/\s/%20/g;
3677
print HISTORYTMP "$newkey ".int($_pagesrefs_p{$_}||0)." $_pagesrefs_h{$_}\n";
3679
print HISTORYTMP "END_PAGEREFS\n";
3681
if ($sectiontosave eq 'searchwords') {
3682
print HISTORYTMP "\n";
3683
print HISTORYTMP "# Search keyphrases - Number of search\n";
3684
print HISTORYTMP "# The $MaxNbOf{'KeyphrasesShown'} first number of search must be first (order not required for others)\n";
3685
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3686
print HISTORYTMP "BEGIN_SEARCHWORDS ".(scalar keys %_keyphrases)."\n";
3687
# We will also build _keywords
3689
# We save key list in score sorted order to get a -output faster and with less use of memory.
3690
&BuildKeyList($MaxNbOf{'KeywordsShown'},$MinHit{'Keyword'},\%_keyphrases,\%_keyphrases);
3692
foreach my $key (@keylist) {
3693
$keysinkeylist{$key}=1;
3695
print HISTORYTMP "$keyphrase $_keyphrases{$key}\n";
3696
foreach (split(/\+/,$key)) { $_keywords{$_}+=$_keyphrases{$key}; } # To init %_keywords
3698
foreach my $key (keys %_keyphrases) {
3699
if ($keysinkeylist{$key}) { next; }
3701
print HISTORYTMP "$keyphrase $_keyphrases{$key}\n";
3702
foreach (split(/\+/,$key)) { $_keywords{$_}+=$_keyphrases{$key}; } # To init %_keywords
3704
print HISTORYTMP "END_SEARCHWORDS\n";
3705
# Now save keywords section
3706
print HISTORYTMP "\n";
3707
print HISTORYTMP "# Search keywords - Number of search\n";
3708
print HISTORYTMP "# The $MaxNbOf{'KeywordsShown'} first number of search must be first (order not required for others)\n";
3709
$ValueInFile{"keywords"}=tell HISTORYTMP;
3710
print HISTORYTMP "BEGIN_KEYWORDS ".(scalar keys %_keywords)."\n";
3711
# We save key list in score sorted order to get a -output faster and with less use of memory.
3712
&BuildKeyList($MaxNbOf{'KeywordsShown'},$MinHit{'Keyword'},\%_keywords,\%_keywords);
3714
foreach (@keylist) {
3715
$keysinkeylist{$_}=1;
3717
print HISTORYTMP "$keyword $_keywords{$_}\n";
3719
foreach (keys %_keywords) {
3720
if ($keysinkeylist{$_}) { next; }
3722
print HISTORYTMP "$keyword $_keywords{$_}\n";
3724
print HISTORYTMP "END_KEYWORDS\n";
3728
if ($sectiontosave eq 'cluster') {
3729
print HISTORYTMP "\n";
3730
print HISTORYTMP "# Cluster ID - Pages - Hits - Bandwidth\n";
3731
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3732
print HISTORYTMP "BEGIN_CLUSTER ".(scalar keys %_cluster_h)."\n";
3733
foreach (keys %_cluster_h) { print HISTORYTMP "$_ ".int($_cluster_p{$_}||0)." ".int($_cluster_h{$_}||0)." ".int($_cluster_k{$_}||0)."\n"; }
3734
print HISTORYTMP "END_CLUSTER\n";
3736
if ($sectiontosave eq 'misc') {
3737
print HISTORYTMP "\n";
3738
print HISTORYTMP "# Misc ID - Pages - Hits - Bandwidth\n";
3739
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3740
print HISTORYTMP "BEGIN_MISC ".(scalar keys %MiscListCalc)."\n";
3741
foreach (keys %MiscListCalc) { print HISTORYTMP "$_ ".int($_misc_p{$_}||0)." ".int($_misc_h{$_}||0)." ".int($_misc_k{$_}||0)."\n"; }
3742
print HISTORYTMP "END_MISC\n";
3744
if ($sectiontosave eq 'errors') {
3745
print HISTORYTMP "\n";
3746
print HISTORYTMP "# Errors - Hits - Bandwidth\n";
3747
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3748
print HISTORYTMP "BEGIN_ERRORS ".(scalar keys %_errors_h)."\n";
3749
foreach (keys %_errors_h) { print HISTORYTMP "$_ $_errors_h{$_} ".int($_errors_k{$_}||0)."\n"; }
3750
print HISTORYTMP "END_ERRORS\n";
3752
# Other - Trapped errors
3753
foreach my $code (keys %TrapInfosForHTTPErrorCodes) {
3754
if ($sectiontosave eq "sider_$code") {
3755
print HISTORYTMP "\n";
3756
print HISTORYTMP "# URL with $code errors - Hits - Last URL referer\n";
3757
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3758
print HISTORYTMP "BEGIN_SIDER_$code ".(scalar keys %_sider404_h)."\n";
3759
foreach (keys %_sider404_h) {
3761
my $newreferer=$_referer404_h{$_}||''; $newreferer =~ s/\s/%20/g;
3762
print HISTORYTMP "$newkey $_sider404_h{$_} $newreferer\n";
3764
print HISTORYTMP "END_SIDER_$code\n";
3767
# Other - Extra stats sections
3768
foreach my $extranum (1..@ExtraName-1) {
3769
if ($sectiontosave eq "extra_$extranum") {
3770
print HISTORYTMP "\n";
3771
print HISTORYTMP "# Extra key - Pages - Hits - Last access - Bandwidth\n";
3772
$ValueInFile{$sectiontosave}=tell HISTORYTMP;
3773
print HISTORYTMP "BEGIN_EXTRA_$extranum\n";
3774
&BuildKeyList($MaxNbOfExtra[$extranum],$MinHitExtra[$extranum],\%{'_section_' . $extranum . '_h'},\%{'_section_' . $extranum . '_p'});
3776
foreach (@keylist) {
3777
$keysinkeylist{$_}=1;
3778
my $page=${'_section_' . $extranum . '_p'}{$_}||0;
3779
my $bytes=${'_section_' . $extranum . '_k'}{$_}||0;
3780
my $lastaccess=${'_section_' . $extranum . '_l'}{$_}||'';
3781
print HISTORYTMP "$_ $page ", ${'_section_' . $extranum . '_h'}{$_}, " $bytes $lastaccess\n"; next;
3783
foreach (keys %{'_section_' . $extranum . '_h'}) {
3784
if ($keysinkeylist{$_}) { next; }
3785
my $page=${'_section_' . $extranum . '_p'}{$_}||0;
3786
my $bytes=${'_section_' . $extranum . '_k'}{$_}||0;
3787
my $lastaccess=${'_section_' . $extranum . '_l'}{$_}||'';
3788
print HISTORYTMP "$_ $page ", ${'_section_' . $extranum . '_h'}{$_}, " $bytes $lastaccess\n"; next;
3790
print HISTORYTMP "END_EXTRA_$extranum\n";
3797
#--------------------------------------------------------------------
3798
# Function: Rename all tmp history file into history
3800
# Input: $DirData $PROG $FileSuffix
3801
# $KeepBackupOfHistoricFile $SaveDatabaseFilesWithPermissionsForEveryone
3803
# Return: 1 Ok, 0 at least one error (tmp files are removed)
3804
#--------------------------------------------------------------------
3805
sub Rename_All_Tmp_History {
3809
if ($Debug) { debug("Call to Rename_All_Tmp_History"); }
3811
opendir(DIR,"$DirData");
3812
foreach (grep /^$PROG(\d\d\d\d\d\d)$FileSuffix\.tmp\.$pid$/, sort readdir DIR) {
3813
/^$PROG(\d\d\d\d\d\d)$FileSuffix\.tmp\.$pid$/;
3814
if ($renameok) { # No rename error yet
3815
if ($Debug) { debug(" Rename new tmp history file $PROG$1$FileSuffix.tmp.$$ into $PROG$1$FileSuffix.txt",1); }
3816
if (-s "$DirData/$PROG$1$FileSuffix.tmp.$$") { # Rename tmp files if size > 0
3817
if ($KeepBackupOfHistoricFiles) {
3818
if (-s "$DirData/$PROG$1$FileSuffix.txt") { # History file already exists. We backup it
3819
if ($Debug) { debug(" Make a backup of old history file into $PROG$1$FileSuffix.bak before",1); }
3820
#if (FileCopy("$DirData/$PROG$1$FileSuffix.txt","$DirData/$PROG$1$FileSuffix.bak")) {
3821
if (rename("$DirData/$PROG$1$FileSuffix.txt", "$DirData/$PROG$1$FileSuffix.bak")==0) {
3822
warning("Warning: Failed to make a backup of \"$DirData/$PROG$1$FileSuffix.txt\" into \"$DirData/$PROG$1$FileSuffix.bak\".");
3824
if ($SaveDatabaseFilesWithPermissionsForEveryone) {
3825
chmod 0666,"$DirData/$PROG$1$FileSuffix.bak";
3829
if ($Debug) { debug(" No need to backup old history file",1); }
3832
if (rename("$DirData/$PROG$1$FileSuffix.tmp.$$", "$DirData/$PROG$1$FileSuffix.txt")==0) {
3833
$renameok=0; # At least one error in renaming working files
3835
unlink "$DirData/$PROG$1$FileSuffix.tmp.$$";
3836
warning("Warning: Failed to rename \"$DirData/$PROG$1$FileSuffix.tmp.$$\" into \"$DirData/$PROG$1$FileSuffix.txt\".\nWrite permissions on \"$PROG$1$FileSuffix.txt\" might be wrong".($ENV{'GATEWAY_INTERFACE'}?" for an 'update from web'":"")." or file might be opened.");
3839
if ($SaveDatabaseFilesWithPermissionsForEveryone) {
3840
chmod 0666,"$DirData/$PROG$1$FileSuffix.txt";
3844
else { # Because of rename error, we remove all remaining tmp files
3845
unlink "$DirData/$PROG$1$FileSuffix.tmp.$$";
3852
#------------------------------------------------------------------------------
3853
# Function: Load DNS cache file entries into a memory hash array
3854
# Parameters: Hash array ref to load into,
3855
# File name to load,
3856
# File suffix to use
3857
# Save to a second plugin file if not up to date
3859
# Output: Hash array is loaded
3860
# Return: 1 No DNS Cache file found, 0 OK
3861
#------------------------------------------------------------------------------
3862
sub Read_DNS_Cache {
3863
my $hashtoload=shift;
3864
my $dnscachefile=shift;
3865
my $filesuffix=shift;
3866
my $savetohash=shift;
3870
my $timetoload = time();
3872
if ($Debug) { debug("Call to Read_DNS_Cache [file=\"$dnscachefile\"]"); }
3873
if ($dnscachefile =~ s/(\.\w+)$//) { $dnscacheext=$1; }
3874
foreach my $dir ("$DirData",".","") {
3876
if ($searchdir && (!($searchdir =~ /\/$/)) && (!($searchdir =~ /\\$/)) ) { $searchdir .= "/"; }
3877
if (-f "${searchdir}$dnscachefile$filesuffix$dnscacheext") { $filetoload="${searchdir}$dnscachefile$filesuffix$dnscacheext"; }
3878
# Plugin call : Change filetoload
3879
if ($PluginsLoaded{'SearchFile'}{'hashfiles'}) { SearchFile_hashfiles($searchdir,$dnscachefile,$filesuffix,$dnscacheext,$filetoload); }
3880
if ($filetoload) { last; } # We found a file to load
3883
if (! $filetoload) {
3884
if ($Debug) { debug(" No DNS Cache file found"); }
3888
# Plugin call : Load hashtoload
3889
if ($PluginsLoaded{'LoadCache'}{'hashfiles'}) { LoadCache_hashfiles($filetoload,$hashtoload); }
3890
if (! scalar keys %$hashtoload) {
3891
open(DNSFILE,"$filetoload") or error("Couldn't open DNS Cache file \"$filetoload\": $!");
3892
#binmode DNSFILE; # If we set binmode here, it seems that the load is broken on ActiveState 5.8
3893
# This is a fast way to load with regexp
3894
%$hashtoload = map(/^(?:\d{0,10}\s+)?([0-9A-F:\.]+)\s+([^\s]+)$/oi,<DNSFILE>);
3897
# Plugin call : Save hash file (all records) with test if up to date to save
3898
if ($PluginsLoaded{'SaveHash'}{'hashfiles'}) { SaveHash_hashfiles($filetoload,$hashtoload,1,0); }
3901
if ($Debug) { debug(" Loaded ".(scalar keys %$hashtoload)." items from $filetoload in ".(time()-$timetoload)." seconds.",1); }
3905
#------------------------------------------------------------------------------
3906
# Function: Save a memory hash array into a DNS cache file
3907
# Parameters: Hash array ref to save,
3908
# File name to save,
3909
# File suffix to use
3912
# Return: 0 OK, 1 Error
3913
#------------------------------------------------------------------------------
3914
sub Save_DNS_Cache_File {
3915
my $hashtosave=shift;
3916
my $dnscachefile=shift;
3917
my $filesuffix=shift;
3921
my $timetosave = time();
3922
my $nbofelemtosave=$NBOFLASTUPDATELOOKUPTOSAVE;
3923
my $nbofelemsaved=0;
3925
if ($Debug) { debug("Call to Save_DNS_Cache_File [file=\"$dnscachefile\"]"); }
3926
if (! scalar keys %$hashtosave) {
3927
if ($Debug) { debug(" No data to save"); }
3930
if ($dnscachefile =~ s/(\.\w+)$//) { $dnscacheext=$1; }
3931
$filetosave="$dnscachefile$filesuffix$dnscacheext";
3932
# Plugin call : Save hash file (only $NBOFLASTUPDATELOOKUPTOSAVE records) with no test if up to date
3933
if ($PluginsLoaded{'SaveHash'}{'hashfiles'}) { SaveHash_hashfiles($filetosave,$hashtosave,0,$nbofelemtosave,$nbofelemsaved); }
3934
if (! $nbofelemsaved) {
3935
$filetosave="$dnscachefile$filesuffix$dnscacheext";
3936
if ($Debug) { debug(" Save data ".($nbofelemtosave?"($nbofelemtosave records max)":"(all records)")." into file $filetosave"); }
3937
if (! open(DNSFILE,">$filetosave")) {
3938
warning("Warning: Failed to open for writing last update DNS Cache file \"$filetosave\": $!");
3942
my $starttimemin=int($starttime/60);
3943
foreach my $key (keys %$hashtosave) {
3944
#if ($hashtosave->{$key} ne '*') {
3945
my $ipsolved=$hashtosave->{$key};
3946
print DNSFILE "$starttimemin\t$key\t".($ipsolved eq 'ip'?'*':$ipsolved)."\n"; # Change 'ip' to '*' for backward compatibility
3947
if (++$nbofelemsaved >= $NBOFLASTUPDATELOOKUPTOSAVE) { last; }
3952
if ($SaveDatabaseFilesWithPermissionsForEveryone) {
3953
chmod 0666,"$filetosave";
3957
if ($Debug) { debug(" Saved $nbofelemsaved items into $filetosave in ".(time()-$timetosave)." seconds.",1); }
3961
#------------------------------------------------------------------------------
3962
# Function: Return time elapsed since last call in miliseconds
3963
# Parameters: 0|1 (0 reset counter, 1 no reset)
3966
# Return: Number of miliseconds elapsed since last call
3967
#------------------------------------------------------------------------------
3968
sub GetDelaySinceStart {
3969
if (shift) { $StartSeconds=0; } # Reset chrono
3970
my ($newseconds, $newmicroseconds)=(time(),0);
3971
# Plugin call : Return seconds and milliseconds
3972
if ($PluginsLoaded{'GetTime'}{'timehires'}) { GetTime_timehires($newseconds, $newmicroseconds); }
3973
if (! $StartSeconds) { $StartSeconds=$newseconds; $StartMicroseconds=$newmicroseconds; }
3974
return (($newseconds-$StartSeconds)*1000+int(($newmicroseconds-$StartMicroseconds)/1000));
3977
#------------------------------------------------------------------------------
3978
# Function: Reset all variables whose name start with _ because a new month start
3980
# Input: $YearRequired All variables whose name start with _
3981
# Output: All variables whose name start with _
3983
#------------------------------------------------------------------------------
3984
sub Init_HashArray {
3985
if ($Debug) { debug("Call to Init_HashArray"); }
3986
# Reset global hash arrays
3987
%FirstTime = %LastTime = ();
3988
%MonthHostsKnown = %MonthHostsUnknown = ();
3989
%MonthVisits = %MonthUnique = ();
3990
%MonthPages = %MonthHits = %MonthBytes = ();
3991
%MonthNotViewedPages = %MonthNotViewedHits = %MonthNotViewedBytes = ();
3992
%DayPages = %DayHits = %DayBytes = %DayVisits = ();
3993
# Reset all arrays with name beginning by _
3994
for (my $ix=0; $ix<6; $ix++) { $_from_p[$ix]=0; $_from_h[$ix]=0; }
3995
for (my $ix=0; $ix<24; $ix++) { $_time_h[$ix]=0; $_time_k[$ix]=0; $_time_p[$ix]=0; $_time_nv_h[$ix]=0; $_time_nv_k[$ix]=0; $_time_nv_p[$ix]=0; }
3996
# Reset all hash arrays with name beginning by _
3997
%_session = %_browser_h = ();
3998
%_domener_p = %_domener_h = %_domener_k = %_errors_h = %_errors_k = ();
3999
%_filetypes_h = %_filetypes_k = %_filetypes_gz_in = %_filetypes_gz_out = ();
4000
%_host_p = %_host_h = %_host_k = %_host_l = %_host_s = %_host_u = ();
4001
%_waithost_e = %_waithost_l = %_waithost_s = %_waithost_u = ();
4002
%_keyphrases = %_keywords = %_os_h = %_pagesrefs_p = %_pagesrefs_h = %_robot_h = %_robot_k = %_robot_l = %_robot_r = ();
4003
%_worm_h = %_worm_k = %_worm_l = %_login_p = %_login_h = %_login_k = %_login_l = %_screensize_h = ();
4004
%_misc_p = %_misc_h = %_misc_k = ();
4005
%_cluster_p = %_cluster_h = %_cluster_k = ();
4006
%_se_referrals_p = %_se_referrals_h = %_sider404_h = %_referer404_h = %_url_p = %_url_k = %_url_e = %_url_x = ();
4007
%_unknownreferer_l = %_unknownrefererbrowser_l = ();
4008
%_emails_h = %_emails_k = %_emails_l = %_emailr_h = %_emailr_k = %_emailr_l = ();
4009
for (my $ix=1; $ix < @ExtraName; $ix++) {
4010
%{'_section_' . $ix . '_h'} = %{'_section_' . $ix . '_o'} = %{'_section_' . $ix . '_k'} =
4011
%{'_section_' . $ix . '_l'} = %{'_section_' . $ix . '_p'} = ();
4015
#------------------------------------------------------------------------------
4016
# Function: Change word separators of a keyphrase string into space and
4017
# remove bad coded chars
4018
# Parameters: stringtodecode
4021
# Return: decodedstring
4022
#------------------------------------------------------------------------------
4023
sub ChangeWordSeparatorsIntoSpace {
4024
$_[0] =~ s/%0[ad]/ /ig; # LF,CR
4025
$_[0] =~ s/%2[02789abc]/ /ig; #
4026
$_[0] =~ s/%3a/ /ig; # :
4027
$_[0] =~ tr/\+\'\(\)\"\*,:/ /s; # "&" and "=" must not be in this list
4030
#------------------------------------------------------------------------------
4031
# Function: Transforms & into & as needed in XML/XHTML
4032
# Parameters: stringtoencode
4033
# Return: encodedstring
4034
#------------------------------------------------------------------------------
4037
if ($BuildReportFormat ne 'xml') { return $string; }
4038
$string =~ s/&/&/g;
4042
#------------------------------------------------------------------------------
4043
# Function: Encode a binary string into an ASCII string
4044
# Parameters: stringtoencode
4045
# Return: encodedstring
4046
#------------------------------------------------------------------------------
4050
$string =~ s/([\x2B\x80-\xFF])/sprintf ("%%%2x", ord($1))/eg;
4052
$string =~ tr/ /+/s;
4056
#------------------------------------------------------------------------------
4057
# Function: Decode an only text string into a binary string
4058
# Parameters: stringtodecode
4061
# Return: decodedstring
4062
#------------------------------------------------------------------------------
4063
sub DecodeEncodedString {
4064
my $stringtodecode=shift;
4065
$stringtodecode =~ tr/\+/ /s;
4066
$stringtodecode =~ s/%([A-F0-9][A-F0-9])/pack("C", hex($1))/ieg;
4067
return $stringtodecode;
4070
#------------------------------------------------------------------------------
4071
# Function: Decode an precompiled regex value to a common regex value
4072
# Parameters: compiledregextodecode
4075
# Return: standardregex
4076
#------------------------------------------------------------------------------
4077
sub UnCompileRegex {
4078
shift =~ /\(\?[-\w]*:(.*)\)/;
4082
#------------------------------------------------------------------------------
4083
# Function: Clean a string of HTML tags to avoid 'Cross Site Scripting attacks'
4084
# Parameters: stringtodecode
4087
# Return: decodedstring
4088
#------------------------------------------------------------------------------
4090
my $stringtoclean=shift;
4091
# $stringtoclean =~ s/[<>].*$//;
4092
$stringtoclean =~ s/</</g;
4093
$stringtoclean =~ s/>/>/g;
4094
return $stringtoclean;
4097
#------------------------------------------------------------------------------
4098
# Function: Copy one file into another
4099
# Parameters: sourcefilename targetfilename
4102
# Return: 0 if copy is ok, 1 else
4103
#------------------------------------------------------------------------------
4105
my $filesource = shift;
4106
my $filetarget = shift;
4107
if ($Debug) { debug("FileCopy($filesource,$filetarget)",1); }
4108
open(FILESOURCE,"$filesource") || return 1;
4109
open(FILETARGET,">$filetarget") || return 1;
4115
if ($Debug) { debug(" File copied",1); }
4119
#------------------------------------------------------------------------------
4120
# Function: Show flags for other language translations
4121
# Parameters: Current languade id (en, fr, ...)
4125
#------------------------------------------------------------------------------
4126
sub Show_Flag_Links {
4127
my $CurrentLang = shift;
4130
my $NewLinkParams=$QueryString;
4131
my $NewLinkTarget='';
4132
if ($ENV{'GATEWAY_INTERFACE'}) {
4133
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
4134
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
4135
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
4136
$NewLinkParams =~ s/(^|&)lang=[^&]*//i;
4137
if ($FrameName eq 'mainright') { $NewLinkTarget=" target=\"_parent\""; }
4138
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
4139
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
4142
$NewLinkParams=($SiteConfig?"config=$SiteConfig&":"")."year=$YearRequired&month=$MonthRequired&";
4144
if ($FrameName eq 'mainright') { $NewLinkParams.='framename=index&'; }
4146
foreach my $lng (split(/\s+/,$ShowFlagLinks)) {
4147
if ($lng ne $CurrentLang) {
4148
my %lngtitle=('en','English','fr','French','de','German','it','Italian','nl','Dutch','es','Spanish');
4149
my $lngtitle=($lngtitle{$lng}?$lngtitle{$lng}:$lng);
4150
my $flag=($LangAWStatsToCountryAwstats{$lng}?$LangAWStatsToCountryAwstats{$lng}:$lng);
4151
print "<a href=\"".XMLEncode("$AWScript?${NewLinkParams}lang=$lng")."\"$NewLinkTarget><img src=\"$DirIcons\/flags\/$flag.png\" height=\"14\" border=\"0\"".AltTitle("$lngtitle")." /></a> \n";
4156
#------------------------------------------------------------------------------
4157
# Function: Format value in bytes in a string (Bytes, Kb, Mb, Gb)
4158
# Parameters: bytes (integer value or "0.00")
4161
# Return: "x.yz MB" or "x.yy KB" or "x Bytes" or "0"
4162
#------------------------------------------------------------------------------
4164
my $bytes = shift||0;
4166
# Do not use exp/log function to calculate 1024power, function make segfault on some unix/perl versions
4167
if ($bytes >= ($fudge << 30)) { return sprintf("%.2f", $bytes/1073741824)." $Message[110]"; }
4168
if ($bytes >= ($fudge << 20)) { return sprintf("%.2f", $bytes/1048576)." $Message[109]"; }
4169
if ($bytes >= ($fudge << 10)) { return sprintf("%.2f", $bytes/1024)." $Message[108]"; }
4170
if ($bytes < 0) { $bytes="?"; }
4171
return int($bytes).(int($bytes)?" $Message[119]":"");
4174
#------------------------------------------------------------------------------
4175
# Function: Return " alt=string title=string"
4176
# Parameters: string
4179
# Return: "alt=string title=string"
4180
#------------------------------------------------------------------------------
4182
my $string = shift||'';
4183
return " alt='$string' title='$string'";
4184
# return " alt=\"$string\" title=\"$string\"";
4185
# return ($BuildReportFormat?"":" alt=\"$string\"")." title=\"$string\"";
4188
#------------------------------------------------------------------------------
4189
# Function: Tell if an email is a local or external email
4191
# Input: $SiteDomain(exact string) $HostAliases(quoted regex string)
4193
# Return: -1, 0 or 1
4194
#------------------------------------------------------------------------------
4196
my $email=shift||'unknown';
4197
if ($email !~ /\@(.*)$/) { return 0; }
4199
if ($domain =~ /^$SiteDomain$/i) { return 1; }
4200
foreach (@HostAliases) { if ($domain =~ /$_/) { return 1; } }
4204
#------------------------------------------------------------------------------
4205
# Function: Format a date according to Message[78] (country date format)
4206
# Parameters: String date YYYYMMDDHHMMSS
4207
# Option 0=LastUpdate and LastTime date
4208
# 1=Arrays date except daymonthvalues
4209
# 2=daymonthvalues date (only year month and day)
4210
# Input: $Message[78]
4212
# Return: Date with format defined by Message[78] and option
4213
#------------------------------------------------------------------------------
4216
my $option=shift||0;
4217
my $year=substr("$date",0,4);
4218
my $month=substr("$date",4,2);
4219
my $day=substr("$date",6,2);
4220
my $hour=substr("$date",8,2);
4221
my $min=substr("$date",10,2);
4222
my $sec=substr("$date",12,2);
4223
my $dateformat=$Message[78];
4225
$dateformat =~ s/^[^ymd]+//g;
4226
$dateformat =~ s/[^ymd]+$//g;
4228
$dateformat =~ s/yyyy/$year/g;
4229
$dateformat =~ s/yy/$year/g;
4230
$dateformat =~ s/mmm/$MonthNumLib{$month}/g;
4231
$dateformat =~ s/mm/$month/g;
4232
$dateformat =~ s/dd/$day/g;
4233
$dateformat =~ s/HH/$hour/g;
4234
$dateformat =~ s/MM/$min/g;
4235
$dateformat =~ s/SS/$sec/g;
4236
return "$dateformat";
4239
#------------------------------------------------------------------------------
4240
# Function: Return 1 if string contains only ascii chars
4241
# Parameters: string
4245
#------------------------------------------------------------------------------
4248
if ($Debug) { debug("IsAscii($string)",5); }
4249
if ($string =~ /^[\w\+\-\/\\\.%,;:=\"\'&?!\s]+$/) {
4250
if ($Debug) { debug(" Yes",6); }
4251
return 1; # Only alphanum chars (and _) or + - / \ . % , ; : = " ' & ? space \t
4253
if ($Debug) { debug(" No",6); }
4257
#------------------------------------------------------------------------------
4258
# Function: Return the lower value between 2 but exclude value if 0
4259
# Parameters: Val1 and Val2
4262
# Return: min(Val1,Val2)
4263
#------------------------------------------------------------------------------
4264
sub MinimumButNoZero {
4265
my ($val1,$val2)=@_;
4266
return ($val1&&($val1<$val2||!$val2)?$val1:$val2);
4269
#------------------------------------------------------------------------------
4270
# Function: Add a val from sorting tree
4271
# Parameters: keytoadd keyval [firstadd]
4275
#------------------------------------------------------------------------------
4279
my $firstadd=shift||0;
4280
if ($firstadd==1) { # Val is the first one
4281
if ($Debug) { debug(" firstadd",4); }
4282
$val{$keyval}=$keytoadd;
4284
if ($Debug) { debug(" lowerval=$lowerval, nb elem val=".(scalar keys %val).", nb elem egal=".(scalar keys %egal).".",4); }
4287
if ($val{$keyval}) { # Val is already in tree
4288
if ($Debug) { debug(" val is already in tree",4); }
4289
$egal{$keytoadd}=$val{$keyval};
4290
$val{$keyval}=$keytoadd;
4291
if ($Debug) { debug(" lowerval=$lowerval, nb elem val=".(scalar keys %val).", nb elem egal=".(scalar keys %egal).".",4); }
4294
if ($keyval <= $lowerval) { # Val is a new one lower (should happens only when tree is not full)
4295
if ($Debug) { debug(" keytoadd val=$keyval is lower or equal to lowerval=$lowerval",4); }
4296
$val{$keyval}=$keytoadd;
4297
$nextval{$keyval}=$lowerval;
4299
if ($Debug) { debug(" lowerval=$lowerval, nb elem val=".(scalar keys %val).", nb elem egal=".(scalar keys %egal).".",4); }
4302
# Val is a new one higher
4303
if ($Debug) { debug(" keytoadd val=$keyval is higher than lowerval=$lowerval",4); }
4304
$val{$keyval}=$keytoadd;
4305
my $valcursor=$lowerval; # valcursor is value just before keyval
4306
while ($nextval{$valcursor} && ($nextval{$valcursor} < $keyval)) { $valcursor=$nextval{$valcursor}; }
4307
if ($nextval{$valcursor}) { # keyval is between valcursor and nextval{valcursor}
4308
$nextval{$keyval}=$nextval{$valcursor};
4310
$nextval{$valcursor}=$keyval;
4311
if ($Debug) { debug(" lowerval=$lowerval, nb elem val=".(scalar keys %val).", nb elem egal=".(scalar keys %egal).".",4); }
4314
#------------------------------------------------------------------------------
4315
# Function: Remove a val from sorting tree
4317
# Input: $lowerval %val %egal
4320
#------------------------------------------------------------------------------
4321
sub Removelowerval {
4322
my $keytoremove=$val{$lowerval}; # This is lower key
4323
if ($Debug) { debug(" remove for lowerval=$lowerval: key=$keytoremove",4); }
4324
if ($egal{$keytoremove}) {
4325
$val{$lowerval}=$egal{$keytoremove};
4326
delete $egal{$keytoremove};
4329
delete $val{$lowerval};
4330
$lowerval=$nextval{$lowerval}; # Set new lowerval
4332
if ($Debug) { debug(" new lower value=$lowerval, val size=".(scalar keys %val).", egal size=".(scalar keys %egal),4); }
4335
#------------------------------------------------------------------------------
4336
# Function: Build @keylist array
4337
# Parameters: Size max for @keylist array,
4338
# Min value in hash for select,
4339
# Hash used for select,
4340
# Hash used for order
4343
# Return: @keylist response array
4344
#------------------------------------------------------------------------------
4346
my $ArraySize=shift||error("System error. Call to BuildKeyList function with incorrect value for first param","","",1);
4347
my $MinValue=shift||error("System error. Call to BuildKeyList function with incorrect value for second param","","",1);
4348
my $hashforselect=shift;
4349
my $hashfororder=shift;
4350
if ($Debug) { debug(" BuildKeyList($ArraySize,$MinValue,$hashforselect with size=".(scalar keys %$hashforselect).",$hashfororder with size=".(scalar keys %$hashfororder).")",2); }
4351
delete $hashforselect->{0};delete $hashforselect->{''}; # Those is to protect from infinite loop when hash array has an incorrect null key
4353
$lowerval=0; # Global because used in AddInTree and Removelowerval
4354
%val=(); %nextval=(); %egal=();
4355
foreach my $key (keys %$hashforselect) {
4356
if ($count < $ArraySize) {
4357
if ($hashforselect->{$key} >= $MinValue) {
4359
if ($Debug) { debug(" Add in tree entry $count : $key (value=".($hashfororder->{$key}||0).", tree not full)",4); }
4360
AddInTree($key,$hashfororder->{$key}||0,$count);
4365
if (($hashfororder->{$key}||0)<=$lowerval) { next; }
4366
if ($Debug) { debug(" Add in tree entry $count : $key (value=".($hashfororder->{$key}||0)." > lowerval=$lowerval)",4); }
4367
AddInTree($key,$hashfororder->{$key}||0);
4368
if ($Debug) { debug(" Removelower in tree",4); }
4372
# Build key list and sort it
4373
if ($Debug) { debug(" Build key list and sort it. lowerval=$lowerval, nb elem val=".(scalar keys %val).", nb elem egal=".(scalar keys %egal).".",2); }
4374
my %notsortedkeylist=();
4375
foreach my $key (values %val) { $notsortedkeylist{$key}=1; }
4376
foreach my $key (values %egal) { $notsortedkeylist{$key}=1; }
4378
@keylist=(sort {($hashfororder->{$b}||0) <=> ($hashfororder->{$a}||0) } keys %notsortedkeylist);
4379
if ($Debug) { debug(" BuildKeyList End (keylist size=".(@keylist).")",2); }
4383
#------------------------------------------------------------------------------
4384
# Function: Lock or unlock update
4385
# Parameters: status (1 to lock, 0 to unlock)
4386
# Input: $DirLock (if status=0) $PROG $FileSuffix
4387
# Output: $DirLock (if status=1)
4389
#------------------------------------------------------------------------------
4392
my $lock="$PROG$FileSuffix.lock";
4394
# We stop if there is at least one lock file wherever it is
4395
foreach my $key ($ENV{"TEMP"},$ENV{"TMP"},"/tmp","/",".") {
4397
$newkey =~ s/[\\\/]$//;
4398
if (-f "$newkey/$lock") { error("An AWStats update process seems to be already running for this config file. Try later.\nIf this is not true, remove manually lock file '$newkey/$lock'.","","",1); }
4400
# Set lock where we can
4401
foreach my $key ($ENV{"TEMP"},$ENV{"TMP"},"/tmp","/",".") {
4402
if (! -d "$key") { next; }
4404
$DirLock =~ s/[\\\/]$//;
4405
if ($Debug) { debug("Update lock file $DirLock/$lock is set"); }
4406
open(LOCK,">$DirLock/$lock") || error("Failed to create lock file $DirLock/$lock","","",1);
4407
print LOCK "AWStats update started by process $$ at $nowyear-$nowmonth-$nowday $nowhour:$nowmin:$nowsec\n";
4414
if ($Debug) { debug("Update lock file $DirLock/$lock is removed"); }
4415
unlink("$DirLock/$lock");
4420
#------------------------------------------------------------------------------
4421
# Function: Signal handler to call Lock_Update to remove lock file
4422
# Parameters: Signal name
4426
#------------------------------------------------------------------------------
4428
my $signame = shift;
4429
print ucfirst($PROG)." process (ID $$) interrupted by signal $signame.\n";
4434
#------------------------------------------------------------------------------
4435
# Function: Convert an IPAddress into an integer
4436
# Parameters: IPAddress
4440
#------------------------------------------------------------------------------
4441
sub Convert_IP_To_Decimal {
4442
my ($IPAddress) = @_;
4443
my @ip_seg_arr = split(/\./,$IPAddress);
4444
my $decimal_ip_address = 256 * 256 *256 * $ip_seg_arr[0] + 256 * 256 * $ip_seg_arr[1] + 256 * $ip_seg_arr[2] + $ip_seg_arr[3];
4445
return($decimal_ip_address);
4448
#------------------------------------------------------------------------------
4449
# Function: Test there is at least on value in list not null
4450
# Parameters: List of values
4453
# Return: 1 There is at least one not null value, 0 else
4454
#------------------------------------------------------------------------------
4455
sub AtLeastOneNotNull {
4456
if ($Debug) { debug(" Call to AtLeastOneNotNull (".join('-',@_).")",3); }
4457
foreach my $val (@_) { if ($val) { return 1; } }
4461
#------------------------------------------------------------------------------
4462
# Function: Insert a form filter
4463
# Parameters: Name of filter field, default for filter field, default for exclude filter field
4464
# Input: $StaticLinks, $QueryString, $SiteConfig, $DirConfig
4467
#------------------------------------------------------------------------------
4468
sub ShowFormFilter {
4469
my $fieldfiltername=shift;
4470
my $fieldfilterinvalue=shift;
4471
my $fieldfilterexvalue=shift;
4472
if (! $StaticLinks) {
4473
my $NewLinkParams=${QueryString};
4474
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
4475
$NewLinkParams =~ s/(^|&)output(=\w*|$)//i;
4476
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
4477
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
4478
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
4479
print "\n<form name=\"FormFilter\" action=\"".XMLEncode("$AWScript?${NewLinkParams}")."\" class=\"aws_border\">\n";
4480
print "<table valign=\"middle\" width=\"99%\" border=\"0\" cellspacing=\"0\" cellpadding=\"2\"><tr>\n";
4481
print "<td align=\"left\" width=\"50\">$Message[79] :</td>\n";
4482
print "<td align=\"left\" width=\"100\"><input type=\"text\" name=\"${fieldfiltername}\" value=\"$fieldfilterinvalue\" class=\"aws_formfield\" /></td>\n";
4483
print "<td> </td>";
4484
print "<td align=\"left\" width=\"100\">$Message[153] :</td>\n";
4485
print "<td align=\"left\" width=\"100\"><input type=\"text\" name=\"${fieldfiltername}ex\" value=\"$fieldfilterexvalue\" class=\"aws_formfield\" /></td>\n";
4487
print "<input type=\"hidden\" name=\"output\" value=\"".join(',',keys %HTMLOutput)."\" />\n";
4488
if ($SiteConfig) { print "<input type=\"hidden\" name=\"config\" value=\"$SiteConfig\" />\n"; }
4489
if ($DirConfig) { print "<input type=\"hidden\" name=\"configdir\" value=\"$DirConfig\" />\n"; }
4490
if ($QueryString =~ /(^|&)year=(\d\d\d\d)/i) { print "<input type=\"hidden\" name=\"year\" value=\"$2\" />\n"; }
4491
if ($QueryString =~ /(^|&)month=(\d\d)/i || $QueryString =~ /(^|&)month=(all)/i) { print "<input type=\"hidden\" name=\"month\" value=\"$2\" />\n"; }
4492
if ($QueryString =~ /(^|&)lang=(\w+)/i) { print "<input type=\"hidden\" name=\"lang\" value=\"$2\" />\n"; }
4493
if ($QueryString =~ /(^|&)debug=(\d+)/i) { print "<input type=\"hidden\" name=\"debug\" value=\"$2\" />\n"; }
4494
if ($QueryString =~ /(^|&)framename=(\w+)/i) { print "<input type=\"hidden\" name=\"framename\" value=\"$2\" />\n"; }
4495
print "<input type=\"submit\" value=\" $Message[115] \" class=\"aws_button\" /></td>\n";
4496
print "<td> </td>";
4497
print "</tr></table>\n";
4504
#------------------------------------------------------------------------------
4505
# Function: Write other user info (with help of plugin)
4507
# Input: $SiteConfig
4510
#------------------------------------------------------------------------------
4513
# Call to plugins' function ShowInfoUser
4514
foreach my $pluginname (keys %{$PluginsLoaded{'ShowInfoUser'}}) {
4515
my $function="ShowInfoUser_$pluginname('$user')";
4520
#------------------------------------------------------------------------------
4521
# Function: Write other host info (with help of plugin)
4523
# Input: $LinksToWhoIs $LinksToWhoIsIp
4526
#------------------------------------------------------------------------------
4529
# Call to plugins' function ShowInfoHost
4530
foreach my $pluginname (keys %{$PluginsLoaded{'ShowInfoHost'}}) {
4531
my $function="ShowInfoHost_$pluginname('$host')";
4536
#------------------------------------------------------------------------------
4537
# Function: Write other url info (with help of plugin)
4539
# Input: %Aliases $MaxLengthOfShownURL $ShowLinksOnUrl $SiteDomain $UseHTTPSLinkForUrl
4542
#------------------------------------------------------------------------------
4545
my $nompage=CleanFromCSSA($url);
4547
# Call to plugins' function ShowInfoURL
4548
foreach my $pluginname (keys %{$PluginsLoaded{'ShowInfoURL'}}) {
4549
my $function="ShowInfoURL_$pluginname('$url')";
4553
if (length($nompage)>$MaxLengthOfShownURL) { $nompage=substr($nompage,0,$MaxLengthOfShownURL)."..."; }
4554
if ($ShowLinksOnUrl) {
4555
my $newkey=CleanFromCSSA($url);
4556
if ($LogType eq 'W' || $LogType eq 'S') { # Web or streaming log file
4557
if ($newkey =~ /^http(s|):/i) { # URL seems to be extracted from a proxy log file
4558
print "<a href=\"".XMLEncode("$newkey")."\" target=\"url\">".XMLEncode($nompage)."</a>";
4560
elsif ($newkey =~ /^\//) { # URL seems to be an url extracted from a web or wap server log file
4561
$newkey =~ s/^\/$SiteDomain//i;
4564
if ($UseHTTPSLinkForUrl && $newkey =~ /^$UseHTTPSLinkForUrl/) { $urlprot='https'; }
4565
print "<a href=\"".XMLEncode("$urlprot://$SiteDomain$newkey\"")." target=\"url\">".XMLEncode($nompage)."</a>";
4568
print XMLEncode($nompage);
4571
elsif ($LogType eq 'F') { # Ftp log file
4572
print XMLEncode($nompage);
4574
elsif ($LogType eq 'M') { # Smtp log file
4575
print XMLEncode($nompage);
4577
else { # Other type log file
4578
print XMLEncode($nompage);
4582
print XMLEncode($nompage);
4586
#------------------------------------------------------------------------------
4587
# Function: Define value for PerlParsingFormat (used for regex log record parsing)
4592
#------------------------------------------------------------------------------
4593
sub DefinePerlParsingFormat {
4594
# Log records examples:
4595
# Apache combined: 62.161.78.73 user - [dd/mmm/yyyy:hh:mm:ss +0000] "GET / HTTP/1.1" 200 1234 "http://www.from.com/from.htm" "Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)"
4596
# Apache combined (408 error): my.domain.com - user [09/Jan/2001:11:38:51 -0600] "OPTIONS /mime-tmp/xxx file.doc HTTP/1.1" 408 - "-" "-"
4597
# Apache combined (408 error): 62.161.78.73 user - [dd/mmm/yyyy:hh:mm:ss +0000] "-" 408 - "-" "-"
4598
# Apache common_with_mod_gzip_info1: %h %l %u %t \"%r\" %>s %b mod_gzip: %{mod_gzip_compression_ratio}npct.
4599
# Apache common_with_mod_gzip_info2: %h %l %u %t \"%r\" %>s %b mod_gzip: %{mod_gzip_result}n In:%{mod_gzip_input_size}n Out:%{mod_gzip_output_size}n:%{mod_gzip_compression_ratio}npct.
4600
# Apache deflate: %h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\" (%{ratio}n)
4601
# IIS: 2000-07-19 14:14:14 62.161.78.73 - GET / 200 1234 HTTP/1.1 Mozilla/4.0+(compatible;+MSIE+5.01;+Windows+NT+5.0) http://www.from.com/from.htm
4602
# WebStar: 05/21/00 00:17:31 OK 200 212.242.30.6 Mozilla/4.0 (compatible; MSIE 5.0; Windows 98; DigExt) http://www.cover.dk/ "www.cover.dk" :Documentation:graphics:starninelogo.white.gif 1133
4603
# Squid extended: 12.229.91.170 - - [27/Jun/2002:03:30:50 -0700] "GET http://www.callistocms.com/images/printable.gif HTTP/1.1" 304 354 "-" "Mozilla/5.0 Galeon/1.0.3 (X11; Linux i686; U;) Gecko/0" TCP_REFRESH_HIT:DIRECT
4604
if ($Debug) { debug("Call To DefinePerlParsingFormat (LogType='$LogType', LogFormat='$LogFormat')"); }
4606
if ($LogFormat =~ /^[1-6]$/) { # Pre-defined log format
4607
if ($LogFormat eq '1' || $LogFormat eq '6') { # Same than "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"".
4608
# %u (user) is "([^\\[]+)" instead of "[^ ]+" because can contain space (Lotus Notes). referer and ua might be "".
4609
# $PerlParsingFormat="([^ ]+) [^ ]+ ([^\\[]+) \\[([^ ]+) [^ ]+\\] \\\"([^ ]+) (.+) [^\\\"]+\\\" ([\\d|-]+) ([\\d|-]+) \\\"(.*?)\\\" \\\"([^\\\"]*)\\\"";
4610
$PerlParsingFormat="([^ ]+) [^ ]+ ([^\\[]+) \\[([^ ]+) [^ ]+\\] \\\"([^ ]+) ([^ ]+) [^\\\"]+\\\" ([\\d|-]+) ([\\d|-]+) \\\"(.*?)\\\" \\\"([^\\\"]*)\\\"";
4611
$pos_host=0;$pos_logname=1;$pos_date=2;$pos_method=3;$pos_url=4;$pos_code=5;$pos_size=6;$pos_referer=7;$pos_agent=8;
4612
@fieldlib=('host','logname','date','method','url','code','size','referer','ua');
4614
elsif ($LogFormat eq '2') { # Same than "date time c-ip cs-username cs-method cs-uri-stem sc-status sc-bytes cs-version cs(User-Agent) cs(Referer)"
4615
$PerlParsingFormat="(\\S+ \\S+) (\\S+) (\\S+) (\\S+) (\\S+) ([\\d|-]+) ([\\d|-]+) \\S+ (\\S+) (\\S+)";
4616
$pos_date=0;$pos_host=1;$pos_logname=2;$pos_method=3;$pos_url=4;$pos_code=5;$pos_size=6;$pos_agent=7;$pos_referer=8;
4617
@fieldlib=('date','host','logname','method','url','code','size','ua','referer');
4619
elsif ($LogFormat eq '3') {
4620
$PerlParsingFormat="([^\\t]*\\t[^\\t]*)\\t([^\\t]*)\\t([\\d|-]*)\\t([^\\t]*)\\t([^\\t]*)\\t([^\\t]*)\\t[^\\t]*\\t([^\\t]*)\\t([\\d]*)";
4621
$pos_date=0;$pos_method=1;$pos_code=2;$pos_host=3;$pos_agent=4;$pos_referer=5;$pos_url=6;$pos_size=7;
4622
@fieldlib=('date','method','code','host','ua','referer','url','size');
4624
elsif ($LogFormat eq '4') { # Same than "%h %l %u %t \"%r\" %>s %b"
4625
# %u (user) is "(.+)" instead of "[^ ]+" because can contain space (Lotus Notes).
4626
$PerlParsingFormat="([^ ]+) [^ ]+ (.+) \\[([^ ]+) [^ ]+\\] \\\"([^ ]+) ([^ ]+) [^\\\"]+\\\" ([\\d|-]+) ([\\d|-]+)";
4627
$pos_host=0;$pos_logname=1;$pos_date=2;$pos_method=3;$pos_url=4;$pos_code=5;$pos_size=6;
4628
@fieldlib=('host','logname','date','method','url','code','size');
4630
# This is a deprecated option, will be removed in a next version.
4631
elsif ($LogFormat eq '5') { # Same than "c-ip cs-username c-agent sc-authenticated date time s-svcname s-computername cs-referred r-host r-ip r-port time-taken cs-bytes sc-bytes cs-protocol cs-transport s-operation cs-uri cs-mime-type s-object-source sc-status s-cache-info"
4632
$PerlParsingFormat="([^\\t]*)\\t([^\\t]*)\\t([^\\t]*)\\t[^\\t]*\\t([^\\t]*\\t[^\\t]*)\\t[^\\t]*\\t[^\\t]*\\t([^\\t]*)\\t[^\\t]*\\t[^\\t]*\\t[^\\t]*\\t[^\\t]*\\t[^\\t]*\\t([^\\t]*)\\t[^\\t]*\\t[^\\t]*\\t([^\\t]*)\\t([^\\t]*)\\t[^\\t]*\\t[^\\t]*\\t([^\\t]*)\\t[^\\t]*";
4633
$pos_host=0;$pos_logname=1;$pos_agent=2;$pos_date=3;$pos_referer=4;$pos_size=5;$pos_method=6;$pos_url=7;$pos_code=8;
4634
@fieldlib=('host','logname','ua','date','referer','size','method','url','code');
4637
else { # Personalized log format
4638
my $LogFormatString=$LogFormat;
4639
# Replacement for Notes format string that are not Apache
4640
$LogFormatString =~ s/%vh/%virtualname/g;
4641
# Replacement for Apache format string
4642
$LogFormatString =~ s/%v(\s)/%virtualname$1/g; $LogFormatString =~ s/%v$/%virtualname/g;
4643
$LogFormatString =~ s/%h(\s)/%host$1/g; $LogFormatString =~ s/%h$/%host/g;
4644
$LogFormatString =~ s/%l(\s)/%other$1/g; $LogFormatString =~ s/%l$/%other/g;
4645
$LogFormatString =~ s/\"%u\"/%lognamequot/g;
4646
$LogFormatString =~ s/%u(\s)/%logname$1/g; $LogFormatString =~ s/%u$/%logname/g;
4647
$LogFormatString =~ s/%t(\s)/%time1$1/g; $LogFormatString =~ s/%t$/%time1/g;
4648
$LogFormatString =~ s/\"%r\"/%methodurl/g;
4649
$LogFormatString =~ s/%>s/%code/g;
4650
$LogFormatString =~ s/%b(\s)/%bytesd$1/g; $LogFormatString =~ s/%b$/%bytesd/g;
4651
$LogFormatString =~ s/\"%{Referer}i\"/%refererquot/g;
4652
$LogFormatString =~ s/\"%{User-Agent}i\"/%uaquot/g;
4653
$LogFormatString =~ s/%{mod_gzip_input_size}n/%gzipin/g;
4654
$LogFormatString =~ s/%{mod_gzip_output_size}n/%gzipout/g;
4655
$LogFormatString =~ s/%{mod_gzip_compression_ratio}n/%gzipratio/g;
4656
$LogFormatString =~ s/\(%{ratio}n\)/%deflateratio/g;
4657
# Replacement for a IIS and ISA format string
4658
$LogFormatString =~ s/cs-uri-query/%query/g; # Must be before cs-uri
4659
$LogFormatString =~ s/date\stime/%time2/g;
4660
$LogFormatString =~ s/c-ip/%host/g;
4661
$LogFormatString =~ s/cs-username/%logname/g;
4662
$LogFormatString =~ s/cs-method/%method/g; # GET, POST, SMTP, RETR STOR
4663
$LogFormatString =~ s/cs-uri-stem/%url/g; $LogFormatString =~ s/cs-uri/%url/g;
4664
$LogFormatString =~ s/sc-status/%code/g;
4665
$LogFormatString =~ s/sc-bytes/%bytesd/g;
4666
$LogFormatString =~ s/cs-version/%other/g; # Protocol
4667
$LogFormatString =~ s/cs\(User-Agent\)/%ua/g; $LogFormatString =~ s/c-agent/%ua/g;
4668
$LogFormatString =~ s/cs\(Referer\)/%referer/g; $LogFormatString =~ s/cs-referred/%referer/g;
4669
$LogFormatString =~ s/sc-authenticated/%other/g;
4670
$LogFormatString =~ s/s-svcname/%other/g;
4671
$LogFormatString =~ s/s-computername/%other/g;
4672
$LogFormatString =~ s/r-host/%virtualname/g;
4673
$LogFormatString =~ s/r-ip/%other/g;
4674
$LogFormatString =~ s/r-port/%other/g;
4675
$LogFormatString =~ s/time-taken/%other/g;
4676
$LogFormatString =~ s/cs-bytes/%other/g;
4677
$LogFormatString =~ s/cs-protocol/%other/g;
4678
$LogFormatString =~ s/cs-transport/%other/g;
4679
$LogFormatString =~ s/s-operation/%method/g; # GET, POST, SMTP, RETR STOR
4680
$LogFormatString =~ s/cs-mime-type/%other/g;
4681
$LogFormatString =~ s/s-object-source/%other/g;
4682
$LogFormatString =~ s/s-cache-info/%other/g;
4684
$LogFormatString =~ s/protocol/%protocolmms/g; # cs-method might not be available
4685
$LogFormatString =~ s/c-status/%codemms/g; # c-status used when sc-status not available
4686
if ($Debug) { debug(" LogFormatString=$LogFormatString"); }
4687
# $LogFormatString has an AWStats format, so we can generate PerlParsingFormat variable
4689
my $LogSeparatorWithoutStar=$LogSeparator; $LogSeparatorWithoutStar =~ s/[\*\+]//g;
4690
foreach my $f (split(/\s+/,$LogFormatString)) {
4691
# Add separator for next field
4692
if ($PerlParsingFormat) { $PerlParsingFormat.="$LogSeparator"; }
4693
# Special for logname
4694
if ($f =~ /%lognamequot$/) {
4695
$pos_logname = $i; $i++; push @fieldlib, 'logname';
4696
$PerlParsingFormat .= "\\\"?([^\\\"]*)\\\"?"; # logname can be "value", "" and - in same log (Lotus notes)
4699
elsif ($f =~ /%time1$/ || $f =~ /%time1b$/) { # [dd/mmm/yyyy:hh:mm:ss +0000] ou [dd/mmm/yyyy:hh:mm:ss], time1b kept for backward compatibility
4700
$pos_date = $i; $i++; push @fieldlib, 'date';
4701
$pos_tz = $i; $i++; push @fieldlib, 'tz';
4702
$PerlParsingFormat .= "\\[([^$LogSeparatorWithoutStar]+)( [^$LogSeparatorWithoutStar]+)?\\]";
4704
elsif ($f =~ /%time2$/) { # yyyy-mm-dd hh:mm:ss
4705
$pos_date = $i; $i++; push @fieldlib, 'date';
4706
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+\\s[^$LogSeparatorWithoutStar]+)"; # Need \s for Exchange log files
4708
elsif ($f =~ /%time3$/) { # mon d hh:mm:ss
4709
$pos_date = $i; $i++; push @fieldlib, 'date';
4710
$PerlParsingFormat .= "(\\w\\w\\w \\s??\\d+ \\d\\d:\\d\\d:\\d\\d)";
4712
# Special for methodurl and methodurlnoprot
4713
elsif ($f =~ /%methodurl$/) {
4714
$pos_method = $i; $i++; push @fieldlib, 'method';
4715
$pos_url = $i; $i++; push @fieldlib, 'url';
4716
$PerlParsingFormat .= "\\\"([^$LogSeparatorWithoutStar]+) ([^$LogSeparatorWithoutStar]+) [^\\\"]+\\\"";
4718
elsif ($f =~ /%methodurlnoprot$/) {
4719
$pos_method = $i; $i++; push @fieldlib, 'method';
4720
$pos_url = $i; $i++; push @fieldlib, 'url';
4721
$PerlParsingFormat .= "\\\"([^$LogSeparatorWithoutStar]+) ([^$LogSeparatorWithoutStar]+)\\\"";
4723
# Common command tags
4724
elsif ($f =~ /%virtualname$/) {
4725
$pos_vh = $i; $i++; push @fieldlib, 'vhost';
4726
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4728
elsif ($f =~ /%host_r$/) {
4729
$pos_hostr = $i; $i++; push @fieldlib, 'hostr';
4730
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4732
elsif ($f =~ /%host$/) {
4733
$pos_host = $i; $i++; push @fieldlib, 'host';
4734
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4736
elsif ($f =~ /%logname$/) {
4737
$pos_logname = $i; $i++; push @fieldlib, 'logname';
4738
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4740
elsif ($f =~ /%method$/) {
4741
$pos_method = $i; $i++; push @fieldlib, 'method';
4742
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4744
elsif ($f =~ /%url$/) {
4745
$pos_url = $i; $i++; push @fieldlib, 'url';
4746
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4748
elsif ($f =~ /%query$/) {
4749
$pos_query = $i; $i++; push @fieldlib, 'query';
4750
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4752
elsif ($f =~ /%code$/) {
4753
$pos_code = $i; $i++; push @fieldlib, 'code';
4754
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4756
elsif ($f =~ /%bytesd$/) {
4757
$pos_size = $i; $i++; push @fieldlib, 'size';
4758
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4760
elsif ($f =~ /%refererquot$/) {
4761
$pos_referer = $i; $i++; push @fieldlib, 'referer';
4762
$PerlParsingFormat .= "\\\"([^\\\"]*)\\\""; # referer might be ""
4764
elsif ($f =~ /%referer$/) {
4765
$pos_referer = $i; $i++; push @fieldlib, 'referer';
4766
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4768
elsif ($f =~ /%uaquot$/) {
4769
$pos_agent = $i; $i++; push @fieldlib, 'ua';
4770
$PerlParsingFormat .= "\\\"([^\\\"]*)\\\""; # ua might be ""
4772
elsif ($f =~ /%uabracket$/) {
4773
$pos_agent = $i; $i++; push @fieldlib, 'ua';
4774
$PerlParsingFormat .= "\\\[([^\\\]]*)\\\]"; # ua might be []
4776
elsif ($f =~ /%ua$/) {
4777
$pos_agent = $i; $i++; push @fieldlib, 'ua';
4778
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4780
elsif ($f =~ /%gzipin$/ ) {
4781
$pos_gzipin=$i;$i++; push @fieldlib, 'gzipin';
4782
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4784
elsif ($f =~ /%gzipout/ ) { # Compare $f to /%gzipout/ and not to /%gzipout$/ like other fields
4785
$pos_gzipout=$i;$i++; push @fieldlib, 'gzipout';
4786
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4788
elsif ($f =~ /%gzipratio/ ) { # Compare $f to /%gzipratio/ and not to /%gzipratio$/ like other fields
4789
$pos_compratio=$i;$i++; push @fieldlib, 'gzipratio';
4790
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4792
elsif ($f =~ /%deflateratio/ ) { # Compare $f to /%deflateratio/ and not to /%deflateratio$/ like other fields
4793
$pos_compratio=$i;$i++; push @fieldlib, 'deflateratio';
4794
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4796
elsif ($f =~ /%email_r$/) {
4797
$pos_emailr = $i; $i++; push @fieldlib, 'email_r';
4798
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4800
elsif ($f =~ /%email$/) {
4801
$pos_emails = $i; $i++; push @fieldlib, 'email';
4802
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4804
elsif ($f =~ /%cluster$/) {
4805
$pos_cluster = $i; $i++; push @fieldlib, 'clusternb';
4806
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4808
# Special for protocolmms, used for method if method not already found (for MMS)
4809
elsif ($f =~ /%protocolmms$/) {
4810
if ($pos_method < 0) {
4811
$pos_method = $i; $i++; push @fieldlib, 'method';
4812
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4815
# Special for codemms, used for code only if code not already found (for MMS)
4816
elsif ($f =~ /%codemms$/) {
4817
if ($pos_code < 0) {
4818
$pos_code = $i; $i++; push @fieldlib, 'code';
4819
$PerlParsingFormat .= "([^$LogSeparatorWithoutStar]+)";
4823
elsif ($f =~ /%other$/) {
4824
$PerlParsingFormat .= "[^$LogSeparatorWithoutStar]+";
4826
elsif ($f =~ /%otherquot$/) {
4827
$PerlParsingFormat .= "\\\"[^\\\"]*\\\"";
4829
# Unknown tag (no parenthesis)
4831
$PerlParsingFormat .= "[^$LogSeparatorWithoutStar]+";
4834
if (! $PerlParsingFormat) { error("No recognized format tag in personalized LogFormat string"); }
4836
if ($pos_host < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%host in your LogFormat string)."); }
4837
if ($pos_date < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%time1 or \%time2 in your LogFormat string)."); }
4838
if ($pos_method < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%methodurl or \%method in your LogFormat string)."); }
4839
if ($pos_url < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%methodurl or \%url in your LogFormat string)."); }
4840
if ($pos_code < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%code in your LogFormat string)."); }
4841
if ($pos_size < 0) { error("Your personalized LogFormat does not include all fields required by AWStats (Add \%bytesd in your LogFormat string)."); }
4842
$PerlParsingFormat=qr/^$PerlParsingFormat/;
4843
if ($Debug) { debug(" PerlParsingFormat is $PerlParsingFormat"); }
4847
sub ShowEmailSendersChart {
4848
my $NewLinkParams=shift;
4849
my $NewLinkTarget=shift;
4850
my $MaxLengthOfShownEMail=48;
4852
my $total_p;my $total_h;my $total_k;
4853
my $max_p;my $max_h;my $max_k;
4854
my $rest_p;my $rest_h;my $rest_k;
4857
#&ShowFormFilter("emailsfilter",$EmailsFilter);
4860
print "$Center<a name=\"emailsenders\"> </a><br />\n";
4862
if ($HTMLOutput{'allemails'} || $HTMLOutput{'lastemails'}) {
4863
$title="$Message[131]";
4866
$title="$Message[131] ($Message[77] $MaxNbOf{'EMailsShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allemails"):"$PROG$StaticLinks.allemails.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>";
4867
if ($ShowEMailSenders =~ /L/i) { $title.=" - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastemails"):"$PROG$StaticLinks.lastemails.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>"; }
4869
&tab_head("$title",19,0,'emailsenders');
4870
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"3\">$Message[131] : ".(scalar keys %_emails_h)."</th>";
4871
if ($ShowEMailSenders =~ /H/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
4872
if ($ShowEMailSenders =~ /B/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
4873
if ($ShowEMailSenders =~ /M/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_k\" width=\"80\">$Message[106]</th>"; }
4874
if ($ShowEMailSenders =~ /L/i) { print "<th rowspan=\"2\" width=\"120\">$Message[9]</th>"; }
4876
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"30%\">Local</th><th> </th><th width=\"30%\">External</th></tr>";
4877
$total_p=$total_h=$total_k=0;
4878
$max_h=1; foreach (values %_emails_h) { if ($_ > $max_h) { $max_h = $_; } }
4879
$max_k=1; foreach (values %_emails_k) { if ($_ > $max_k) { $max_k = $_; } }
4881
if (! $HTMLOutput{'allemails'} && ! $HTMLOutput{'lastemails'}) { &BuildKeyList($MaxNbOf{'EMailsShown'},$MinHit{'EMail'},\%_emails_h,\%_emails_h); }
4882
if ($HTMLOutput{'allemails'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'EMail'},\%_emails_h,\%_emails_h); }
4883
if ($HTMLOutput{'lastemails'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'EMail'},\%_emails_h,\%_emails_l); }
4884
foreach my $key (@keylist) {
4886
if (length($key)>$MaxLengthOfShownEMail) { $newkey=substr($key,0,$MaxLengthOfShownEMail)."..."; }
4887
my $bredde_h=0;my $bredde_k=0;
4888
if ($max_h > 0) { $bredde_h=int($BarWidth*$_emails_h{$key}/$max_h)+1; }
4889
if ($max_k > 0) { $bredde_k=int($BarWidth*$_emails_k{$key}/$max_k)+1; }
4891
my $direction=IsLocalEMail($key);
4892
if ($direction > 0) { print "<td class=\"aws\">$newkey</td><td>-></td><td> </td>"; }
4893
if ($direction == 0) { print "<td colspan=\"3\"><span style=\"color: #$color_other\">$newkey</span></td>"; }
4894
if ($direction < 0) { print "<td class=\"aws\"> </td><td><-</td><td>$newkey</td>"; }
4895
if ($ShowEMailSenders =~ /H/i) { print "<td>$_emails_h{$key}</td>"; }
4896
if ($ShowEMailSenders =~ /B/i) { print "<td>".Format_Bytes($_emails_k{$key})."</td>"; }
4897
if ($ShowEMailSenders =~ /M/i) { print "<td>".Format_Bytes($_emails_k{$key}/($_emails_h{$key}||1))."</td>"; }
4898
if ($ShowEMailSenders =~ /L/i) { print "<td>".($_emails_l{$key}?Format_Date($_emails_l{$key},1):'-')."</td>"; }
4900
#$total_p += $_emails_p{$key};
4901
$total_h += $_emails_h{$key};
4902
$total_k += $_emails_k{$key};
4905
$rest_p=0; # $rest_p=$TotalPages-$total_p;
4906
$rest_h=$TotalHits-$total_h;
4907
$rest_k=$TotalBytes-$total_k;
4908
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other sender emails
4909
print "<tr><td colspan=\"3\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
4910
if ($ShowEMailSenders =~ /H/i) { print "<td>$rest_h</td>"; }
4911
if ($ShowEMailSenders =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
4912
if ($ShowEMailSenders =~ /M/i) { print "<td>".Format_Bytes($rest_k/($rest_h||1))."</td>"; }
4913
if ($ShowEMailSenders =~ /L/i) { print "<td> </td>"; }
4920
sub ShowEmailReceiversChart {
4921
my $NewLinkParams=shift;
4922
my $NewLinkTarget=shift;
4923
my $MaxLengthOfShownEMail=48;
4925
my $total_p;my $total_h;my $total_k;
4926
my $max_p;my $max_h;my $max_k;
4927
my $rest_p;my $rest_h;my $rest_k;
4930
#&ShowFormFilter("emailrfilter",$EmailrFilter);
4933
print "$Center<a name=\"emailreceivers\"> </a><br />\n";
4935
if ($HTMLOutput{'allemailr'} || $HTMLOutput{'lastemailr'}) {
4936
$title="$Message[132]";
4939
$title="$Message[132] ($Message[77] $MaxNbOf{'EMailsShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allemailr"):"$PROG$StaticLinks.allemailr.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>";
4940
if ($ShowEMailReceivers =~ /L/i) { $title.=" - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastemailr"):"$PROG$StaticLinks.lastemailr.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>"; }
4942
&tab_head("$title",19,0,'emailreceivers');
4943
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"3\">$Message[132] : ".(scalar keys %_emailr_h)."</th>";
4944
if ($ShowEMailReceivers =~ /H/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
4945
if ($ShowEMailReceivers =~ /B/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
4946
if ($ShowEMailReceivers =~ /M/i) { print "<th rowspan=\"2\" bgcolor=\"#$color_k\" width=\"80\">$Message[106]</th>"; }
4947
if ($ShowEMailReceivers =~ /L/i) { print "<th rowspan=\"2\" width=\"120\">$Message[9]</th>"; }
4949
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"30%\">Local</th><th> </th><th width=\"30%\">External</th></tr>";
4950
$total_p=$total_h=$total_k=0;
4951
$max_h=1; foreach (values %_emailr_h) { if ($_ > $max_h) { $max_h = $_; } }
4952
$max_k=1; foreach (values %_emailr_k) { if ($_ > $max_k) { $max_k = $_; } }
4954
if (! $HTMLOutput{'allemailr'} && ! $HTMLOutput{'lastemailr'}) { &BuildKeyList($MaxNbOf{'EMailsShown'},$MinHit{'EMail'},\%_emailr_h,\%_emailr_h); }
4955
if ($HTMLOutput{'allemailr'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'EMail'},\%_emailr_h,\%_emailr_h); }
4956
if ($HTMLOutput{'lastemailr'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'EMail'},\%_emailr_h,\%_emailr_l); }
4957
foreach my $key (@keylist) {
4959
if (length($key)>$MaxLengthOfShownEMail) { $newkey=substr($key,0,$MaxLengthOfShownEMail)."..."; }
4960
my $bredde_h=0;my $bredde_k=0;
4961
if ($max_h > 0) { $bredde_h=int($BarWidth*$_emailr_h{$key}/$max_h)+1; }
4962
if ($max_k > 0) { $bredde_k=int($BarWidth*$_emailr_k{$key}/$max_k)+1; }
4964
my $direction=IsLocalEMail($key);
4965
if ($direction > 0) { print "<td class=\"aws\">$newkey</td><td><-</td><td> </td>"; }
4966
if ($direction == 0) { print "<td colspan=\"3\"><span style=\"color: #$color_other\">$newkey</span></td>"; }
4967
if ($direction < 0) { print "<td class=\"aws\"> </td><td>-></td><td>$newkey</td>"; }
4968
if ($ShowEMailReceivers =~ /H/i) { print "<td>$_emailr_h{$key}</td>"; }
4969
if ($ShowEMailReceivers =~ /B/i) { print "<td>".Format_Bytes($_emailr_k{$key})."</td>"; }
4970
if ($ShowEMailReceivers =~ /M/i) { print "<td>".Format_Bytes($_emailr_k{$key}/($_emailr_h{$key}||1))."</td>"; }
4971
if ($ShowEMailReceivers =~ /L/i) { print "<td>".($_emailr_l{$key}?Format_Date($_emailr_l{$key},1):'-')."</td>"; }
4973
#$total_p += $_emailr_p{$key};
4974
$total_h += $_emailr_h{$key};
4975
$total_k += $_emailr_k{$key};
4978
$rest_p=0; # $rest_p=$TotalPages-$total_p;
4979
$rest_h=$TotalHits-$total_h;
4980
$rest_k=$TotalBytes-$total_k;
4981
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other receiver emails
4982
print "<tr><td colspan=\"3\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
4983
if ($ShowEMailReceivers =~ /H/i) { print "<td>$rest_h</td>"; }
4984
if ($ShowEMailReceivers =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
4985
if ($ShowEMailReceivers =~ /M/i) { print "<td>".Format_Bytes($rest_k/($rest_h||1))."</td>"; }
4986
if ($ShowEMailReceivers =~ /L/i) { print "<td> </td>"; }
4994
#------------------------------------------------------------------------------
4996
#------------------------------------------------------------------------------
4997
($DIR=$0) =~ s/([^\/\\]+)$//; ($PROG=$1) =~ s/\.([^\.]*)$//; $Extension=$1;
4998
$DIR||='.'; $DIR =~ s/([^\/\\])[\\\/]+$/$1/;
5002
# Get current time (time when AWStats was started)
5003
($nowsec,$nowmin,$nowhour,$nowday,$nowmonth,$nowyear,$nowwday,$nowyday) = localtime($starttime);
5004
$nowweekofmonth=int($nowday/7);
5005
$nowweekofyear=int(($nowyday-1+6-($nowwday==0?6:$nowwday-1))/7)+1; if ($nowweekofyear > 52) { $nowweekofyear = 1; }
5006
$nowdaymod=$nowday%7;
5008
$nowns=Time::Local::timegm(0,0,0,$nowday,$nowmonth,$nowyear);
5009
if ($nowdaymod <= $nowwday) { if (($nowwday != 7) || ($nowdaymod != 0)) { $nowweekofmonth=$nowweekofmonth+1; } }
5010
if ($nowdaymod > $nowwday) { $nowweekofmonth=$nowweekofmonth+2; }
5011
# Change format of time variables
5012
$nowweekofmonth="0$nowweekofmonth";
5013
if ($nowweekofyear < 10) { $nowweekofyear = "0$nowweekofyear"; }
5014
if ($nowyear < 100) { $nowyear+=2000; } else { $nowyear+=1900; }
5015
$nowsmallyear=$nowyear;$nowsmallyear =~ s/^..//;
5016
if (++$nowmonth < 10) { $nowmonth = "0$nowmonth"; }
5017
if ($nowday < 10) { $nowday = "0$nowday"; }
5018
if ($nowhour < 10) { $nowhour = "0$nowhour"; }
5019
if ($nowmin < 10) { $nowmin = "0$nowmin"; }
5020
if ($nowsec < 10) { $nowsec = "0$nowsec"; }
5021
$nowtime=int($nowyear.$nowmonth.$nowday.$nowhour.$nowmin.$nowsec);
5022
# Get tomorrow time (will be used to discard some record with corrupted date (future date))
5023
my ($tomorrowsec,$tomorrowmin,$tomorrowhour,$tomorrowday,$tomorrowmonth,$tomorrowyear) = localtime($starttime+86400);
5024
if ($tomorrowyear < 100) { $tomorrowyear+=2000; } else { $tomorrowyear+=1900; }
5025
if (++$tomorrowmonth < 10) { $tomorrowmonth = "0$tomorrowmonth"; }
5026
if ($tomorrowday < 10) { $tomorrowday = "0$tomorrowday"; }
5027
if ($tomorrowhour < 10) { $tomorrowhour = "0$tomorrowhour"; }
5028
if ($tomorrowmin < 10) { $tomorrowmin = "0$tomorrowmin"; }
5029
if ($tomorrowsec < 10) { $tomorrowsec = "0$tomorrowsec"; }
5030
$tomorrowtime=int($tomorrowyear.$tomorrowmonth.$tomorrowday.$tomorrowhour.$tomorrowmin.$tomorrowsec);
5033
my @AllowedCLIArgs=('migrate','config',
5034
'logfile','output','runascli','update',
5035
'staticlinks','staticlinksext','noloadplugin','loadplugin',
5036
'hostfilter','urlfilter','refererpagesfilter',
5037
'lang','month','year','framename','debug',
5038
'showsteps','showdropped','showcorrupted','showunknownorigin',
5039
'limitflush','confdir','updatefor',
5040
'hostfilter','hostfilterex','urlfilter','urlfilterex','refererpagesfilter','refererpagesfilterex',
5041
'pluginmode','filterrawlog');
5044
# AWStats use GATEWAY_INTERFACE to known if ran as CLI or CGI. AWSTATS_DEL_GATEWAY_INTERFACE can
5045
# be set to force AWStats to be ran as CLI even from a web page.
5046
if ($ENV{'AWSTATS_DEL_GATEWAY_INTERFACE'}) { $ENV{'GATEWAY_INTERFACE'}=''; }
5047
if ($ENV{'GATEWAY_INTERFACE'}) { # Run from a browser as CGI
5048
if ($BuildReportFormat eq 'xml') { print ($ENV{'HTTP_USER_AGENT'}=~/MSIE|Googlebot/i?"Content-type: text/html\n":"Content-type: text/xml\n"); }
5049
else { print "Content-type: text/html\n"; }
5051
# Prepare QueryString
5052
if ($ENV{'CONTENT_LENGTH'}) {
5054
read(STDIN, $QueryString, $ENV{'CONTENT_LENGTH'});
5056
if ($ENV{'QUERY_STRING'}) { $QueryString = $ENV{'QUERY_STRING'}; }
5058
$QueryString = CleanFromCSSA($QueryString);
5059
# No update but report by default when run from a browser
5060
$UpdateStats=($QueryString=~/update=1/i?1:0);
5062
if ($QueryString =~ /config=([^&]+)/i) { $SiteConfig=&DecodeEncodedString("$1"); }
5063
if ($QueryString =~ /logfile=([^&]+)/i) { $LogFile=&DecodeEncodedString("$1"); }
5064
if ($QueryString =~ /diricons=([^&]+)/i) { $DirIcons=&DecodeEncodedString("$1"); }
5065
if ($QueryString =~ /pluginmode=([^&]+)/i) { $PluginMode=&DecodeEncodedString("$1"); }
5066
if ($QueryString =~ /configdir=([^&]+)/i) { $DirConfig=&DecodeEncodedString("$1"); }
5068
if ($QueryString =~ /hostfilter=([^&]+)/i) { $FilterIn{'host'}=&DecodeEncodedString("$1"); } # Filter on host list can also be defined with hostfilter=filter
5069
if ($QueryString =~ /hostfilterex=([^&]+)/i) { $FilterEx{'host'}=&DecodeEncodedString("$1"); } #
5070
if ($QueryString =~ /urlfilter=([^&]+)/i) { $FilterIn{'url'}=&DecodeEncodedString("$1"); } # Filter on URL list can also be defined with urlfilter=filter
5071
if ($QueryString =~ /urlfilterex=([^&]+)/i) { $FilterEx{'url'}=&DecodeEncodedString("$1"); } #
5072
if ($QueryString =~ /refererpagesfilter=([^&]+)/i) { $FilterIn{'refererpages'}=&DecodeEncodedString("$1"); } # Filter on referer list can also be defined with refererpagesfilter=filter
5073
if ($QueryString =~ /refererpagesfilterex=([^&]+)/i) { $FilterEx{'refererpages'}=&DecodeEncodedString("$1"); } #
5075
if ($QueryString =~ /output=allhosts:([^&]+)/i) { $FilterIn{'host'}=&DecodeEncodedString("$1"); } # Filter on host list can be defined with output=allhosts:filter to reduce number of lines read and showed
5076
if ($QueryString =~ /output=lasthosts:([^&]+)/i) { $FilterIn{'host'}=&DecodeEncodedString("$1"); } # Filter on host list can be defined with output=lasthosts:filter to reduce number of lines read and showed
5077
if ($QueryString =~ /output=urldetail:([^&]+)/i) { $FilterIn{'url'}=&DecodeEncodedString("$1"); } # Filter on URL list can be defined with output=urldetail:filter to reduce number of lines read and showed
5078
if ($QueryString =~ /output=refererpages:([^&]+)/i) { $FilterIn{'refererpages'}=&DecodeEncodedString("$1"); } # Filter on referer list can be defined with output=refererpages:filter to reduce number of lines read and showed
5081
if ($QueryString =~ /(^|-|&)migrate=([^&]+)/i) {
5082
$MigrateStats=&DecodeEncodedString("$2");
5083
$MigrateStats =~ /^(.*)$PROG(\d{0,2})(\d\d)(\d\d\d\d)(.*)\.txt$/;
5084
$SiteConfig=$5?$5:'xxx'; $SiteConfig =~ s/^\.//; # SiteConfig is used to find config file
5087
else { # Run from command line
5088
# Prepare QueryString
5091
if ($ARGV[$_] =~ /(^|-|&)migrate=([^&]+)/i) {
5093
$MigrateStats =~ /^(.*)$PROG(\d{0,2})(\d\d)(\d\d\d\d)(.*)\.txt$/;
5094
$SiteConfig=$5?$5:'xxx'; $SiteConfig =~ s/^\.//; # SiteConfig is used to find config file
5097
# TODO Check if ARGV is in @AllowedArg
5098
if ($QueryString) { $QueryString .= '&'; }
5099
my $NewLinkParams=$ARGV[$_]; $NewLinkParams =~ s/^-+//;
5100
$QueryString .= "$NewLinkParams";
5103
$QueryString = CleanFromCSSA($QueryString);
5104
# Update with no report by default when run from command line
5107
if ($QueryString =~ /config=([^&]+)/i) { $SiteConfig="$1"; }
5108
if ($QueryString =~ /logfile=([^&]+)/i) { $LogFile="$1"; }
5109
if ($QueryString =~ /diricons=([^&]+)/i) { $DirIcons="$1"; }
5110
if ($QueryString =~ /pluginmode=([^&]+)/i) { $PluginMode="$1"; }
5111
if ($QueryString =~ /configdir=([^&]+)/i) { $DirConfig="$1"; }
5113
if ($QueryString =~ /hostfilter=([^&]+)/i) { $FilterIn{'host'}="$1"; } # Filter on host list can also be defined with hostfilter=filter
5114
if ($QueryString =~ /hostfilterex=([^&]+)/i) { $FilterEx{'host'}="$1"; } #
5115
if ($QueryString =~ /urlfilter=([^&]+)/i) { $FilterIn{'url'}="$1"; } # Filter on URL list can also be defined with urlfilter=filter
5116
if ($QueryString =~ /urlfilterex=([^&]+)/i) { $FilterEx{'url'}="$1"; } #
5117
if ($QueryString =~ /refererpagesfilter=([^&]+)/i) { $FilterIn{'refererpages'}="$1"; } # Filter on referer list can also be defined with refererpagesfilter=filter
5118
if ($QueryString =~ /refererpagesfilterex=([^&]+)/i) { $FilterEx{'refererpages'}="$1"; } #
5120
if ($QueryString =~ /output=allhosts:([^&]+)/i) { $FilterIn{'host'}="$1"; } # Filter on host list can be defined with output=allhosts:filter to reduce number of lines read and showed
5121
if ($QueryString =~ /output=lasthosts:([^&]+)/i) { $FilterIn{'host'}="$1"; } # Filter on host list can be defined with output=lasthosts:filter to reduce number of lines read and showed
5122
if ($QueryString =~ /output=urldetail:([^&]+)/i) { $FilterIn{'url'}="$1"; } # Filter on URL list can be defined with output=urldetail:filter to reduce number of lines read and showed
5123
if ($QueryString =~ /output=refererpages:([^&]+)/i) { $FilterIn{'refererpages'}="$1"; } # Filter on referer list can be defined with output=refererpages:filter to reduce number of lines read and showed
5126
if ($QueryString =~ /showsteps/i) { $ShowSteps=1; $QueryString=~s/showsteps[^&]*//i; }
5127
if ($QueryString =~ /showcorrupted/i) { $ShowCorrupted=1; $QueryString=~s/showcorrupted[^&]*//i; }
5128
if ($QueryString =~ /showdropped/i) { $ShowDropped=1; $QueryString=~s/showdropped[^&]*//i; }
5129
if ($QueryString =~ /showunknownorigin/i) { $ShowUnknownOrigin=1; $QueryString=~s/showunknownorigin[^&]*//i; }
5131
if ($QueryString =~ /(^|&)staticlinks/i) { $StaticLinks=".$SiteConfig"; }
5132
if ($QueryString =~ /(^|&)staticlinks=([^&]+)/i) { $StaticLinks=".$2"; } # When ran from awstatsbuildstaticpages.pl
5133
if ($QueryString =~ /(^|&)staticlinksext=([^&]+)/i) { $StaticExt="$2"; }
5134
if ($QueryString =~ /(^|&)framename=([^&]+)/i) { $FrameName="$2"; }
5135
if ($QueryString =~ /(^|&)debug=(\d+)/i) { $Debug=$2; }
5136
if ($QueryString =~ /(^|&)updatefor=(\d+)/i) { $UpdateFor=$2; }
5137
if ($QueryString =~ /(^|&)noloadplugin=([^&]+)/i) { foreach (split(/,/,$2)) { $NoLoadPlugin{"$_"}=1; } }
5138
if ($QueryString =~ /(^|&)loadplugin=([^&]+)/i) { foreach (split(/,/,$2)) { $NoLoadPlugin{"$_"}=-1; } }
5139
if ($QueryString =~ /(^|&)limitflush=(\d+)/i) { $LIMITFLUSH=$2; }
5141
if ($QueryString =~ /(^|&)output(=[^&]*|)(.*)&output(=[^&]*|)(&|$)/i) { error("Only 1 output option is allowed","","",1); }
5142
if ($QueryString =~ /(^|&)output(=[^&]*|)(&|$)/i) {
5143
# At least one output expected. We define %HTMLOutput
5144
my $outputlist="$2";
5146
$outputlist =~ s/^=//;
5147
foreach my $outputparam (split(/,/,$outputlist)) {
5148
$outputparam=~s/:(.*)$//;
5149
if ($outputparam) { $HTMLOutput{lc($outputparam)}="$1"||1; }
5152
# If on command line and no update
5153
if (! $ENV{'GATEWAY_INTERFACE'} && $QueryString !~ /update/i) { $UpdateStats=0; }
5154
# If no output defined, used default value
5155
if (! scalar keys %HTMLOutput) { $HTMLOutput{'main'}=1; }
5157
if ($ENV{'GATEWAY_INTERFACE'} && ! scalar keys %HTMLOutput) { $HTMLOutput{'main'}=1; }
5159
# Remove -output option with no = from QueryString
5160
$QueryString=~s/(^|&)output(&|$)/$1/i; $QueryString=~s/&+$//;
5162
# Check year and month parameters
5163
if ($QueryString =~ /(^|&)month=(year)/i) { error("month=year is a deprecated option. Use month=all instead."); }
5164
if ($QueryString =~ /(^|&)year=(\d\d\d\d)/i) { $YearRequired=sprintf("%04d",$2); }
5165
else { $YearRequired="$nowyear"; }
5166
if ($QueryString =~ /(^|&)month=(\d{1,2})/i) { $MonthRequired=sprintf("%02d",$2); }
5167
elsif ($QueryString =~ /(^|&)month=(all)/i) { $MonthRequired='all'; }
5168
else { $MonthRequired="$nowmonth"; }
5169
if ($QueryString =~ /(^|&)day=(\d{1,2})/i) { $DayRequired=sprintf("%02d",$2); } # day is a hidden option. Must not be used (Make results not understandable). Available for users that rename history files with day.
5170
else { $DayRequired=''; }
5172
# Check parameter validity
5175
# Print AWStats and Perl version
5177
if ($ENV{'GATEWAY_INTERFACE'}) { print "\n"; } # To end the HTTP header and see all debug
5178
debug(ucfirst($PROG)." - $VERSION - Perl $^X $]",1);
5179
debug("DIR=$DIR PROG=$PROG",2);
5180
debug("QUERY_STRING=$QueryString",2);
5181
debug("HTMLOutput=".join(',',keys %HTMLOutput),1);
5182
debug("YearRequired=$YearRequired, MonthRequired=$MonthRequired",2);
5183
debug("UpdateFor=$UpdateFor",2);
5184
debug("PluginMode=$PluginMode",2);
5185
debug("DirConfig=$DirConfig",2);
5188
# Force SiteConfig if AWSTATS_FORCE_CONFIG is defined
5189
if ($ENV{'AWSTATS_CONFIG'}) { $ENV{'AWSTATS_FORCE_CONFIG'}=$ENV{'AWSTATS_CONFIG'}; } # For backward compatibility
5190
if ($ENV{'AWSTATS_FORCE_CONFIG'}) {
5191
if ($Debug) { debug("AWSTATS_FORCE_CONFIG parameter is defined to '".$ENV{'AWSTATS_FORCE_CONFIG'}."'. $PROG will use this as config value."); }
5192
$SiteConfig=$ENV{'AWSTATS_FORCE_CONFIG'};
5195
if ((! $ENV{'GATEWAY_INTERFACE'}) && (! $SiteConfig)) {
5196
&Read_Ref_Data('browsers','domains','operating_systems','robots','search_engines','worms');
5197
print "----- $PROG $VERSION (c) Laurent Destailleur -----\n";
5198
print "$PROG is a free web server logfile analyzer to show you advanced web\n";
5199
print "statistics.\n";
5200
print "$PROG comes with ABSOLUTELY NO WARRANTY. It's a free software distributed\n";
5201
print "with a GNU General Public License (See LICENSE file for details).\n";
5203
print "Syntax: $PROG.$Extension -config=virtualhostname [options]\n";
5205
print " This runs $PROG in command line to update statistics of a web site, from\n";
5206
print " the log file defined in config file, and/or returns a HTML report.\n";
5207
print " First, $PROG tries to read $PROG.virtualhostname.conf as the config file.\n";
5208
print " If not found, $PROG tries to read $PROG.conf\n";
5209
print " Note 1: Config files ($PROG.virtualhostname.conf or $PROG.conf) must be\n";
5210
print " in /etc/awstats, /usr/local/etc/awstats, /etc or same directory than\n";
5211
print " awstats.pl file.\n";
5212
print " Note 2: If AWSTATS_FORCE_CONFIG environment variable is defined, AWStats will\n";
5213
print " use it as the \"config\" value, whatever is the value on command line or URL.\n";
5214
print " See AWStats documentation for all setup instrutions.\n";
5216
print "Options to update statistics:\n";
5217
print " -update to update statistics (default)\n";
5218
print " -showsteps to add benchmark information every $NBOFLINESFORBENCHMARK lines processed\n";
5219
print " -showcorrupted to add output for each corrupted lines found, with reason\n";
5220
print " -showdropped to add output for each dropped lines found, with reason\n";
5221
print " -logfile=x to change log to analyze whatever is 'LogFile' in config file\n";
5222
print " -updatefor=n to stop the update process after parsing n lines\n";
5223
print " Be care to process log files in chronological order when updating statistics.\n";
5225
print "Options to show statistics:\n";
5226
print " -output to output main HTML report (no update made except with -update)\n";
5227
print " -output=x to output other report pages where x is:\n";
5228
print " alldomains to build page of all domains/countries\n";
5229
print " allhosts to build page of all hosts\n";
5230
print " lasthosts to build page of last hits for hosts\n";
5231
print " unknownip to build page of all unresolved IP\n";
5232
print " allemails to build page of all email senders (maillog)\n";
5233
print " lastemails to build page of last email senders (maillog)\n";
5234
print " allemailr to build page of all email receivers (maillog)\n";
5235
print " lastemailr to build page of last email receivers (maillog)\n";
5236
print " alllogins to build page of all logins used\n";
5237
print " lastlogins to build page of last hits for logins\n";
5238
print " allrobots to build page of all robots/spider visits\n";
5239
print " lastrobots to build page of last hits for robots\n";
5240
print " urldetail to list most often viewed pages \n";
5241
print " urldetail:filter to list most often viewed pages matching filter\n";
5242
print " urlentry to list entry pages\n";
5243
print " urlentry:filter to list entry pages matching filter\n";
5244
print " urlexit to list exit pages\n";
5245
print " urlexit:filter to list exit pages matching filter\n";
5246
print " osdetail to build page with os detailed versions\n";
5247
print " browserdetail to build page with browsers detailed versions\n";
5248
print " unknownbrowser to list 'User Agents' with unknown browser\n";
5249
print " unknownos to list 'User Agents' with unknown OS\n";
5250
print " refererse to build page of all refering search engines\n";
5251
print " refererpages to build page of all refering pages\n";
5252
#print " referersites to build page of all refering sites\n";
5253
print " keyphrases to list all keyphrases used on search engines\n";
5254
print " keywords to list all keywords used on search engines\n";
5255
print " errors404 to list 'Referers' for 404 errors\n";
5256
print " -staticlinks to have static links in HTML report page\n";
5257
print " -staticlinksext=xxx to have static links with .xxx extension instead of .html\n";
5258
print " -lang=LL to output a HTML report in language LL (en,de,es,fr,it,nl,...)\n";
5259
print " -month=MM to output a HTML report for an old month MM\n";
5260
print " -year=YYYY to output a HTML report for an old year YYYY\n";
5261
print " Those 'date' options doesn't allow you to process old log file. They only\n";
5262
print " allow you to see a past report for a chosen month/year period instead of\n";
5263
print " current month/year.\n";
5265
print "Other options:\n";
5266
print " -debug=X to add debug informations lesser than level X (speed reduced)\n";
5268
print "Now supports/detects:\n";
5269
print " Web/Ftp/Mail log analyze\n";
5270
print " Reverse DNS lookup (IPv4 and IPv6) and GeoIP lookup\n";
5271
print " Number of visits, number of unique visitors\n";
5272
print " Visits duration and list of last visits\n";
5273
print " Authenticated users\n";
5274
print " Days of week and rush hours\n";
5275
print " Hosts list and unresolved IP addresses list\n";
5276
print " Most viewed, entry and exit pages\n";
5277
print " Files type and Web compression\n";
5278
print " Screen size\n";
5279
print " Number of times site is 'added to favorites bookmarks'\n";
5280
print " Ratio of Browsers with support of: Java, Flash, RealG2 reader,\n";
5281
print " Quicktime reader, WMA reader, PDF reader\n";
5282
print " Personalized reports\n";
5283
print " ".(scalar keys %DomainsHashIDLib)." domains/countries\n";
5284
print " ".(scalar keys %RobotsHashIDLib)." robots\n";
5285
print " ".(scalar keys %OSHashLib)." operating systems\n";
5286
print " ".(scalar keys %BrowsersHashIDLib)." browsers\n";
5287
print " ".(scalar keys %SearchEnginesHashLib)." search engines (and keyphrases/keywords used from them)\n";
5288
print " All HTTP errors with last referrer\n";
5289
print " Report by day/month/year\n";
5290
print " Dynamic or static HTML reports, static PDF reports\n";
5291
print " And a lot of other advanced options...\n";
5292
print "New versions and FAQ at http://awstats.sourceforge.net\n";
5295
$SiteConfig||=$ENV{'SERVER_NAME'};
5296
#$ENV{'SERVER_NAME'}||=$SiteConfig; # For thoose who use __SERVER_NAME__ in conf file and use CLI.
5297
$ENV{'AWSTATS_CURRENT_CONFIG'}=$SiteConfig;
5299
# Read config file (SiteConfig must be defined)
5300
&Read_Config($DirConfig);
5302
if ($ENV{'GATEWAY_INTERFACE'}) { # Run from a browser as CGI
5303
# Expires must be GMT ANSI asctime and must be after Content-type to avoid pb with some servers (SAMBAR)
5304
if (! $HeaderHTTPComplete) {
5305
if ($Expires =~ /^\d+$/) {
5306
print "Cache-Control: public\n";
5307
print "Last-Modified: ".gmtime($starttime)."\n";
5308
print "Expires: ".(gmtime($starttime+$Expires))."\n";
5312
$HeaderHTTPComplete=1;
5316
if ($QueryString =~ /(^|&)lang=([^&]+)/i) { $Lang="$2"; }
5317
if (! $Lang || $Lang eq 'auto') { # If lang not defined or forced to auto
5318
my $langlist=$ENV{'HTTP_ACCEPT_LANGUAGE'}||''; $langlist =~ s/;[^,]*//g;
5319
if ($Debug) { debug("Search an available language among HTTP_ACCEPT_LANGUAGE=$langlist",1); }
5320
foreach my $code (split(/,/,$langlist)) { # Search for a valid lang in priority
5321
if ($LangBrowserToLangAwstats{$code}) { $Lang=$LangBrowserToLangAwstats{$code}; if ($Debug) { debug(" Will try to use Lang=$Lang",1); } last; }
5323
if ($LangBrowserToLangAwstats{$code}) { $Lang=$LangBrowserToLangAwstats{$code}; if ($Debug) { debug(" Will try to use Lang=$Lang",1); } last; }
5326
if (! $Lang || $Lang eq 'auto') {
5327
if ($Debug) { debug(" No language defined or available. Will use Lang=en",1); }
5331
# Check and correct bad parameters
5333
# Now SiteDomain is defined
5335
# Define frame name and correct variable for frames
5337
if ($ENV{'GATEWAY_INTERFACE'} && $UseFramesWhenCGI && $HTMLOutput{'main'} && ! $PluginMode) { $FrameName='index'; }
5338
else { $FrameName='main'; }
5341
# Load Message files, Reference data files and Plugins
5342
if ($Debug) { debug("FrameName=$FrameName",1); }
5343
if ($FrameName ne 'index') {
5344
&Read_Language_Data($Lang);
5345
if ($FrameName ne 'mainleft') {
5347
if ($UpdateStats) { # If update
5348
if ($LevelForFileTypesDetection<2) { $datatoload{'mime'}=1; } # Only if need to filter on known extensions
5349
if ($LevelForRobotsDetection) { $datatoload{'robots'}=1; } # ua
5350
if ($LevelForWormsDetection) { $datatoload{'worms'}=1; } # url
5351
if ($LevelForBrowsersDetection) { $datatoload{'browsers'}=1; } # ua
5352
if ($LevelForOSDetection) { $datatoload{'operating_systems'}=1; } # ua
5353
if ($LevelForRefererAnalyze) { $datatoload{'search_engines'}=1; } # referer
5354
# if (...) { $datatoload{'referer_spam'}=1; }
5356
if (scalar keys %HTMLOutput) { # If output
5357
if ($ShowDomainsStats) { $datatoload{'domains'}=1; }
5358
if ($ShowFileTypesStats) { $datatoload{'mime'}=1; }
5359
if ($ShowRobotsStats) { $datatoload{'robots'}=1; }
5360
if ($ShowWormsStats) { $datatoload{'worms'}=1; }
5361
if ($ShowBrowsersStats) { $datatoload{'browsers'}=1; }
5362
if ($ShowOSStats) { $datatoload{'operating_systems'}=1; }
5363
if ($ShowOriginStats) { $datatoload{'search_engines'}=1; }
5364
if ($ShowHTTPErrorsStats) { $datatoload{'status_http'}=1; }
5365
if ($ShowSMTPErrorsStats) { $datatoload{'status_smtp'}=1; }
5367
&Read_Ref_Data(keys %datatoload);
5372
# Init other parameters
5373
$NBOFLINESFORBENCHMARK--;
5374
if ($ENV{'GATEWAY_INTERFACE'}) { $DirCgi=''; }
5375
if ($DirCgi && !($DirCgi =~ /\/$/) && !($DirCgi =~ /\\$/)) { $DirCgi .= '/'; }
5376
if (! $DirData || $DirData =~ /^\./) {
5377
if (! $DirData || $DirData eq '.') { $DirData="$DIR"; } # If not defined or chosen to '.' value then DirData is current dir
5378
elsif ($DIR && $DIR ne '.') { $DirData="$DIR/$DirData"; }
5380
$DirData||='.'; # If current dir not defined then we put it to '.'
5381
$DirData =~ s/[\\\/]+$//;
5382
# Define SiteToAnalyze and SiteToAnalyzeWithoutwww for regex operations
5383
$SiteToAnalyze=lc($SiteDomain); $SiteToAnalyze =~ s/\./\\\./g;
5384
$SiteToAnalyzeWithoutwww = $SiteToAnalyze; $SiteToAnalyzeWithoutwww =~ s/www\.//;
5385
if ($FirstDayOfWeek == 1) { @DOWIndex = (1,2,3,4,5,6,0); }
5386
else { @DOWIndex = (0,1,2,3,4,5,6); }
5388
# Should we link to ourselves or to a wrapper script
5389
$AWScript=($WrapperScript?"$WrapperScript":"$DirCgi$PROG.$Extension");
5391
# Print html header (Need HTMLOutput,Expires,Lang,StyleSheet,HTMLHeadSectionExpires defined by Read_Config, PageCodes defined by Read_Language_Data)
5392
if (! $HeaderHTMLComplete) { &html_head; }
5394
# AWStats output is replaced by a plugin output
5396
my $function="BuildFullHTMLOutput_$PluginMode()";
5398
if ($? || $@) { error("$@"); }
5404
if ($AllowAccessFromWebToAuthenticatedUsersOnly && $ENV{'GATEWAY_INTERFACE'}) {
5405
if ($Debug) { debug("REMOTE_USER=".$ENV{"REMOTE_USER"}); }
5406
if (! $ENV{"REMOTE_USER"}) {
5407
error("Access to statistics is only allowed from an authenticated session to authenticated users.");
5409
if (@AllowAccessFromWebToFollowingAuthenticatedUsers) {
5411
my $currentuser=$ENV{"REMOTE_USER"};
5412
$currentuser =~ s/\s/%20/g; # Allow authenticated user with space in name to be compared to allowed user list
5413
foreach my $key (@AllowAccessFromWebToFollowingAuthenticatedUsers) {
5414
if ($currentuser eq $key) { $userisinlist=1; last; }
5416
if (! $userisinlist) {
5417
error("User '$currentuser' is not allowed to access statistics of this domain/config.");
5421
if ($AllowAccessFromWebToFollowingIPAddresses && $ENV{'GATEWAY_INTERFACE'}) {
5422
my $useripaddress=&Convert_IP_To_Decimal($ENV{"REMOTE_ADDR"});
5423
my @allowaccessfromipaddresses = split (/[\s,]+/, $AllowAccessFromWebToFollowingIPAddresses);
5424
my $allowaccess = 0;
5425
foreach my $ipaddressrange (@allowaccessfromipaddresses) {
5426
if ($ipaddressrange !~ /^(\d+\.\d+\.\d+\.\d+)(?:-(\d+\.\d+\.\d+\.\d+))*$/) {
5427
error("AllowAccessFromWebToFollowingIPAddresses is defined to '$AllowAccessFromWebToFollowingIPAddresses' but does not match the correct syntax: IPAddressMin[-IPAddressMax]");
5429
my $ipmin=&Convert_IP_To_Decimal($1);
5430
my $ipmax=$2?&Convert_IP_To_Decimal($2):$ipmin;
5431
# Is it an authorized ip ?
5432
if (($useripaddress >= $ipmin) && ($useripaddress <= $ipmax)) {
5437
if (! $allowaccess) {
5438
error("Access to statistics is not allowed from your IP Address ".$ENV{"REMOTE_ADDR"});
5441
if (($UpdateStats || $MigrateStats) && (! $AllowToUpdateStatsFromBrowser) && $ENV{'GATEWAY_INTERFACE'}) {
5442
error("".($UpdateStats?"Update":"Migrate")." of statistics has not been allowed from a browser (AllowToUpdateStatsFromBrowser should be set to 1).");
5444
if (scalar keys %HTMLOutput && $MonthRequired eq 'all') {
5445
if (! $AllowFullYearView) { error("Full year view has not been allowed (AllowFullYearView is set to 0)."); }
5446
if ($AllowFullYearView < 3 && $ENV{'GATEWAY_INTERFACE'}) { error("Full year view has not been allowed from a browser (AllowFullYearView should be set to 3)."); }
5450
#------------------------------------------
5451
# MIGRATE PROCESS (Must be after reading config cause we need MaxNbOf... and Min...)
5452
#------------------------------------------
5453
if ($MigrateStats) {
5454
if ($Debug) { debug("MigrateStats is $MigrateStats",2); }
5455
if ($MigrateStats !~ /^(.*)$PROG(\d{0,2})(\d\d)(\d\d\d\d)(.*)\.txt$/) {
5456
error("AWStats history file name must match following syntax: ${PROG}MMYYYY[.config].txt","","",1);
5460
$MonthRequired="$3";
5464
if (! $DirData || $DirData =~ /^\./) {
5465
if (! $DirData || $DirData eq '.') { $DirData="$DIR"; } # If not defined or chosen to '.' value then DirData is current dir
5466
elsif ($DIR && $DIR ne '.') { $DirData="$DIR/$DirData"; }
5468
$DirData||='.'; # If current dir not defined then we put it to '.'
5469
$DirData =~ s/[\\\/]+$//;
5470
print "Start migration for file '$MigrateStats'."; print $ENV{'GATEWAY_INTERFACE'}?"<br />\n":"\n";
5471
if ($EnableLockForUpdate) { &Lock_Update(1); }
5472
my $newhistory=&Read_History_With_TmpUpdate($YearRequired,$MonthRequired,1,0,'all');
5473
if (rename("$newhistory","$MigrateStats")==0) {
5474
unlink "$newhistory";
5475
error("Failed to rename \"$newhistory\" into \"$MigrateStats\".\nWrite permissions on \"$MigrateStats\" might be wrong".($ENV{'GATEWAY_INTERFACE'}?" for a 'migration from web'":"")." or file might be opened.");
5477
if ($EnableLockForUpdate) { &Lock_Update(0); }
5478
print "Migration for file '$MigrateStats' successful."; print $ENV{'GATEWAY_INTERFACE'}?"<br />\n":"\n";
5483
# Output main frame page and exit. This must be after the security check.
5484
if ($FrameName eq 'index') {
5485
# Define the NewLinkParams for main chart
5486
my $NewLinkParams=${QueryString};
5487
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
5488
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
5489
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
5490
# Exit if main frame
5491
print "<frameset cols=\"$FRAMEWIDTH,*\" border=\"0\" framespacing=\"2\" frameborder=\"0\">\n";
5492
print "<frame name=\"mainleft\" src=\"".XMLEncode("$AWScript?${NewLinkParams}framename=mainleft")."\" noresize=\"0\" frameborder=\"0\" />\n";
5493
print "<frame name=\"mainright\" src=\"".XMLEncode("$AWScript?${NewLinkParams}framename=mainright")."\" noresize=\"0\" scrolling=\"YES\" frameborder=\"0\" />\n";
5494
print "<noframes><body>";
5495
print "Your browser does not support frames.<br />\n";
5496
print "You must set AWStats UseFramesWhenCGI parameter to 0\n";
5497
print "to see your reports.<br />\n";
5498
print "</body></noframes>\n";
5499
print "</frameset>\n";
5504
%MonthNumLib = ("01","$Message[60]","02","$Message[61]","03","$Message[62]","04","$Message[63]","05","$Message[64]","06","$Message[65]","07","$Message[66]","08","$Message[67]","09","$Message[68]","10","$Message[69]","11","$Message[70]","12","$Message[71]");
5506
# Build ListOfYears list with all existing years
5507
if ($Debug) { debug("Scan for last history files into DirData='$DirData'"); }
5508
$lastyearbeforeupdate=0;
5509
opendir(DIR,"$DirData");
5510
foreach (grep /^$PROG(\d\d)(\d\d\d\d)$FileSuffix\.txt(|\.gz)$/, sort readdir DIR) {
5511
/^$PROG(\d\d)(\d\d\d\d)$FileSuffix\.txt(|\.gz)$/;
5512
if (! $ListOfYears{"$2"} || "$1" gt $ListOfYears{"$2"}) {
5513
$ListOfYears{"$2"}="$1"; # ListOfYears contains max month found
5514
if ("$2" gt $lastyearbeforeupdate) { $lastyearbeforeupdate="$2"; }
5519
# Get value for LastLine
5520
if ($lastyearbeforeupdate) {
5521
# Read 'general' section of last history file for LastLine
5522
&Read_History_With_TmpUpdate($lastyearbeforeupdate,$ListOfYears{$lastyearbeforeupdate},0,0,"general");
5525
debug("Last year=$lastyearbeforeupdate - Last month=$ListOfYears{$lastyearbeforeupdate}");
5526
debug("LastLine=$LastLine");
5527
debug("LastLineNumber=$LastLineNumber");
5528
debug("LastLineOffset=$LastLineOffset");
5529
debug("LastLineChecksum=$LastLineChecksum");
5536
#------------------------------------------
5538
#------------------------------------------
5539
my $lastlinenumber=0; my $lastlineoffset=0; my $lastlineoffsetnext=0;
5541
if ($Debug) { debug("UpdateStats is $UpdateStats",2); }
5542
if ($UpdateStats && $FrameName ne 'index' && $FrameName ne 'mainleft') { # Update only on index page or when not framed to avoid update twice
5544
my %MonthNum = ("Jan","01","jan","01","Feb","02","feb","02","Mar","03","mar","03","Apr","04","apr","04","May","05","may","05","Jun","06","jun","06","Jul","07","jul","07","Aug","08","aug","08","Sep","09","sep","09","Oct","10","oct","10","Nov","11","nov","11","Dec","12","dec","12"); # MonthNum must be in english because used to translate log date in apache log files
5546
if (! scalar keys %HTMLOutput) {
5547
print "Update for config \"$FileConfig\"\n";
5548
print "With data in log file \"$LogFile\"...\n";
5551
my $lastprocessedyear=$lastyearbeforeupdate;
5552
my $lastprocessedmonth=$ListOfYears{$lastyearbeforeupdate}||0;
5553
my $lastprocessedyearmonth=sprintf("%04i%02i",$lastprocessedyear,$lastprocessedmonth);
5556
# Init RobotsSearchIDOrder required for update process
5558
if ($LevelForRobotsDetection >= 1) {
5559
foreach (1..$LevelForRobotsDetection) { push @list,"list$_"; }
5560
push @list,"listgen"; # Always added
5562
foreach my $key (@list) {
5563
push @RobotsSearchIDOrder,@{"RobotsSearchIDOrder_$key"};
5564
if ($Debug) { debug("Add ".@{"RobotsSearchIDOrder_$key"}." elements from RobotsSearchIDOrder_$key into RobotsSearchIDOrder",2); }
5566
if ($Debug) { debug("RobotsSearchIDOrder has now ".@RobotsSearchIDOrder." elements",1); }
5567
# Init SearchEnginesIDOrder required for update process
5569
if ($LevelForSearchEnginesDetection >= 1) {
5570
foreach (1..$LevelForSearchEnginesDetection) { push @list,"list$_"; }
5571
push @list,"listgen"; # Always added
5573
foreach my $key (@list) {
5574
push @SearchEnginesSearchIDOrder,@{"SearchEnginesSearchIDOrder_$key"};
5575
if ($Debug) { debug("Add ".@{"SearchEnginesSearchIDOrder_$key"}." elements from SearchEnginesSearchIDOrder_$key into SearchEnginesSearchIDOrder",2); }
5577
if ($Debug) { debug("SearchEnginesSearchIDOrder has now ".@SearchEnginesSearchIDOrder." elements",1); }
5579
# Complete HostAliases array
5580
if (! @HostAliases) {
5581
warning("Warning: HostAliases parameter is not defined, $PROG choose \"$SiteDomain localhost 127.0.0.1\".");
5582
push @HostAliases,qr/^$SiteToAnalyze$/i; push @HostAliases,qr/^localhost$/i; push @HostAliases,qr/^127\.0\.0\.1$/i;
5584
unshift @HostAliases,qr/^$SiteToAnalyze$/i; # Add SiteToAnalyze as first value
5587
@HostAliases=&OptimizeArray(\@HostAliases,1); if ($Debug) { debug("HostAliases precompiled regex list is now @HostAliases",1); }
5588
@SkipDNSLookupFor=&OptimizeArray(\@SkipDNSLookupFor,1); if ($Debug) { debug("SkipDNSLookupFor precompiled regex list is now @SkipDNSLookupFor",1); }
5589
@SkipHosts=&OptimizeArray(\@SkipHosts,1); if ($Debug) { debug("SkipHosts precompiled regex list is now @SkipHosts",1); }
5590
@SkipUserAgents=&OptimizeArray(\@SkipUserAgents,1); if ($Debug) { debug("SkipUserAgents precompiled regex list is now @SkipUserAgents",1); }
5591
@SkipFiles=&OptimizeArray(\@SkipFiles,$URLNotCaseSensitive); if ($Debug) { debug("SkipFiles precompiled regex list is now @SkipFiles",1); }
5592
@OnlyHosts=&OptimizeArray(\@OnlyHosts,1); if ($Debug) { debug("OnlyHosts precompiled regex list is now @OnlyHosts",1); }
5593
@OnlyUserAgents=&OptimizeArray(\@OnlyUserAgents,1); if ($Debug) { debug("OnlyUserAgents precompiled regex list is now @OnlyUserAgents",1); }
5594
@OnlyFiles=&OptimizeArray(\@OnlyFiles,$URLNotCaseSensitive); if ($Debug) { debug("OnlyFiles precompiled regex list is now @OnlyFiles",1); }
5595
# Precompile the regex search strings with qr
5596
@RobotsSearchIDOrder=map{qr/$_/i} @RobotsSearchIDOrder;
5597
@WormsSearchIDOrder=map{qr/$_/i} @WormsSearchIDOrder;
5598
@BrowsersSearchIDOrder=map{qr/$_/i} @BrowsersSearchIDOrder;
5599
@OSSearchIDOrder=map{qr/$_/i} @OSSearchIDOrder;
5600
@SearchEnginesSearchIDOrder=map{qr/$_/i} @SearchEnginesSearchIDOrder;
5601
my $miscquoted=quotemeta("$MiscTrackerUrl");
5602
my $defquoted=quotemeta("/$DefaultFile[0]");
5603
# Define precompiled regex
5604
my $regmisc=qr/^$miscquoted/;
5605
my $regrobot=qr/^\/robots\.txt$/i;
5606
my $regtruncanchor=qr/#(\w*)$/;
5607
my $regtruncurl=qr/([$URLQuerySeparators])(.*)$/;
5608
my $regext=qr/\.(\w{1,6})$/;
5610
if ($URLNotCaseSensitive) { $regdefault=qr/$defquoted$/i; }
5611
else { $regdefault=qr/$defquoted$/; }
5612
my $regipv4=qr/^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/;
5613
my $regipv6=qr/^[0-9A-F]*:/i;
5614
my $regvermsie=qr/msie([+_ ]|)([\d\.]*)/i;
5615
my $regvernetscape=qr/netscape.?\/([\d\.]*)/i;
5616
my $regvermozilla=qr/mozilla(\/|)([\d\.]*)/i;
5617
my $regnotie=qr/webtv|omniweb|opera/i;
5618
my $regnotnetscape=qr/gecko|compatible|opera|galeon|safari/i;
5619
my $regreferer=qr/^(\w+):\/\/([^\/:]+)(:\d+|)/;
5620
my $regreferernoquery=qr/^([^$URLQuerySeparators]+)/;
5622
# Define value of $PerlParsingFormat and @fieldlib
5623
&DefinePerlParsingFormat();
5625
# Load DNS Cache Files
5626
#------------------------------------------
5628
&Read_DNS_Cache(\%MyDNSTable,"$DNSStaticCacheFile","",1); # Load with save into a second plugin file if plugin enabled and second file not up to date. No use of FileSuffix
5629
if ($DNSLookup == 1) { # System DNS lookup required
5630
#if (! eval("use Socket;")) { error("Failed to load perl module Socket."); }
5632
&Read_DNS_Cache(\%TmpDNSLookup,"$DNSLastUpdateCacheFile","$FileSuffix",0); # Load with no save into a second plugin file. Use FileSuffix
5637
#------------------------------------------
5639
if ($EnableLockForUpdate) {
5640
# Trap signals to remove lock
5641
$SIG{INT} = \&SigHandler; # 2
5642
#$SIG{KILL} = \&SigHandler; # 9
5643
#$SIG{TERM} = \&SigHandler; # 15
5644
# Set AWStats update lock
5648
if ($Debug) { debug("Start Update process (lastprocessedmonth=$lastprocessedmonth, lastprocessedyear=$lastprocessedyear)"); }
5651
if ($Debug) { debug("Open log file \"$LogFile\""); }
5652
open(LOG,"$LogFile") || error("Couldn't open server log file \"$LogFile\" : $!");
5653
binmode LOG; # Avoid premature EOF due to log files corrupted with \cZ or bin chars
5655
# Define local variables for loop scan
5657
my $counterforflushtest=0;
5659
my $countedtraffic=0;
5660
# Reset chrono for benchmark (first call to GetDelaySinceStart)
5661
&GetDelaySinceStart(1);
5662
if (! scalar keys %HTMLOutput) { print "Phase 1 : First bypass old records, searching new record...\n"; }
5664
# Can we try a direct seek access in log ?
5666
if ($LastLine && $LastLineNumber && $LastLineOffset && $LastLineChecksum) {
5667
# Try a direct seek access to save time
5668
if ($Debug) { debug("Try a direct access to LastLine=$LastLine, LastLineNumber=$LastLineNumber, LastLineOffset=$LastLineOffset, LastLineChecksum=$LastLineChecksum"); }
5669
seek(LOG,$LastLineOffset,0);
5671
chomp $line; $line =~ s/\r$//;
5672
@field=map(/$PerlParsingFormat/,$line);
5675
foreach (0..@field-1) { $string.="$fieldlib[$_]=$field[$_] "; }
5676
if ($Debug) { debug(" Read line after direct access: $string",1); }
5678
my $checksum=&CheckSum($line);
5679
if ($Debug) { debug(" LastLineChecksum=$LastLineChecksum, Read line checksum=$checksum",1); }
5680
if ($checksum == $LastLineChecksum ) {
5681
if (! scalar keys %HTMLOutput) { print "Direct access after last updated record successfull (after line $LastLineNumber)\n"; }
5682
$lastlinenumber=$LastLineNumber;
5683
$lastlineoffset=$LastLineOffset;
5684
$lastlineoffsetnext=$LastLineOffset;
5685
#seek(LOG,$LastLineOffset,0); # Direct access succesful, we keep it.
5688
if (! scalar keys %HTMLOutput) { print "Direct access to last remembered record has fallen on another record.\nSo searching new records from beginning of log file...\n"; }
5691
$lastlineoffsetnext=0;
5696
if (! scalar keys %HTMLOutput) { print "Direct access to last remembered record is out of file.\nSo searching it from beginning of log file...\n"; }
5699
$lastlineoffsetnext=0;
5704
# No try of direct seek access
5705
if (! scalar keys %HTMLOutput) { print "Searching new records from beginning of log file...\n"; }
5708
$lastlineoffsetnext=0;
5711
while ($line=<LOG>) {
5712
chomp $line; $line =~ s/\r$//;
5713
if ($UpdateFor && $NbOfLinesParsed >= $UpdateFor) { last; }
5716
$lastlineoffset=$lastlineoffsetnext; $lastlineoffsetnext=tell LOG;
5719
if ((++$NbOfLinesShowsteps & $NBOFLINESFORBENCHMARK) == 0) {
5720
my $delay=&GetDelaySinceStart(0);
5721
print "$NbOfLinesParsed lines processed (".($delay>0?$delay:1000)." ms, ".int(1000*$NbOfLinesShowsteps/($delay>0?$delay:1000))." lines/second)\n";
5725
# Parse line record to get all required fields
5726
if (! (@field=map(/$PerlParsingFormat/,$line))) {
5727
$NbOfLinesCorrupted++;
5728
if ($ShowCorrupted) {
5729
if ($line =~ /^#/ || $line =~ /^!/) { print "Corrupted record line ".($lastlinenumber+$NbOfLinesParsed)." (comment line): $line\n"; }
5730
elsif ($line =~ /^\s*$/) { print "Corrupted record line ".($lastlinenumber+$NbOfLinesParsed)." (blank line)\n"; }
5731
else { print "Corrupted record line ".($lastlinenumber+$NbOfLinesParsed)." (record format does not match LogFormat parameter): $line\n"; }
5733
if ($NbOfLinesParsed >= $NbOfLinesForCorruptedLog && $NbOfLinesParsed == $NbOfLinesCorrupted) { error("Format error",$line,$LogFile); } # Exit with format error
5734
if ($line =~ /^__end_of_file__/) { last; } # For test purpose only
5740
foreach (0..@field-1) { $string.="$fieldlib[$_]=$field[$_] "; }
5741
if ($Debug) { debug(" Correct format line ".($lastlinenumber+$NbOfLinesParsed).": $string",4); }
5744
# Drop wrong virtual host name
5745
#----------------------------------------------------------------------
5746
if ($pos_vh>=0 && $field[$pos_vh] !~ /^$SiteDomain$/i) {
5748
foreach (@HostAliases) {
5749
if ($field[$pos_vh] =~ /$_/) { $skip=0; last; }
5752
$NbOfLinesDropped++;
5753
if ($ShowDropped) { print "Dropped record (virtual hostname '$field[$pos_vh]' does not match SiteDomain='$SiteDomain' nor HostAliases parameters): $line\n"; }
5758
# Drop wrong method/protocol
5759
#---------------------------
5760
if ($LogType ne 'M') { $field[$pos_url] =~ s/\s/%20/g; }
5761
if ($LogType eq 'W' && ($field[$pos_method] eq 'GET' || $field[$pos_method] eq 'POST' || $field[$pos_method] eq 'HEAD' || $field[$pos_method] =~ /OK/i || $field[$pos_method] =~ /ERR\!/i)) {
5762
# HTTP request. Keep only GET, POST, HEAD, *OK* and ERR! for Webstar. Do not keep OPTIONS
5764
elsif (($LogType eq 'W' || $LogType eq 'S') && ($field[$pos_method] eq 'mms'|| $field[$pos_method] eq 'rtsp' || $field[$pos_method] eq 'http' || $field[$pos_method] eq 'RTP')) {
5765
# Streaming request (windows media server or darwin streaming server)
5767
elsif ($LogType eq 'M' && $field[$pos_method] eq 'SMTP') {
5768
# Mail request ('SMTP' for mail log with maillogconvert.pl preprocessor)
5770
elsif ($LogType eq 'F' && ($field[$pos_method] eq 'RETR' || $field[$pos_method] eq 'o' || $field[$pos_method] =~ /get/i)) {
5773
elsif ($LogType eq 'F' && ($field[$pos_method] eq 'STOR' || $field[$pos_method] eq 'i' || $field[$pos_method] =~ /sent/i)) {
5777
$NbOfLinesDropped++;
5778
if ($ShowDropped) { print "Dropped record (method/protocol '$field[$pos_method]' not qualified when LogType=$LogType): $line\n"; }
5782
# Split DD/Month/YYYY:HH:MM:SS or YYYY-MM-DD HH:MM:SS or MM/DD/YY\tHH:MM:SS
5783
$field[$pos_date] =~ tr/,-\/ \t/:::::/; # " \t" is used instead of "\s" not known with tr
5784
my @dateparts=split(/:/,$field[$pos_date]); # tr and split faster than @dateparts=split(/[\/\-:\s]/,$field[$pos_date])
5785
if ($dateparts[0] =~ /^....$/) { my $tmp=$dateparts[0]; $dateparts[0]=$dateparts[2]; $dateparts[2]=$tmp; }
5786
elsif ($field[$pos_date] =~ /^..:..:..:/) { $dateparts[2]+=2000; my $tmp=$dateparts[0]; $dateparts[0]=$dateparts[1]; $dateparts[1]=$tmp; }
5787
if ($MonthNum{$dateparts[1]}) { $dateparts[1]=$MonthNum{$dateparts[1]}; } # Change lib month in num month if necessary
5789
# Now @dateparts is (DD,MM,YYYY,HH,MM,SS) and we're going to create $timerecord=YYYYMMDDHHMMSS
5790
# Plugin call : Convert a @datepart into another @datepart
5791
if ($PluginsLoaded{'ChangeTime'}{'timezone'}) { @dateparts=ChangeTime_timezone(\@dateparts); }
5792
my $yearrecord=int($dateparts[2]);
5793
my $monthrecord=int($dateparts[1]);
5794
my $hourrecord=int($dateparts[3]);
5795
my $yearmonthdayrecord=sprintf("$dateparts[2]%02i%02i",$dateparts[1],$dateparts[0]);
5796
my $timerecord=((int("$yearmonthdayrecord")*100+$dateparts[3])*100+$dateparts[4])*100+$dateparts[5];
5799
#-----------------------
5800
if ($timerecord < 10000000000000 || $timerecord > $tomorrowtime) {
5801
$NbOfLinesCorrupted++;
5802
if ($ShowCorrupted) { print "Corrupted record (invalid date, timerecord=$timerecord): $line\n"; }
5803
next; # Should not happen, kept in case of parasite/corrupted line
5805
if ($NewLinePhase) {
5806
# TODO NOTSORTEDRECORDTOLERANCE does not work around midnight
5807
if ($timerecord < ($LastLine - $NOTSORTEDRECORDTOLERANCE)) {
5808
# Should not happen, kept in case of parasite/corrupted old line
5809
$NbOfLinesCorrupted++;
5810
if ($ShowCorrupted) { print "Corrupted record (date $timerecord lower than $LastLine-$NOTSORTEDRECORDTOLERANCE): $line\n"; } next;
5814
if ($timerecord <= $LastLine) { # Already processed
5818
# We found a new line. This will replace comparison "<=" with "<" between timerecord and LastLine (we should have only new lines now)
5819
$NewLinePhase=1; # We will never enter here again
5821
if ($NbOfLinesShowsteps > 1 && ($NbOfLinesShowsteps & $NBOFLINESFORBENCHMARK)) {
5822
my $delay=&GetDelaySinceStart(0);
5823
print "".($NbOfLinesParsed-1)." lines processed (".($delay>0?$delay:1000)." ms, ".int(1000*($NbOfLinesShowsteps-1)/($delay>0?$delay:1000))." lines/second)\n";
5825
&GetDelaySinceStart(1); $NbOfLinesShowsteps=1;
5827
if (! scalar keys %HTMLOutput) {
5828
print "Phase 2 : Now process new records (Flush history on disk after ".($LIMITFLUSH<<2)." hosts)...\n";
5829
#print "Phase 2 : Now process new records (Flush history on disk after ".($LIMITFLUSH<<2)." hosts or ".($LIMITFLUSH)." URLs)...\n";
5833
# Convert URL for Webstar to common URL
5834
if ($LogFormat eq '3') {
5835
$field[$pos_url]=~s/:/\//g;
5836
if ($field[$pos_code] eq '-') { $field[$pos_code]='200'; }
5839
# Here, field array, timerecord and yearmonthdayrecord are initialized for log record
5840
if ($Debug) { debug(" This is a not already processed record ($timerecord)",4); }
5842
# We found a new line
5843
#----------------------------------------
5844
if ($timerecord > $LastLine) { $LastLine = $timerecord; } # Test should always be true except with not sorted log files
5846
# Skip for some client host IP addresses, some URLs, other URLs
5847
if (@SkipHosts && (&SkipHost($field[$pos_host]) || ($pos_hostr && &SkipHost($field[$pos_hostr])))) { $qualifdrop="Dropped record (host $field[$pos_host]".($pos_hostr?" and $field[$pos_hostr]":"")." not qualified by SkipHosts)"; }
5848
elsif (@SkipFiles && &SkipFile($field[$pos_url])) { $qualifdrop="Dropped record (URL $field[$pos_url] not qualified by SkipFiles)"; }
5849
elsif (@SkipUserAgents && $pos_agent >= 0 && &SkipUserAgent($field[$pos_agent])) { $qualifdrop="Dropped record (user agent '$field[$pos_agent]' not qualified by SkipUserAgents)"; }
5850
elsif (@OnlyHosts && ! &OnlyHost($field[$pos_host]) && (! $pos_hostr || ! &OnlyHost($field[$pos_hostr]))) { $qualifdrop="Dropped record (host $field[$pos_host]".($pos_hostr?" and $field[$pos_hostr]":"")." not qualified by OnlyHosts)"; }
5851
elsif (@OnlyFiles && ! &OnlyFile($field[$pos_url])) { $qualifdrop="Dropped record (URL $field[$pos_url] not qualified by OnlyFiles)"; }
5852
elsif (@OnlyUserAgents && ! &OnlyUserAgent($field[$pos_agent])) { $qualifdrop="Dropped record (user agent '$field[$pos_agent]' not qualified by OnlyUserAgents)"; }
5854
$NbOfLinesDropped++;
5855
if ($Debug) { debug("$qualifdrop: $line",4); }
5856
if ($ShowDropped) { print "$qualifdrop: $line\n"; }
5861
# Record is approved
5862
#-------------------
5864
# Is it in a new month section ?
5865
#-------------------------------
5866
if ((($monthrecord > $lastprocessedmonth) && ($yearrecord >= $lastprocessedyear)) || ($yearrecord > $lastprocessedyear)) {
5867
# A new month to process
5868
if ($lastprocessedmonth) {
5869
# We save data of processed month
5870
&Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,1,1,"all",($lastlinenumber+$NbOfLinesParsed),$lastlineoffset,&CheckSum($line));
5871
$counterforflushtest=0; # We reset counterforflushtest
5873
$lastprocessedyearmonth=sprintf("%04i%02i",$lastprocessedyear=$yearrecord,$lastprocessedmonth=$monthrecord);
5879
# Convert $field[$pos_size]
5880
# if ($field[$pos_size] eq '-') { $field[$pos_size]=0; }
5882
# Define a clean target URL and referrer URL
5883
# We keep a clean $field[$pos_url] and
5884
# we store original value for urlwithnoquery, tokenquery and standalonequery
5885
#---------------------------------------------------------------------------
5886
if ($URLNotCaseSensitive) { $field[$pos_url]=lc($field[$pos_url]); }
5887
# Possible URL syntax for $field[$pos_url]: /mydir/mypage.ext?param1=x¶m2=y#aaa, /mydir/mypage.ext#aaa, /
5888
my $urlwithnoquery; my $tokenquery; my $standalonequery; my $anchor='';
5889
if ($field[$pos_url] =~ s/$regtruncanchor//o) { $anchor=$1; } # Remove and save anchor
5890
if ($URLWithQuery) {
5891
$urlwithnoquery=$field[$pos_url];
5892
my $foundparam=($urlwithnoquery =~ s/$regtruncurl//o);
5894
$standalonequery=$2||'';
5895
# For IIS setup, if pos_query is enabled we need to combine the URL to query strings
5896
if (! $foundparam && $pos_query >=0 && $field[$pos_query] && $field[$pos_query] ne '-') {
5899
$standalonequery=$field[$pos_query];
5901
$field[$pos_url] .= '?'.$field[$pos_query];
5904
# Keep only params that are defined in URLWithQueryWithOnlyFollowingParameters
5905
my $newstandalonequery='';
5906
if (@URLWithQueryWithOnly) {
5907
foreach (@URLWithQueryWithOnly) {
5908
foreach my $p (split(/&/,$standalonequery)) {
5909
if ($URLNotCaseSensitive) { if ($p =~ /^$_=/i) { $newstandalonequery.="$p&"; last; } }
5910
else { if ($p =~ /^$_=/) { $newstandalonequery.="$p&"; last; } }
5913
chop $newstandalonequery;
5915
# Remove params that are marked to be ignored in URLWithQueryWithoutFollowingParameters
5916
elsif (@URLWithQueryWithout) {
5917
foreach my $p (split(/&/,$standalonequery)) {
5919
foreach (@URLWithQueryWithout) {
5920
#if ($Debug) { debug(" Check if '$_=' is param '$p' to remove it from query",5); }
5921
if ($URLNotCaseSensitive) { if ($p =~ /^$_=/i) { $found=1; last; } }
5922
else { if ($p =~ /^$_=/) { $found=1; last; } }
5924
if (! $found) { $newstandalonequery.="$p&"; }
5926
chop $newstandalonequery;
5928
else { $newstandalonequery=$standalonequery; }
5930
$field[$pos_url]=$urlwithnoquery;
5931
if ($newstandalonequery) { $field[$pos_url].="$tokenquery$newstandalonequery"; }
5935
# Trunc parameters of URL
5936
$field[$pos_url] =~ s/$regtruncurl//o;
5937
$urlwithnoquery=$field[$pos_url];
5939
$standalonequery=$2||'';
5941
if ($URLWithAnchor && $anchor) { $field[$pos_url].="#$anchor"; } # Restore anchor
5942
# Here now urlwithnoquery is /mydir/mypage.ext, /mydir, /, /page#XXX
5943
# Here now tokenquery is '' or '?' or ';'
5944
# Here now standalonequery is '' or 'param1=x'
5946
# Define page and extension
5947
#--------------------------
5951
if ($urlwithnoquery =~ /$regext/o || ($urlwithnoquery =~ /[\\\/]$/ && $DefaultFile[0] =~ /$regext/o)) {
5952
$extension=($LevelForFileTypesDetection>=2 || $MimeHashFamily{$1})?lc($1):'Unknown';
5953
if ($NotPageList{$extension}) { $PageBool=0; }
5956
$extension='Unknown';
5959
# Analyze: misc tracker (must be before return code)
5960
#---------------------------------------------------
5961
if ($urlwithnoquery =~ /$regmisc/o) {
5962
if ($Debug) { debug(" Found an URL that is a MiscTracker record with standalonequery=$standalonequery",2); }
5964
foreach (split(/&/,$standalonequery)) {
5965
if ($_ =~ /^screen=(\d+)x(\d+)/i) { $foundparam++; $_screensize_h{"$1x$2"}++; next; }
5966
#if ($_ =~ /cdi=(\d+)/i) { $foundparam++; $_screendepth_h{"$1"}++; next; }
5967
if ($_ =~ /^java=(\w+)/i) { $foundparam++; if ($1 eq 'true') { $_misc_h{"JavaEnabled"}++; } next; }
5968
if ($_ =~ /^shk=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"DirectorSupport"}++; } next; }
5969
if ($_ =~ /^fla=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"FlashSupport"}++; } next; }
5970
if ($_ =~ /^rp=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"RealPlayerSupport"}++; } next; }
5971
if ($_ =~ /^mov=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"QuickTimeSupport"}++; } next; }
5972
if ($_ =~ /^wma=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"WindowsMediaPlayerSupport"}++; } next; }
5973
if ($_ =~ /^pdf=(\w+)/i) { $foundparam++; if ($1 eq 'y') { $_misc_h{"PDFSupport"}++; } next; }
5975
if ($foundparam) { $_misc_h{"TotalMisc"}++; }
5980
if ($urlwithnoquery =~ /\/favicon\.ico$/i) {
5981
if (($field[$pos_code] != 404 || $urlwithnoquery !~ /\/.+\/favicon\.ico$/i) && ($field[$pos_agent] =~ /MSIE/)) {
5982
# We don't count one hit if (not on root and error) and MSIE
5983
# If error not on root, another hit will be made on root. If not MSIE, hit are made not only for "Adding".
5984
$_misc_h{'AddToFavourites'}++; # Hit on favicon on root or without error, we count it
5986
$countedtraffic=1; # favicon is the only case not counted anywhere
5991
if ($LevelForWormsDetection) {
5992
foreach (@WormsSearchIDOrder) {
5993
if ($field[$pos_url] =~ /$_/) {
5995
my $worm=&UnCompileRegex($_);
5996
if ($Debug) { debug(" Record is a hit from a worm identified by '$worm'",2); }
5997
$worm=$WormsHashID{$worm}||'unknown';
5999
$_worm_k{$worm}+=int($field[$pos_size]);
6000
$_worm_l{$worm}=$timerecord;
6002
if ($PageBool) { $_time_nv_p[$hourrecord]++; }
6003
$_time_nv_h[$hourrecord]++;
6004
$_time_nv_k[$hourrecord]+=int($field[$pos_size]);
6010
# Analyze: Status code
6011
#---------------------
6012
if (! $countedtraffic) {
6013
if ($LogType eq 'W' || $LogType eq 'S') { # HTTP record or Stream record
6014
if ($ValidHTTPCodes{$field[$pos_code]}) { # Code is valid
6015
if ($field[$pos_code] == 304) { $field[$pos_size]=0; }
6017
else { # Code is not valid
6018
if ($field[$pos_code] !~ /^\d\d\d$/) { $field[$pos_code]=999; }
6019
$_errors_h{$field[$pos_code]}++;
6020
$_errors_k{$field[$pos_code]}+=int($field[$pos_size]);
6021
foreach my $code (keys %TrapInfosForHTTPErrorCodes) {
6022
if ($field[$pos_code] == $code) {
6023
my $newurl=substr($field[$pos_url],0,$MaxLengthOfStoredURL);
6024
$newurl =~ s/[$URLQuerySeparators].*$//;
6025
$_sider404_h{$newurl}++;
6026
my $newreferer=$field[$pos_referer];
6027
if (! $URLReferrerWithQuery) { $newreferer =~ s/[$URLQuerySeparators].*$//; }
6028
$_referer404_h{$newurl}=$newreferer;
6032
if ($Debug) { debug(" Record stored in the status code chart (status code=$field[$pos_code])",2); }
6034
if ($PageBool) { $_time_nv_p[$hourrecord]++; }
6035
$_time_nv_h[$hourrecord]++;
6036
$_time_nv_k[$hourrecord]+=int($field[$pos_size]);
6039
elsif ($LogType eq 'M') { # Mail record
6040
if (! $ValidSMTPCodes{$field[$pos_code]}) { # Code is not valid
6041
$_errors_h{$field[$pos_code]}++;
6042
#$_errors_k{$field[$pos_code]}+=int($field[$pos_size]); # Useless since pos_size is often 0 or ? when error
6043
if ($Debug) { debug(" Record stored in the status code chart (status code=$field[$pos_code])",2); }
6045
if ($PageBool) { $_time_nv_p[$hourrecord]++; }
6046
$_time_nv_h[$hourrecord]++;
6047
$_time_nv_k[$hourrecord]+=int($field[$pos_size]);
6050
elsif ($LogType eq 'F') { # FTP record
6054
# Analyze: Robot from robot database
6055
#-----------------------------------
6056
if (! $countedtraffic) {
6057
if ($pos_agent >= 0) {
6058
if ($DecodeUA) { $field[$pos_agent] =~ s/%20/_/g; } # This is to support servers (like Roxen) that writes user agent with %20 in it
6059
$UserAgent=$field[$pos_agent];
6061
if ($LevelForRobotsDetection) {
6063
my $uarobot=$TmpRobot{$UserAgent};
6065
#study $UserAgent; Does not increase speed
6066
foreach (@RobotsSearchIDOrder) {
6067
if ($UserAgent =~ /$_/) {
6068
my $bot=&UnCompileRegex($_);
6069
$TmpRobot{$UserAgent}=$uarobot="$bot"; # Last time, we won't search if robot or not. We know it is.
6070
if ($Debug) { debug(" UserAgent '$UserAgent' is added to TmpRobot with value '$bot'",2); }
6074
if (! $uarobot) { # Last time, we won't search if robot or not. We know it's not.
6075
$TmpRobot{$UserAgent}=$uarobot='-';
6078
if ($uarobot ne '-') {
6079
# If robot, we stop here
6080
if ($Debug) { debug(" UserAgent '$UserAgent' contains robot ID '$uarobot'",2); }
6081
$_robot_h{$uarobot}++;
6082
$_robot_k{$uarobot}+=int($field[$pos_size]);
6083
$_robot_l{$uarobot}=$timerecord;
6084
if ($urlwithnoquery =~ /$regrobot/o) { $_robot_r{$uarobot}++; }
6086
if ($PageBool) { $_time_nv_p[$hourrecord]++; }
6087
$_time_nv_h[$hourrecord]++;
6088
$_time_nv_k[$hourrecord]+=int($field[$pos_size]);
6094
# Analyze: Robot from "hit on robots.txt" file
6095
# --------------------------------------------
6096
if (! $countedtraffic) {
6097
if ($urlwithnoquery =~ /$regrobot/o) {
6098
if ($Debug) { debug(" It's an unknown robot",2); }
6099
$_robot_h{'unknown'}++;
6100
$_robot_k{'unknown'}+=int($field[$pos_size]);
6101
$_robot_l{'unknown'}=$timerecord;
6102
$_robot_r{'unknown'}++;
6104
if ($PageBool) { $_time_nv_p[$hourrecord]++; }
6105
$_time_nv_h[$hourrecord]++;
6106
$_time_nv_k[$hourrecord]+=int($field[$pos_size]);
6110
# Analyze: File type - Compression
6111
#---------------------------------
6112
if (! $countedtraffic) {
6113
if ($LevelForFileTypesDetection) {
6114
$_filetypes_h{$extension}++;
6115
$_filetypes_k{$extension}+=int($field[$pos_size]); # TODO can cause a warning
6117
if ($pos_compratio>=0 && ($field[$pos_compratio] =~ /(\d+)/)) { # Calculate in/out size from percentage (% is size after/before)
6118
#$_filetypes_gz_in{$extension}+=int($field[$pos_size]*100/((100-$1)||1));
6119
$_filetypes_gz_in{$extension}+=int($field[$pos_size]*100/($1||1));
6120
$_filetypes_gz_out{$extension}+=int($field[$pos_size]);
6122
elsif ($pos_gzipin>=0 && $field[$pos_gzipin]) { # If in and out in log
6123
my ($notused,$in)=split(/:/,$field[$pos_gzipin]);
6124
my ($notused1,$out,$notused2)=split(/:/,$field[$pos_gzipout]);
6126
$_filetypes_gz_in{$extension}+=$in;
6127
$_filetypes_gz_out{$extension}+=$out;
6132
# Analyze: Date - Hour - Pages - Hits - Kilo
6133
#-------------------------------------------
6135
# Replace default page name with / only ('if' is to increase speed when only 1 value in @DefaultFile)
6136
if (@DefaultFile > 1) { foreach my $elem (@DefaultFile) { if ($field[$pos_url] =~ s/\/$elem$/\//o) { last; } } }
6137
else { $field[$pos_url] =~ s/$regdefault/\//o; }
6138
# FirstTime and LastTime are First and Last human visits (so changed if access to a page)
6139
$FirstTime{$lastprocessedyearmonth}||=$timerecord;
6140
$LastTime{$lastprocessedyearmonth}=$timerecord;
6141
$DayPages{$yearmonthdayrecord}++;
6142
# $MonthPages{$lastprocessedyearmonth}++;
6143
$_url_p{$field[$pos_url]}++; #Count accesses for page (page)
6144
$_url_k{$field[$pos_url]}+=int($field[$pos_size]);
6145
$_time_p[$hourrecord]++; #Count accesses for hour (page)
6147
$_time_h[$hourrecord]++;
6148
$_time_k[$hourrecord]+=int($field[$pos_size]);
6149
$DayHits{$yearmonthdayrecord}++; #Count accesses for hour (hit)
6150
$DayBytes{$yearmonthdayrecord}+=int($field[$pos_size]); #Count accesses for hour (kb)
6151
# $MonthHits{$lastprocessedyearmonth}++;
6152
# $MonthBytes{$lastprocessedyearmonth}+=int($field[$pos_size]);
6156
if ($pos_logname>=0 && $field[$pos_logname] && $field[$pos_logname] ne '-') {
6157
$field[$pos_logname] =~ s/ /_/g; # This is to allow space in logname
6158
if ($LogFormat eq '6') { $field[$pos_logname] =~ s/^\"//; $field[$pos_logname] =~ s/\"$//;} # logname field has " with Domino 6+
6159
if ($AuthenticatedUsersNotCaseSensitive) { $field[$pos_logname]=lc($field[$pos_logname]); }
6161
# We found an authenticated user
6162
if ($PageBool) { $_login_p{$field[$pos_logname]}++; } #Count accesses for page (page)
6163
$_login_h{$field[$pos_logname]}++; #Count accesses for page (hit)
6164
$_login_k{$field[$pos_logname]}+=int($field[$pos_size]); #Count accesses for page (kb)
6165
$_login_l{$field[$pos_logname]}=$timerecord;
6171
my $Host=$field[$pos_host];
6172
my $HostResolved='';
6174
if (! $countedtraffic) {
6176
if ($DNSLookup) { # DNS lookup is 1 or 2
6177
if ($Host =~ /$regipv4/o) { $ip=4; } # IPv4
6178
elsif ($Host =~ /$regipv6/o) { $ip=6; } # IPv6
6180
# Check in static DNS cache file
6181
$HostResolved=$MyDNSTable{$Host};
6182
if ($HostResolved) {
6183
if ($Debug) { debug(" DNS lookup asked for $Host and found in static DNS cache file: $HostResolved",4); }
6185
elsif ($DNSLookup==1) {
6186
# Check in session cache (dynamic DNS cache file + session DNS cache)
6187
$HostResolved=$TmpDNSLookup{$Host};
6188
if (! $HostResolved) {
6189
if (@SkipDNSLookupFor && &SkipDNSLookup($Host)) {
6190
$HostResolved=$TmpDNSLookup{$Host}='*';
6191
if ($Debug) { debug(" No need of reverse DNS lookup for $Host, skipped at user request.",4); }
6195
my $lookupresult=gethostbyaddr(pack("C4",split(/\./,$Host)),AF_INET); # This is very slow, may spend 20 seconds
6196
if (! $lookupresult || $lookupresult =~ /$regipv4/o || ! IsAscii($lookupresult)) {
6197
$TmpDNSLookup{$Host}=$HostResolved='*';
6200
$TmpDNSLookup{$Host}=$HostResolved=$lookupresult;
6202
if ($Debug) { debug(" Reverse DNS lookup for $Host done: $HostResolved",4); }
6205
if ($PluginsLoaded{'GetResolvedIP'}{'ipv6'}) {
6206
my $lookupresult=GetResolvedIP_ipv6($Host);
6207
if (! $lookupresult || ! IsAscii($lookupresult)) {
6208
$TmpDNSLookup{$Host}=$HostResolved='*';
6211
$TmpDNSLookup{$Host}=$HostResolved=$lookupresult;
6214
$TmpDNSLookup{$Host}=$HostResolved='*';
6215
warning("Reverse DNS lookup for $Host not available without ipv6 plugin enabled.");
6218
else { error("Bad value vor ip"); }
6224
if ($Debug) { debug(" DNS lookup by static DNS cache file asked for $Host but not found.",4); }
6228
if ($Debug) { debug(" DNS lookup asked for $Host but this is not an IP address.",4); }
6229
$DNSLookupAlreadyDone=$LogFile;
6233
if ($Host =~ /$regipv4/o) { $HostResolved='*'; $ip=4; } # IPv4
6234
elsif ($Host =~ /$regipv6/o) { $HostResolved='*'; $ip=6; } # IPv6
6235
if ($Debug) { debug(" No DNS lookup asked.",4); }
6238
# Analyze: Country (Top-level domain)
6239
#------------------------------------
6240
if ($Debug) { debug(" Search country (Host=$Host HostResolved=$HostResolved ip=$ip)",4); }
6242
# Set $HostResolved to host and resolve domain
6243
if ($HostResolved eq '*') {
6244
# $Host is an IP address and is not resolved (failed or not asked) or resolution gives an IP address
6245
$HostResolved = $Host;
6247
if ($PluginsLoaded{'GetCountryCodeByAddr'}{'geoipfree'}) { $Domain=GetCountryCodeByAddr_geoipfree($HostResolved); }
6248
elsif ($PluginsLoaded{'GetCountryCodeByAddr'}{'geoip'}) { $Domain=GetCountryCodeByAddr_geoip($HostResolved); }
6251
# $Host was already a host name ($Host=name => $HostResolved='', $ip=0) or has been resolved ($Host=ip => $HostResolved defined, $ip>0)
6252
$HostResolved = lc($HostResolved?$HostResolved:$Host);
6255
if ($PluginsLoaded{'GetCountryCodeByAddr'}{'geoipfree'}) { $Domain=GetCountryCodeByAddr_geoipfree($Host); }
6256
elsif ($PluginsLoaded{'GetCountryCodeByAddr'}{'geoip'}) { $Domain=GetCountryCodeByAddr_geoip($Host); }
6257
elsif ($HostResolved =~ /\.(\w+)$/) { $Domain=$1; }
6260
if ($PluginsLoaded{'GetCountryCodeByName'}{'geoipfree'}) { $Domain=GetCountryCodeByName_geoipfree($HostResolved); }
6261
elsif ($PluginsLoaded{'GetCountryCodeByName'}{'geoip'}) { $Domain=GetCountryCodeByName_geoip($HostResolved); }
6262
elsif ($HostResolved =~ /\.(\w+)$/) { $Domain=$1; }
6266
if ($PageBool) { $_domener_p{$Domain}++; }
6267
$_domener_h{$Domain}++;
6268
$_domener_k{$Domain}+=int($field[$pos_size]);
6270
# Analyze: Host, URL and Session
6271
#-------------------------------
6273
my $timehostl=$_host_l{$HostResolved};
6275
# A visit for this host was already detected
6276
# TODO everywhere there is $VISITTIMEOUT
6277
# $timehostl =~ /^\d\d\d\d\d\d(\d\d)/; my $daytimehostl=$1;
6278
# if ($timerecord > ($timehostl+$VISITTIMEOUT+($dateparts[3]>$daytimehostl?$NEWDAYVISITTIMEOUT:0))) {
6279
if ($timerecord > ($timehostl+$VISITTIMEOUT)) {
6280
# This is a second visit or more
6281
if (! $_waithost_s{$HostResolved}) {
6282
# This is a second visit or more
6283
# We count 'visit','exit','entry','DayVisits'
6284
if ($Debug) { debug(" This is a second visit for $HostResolved.",4); }
6285
my $timehosts=$_host_s{$HostResolved};
6286
my $page=$_host_u{$HostResolved};
6287
if ($page) { $_url_x{$page}++; }
6288
$_url_e{$field[$pos_url]}++;
6289
$DayVisits{$yearmonthdayrecord}++;
6290
# We can't count session yet because we don't have the start so
6291
# we save save params of first 'wait' session
6292
$_waithost_l{$HostResolved}=$timehostl;
6293
$_waithost_s{$HostResolved}=$timehosts;
6294
$_waithost_u{$HostResolved}=$page;
6297
# This is third visit or more
6298
# We count 'session','visit','exit','entry','DayVisits'
6299
if ($Debug) { debug(" This is a third visit or more for $HostResolved.",4); }
6300
my $timehosts=$_host_s{$HostResolved};
6301
my $page=$_host_u{$HostResolved};
6302
if ($page) { $_url_x{$page}++; }
6303
$_url_e{$field[$pos_url]}++;
6304
$DayVisits{$yearmonthdayrecord}++;
6305
if ($timehosts) { $_session{GetSessionRange($timehosts,$timehostl)}++; }
6307
# Save new session properties
6308
$_host_s{$HostResolved}=$timerecord;
6309
$_host_l{$HostResolved}=$timerecord;
6310
$_host_u{$HostResolved}=$field[$pos_url];
6312
elsif ($timerecord > $timehostl) {
6313
# This is a same visit we can count
6314
if ($Debug) { debug(" This is same visit still running for $HostResolved. host_l/host_u changed to $timerecord/$field[$pos_url]",4); }
6315
$_host_l{$HostResolved}=$timerecord;
6316
$_host_u{$HostResolved}=$field[$pos_url];
6318
elsif ($timerecord == $timehostl) {
6319
# This is a same visit we can count
6320
if ($Debug) { debug(" This is same visit still running for $HostResolved. host_l/host_u changed to $timerecord/$field[$pos_url]",4); }
6321
$_host_u{$HostResolved}=$field[$pos_url];
6323
elsif ($timerecord < $_host_s{$HostResolved}) {
6324
# Should happens only with not correctly sorted log files
6325
if ($Debug) { debug(" This is same visit still running for $HostResolved with start not in order. host_s changed to $timerecord (entry page also changed if first visit)",4); }
6326
if (! $_waithost_s{$HostResolved}) {
6327
# We can reorder entry page only if it's the first visit found in this update run (The saved entry page was $_waithost_e if $_waithost_s{$HostResolved} is not defined. If second visit or more, entry was directly counted and not saved)
6328
$_waithost_e{$HostResolved}=$field[$pos_url];
6331
# We can't change entry counted as we dont't know what was the url counted as entry
6333
$_host_s{$HostResolved}=$timerecord;
6336
if ($Debug) { debug(" This is same visit still running for $HostResolved with hit between start and last hits. No change",4); }
6340
# This is a new visit (may be). First new visit found for this host. We save in wait array the entry page to count later
6341
if ($Debug) { debug(" New session (may be) for $HostResolved. Save in wait array to see later",4); }
6342
$_waithost_e{$HostResolved}=$field[$pos_url];
6343
# Save new session properties
6344
$_host_u{$HostResolved}=$field[$pos_url];
6345
$_host_s{$HostResolved}=$timerecord;
6346
$_host_l{$HostResolved}=$timerecord;
6348
$_host_p{$HostResolved}++;
6350
$_host_h{$HostResolved}++;
6351
$_host_k{$HostResolved}+=int($field[$pos_size]);
6353
# Analyze: Browser - OS
6354
#----------------------
6355
if ($pos_agent >= 0 && $UserAgent) {
6357
if ($LevelForBrowsersDetection) {
6361
my $uabrowser=$TmpBrowser{$UserAgent};
6365
if ($UserAgent =~ /$regvermsie/o && $UserAgent !~ /$regnotie/o) {
6366
$_browser_h{"msie$2"}++;
6367
$TmpBrowser{$UserAgent}="msie$2";
6369
# Netscape 6.x, 7.x ... ?
6370
elsif ($UserAgent =~ /$regvernetscape/o) {
6371
$_browser_h{"netscape$1"}++;
6372
$TmpBrowser{$UserAgent}="netscape$1";
6374
# Netscape 3.x, 4.x ... ?
6375
elsif ($UserAgent =~ /$regvermozilla/o && $UserAgent !~ /$regnotnetscape/o) {
6376
$_browser_h{"netscape$2"}++;
6377
$TmpBrowser{$UserAgent}="netscape$2";
6379
# Other known browsers ?
6382
foreach (@BrowsersSearchIDOrder) { # Search ID in order of BrowsersSearchIDOrder
6383
if ($UserAgent =~ /$_/) {
6384
my $browser=&UnCompileRegex($_);
6385
# TODO If browser is in a family, use version
6386
$_browser_h{"$browser"}++;
6387
$TmpBrowser{$UserAgent}="$browser";
6395
$_browser_h{'Unknown'}++;
6396
$TmpBrowser{$UserAgent}='Unknown';
6397
my $newua=$UserAgent; $newua =~ tr/\+ /__/;
6398
$_unknownrefererbrowser_l{$newua}=$timerecord;
6402
$_browser_h{$uabrowser}++;
6403
if ($uabrowser eq 'Unknown') {
6404
my $newua=$UserAgent; $newua =~ tr/\+ /__/;
6405
$_unknownrefererbrowser_l{$newua}=$timerecord;
6411
if ($LevelForOSDetection) {
6415
my $uaos=$TmpOS{$UserAgent};
6418
# in OSHashID list ?
6419
foreach (@OSSearchIDOrder) { # Search ID in order of OSSearchIDOrder
6420
if ($UserAgent =~ /$_/) {
6421
my $osid=$OSHashID{&UnCompileRegex($_)};
6423
$TmpOS{$UserAgent}="$osid";
6430
$_os_h{'Unknown'}++;
6431
$TmpOS{$UserAgent}='Unknown';
6432
my $newua=$UserAgent; $newua =~ tr/\+ /__/;
6433
$_unknownreferer_l{$newua}=$timerecord;
6438
if ($uaos eq 'Unknown') {
6439
my $newua=$UserAgent; $newua =~ tr/\+ /__/;
6440
$_unknownreferer_l{$newua}=$timerecord;
6448
$_browser_h{'Unknown'}++;
6449
$_os_h{'Unknown'}++;
6455
if ($pos_referer >= 0 && $LevelForRefererAnalyze && $field[$pos_referer]) {
6458
if ($field[$pos_referer] eq '-' || $field[$pos_referer] eq 'bookmarks') { # "bookmarks" is sent by Netscape, '-' by all others browsers
6460
if ($PageBool) { $_from_p[0]++; }
6465
$field[$pos_referer] =~ /$regreferer/o;
6467
my $refererserver=($2||'').(! $3 || $3 eq ':80'?'':$3); # refererserver is www.xxx.com or www.xxx.com:81 but not www.xxx.com:80
6469
if ($refererprot =~ /^http/i) {
6470
#if ($Debug) { debug(" Analyze referer refererprot=$refererprot refererserver=$refererserver",5); }
6473
if (!$TmpRefererServer{$refererserver}) { # is "=" if same site, "search egine key" if search engine, not defined otherwise
6474
if ($refererserver =~ /^(www\.|)$SiteToAnalyzeWithoutwww/i) {
6475
# Intern (This hit came from another page of the site)
6476
if ($Debug) { debug(" Server '$refererserver' is added to TmpRefererServer with value '='",2); }
6477
$TmpRefererServer{$refererserver}='=';
6481
foreach (@HostAliases) {
6482
if ($refererserver =~ /$_/) {
6483
# Intern (This hit came from another page of the site)
6484
if ($Debug) { debug(" Server '$refererserver' is added to TmpRefererServer with value '='",2); }
6485
$TmpRefererServer{$refererserver}='=';
6491
# Extern (This hit came from an external web site).
6493
if ($LevelForSearchEnginesDetection) {
6495
foreach (@SearchEnginesSearchIDOrder) { # Search ID in order of SearchEnginesSearchIDOrder
6496
if ($refererserver =~ /$_/) {
6497
my $key=&UnCompileRegex($_);
6498
if (! $NotSearchEnginesKeys{$key} || $refererserver !~ /$NotSearchEnginesKeys{$key}/i) {
6499
# This hit came from the search engine $key
6500
if ($Debug) { debug(" Server '$refererserver' is added to TmpRefererServer with value '$key'",2); }
6501
$TmpRefererServer{$refererserver}=$SearchEnginesHashID{$key};
6513
if ($TmpRefererServer{$refererserver}) {
6514
if ($TmpRefererServer{$refererserver} eq '=') {
6515
# Intern (This hit came from another page of the site)
6516
if ($PageBool) { $_from_p[4]++; }
6521
# This hit came from a search engine
6522
if ($PageBool) { $_from_p[2]++; $_se_referrals_p{$TmpRefererServer{$refererserver}}++; }
6524
$_se_referrals_h{$TmpRefererServer{$refererserver}}++;
6526
if ($PageBool && $LevelForKeywordsDetection) {
6527
# we will complete %_keyphrases hash array
6528
my @refurl=split(/\?/,$field[$pos_referer],2); # TODO Use \? or [$URLQuerySeparators] ?
6530
# Extract params of referer query string (q=cache:mmm:www/zzz+aaa+bbb q=aaa+bbb/ccc key=ddd%20eee lang_en ie=UTF-8 ...)
6531
if ($SearchEnginesKnownUrl{$TmpRefererServer{$refererserver}}) { # Search engine with known URL syntax
6532
my @paramlist=split(/&/,$KeyWordsNotSensitive?lc($refurl[1]):$refurl[1]);
6533
foreach my $param (@paramlist) {
6534
if ($param =~ s/^$SearchEnginesKnownUrl{$TmpRefererServer{$refererserver}}//) {
6535
# We found good parameter
6536
# Now param is keyphrase: "cache:mmm:www/zzz+aaa+bbb/ccc+ddd%20eee'fff,ggg"
6537
$param =~ s/^(cache|related):[^\+]+//; # Should ne useless since this is for hit on 'not pages'
6538
&ChangeWordSeparatorsIntoSpace($param); # Change [ aaa+bbb/ccc+ddd%20eee'fff,ggg ] into [ aaa bbb/ccc ddd eee fff ggg]
6539
$param =~ s/^ +//; $param =~ s/ +$//; $param =~ tr/ /\+/s;
6540
if ((length $param) > 0) { $_keyphrases{$param}++; }
6545
elsif ($LevelForKeywordsDetection >= 2) { # Search engine with unknown URL syntax
6546
my @paramlist=split(/&/,$KeyWordsNotSensitive?lc($refurl[1]):$refurl[1]);
6547
foreach my $param (@paramlist) {
6548
my $foundexcludeparam=0;
6549
foreach my $paramtoexclude (@WordsToCleanSearchUrl) {
6550
if ($param =~ /$paramtoexclude/i) { $foundexcludeparam=1; last; } # Not the param with search criteria
6552
if ($foundexcludeparam) { next; }
6553
# We found good parameter
6555
# Now param is keyphrase: "aaa+bbb/ccc+ddd%20eee'fff,ggg"
6556
$param =~ s/^(cache|related):[^\+]+//; # Should ne useless since this is for hit on 'not pages'
6557
&ChangeWordSeparatorsIntoSpace($param); # Change [ aaa+bbb/ccc+ddd%20eee'fff,ggg ] into [ aaa bbb/ccc ddd eee fff ggg ]
6558
$param =~ s/^ +//; $param =~ s/ +$//; $param =~ tr/ /\+/s;
6559
if ((length $param) > 2) { $_keyphrases{$param}++; last; }
6562
} # End of if refurl[1]
6565
} # End of if ($TmpRefererServer)
6567
# This hit came from a site other than a search engine
6568
if ($PageBool) { $_from_p[3]++; }
6570
# http://www.mysite.com/ must be same referer than http://www.mysite.com but .../mypage/ differs of .../mypage
6571
#if ($refurl[0] =~ /^[^\/]+\/$/) { $field[$pos_referer] =~ s/\/$//; } # Code moved in Save_History
6572
# TODO: lowercase the value for referer server to have refering server not case sensitive
6573
if ($URLReferrerWithQuery) {
6574
if ($PageBool) { $_pagesrefs_p{$field[$pos_referer]}++; }
6575
$_pagesrefs_h{$field[$pos_referer]}++;
6578
# We discard query for referer
6579
if ($field[$pos_referer]=~/$regreferernoquery/o) {
6580
if ($PageBool) { $_pagesrefs_p{"$1"}++; }
6581
$_pagesrefs_h{"$1"}++;
6584
if ($PageBool) { $_pagesrefs_p{$field[$pos_referer]}++; }
6585
$_pagesrefs_h{$field[$pos_referer]}++;
6593
if (! $found && $refererprot =~ /^news/i) {
6595
if ($PageBool) { $_from_p[5]++; }
6603
if ($ShowUnknownOrigin) { print "Unknown origin: $field[$pos_referer]\n"; }
6604
if ($PageBool) { $_from_p[1]++; }
6610
if ($pos_emails>=0 && $field[$pos_emails]) {
6611
if ($field[$pos_emails] eq '<>') { $field[$pos_emails]='Unknown'; }
6612
elsif ($field[$pos_emails] !~ /\@/) { $field[$pos_emails].="\@$SiteDomain"; }
6613
$_emails_h{lc($field[$pos_emails])}++; #Count accesses for sender email (hit)
6614
$_emails_k{lc($field[$pos_emails])}+=int($field[$pos_size]); #Count accesses for sender email (kb)
6615
$_emails_l{lc($field[$pos_emails])}=$timerecord;
6617
if ($pos_emailr>=0 && $field[$pos_emailr]) {
6618
if ($field[$pos_emailr] !~ /\@/) { $field[$pos_emailr].="\@$SiteDomain"; }
6619
$_emailr_h{lc($field[$pos_emailr])}++; #Count accesses for receiver email (hit)
6620
$_emailr_k{lc($field[$pos_emailr])}+=int($field[$pos_size]); #Count accesses for receiver email (kb)
6621
$_emailr_l{lc($field[$pos_emailr])}=$timerecord;
6627
if ($pos_cluster>=0) {
6628
if ($PageBool) { $_cluster_p{$field[$pos_cluster]}++; } #Count accesses for page (page)
6629
$_cluster_h{$field[$pos_cluster]}++; #Count accesses for page (hit)
6630
$_cluster_k{$field[$pos_cluster]}+=int($field[$pos_size]); #Count accesses for page (kb)
6635
foreach my $extranum (1..@ExtraName-1) {
6636
if ($Debug) { debug(" Process extra analyze $extranum",4); }
6640
foreach my $condnum (0..@{$ExtraConditionType[$extranum]}-1) {
6641
my $conditiontype=$ExtraConditionType[$extranum][$condnum];
6642
my $conditiontypeval=$ExtraConditionTypeVal[$extranum][$condnum];
6643
if ($conditiontype eq 'URL') {
6644
if ($Debug) { debug(" Check condition '$conditiontype' must contain '$conditiontypeval' in $urlwithnoquery.",5); }
6645
if ($urlwithnoquery =~ /$conditiontypeval/) { $conditionok=1; last; }
6647
elsif ($conditiontype eq 'QUERY_STRING') {
6648
if ($Debug) { debug(" Check condition '$conditiontype' must contain '$conditiontypeval' in $standalonequery.",5); }
6649
if ($standalonequery =~ /$conditiontypeval/) { $conditionok=1; last; }
6651
elsif ($conditiontype eq 'REFERER') {
6652
if ($Debug) { debug(" Check condition '$conditiontype' must contain '$conditiontypeval' in $field[$pos_referer]",5); }
6653
if ($field[$pos_referer] =~ /$conditiontypeval/) { $conditionok=1; last; }
6655
elsif ($conditiontype eq 'UA') {
6656
if ($Debug) { debug(" Check condition '$conditiontype' must contain '$conditiontypeval' in $field[$pos_agent]",5); }
6657
if ($field[$pos_agent] =~ /$conditiontypeval/) { $conditionok=1; last; }
6659
elsif ($conditiontype eq 'HOST') {
6660
if ($Debug) { debug(" Check condition '$conditiontype' must contain '$conditiontypeval' in $field[$pos_host]",5); }
6661
if ($HostResolved =~ /$conditiontypeval/) { $conditionok=1; last; }
6663
else { error("Wrong value of parameter ExtraSectionCondition$extranum"); }
6665
if (! $conditionok && @{$ExtraConditionType[$extranum]}) { next; } # End for this section
6667
if ($Debug) { debug(" No condition or Condition is OK. Now we extract value for first column of extra chart.",5); }
6669
# Determine actual column value to use.
6672
foreach my $rowkeynum (0..@{$ExtraFirstColumnValuesType[$extranum]}-1) {
6673
my $rowkeytype=$ExtraFirstColumnValuesType[$extranum][$rowkeynum];
6674
my $rowkeytypeval=$ExtraFirstColumnValuesTypeVal[$extranum][$rowkeynum];
6675
if ($rowkeytype eq 'URL') {
6676
if ($urlwithnoquery =~ /$rowkeytypeval/) { $rowkeyval = "$1"; $rowkeyok = 1; last; }
6678
elsif ($rowkeytype eq 'QUERY_STRING') {
6679
if ($Debug) { debug(" Extract value from '$standalonequery' with regex '$rowkeytypeval'.",5); }
6680
if ($standalonequery =~ /$rowkeytypeval/) { $rowkeyval = "$1"; $rowkeyok = 1; last; }
6682
elsif ($rowkeytype eq 'REFERER') {
6683
if ($field[$pos_referer] =~ /$rowkeytypeval/) { $rowkeyval = "$1"; $rowkeyok = 1; last; }
6685
elsif ($rowkeytype eq 'UA') {
6686
if ($field[$pos_agent] =~ /$rowkeytypeval/) { $rowkeyval = "$1"; $rowkeyok = 1; last; }
6688
elsif ($rowkeytype eq 'HOST') {
6689
if ($HostResolved =~ /$rowkeytypeval/) { $rowkeyval = "$1"; $rowkeyok = 1; last; }
6691
else { error("Wrong value of parameter ExtraSectionFirstColumnValues$extranum"); }
6693
if (! $rowkeyok) { next; } # End for this section
6694
if ($Debug) { debug(" Key val was found: $rowkeyval",5); }
6696
# Here we got all values to increase counters
6697
if ($PageBool && $ExtraStatTypes[$extranum] =~ /P/i) { ${'_section_' . $extranum . '_p'}{$rowkeyval}++; }
6698
${'_section_' . $extranum . '_h'}{$rowkeyval}++; # Must be set
6699
if ($ExtraStatTypes[$extranum] =~ /B/i) { ${'_section_' . $extranum . '_k'}{$rowkeyval}+=int($field[$pos_size]); }
6700
if ($ExtraStatTypes[$extranum] =~ /L/i) {
6701
if (${'_section_' . $extranum . '_l'}{$rowkeyval}||0 < $timerecord) { ${'_section_' . $extranum . '_l'}{$rowkeyval}=$timerecord; }
6703
# Check to avoid too large extra sections
6704
if (scalar keys %{'_section_' . $extranum . '_h'} > $MAXDIFFEXTRA) {
6705
error("Too many (more than MAXDIFFEXTRA=$MAXDIFFEXTRA) different values for row keys of extra section $extranum. Are you sure you want to track an array with so many values (may be your ExtraSection setup is wrong) ? If yes, increase the MAXDIFFEXTRA constant in awstats.pl");
6709
# Every 20,000 approved lines after a flush, we test to clean too large hash arrays to flush data in tmp file
6710
if (++$counterforflushtest >= 20000) {
6711
#if (++$counterforflushtest >= 1) {
6712
if ((scalar keys %_host_u) > ($LIMITFLUSH<<2) || (scalar keys %_url_p) > $LIMITFLUSH) {
6713
# warning("Warning: Try to run AWStats update process more frequently to analyze smaler log files.");
6714
if ($^X =~ /activestate/i || $^X =~ /activeperl/i) {
6715
# We don't flush if perl is activestate to avoid slowing process because of memory hole
6718
# Clean tmp hash arrays
6719
#%TmpDNSLookup = ();
6720
%TmpOS = %TmpRefererServer = %TmpRobot = %TmpBrowser = ();
6721
# We flush if perl is not activestate
6722
print "Flush history file on disk";
6723
if ((scalar keys %_host_u) > ($LIMITFLUSH<<2)) { print " (unique hosts reach flush limit of ".($LIMITFLUSH<<2).")"; }
6724
if ((scalar keys %_url_p) > $LIMITFLUSH) { print " (unique url reach flush limit of ".($LIMITFLUSH).")"; }
6727
debug("End of set of $counterforflushtest records: Some hash arrays are too large. We flush and clean some.",2);
6728
print " _host_p:".(scalar keys %_host_p)." _host_h:".(scalar keys %_host_h)." _host_k:".(scalar keys %_host_k)." _host_l:".(scalar keys %_host_l)." _host_s:".(scalar keys %_host_s)." _host_u:".(scalar keys %_host_u)."\n";
6729
print " _url_p:".(scalar keys %_url_p)." _url_k:".(scalar keys %_url_k)." _url_e:".(scalar keys %_url_e)." _url_x:".(scalar keys %_url_x)."\n";
6730
print " _waithost_e:".(scalar keys %_waithost_e)." _waithost_l:".(scalar keys %_waithost_l)." _waithost_s:".(scalar keys %_waithost_s)." _waithost_u:".(scalar keys %_waithost_u)."\n";
6732
&Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,1,1,"all",($lastlinenumber+$NbOfLinesParsed),$lastlineoffset,&CheckSum($_));
6733
&GetDelaySinceStart(1); $NbOfLinesShowsteps=1;
6736
$counterforflushtest=0;
6739
} # End of loop for processing new record.
6742
debug(" _host_p:".(scalar keys %_host_p)." _host_h:".(scalar keys %_host_h)." _host_k:".(scalar keys %_host_k)." _host_l:".(scalar keys %_host_l)." _host_s:".(scalar keys %_host_s)." _host_u:".(scalar keys %_host_u)."\n",1);
6743
debug(" _url_p:".(scalar keys %_url_p)." _url_k:".(scalar keys %_url_k)." _url_e:".(scalar keys %_url_e)." _url_x:".(scalar keys %_url_x)."\n",1);
6744
debug(" _waithost_e:".(scalar keys %_waithost_e)." _waithost_l:".(scalar keys %_waithost_l)." _waithost_s:".(scalar keys %_waithost_s)." _waithost_u:".(scalar keys %_waithost_u)."\n",1);
6745
debug("End of processing log file (AWStats memory cache is TmpDNSLookup=".(scalar keys %TmpDNSLookup)." TmpBrowser=".(scalar keys %TmpBrowser)." TmpOS=".(scalar keys %TmpOS)." TmpRefererServer=".(scalar keys %TmpRefererServer)." TmpRobot=".(scalar keys %TmpRobot).")",1);
6748
# Save current processed month $lastprocessedmonth
6749
# If lastprocessedmonth > 0 means there is at least one approved new record in log or at least one existing history file
6750
if ($lastprocessedmonth) { # TODO: Do not save if we are sure a flush was just already done
6752
seek(LOG,$lastlineoffset,0);
6754
chomp $line; $line =~ s/\r$//;
6755
if (! $NbOfLinesParsed) {
6756
# TODO If there was no lines parsed (log was empty), we only update LastUpdate line with YYYYMMDDHHMMSS 0 0 0 0 0
6757
&Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,1,1,"all",($lastlinenumber+$NbOfLinesParsed),$lastlineoffset,&CheckSum($line));
6760
&Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,1,1,"all",($lastlinenumber+$NbOfLinesParsed),$lastlineoffset,&CheckSum($line));
6764
if ($Debug) { debug("Close log file \"$LogFile\""); }
6765
close LOG || error("Command for pipe '$LogFile' failed");
6767
# Process the Rename - Archive - Purge phase
6768
my $renameok=1; my $archiveok=1;
6770
# Open Log file for writing if PurgeLogFile is on
6771
if ($PurgeLogFile == 1) {
6772
if ($ArchiveLogRecords == 1) {
6773
$ArchiveFileName="$DirData/${PROG}_archive$FileSuffix.log";
6774
open(LOG,"+<$LogFile") || error("Enable to archive log records of \"$LogFile\" into \"$ArchiveFileName\" because source can't be opened for read and write: $!<br />\n");
6777
open(LOG,"+<$LogFile");
6782
# Rename all HISTORYTMP files into HISTORYTXT
6783
&Rename_All_Tmp_History;
6785
# Purge Log file if option is on and all renaming are ok
6786
if ($PurgeLogFile == 1) {
6787
# Archive LOG file into ARCHIVELOG
6788
if ($ArchiveLogRecords == 1) {
6789
if ($Debug) { debug("Start of archiving log file"); }
6790
open(ARCHIVELOG,">>$ArchiveFileName") || error("Couldn't open file \"$ArchiveFileName\" to archive log: $!");
6793
if (! print ARCHIVELOG $_) { $archiveok=0; last; }
6795
close(ARCHIVELOG) || error("Archiving failed during closing archive: $!");
6796
if ($SaveDatabaseFilesWithPermissionsForEveryone) { chmod 0666,"$ArchiveFileName"; }
6797
if ($Debug) { debug("End of archiving log file"); }
6799
# If rename and archive ok
6800
if ($renameok && $archiveok) {
6801
if ($Debug) { debug("Purge log file"); }
6802
my $bold=($ENV{'GATEWAY_INTERFACE'}?'<b>':'');
6803
my $unbold=($ENV{'GATEWAY_INTERFACE'}?'</b>':'');
6804
my $br=($ENV{'GATEWAY_INTERFACE'}?'<br />':'');
6805
truncate(LOG,0) || warning("Warning: $bold$PROG$unbold couldn't purge logfile \"$bold$LogFile$unbold\".$br\nChange your logfile permissions to allow write for your web server CGI process or change PurgeLogFile=1 into PurgeLogFile=0 in configure file and think to purge sometines manually your logfile (just after running an update process to not loose any not already processed records your log file contains).");
6810
if ($DNSLookup==1 && $DNSLookupAlreadyDone) {
6812
my $bold=($ENV{'GATEWAY_INTERFACE'}?'<b>':'');
6813
my $unbold=($ENV{'GATEWAY_INTERFACE'}?'</b>':'');
6814
my $br=($ENV{'GATEWAY_INTERFACE'}?'<br />':'');
6815
warning("Warning: $bold$PROG$unbold has detected that some hosts names were already resolved in your logfile $bold$DNSLookupAlreadyDone$unbold.$br\nIf DNS lookup was already made by the logger (web server), you should change your setup DNSLookup=$DNSLookup into DNSLookup=0 to increase $PROG speed.");
6817
if ($DNSLookup==1 && $NbOfNewLines) {
6818
# Save new DNS last update cache file
6819
Save_DNS_Cache_File(\%TmpDNSLookup,"$DirData/$DNSLastUpdateCacheFile","$FileSuffix"); # Save into file using FileSuffix
6822
if ($EnableLockForUpdate) {
6825
# Restore signals handler
6826
$SIG{INT} = 'DEFAULT'; # 2
6827
#$SIG{KILL} = 'DEFAULT'; # 9
6828
#$SIG{TERM} = 'DEFAULT'; # 15
6832
# End of log processing if ($UPdateStats)
6835
#---------------------------------------------------------------------
6837
#---------------------------------------------------------------------
6839
if (scalar keys %HTMLOutput) {
6841
my $max_p; my $max_h; my $max_k; my $max_v;
6842
my $total_u; my $total_v; my $total_p; my $total_h; my $total_k; my $total_e; my $total_x; my $total_s; my $total_l; my $total_r;
6843
my $average_u; my $average_v; my $average_p; my $average_h; my $average_k; my $average_s;
6844
my $rest_p; my $rest_h; my $rest_k; my $rest_e; my $rest_x; my $rest_s; my $rest_l; my $rest_r;
6847
# Define the NewLinkParams for main chart
6848
my $NewLinkParams=${QueryString};
6849
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
6850
$NewLinkParams =~ s/(^|&)output(=\w*|$)//i;
6851
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
6852
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
6853
my $NewLinkTarget='';
6854
if ($DetailedReportsOnNewWindows) { $NewLinkTarget=" target=\"awstatsbis\""; }
6855
if (($FrameName eq 'mainleft' || $FrameName eq 'mainright') && $DetailedReportsOnNewWindows < 2) {
6856
$NewLinkParams.="&framename=mainright";
6857
$NewLinkTarget=" target=\"mainright\"";
6859
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
6860
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
6862
if ($FrameName ne 'mainleft') {
6868
# Loop on each month of year
6869
for (my $ix=12; $ix>=1; $ix--) {
6870
my $monthix=sprintf("%02s",$ix);
6871
if ($MonthRequired eq 'all' || $monthix eq $MonthRequired) {
6872
&Read_History_With_TmpUpdate($YearRequired,$monthix,0,0,"all"); # Read full history file
6874
elsif (($HTMLOutput{'main'} && $ShowMonthStats) || $HTMLOutput{'alldays'}) {
6875
&Read_History_With_TmpUpdate($YearRequired,$monthix,0,0,"general time"); # Read general and time sections.
6881
if ($FrameName ne 'index' && $FrameName ne 'mainleft') {
6882
print "<a name=\"top\"> </a>\n\n";
6883
print "$HTMLHeadSection\n";
6887
# Call to plugins' function AddHTMLBodyHeader
6888
foreach my $pluginname (keys %{$PluginsLoaded{'AddHTMLBodyHeader'}}) {
6889
my $function="AddHTMLBodyHeader_$pluginname()";
6894
#---------------------------------------------------------------------
6895
if ($ShowMenu || $FrameName eq 'mainleft') {
6896
if ($Debug) { debug("ShowMenu",2); }
6897
my $frame=($FrameName eq 'mainleft');
6898
print "$Center<a name=\"menu\"> </a>\n";
6900
my $WIDTHMENU1=($FrameName eq 'mainleft'?$FRAMEWIDTH:150);
6902
if ($FrameName ne 'mainleft') {
6903
my $NewLinkParams=${QueryString};
6904
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
6905
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
6906
$NewLinkParams =~ s/(^|&)year=[^&]*//i;
6907
$NewLinkParams =~ s/(^|&)month=[^&]*//i;
6908
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
6909
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
6910
my $NewLinkTarget='';
6911
if ($FrameName eq 'mainright') { $NewLinkTarget=" target=\"_parent\""; }
6912
print "<form name=\"FormDateFilter\" action=\"".XMLEncode("$AWScript?${NewLinkParams}")."\" style=\"padding: 0px 0px 0px 0px; margin-top: 0\"$NewLinkTarget>\n";
6915
if ($QueryString !~ /buildpdf/i) {
6916
print "<table class=\"aws_border\" border=\"0\" cellpadding=\"2\" cellspacing=\"0\" width=\"100%\">\n";
6918
print "<table class=\"aws_data\" border=\"0\" cellpadding=\"1\" cellspacing=\"0\" width=\"100%\">\n";
6921
print "<table width=\"100%\">\n";
6924
if ($FrameName ne 'mainright') {
6925
# Print Statistics Of
6926
if ($FrameName eq 'mainleft') { print "<tr><td class=\"awsm\"><b>$Message[7]:</b></td></tr><tr><td class=\"aws\"><span style=\"font-size: 12px;\">$SiteDomain</span></td>"; }
6927
else { print "<tr><td class=\"aws\" valign=\"middle\"><b>$Message[7]:</b> </td><td class=\"aws\"><span style=\"font-size: 14px;\">$SiteDomain</span></td>"; }
6930
if ($FrameName ne 'mainleft') {
6931
if ($LogoLink =~ "http://awstats.sourceforge.net") {
6932
print "<td align=\"right\" rowspan=\"3\"><a href=\"".XMLEncode($LogoLink)."\" target=\"awstatshome\"><img src=\"$DirIcons/other/$Logo\" border=\"0\"".AltTitle(ucfirst($PROG)." Web Site")." /></a>";
6935
print "<td align=\"right\" rowspan=\"3\"><a href=\"".XMLEncode($LogoLink)."\" target=\"awstatshome\"><img src=\"$DirIcons/other/$Logo\" border=\"0\" /></a>";
6937
if (! $StaticLinks) { print "<br />"; Show_Flag_Links($Lang); }
6942
if ($FrameName ne 'mainleft') {
6944
print "<tr valign=\"middle\"><td class=\"aws\" valign=\"middle\" width=\"$WIDTHMENU1\"><b>$Message[35]:</b> </td>";
6945
print "<td class=\"aws\" valign=\"middle\"><span style=\"font-size: 12px;\">";
6946
if ($LastUpdate) { print Format_Date($LastUpdate,0); }
6948
# Here NbOfOldLines = 0 (because LastUpdate is not defined)
6949
if (! $UpdateStats) { print "<span style=\"color: #880000\">$Message[24]</span>"; }
6950
else { print "<span style=\"color: #880000\">No qualified records found in log ($NbOfLinesCorrupted corrupted, $NbOfLinesDropped dropped)</span>"; }
6954
# Print Update Now link
6955
if ($AllowToUpdateStatsFromBrowser && ! $StaticLinks) {
6956
my $NewLinkParams=${QueryString};
6957
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
6958
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
6959
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
6960
if ($FrameName eq 'mainright') { $NewLinkParams.="&framename=mainright"; }
6961
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
6962
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
6963
print " ";
6964
print "<a href=\"".XMLEncode("$AWScript?${NewLinkParams}update=1")."\">$Message[74]</a>";
6969
if ($FrameName eq 'mainright') {
6970
if ($LogoLink =~ "http://awstats.sourceforge.net") {
6971
print "<td align=\"right\" rowspan=\"2\"><a href=\"".XMLEncode($LogoLink)."\" target=\"awstatshome\"><img src=\"$DirIcons/other/$Logo\" border=\"0\"".AltTitle(ucfirst($PROG)." Web Site")." /></a>\n";
6974
print "<td align=\"right\" rowspan=\"2\"><a href=\"".XMLEncode($LogoLink)."\" target=\"awstatshome\"><img src=\"$DirIcons/other/$Logo\" border=\"0\" /></a>\n";
6976
if (! $StaticLinks) { print "<br />"; Show_Flag_Links($Lang); }
6981
# Print selected period of analysis (month and year required)
6982
print "<tr><td class=\"aws\" valign=\"middle\"><b>$Message[133]:</b></td>";
6983
print "<td class=\"aws\" valign=\"middle\">";
6984
if ($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) {
6985
print "<select class=\"aws_formfield\" name=\"month\">\n";
6986
foreach (1..12) { my $monthix=sprintf("%02s",$_); print "<option".($MonthRequired eq "$monthix"?" selected=\"true\"":"")." value=\"$monthix\">$MonthNumLib{$monthix}</option>\n"; }
6987
if ($AllowFullYearView >= 2) {
6988
print "<option".($MonthRequired eq 'all'?" selected=\"true\"":"")." value='all'>- $Message[6] -</option>\n";
6990
print "</select>\n";
6991
print "<select class=\"aws_formfield\" name=\"year\">\n";
6992
# Add YearRequired in list if not in ListOfYears
6993
$ListOfYears{$YearRequired}||=$MonthRequired;
6994
foreach (sort keys %ListOfYears) { print "<option".($YearRequired eq "$_"?" selected=\"true\"":"")." value=\"$_\">$_</option>\n"; }
6995
print "</select>\n";
6996
print "<input type=\"hidden\" name=\"output\" value=\"".join(',',keys %HTMLOutput)."\" />\n";
6997
if ($SiteConfig) { print "<input type=\"hidden\" name=\"config\" value=\"$SiteConfig\" />\n"; }
6998
if ($DirConfig) { print "<input type=\"hidden\" name=\"configdir\" value=\"$DirConfig\" />\n"; }
6999
if ($QueryString =~ /lang=(\w+)/i) { print "<input type=\"hidden\" name=\"lang\" value=\"$1\" />\n"; }
7000
if ($QueryString =~ /debug=(\d+)/i) { print "<input type=\"hidden\" name=\"debug\" value=\"$1\" />\n"; }
7001
if ($FrameName eq 'mainright') { print "<input type=\"hidden\" name=\"framename\" value=\"index\" />\n"; }
7002
print "<input type=\"submit\" value=\" $Message[115] \" class=\"aws_button\" />";
7005
print "<span style=\"font-size: 14px;\">";
7006
if ($MonthRequired eq 'all') { print "$Message[6] $YearRequired"; }
7007
else { print "$Message[5] $MonthNumLib{$MonthRequired} $YearRequired"; }
7010
print "</td></tr>\n";
7012
if ($QueryString !~ /buidpdf/i) {
7014
print "</td></tr></table>\n";
7020
if ($FrameName ne 'mainleft') { print "</form>\n"; }
7021
else { print "<br />\n"; }
7025
if (($HTMLOutput{'main'} && $FrameName ne 'mainright') || $FrameName eq 'mainleft') { # If main page asked
7026
# Define link anchor
7027
my $linkanchor=($FrameName eq 'mainleft'?"$AWScript?${NewLinkParams}":"");
7028
if ($linkanchor && ($linkanchor !~ /framename=mainright/)) { $linkanchor.="framename=mainright"; }
7029
$linkanchor =~ s/&$//; $linkanchor=XMLEncode("$linkanchor");
7031
my $targetpage=($FrameName eq 'mainleft'?" target=\"mainright\"":"");
7034
if (! $PluginsLoaded{'ShowMenu'}{'menuapplet'}) {
7037
print "<table".($frame?" cellspacing=\"0\" cellpadding=\"0\" border=\"0\"":"").">\n";
7038
if ($FrameName eq 'mainleft' && $ShowMonthStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#TOP\"$targetpage>$Message[128]</a>"; print ($frame?"</td></tr>\n":" "); }
7040
$linetitle=&AtLeastOneNotNull($ShowMonthStats,$ShowDaysOfMonthStats,$ShowDaysOfWeekStats,$ShowHoursStats);
7041
if ($linetitle) { print "<tr><td class=\"awsm\" width=\"$WIDTHMENU1\"".($frame?"":" valign=\"top\"").">".($menuicon?"<img src=\"$DirIcons/other/menu4.png\" /> ":"")."<b>$Message[93]:</b></td>\n"; }
7042
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7043
if ($ShowMonthStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#month\"$targetpage>$Message[162]</a>"; print ($frame?"</td></tr>\n":" "); }
7044
#if ($ShowMonthDayStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=alldays"):"$PROG$StaticLinks.alldays.$StaticExt")."\"$NewLinkTarget>$Message[130]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7045
if ($ShowDaysOfMonthStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#daysofmonth\"$targetpage>$Message[138]</a>"; print ($frame?"</td></tr>\n":" "); }
7046
if ($ShowDaysOfWeekStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#daysofweek\"$targetpage>$Message[91]</a>"; print ($frame?"</td></tr>\n":" "); }
7047
if ($ShowHoursStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#hours\"$targetpage>$Message[20]</a>"; print ($frame?"</td></tr>\n":" "); }
7048
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7050
$linetitle=&AtLeastOneNotNull($ShowDomainsStats,$ShowHostsStats,$ShowAuthenticatedUsers,$ShowEMailSenders,$ShowEMailReceivers,$ShowRobotsStats,$ShowWormsStats);
7051
if ($linetitle) { print "<tr><td class=\"awsm\"".($frame?"":" valign=\"top\"").">".($menuicon?"<img src=\"$DirIcons/other/menu5.png\" /> ":"")."<b>$Message[92]:</b></td>\n"; }
7052
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7053
if ($ShowDomainsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#countries\"$targetpage>$Message[148]</a>"; print ($frame?"</td></tr>\n":" "); }
7054
if ($ShowDomainsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=alldomains"):"$PROG$StaticLinks.alldomains.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7055
if ($ShowHostsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#visitors\"$targetpage>".ucfirst($Message[81])."</a>"; print ($frame?"</td></tr>\n":" "); }
7056
if ($ShowHostsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allhosts"):"$PROG$StaticLinks.allhosts.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7057
if ($ShowHostsStats =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lasthosts"):"$PROG$StaticLinks.lasthosts.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7058
if ($ShowHostsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownip"):"$PROG$StaticLinks.unknownip.$StaticExt")."\"$NewLinkTarget>$Message[45]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7059
if ($ShowAuthenticatedUsers) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#logins\"$targetpage>$Message[94]</a>"; print ($frame?"</td></tr>\n":" "); }
7060
if ($ShowAuthenticatedUsers) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=alllogins"):"$PROG$StaticLinks.alllogins.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7061
if ($ShowAuthenticatedUsers =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastlogins"):"$PROG$StaticLinks.lastlogins.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7062
if ($ShowEMailSenders) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#emailsenders\"$targetpage>$Message[131]</a>"; print ($frame?"</td></tr>\n":" "); }
7063
if ($ShowEMailSenders) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allemails"):"$PROG$StaticLinks.allemails.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7064
if ($ShowEMailSenders =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastemails"):"$PROG$StaticLinks.lastemails.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7065
if ($ShowEMailReceivers) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#emailreceivers\"$targetpage>$Message[132]</a>"; print ($frame?"</td></tr>\n":" "); }
7066
if ($ShowEMailReceivers) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allemailr"):"$PROG$StaticLinks.allemailr.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7067
if ($ShowEMailReceivers =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastemailr"):"$PROG$StaticLinks.lastemailr.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7068
if ($ShowRobotsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#robots\"$targetpage>$Message[53]</a>"; print ($frame?"</td></tr>\n":" "); }
7069
if ($ShowRobotsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allrobots"):"$PROG$StaticLinks.allrobots.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7070
if ($ShowRobotsStats =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastrobots"):"$PROG$StaticLinks.lastrobots.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7071
if ($ShowWormsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#worms\"$targetpage>$Message[136]</a>"; print ($frame?"</td></tr>\n":" "); }
7072
#if ($ShowWormsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allworms"):"$PROG$StaticLinks.allworms.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7073
#if ($ShowWormsStats =~ /L/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastworms"):"$PROG$StaticLinks.lastworms.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7074
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7076
$linetitle=&AtLeastOneNotNull($ShowSessionsStats,$ShowPagesStats,$ShowFileTypesStats,$ShowFileSizesStats,$ShowOSStats,$ShowBrowsersStats,$ShowScreenSizeStats);
7077
if ($linetitle) { print "<tr><td class=\"awsm\"".($frame?"":" valign=\"top\"").">".($menuicon?"<img src=\"$DirIcons/other/menu2.png\" /> ":"")."<b>$Message[72]:</b></td>\n"; }
7078
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7079
if ($ShowSessionsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#sessions\"$targetpage>$Message[117]</a>"; print ($frame?"</td></tr>\n":" "); }
7080
if ($ShowFileTypesStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#filetypes\"$targetpage>$Message[73]</a>"; print ($frame?"</td></tr>\n":" "); }
7081
if ($ShowPagesStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#urls\"$targetpage>$Message[29]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7082
if ($ShowPagesStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urldetail"):"$PROG$StaticLinks.urldetail.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7083
if ($ShowPagesStats =~ /E/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urlentry"):"$PROG$StaticLinks.urlentry.$StaticExt")."\"$NewLinkTarget>$Message[104]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7084
if ($ShowPagesStats =~ /X/i) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urlexit"):"$PROG$StaticLinks.urlexit.$StaticExt")."\"$NewLinkTarget>$Message[116]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7085
if ($ShowOSStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#os\"$targetpage>$Message[59]</a>"; print ($frame?"</td></tr>\n":" "); }
7086
if ($ShowOSStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=osdetail"):"$PROG$StaticLinks.osdetail.$StaticExt")."\"$NewLinkTarget>$Message[58]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7087
if ($ShowOSStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownos"):"$PROG$StaticLinks.unknownos.$StaticExt")."\"$NewLinkTarget>$Message[0]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7088
if ($ShowBrowsersStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#browsers\"$targetpage>$Message[21]</a>"; print ($frame?"</td></tr>\n":" "); }
7089
if ($ShowBrowsersStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=browserdetail"):"$PROG$StaticLinks.browserdetail.$StaticExt")."\"$NewLinkTarget>$Message[58]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7090
if ($ShowBrowsersStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownbrowser"):"$PROG$StaticLinks.unknownbrowser.$StaticExt")."\"$NewLinkTarget>$Message[0]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7091
if ($ShowScreenSizeStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#screensizes\"$targetpage>$Message[135]</a>"; print ($frame?"</td></tr>\n":" "); }
7092
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7094
$linetitle=&AtLeastOneNotNull($ShowOriginStats,$ShowKeyphrasesStats,$ShowKeywordsStats);
7095
if ($linetitle) { print "<tr><td class=\"awsm\"".($frame?"":" valign=\"top\"").">".($menuicon?"<img src=\"$DirIcons/other/menu7.png\" /> ":"")."<b>$Message[23]:</b></td>\n"; }
7096
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7097
if ($ShowOriginStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#referer\"$targetpage>$Message[37]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7098
if ($ShowOriginStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=refererse"):"$PROG$StaticLinks.refererse.$StaticExt")."\"$NewLinkTarget>$Message[126]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7099
if ($ShowOriginStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=refererpages"):"$PROG$StaticLinks.refererpages.$StaticExt")."\"$NewLinkTarget>$Message[127]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7100
if ($ShowKeyphrasesStats || $ShowKeywordsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#keys\"$targetpage>$Message[14]</a>"; print ($frame?"</td></tr>\n":" "); }
7101
if ($ShowKeyphrasesStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=keyphrases"):"$PROG$StaticLinks.keyphrases.$StaticExt")."\"$NewLinkTarget>$Message[120]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7102
if ($ShowKeywordsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=keywords"):"$PROG$StaticLinks.keywords.$StaticExt")."\"$NewLinkTarget>$Message[121]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7103
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7105
$linetitle=&AtLeastOneNotNull($ShowFileTypesStats=~/C/i,$ShowMiscStats,$ShowHTTPErrorsStats,$ShowSMTPErrorsStats,$ShowClusterStats);
7106
if ($linetitle) { print "<tr><td class=\"awsm\"".($frame?"":" valign=\"top\"").">".($menuicon?"<img src=\"$DirIcons/other/menu8.png\" /> ":"")."<b>$Message[2]:</b></td>\n"; }
7107
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7108
if ($ShowFileTypesStats =~ /C/i) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#filetypes\"$targetpage>$Message[98]</a>"; print ($frame?"</td></tr>\n":" "); }
7109
if ($ShowMiscStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#misc\"$targetpage>$Message[139]</a>"; print ($frame?"</td></tr>\n":" "); }
7110
if ($ShowHTTPErrorsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#errors\"$targetpage>$Message[32]</a>"; print ($frame?"</td></tr>\n":" "); }
7111
foreach (keys %TrapInfosForHTTPErrorCodes) {
7112
if ($ShowHTTPErrorsStats) { print ($frame?"<tr><td class=\"awsm\"> <img height=\"8\" width=\"9\" src=\"$DirIcons/other/page.png\" alt=\"...\" /> ":""); print "<a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=errors$_"):"$PROG$StaticLinks.errors$_.$StaticExt")."\"$NewLinkTarget>$Message[31]</a>\n"; print ($frame?"</td></tr>\n":" "); }
7114
if ($ShowSMTPErrorsStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#errors\"$targetpage>$Message[147]</a>"; print ($frame?"</td></tr>\n":" "); }
7115
if ($ShowClusterStats) { print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#clusters\"$targetpage>$Message[155]</a>"; print ($frame?"</td></tr>\n":" "); }
7116
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7118
$linetitle=&AtLeastOneNotNull(@ExtraStatTypes);
7119
if ($linetitle) { print "<tr><td class=\"awsm\"".($frame?"":" valign=\"top\"")."><b>$Message[134]:</b></td>\n"; }
7120
if ($linetitle) { print ($frame?"</tr>\n":"<td class=\"awsm\">"); }
7121
foreach (1..@ExtraName-1) {
7122
print ($frame?"<tr><td class=\"awsm\">":""); print "<a href=\"$linkanchor#extra$_\"$targetpage>$ExtraName[$_]</a>\n"; print ($frame?"</td></tr>\n":" ");
7124
if ($linetitle) { print ($frame?"":"</td></tr>\n"); }
7132
#print ($frame?"":"<br />\n");
7136
elsif (! $HTMLOutput{'main'}) {
7138
$NewLinkParams =~ s/(^|&)hostfilter=[^&]*//i;
7139
$NewLinkParams =~ s/(^|&)urlfilter=[^&]*//i;
7140
$NewLinkParams =~ s/(^|&)refererpagesfilter=[^&]*//i;
7141
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/&$//;
7142
if (! $DetailedReportsOnNewWindows || $FrameName eq 'mainright' || $QueryString =~ /buildpdf/i) {
7143
print "<tr><td class=\"aws\"><a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript".(${NewLinkParams}?"?${NewLinkParams}":"")):"$PROG$StaticLinks.$StaticExt")."\">$Message[76]</a></td></tr>\n";
7146
print "<tr><td class=\"aws\"><a href=\"javascript:parent.window.close();\">$Message[118]</a></td></tr>\n";
7153
# Call to plugins' function AddHTMLMenuFooter
7154
foreach my $pluginname (keys %{$PluginsLoaded{'AddHTMLMenuFooter'}}) {
7155
my $function="AddHTMLMenuFooter_$pluginname()";
7159
# Exit if left frame
7160
if ($FrameName eq 'mainleft') {
7165
# FirstTime LastTime TotalVisits TotalUnique TotalPages TotalHits TotalBytes TotalHostsKnown TotalHostsUnknown
7168
$TotalUnique=$TotalVisits=$TotalPages=$TotalHits=$TotalBytes=0;
7169
$TotalNotViewedPages=$TotalNotViewedHits=$TotalNotViewedBytes=0;
7170
$TotalHostsKnown=$TotalHostsUnknown=0;
7171
my $beginmonth=$MonthRequired;my $endmonth=$MonthRequired;
7172
if ($MonthRequired eq 'all') { $beginmonth=1;$endmonth=12; }
7173
for (my $month=$beginmonth; $month<=$endmonth; $month++) {
7174
my $monthix=sprintf("%02s",$month);
7175
if ($FirstTime{$YearRequired.$monthix} && ($FirstTime == 0 || $FirstTime > $FirstTime{$YearRequired.$monthix})) { $FirstTime = $FirstTime{$YearRequired.$monthix}; }
7176
if ($LastTime < ($LastTime{$YearRequired.$monthix}||0)) { $LastTime = $LastTime{$YearRequired.$monthix}; }
7177
$TotalHostsKnown+=$MonthHostsKnown{$YearRequired.$monthix}||0; # Wrong in year view
7178
$TotalHostsUnknown+=$MonthHostsUnknown{$YearRequired.$monthix}||0; # Wrong in year view
7179
$TotalUnique+=$MonthUnique{$YearRequired.$monthix}||0; # Wrong in year view
7180
$TotalVisits+=$MonthVisits{$YearRequired.$monthix}||0;
7181
$TotalPages+=$MonthPages{$YearRequired.$monthix}||0;
7182
$TotalHits+=$MonthHits{$YearRequired.$monthix}||0;
7183
$TotalBytes+=$MonthBytes{$YearRequired.$monthix}||0;
7184
$TotalNotViewedPages+=$MonthNotViewedPages{$YearRequired.$monthix}||0;
7185
$TotalNotViewedHits+=$MonthNotViewedHits{$YearRequired.$monthix}||0;
7186
$TotalNotViewedBytes+=$MonthNotViewedBytes{$YearRequired.$monthix}||0;
7188
# TotalHitsErrors TotalBytesErrors
7189
my $TotalHitsErrors=0; my $TotalBytesErrors=0;
7190
foreach (keys %_errors_h) { $TotalHitsErrors+=$_errors_h{$_}; $TotalBytesErrors+=$_errors_k{$_}; }
7191
# TotalEntries (if not already specifically counted, we init it from _url_e hash table)
7192
if (!$TotalEntries) { foreach (keys %_url_e) { $TotalEntries+=$_url_e{$_}; } }
7193
# TotalExits (if not already specifically counted, we init it from _url_x hash table)
7194
if (!$TotalExits) { foreach (keys %_url_x) { $TotalExits+=$_url_x{$_}; } }
7195
# TotalBytesPages (if not already specifically counted, we init it from _url_k hash table)
7196
if (!$TotalBytesPages) { foreach (keys %_url_k) { $TotalBytesPages+=$_url_k{$_}; } }
7197
# TotalKeyphrases (if not already specifically counted, we init it from _keyphrases hash table)
7198
if (!$TotalKeyphrases) { foreach (keys %_keyphrases) { $TotalKeyphrases+=$_keyphrases{$_}; } }
7199
# TotalKeywords (if not already specifically counted, we init it from _keywords hash table)
7200
if (!$TotalKeywords) { foreach (keys %_keywords) { $TotalKeywords+=$_keywords{$_}; } }
7201
# TotalSearchEnginesPages (if not already specifically counted, we init it from _se_referrals_p hash table)
7202
if (!$TotalSearchEnginesPages) { foreach (keys %_se_referrals_p) { $TotalSearchEnginesPages+=$_se_referrals_p{$_}; } }
7203
# TotalSearchEnginesHits (if not already specifically counted, we init it from _se_referrals_h hash table)
7204
if (!$TotalSearchEnginesHits) { foreach (keys %_se_referrals_h) { $TotalSearchEnginesHits+=$_se_referrals_h{$_}; } }
7205
# TotalRefererPages (if not already specifically counted, we init it from _pagesrefs_p hash table)
7206
if (!$TotalRefererPages) { foreach (keys %_pagesrefs_p) { $TotalRefererPages+=$_pagesrefs_p{$_}; } }
7207
# TotalRefererHits (if not already specifically counted, we init it from _pagesrefs_h hash table)
7208
if (!$TotalRefererHits) { foreach (keys %_pagesrefs_h) { $TotalRefererHits+=$_pagesrefs_h{$_}; } }
7209
# TotalDifferentPages (if not already specifically counted, we init it from _url_p hash table)
7210
$TotalDifferentPages||=scalar keys %_url_p;
7211
# TotalDifferentKeyphrases (if not already specifically counted, we init it from _keyphrases hash table)
7212
$TotalDifferentKeyphrases||=scalar keys %_keyphrases;
7213
# TotalDifferentKeywords (if not already specifically counted, we init it from _keywords hash table)
7214
$TotalDifferentKeywords||=scalar keys %_keywords;
7215
# TotalDifferentSearchEngines (if not already specifically counted, we init it from _se_referrals_h hash table)
7216
$TotalDifferentSearchEngines||=scalar keys %_se_referrals_h;
7217
# TotalDifferentReferer (if not already specifically counted, we init it from _pagesrefs_h hash table)
7218
$TotalDifferentReferer||=scalar keys %_pagesrefs_h;
7220
# Define firstdaytocountaverage, lastdaytocountaverage, firstdaytoshowtime, lastdaytoshowtime
7221
my $firstdaytocountaverage=$nowyear.$nowmonth."01"; # Set day cursor to 1st day of month
7222
my $firstdaytoshowtime=$nowyear.$nowmonth."01"; # Set day cursor to 1st day of month
7223
my $lastdaytocountaverage=$nowyear.$nowmonth.$nowday; # Set day cursor to today
7224
my $lastdaytoshowtime=$nowyear.$nowmonth."31"; # Set day cursor to last day of month
7225
if ($MonthRequired eq 'all') {
7226
$firstdaytocountaverage=$YearRequired."0101"; # Set day cursor to 1st day of the required year
7228
if (($MonthRequired ne $nowmonth && $MonthRequired ne 'all') || $YearRequired ne $nowyear) {
7229
if ($MonthRequired eq 'all') {
7230
$firstdaytocountaverage=$YearRequired."0101"; # Set day cursor to 1st day of the required year
7231
$firstdaytoshowtime=$YearRequired."1201"; # Set day cursor to 1st day of last month of required year
7232
$lastdaytocountaverage=$YearRequired."1231"; # Set day cursor to last day of the required year
7233
$lastdaytoshowtime=$YearRequired."1231"; # Set day cursor to last day of last month of required year
7236
$firstdaytocountaverage=$YearRequired.$MonthRequired."01"; # Set day cursor to 1st day of the required month
7237
$firstdaytoshowtime=$YearRequired.$MonthRequired."01"; # Set day cursor to 1st day of the required month
7238
$lastdaytocountaverage=$YearRequired.$MonthRequired."31"; # Set day cursor to last day of the required month
7239
$lastdaytoshowtime=$YearRequired.$MonthRequired."31"; # Set day cursor to last day of the required month
7243
debug("firstdaytocountaverage=$firstdaytocountaverage, lastdaytocountaverage=$lastdaytocountaverage",1);
7244
debug("firstdaytoshowtime=$firstdaytoshowtime, lastdaytoshowtime=$lastdaytoshowtime",1);
7247
# Output particular part
7249
# if ($HTMLOutput{'alldays'}) {
7250
# if ($Debug) { debug("ShowMonthDayStats",2); }
7251
# print "$Center<a name=\"monthday\"> </a><br />\n";
7252
# &tab_head("$Message[5]",0,0,"alldays");
7254
# my $NewLinkParams=${QueryString};
7255
# $NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
7256
# $NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
7257
# $NewLinkParams =~ s/(^|&)year=[^&]*//i;
7258
# $NewLinkParams =~ s/(^|&)month=[^&]*//i;
7259
# $NewLinkParams =~ s/(^|&)framename=[^&]*//i;
7260
# $NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
7261
# if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
7262
# my $NewLinkTarget="";
7263
# if ($FrameName eq 'mainright') { $NewLinkTarget=" target=\"_parent\""; }
7265
# # Show monthly stats
7266
# print "<tr valign=\"bottom\"><td align=\"center\">";
7270
# print "<tr valign=\"bottom\"><td></td>";
7271
# $max_v=$max_p=$max_h=$max_k=1;
7272
# for (my $ix=1; $ix<=12; $ix++) {
7273
# my $monthix=sprintf("%02s",$ix);
7274
# #if ($MonthUnique{$YearRequired.$monthix} > $max_v) { $max_v=$MonthUnique{$YearRequired.$monthix}; }
7275
# if ($MonthVisits{$YearRequired.$monthix} > $max_v) { $max_v=$MonthVisits{$YearRequired.$monthix}; }
7276
# #if ($MonthPages{$YearRequired.$monthix} > $max_p) { $max_p=$MonthPages{$YearRequired.$monthix}; }
7277
# if ($MonthHits{$YearRequired.$monthix} > $max_h) { $max_h=$MonthHits{$YearRequired.$monthix}; }
7278
# if ($MonthBytes{$YearRequired.$monthix} > $max_k) { $max_k=$MonthBytes{$YearRequired.$monthix}; }
7280
# for (my $ix=1; $ix<=12; $ix++) {
7281
# my $monthix=sprintf("%02s",$ix);
7282
# my $bredde_u=0; my $bredde_v=0;my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
7283
# if ($max_v > 0) { $bredde_u=int($MonthUnique{$YearRequired.$monthix}/$max_v*$BarHeight)+1; }
7284
# if ($max_v > 0) { $bredde_v=int($MonthVisits{$YearRequired.$monthix}/$max_v*$BarHeight)+1; }
7285
# if ($max_h > 0) { $bredde_p=int($MonthPages{$YearRequired.$monthix}/$max_h*$BarHeight)+1; }
7286
# if ($max_h > 0) { $bredde_h=int($MonthHits{$YearRequired.$monthix}/$max_h*$BarHeight)+1; }
7287
# if ($max_k > 0) { $bredde_k=int($MonthBytes{$YearRequired.$monthix}/$max_k*$BarHeight)+1; }
7289
# if ($ShowMonthDayStats =~ /U/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vu'}\" height=\"$bredde_u\" width=\"8\"".AltTitle("$Message[11]: $MonthUnique{$YearRequired.$monthix}")." />"; }
7290
# if ($ShowMonthDayStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"8\"".AltTitle("$Message[10]: $MonthVisits{$YearRequired.$monthix}")." />"; }
7292
# if ($ShowMonthDayStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"8\"".AltTitle("$Message[56]: $MonthPages{$YearRequired.$monthix}")." />"; }
7293
# if ($ShowMonthDayStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"8\"".AltTitle("$Message[57]: $MonthHits{$YearRequired.$monthix}")." />"; }
7294
# if ($ShowMonthDayStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"8\"".AltTitle("$Message[75]: ".Format_Bytes($MonthBytes{$YearRequired.$monthix}))." />"; }
7298
# # Show lib for month
7299
# print "<tr valign=\"middle\" cellspacing=\"0\" cellpadding=\"0\"><td></td>";
7300
# for (my $ix=1; $ix<=12; $ix++) {
7301
# my $monthix=($ix<10?"0$ix":"$ix");
7303
# if (($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) && ! $HTMLOutput{'alldays'}) { print "<a href=\"".XMLEncode($AWScript?${NewLinkParams}year=$YearRequired&month=$monthix)."\"$NewLinkTarget>"; }
7304
# print "$MonthNumLib{$monthix}";
7305
# if (($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) && ! $HTMLOutput{'alldays'}) { print "</a>"; }
7309
# print "</table>\n<br />\n";
7311
# # Show data array for month
7312
# print "<table>\n";
7313
# print "<tr><td width=\"15%\" bgcolor=\"#$color_TableBGRowTitle\">$Message[5]</td>";
7314
# if ($ShowMonthDayStats =~ /U/i) { print "<td width=\"17%\" bgcolor=\"#$color_u\" onmouseover=\"ShowTip(2);\" onmouseout=\"HideTip(2);\">$Message[11]</td>"; }
7315
# if ($ShowMonthDayStats =~ /V/i) { print "<td width=\"17%\" bgcolor=\"#$color_v\" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\">$Message[10]</td>"; }
7316
# if ($ShowMonthDayStats =~ /P/i) { print "<td width=\"17%\" bgcolor=\"#$color_p\" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\">$Message[56]</td>"; }
7317
# if ($ShowMonthDayStats =~ /H/i) { print "<td width=\"17%\" bgcolor=\"#$color_h\" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\">$Message[57]</td>"; }
7318
# if ($ShowMonthDayStats =~ /B/i) { print "<td width=\"17%\" bgcolor=\"#$color_k\" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\">$Message[75]</td>"; }
7320
# for (my $ix=1; $ix<=12; $ix++) {
7321
# my $monthix=($ix<10?"0$ix":"$ix");
7323
# print "<td>",$MonthNumLib{$monthix},"</td>";
7324
# if ($ShowMonthDayStats =~ /U/i) { print "<td>",$MonthUnique{$YearRequired.$monthix}?$MonthUnique{$YearRequired.$monthix}:"0","</td>"; }
7325
# if ($ShowMonthDayStats =~ /V/i) { print "<td>",$MonthVisits{$YearRequired.$monthix}?$MonthVisits{$YearRequired.$monthix}:"0","</td>"; }
7326
# if ($ShowMonthDayStats =~ /P/i) { print "<td>",$MonthPages{$YearRequired.$monthix}?$MonthPages{$YearRequired.$monthix}:"0","</td>"; }
7327
# if ($ShowMonthDayStats =~ /H/i) { print "<td>",$MonthHits{$YearRequired.$monthix}?$MonthHits{$YearRequired.$monthix}:"0","</td>"; }
7328
# if ($ShowMonthDayStats =~ /B/i) { print "<td>",Format_Bytes(int($MonthBytes{$YearRequired.$monthix})),"</td>"; }
7331
# print "</table>\n<br />";
7333
# print "</center>\n";
7334
# print "</td></tr>\n";
7339
# &tab_head("$Message[4]",0,0,"");
7340
# print "<tr valign=\"bottom\"><td align=\"center\">";
7344
# print "<tr valign=\"bottom\"><td></td>";
7345
# # Get max_v, max_h and max_k values
7346
# $max_v=$max_h=$max_k=0; # Start from 0 because can be lower than 1
7347
# foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
7348
# $daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
7349
# my $year=$1; my $month=$2; my $day=$3;
7350
# if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
7351
# if (($DayVisits{$year.$month.$day}||0) > $max_v) { $max_v=$DayVisits{$year.$month.$day}; }
7352
# #if (($DayPages{$year.$month.$day}||0) > $max_p) { $max_p=$DayPages{$year.$month.$day}; }
7353
# if (($DayHits{$year.$month.$day}||0) > $max_h) { $max_h=$DayHits{$year.$month.$day}; }
7354
# if (($DayBytes{$year.$month.$day}||0) > $max_k) { $max_k=$DayBytes{$year.$month.$day}; }
7356
# # Calculate average values
7357
# my $average_nb=0; my $average_v=0; my $average_p=0; my $average_h=0; my $average_k=0;
7358
# foreach my $daycursor ($firstdaytocountaverage..$lastdaytocountaverage) {
7359
# $daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
7360
# my $year=$1; my $month=$2; my $day=$3;
7361
# if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
7362
# $average_nb++; # Increase number of day used to count
7363
# $average_v+=($DayVisits{$daycursor}||0);
7364
# $average_p+=($DayPages{$daycursor}||0);
7365
# $average_h+=($DayHits{$daycursor}||0);
7366
# $average_k+=($DayBytes{$daycursor}||0);
7368
# if ($average_nb) {
7369
# $average_v=$average_v/$average_nb;
7370
# $average_p=$average_p/$average_nb;
7371
# $average_h=$average_h/$average_nb;
7372
# $average_k=$average_k/$average_nb;
7373
# if ($average_v > $max_v) { $max_v=$average_v; }
7374
# #if ($average_p > $max_p) { $max_p=$average_p; }
7375
# if ($average_h > $max_h) { $max_h=$average_h; }
7376
# if ($average_k > $max_k) { $max_k=$average_k; }
7384
# foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
7385
# $daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
7386
# my $year=$1; my $month=$2; my $day=$3;
7387
# if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
7388
# my $bredde_v=0; my $bredde_p=0; my $bredde_h=0; my $bredde_k=0;
7389
# if ($max_v > 0) { $bredde_v=int(($DayVisits{$year.$month.$day}||0)/$max_v*$BarHeight)+1; }
7390
# if ($max_h > 0) { $bredde_p=int(($DayPages{$year.$month.$day}||0)/$max_h*$BarHeight)+1; }
7391
# if ($max_h > 0) { $bredde_h=int(($DayHits{$year.$month.$day}||0)/$max_h*$BarHeight)+1; }
7392
# if ($max_k > 0) { $bredde_k=int(($DayBytes{$year.$month.$day}||0)/$max_k*$BarHeight)+1; }
7394
# if ($ShowMonthDayStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"4\"".AltTitle("$Message[10]: ".int($DayVisits{$year.$month.$day}||0))." />"; }
7395
# if ($ShowMonthDayStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"4\"".AltTitle("$Message[56]: ".int($DayPages{$year.$month.$day}||0))." />"; }
7396
# if ($ShowMonthDayStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"4\"".AltTitle("$Message[57]: ".int($DayHits{$year.$month.$day}||0))." />"; }
7397
# if ($ShowMonthDayStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"4\"".AltTitle("$Message[75]: ".Format_Bytes($DayBytes{$year.$month.$day}))." />"; }
7400
# print "<td> </td>";
7401
# print "<td>"; # Show average value cell
7402
# my $bredde_v=0; my $bredde_p=0; my $bredde_h=0; my $bredde_k=0;
7403
# if ($max_v > 0) { $bredde_v=int($average_v/$max_v*$BarHeight)+1; }
7404
# if ($max_h > 0) { $bredde_p=int($average_p/$max_h*$BarHeight)+1; }
7405
# if ($max_h > 0) { $bredde_h=int($average_h/$max_h*$BarHeight)+1; }
7406
# if ($max_k > 0) { $bredde_k=int($average_k/$max_k*$BarHeight)+1; }
7407
# $average_v=sprintf("%.2f",$average_v);
7408
# $average_p=sprintf("%.2f",$average_p);
7409
# $average_h=sprintf("%.2f",$average_h);
7410
# $average_k=sprintf("%.2f",$average_k);
7411
# if ($ShowMonthDayStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"4\"".AltTitle("$Message[10]: $average_v")." />"; }
7412
# if ($ShowMonthDayStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"4\"".AltTitle("$Message[56]: $average_p")." />"; }
7413
# if ($ShowMonthDayStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"4\"".AltTitle("$Message[57]: $average_h")." />"; }
7414
# if ($ShowMonthDayStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"4\"".AltTitle("$Message[75]: ".Format_Bytes($average_k))." />"; }
7416
# print "<td></td>\n";
7418
# # Show lib for days
7419
# print "<tr><td></td>";
7420
# foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
7421
# $daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
7422
# my $year=$1; my $month=$2; my $day=$3;
7423
# if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
7424
# my $dayofweekcursor=DayOfWeek($day,$month,$year);
7425
# print "<td valign=\"middle\"".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">";
7426
# print ($day==$nowday && $month==$nowmonth && $year==$nowyear?'<b>':'');
7427
# print "$day<br /><span style=\"font-size: ".($FrameName ne 'mainright'?"10":"9")."px;\">".$MonthNumLib{$month}."</span>";
7428
# print ($day==$nowday && $month==$nowmonth && $year==$nowyear?'</b>':'');
7431
# print "<td> </td>";
7432
# print "<td valign=\"middle\"".($TOOLTIPON?" onmouseover=\"ShowTip(18);\" onmouseout=\"HideTip(18);\"":"").">$Message[96]</td>\n";
7433
# print "<td></td>\n";
7435
# print "</table>\n<br />\n";
7437
# # Show data array for days
7438
# print "<table>\n";
7439
# print "<tr><td width=\"20%\" bgcolor=\"#$color_TableBGRowTitle\">$Message[4]</td>";
7440
# if ($ShowMonthDayStats =~ /V/i) { print "<td width=\"20%\" bgcolor=\"#$color_v\"".($TOOLTIPON?" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\"":"").">$Message[10]</td>"; }
7441
# if ($ShowMonthDayStats =~ /P/i) { print "<td width=\"20%\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
7442
# if ($ShowMonthDayStats =~ /H/i) { print "<td width=\"20%\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
7443
# if ($ShowMonthDayStats =~ /B/i) { print "<td width=\"20%\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td>"; }
7445
# foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
7446
# $daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
7447
# my $year=$1; my $month=$2; my $day=$3;
7448
# if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
7449
# my $dayofweekcursor=DayOfWeek($day,$month,$year);
7451
# print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">",Format_Date("$year$month$day"."000000",2),"</td>";
7452
# if ($ShowMonthDayStats =~ /V/i) { print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">",$DayVisits{$year.$month.$day}?$DayVisits{$year.$month.$day}:"0","</td>"; }
7453
# if ($ShowMonthDayStats =~ /P/i) { print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">",$DayPages{$year.$month.$day}?$DayPages{$year.$month.$day}:"0","</td>"; }
7454
# if ($ShowMonthDayStats =~ /H/i) { print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">",$DayHits{$year.$month.$day}?$DayHits{$year.$month.$day}:"0","</td>"; }
7455
# if ($ShowMonthDayStats =~ /B/i) { print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">",Format_Bytes(int($DayBytes{$year.$month.$day})),"</td>"; }
7458
# print "</table>\n<br />";
7460
# print "</center>\n";
7461
# print "</td></tr>\n";
7466
if ($HTMLOutput{'alldomains'}) {
7467
print "$Center<a name=\"domains\"> </a><br />\n";
7469
my $title=''; my $cpt=0;
7470
if ($HTMLOutput{'alldomains'}) { $title.="$Message[25]"; $cpt=(scalar keys %_domener_h); }
7471
&tab_head("$title",19,0,'domains');
7472
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"$WIDTHCOLICON\"> </th><th colspan=\"2\">$Message[17]</th>";
7473
if ($ShowDomainsStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
7474
if ($ShowDomainsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
7475
if ($ShowDomainsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
7476
print "<th> </th>";
7478
$total_p=$total_h=$total_k=0;
7479
$max_h=1; foreach (values %_domener_h) { if ($_ > $max_h) { $max_h = $_; } }
7480
$max_k=1; foreach (values %_domener_k) { if ($_ > $max_k) { $max_k = $_; } }
7482
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_domener_h,\%_domener_p);
7483
foreach my $key (@keylist) {
7484
my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
7485
if ($max_h > 0) { $bredde_p=int($BarWidth*$_domener_p{$key}/$max_h)+1; } # use max_h to enable to compare pages with hits
7486
if ($_domener_p{$key} && $bredde_p==1) { $bredde_p=2; }
7487
if ($max_h > 0) { $bredde_h=int($BarWidth*$_domener_h{$key}/$max_h)+1; }
7488
if ($_domener_h{$key} && $bredde_h==1) { $bredde_h=2; }
7489
if ($max_k > 0) { $bredde_k=int($BarWidth*($_domener_k{$key}||0)/$max_k)+1; }
7490
if ($_domener_k{$key} && $bredde_k==1) { $bredde_k=2; }
7491
my $newkey=lc($key);
7492
if ($newkey eq 'ip' || ! $DomainsHashIDLib{$newkey}) {
7493
print "<tr><td width=\"$WIDTHCOLICON\"><img src=\"$DirIcons\/flags\/ip.png\" height=\"14\"".AltTitle("$Message[0]")." /></td><td class=\"aws\">$Message[0]</td><td>$newkey</td>";
7496
print "<tr><td width=\"$WIDTHCOLICON\"><img src=\"$DirIcons\/flags\/$newkey.png\" height=\"14\"".AltTitle("$newkey")." /></td><td class=\"aws\">$DomainsHashIDLib{$newkey}</td><td>$newkey</td>";
7498
if ($ShowDomainsStats =~ /P/i) { print "<td>$_domener_p{$key}</td>"; }
7499
if ($ShowDomainsStats =~ /H/i) { print "<td>$_domener_h{$key}</td>"; }
7500
if ($ShowDomainsStats =~ /B/i) { print "<td>".Format_Bytes($_domener_k{$key})."</td>"; }
7501
print "<td style=\"text-align:left; font-size:4px;\">";
7502
if ($ShowDomainsStats =~ /P/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hp'}\" width=\"$bredde_p\" height=\"5\"".AltTitle("$Message[56]: ".int($_domener_p{$key}))." /><br />\n"; }
7503
if ($ShowDomainsStats =~ /H/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\"".AltTitle("$Message[57]: ".int($_domener_h{$key}))." /><br />\n"; }
7504
if ($ShowDomainsStats =~ /B/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hk'}\" width=\"$bredde_k\" height=\"5\"".AltTitle("$Message[75]: ".Format_Bytes($_domener_k{$key}))." />"; }
7507
$total_p += $_domener_p{$key};
7508
$total_h += $_domener_h{$key};
7509
$total_k += $_domener_k{$key}||0;
7512
$rest_p=$TotalPages-$total_p;
7513
$rest_h=$TotalHits-$total_h;
7514
$rest_k=$TotalBytes-$total_k;
7515
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other domains (known or not)
7516
print "<tr><td width=\"$WIDTHCOLICON\"> </td><td colspan=\"2\" class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7517
if ($ShowDomainsStats =~ /P/i) { print "<td>$rest_p</td>"; }
7518
if ($ShowDomainsStats =~ /H/i) { print "<td>$rest_h</td>"; }
7519
if ($ShowDomainsStats =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
7520
print "<td class=\"aws\"> </td>";
7526
if ($HTMLOutput{'allhosts'} || $HTMLOutput{'lasthosts'}) {
7527
print "$Center<a name=\"hosts\"> </a><br />\n";
7529
&ShowFormFilter("hostfilter",$FilterIn{'host'},$FilterEx{'host'});
7531
my $title=''; my $cpt=0;
7532
if ($HTMLOutput{'allhosts'}) { $title.="$Message[81]"; $cpt=(scalar keys %_host_h); }
7533
if ($HTMLOutput{'lasthosts'}) { $title.="$Message[9]"; $cpt=(scalar keys %_host_h); }
7534
&tab_head("$title",19,0,'hosts');
7535
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>";
7536
if ($FilterIn{'host'} || $FilterEx{'host'}) { # With filter
7537
if ($FilterIn{'host'}) { print "$Message[79] '<b>$FilterIn{'host'}</b>'"; }
7538
if ($FilterIn{'host'} && $FilterEx{'host'}) { print " - "; }
7539
if ($FilterEx{'host'}) { print " Exlude $Message[79] '<b>$FilterEx{'host'}</b>'"; }
7540
if ($FilterIn{'host'} || $FilterEx{'host'}) { print ": "; }
7541
print "$cpt $Message[81]";
7542
if ($MonthRequired ne 'all') {
7543
if ($HTMLOutput{'allhosts'} || $HTMLOutput{'lasthosts'}) { print "<br />$Message[102]: $TotalHostsKnown $Message[82], $TotalHostsUnknown $Message[1] - $TotalUnique $Message[11]"; }
7546
else { # Without filter
7547
if ($MonthRequired ne 'all') { print "$Message[102] : $TotalHostsKnown $Message[82], $TotalHostsUnknown $Message[1] - $TotalUnique $Message[11]"; }
7548
else { print "$Message[102] : ".(scalar keys %_host_h); }
7551
&ShowHostInfo('__title__');
7552
if ($ShowHostsStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
7553
if ($ShowHostsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
7554
if ($ShowHostsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
7555
if ($ShowHostsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
7557
$total_p=$total_h=$total_k=0;
7559
if ($HTMLOutput{'allhosts'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Host'},\%_host_h,\%_host_p); }
7560
if ($HTMLOutput{'lasthosts'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Host'},\%_host_h,\%_host_l); }
7561
foreach my $key (@keylist) {
7562
my $host=CleanFromCSSA($key);
7563
print "<tr><td class=\"aws\">".($_robot_l{$key}?'<b>':'')."$host".($_robot_l{$key}?'</b>':'')."</td>";
7564
&ShowHostInfo($key);
7565
if ($ShowHostsStats =~ /P/i) { print "<td>".($_host_p{$key}?$_host_p{$key}:" ")."</td>"; }
7566
if ($ShowHostsStats =~ /H/i) { print "<td>$_host_h{$key}</td>"; }
7567
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($_host_k{$key})."</td>"; }
7568
if ($ShowHostsStats =~ /L/i) { print "<td>".($_host_l{$key}?Format_Date($_host_l{$key},1):'-')."</td>"; }
7570
$total_p += $_host_p{$key};
7571
$total_h += $_host_h{$key};
7572
$total_k += $_host_k{$key}||0;
7575
if ($Debug) { debug("Total real / shown : $TotalPages / $total_p - $TotalHits / $total_h - $TotalBytes / $total_h",2); }
7576
$rest_p=$TotalPages-$total_p;
7577
$rest_h=$TotalHits-$total_h;
7578
$rest_k=$TotalBytes-$total_k;
7579
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other visitors (known or not)
7580
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7582
if ($ShowHostsStats =~ /P/i) { print "<td>".($rest_p?$rest_p:" ")."</td>"; }
7583
if ($ShowHostsStats =~ /H/i) { print "<td>$rest_h</td>"; }
7584
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
7585
if ($ShowHostsStats =~ /L/i) { print "<td> </td>"; }
7591
if ($HTMLOutput{'unknownip'}) {
7592
print "$Center<a name=\"unknownip\"> </a><br />\n";
7593
&tab_head("$Message[45]",19,0,'unknownwip');
7594
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>".(scalar keys %_host_h)." $Message[1]</th>";
7595
&ShowHostInfo('__title__');
7596
if ($ShowHostsStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
7597
if ($ShowHostsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
7598
if ($ShowHostsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
7599
if ($ShowHostsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
7601
$total_p=$total_h=$total_k=0;
7603
&BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Host'},\%_host_h,\%_host_p);
7604
foreach my $key (@keylist) {
7605
my $host=CleanFromCSSA($key);
7606
print "<tr><td class=\"aws\">$host</td>";
7607
&ShowHostInfo($key);
7608
if ($ShowHostsStats =~ /P/i) { print "<td>".($_host_p{$key}?$_host_p{$key}:" ")."</td>"; }
7609
if ($ShowHostsStats =~ /H/i) { print "<td>$_host_h{$key}</td>"; }
7610
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($_host_k{$key})."</td>"; }
7611
if ($ShowHostsStats =~ /L/i) { print "<td>".($_host_l{$key}?Format_Date($_host_l{$key},1):'-')."</td>"; }
7613
$total_p += $_host_p{$key};
7614
$total_h += $_host_h{$key};
7615
$total_k += $_host_k{$key}||0;
7618
if ($Debug) { debug("Total real / shown : $TotalPages / $total_p - $TotalHits / $total_h - $TotalBytes / $total_h",2); }
7619
$rest_p=$TotalPages-$total_p;
7620
$rest_h=$TotalHits-$total_h;
7621
$rest_k=$TotalBytes-$total_k;
7622
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other visitors (known or not)
7623
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[82]</span></td>";
7625
if ($ShowHostsStats =~ /P/i) { print "<td>".($rest_p?$rest_p:" ")."</td>"; }
7626
if ($ShowHostsStats =~ /H/i) { print "<td>$rest_h</td>"; }
7627
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
7628
if ($ShowHostsStats =~ /L/i) { print "<td> </td>"; }
7634
if ($HTMLOutput{'allemails'} || $HTMLOutput{'lastemails'}) {
7635
&ShowEmailSendersChart($NewLinkParams,$NewLinkTarget);
7638
if ($HTMLOutput{'allemailr'} || $HTMLOutput{'lastemailr'}) {
7639
&ShowEmailReceiversChart($NewLinkParams,$NewLinkTarget);
7642
if ($HTMLOutput{'alllogins'} || $HTMLOutput{'lastlogins'}) {
7643
print "$Center<a name=\"logins\"> </a><br />\n";
7645
if ($HTMLOutput{'alllogins'}) { $title.="$Message[94]"; }
7646
if ($HTMLOutput{'lastlogins'}) { $title.="$Message[9]"; }
7647
&tab_head("$title",19,0,'logins');
7648
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$Message[94] : ".(scalar keys %_login_h)."</th>";
7649
&ShowUserInfo('__title__');
7650
if ($ShowAuthenticatedUsers =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
7651
if ($ShowAuthenticatedUsers =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
7652
if ($ShowAuthenticatedUsers =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
7653
if ($ShowAuthenticatedUsers =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
7655
$total_p=$total_h=$total_k=0;
7657
if ($HTMLOutput{'alllogins'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Host'},\%_login_h,\%_login_p); }
7658
if ($HTMLOutput{'lastlogins'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Host'},\%_login_h,\%_login_l); }
7659
foreach my $key (@keylist) {
7660
print "<tr><td class=\"aws\">$key</td>";
7661
&ShowUserInfo($key);
7662
if ($ShowAuthenticatedUsers =~ /P/i) { print "<td>".($_login_p{$key}?$_login_p{$key}:" ")."</td>"; }
7663
if ($ShowAuthenticatedUsers =~ /H/i) { print "<td>$_login_h{$key}</td>"; }
7664
if ($ShowAuthenticatedUsers =~ /B/i) { print "<td>".Format_Bytes($_login_k{$key})."</td>"; }
7665
if ($ShowAuthenticatedUsers =~ /L/i) { print "<td>".($_login_l{$key}?Format_Date($_login_l{$key},1):'-')."</td>"; }
7667
$total_p += $_login_p{$key}||0;
7668
$total_h += $_login_h{$key};
7669
$total_k += $_login_k{$key}||0;
7672
if ($Debug) { debug("Total real / shown : $TotalPages / $total_p - $TotalHits / $total_h - $TotalBytes / $total_h",2); }
7673
$rest_p=$TotalPages-$total_p;
7674
$rest_h=$TotalHits-$total_h;
7675
$rest_k=$TotalBytes-$total_k;
7676
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other logins and/or anonymous
7677
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[125]</span></td>";
7679
if ($ShowAuthenticatedUsers =~ /P/i) { print "<td>".($rest_p?$rest_p:" ")."</td>"; }
7680
if ($ShowAuthenticatedUsers =~ /H/i) { print "<td>$rest_h</td>"; }
7681
if ($ShowAuthenticatedUsers =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
7682
if ($ShowAuthenticatedUsers =~ /L/i) { print "<td> </td>"; }
7688
if ($HTMLOutput{'allrobots'} || $HTMLOutput{'lastrobots'}) {
7689
print "$Center<a name=\"robots\"> </a><br />\n";
7691
if ($HTMLOutput{'allrobots'}) { $title.="$Message[53]"; }
7692
if ($HTMLOutput{'lastrobots'}) { $title.="$Message[9]"; }
7693
&tab_head("$title",19,0,'robots');
7694
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>".(scalar keys %_robot_h)." $Message[51]</th>";
7695
if ($ShowRobotsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
7696
if ($ShowRobotsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
7697
if ($ShowRobotsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
7699
$total_p=$total_h=$total_k=$total_r=0;
7701
if ($HTMLOutput{'allrobots'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Robot'},\%_robot_h,\%_robot_h); }
7702
if ($HTMLOutput{'lastrobots'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Robot'},\%_robot_h,\%_robot_l); }
7703
foreach my $key (@keylist) {
7704
print "<tr><td class=\"aws\">".($RobotsHashIDLib{$key}?$RobotsHashIDLib{$key}:$key)."</td>";
7705
if ($ShowRobotsStats =~ /H/i) { print "<td>".($_robot_h{$key}-$_robot_r{$key}).($_robot_r{$key}?"+$_robot_r{$key}":"")."</td>"; }
7706
if ($ShowRobotsStats =~ /B/i) { print "<td>".Format_Bytes($_robot_k{$key})."</td>"; }
7707
if ($ShowRobotsStats =~ /L/i) { print "<td>".($_robot_l{$key}?Format_Date($_robot_l{$key},1):'-')."</td>"; }
7709
#$total_p += $_robot_p{$key}||0;
7710
$total_h += $_robot_h{$key};
7711
$total_k += $_robot_k{$key}||0;
7712
$total_r += $_robot_r{$key}||0;
7715
# For bots we need to count Totals
7716
my $TotalPagesRobots = 0; #foreach (values %_robot_p) { $TotalPagesRobots+=$_; }
7717
my $TotalHitsRobots = 0; foreach (values %_robot_h) { $TotalHitsRobots+=$_; }
7718
my $TotalBytesRobots = 0; foreach (values %_robot_k) { $TotalBytesRobots+=$_; }
7719
my $TotalRRobots = 0; foreach (values %_robot_r) { $TotalRRobots+=$_; }
7720
$rest_p=0; #$rest_p=$TotalPagesRobots-$total_p;
7721
$rest_h=$TotalHitsRobots-$total_h;
7722
$rest_k=$TotalBytesRobots-$total_k;
7723
$rest_r=$TotalRRobots-$total_r;
7724
if ($Debug) { debug("Total real / shown : $TotalPagesRobots / $total_p - $TotalHitsRobots / $total_h - $TotalBytesRobots / $total_k",2); }
7725
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0 || $rest_r > 0) { # All other robots
7726
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7727
if ($ShowRobotsStats =~ /H/i) { print "<td>$rest_h</td>"; }
7728
if ($ShowRobotsStats =~ /B/i) { print "<td>".(Format_Bytes($rest_k))."</td>"; }
7729
if ($ShowRobotsStats =~ /L/i) { print "<td> </td>"; }
7732
&tab_end("* $Message[157]");
7735
if ($HTMLOutput{'urldetail'} || $HTMLOutput{'urlentry'} || $HTMLOutput{'urlexit'}) {
7736
# Call to plugins' function ShowPagesFilter
7737
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesFilter'}}) {
7738
my $function="ShowPagesFilter_$pluginname()";
7741
print "$Center<a name=\"urls\"> </a><br />\n";
7743
&ShowFormFilter("urlfilter",$FilterIn{'url'},$FilterEx{'url'});
7745
my $title=''; my $cpt=0;
7746
if ($HTMLOutput{'urldetail'}) { $title=$Message[19]; $cpt=(scalar keys %_url_p); }
7747
if ($HTMLOutput{'urlentry'}) { $title=$Message[104]; $cpt=(scalar keys %_url_e); }
7748
if ($HTMLOutput{'urlexit'}) { $title=$Message[116]; $cpt=(scalar keys %_url_x); }
7749
&tab_head("$title",19,0,'urls');
7750
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>";
7751
if ($FilterIn{'url'} || $FilterEx{'url'}) {
7752
if ($FilterIn{'url'}) { print "$Message[79] <b>$FilterIn{'url'}</b>"; }
7753
if ($FilterIn{'url'} && $FilterEx{'url'}) { print " - "; }
7754
if ($FilterEx{'url'}) { print "Exclude $Message[79] <b>$FilterEx{'url'}</b>"; }
7755
if ($FilterIn{'url'} || $FilterEx{'url'}) { print ": "; }
7756
print "$cpt $Message[28]";
7757
if ($MonthRequired ne 'all') {
7758
if ($HTMLOutput{'urldetail'}) { print "<br />$Message[102]: $TotalDifferentPages $Message[28]"; }
7761
else { print "$Message[102]: $cpt $Message[28]"; }
7763
if ($ShowPagesStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[29]</th>"; }
7764
if ($ShowPagesStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[106]</th>"; }
7765
if ($ShowPagesStats =~ /E/i) { print "<th bgcolor=\"#$color_e\" width=\"80\">$Message[104]</th>"; }
7766
if ($ShowPagesStats =~ /X/i) { print "<th bgcolor=\"#$color_x\" width=\"80\">$Message[116]</th>"; }
7767
# Call to plugins' function ShowPagesAddField
7768
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
7769
my $function="ShowPagesAddField_$pluginname('title')";
7772
print "<th> </th></tr>\n";
7773
$total_p=$total_k=$total_e=$total_x=0;
7775
if ($HTMLOutput{'urlentry'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'File'},\%_url_e,\%_url_e); }
7776
elsif ($HTMLOutput{'urlexit'}) { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'File'},\%_url_x,\%_url_x); }
7777
else { &BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'File'},\%_url_p,\%_url_p); }
7779
foreach my $key (@keylist) {
7780
if ($_url_p{$key} > $max_p) { $max_p = $_url_p{$key}; }
7781
if ($_url_k{$key}/($_url_p{$key}||1) > $max_k) { $max_k = $_url_k{$key}/($_url_p{$key}||1); }
7783
foreach my $key (@keylist) {
7784
print "<tr><td class=\"aws\">";
7787
my $bredde_p=0; my $bredde_e=0; my $bredde_x=0; my $bredde_k=0;
7788
if ($max_p > 0) { $bredde_p=int($BarWidth*($_url_p{$key}||0)/$max_p)+1; }
7789
if (($bredde_p==1) && $_url_p{$key}) { $bredde_p=2; }
7790
if ($max_p > 0) { $bredde_e=int($BarWidth*($_url_e{$key}||0)/$max_p)+1; }
7791
if (($bredde_e==1) && $_url_e{$key}) { $bredde_e=2; }
7792
if ($max_p > 0) { $bredde_x=int($BarWidth*($_url_x{$key}||0)/$max_p)+1; }
7793
if (($bredde_x==1) && $_url_x{$key}) { $bredde_x=2; }
7794
if ($max_k > 0) { $bredde_k=int($BarWidth*(($_url_k{$key}||0)/($_url_p{$key}||1))/$max_k)+1; }
7795
if (($bredde_k==1) && $_url_k{$key}) { $bredde_k=2; }
7796
if ($ShowPagesStats =~ /P/i) { print "<td>$_url_p{$key}</td>"; }
7797
if ($ShowPagesStats =~ /B/i) { print "<td>".($_url_k{$key}?Format_Bytes($_url_k{$key}/($_url_p{$key}||1)):" ")."</td>"; }
7798
if ($ShowPagesStats =~ /E/i) { print "<td>".($_url_e{$key}?$_url_e{$key}:" ")."</td>"; }
7799
if ($ShowPagesStats =~ /X/i) { print "<td>".($_url_x{$key}?$_url_x{$key}:" ")."</td>"; }
7800
# Call to plugins' function ShowPagesAddField
7801
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
7802
my $function="ShowPagesAddField_$pluginname('$key')";
7805
print "<td style=\"text-align:left; font-size:4px;\">";
7806
# alt and title are not provided to reduce page size
7807
if ($ShowPagesStats =~ /P/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hp'}\" width=\"$bredde_p\" height=\"4\" /><br />"; }
7808
if ($ShowPagesStats =~ /B/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hk'}\" width=\"$bredde_k\" height=\"4\" /><br />"; }
7809
if ($ShowPagesStats =~ /E/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'he'}\" width=\"$bredde_e\" height=\"4\" /><br />"; }
7810
if ($ShowPagesStats =~ /X/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hx'}\" width=\"$bredde_x\" height=\"4\" />"; }
7811
print "</td></tr>\n";
7812
$total_p += $_url_p{$key};
7813
$total_e += $_url_e{$key};
7814
$total_x += $_url_x{$key};
7815
$total_k += $_url_k{$key};
7818
if ($Debug) { debug("Total real / shown : $TotalPages / $total_p - $TotalEntries / $total_e - $TotalExits / $total_x - $TotalBytesPages / $total_k",2); }
7819
$rest_p=$TotalPages-$total_p;
7820
$rest_k=$TotalBytesPages-$total_k;
7821
$rest_e=$TotalEntries-$total_e;
7822
$rest_x=$TotalExits-$total_x;
7823
if ($rest_p > 0 || $rest_e > 0 || $rest_k > 0) {
7824
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7825
if ($ShowPagesStats =~ /P/i) { print "<td>".($rest_p?$rest_p:" ")."</td>"; }
7826
if ($ShowPagesStats =~ /B/i) { print "<td>".($rest_k?Format_Bytes($rest_k/($rest_p||1)):" ")."</td>"; }
7827
if ($ShowPagesStats =~ /E/i) { print "<td>".($rest_e?$rest_e:" ")."</td>"; }
7828
if ($ShowPagesStats =~ /X/i) { print "<td>".($rest_x?$rest_x:" ")."</td>"; }
7829
# Call to plugins' function ShowPagesAddField
7830
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
7831
my $function="ShowPagesAddField_$pluginname('')";
7834
print "<td> </td></tr>\n";
7839
if ($HTMLOutput{'unknownos'}) {
7840
print "$Center<a name=\"unknownos\"> </a><br />\n";
7841
my $title="$Message[46]";
7842
&tab_head("$title",19,0,'unknownos');
7843
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>User agent (".(scalar keys %_unknownreferer_l).")</th><th>$Message[9]</th></tr>\n";
7846
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_unknownreferer_l,\%_unknownreferer_l);
7847
foreach my $key (@keylist) {
7848
my $useragent=CleanFromCSSA($key);
7849
print "<tr><td class=\"aws\">$useragent</td>";
7850
print "<td>".Format_Date($_unknownreferer_l{$key},1)."</td>";
7855
$rest_l=(scalar keys %_unknownreferer_l)-$total_l;
7857
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7864
if ($HTMLOutput{'unknownbrowser'}) {
7865
print "$Center<a name=\"unknownbrowser\"> </a><br />\n";
7866
my $title="$Message[50]";
7867
&tab_head("$title",19,0,'unknownbrowser');
7868
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>User agent (".(scalar keys %_unknownrefererbrowser_l).")</th><th>$Message[9]</th></tr>\n";
7871
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_unknownrefererbrowser_l,\%_unknownrefererbrowser_l);
7872
foreach my $key (@keylist) {
7873
my $useragent=CleanFromCSSA($key);
7874
print "<tr><td class=\"aws\">$useragent</td><td>".Format_Date($_unknownrefererbrowser_l{$key},1)."</td></tr>\n";
7878
$rest_l=(scalar keys %_unknownrefererbrowser_l)-$total_l;
7880
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
7887
if ($HTMLOutput{'osdetail'}) {
7889
print "$Center<a name=\"osversions\"> </a><br />";
7890
my $title="$Message[59]";
7891
&tab_head("$title",19,0,'osversions');
7892
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"2\">$Message[58]</th>";
7893
print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>";
7894
print "<th> </th>";
7898
&BuildKeyList(MinimumButNoZero(scalar keys %_os_h,500),1,\%_os_h,\%_os_h);
7899
my %keysinkeylist=();
7901
# Count total by family
7902
my %totalfamily_h=();
7904
OSLOOP: foreach my $key (@keylist) {
7905
$total_h+=$_os_h{$key};
7906
if ($_os_h{$key} > $max_h) { $max_h = $_os_h{$key}; }
7907
foreach my $family (@OSFamily) { if ($key =~ /^$family/i) { $totalfamily_h{$family}+=$_os_h{$key}; $TotalFamily+=$_os_h{$key}; next OSLOOP; } }
7909
# Write records grouped in a browser family
7910
foreach my $family (@OSFamily) {
7912
if ($total_h) { $p=int($totalfamily_h{$family}/$total_h*1000)/10; $p="$p %"; }
7913
my $familyheadershown=0;
7914
foreach my $key (reverse sort keys %_os_h) {
7915
if ($key =~ /^$family(.*)/i) {
7916
if (! $familyheadershown) {
7917
print "<tr bgcolor=\"#F6F6F6\"><td class=\"aws\" colspan=\"2\"><b>".uc($family)."</b></td>";
7918
print "<td><b>".int($totalfamily_h{$family})."</b></td><td><b>$p</b></td><td> </td>";
7920
$familyheadershown=1;
7922
$keysinkeylist{$key}=1;
7925
if ($total_h) { $p=int($_os_h{$key}/$total_h*1000)/10; $p="$p %"; }
7927
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/os\/$key.png\"".AltTitle("")." /></td>";
7928
print "<td class=\"aws\">$OSHashLib{$key}</td>";
7930
if ($max_h > 0) { $bredde_h=int($BarWidth*($_os_h{$key}||0)/$max_h)+1; }
7931
if (($bredde_h==1) && $_os_h{$key}) { $bredde_h=2; }
7932
print "<td>$_os_h{$key}</td><td>$p</td>";
7933
print "<td class=\"aws\">";
7934
# alt and title are not provided to reduce page size
7935
if ($ShowOSStats) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\" /><br />"; }
7942
# Write other records
7943
my $familyheadershown=0;
7944
foreach my $key (@keylist) {
7945
if ($keysinkeylist{$key}) { next; }
7946
if (! $familyheadershown) {
7948
if ($total_h) { $p=int(($total_h-$TotalFamily)/$total_h*1000)/10; $p="$p %"; }
7949
print "<tr bgcolor=\"#F6F6F6\"><td class=\"aws\" colspan=\"2\"><b>".uc($Message[2])."</b></td>";
7950
print "<td><b>".($total_h-$TotalFamily)."</b></td><td><b>$p</b></td><td> </td>";
7952
$familyheadershown=1;
7955
if ($total_h) { $p=int($_os_h{$key}/$total_h*1000)/10; $p="$p %"; }
7957
if ($key eq 'Unknown') {
7958
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/unknown.png\"".AltTitle("")." /></td><td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td>";
7961
my $keywithoutcumul=$key; $keywithoutcumul =~ s/cumul$//i;
7962
my $libos=$OSHashLib{$keywithoutcumul}||$keywithoutcumul;
7963
my $nameicon=$keywithoutcumul; $nameicon =~ s/[^\w]//g;
7964
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/os\/$nameicon.png\"".AltTitle("")." /></td><td class=\"aws\">$libos</td>";
7967
if ($max_h > 0) { $bredde_h=int($BarWidth*($_os_h{$key}||0)/$max_h)+1; }
7968
if (($bredde_h==1) && $_os_h{$key}) { $bredde_h=2; }
7969
print "<td>$_os_h{$key}</td><td>$p</td>";
7970
print "<td class=\"aws\">";
7971
# alt and title are not provided to reduce page size
7972
if ($ShowOSStats) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\" /><br />"; }
7979
if ($HTMLOutput{'browserdetail'}) {
7980
# Show browsers versions
7981
print "$Center<a name=\"browsersversions\"> </a><br />";
7982
my $title="$Message[21]";
7983
&tab_head("$title",19,0,'browsersversions');
7984
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"2\">$Message[58]</th>";
7985
print "<th width=\"80\">$Message[111]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>";
7986
print "<th> </th>";
7990
&BuildKeyList(MinimumButNoZero(scalar keys %_browser_h,500),1,\%_browser_h,\%_browser_h);
7991
my %keysinkeylist=();
7993
# Count total by family
7994
my %totalfamily_h=();
7996
BROWSERLOOP: foreach my $key (@keylist) {
7997
$total_h+=$_browser_h{$key};
7998
if ($_browser_h{$key} > $max_h) { $max_h = $_browser_h{$key}; }
7999
foreach my $family (keys %BrowsersFamily) { if ($key =~ /^$family/i) { $totalfamily_h{$family}+=$_browser_h{$key}; $TotalFamily+=$_browser_h{$key}; next BROWSERLOOP; } }
8001
# Write records grouped in a browser family
8002
foreach my $family (sort { $BrowsersFamily{$a} <=> $BrowsersFamily{$b} } keys %BrowsersFamily) {
8004
if ($total_h) { $p=int($totalfamily_h{$family}/$total_h*1000)/10; $p="$p %"; }
8005
my $familyheadershown=0;
8006
foreach my $key (reverse sort keys %_browser_h) {
8007
if ($key =~ /^$family(.*)/i) {
8008
if (! $familyheadershown) {
8009
print "<tr bgcolor=\"#F6F6F6\"><td class=\"aws\" colspan=\"2\"><b>".uc($family)."</b></td>";
8010
print "<td> </td><td><b>".int($totalfamily_h{$family})."</b></td><td><b>$p</b></td><td> </td>";
8012
$familyheadershown=1;
8014
$keysinkeylist{$key}=1;
8017
if ($total_h) { $p=int($_browser_h{$key}/$total_h*1000)/10; $p="$p %"; }
8019
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/$family.png\"".AltTitle("")." /></td>";
8020
print "<td class=\"aws\">".ucfirst($family)." ".($ver?"$ver":"?")."</td>";
8021
print "<td>".($BrowsersHereAreGrabbers{$family}?"<b>$Message[112]</b>":"$Message[113]")."</td>";
8023
if ($max_h > 0) { $bredde_h=int($BarWidth*($_browser_h{$key}||0)/$max_h)+1; }
8024
if (($bredde_h==1) && $_browser_h{$key}) { $bredde_h=2; }
8025
print "<td>$_browser_h{$key}</td><td>$p</td>";
8026
print "<td class=\"aws\">";
8027
# alt and title are not provided to reduce page size
8028
if ($ShowBrowsersStats) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\" /><br />"; }
8035
# Write other records
8036
my $familyheadershown=0;
8037
foreach my $key (@keylist) {
8038
if ($keysinkeylist{$key}) { next; }
8039
if (! $familyheadershown) {
8041
if ($total_h) { $p=int(($total_h-$TotalFamily)/$total_h*1000)/10; $p="$p %"; }
8042
print "<tr bgcolor=\"#F6F6F6\"><td class=\"aws\" colspan=\"2\"><b>".uc($Message[2])."</b></td>";
8043
print "<td> </td><td><b>".($total_h-$TotalFamily)."</b></td><td><b>$p</b></td><td> </td>";
8045
$familyheadershown=1;
8048
if ($total_h) { $p=int($_browser_h{$key}/$total_h*1000)/10; $p="$p %"; }
8050
if ($key eq 'Unknown') {
8051
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/unknown.png\"".AltTitle("")." /></td><td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td><td width=\"80\">?</td>";
8054
my $keywithoutcumul=$key; $keywithoutcumul =~ s/cumul$//i;
8055
my $libbrowser=$BrowsersHashIDLib{$keywithoutcumul}||$keywithoutcumul;
8056
my $nameicon=$BrowsersHashIcon{$keywithoutcumul}||"notavailable";
8057
print "<td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/$nameicon.png\"".AltTitle("")." /></td><td class=\"aws\">$libbrowser</td><td>".($BrowsersHereAreGrabbers{$key}?"<b>$Message[112]</b>":"$Message[113]")."</td>";
8060
if ($max_h > 0) { $bredde_h=int($BarWidth*($_browser_h{$key}||0)/$max_h)+1; }
8061
if (($bredde_h==1) && $_browser_h{$key}) { $bredde_h=2; }
8062
print "<td>$_browser_h{$key}</td><td>$p</td>";
8063
print "<td class=\"aws\">";
8064
# alt and title are not provided to reduce page size
8065
if ($ShowBrowsersStats) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\" /><br />"; }
8072
if ($HTMLOutput{'refererse'}) {
8073
print "$Center<a name=\"refererse\"> </a><br />\n";
8074
my $title="$Message[40]";
8075
&tab_head("$title",19,0,'refererse');
8076
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$TotalDifferentSearchEngines $Message[122]</th>";
8077
print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th><th bgcolor=\"#$color_p\" width=\"80\">$Message[15]</th>";
8078
print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>";
8082
&BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Refer'},\%_se_referrals_h,\%_se_referrals_p);
8083
foreach my $key (@keylist) {
8084
my $newreferer=CleanFromCSSA($SearchEnginesHashLib{$key}||$key);
8086
if ($TotalSearchEnginesPages) { $p_p=int($_se_referrals_p{$key}/$TotalSearchEnginesPages*1000)/10; }
8087
if ($TotalSearchEnginesHits) { $p_h=int($_se_referrals_h{$key}/$TotalSearchEnginesHits*1000)/10; }
8088
print "<tr><td class=\"aws\">$newreferer</td>";
8089
print "<td>".($_se_referrals_p{$key}?$_se_referrals_p{$key}:' ')."</td>";
8090
print "<td>".($_se_referrals_p{$key}?"$p_p %":' ')."</td>";
8091
print "<td>$_se_referrals_h{$key}</td>";
8092
print "<td>$p_h %</td>";
8094
$total_p += $_se_referrals_p{$key};
8095
$total_h += $_se_referrals_h{$key};
8098
if ($Debug) { debug("Total real / shown : $TotalSearchEnginesPages / $total_p - $TotalSearchEnginesHits / $total_h",2); }
8099
$rest_p=$TotalSearchEnginesPages-$total_p;
8100
$rest_h=$TotalSearchEnginesHits-$total_h;
8101
if ($rest_p > 0 || $rest_h > 0) {
8103
if ($TotalSearchEnginesPages) { $p_p=int($rest_p/$TotalSearchEnginesPages*1000)/10; }
8104
if ($TotalSearchEnginesHits) { $p_h=int($rest_h/$TotalSearchEnginesHits*1000)/10; }
8105
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
8106
print "<td>".($rest_p?$rest_p:' ')."</td>";
8107
print "<td>".($rest_p?"$p_p %":' ')."</td>";
8108
print "<td>$rest_h</td>";
8109
print "<td>$p_h %</td>";
8115
if ($HTMLOutput{'refererpages'}) {
8116
print "$Center<a name=\"refererpages\"> </a><br />\n";
8118
&ShowFormFilter("refererpagesfilter",$FilterIn{'refererpages'},$FilterEx{'refererpages'});
8119
my $title="$Message[41]"; my $cpt=0;
8120
$cpt=(scalar keys %_pagesrefs_h);
8121
&tab_head("$title",19,0,'refererpages');
8122
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>";
8123
if ($FilterIn{'refererpages'} || $FilterEx{'refererpages'}) {
8124
if ($FilterIn{'refererpages'}) { print "$Message[79] <b>$FilterIn{'refererpages'}</b>"; }
8125
if ($FilterIn{'refererpages'} && $FilterEx{'refererpages'}) { print " - "; }
8126
if ($FilterEx{'refererpages'}) { print "Exclude $Message[79] <b>$FilterEx{'refererpages'}</b>"; }
8127
if ($FilterIn{'refererpages'} || $FilterEx{'refererpages'}) { print ": "; }
8128
print "$cpt $Message[28]";
8129
#if ($MonthRequired ne 'all') {
8130
# if ($HTMLOutput{'refererpages'}) { print "<br />$Message[102]: $TotalDifferentPages $Message[28]"; }
8133
else { print "$Message[102]: $cpt $Message[28]"; }
8135
print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th><th bgcolor=\"#$color_p\" width=\"80\">$Message[15]</th>";
8136
print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>";
8140
&BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Refer'},\%_pagesrefs_h,\%_pagesrefs_p);
8141
foreach my $key (@keylist) {
8142
my $nompage=CleanFromCSSA($key);
8143
if (length($nompage)>$MaxLengthOfShownURL) { $nompage=substr($nompage,0,$MaxLengthOfShownURL)."..."; }
8145
if ($TotalRefererPages) { $p_p=int($_pagesrefs_p{$key}/$TotalRefererPages*1000)/10; }
8146
if ($TotalRefererHits) { $p_h=int($_pagesrefs_h{$key}/$TotalRefererHits*1000)/10; }
8147
print "<tr><td class=\"aws\">";
8150
print "<td>".($_pagesrefs_p{$key}?$_pagesrefs_p{$key}:' ')."</td><td>".($_pagesrefs_p{$key}?"$p_p %":' ')."</td>";
8151
print "<td>".($_pagesrefs_h{$key}?$_pagesrefs_h{$key}:' ')."</td><td>".($_pagesrefs_h{$key}?"$p_h %":' ')."</td>";
8153
$total_p += $_pagesrefs_p{$key};
8154
$total_h += $_pagesrefs_h{$key};
8157
if ($Debug) { debug("Total real / shown : $TotalRefererPages / $total_p - $TotalRefererHits / $total_h",2); }
8158
$rest_p=$TotalRefererPages-$total_p;
8159
$rest_h=$TotalRefererHits-$total_h;
8160
if ($rest_p > 0 || $rest_h > 0) {
8162
if ($TotalRefererPages) { $p_p=int($rest_p/$TotalRefererPages*1000)/10; }
8163
if ($TotalRefererHits) { $p_h=int($rest_h/$TotalRefererHits*1000)/10; }
8164
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
8165
print "<td>".($rest_p?$rest_p:' ')."</td>";
8166
print "<td>".($rest_p?"$p_p %":' ')."</td>";
8167
print "<td>$rest_h</td>";
8168
print "<td>$p_h %</td>";
8174
if ($HTMLOutput{'keyphrases'}) {
8175
print "$Center<a name=\"keyphrases\"> </a><br />\n";
8176
&tab_head($Message[43],19,0,'keyphrases');
8177
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(15);\" onmouseout=\"HideTip(15);\"":"")."><th>$TotalDifferentKeyphrases $Message[103]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[14]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[15]</th></tr>\n";
8180
&BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Keyphrase'},\%_keyphrases,\%_keyphrases);
8181
foreach my $key (@keylist) {
8183
# Convert coded keywords (utf8,...) to be correctly reported in HTML page.
8184
if ($PluginsLoaded{'DecodeKey'}{'decodeutfkeys'}) { $mot=CleanFromCSSA(DecodeKey_decodeutfkeys($key,$PageCode||'iso-8859-1')); }
8185
else { $mot = CleanFromCSSA(DecodeEncodedString($key)); }
8187
if ($TotalKeyphrases) { $p=int($_keyphrases{$key}/$TotalKeyphrases*1000)/10; }
8188
print "<tr><td class=\"aws\">".XMLEncode($mot)."</td><td>$_keyphrases{$key}</td><td>$p %</td></tr>\n";
8189
$total_s += $_keyphrases{$key};
8192
if ($Debug) { debug("Total real / shown : $TotalKeyphrases / $total_s",2); }
8193
$rest_s=$TotalKeyphrases-$total_s;
8196
if ($TotalKeyphrases) { $p=int($rest_s/$TotalKeyphrases*1000)/10; }
8197
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[124]</span></td><td>$rest_s</td>";
8198
print "<td>$p %</td></tr>\n";
8203
if ($HTMLOutput{'keywords'}) {
8204
print "$Center<a name=\"keywords\"> </a><br />\n";
8205
&tab_head($Message[44],19,0,'keywords');
8206
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(15);\" onmouseout=\"HideTip(15);\"":"")."><th>$TotalDifferentKeywords $Message[13]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[14]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[15]</th></tr>\n";
8209
&BuildKeyList($MaxRowsInHTMLOutput,$MinHit{'Keyword'},\%_keywords,\%_keywords);
8210
foreach my $key (@keylist) {
8212
# Convert coded keywords (utf8,...) to be correctly reported in HTML page.
8213
if ($PluginsLoaded{'DecodeKey'}{'decodeutfkeys'}) { $mot=CleanFromCSSA(DecodeKey_decodeutfkeys($key,$PageCode||'iso-8859-1')); }
8214
else { $mot = CleanFromCSSA(DecodeEncodedString($key)); }
8216
if ($TotalKeywords) { $p=int($_keywords{$key}/$TotalKeywords*1000)/10; }
8217
print "<tr><td class=\"aws\">".XMLEncode($mot)."</td><td>$_keywords{$key}</td><td>$p %</td></tr>\n";
8218
$total_s += $_keywords{$key};
8221
if ($Debug) { debug("Total real / shown : $TotalKeywords / $total_s",2); }
8222
$rest_s=$TotalKeywords-$total_s;
8225
if ($TotalKeywords) { $p=int($rest_s/$TotalKeywords*1000)/10; }
8226
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[30]</span></td><td>$rest_s</td>";
8227
print "<td>$p %</td></tr>\n";
8232
foreach my $code (keys %TrapInfosForHTTPErrorCodes) {
8233
if ($HTMLOutput{"errors$code"}) {
8234
print "$Center<a name=\"errors$code\"> </a><br />\n";
8235
&tab_head($Message[47],19,0,"errors$code");
8236
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>URL (".(scalar keys %_sider404_h).")</th><th bgcolor=\"#$color_h\">$Message[49]</th><th>$Message[23]</th></tr>\n";
8239
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_sider404_h,\%_sider404_h);
8240
foreach my $key (@keylist) {
8241
my $nompage=CleanFromCSSA($key);
8242
#if (length($nompage)>$MaxLengthOfShownURL) { $nompage=substr($nompage,0,$MaxLengthOfShownURL)."..."; }
8243
my $referer=CleanFromCSSA($_referer404_h{$key});
8244
print "<tr><td class=\"aws\">$nompage</td>";
8245
print "<td>$_sider404_h{$key}</td>";
8246
print "<td class=\"aws\">".($referer?"$referer":" ")."</td>";
8248
$total_s += $_sider404_h{$key};
8251
# TODO Build TotalErrorHits
8252
# if ($Debug) { debug("Total real / shown : $TotalErrorHits / $total_h",2); }
8253
# $rest_h=$TotalErrorHits-$total_h;
8254
# if ($rest_h > 0) {
8256
# if ($TotalErrorHits) { $p=int($rest_h/$TotalErrorHits*1000)/10; }
8257
# print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[30]</span></td>";
8258
# print "<td>$rest_h</td>";
8259
# print "<td>...</td>";
8266
if ($HTMLOutput{'info'}) {
8268
print "$Center<a name=\"info\"> </a><br />";
8271
if ($HTMLOutput{'main'}) {
8274
#---------------------------------------------------------------------
8275
if ($ShowMonthStats) {
8276
if ($Debug) { debug("ShowMonthStats",2); }
8277
my $title="$Message[128]";
8278
&tab_head("$title",0,0,'month');
8280
my $NewLinkParams=${QueryString};
8281
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
8282
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
8283
$NewLinkParams =~ s/(^|&)year=[^&]*//i;
8284
$NewLinkParams =~ s/(^|&)month=[^&]*//i;
8285
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
8286
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
8287
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
8288
my $NewLinkTarget='';
8289
if ($FrameName eq 'mainright') { $NewLinkTarget=" target=\"_parent\""; }
8292
my $RatioVisits=0; my $RatioPages=0; my $RatioHits=0; my $RatioBytes=0;
8293
if ($TotalUnique > 0) { $RatioVisits=int($TotalVisits/$TotalUnique*100)/100; }
8294
if ($TotalVisits > 0) { $RatioPages=int($TotalPages/$TotalVisits*100)/100; }
8295
if ($TotalVisits > 0) { $RatioHits=int($TotalHits/$TotalVisits*100)/100; }
8296
if ($TotalVisits > 0) { $RatioBytes=int(($TotalBytes/1024)*100/($LogType eq 'M'?$TotalHits:$TotalVisits))/100; }
8300
if ($LogType eq 'W' || $LogType eq 'S') { $w='17'; $colspan=6; }
8302
print "<tr bgcolor=\"#$color_TableBGRowTitle\">";
8303
if ($LogType eq 'W' || $LogType eq 'S') { print "<td> </td>"; }
8304
print "<td><b>$Message[8]</b></td>\n";
8305
print "<td colspan=\"3\">$Message[128]</td>";
8306
print "<td><b>$Message[9]</b></td></tr>\n";
8307
print "<tr bgcolor=\"#$color_TableBGRowTitle\">";
8308
if ($LogType eq 'W' || $LogType eq 'S') { print "<td> </td>"; }
8309
if ($FirstTime) { print "<td>".Format_Date($FirstTime,0)."</td>"; }
8310
else { print "<td>NA</td>"; }
8311
print "<td colspan=\"3\"><b>";
8312
print ($MonthRequired eq 'all'?"$Message[6] $YearRequired":"$Message[5] ".$MonthNumLib{$MonthRequired}." $YearRequired");
8314
if ($LastTime) { print "<td>".Format_Date($LastTime,0)."</td></tr>\n"; }
8315
else { print "<td>NA</td></tr>\n"; }
8316
# Show main indicators
8318
if ($LogType eq 'W' || $LogType eq 'S') { print "<td bgcolor=\"#$color_TableBGRowTitle\"> </td>"; }
8319
if ($ShowMonthStats =~ /U/i) { print "<td width=\"$w%\" bgcolor=\"#$color_u\"".($TOOLTIPON?" onmouseover=\"ShowTip(2);\" onmouseout=\"HideTip(2);\"":"").">$Message[11]</td>"; } else { print "<td width=\"20%\"> </td>"; }
8320
if ($ShowMonthStats =~ /V/i) { print "<td width=\"$w%\" bgcolor=\"#$color_v\"".($TOOLTIPON?" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\"":"").">$Message[10]</td>"; } else { print "<td width=\"20%\"> </td>"; }
8321
if ($ShowMonthStats =~ /P/i) { print "<td width=\"$w%\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; } else { print "<td width=\"20%\"> </td>"; }
8322
if ($ShowMonthStats =~ /H/i) { print "<td width=\"$w%\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; } else { print "<td width=\"20%\"> </td>"; }
8323
if ($ShowMonthStats =~ /B/i) { print "<td width=\"$w%\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td>"; } else { print "<td width=\"20%\"> </td>"; }
8326
if ($LogType eq 'W' || $LogType eq 'S') { $w='17'; print "<td class=\"aws\">$Message[160] *</td>"; }
8327
if ($ShowMonthStats =~ /U/i) { print "<td>".($MonthRequired eq 'all'?"<b><= $TotalUnique</b><br />$Message[129]":"<b>$TotalUnique</b><br /> ")."</td>"; } else { print "<td> </td>"; }
8328
if ($ShowMonthStats =~ /V/i) { print "<td><b>$TotalVisits</b><br />($RatioVisits $Message[52])</td>"; } else { print "<td> </td>"; }
8329
if ($ShowMonthStats =~ /P/i) { print "<td><b>$TotalPages</b><br />($RatioPages ".lc($Message[56]."/".$Message[12]).")</td>"; } else { print "<td> </td>"; }
8330
if ($ShowMonthStats =~ /H/i) { print "<td><b>$TotalHits</b>".($LogType eq 'M'?"":"<br />($RatioHits ".lc($Message[57]."/".$Message[12]).")</td>"); } else { print "<td> </td>"; }
8331
if ($ShowMonthStats =~ /B/i) { print "<td><b>".Format_Bytes(int($TotalBytes))."</b><br />($RatioBytes $Message[108]/".lc($Message[($LogType eq 'M'?149:12)]).")</td>"; } else { print "<td> </td>"; }
8334
if ($LogType eq 'W' || $LogType eq 'S') {
8335
print "<td class=\"aws\">$Message[161] *</td>";
8336
print "<td colspan=2> <br> </td>\n";
8337
if ($ShowMonthStats =~ /P/i) { print "<td><b>$TotalNotViewedPages</b></td>"; } else { print "<td> </td>"; }
8338
if ($ShowMonthStats =~ /H/i) { print "<td><b>$TotalNotViewedHits</b></td>"; } else { print "<td> </td>"; }
8339
if ($ShowMonthStats =~ /B/i) { print "<td><b>".Format_Bytes(int($TotalNotViewedBytes))."</b></td>"; } else { print "<td> </td>"; }
8342
&tab_end($LogType eq 'W' || $LogType eq 'S'?"* $Message[159]":"");
8345
#---------------------------------------------------------------------
8346
if ($ShowMonthStats) {
8348
if ($Debug) { debug("ShowMonthStats",2); }
8349
print "$Center<a name=\"month\"> </a><br />\n";
8350
my $title="$Message[162]";
8351
&tab_head("$title",0,0,'month');
8352
print "<tr><td align=\"center\">\n";
8355
$average_nb=$average_u=$average_v=$average_p=$average_h=$average_k=0;
8356
$total_u=$total_v=$total_p=$total_h=$total_k=0;
8358
$max_v=$max_p=$max_h=$max_k=1;
8359
# Define total and max
8360
for (my $ix=1; $ix<=12; $ix++) {
8361
my $monthix=sprintf("%02s",$ix);
8362
$total_u+=$MonthUnique{$YearRequired.$monthix}||0;
8363
$total_v+=$MonthVisits{$YearRequired.$monthix}||0;
8364
$total_p+=$MonthPages{$YearRequired.$monthix}||0;
8365
$total_h+=$MonthHits{$YearRequired.$monthix}||0;
8366
$total_k+=$MonthBytes{$YearRequired.$monthix}||0;
8367
#if (($MonthUnique{$YearRequired.$monthix}||0) > $max_v) { $max_v=$MonthUnique{$YearRequired.$monthix}; }
8368
if (($MonthVisits{$YearRequired.$monthix}||0) > $max_v) { $max_v=$MonthVisits{$YearRequired.$monthix}; }
8369
#if (($MonthPages{$YearRequired.$monthix}||0) > $max_p) { $max_p=$MonthPages{$YearRequired.$monthix}; }
8370
if (($MonthHits{$YearRequired.$monthix}||0) > $max_h) { $max_h=$MonthHits{$YearRequired.$monthix}; }
8371
if (($MonthBytes{$YearRequired.$monthix}||0) > $max_k) { $max_k=$MonthBytes{$YearRequired.$monthix}; }
8376
# Show bars for month
8377
if ($PluginsLoaded{'ShowGraph'}{'graphapplet'}) {
8379
for (my $ix=1; $ix<=12; $ix++) {
8380
my $monthix=sprintf("%02s",$ix);
8381
push @blocklabel,"$MonthNumLib{$monthix}ļæ½$YearRequired";
8383
my @vallabel=("$Message[11]","$Message[10]","$Message[56]","$Message[57]","$Message[75]");
8384
my @valcolor=("$color_u","$color_v","$color_p","$color_h","$color_k");
8385
my @valmax=($max_v,$max_v,$max_h,$max_h,$max_k);
8386
my @valtotal=($total_u,$total_v,$total_p,$total_h,$total_k);
8388
#my @valaverage=($average_v,$average_p,$average_h,$average_k);
8391
for (my $ix=1; $ix<=12; $ix++) {
8392
my $monthix=sprintf("%02s",$ix);
8393
$valdata[$xx++]=$MonthUnique{$YearRequired.$monthix}||0;
8394
$valdata[$xx++]=$MonthVisits{$YearRequired.$monthix}||0;
8395
$valdata[$xx++]=$MonthPages{$YearRequired.$monthix}||0;
8396
$valdata[$xx++]=$MonthHits{$YearRequired.$monthix}||0;
8397
$valdata[$xx++]=$MonthBytes{$YearRequired.$monthix}||0;
8399
ShowGraph_graphapplet("$title","month",$ShowMonthStats,\@blocklabel,\@vallabel,\@valcolor,\@valmax,\@valtotal,\@valaverage,\@valdata);
8403
print "<tr valign=\"bottom\">";
8404
print "<td> </td>\n";
8405
for (my $ix=1; $ix<=12; $ix++) {
8406
my $monthix=sprintf("%02s",$ix);
8407
my $bredde_u=0; my $bredde_v=0;my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
8408
if ($max_v > 0) { $bredde_u=int(($MonthUnique{$YearRequired.$monthix}||0)/$max_v*$BarHeight)+1; }
8409
if ($max_v > 0) { $bredde_v=int(($MonthVisits{$YearRequired.$monthix}||0)/$max_v*$BarHeight)+1; }
8410
if ($max_h > 0) { $bredde_p=int(($MonthPages{$YearRequired.$monthix}||0)/$max_h*$BarHeight)+1; }
8411
if ($max_h > 0) { $bredde_h=int(($MonthHits{$YearRequired.$monthix}||0)/$max_h*$BarHeight)+1; }
8412
if ($max_k > 0) { $bredde_k=int(($MonthBytes{$YearRequired.$monthix}||0)/$max_k*$BarHeight)+1; }
8414
if ($ShowMonthStats =~ /U/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vu'}\" height=\"$bredde_u\" width=\"6\"".AltTitle("$Message[11]: ".($MonthUnique{$YearRequired.$monthix}||0))." />"; }
8415
if ($ShowMonthStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"6\"".AltTitle("$Message[10]: ".($MonthVisits{$YearRequired.$monthix}||0))." />"; }
8416
if ($QueryString !~ /buildpdf/i) { print " "; }
8417
if ($ShowMonthStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"6\"".AltTitle("$Message[56]: ".($MonthPages{$YearRequired.$monthix}||0))." />"; }
8418
if ($ShowMonthStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"6\"".AltTitle("$Message[57]: ".($MonthHits{$YearRequired.$monthix}||0))." />"; }
8419
if ($ShowMonthStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"6\"".AltTitle("$Message[75]: ".Format_Bytes($MonthBytes{$YearRequired.$monthix}))." />"; }
8422
print "<td> </td>";
8424
# Show lib for month
8425
print "<tr valign=\"middle\">";
8426
# if ($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) {
8427
# print "<td><a href=\"".XMLEncode("$AWScript?${NewLinkParams}month=12&year=".($YearRequired-1))."\"><<</a></td>";
8430
print "<td> </td>";
8432
for (my $ix=1; $ix<=12; $ix++) {
8433
my $monthix=sprintf("%02s",$ix);
8434
# if ($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) {
8435
# print "<td><a href=\"".XMLEncode("$AWScript?${NewLinkParams}month=$monthix&year=$YearRequired")."\">$MonthNumLib{$monthix}<br />$YearRequired</a></td>";
8438
print "<td>$MonthNumLib{$monthix}<br />$YearRequired</td>";
8441
# if ($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks) {
8442
# print "<td><a href=\"".XMLEncode("$AWScript?${NewLinkParams}month=1&year=".($YearRequired+1))."\">>></a></td>";
8445
print "<td> </td>";
8452
# Show data array for month
8453
if ($AddDataArrayMonthStats) {
8455
print "<tr><td width=\"80\" bgcolor=\"#$color_TableBGRowTitle\">$Message[5]</td>";
8456
if ($ShowMonthStats =~ /U/i) { print "<td width=\"80\" bgcolor=\"#$color_u\"".($TOOLTIPON?" onmouseover=\"ShowTip(2);\" onmouseout=\"HideTip(2);\"":"").">$Message[11]</td>"; }
8457
if ($ShowMonthStats =~ /V/i) { print "<td width=\"80\" bgcolor=\"#$color_v\"".($TOOLTIPON?" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\"":"").">$Message[10]</td>"; }
8458
if ($ShowMonthStats =~ /P/i) { print "<td width=\"80\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
8459
if ($ShowMonthStats =~ /H/i) { print "<td width=\"80\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
8460
if ($ShowMonthStats =~ /B/i) { print "<td width=\"80\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td>"; }
8462
for (my $ix=1; $ix<=12; $ix++) {
8463
my $monthix=sprintf("%02s",$ix);
8465
print "<td>$MonthNumLib{$monthix} $YearRequired</td>";
8466
if ($ShowMonthStats =~ /U/i) { print "<td>",$MonthUnique{$YearRequired.$monthix}?$MonthUnique{$YearRequired.$monthix}:"0","</td>"; }
8467
if ($ShowMonthStats =~ /V/i) { print "<td>",$MonthVisits{$YearRequired.$monthix}?$MonthVisits{$YearRequired.$monthix}:"0","</td>"; }
8468
if ($ShowMonthStats =~ /P/i) { print "<td>",$MonthPages{$YearRequired.$monthix}?$MonthPages{$YearRequired.$monthix}:"0","</td>"; }
8469
if ($ShowMonthStats =~ /H/i) { print "<td>",$MonthHits{$YearRequired.$monthix}?$MonthHits{$YearRequired.$monthix}:"0","</td>"; }
8470
if ($ShowMonthStats =~ /B/i) { print "<td>",Format_Bytes(int($MonthBytes{$YearRequired.$monthix}||0)),"</td>"; }
8476
print "<tr><td bgcolor=\"#$color_TableBGRowTitle\">$Message[102]</td>";
8477
if ($ShowMonthStats =~ /U/i) { print "<td bgcolor=\"#$color_TableBGRowTitle\">$total_u</td>"; }
8478
if ($ShowMonthStats =~ /V/i) { print "<td bgcolor=\"#$color_TableBGRowTitle\">$total_v</td>"; }
8479
if ($ShowMonthStats =~ /P/i) { print "<td bgcolor=\"#$color_TableBGRowTitle\">$total_p</td>"; }
8480
if ($ShowMonthStats =~ /H/i) { print "<td bgcolor=\"#$color_TableBGRowTitle\">$total_h</td>"; }
8481
if ($ShowMonthStats =~ /B/i) { print "<td bgcolor=\"#$color_TableBGRowTitle\">".Format_Bytes($total_k)."</td>"; }
8483
print "</table>\n<br />\n";
8486
print "</center>\n";
8487
print "</td></tr>\n";
8492
print "\n<a name=\"when\"> </a>\n\n";
8495
#---------------------------------------------------------------------
8496
if ($ShowDaysOfMonthStats) {
8497
if ($Debug) { debug("ShowDaysOfMonthStats",2); }
8498
print "$Center<a name=\"daysofmonth\"> </a><br />\n";
8499
my $title="$Message[138]";
8500
&tab_head("$title",0,0,'daysofmonth');
8502
print "<td align=\"center\">\n";
8505
my $NewLinkParams=${QueryString};
8506
$NewLinkParams =~ s/(^|&)update(=\w*|$)//i;
8507
$NewLinkParams =~ s/(^|&)staticlinks(=\w*|$)//i;
8508
$NewLinkParams =~ s/(^|&)year=[^&]*//i;
8509
$NewLinkParams =~ s/(^|&)month=[^&]*//i;
8510
$NewLinkParams =~ s/(^|&)framename=[^&]*//i;
8511
$NewLinkParams =~ tr/&/&/s; $NewLinkParams =~ s/^&//; $NewLinkParams =~ s/&$//;
8512
if ($NewLinkParams) { $NewLinkParams="${NewLinkParams}&"; }
8513
my $NewLinkTarget='';
8514
if ($FrameName eq 'mainright') { $NewLinkTarget=" target=\"_parent\""; }
8516
$average_nb=$average_u=$average_v=$average_p=$average_h=$average_k=0;
8517
$total_u=$total_v=$total_p=$total_h=$total_k=0;
8518
# Define total and max
8519
$max_v=$max_h=$max_k=0; # Start from 0 because can be lower than 1
8520
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8521
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8522
my $year=$1; my $month=$2; my $day=$3;
8523
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8524
$total_v+=$DayVisits{$year.$month.$day}||0;
8525
$total_p+=$DayPages{$year.$month.$day}||0;
8526
$total_h+=$DayHits{$year.$month.$day}||0;
8527
$total_k+=$DayBytes{$year.$month.$day}||0;
8528
if (($DayVisits{$year.$month.$day}||0) > $max_v) { $max_v=$DayVisits{$year.$month.$day}; }
8529
#if (($DayPages{$year.$month.$day}||0) > $max_p) { $max_p=$DayPages{$year.$month.$day}; }
8530
if (($DayHits{$year.$month.$day}||0) > $max_h) { $max_h=$DayHits{$year.$month.$day}; }
8531
if (($DayBytes{$year.$month.$day}||0) > $max_k) { $max_k=$DayBytes{$year.$month.$day}; }
8534
foreach my $daycursor ($firstdaytocountaverage..$lastdaytocountaverage) {
8535
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8536
my $year=$1; my $month=$2; my $day=$3;
8537
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8538
$average_nb++; # Increase number of day used to count
8539
$average_v+=($DayVisits{$daycursor}||0);
8540
$average_p+=($DayPages{$daycursor}||0);
8541
$average_h+=($DayHits{$daycursor}||0);
8542
$average_k+=($DayBytes{$daycursor}||0);
8545
$average_v=$average_v/$average_nb;
8546
$average_p=$average_p/$average_nb;
8547
$average_h=$average_h/$average_nb;
8548
$average_k=$average_k/$average_nb;
8549
if ($average_v > $max_v) { $max_v=$average_v; }
8550
#if ($average_p > $max_p) { $max_p=$average_p; }
8551
if ($average_h > $max_h) { $max_h=$average_h; }
8552
if ($average_k > $max_k) { $max_k=$average_k; }
8562
if ($PluginsLoaded{'ShowGraph'}{'graphapplet'}) {
8564
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8565
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8566
my $year=$1; my $month=$2; my $day=$3;
8567
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8568
my $bold=($day==$nowday && $month==$nowmonth && $year==$nowyear?':':'');
8569
my $weekend=(DayOfWeek($day,$month,$year)=~/[06]/?'!':'');
8570
push @blocklabel,"$dayļæ½$MonthNumLib{$month}$weekend$bold";
8572
my @vallabel=("$Message[10]","$Message[56]","$Message[57]","$Message[75]");
8573
my @valcolor=("$color_v","$color_p","$color_h","$color_k");
8574
my @valmax=($max_v,$max_h,$max_h,$max_k);
8575
my @valtotal=($total_v,$total_p,$total_h,$total_k);
8576
$average_v=sprintf("%.2f",$average_v);
8577
$average_p=sprintf("%.2f",$average_p);
8578
$average_h=sprintf("%.2f",$average_h);
8579
$average_k=(int($average_k)?Format_Bytes(sprintf("%.2f",$average_k)):"0.00");
8580
my @valaverage=($average_v,$average_p,$average_h,$average_k);
8583
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8584
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8585
my $year=$1; my $month=$2; my $day=$3;
8586
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8587
$valdata[$xx++]=$DayVisits{$year.$month.$day}||0;
8588
$valdata[$xx++]=$DayPages{$year.$month.$day}||0;
8589
$valdata[$xx++]=$DayHits{$year.$month.$day}||0;
8590
$valdata[$xx++]=$DayBytes{$year.$month.$day}||0;
8592
ShowGraph_graphapplet("$title","daysofmonth",$ShowDaysOfMonthStats,\@blocklabel,\@vallabel,\@valcolor,\@valmax,\@valtotal,\@valaverage,\@valdata);
8596
print "<tr valign=\"bottom\">\n";
8597
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8598
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8599
my $year=$1; my $month=$2; my $day=$3;
8600
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8601
my $bredde_v=0; my $bredde_p=0; my $bredde_h=0; my $bredde_k=0;
8602
if ($max_v > 0) { $bredde_v=int(($DayVisits{$year.$month.$day}||0)/$max_v*$BarHeight)+1; }
8603
if ($max_h > 0) { $bredde_p=int(($DayPages{$year.$month.$day}||0)/$max_h*$BarHeight)+1; }
8604
if ($max_h > 0) { $bredde_h=int(($DayHits{$year.$month.$day}||0)/$max_h*$BarHeight)+1; }
8605
if ($max_k > 0) { $bredde_k=int(($DayBytes{$year.$month.$day}||0)/$max_k*$BarHeight)+1; }
8607
if ($ShowDaysOfMonthStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"4\"".AltTitle("$Message[10]: ".int($DayVisits{$year.$month.$day}||0))." />"; }
8608
if ($ShowDaysOfMonthStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"4\"".AltTitle("$Message[56]: ".int($DayPages{$year.$month.$day}||0))." />"; }
8609
if ($ShowDaysOfMonthStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"4\"".AltTitle("$Message[57]: ".int($DayHits{$year.$month.$day}||0))." />"; }
8610
if ($ShowDaysOfMonthStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"4\"".AltTitle("$Message[75]: ".Format_Bytes($DayBytes{$year.$month.$day}))." />"; }
8613
print "<td> </td>";
8614
# Show average value cell
8616
my $bredde_v=0; my $bredde_p=0; my $bredde_h=0; my $bredde_k=0;
8617
if ($max_v > 0) { $bredde_v=int($average_v/$max_v*$BarHeight)+1; }
8618
if ($max_h > 0) { $bredde_p=int($average_p/$max_h*$BarHeight)+1; }
8619
if ($max_h > 0) { $bredde_h=int($average_h/$max_h*$BarHeight)+1; }
8620
if ($max_k > 0) { $bredde_k=int($average_k/$max_k*$BarHeight)+1; }
8621
$average_v=sprintf("%.2f",$average_v);
8622
$average_p=sprintf("%.2f",$average_p);
8623
$average_h=sprintf("%.2f",$average_h);
8624
$average_k=(int($average_k)?Format_Bytes(sprintf("%.2f",$average_k)):"0.00");
8625
if ($ShowDaysOfMonthStats =~ /V/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vv'}\" height=\"$bredde_v\" width=\"4\"".AltTitle("$Message[10]: $average_v")." />"; }
8626
if ($ShowDaysOfMonthStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"4\"".AltTitle("$Message[56]: $average_p")." />"; }
8627
if ($ShowDaysOfMonthStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"4\"".AltTitle("$Message[57]: $average_h")." />"; }
8628
if ($ShowDaysOfMonthStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"4\"".AltTitle("$Message[75]: $average_k")." />"; }
8632
print "<tr valign=\"middle\">";
8633
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8634
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8635
my $year=$1; my $month=$2; my $day=$3;
8636
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8637
my $dayofweekcursor=DayOfWeek($day,$month,$year);
8638
print "<td".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">";
8639
print ($day==$nowday && $month==$nowmonth && $year==$nowyear?'<b>':'');
8640
print "$day<br /><span style=\"font-size: ".($FrameName ne 'mainright' && $QueryString !~ /buildpdf/i?"9":"8")."px;\">".$MonthNumLib{$month}."</span>";
8641
print ($day==$nowday && $month==$nowmonth && $year==$nowyear?'</b>':'');
8644
print "<td> </td>";
8645
print "<td valign=\"middle\"".($TOOLTIPON?" onmouseover=\"ShowTip(18);\" onmouseout=\"HideTip(18);\"":"").">$Message[96]</td>\n";
8651
# Show data array for days
8652
if ($AddDataArrayShowDaysOfMonthStats) {
8654
print "<tr><td width=\"80\" bgcolor=\"#$color_TableBGRowTitle\">$Message[4]</td>";
8655
if ($ShowDaysOfMonthStats =~ /V/i) { print "<td width=\"80\" bgcolor=\"#$color_v\"".($TOOLTIPON?" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\"":"").">$Message[10]</td>"; }
8656
if ($ShowDaysOfMonthStats =~ /P/i) { print "<td width=\"80\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
8657
if ($ShowDaysOfMonthStats =~ /H/i) { print "<td width=\"80\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
8658
if ($ShowDaysOfMonthStats =~ /B/i) { print "<td width=\"80\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td></tr>"; }
8659
foreach my $daycursor ($firstdaytoshowtime..$lastdaytoshowtime) {
8660
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8661
my $year=$1; my $month=$2; my $day=$3;
8662
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8663
my $dayofweekcursor=DayOfWeek($day,$month,$year);
8664
print "<tr".($dayofweekcursor=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">";
8665
print "<td>",Format_Date("$year$month$day"."000000",2),"</td>";
8666
if ($ShowDaysOfMonthStats =~ /V/i) { print "<td>",$DayVisits{$year.$month.$day}?$DayVisits{$year.$month.$day}:"0","</td>"; }
8667
if ($ShowDaysOfMonthStats =~ /P/i) { print "<td>",$DayPages{$year.$month.$day}?$DayPages{$year.$month.$day}:"0","</td>"; }
8668
if ($ShowDaysOfMonthStats =~ /H/i) { print "<td>",$DayHits{$year.$month.$day}?$DayHits{$year.$month.$day}:"0","</td>"; }
8669
if ($ShowDaysOfMonthStats =~ /B/i) { print "<td>",Format_Bytes(int($DayBytes{$year.$month.$day}||0)),"</td>"; }
8673
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><td>$Message[96]</td>";
8674
if ($ShowDaysOfMonthStats =~ /V/i) { print "<td>$average_v</td>"; }
8675
if ($ShowDaysOfMonthStats =~ /P/i) { print "<td>$average_p</td>"; }
8676
if ($ShowDaysOfMonthStats =~ /H/i) { print "<td>$average_h</td>"; }
8677
if ($ShowDaysOfMonthStats =~ /B/i) { print "<td>$average_k</td>"; }
8680
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><td>$Message[102]</td>";
8681
if ($ShowDaysOfMonthStats =~ /V/i) { print "<td>$total_v</td>"; }
8682
if ($ShowDaysOfMonthStats =~ /P/i) { print "<td>$total_p</td>"; }
8683
if ($ShowDaysOfMonthStats =~ /H/i) { print "<td>$total_h</td>"; }
8684
if ($ShowDaysOfMonthStats =~ /B/i) { print "<td>".Format_Bytes($total_k)."</td>"; }
8686
print "</table>\n<br />";
8689
print "</center>\n";
8690
print "</td></tr>\n";
8695
#-------------------------
8696
if ($ShowDaysOfWeekStats) {
8697
if ($Debug) { debug("ShowDaysOfWeekStats",2); }
8698
print "$Center<a name=\"daysofweek\"> </a><br />\n";
8699
my $title="$Message[91]";
8700
&tab_head("$title",18,0,'daysofweek');
8702
print "<td align=\"center\">";
8705
$max_h=$max_k=0; # Start from 0 because can be lower than 1
8706
# Get average value for day of week
8707
my @avg_dayofweek_nb = my @avg_dayofweek_p = my @avg_dayofweek_h = my @avg_dayofweek_k = ();
8708
foreach my $daycursor ($firstdaytocountaverage..$lastdaytocountaverage) {
8709
$daycursor =~ /^(\d\d\d\d)(\d\d)(\d\d)/;
8710
my $year=$1; my $month=$2; my $day=$3;
8711
if (! DateIsValid($day,$month,$year)) { next; } # If not an existing day, go to next
8712
my $dayofweekcursor=DayOfWeek($day,$month,$year);
8713
$avg_dayofweek_nb[$dayofweekcursor]++; # Increase number of day used to count for this day of week
8714
$avg_dayofweek_p[$dayofweekcursor]+=($DayPages{$daycursor}||0);
8715
$avg_dayofweek_h[$dayofweekcursor]+=($DayHits{$daycursor}||0);
8716
$avg_dayofweek_k[$dayofweekcursor]+=($DayBytes{$daycursor}||0);
8719
if ($avg_dayofweek_nb[$_]) {
8720
$avg_dayofweek_p[$_]=$avg_dayofweek_p[$_]/$avg_dayofweek_nb[$_];
8721
$avg_dayofweek_h[$_]=$avg_dayofweek_h[$_]/$avg_dayofweek_nb[$_];
8722
$avg_dayofweek_k[$_]=$avg_dayofweek_k[$_]/$avg_dayofweek_nb[$_];
8723
#if ($avg_dayofweek_p[$_] > $max_p) { $max_p = $avg_dayofweek_p[$_]; }
8724
if ($avg_dayofweek_h[$_] > $max_h) { $max_h = $avg_dayofweek_h[$_]; }
8725
if ($avg_dayofweek_k[$_] > $max_k) { $max_k = $avg_dayofweek_k[$_]; }
8728
$avg_dayofweek_p[$_]="?";
8729
$avg_dayofweek_h[$_]="?";
8730
$avg_dayofweek_k[$_]="?";
8734
# Show bars for days of week
8735
if ($PluginsLoaded{'ShowGraph'}{'graphapplet'}) {
8737
for (@DOWIndex) { push @blocklabel,($Message[$_+84].($_=~/[06]/?"!":"")); }
8738
my @vallabel=("$Message[56]","$Message[57]","$Message[75]");
8739
my @valcolor=("$color_p","$color_h","$color_k");
8740
my @valmax=(int($max_h),int($max_h),int($max_k));
8741
my @valtotal=($total_p,$total_h,$total_k);
8742
$average_p=sprintf("%.2f",$average_p);
8743
$average_h=sprintf("%.2f",$average_h);
8744
$average_k=(int($average_k)?Format_Bytes(sprintf("%.2f",$average_k)):"0.00");
8745
my @valaverage=($average_p,$average_h,$average_k);
8749
$valdata[$xx++]=$avg_dayofweek_p[$_]||0;
8750
$valdata[$xx++]=$avg_dayofweek_h[$_]||0;
8751
$valdata[$xx++]=$avg_dayofweek_k[$_]||0;
8752
# Round to be ready to show array
8753
$avg_dayofweek_p[$_]=sprintf("%.2f",$avg_dayofweek_p[$_]);
8754
$avg_dayofweek_h[$_]=sprintf("%.2f",$avg_dayofweek_h[$_]);
8755
$avg_dayofweek_k[$_]=sprintf("%.2f",$avg_dayofweek_k[$_]);
8756
# Remove decimal part that are .0
8757
if ($avg_dayofweek_p[$_] == int($avg_dayofweek_p[$_])) { $avg_dayofweek_p[$_]=int($avg_dayofweek_p[$_]); }
8758
if ($avg_dayofweek_h[$_] == int($avg_dayofweek_h[$_])) { $avg_dayofweek_h[$_]=int($avg_dayofweek_h[$_]); }
8760
ShowGraph_graphapplet("$title","daysofweek",$ShowDaysOfWeekStats,\@blocklabel,\@vallabel,\@valcolor,\@valmax,\@valtotal,\@valaverage,\@valdata);
8764
print "<tr valign=\"bottom\">\n";
8766
my $bredde_p=0; my $bredde_h=0; my $bredde_k=0;
8767
if ($max_h > 0) { $bredde_p=int($avg_dayofweek_p[$_]/$max_h*$BarHeight)+1; }
8768
if ($max_h > 0) { $bredde_h=int($avg_dayofweek_h[$_]/$max_h*$BarHeight)+1; }
8769
if ($max_k > 0) { $bredde_k=int($avg_dayofweek_k[$_]/$max_k*$BarHeight)+1; }
8770
$avg_dayofweek_p[$_]=sprintf("%.2f",$avg_dayofweek_p[$_]);
8771
$avg_dayofweek_h[$_]=sprintf("%.2f",$avg_dayofweek_h[$_]);
8772
$avg_dayofweek_k[$_]=sprintf("%.2f",$avg_dayofweek_k[$_]);
8773
# Remove decimal part that are .0
8774
if ($avg_dayofweek_p[$_] == int($avg_dayofweek_p[$_])) { $avg_dayofweek_p[$_]=int($avg_dayofweek_p[$_]); }
8775
if ($avg_dayofweek_h[$_] == int($avg_dayofweek_h[$_])) { $avg_dayofweek_h[$_]=int($avg_dayofweek_h[$_]); }
8776
print "<td valign=\"bottom\">";
8777
if ($ShowDaysOfWeekStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"6\"".AltTitle("$Message[56]: $avg_dayofweek_p[$_]")." />"; }
8778
if ($ShowDaysOfWeekStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"6\"".AltTitle("$Message[57]: $avg_dayofweek_h[$_]")." />"; }
8779
if ($ShowDaysOfWeekStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"6\"".AltTitle("$Message[75]: ".Format_Bytes($avg_dayofweek_k[$_]))." />"; }
8783
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(17);\" onmouseout=\"HideTip(17);\"":"").">\n";
8785
print "<td".($_=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">".$Message[$_+84]."</td>";
8787
print "</tr>\n</table>\n";
8791
# Show data array for days of week
8792
if ($AddDataArrayShowDaysOfWeekStats) {
8794
print "<tr><td width=\"80\" bgcolor=\"#$color_TableBGRowTitle\">$Message[4]</td>";
8795
if ($ShowDaysOfWeekStats =~ /P/i) { print "<td width=\"80\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
8796
if ($ShowDaysOfWeekStats =~ /H/i) { print "<td width=\"80\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
8797
if ($ShowDaysOfWeekStats =~ /B/i) { print "<td width=\"80\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td></tr>"; }
8799
print "<tr".($_=~/[06]/?" bgcolor=\"#$color_weekend\"":"").">";
8800
print "<td>".$Message[$_+84]."</td>";
8801
if ($ShowDaysOfWeekStats =~ /P/i) { print "<td>",$avg_dayofweek_p[$_],"</td>"; }
8802
if ($ShowDaysOfWeekStats =~ /H/i) { print "<td>",$avg_dayofweek_h[$_],"</td>"; }
8803
if ($ShowDaysOfWeekStats =~ /B/i) { print "<td>",Format_Bytes($avg_dayofweek_k[$_]),"</td>"; }
8806
print "</table>\n<br />\n";
8809
print "</center></td>";
8815
#----------------------------
8816
if ($ShowHoursStats) {
8817
if ($Debug) { debug("ShowHoursStats",2); }
8818
print "$Center<a name=\"hours\"> </a><br />\n";
8819
my $title="$Message[20]";
8820
if ($PluginsLoaded{'GetTimeZoneTitle'}{'timezone'}) { $title.=" (GMT ".(GetTimeZoneTitle_timezone()>=0?"+":"").int(GetTimeZoneTitle_timezone()).")"; }
8821
&tab_head("$title",19,0,'hours');
8822
print "<tr><td align=\"center\">\n";
8826
for (my $ix=0; $ix<=23; $ix++) {
8827
#if ($_time_p[$ix]>$max_p) { $max_p=$_time_p[$ix]; }
8828
if ($_time_h[$ix]>$max_h) { $max_h=$_time_h[$ix]; }
8829
if ($_time_k[$ix]>$max_k) { $max_k=$_time_k[$ix]; }
8832
# Show bars for hour
8833
if ($PluginsLoaded{'ShowGraph'}{'graphapplet'}) {
8834
my @blocklabel=(0..23);
8835
my @vallabel=("$Message[56]","$Message[57]","$Message[75]");
8836
my @valcolor=("$color_p","$color_h","$color_k");
8837
my @valmax=(int($max_h),int($max_h),int($max_k));
8838
my @valtotal=($total_p,$total_h,$total_k);
8839
my @valaverage=($average_p,$average_h,$average_k);
8843
$valdata[$xx++]=$_time_p[$_]||0;
8844
$valdata[$xx++]=$_time_h[$_]||0;
8845
$valdata[$xx++]=$_time_k[$_]||0;
8847
ShowGraph_graphapplet("$title","hours",$ShowHoursStats,\@blocklabel,\@vallabel,\@valcolor,\@valmax,\@valtotal,\@valaverage,\@valdata);
8851
print "<tr valign=\"bottom\">\n";
8852
for (my $ix=0; $ix<=23; $ix++) {
8853
my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
8854
if ($max_h > 0) { $bredde_p=int($BarHeight*$_time_p[$ix]/$max_h)+1; }
8855
if ($max_h > 0) { $bredde_h=int($BarHeight*$_time_h[$ix]/$max_h)+1; }
8856
if ($max_k > 0) { $bredde_k=int($BarHeight*$_time_k[$ix]/$max_k)+1; }
8858
if ($ShowHoursStats =~ /P/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vp'}\" height=\"$bredde_p\" width=\"6\"".AltTitle("$Message[56]: ".int($_time_p[$ix]))." />"; }
8859
if ($ShowHoursStats =~ /H/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vh'}\" height=\"$bredde_h\" width=\"6\"".AltTitle("$Message[57]: ".int($_time_h[$ix]))." />"; }
8860
if ($ShowHoursStats =~ /B/i) { print "<img align=\"bottom\" src=\"$DirIcons\/other\/$BarPng{'vk'}\" height=\"$bredde_k\" width=\"6\"".AltTitle("$Message[75]: ".Format_Bytes($_time_k[$ix]))." />"; }
8865
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(17);\" onmouseout=\"HideTip(17);\"":"").">";
8866
for (my $ix=0; $ix<=23; $ix++) {
8867
print "<th width=\"19\">$ix</th>\n"; # width=19 instead of 18 to avoid a MacOS browser bug.
8871
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(17);\" onmouseout=\"HideTip(17);\"":"").">\n";
8872
for (my $ix=0; $ix<=23; $ix++) {
8873
my $hrs=($ix>=12?$ix-12:$ix);
8874
my $hre=($ix>=12?$ix-11:$ix+1);
8875
my $apm=($ix>=12?"pm":"am");
8876
print "<td><img src=\"$DirIcons\/clock\/hr$hre.png\" width=\"10\" alt=\"$hrs:00 - $hre:00 $apm\" /></td>\n";
8883
# Show data array for hours
8884
if ($AddDataArrayShowHoursStats) {
8885
print "<table width=\"650\"><tr>\n";
8886
print "<td align=\"center\"><center>\n";
8889
print "<tr><td width=\"80\" bgcolor=\"#$color_TableBGRowTitle\">$Message[20]</td>";
8890
if ($ShowHoursStats =~ /P/i) { print "<td width=\"80\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
8891
if ($ShowHoursStats =~ /H/i) { print "<td width=\"80\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
8892
if ($ShowHoursStats =~ /B/i) { print "<td width=\"80\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td>"; }
8894
for (my $ix=0; $ix<=11; $ix++) {
8895
my $monthix=($ix<10?"0$ix":"$ix");
8897
print "<td>$monthix</td>";
8898
if ($ShowHoursStats =~ /P/i) { print "<td>",$_time_p[$monthix]?$_time_p[$monthix]:"0","</td>"; }
8899
if ($ShowHoursStats =~ /H/i) { print "<td>",$_time_h[$monthix]?$_time_h[$monthix]:"0","</td>"; }
8900
if ($ShowHoursStats =~ /B/i) { print "<td>",Format_Bytes(int($_time_k[$monthix])),"</td>"; }
8905
print "</center></td>";
8906
print "<td width=\"10\"> </td>";
8907
print "<td align=\"center\"><center>\n";
8910
print "<tr><td width=\"80\" bgcolor=\"#$color_TableBGRowTitle\">$Message[20]</td>";
8911
if ($ShowHoursStats =~ /P/i) { print "<td width=\"80\" bgcolor=\"#$color_p\"".($TOOLTIPON?" onmouseover=\"ShowTip(3);\" onmouseout=\"HideTip(3);\"":"").">$Message[56]</td>"; }
8912
if ($ShowHoursStats =~ /H/i) { print "<td width=\"80\" bgcolor=\"#$color_h\"".($TOOLTIPON?" onmouseover=\"ShowTip(4);\" onmouseout=\"HideTip(4);\"":"").">$Message[57]</td>"; }
8913
if ($ShowHoursStats =~ /B/i) { print "<td width=\"80\" bgcolor=\"#$color_k\"".($TOOLTIPON?" onmouseover=\"ShowTip(5);\" onmouseout=\"HideTip(5);\"":"").">$Message[75]</td>"; }
8915
for (my $ix=12; $ix<=23; $ix++) {
8916
my $monthix=($ix<10?"0$ix":"$ix");
8918
print "<td>$monthix</td>";
8919
if ($ShowHoursStats =~ /P/i) { print "<td>",$_time_p[$monthix]?$_time_p[$monthix]:"0","</td>"; }
8920
if ($ShowHoursStats =~ /H/i) { print "<td>",$_time_h[$monthix]?$_time_h[$monthix]:"0","</td>"; }
8921
if ($ShowHoursStats =~ /B/i) { print "<td>",Format_Bytes(int($_time_k[$monthix])),"</td>"; }
8926
print "</center></td></tr></table>\n";
8930
print "</center></td></tr>\n";
8934
print "\n<a name=\"who\"> </a>\n\n";
8937
#---------------------------
8938
if ($ShowDomainsStats) {
8939
if ($Debug) { debug("ShowDomainsStats",2); }
8940
print "$Center<a name=\"countries\"> </a><br />\n";
8941
my $title="$Message[25] ($Message[77] $MaxNbOf{'Domain'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=alldomains"):"$PROG$StaticLinks.alldomains.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>";
8942
&tab_head("$title",19,0,'countries');
8943
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"$WIDTHCOLICON\"> </th><th colspan=\"2\">$Message[17]</th>";
8944
if ($ShowDomainsStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
8945
if ($ShowDomainsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
8946
if ($ShowDomainsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
8947
print "<th> </th>";
8949
$total_p=$total_h=$total_k=0;
8950
$max_h=1; foreach (values %_domener_h) { if ($_ > $max_h) { $max_h = $_; } }
8951
$max_k=1; foreach (values %_domener_k) { if ($_ > $max_k) { $max_k = $_; } }
8953
&BuildKeyList($MaxNbOf{'Domain'},$MinHit{'Domain'},\%_domener_h,\%_domener_p);
8954
foreach my $key (@keylist) {
8955
my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
8956
if ($max_h > 0) { $bredde_p=int($BarWidth*$_domener_p{$key}/$max_h)+1; } # use max_h to enable to compare pages with hits
8957
if ($_domener_p{$key} && $bredde_p==1) { $bredde_p=2; }
8958
if ($max_h > 0) { $bredde_h=int($BarWidth*$_domener_h{$key}/$max_h)+1; }
8959
if ($_domener_h{$key} && $bredde_h==1) { $bredde_h=2; }
8960
if ($max_k > 0) { $bredde_k=int($BarWidth*($_domener_k{$key}||0)/$max_k)+1; }
8961
if ($_domener_k{$key} && $bredde_k==1) { $bredde_k=2; }
8962
my $newkey=lc($key);
8963
if ($newkey eq 'ip' || ! $DomainsHashIDLib{$newkey}) {
8964
print "<tr><td width=\"$WIDTHCOLICON\"><img src=\"$DirIcons\/flags\/ip.png\" height=\"14\"".AltTitle("$Message[0]")." /></td><td class=\"aws\">$Message[0]</td><td>$newkey</td>";
8967
print "<tr><td width=\"$WIDTHCOLICON\"><img src=\"$DirIcons\/flags\/$newkey.png\" height=\"14\"".AltTitle("$newkey")." /></td><td class=\"aws\">$DomainsHashIDLib{$newkey}</td><td>$newkey</td>";
8969
if ($ShowDomainsStats =~ /P/i) { print "<td>".($_domener_p{$key}?$_domener_p{$key}:' ')."</td>"; }
8970
if ($ShowDomainsStats =~ /H/i) { print "<td>$_domener_h{$key}</td>"; }
8971
if ($ShowDomainsStats =~ /B/i) { print "<td>".Format_Bytes($_domener_k{$key})."</td>"; }
8972
print "<td style=\"text-align:left; font-size:4px;\">";
8973
if ($ShowDomainsStats =~ /P/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hp'}\" width=\"$bredde_p\" height=\"5\"".AltTitle("")." /><br />\n"; }
8974
if ($ShowDomainsStats =~ /H/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hh'}\" width=\"$bredde_h\" height=\"5\"".AltTitle("")." /><br />\n"; }
8975
if ($ShowDomainsStats =~ /B/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hk'}\" width=\"$bredde_k\" height=\"5\"".AltTitle("")." />"; }
8978
$total_p += $_domener_p{$key};
8979
$total_h += $_domener_h{$key};
8980
$total_k += $_domener_k{$key}||0;
8983
$rest_p=$TotalPages-$total_p;
8984
$rest_h=$TotalHits-$total_h;
8985
$rest_k=$TotalBytes-$total_k;
8986
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other domains (known or not)
8987
print "<tr><td width=\"$WIDTHCOLICON\"> </td><td colspan=\"2\" class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
8988
if ($ShowDomainsStats =~ /P/i) { print "<td>$rest_p</td>"; }
8989
if ($ShowDomainsStats =~ /H/i) { print "<td>$rest_h</td>"; }
8990
if ($ShowDomainsStats =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
8991
print "<td class=\"aws\"> </td>";
8998
#--------------------------
8999
if ($ShowHostsStats) {
9000
if ($Debug) { debug("ShowHostsStats",2); }
9001
print "$Center<a name=\"visitors\"> </a><br />\n";
9002
my $title="$Message[81] ($Message[77] $MaxNbOf{'HostsShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allhosts"):"$PROG$StaticLinks.allhosts.$StaticExt")."\"$NewLinkTarget>$Message[80]</a> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lasthosts"):"$PROG$StaticLinks.lasthosts.$StaticExt")."\"$NewLinkTarget>$Message[9]</a> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownip"):"$PROG$StaticLinks.unknownip.$StaticExt")."\"$NewLinkTarget>$Message[45]</a>";
9003
&tab_head("$title",19,0,'visitors');
9004
print "<tr bgcolor=\"#$color_TableBGRowTitle\">";
9006
if ($MonthRequired ne 'all') { print "$Message[81] : $TotalHostsKnown $Message[82], $TotalHostsUnknown $Message[1] - $TotalUnique $Message[11]</th>"; }
9007
else { print "$Message[81] : ".(scalar keys %_host_h)."</th>"; }
9008
&ShowHostInfo('__title__');
9009
if ($ShowHostsStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
9010
if ($ShowHostsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
9011
if ($ShowHostsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
9012
if ($ShowHostsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
9014
$total_p=$total_h=$total_k=0;
9016
&BuildKeyList($MaxNbOf{'HostsShown'},$MinHit{'Host'},\%_host_h,\%_host_p);
9017
foreach my $key (@keylist) {
9019
print "<td class=\"aws\">$key</td>";
9020
&ShowHostInfo($key);
9021
if ($ShowHostsStats =~ /P/i) { print "<td>".($_host_p{$key}||" ")."</td>"; }
9022
if ($ShowHostsStats =~ /H/i) { print "<td>$_host_h{$key}</td>"; }
9023
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($_host_k{$key})."</td>"; }
9024
if ($ShowHostsStats =~ /L/i) { print "<td>".($_host_l{$key}?Format_Date($_host_l{$key},1):'-')."</td>"; }
9026
$total_p += $_host_p{$key};
9027
$total_h += $_host_h{$key};
9028
$total_k += $_host_k{$key}||0;
9031
$rest_p=$TotalPages-$total_p;
9032
$rest_h=$TotalHits-$total_h;
9033
$rest_k=$TotalBytes-$total_k;
9034
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other visitors (known or not)
9036
print "<td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
9038
if ($ShowHostsStats =~ /P/i) { print "<td>$rest_p</td>"; }
9039
if ($ShowHostsStats =~ /H/i) { print "<td>$rest_h</td>"; }
9040
if ($ShowHostsStats =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
9041
if ($ShowHostsStats =~ /L/i) { print "<td> </td>"; }
9048
#----------------------------
9049
if ($ShowEMailSenders) {
9050
&ShowEmailSendersChart($NewLinkParams,$NewLinkTarget);
9054
#----------------------------
9055
if ($ShowEMailReceivers) {
9056
&ShowEmailReceiversChart($NewLinkParams,$NewLinkTarget);
9060
#----------------------------
9061
if ($ShowAuthenticatedUsers) {
9062
if ($Debug) { debug("ShowAuthenticatedUsers",2); }
9063
print "$Center<a name=\"logins\"> </a><br />\n";
9064
my $title="$Message[94] ($Message[77] $MaxNbOf{'LoginShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=alllogins"):"$PROG$StaticLinks.alllogins.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>";
9065
if ($ShowAuthenticatedUsers =~ /L/i) { $title.=" - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastlogins"):"$PROG$StaticLinks.lastlogins.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>"; }
9066
&tab_head("$title",19,0,'logins');
9067
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$Message[94] : ".(scalar keys %_login_h)."</th>";
9068
&ShowUserInfo('__title__');
9069
if ($ShowAuthenticatedUsers =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
9070
if ($ShowAuthenticatedUsers =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
9071
if ($ShowAuthenticatedUsers =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
9072
if ($ShowAuthenticatedUsers =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
9074
$total_p=$total_h=$total_k=0;
9075
$max_h=1; foreach (values %_login_h) { if ($_ > $max_h) { $max_h = $_; } }
9076
$max_k=1; foreach (values %_login_k) { if ($_ > $max_k) { $max_k = $_; } }
9078
&BuildKeyList($MaxNbOf{'LoginShown'},$MinHit{'Login'},\%_login_h,\%_login_p);
9079
foreach my $key (@keylist) {
9080
my $bredde_p=0;my $bredde_h=0;my $bredde_k=0;
9081
if ($max_h > 0) { $bredde_p=int($BarWidth*$_login_p{$key}/$max_h)+1; } # use max_h to enable to compare pages with hits
9082
if ($max_h > 0) { $bredde_h=int($BarWidth*$_login_h{$key}/$max_h)+1; }
9083
if ($max_k > 0) { $bredde_k=int($BarWidth*$_login_k{$key}/$max_k)+1; }
9084
print "<tr><td class=\"aws\">$key</td>";
9085
&ShowUserInfo($key);
9086
if ($ShowAuthenticatedUsers =~ /P/i) { print "<td>".($_login_p{$key}?$_login_p{$key}:" ")."</td>"; }
9087
if ($ShowAuthenticatedUsers =~ /H/i) { print "<td>$_login_h{$key}</td>"; }
9088
if ($ShowAuthenticatedUsers =~ /B/i) { print "<td>".Format_Bytes($_login_k{$key})."</td>"; }
9089
if ($ShowAuthenticatedUsers =~ /L/i) { print "<td>".($_login_l{$key}?Format_Date($_login_l{$key},1):'-')."</td>"; }
9091
$total_p += $_login_p{$key};
9092
$total_h += $_login_h{$key};
9093
$total_k += $_login_k{$key};
9096
$rest_p=$TotalPages-$total_p;
9097
$rest_h=$TotalHits-$total_h;
9098
$rest_k=$TotalBytes-$total_k;
9099
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other logins
9100
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">".($PageDir eq 'rtl'?"<span dir=\"ltr\">":"")."$Message[125]".($PageDir eq 'rtl'?"</span>":"")."</span></td>";
9102
if ($ShowAuthenticatedUsers =~ /P/i) { print "<td>".($rest_p?$rest_p:" ")."</td>"; }
9103
if ($ShowAuthenticatedUsers =~ /H/i) { print "<td>$rest_h</td>"; }
9104
if ($ShowAuthenticatedUsers =~ /B/i) { print "<td>".Format_Bytes($rest_k)."</td>"; }
9105
if ($ShowAuthenticatedUsers =~ /L/i) { print "<td> </td>"; }
9112
#----------------------------
9113
if ($ShowRobotsStats) {
9114
if ($Debug) { debug("ShowRobotStats",2); }
9115
print "$Center<a name=\"robots\"> </a><br />\n";
9116
&tab_head("$Message[53] ($Message[77] $MaxNbOf{'RobotShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=allrobots"):"$PROG$StaticLinks.allrobots.$StaticExt")."\"$NewLinkTarget>$Message[80]</a> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=lastrobots"):"$PROG$StaticLinks.lastrobots.$StaticExt")."\"$NewLinkTarget>$Message[9]</a>",19,0,'robots');
9117
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(16);\" onmouseout=\"HideTip(16);\"":"")."><th>".(scalar keys %_robot_h)." $Message[51]*</th>";
9118
if ($ShowRobotsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
9119
if ($ShowRobotsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
9120
if ($ShowRobotsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
9122
$total_p=$total_h=$total_k=$total_r=0;
9124
&BuildKeyList($MaxNbOf{'RobotShown'},$MinHit{'Robot'},\%_robot_h,\%_robot_h);
9125
foreach my $key (@keylist) {
9126
print "<tr><td class=\"aws\">".($PageDir eq 'rtl'?"<span dir=\"ltr\">":"").($RobotsHashIDLib{$key}?$RobotsHashIDLib{$key}:$key).($PageDir eq 'rtl'?"</span>":"")."</td>";
9127
if ($ShowRobotsStats =~ /H/i) { print "<td>".($_robot_h{$key}-$_robot_r{$key}).($_robot_r{$key}?"+$_robot_r{$key}":"")."</td>"; }
9128
if ($ShowRobotsStats =~ /B/i) { print "<td>".Format_Bytes($_robot_k{$key})."</td>"; }
9129
if ($ShowRobotsStats =~ /L/i) { print "<td>".($_robot_l{$key}?Format_Date($_robot_l{$key},1):'-')."</td>"; }
9131
#$total_p += $_robot_p{$key};
9132
$total_h += $_robot_h{$key};
9133
$total_k += $_robot_k{$key}||0;
9134
$total_r += $_robot_r{$key}||0;
9137
# For bots we need to count Totals
9138
my $TotalPagesRobots = 0; #foreach (values %_robot_p) { $TotalPagesRobots+=$_; }
9139
my $TotalHitsRobots = 0; foreach (values %_robot_h) { $TotalHitsRobots+=$_; }
9140
my $TotalBytesRobots = 0; foreach (values %_robot_k) { $TotalBytesRobots+=$_; }
9141
my $TotalRRobots = 0; foreach (values %_robot_r) { $TotalRRobots+=$_; }
9142
$rest_p=0; #$rest_p=$TotalPagesRobots-$total_p;
9143
$rest_h=$TotalHitsRobots-$total_h;
9144
$rest_k=$TotalBytesRobots-$total_k;
9145
$rest_r=$TotalRRobots-$total_r;
9146
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0 || $rest_r > 0) { # All other robots
9147
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
9148
if ($ShowRobotsStats =~ /H/i) { print "<td>".($rest_h-$rest_r).($rest_r?"+$rest_r":"")."</td>"; }
9149
if ($ShowRobotsStats =~ /B/i) { print "<td>".(Format_Bytes($rest_k))."</td>"; }
9150
if ($ShowRobotsStats =~ /L/i) { print "<td> </td>"; }
9153
&tab_end("* $Message[156]".($TotalRRobots?" $Message[157]":""));
9157
#----------------------------
9158
if ($ShowWormsStats) {
9159
if ($Debug) { debug("ShowWormsStats",2); }
9160
print "$Center<a name=\"worms\"> </a><br />\n";
9161
&tab_head("$Message[163] ($Message[77] $MaxNbOf{'WormsShown'})",19,0,'worms');
9162
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(16);\" onmouseout=\"HideTip(16);\"":"")."><th>".(scalar keys %_worm_h)." $Message[164]*</th>";
9163
if ($ShowWormsStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
9164
if ($ShowWormsStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
9165
if ($ShowWormsStats =~ /L/i) { print "<th width=\"120\">$Message[9]</th>"; }
9167
$total_p=$total_h=$total_k=0;
9169
&BuildKeyList($MaxNbOf{'WormsShown'},$MinHit{'Worm'},\%_worm_h,\%_worm_h);
9170
foreach my $key (@keylist) {
9171
print "<tr><td class=\"aws\">".($PageDir eq 'rtl'?"<span dir=\"ltr\">":"").($WormsHashLib{$key}?$WormsHashLib{$key}:$key).($PageDir eq 'rtl'?"</span>":"")."</td>";
9172
if ($ShowWormsStats =~ /H/i) { print "<td>".$_worm_h{$key}."</td>"; }
9173
if ($ShowWormsStats =~ /B/i) { print "<td>".Format_Bytes($_worm_k{$key})."</td>"; }
9174
if ($ShowWormsStats =~ /L/i) { print "<td>".($_worm_l{$key}?Format_Date($_worm_l{$key},1):'-')."</td>"; }
9176
#$total_p += $_worm_p{$key};
9177
$total_h += $_worm_h{$key};
9178
$total_k += $_worm_k{$key}||0;
9181
# For worms we need to count Totals
9182
my $TotalPagesWorms = 0; #foreach (values %_worm_p) { $TotalPagesWorms+=$_; }
9183
my $TotalHitsWorms = 0; foreach (values %_worm_h) { $TotalHitsWorms+=$_; }
9184
my $TotalBytesWorms = 0; foreach (values %_worm_k) { $TotalBytesWorms+=$_; }
9185
$rest_p=0; #$rest_p=$TotalPagesRobots-$total_p;
9186
$rest_h=$TotalHitsWorms-$total_h;
9187
$rest_k=$TotalBytesWorms-$total_k;
9188
if ($rest_p > 0 || $rest_h > 0 || $rest_k > 0) { # All other worms
9189
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
9190
if ($ShowWormsStats =~ /H/i) { print "<td>".($rest_h)."</td>"; }
9191
if ($ShowWormsStats =~ /B/i) { print "<td>".(Format_Bytes($rest_k))."</td>"; }
9192
if ($ShowWormsStats =~ /L/i) { print "<td> </td>"; }
9195
&tab_end("* $Message[158]");
9198
print "\n<a name=\"how\"> </a>\n\n";
9201
#----------------------------
9202
if ($ShowSessionsStats) {
9203
if ($Debug) { debug("ShowSessionsStats",2); }
9204
print "$Center<a name=\"sessions\"> </a><br />\n";
9205
my $title="$Message[117]";
9206
&tab_head($title,19,0,'sessions');
9207
my $Totals=0; foreach (@SessionsRange) { $average_s+=($_session{$_}||0)*$SessionsAverage{$_}; $Totals+=$_session{$_}||0; }
9208
if ($Totals) { $average_s=int($average_s/$Totals); }
9209
else { $average_s='?'; }
9210
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(1);\" onmouseout=\"HideTip(1);\"":"")."><th>$Message[10]: $TotalVisits - $Message[96]: $average_s s</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[10]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[15]</th></tr>\n";
9214
foreach my $key (@SessionsRange) {
9216
if ($TotalVisits) { $p=int($_session{$key}/$TotalVisits*1000)/10; }
9217
$total_s+=$_session{$key}||0;
9218
print "<tr><td class=\"aws\">$key</td>";
9219
print "<td>".($_session{$key}?$_session{$key}:" ")."</td>";
9220
print "<td>".($_session{$key}?"$p %":" ")."</td>";
9224
$rest_s=$TotalVisits-$total_s;
9225
if ($rest_s > 0) { # All others sessions
9227
if ($TotalVisits) { $p=int($rest_s/$TotalVisits*1000)/10; }
9228
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(20);\" onmouseout=\"HideTip(20);\"":"")."><td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td>";
9229
print "<td>$rest_s</td>";
9230
print "<td>".($rest_s?"$p %":" ")."</td>";
9237
#-------------------------
9238
if ($ShowFileTypesStats) {
9239
if ($Debug) { debug("ShowFileTypesStatsCompressionStats",2); }
9240
print "$Center<a name=\"filetypes\"> </a><br />\n";
9241
my $Totalh=0; foreach (keys %_filetypes_h) { $Totalh+=$_filetypes_h{$_}; }
9242
my $Totalk=0; foreach (keys %_filetypes_k) { $Totalk+=$_filetypes_k{$_}; }
9243
my $title="$Message[73]";
9244
if ($ShowFileTypesStats =~ /C/i) { $title.=" - $Message[98]"; }
9245
&tab_head("$title",19,0,'filetypes');
9246
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"3\">$Message[73]</th>";
9247
if ($ShowFileTypesStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>"; }
9248
if ($ShowFileTypesStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th><th bgcolor=\"#$color_k\" width=\"80\">$Message[15]</th>"; }
9249
if ($ShowFileTypesStats =~ /C/i) { print "<th bgcolor=\"#$color_k\" width=\"120\">$Message[100]</th><th bgcolor=\"#$color_k\" width=\"120\">$Message[101]</th><th bgcolor=\"#$color_k\" width=\"120\">$Message[99]</th>"; }
9251
my $total_con=0; my $total_cre=0;
9253
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_filetypes_h,\%_filetypes_h);
9254
foreach my $key (@keylist) {
9255
my $p_h=' '; my $p_k=' ';
9256
if ($Totalh) { $p_h=int($_filetypes_h{$key}/$Totalh*1000)/10; $p_h="$p_h %"; }
9257
if ($Totalk) { $p_k=int($_filetypes_k{$key}/$Totalk*1000)/10; $p_k="$p_k %"; }
9258
if ($key eq 'Unknown') {
9259
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/mime\/unknown.png\"".AltTitle("")." /></td><td class=\"aws\" colspan=\"2\"><span style=\"color: #$color_other\">$Message[0]</span></td>";
9262
my $nameicon=$MimeHashIcon{$key}||"notavailable";
9263
my $nametype=$MimeHashLib{$MimeHashFamily{$key}||""}||" ";
9264
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/mime\/$nameicon.png\"".AltTitle("")." /></td><td class=\"aws\">$key</td>";
9265
print "<td class=\"aws\">$nametype</td>";
9267
if ($ShowFileTypesStats =~ /H/i) { print "<td>$_filetypes_h{$key}</td><td>$p_h</td>"; }
9268
if ($ShowFileTypesStats =~ /B/i) { print "<td>".Format_Bytes($_filetypes_k{$key})."</td><td>$p_k</td>"; }
9269
if ($ShowFileTypesStats =~ /C/i) {
9270
if ($_filetypes_gz_in{$key}) {
9271
my $percent=int(100*(1-$_filetypes_gz_out{$key}/$_filetypes_gz_in{$key}));
9272
printf("<td>%s</td><td>%s</td><td>%s (%s%)</td>",Format_Bytes($_filetypes_gz_in{$key}),Format_Bytes($_filetypes_gz_out{$key}),Format_Bytes($_filetypes_gz_in{$key}-$_filetypes_gz_out{$key}),$percent);
9273
$total_con+=$_filetypes_gz_in{$key};
9274
$total_cre+=$_filetypes_gz_out{$key};
9277
print "<td> </td><td> </td><td> </td>";
9283
# Add total (only usefull if compression is enabled)
9284
if ($ShowFileTypesStats =~ /C/i) {
9286
if ($ShowFileTypesStats =~ /H/i) { $colspan+=2; }
9287
if ($ShowFileTypesStats =~ /B/i) { $colspan+=2; }
9289
print "<td class=\"aws\" colspan=\"$colspan\"><b>$Message[98]</b></td>";
9290
if ($ShowFileTypesStats =~ /C/i) {
9292
my $percent=int(100*(1-$total_cre/$total_con));
9293
printf("<td>%s</td><td>%s</td><td>%s (%s%)</td>",Format_Bytes($total_con),Format_Bytes($total_cre),Format_Bytes($total_con-$total_cre),$percent);
9296
print "<td> </td><td> </td><td> </td>";
9305
#-------------------------
9306
if ($ShowFileSizesStats) {
9311
#-------------------------
9312
if ($ShowPagesStats) {
9313
if ($Debug) { debug("ShowPagesStats (MaxNbOf{'PageShown'}=$MaxNbOf{'PageShown'} TotalDifferentPages=$TotalDifferentPages)",2); }
9314
print "$Center<a name=\"urls\"> </a><a name=\"entry\"> </a><a name=\"exit\"> </a><br />\n";
9315
my $title="$Message[19] ($Message[77] $MaxNbOf{'PageShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urldetail"):"$PROG$StaticLinks.urldetail.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>";
9316
if ($ShowPagesStats =~ /E/i) { $title.=" - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urlentry"):"$PROG$StaticLinks.urlentry.$StaticExt")."\"$NewLinkTarget>$Message[104]</a>"; }
9317
if ($ShowPagesStats =~ /X/i) { $title.=" - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=urlexit"):"$PROG$StaticLinks.urlexit.$StaticExt")."\"$NewLinkTarget>$Message[116]</a>"; }
9318
&tab_head("$title",19,0,'urls');
9319
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$TotalDifferentPages $Message[28]</th>";
9320
if ($ShowPagesStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[29]</th>"; }
9321
if ($ShowPagesStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[106]</th>"; }
9322
if ($ShowPagesStats =~ /E/i) { print "<th bgcolor=\"#$color_e\" width=\"80\">$Message[104]</th>"; }
9323
if ($ShowPagesStats =~ /X/i) { print "<th bgcolor=\"#$color_x\" width=\"80\">$Message[116]</th>"; }
9324
# Call to plugins' function ShowPagesAddField
9325
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
9326
my $function="ShowPagesAddField_$pluginname('title')";
9329
print "<th> </th></tr>\n";
9330
$total_p=$total_e=$total_x=$total_k=0;
9333
&BuildKeyList($MaxNbOf{'PageShown'},$MinHit{'File'},\%_url_p,\%_url_p);
9334
foreach my $key (@keylist) {
9335
if ($_url_p{$key} > $max_p) { $max_p = $_url_p{$key}; }
9336
if ($_url_k{$key}/($_url_p{$key}||1) > $max_k) { $max_k = $_url_k{$key}/($_url_p{$key}||1); }
9338
foreach my $key (@keylist) {
9339
print "<tr><td class=\"aws\">";
9342
my $bredde_p=0; my $bredde_e=0; my $bredde_x=0; my $bredde_k=0;
9343
if ($max_p > 0) { $bredde_p=int($BarWidth*($_url_p{$key}||0)/$max_p)+1; }
9344
if (($bredde_p==1) && $_url_p{$key}) { $bredde_p=2; }
9345
if ($max_p > 0) { $bredde_e=int($BarWidth*($_url_e{$key}||0)/$max_p)+1; }
9346
if (($bredde_e==1) && $_url_e{$key}) { $bredde_e=2; }
9347
if ($max_p > 0) { $bredde_x=int($BarWidth*($_url_x{$key}||0)/$max_p)+1; }
9348
if (($bredde_x==1) && $_url_x{$key}) { $bredde_x=2; }
9349
if ($max_k > 0) { $bredde_k=int($BarWidth*(($_url_k{$key}||0)/($_url_p{$key}||1))/$max_k)+1; }
9350
if (($bredde_k==1) && $_url_k{$key}) { $bredde_k=2; }
9351
if ($ShowPagesStats =~ /P/i) { print "<td>$_url_p{$key}</td>"; }
9352
if ($ShowPagesStats =~ /B/i) { print "<td>".($_url_k{$key}?Format_Bytes($_url_k{$key}/($_url_p{$key}||1)):" ")."</td>"; }
9353
if ($ShowPagesStats =~ /E/i) { print "<td>".($_url_e{$key}?$_url_e{$key}:" ")."</td>"; }
9354
if ($ShowPagesStats =~ /X/i) { print "<td>".($_url_x{$key}?$_url_x{$key}:" ")."</td>"; }
9355
# Call to plugins' function ShowPagesAddField
9356
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
9357
my $function="ShowPagesAddField_$pluginname('$key')";
9360
print "<td style=\"text-align:left; font-size:4px;\">";
9361
if ($ShowPagesStats =~ /P/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hp'}\" width=\"$bredde_p\" height=\"4\"".AltTitle("")." /><br />"; }
9362
if ($ShowPagesStats =~ /B/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hk'}\" width=\"$bredde_k\" height=\"4\"".AltTitle("")." /><br />"; }
9363
if ($ShowPagesStats =~ /E/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'he'}\" width=\"$bredde_e\" height=\"4\"".AltTitle("")." /><br />"; }
9364
if ($ShowPagesStats =~ /X/i) { print "<img src=\"$DirIcons\/other\/$BarPng{'hx'}\" width=\"$bredde_x\" height=\"4\"".AltTitle("")." />"; }
9365
print "</td></tr>\n";
9366
$total_p += $_url_p{$key};
9367
$total_e += $_url_e{$key};
9368
$total_x += $_url_x{$key};
9369
$total_k += $_url_k{$key};
9372
$rest_p=$TotalPages-$total_p;
9373
$rest_e=$TotalEntries-$total_e;
9374
$rest_x=$TotalExits-$total_x;
9375
$rest_k=$TotalBytesPages-$total_k;
9376
if ($rest_p > 0 || $rest_k > 0 || $rest_e > 0 || $rest_x > 0) { # All other urls
9377
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
9378
if ($ShowPagesStats =~ /P/i) { print "<td>$rest_p</td>"; }
9379
if ($ShowPagesStats =~ /B/i) { print "<td>".($rest_k?Format_Bytes($rest_k/($rest_p||1)):" ")."</td>"; }
9380
if ($ShowPagesStats =~ /E/i) { print "<td>".($rest_e?$rest_e:" ")."</td>"; }
9381
if ($ShowPagesStats =~ /X/i) { print "<td>".($rest_x?$rest_x:" ")."</td>"; }
9382
# Call to plugins' function ShowPagesAddField
9383
foreach my $pluginname (keys %{$PluginsLoaded{'ShowPagesAddField'}}) {
9384
my $function="ShowPagesAddField_$pluginname('')";
9387
print "<td> </td></tr>\n";
9393
#----------------------------
9395
if ($Debug) { debug("ShowOSStats",2); }
9396
print "$Center<a name=\"os\"> </a><br />\n";
9397
my $Totalh=0; my %new_os_h=();
9398
OSLOOP: foreach my $key (keys %_os_h) {
9399
$Totalh+=$_os_h{$key};
9400
foreach my $family (@OSFamily) { if ($key =~ /^$family/i) { $new_os_h{"${family}cumul"}+=$_os_h{$key}; next OSLOOP; } }
9401
$new_os_h{$key}+=$_os_h{$key};
9403
my $title="$Message[59] ($Message[77] $MaxNbOf{'OsShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=osdetail"):"$PROG$StaticLinks.osdetail.$StaticExt")."\"$NewLinkTarget>$Message[80]/$Message[58]</a> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownos"):"$PROG$StaticLinks.unknownos.$StaticExt")."\"$NewLinkTarget>$Message[0]</a>";
9404
&tab_head("$title",19,0,'os');
9405
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"$WIDTHCOLICON\"> </th><th>$Message[59]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th></tr>\n";
9408
&BuildKeyList($MaxNbOf{'OsShown'},$MinHit{'Os'},\%new_os_h,\%new_os_h);
9409
foreach my $key (@keylist) {
9411
if ($Totalh) { $p=int($new_os_h{$key}/$Totalh*1000)/10; $p="$p %"; }
9412
if ($key eq 'Unknown') {
9413
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/os\/unknown.png\"".AltTitle("")." /></td><td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td><td>$_os_h{$key}</td><td>$p</td></tr>\n";
9416
my $keywithoutcumul=$key; $keywithoutcumul =~ s/cumul$//i;
9417
my $libos=$OSHashLib{$keywithoutcumul}||$keywithoutcumul;
9418
my $nameicon=$keywithoutcumul; $nameicon =~ s/[^\w]//g;
9419
# TODO Use OSFamilyLib
9420
if ($libos eq 'win') { $libos="<b>Windows</b>"; }
9421
if ($libos eq 'mac') { $libos="<b>Macintosh</b>"; }
9422
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/os\/$nameicon.png\"".AltTitle("")." /></td><td class=\"aws\">$libos</td><td>$new_os_h{$key}</td><td>$p</td></tr>\n";
9424
$total_h += $new_os_h{$key};
9427
if ($Debug) { debug("Total real / shown : $Totalh / $total_h",2); }
9428
$rest_h=$Totalh-$total_h;
9431
if ($Totalh) { $p=int($rest_h/$Totalh*1000)/10; }
9433
print "<td> </td>";
9434
print "<td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td><td>$rest_h</td>";
9435
print "<td>$p %</td></tr>\n";
9441
#----------------------------
9442
if ($ShowBrowsersStats) {
9443
if ($Debug) { debug("ShowBrowsersStats",2); }
9444
print "$Center<a name=\"browsers\"> </a><br />\n";
9445
my $Totalh=0; my %new_browser_h=();
9446
BROWSERLOOP: foreach my $key (keys %_browser_h) {
9447
$Totalh+=$_browser_h{$key};
9448
foreach my $family (keys %BrowsersFamily) { if ($key =~ /^$family/i) { $new_browser_h{"${family}cumul"}+=$_browser_h{$key}; next BROWSERLOOP; } }
9449
$new_browser_h{$key}+=$_browser_h{$key};
9451
my $title="$Message[21] ($Message[77] $MaxNbOf{'BrowsersShown'}) - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=browserdetail"):"$PROG$StaticLinks.browserdetail.$StaticExt")."\"$NewLinkTarget>$Message[80]/$Message[58]</a> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=unknownbrowser"):"$PROG$StaticLinks.unknownbrowser.$StaticExt")."\"$NewLinkTarget>$Message[0]</a>";
9452
&tab_head("$title",19,0,'browsers');
9453
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th width=\"$WIDTHCOLICON\"> </th><th>$Message[21]</th><th width=\"80\">$Message[111]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th></tr>\n";
9456
&BuildKeyList($MaxNbOf{'BrowsersShown'},$MinHit{'Browser'},\%new_browser_h,\%new_browser_h);
9457
foreach my $key (@keylist) {
9459
if ($Totalh) { $p=int($new_browser_h{$key}/$Totalh*1000)/10; $p="$p %"; }
9460
if ($key eq 'Unknown') {
9461
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/unknown.png\"".AltTitle("")." /></td><td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td><td width=\"80\">?</td><td>$_browser_h{$key}</td><td>$p</td></tr>\n";
9464
my $keywithoutcumul=$key; $keywithoutcumul =~ s/cumul$//i;
9465
my $libbrowser=$BrowsersHashIDLib{$keywithoutcumul}||$keywithoutcumul;
9466
my $nameicon=$BrowsersHashIcon{$keywithoutcumul}||"notavailable";
9467
if ($BrowsersFamily{$keywithoutcumul}) { $libbrowser="<b>$libbrowser</b>"; }
9468
print "<tr><td".($count?"":" width=\"$WIDTHCOLICON\"")."><img src=\"$DirIcons\/browser\/$nameicon.png\"".AltTitle("")." /></td><td class=\"aws\">".($PageDir eq 'rtl'?"<span dir=\"ltr\">":"")."$libbrowser".($PageDir eq 'rtl'?"</span>":"")."</td><td>".($BrowsersHereAreGrabbers{$key}?"<b>$Message[112]</b>":"$Message[113]")."</td><td>$new_browser_h{$key}</td><td>$p</td></tr>\n";
9470
$total_h += $new_browser_h{$key};
9473
if ($Debug) { debug("Total real / shown : $Totalh / $total_h",2); }
9474
$rest_h=$Totalh-$total_h;
9477
if ($Totalh) { $p=int($rest_h/$Totalh*1000)/10; }
9479
print "<td> </td>";
9480
print "<td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td><td> </td><td>$rest_h</td>";
9481
print "<td>$p %</td></tr>\n";
9487
#----------------------------
9488
if ($ShowScreenSizeStats) {
9489
if ($Debug) { debug("ShowScreenSizeStats",2); }
9490
print "$Center<a name=\"screensizes\"> </a><br />\n";
9491
my $Totalh=0; foreach (keys %_screensize_h) { $Totalh+=$_screensize_h{$_}; }
9492
my $title="$Message[135] ($Message[77] $MaxNbOf{'ScreenSizesShown'})";
9493
&tab_head("$title",0,0,'screensizes');
9494
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$Message[135]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th></tr>\n";
9497
&BuildKeyList($MaxNbOf{'ScreenSizesShown'},$MinHit{'ScreenSize'},\%_screensize_h,\%_screensize_h);
9498
foreach my $key (@keylist) {
9500
if ($Totalh) { $p=int($_screensize_h{$key}/$Totalh*1000)/10; $p="$p %"; }
9501
$total_h+=$_screensize_h{$key}||0;
9503
if ($key eq 'Unknown') {
9504
print "<td class=\"aws\"><span style=\"color: #$color_other\">$Message[0]</span></td>";
9505
print "<td>$p</td>";
9508
my $screensize=$key;
9509
print "<td class=\"aws\">$screensize</td>";
9510
print "<td>$p</td>";
9515
$rest_h=$Totalh-$total_h;
9516
if ($rest_h > 0) { # All others sessions
9518
if ($Totalh) { $p=int($rest_h/$Totalh*1000)/10; }
9519
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[2]</span></td>";
9520
print "<td>".($rest_h?"$p %":" ")."</td>";
9526
print "\n<a name=\"refering\"> </a>\n\n";
9529
#---------------------------
9530
if ($ShowOriginStats) {
9531
if ($Debug) { debug("ShowOriginStats",2); }
9532
print "$Center<a name=\"referer\"> </a><br />\n";
9533
my $Totalp=0; foreach (0..5) { $Totalp+=$_from_p[$_]; }
9534
my $Totalh=0; foreach (0..5) { $Totalh+=$_from_h[$_]; }
9535
&tab_head($Message[36],19,0,'referer');
9536
my @p_p=(0,0,0,0,0,0);
9538
$p_p[0]=int($_from_p[0]/$Totalp*1000)/10;
9539
$p_p[1]=int($_from_p[1]/$Totalp*1000)/10;
9540
$p_p[2]=int($_from_p[2]/$Totalp*1000)/10;
9541
$p_p[3]=int($_from_p[3]/$Totalp*1000)/10;
9542
$p_p[4]=int($_from_p[4]/$Totalp*1000)/10;
9543
$p_p[5]=int($_from_p[5]/$Totalp*1000)/10;
9545
my @p_h=(0,0,0,0,0,0);
9547
$p_h[0]=int($_from_h[0]/$Totalh*1000)/10;
9548
$p_h[1]=int($_from_h[1]/$Totalh*1000)/10;
9549
$p_h[2]=int($_from_h[2]/$Totalh*1000)/10;
9550
$p_h[3]=int($_from_h[3]/$Totalh*1000)/10;
9551
$p_h[4]=int($_from_h[4]/$Totalh*1000)/10;
9552
$p_h[5]=int($_from_h[5]/$Totalh*1000)/10;
9554
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$Message[37]</th>";
9555
if ($ShowOriginStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th><th bgcolor=\"#$color_p\" width=\"80\">$Message[15]</th>"; }
9556
if ($ShowOriginStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>"; }
9558
#------- Referrals by direct address/bookmarks
9559
print "<tr><td class=\"aws\"><b>$Message[38]</b></td>";
9560
if ($ShowOriginStats =~ /P/i) { print "<td>".($_from_p[0]?$_from_p[0]:" ")."</td><td>".($_from_p[0]?"$p_p[0] %":" ")."</td>"; }
9561
if ($ShowOriginStats =~ /H/i) { print "<td>".($_from_h[0]?$_from_h[0]:" ")."</td><td>".($_from_h[0]?"$p_h[0] %":" ")."</td>"; }
9563
#------- Referrals by news group
9564
print "<tr><td class=\"aws\"><b>$Message[107]</b></td>";
9565
if ($ShowOriginStats =~ /P/i) { print "<td>".($_from_p[5]?$_from_p[5]:" ")."</td><td>".($_from_p[5]?"$p_p[5] %":" ")."</td>"; }
9566
if ($ShowOriginStats =~ /H/i) { print "<td>".($_from_h[5]?$_from_h[5]:" ")."</td><td>".($_from_h[5]?"$p_h[5] %":" ")."</td>"; }
9568
#------- Referrals by search engines
9569
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(13);\" onmouseout=\"HideTip(13);\"":"")."><td class=\"aws\"><b>$Message[40]</b> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=refererse"):"$PROG$StaticLinks.refererse.$StaticExt")."\"$NewLinkTarget>$Message[80]</a><br />\n";
9570
if (scalar keys %_se_referrals_h) {
9572
$total_p=0; $total_h=0;
9574
&BuildKeyList($MaxNbOf{'RefererShown'},$MinHit{'Refer'},\%_se_referrals_h,\%_se_referrals_p);
9575
foreach my $key (@keylist) {
9576
my $newreferer=CleanFromCSSA($SearchEnginesHashLib{$key}||$key);
9577
print "<tr><td class=\"aws\">- $newreferer</td>";
9578
print "<td>".($_se_referrals_p{$key}?$_se_referrals_p{$key}:'0')."</td>";
9579
print "<td>$_se_referrals_h{$key}</td>";
9581
$total_p += $_se_referrals_p{$key};
9582
$total_h += $_se_referrals_h{$key};
9585
if ($Debug) { debug("Total real / shown : $TotalSearchEnginesPages / $total_p - $TotalSearchEnginesHits / $total_h",2); }
9586
$rest_p=$TotalSearchEnginesPages-$total_p;
9587
$rest_h=$TotalSearchEnginesHits-$total_h;
9588
if ($rest_p > 0 || $rest_h > 0) {
9589
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">- $Message[2]</span></td>";
9590
print "<td>$rest_p</td>";
9591
print "<td>$rest_h</td>";
9597
if ($ShowOriginStats =~ /P/i) { print "<td valign=\"top\">".($_from_p[2]?$_from_p[2]:" ")."</td><td valign=\"top\">".($_from_p[2]?"$p_p[2] %":" ")."</td>"; }
9598
if ($ShowOriginStats =~ /H/i) { print "<td valign=\"top\">".($_from_h[2]?$_from_h[2]:" ")."</td><td valign=\"top\">".($_from_h[2]?"$p_h[2] %":" ")."</td>"; }
9600
#------- Referrals by external HTML link
9601
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip(14);\" onmouseout=\"HideTip(14);\"":"")."><td class=\"aws\"><b>$Message[41]</b> - <a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=refererpages"):"$PROG$StaticLinks.refererpages.$StaticExt")."\"$NewLinkTarget>$Message[80]</a><br />\n";
9602
if (scalar keys %_pagesrefs_h) {
9604
$total_p=0; $total_h=0;
9606
&BuildKeyList($MaxNbOf{'RefererShown'},$MinHit{'Refer'},\%_pagesrefs_h,\%_pagesrefs_p);
9607
foreach my $key (@keylist) {
9608
print "<tr><td class=\"aws\">- ";
9611
print "<td>".($_pagesrefs_p{$key}?$_pagesrefs_p{$key}:'0')."</td>";
9612
print "<td>$_pagesrefs_h{$key}</td>";
9614
$total_p += $_pagesrefs_p{$key};
9615
$total_h += $_pagesrefs_h{$key};
9618
if ($Debug) { debug("Total real / shown : $TotalRefererPages / $total_p - $TotalRefererHits / $total_h",2); }
9619
$rest_p=$TotalRefererPages-$total_p;
9620
$rest_h=$TotalRefererHits-$total_h;
9621
if ($rest_p > 0 || $rest_h > 0) {
9622
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">- $Message[2]</span></td>";
9623
print "<td>$rest_p</td>";
9624
print "<td>$rest_h</td>";
9630
if ($ShowOriginStats =~ /P/i) { print "<td valign=\"top\">".($_from_p[3]?$_from_p[3]:" ")."</td><td valign=\"top\">".($_from_p[3]?"$p_p[3] %":" ")."</td>"; }
9631
if ($ShowOriginStats =~ /H/i) { print "<td valign=\"top\">".($_from_h[3]?$_from_h[3]:" ")."</td><td valign=\"top\">".($_from_h[3]?"$p_h[3] %":" ")."</td>"; }
9633
#------- Referrals by internal HTML link
9634
print "<tr><td class=\"aws\"><b>$Message[42]</b></td>";
9635
if ($ShowOriginStats =~ /P/i) { print "<td>".($_from_p[4]?$_from_p[4]:" ")."</td><td>".($_from_p[4]?"$p_p[4] %":" ")."</td>"; }
9636
if ($ShowOriginStats =~ /H/i) { print "<td>".($_from_h[4]?$_from_h[4]:" ")."</td><td>".($_from_h[4]?"$p_h[4] %":" ")."</td>"; }
9638
#------- Unknown origin
9639
print "<tr><td class=\"aws\"><b>$Message[39]</b></td>";
9640
if ($ShowOriginStats =~ /P/i) { print "<td>".($_from_p[1]?$_from_p[1]:" ")."</td><td>".($_from_p[1]?"$p_p[1] %":" ")."</td>"; }
9641
if ($ShowOriginStats =~ /H/i) { print "<td>".($_from_h[1]?$_from_h[1]:" ")."</td><td>".($_from_h[1]?"$p_h[1] %":" ")."</td>"; }
9646
print "\n<a name=\"keys\"> </a>\n\n";
9648
# BY SEARCH KEYWORDS AND/OR KEYPHRASES
9649
#-------------------------------------
9650
if ($ShowKeyphrasesStats) { print "$Center<a name=\"keyphrases\"> </a>"; }
9651
if ($ShowKeywordsStats) { print "$Center<a name=\"keywords\"> </a>"; }
9652
if ($ShowKeyphrasesStats || $ShowKeywordsStats) { print "<br />\n"; }
9653
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "<table width=\"100%\" cellpadding=\"0\" cellspacing=\"0\"><tr>"; }
9654
if ($ShowKeyphrasesStats) {
9656
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "<td width=\"50%\" valign=\"top\">\n"; }
9657
if ($Debug) { debug("ShowKeyphrasesStats",2); }
9658
&tab_head("$Message[120] ($Message[77] $MaxNbOf{'KeyphrasesShown'})<br /><a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=keyphrases"):"$PROG$StaticLinks.keyphrases.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>",19,($ShowKeyphrasesStats && $ShowKeywordsStats)?95:70,'keyphrases');
9659
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(15);\" onmouseout=\"HideTip(15);\"":"")."><th>$TotalDifferentKeyphrases $Message[103]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[14]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[15]</th></tr>\n";
9662
&BuildKeyList($MaxNbOf{'KeyphrasesShown'},$MinHit{'Keyphrase'},\%_keyphrases,\%_keyphrases);
9663
foreach my $key (@keylist) {
9665
# Convert coded keywords (utf8,...) to be correctly reported in HTML page.
9666
if ($PluginsLoaded{'DecodeKey'}{'decodeutfkeys'}) { $mot=CleanFromCSSA(DecodeKey_decodeutfkeys($key,$PageCode||'iso-8859-1')); }
9667
else { $mot = CleanFromCSSA(DecodeEncodedString($key)); }
9669
if ($TotalKeyphrases) { $p=int($_keyphrases{$key}/$TotalKeyphrases*1000)/10; }
9670
print "<tr><td class=\"aws\">".XMLEncode($mot)."</td><td>$_keyphrases{$key}</td><td>$p %</td></tr>\n";
9671
$total_s += $_keyphrases{$key};
9674
if ($Debug) { debug("Total real / shown : $TotalKeyphrases / $total_s",2); }
9675
$rest_s=$TotalKeyphrases-$total_s;
9678
if ($TotalKeyphrases) { $p=int($rest_s/$TotalKeyphrases*1000)/10; }
9679
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[124]</span></td><td>$rest_s</td>";
9680
print "<td>$p %</td></tr>\n";
9683
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "</td>\n"; }
9685
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "<td> </td>"; }
9686
if ($ShowKeywordsStats) {
9688
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "<td width=\"50%\" valign=\"top\">\n"; }
9689
if ($Debug) { debug("ShowKeywordsStats",2); }
9690
&tab_head("$Message[121] ($Message[77] $MaxNbOf{'KeywordsShown'})<br /><a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=keywords"):"$PROG$StaticLinks.keywords.$StaticExt")."\"$NewLinkTarget>$Message[80]</a>",19,($ShowKeyphrasesStats && $ShowKeywordsStats)?95:70,'keywords');
9691
print "<tr bgcolor=\"#$color_TableBGRowTitle\"".($TOOLTIPON?" onmouseover=\"ShowTip(15);\" onmouseout=\"HideTip(15);\"":"")."><th>$TotalDifferentKeywords $Message[13]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[14]</th><th bgcolor=\"#$color_s\" width=\"80\">$Message[15]</th></tr>\n";
9694
&BuildKeyList($MaxNbOf{'KeywordsShown'},$MinHit{'Keyword'},\%_keywords,\%_keywords);
9695
foreach my $key (@keylist) {
9697
# Convert coded keywords (utf8,...) to be correctly reported in HTML page.
9698
if ($PluginsLoaded{'DecodeKey'}{'decodeutfkeys'}) { $mot=CleanFromCSSA(DecodeKey_decodeutfkeys($key,$PageCode||'iso-8859-1')); }
9699
else { $mot = CleanFromCSSA(DecodeEncodedString($key)); }
9701
if ($TotalKeywords) { $p=int($_keywords{$key}/$TotalKeywords*1000)/10; }
9702
print "<tr><td class=\"aws\">".XMLEncode($mot)."</td><td>$_keywords{$key}</td><td>$p %</td></tr>\n";
9703
$total_s += $_keywords{$key};
9706
if ($Debug) { debug("Total real / shown : $TotalKeywords / $total_s",2); }
9707
$rest_s=$TotalKeywords-$total_s;
9710
if ($TotalKeywords) { $p=int($rest_s/$TotalKeywords*1000)/10; }
9711
print "<tr><td class=\"aws\"><span style=\"color: #$color_other\">$Message[30]</span></td><td>$rest_s</td>";
9712
print "<td>$p %</td></tr>\n";
9715
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "</td>\n"; }
9717
if ($ShowKeyphrasesStats && $ShowKeywordsStats) { print "</tr></table>\n"; }
9719
print "\n<a name=\"other\"> </a>\n\n";
9722
#----------------------------
9723
if ($ShowMiscStats) {
9724
if ($Debug) { debug("ShowMiscStats",2); }
9725
print "$Center<a name=\"misc\"> </a><br />\n";
9726
my $Totalh=0; my %new_browser_h=();
9727
if ($_misc_h{'AddToFavourites'}) {
9728
foreach my $key (keys %_browser_h) {
9729
$Totalh+=$_browser_h{$key};
9730
if ($key =~ /^msie/i) { $new_browser_h{"msiecumul"}+=$_browser_h{$key}; }
9732
if ($new_browser_h{'msiecumul'}) { $_misc_h{'AddToFavourites'}=int(0.5+$_misc_h{'AddToFavourites'}*$Totalh/$new_browser_h{'msiecumul'}); }
9734
my $title="$Message[139]";
9735
&tab_head("$title",19,0,'misc');
9736
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th>$Message[139]</th>";
9737
print "<th width=\"100\"> </th>";
9738
print "<th width=\"100\"> </th>";
9740
my %label=('AddToFavourites'=>$Message[137],'JavaEnabled'=>$Message[140],'DirectorSupport'=>$Message[141],
9741
'FlashSupport'=>$Message[142],'RealPlayerSupport'=>$Message[143],'QuickTimeSupport'=>$Message[144],
9742
'WindowsMediaPlayerSupport'=>$Message[145],'PDFSupport'=>$Message[146]);
9743
foreach my $key (@MiscListOrder) {
9744
my $mischar=substr($key,0,1);
9745
if ($ShowMiscStats !~ /$mischar/i) { next; }
9748
if ($MiscListCalc{$key} eq 'v') { $total=$TotalVisits; }
9749
if ($MiscListCalc{$key} eq 'u') { $total=$TotalUnique; }
9750
if ($MiscListCalc{$key} eq 'hm') { $total=$_misc_h{'TotalMisc'}||0; }
9751
if ($total) { $p=int($_misc_h{$key}/$total*1000)/10; }
9753
print "<td class=\"aws\">".($PageDir eq 'rtl'?"<span dir=\"ltr\">":"").$label{$key}.($PageDir eq 'rtl'?"</span>":"")."</td>";
9754
if ($MiscListCalc{$key} eq 'v') { print "<td>".($_misc_h{$key}||0)." / $total $Message[12]</td>"; }
9755
if ($MiscListCalc{$key} eq 'u') { print "<td>".($_misc_h{$key}||0)." / $total $Message[18]</td>"; }
9756
if ($MiscListCalc{$key} eq 'hm') { print "<td>-</td>"; }
9757
print "<td>".($total?"$p %":" ")."</td>";
9764
#----------------------------
9765
if ($ShowHTTPErrorsStats) {
9766
if ($Debug) { debug("ShowHTTPErrorsStats",2); }
9767
print "$Center<a name=\"errors\"> </a><br />\n";
9768
my $title="$Message[32]";
9769
&tab_head("$title",19,0,'errors');
9770
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"2\">$Message[32]*</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th><th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th></tr>\n";
9773
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_errors_h,\%_errors_h);
9774
foreach my $key (@keylist) {
9775
my $p=int($_errors_h{$key}/$TotalHitsErrors*1000)/10;
9776
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip($key);\" onmouseout=\"HideTip($key);\"":"").">";
9777
if ($TrapInfosForHTTPErrorCodes{$key}) { print "<td><a href=\"".($ENV{'GATEWAY_INTERFACE'} || !$StaticLinks?XMLEncode("$AWScript?${NewLinkParams}output=errors$key"):"$PROG$StaticLinks.errors$key.$StaticExt")."\"$NewLinkTarget>$key</a></td>"; }
9778
else { print "<td valign=\"top\">$key</td>"; }
9779
print "<td class=\"aws\">".($httpcodelib{$key}?$httpcodelib{$key}:'Unknown error')."</td><td>$_errors_h{$key}</td><td>$p %</td><td>".Format_Bytes($_errors_k{$key})."</td>";
9781
$total_h+=$_errors_h{$key};
9784
&tab_end("* $Message[154]");
9788
#----------------------------
9789
if ($ShowSMTPErrorsStats) {
9790
if ($Debug) { debug("ShowSMTPErrorsStats",2); }
9791
print "$Center<a name=\"errors\"> </a><br />\n";
9792
my $title="$Message[147]";
9793
&tab_head("$title",19,0,'errors');
9794
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"2\">$Message[147]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th><th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th></tr>\n";
9797
&BuildKeyList($MaxRowsInHTMLOutput,1,\%_errors_h,\%_errors_h);
9798
foreach my $key (@keylist) {
9799
my $p=int($_errors_h{$key}/$TotalHitsErrors*1000)/10;
9800
print "<tr".($TOOLTIPON?" onmouseover=\"ShowTip($key);\" onmouseout=\"HideTip($key);\"":"").">";
9801
print "<td valign=\"top\">$key</td>";
9802
print "<td class=\"aws\">".($smtpcodelib{$key}?$smtpcodelib{$key}:'Unknown error')."</td><td>$_errors_h{$key}</td><td>$p %</td><td>".Format_Bytes($_errors_k{$key})."</td>";
9804
$total_h+=$_errors_h{$key};
9811
#----------------------------
9812
if ($ShowClusterStats) {
9813
if ($Debug) { debug("ShowClusterStats",2); }
9814
print "$Center<a name=\"clusters\"> </a><br />\n";
9815
my $title="$Message[155]";
9816
&tab_head("$title",19,0,'clusters');
9817
print "<tr bgcolor=\"#$color_TableBGRowTitle\"><th colspan=\"2\">$Message[155]</th>";
9818
if ($ShowClusterStats =~ /P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th><th bgcolor=\"#$color_p\" width=\"80\">$Message[15]</th>"; }
9819
if ($ShowClusterStats =~ /H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th><th bgcolor=\"#$color_h\" width=\"80\">$Message[15]</th>"; }
9820
if ($ShowClusterStats =~ /B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th><th bgcolor=\"#$color_k\" width=\"80\">$Message[15]</th>"; }
9822
$total_p=$total_h=$total_k=0;
9823
# Cluster feature might have been enable in middle of month so we recalculate
9824
# total for cluster section only, to calculate ratio, instead of using global total
9825
foreach my $key (keys %_cluster_h) {
9826
$total_p+=int($_cluster_p{$key}||0);
9827
$total_h+=int($_cluster_h{$key}||0);
9828
$total_k+=int($_cluster_k{$key}||0);
9831
foreach my $key (keys %_cluster_h) {
9832
my $p_p=int($_cluster_p{$key}/$total_p*1000)/10;
9833
my $p_h=int($_cluster_h{$key}/$total_h*1000)/10;
9834
my $p_k=int($_cluster_k{$key}/$total_k*1000)/10;
9836
print "<td class=\"aws\" colspan=\"2\">Computer $key</td>";
9837
if ($ShowClusterStats =~ /P/i) { print "<td>".($_cluster_p{$key}?$_cluster_p{$key}:" ")."</td><td>$p_p %</td>"; }
9838
if ($ShowClusterStats =~ /H/i) { print "<td>$_cluster_h{$key}</td><td>$p_h %</td>"; }
9839
if ($ShowClusterStats =~ /B/i) { print "<td>".Format_Bytes($_cluster_k{$key})."</td><td>$p_k %</td>"; }
9847
#----------------------------
9848
foreach my $extranum (1..@ExtraName-1) {
9849
if ($Debug) { debug("ExtraName$extranum",2); }
9850
print "$Center<a name=\"extra$extranum\"> </a><br />";
9851
my $title=$ExtraName[$extranum];
9852
&tab_head("$title",19,0,"extra$extranum");
9853
print "<tr bgcolor=\"#$color_TableBGRowTitle\">";
9854
print "<th>".$ExtraFirstColumnTitle[$extranum]."</th>";
9855
if ($ExtraStatTypes[$extranum] =~ m/P/i) { print "<th bgcolor=\"#$color_p\" width=\"80\">$Message[56]</th>"; }
9856
if ($ExtraStatTypes[$extranum] =~ m/H/i) { print "<th bgcolor=\"#$color_h\" width=\"80\">$Message[57]</th>"; }
9857
if ($ExtraStatTypes[$extranum] =~ m/B/i) { print "<th bgcolor=\"#$color_k\" width=\"80\">$Message[75]</th>"; }
9858
if ($ExtraStatTypes[$extranum] =~ m/L/i) { print "<th width=\"120\">$Message[9]</th>"; }
9860
$total_p=$total_h=$total_k=0;
9861
#$max_h=1; foreach (values %_login_h) { if ($_ > $max_h) { $max_h = $_; } }
9862
#$max_k=1; foreach (values %_login_k) { if ($_ > $max_k) { $max_k = $_; } }
9864
if ($ExtraStatTypes[$extranum] =~ m/P/i) {
9865
&BuildKeyList($MaxNbOfExtra[$extranum],$MinHitExtra[$extranum],\%{'_section_' . $extranum . '_h'},\%{'_section_' . $extranum . '_p'});
9868
&BuildKeyList($MaxNbOfExtra[$extranum],$MinHitExtra[$extranum],\%{'_section_' . $extranum . '_h'},\%{'_section_' . $extranum . '_h'});
9870
foreach my $key (@keylist) {
9871
my $firstcol = CleanFromCSSA(DecodeEncodedString($key));
9872
$total_p+=${'_section_' . $extranum . '_p'}{$key};
9873
$total_h+=${'_section_' . $extranum . '_h'}{$key};
9874
$total_k+=${'_section_' . $extranum . '_k'}{$key};
9876
printf("<td class=\"aws\">$ExtraFirstColumnFormat[$extranum]</td>", $firstcol, $firstcol, $firstcol, $firstcol, $firstcol);
9877
if ($ExtraStatTypes[$extranum] =~ m/P/i) { print "<td>" . ${'_section_' . $extranum . '_p'}{$key} . "</td>"; }
9878
if ($ExtraStatTypes[$extranum] =~ m/H/i) { print "<td>" . ${'_section_' . $extranum . '_h'}{$key} . "</td>"; }
9879
if ($ExtraStatTypes[$extranum] =~ m/B/i) { print "<td>" . Format_Bytes(${'_section_' . $extranum . '_k'}{$key}) . "</td>"; }
9880
if ($ExtraStatTypes[$extranum] =~ m/L/i) { print "<td>" . (${'_section_' . $extranum . '_l'}{$key}?Format_Date(${'_section_' . $extranum . '_l'}{$key},1):'-') . "</td>"; }
9884
if ($ExtraAddAverageRow[$extranum]) {
9886
print "<td class=\"aws\"><b>$Message[96]</b></td>";
9887
if ($ExtraStatTypes[$extranum] =~ m/P/i) { print "<td>" . ($count?($total_p/$count):" ") . "</td>"; }
9888
if ($ExtraStatTypes[$extranum] =~ m/H/i) { print "<td>" . ($count?($total_h/$count):" ") . "</td>"; }
9889
if ($ExtraStatTypes[$extranum] =~ m/B/i) { print "<td>" . ($count?Format_Bytes($total_k/$count):" ") . "</td>"; }
9890
if ($ExtraStatTypes[$extranum] =~ m/L/i) { print "<td> </td>"; }
9893
if ($ExtraAddSumRow[$extranum]) {
9895
print "<td class=\"aws\"><b>$Message[102]</b></td>";
9896
if ($ExtraStatTypes[$extranum] =~ m/P/i) { print "<td>" . ($total_p) . "</td>"; }
9897
if ($ExtraStatTypes[$extranum] =~ m/H/i) { print "<td>" . ($total_h) . "</td>"; }
9898
if ($ExtraStatTypes[$extranum] =~ m/B/i) { print "<td>" . Format_Bytes($total_k) . "</td>"; }
9899
if ($ExtraStatTypes[$extranum] =~ m/L/i) { print "<td> </td>"; }
9909
print "Jumped lines in file: $lastlinenumber\n";
9910
if ($lastlinenumber) { print " Found $lastlinenumber old records.\n"; }
9911
print "Parsed lines in file: $NbOfLinesParsed\n";
9912
print " Found $NbOfLinesDropped dropped records,\n";
9913
print " Found $NbOfLinesCorrupted corrupted records,\n";
9914
print " Found $NbOfOldLines old records,\n";
9915
print " Found $NbOfNewLines new qualified records.\n";
9920
0; # Do not remove this line
9923
#-------------------------------------------------------
9927
# Check_Config() and Init variables
9928
# if 'frame not index'
9929
# &Read_Language_Data($Lang);
9930
# if 'frame not mainleft'
9936
# We create/update tmp file with
9937
# &Read_History_With_TmpUpdate(year,month,UPDATE,NOPURGE,"all");
9938
# Rename the tmp file
9943
# Get last history file name
9944
# Get value for $LastLine $LastLineNumber $LastLineOffset $LastLineChecksum with
9945
# &Read_History_With_TmpUpdate(lastyear,lastmonth,NOUPDATE,NOPURGE,"general");
9950
# Loop on each new line in log file
9951
# lastlineoffset=lastlineoffsetnext; lastlineoffsetnext=file pointer position
9952
# If line corrupted, skip --> next on loop
9953
# Drop wrong virtual host --> next on loop
9954
# Drop wrong method/protocol --> next on loop
9955
# Check date --> next on loop
9956
# If line older than $LastLine, skip --> next on loop
9958
# $LastLine = time or record
9959
# Skip if url is /robots.txt --> next on loop
9960
# Skip line for @SkipHosts --> next on loop
9961
# Skip line for @SkipFiles --> next on loop
9962
# Skip line for @SkipUserAgent --> next on loop
9963
# Skip line for not @OnlyHosts --> next on loop
9964
# Skip line for not @OnlyFiles --> next on loop
9965
# Skip line for not @OnlyUserAgent --> next on loop
9966
# So it's new line approved
9967
# If other month/year, create/update tmp file and purge data arrays with
9968
# &Read_History_With_TmpUpdate(lastprocessedyear,lastprocessedmonth,UPDATE,PURGE,"all",lastlinenumber,lastlineoffset,CheckSum($_));
9969
# Define a clean Url and Query (set urlwithnoquery, tokenquery and standalonequery and $field[$pos_url])
9970
# Define PageBool and extension
9971
# Analyze: Misc tracker --> complete %misc
9972
# Analyze: Add to favorites --> complete %_misc, next on loop
9973
# Analyze: Worms --> complete %_worms, countedtraffic=1
9974
# If (!countedtraffic) Analyze: Status code --> complete %_error_, %_sider404, %_referrer404 --> countedtraffic=1
9975
# If (!countedtraffic) Analyze: Robots known --> complete %_robot, countedtraffic=1
9976
# If (!countedtraffic) Analyze: Robots unkown on robots.txt --> complete %_robot, countedtraffic=1
9977
# If (!countedtraffic) Analyze: File types - Compression
9978
# If (!countedtraffic) Analyze: Date - Hour - Pages - Hits - Kilo
9979
# If (!countedtraffic) Analyze: Login
9980
# If (!countedtraffic) Analyze: Lookup
9981
# If (!countedtraffic) Analyze: Country
9982
# If (!countedtraffic) Analyze: Host - Url - Session
9983
# If (!countedtraffic) Analyze: Browser - OS
9984
# If (!countedtraffic) Analyze: Referer
9985
# If (!countedtraffic) Analyze: EMail
9987
# Analyze: Extra (must be after 'Clean Url and Query')
9988
# If too many records, we flush data arrays with
9989
# &Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,UPDATE,PURGE,"all",lastlinenumber,lastlineoffset,CheckSum($_));
9991
# Create/update tmp file
9992
# Seek to lastlineoffset to read and get last line into $_
9993
# &Read_History_With_TmpUpdate($lastprocessedyear,$lastprocessedmonth,UPDATE,PURGE,"all",lastlinenumber,lastlineoffset,CheckSum($_))
9994
# Rename all tmp files
10000
# Loop for each month of required year
10001
# &Read_History_With_TmpUpdate($YearRequired,monthloop,NOUPDATE,NOPURGE,"all" or "general time" if not required month)
10003
# Show data arrays in HTML page
10006
#-------------------------------------------------------
10008
#-------------------------------------------------------
10009
# DNS CACHE FILE FORMATS SUPPORTED BY AWSTATS
10010
# Format /etc/hosts x.y.z.w hostname
10011
# Format analog UT/60 x.y.z.w hostname
10012
#-------------------------------------------------------
10014
#-------------------------------------------------------
10015
# IP Format (d=decimal on 16 bits, x=hexadecimal on 16 bits)
10017
# 13.1.68.3 IPv4 (d.d.d.d)
10018
# 0:0:0:0:0:0:13.1.68.3 IPv6 (x:x:x:x:x:x:d.d.d.d)
10020
# 0:0:0:0:0:FFFF:13.1.68.3 IPv6 (x:x:x:x:x:x:d.d.d.d)
10021
# ::FFFF:13.1.68.3 IPv6
10023
# 1070:0:0:0:0:800:200C:417B IPv6
10024
# 1070:0:0:0:0:800:200C:417B IPv6
10025
# 1070::800:200C:417B IPv6
10026
#-------------------------------------------------------