]> git.ipfire.org Git - thirdparty/sarg.git/blobdiff - datafile.c
Generate redirector log even if -d is not given
[thirdparty/sarg.git] / datafile.c
index e866ee0675f8dcff257222bc0054e371334b524c..54608c612dbe8e8abb0384634971ad30caf542a5 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * SARG Squid Analysis Report Generator      http://sarg.sourceforge.net
- *                                                            1998, 2010
+ *                                                            1998, 2015
  *
  * SARG donations:
  *      please look at http://sarg.sourceforge.net/donations.php
 #include "include/conf.h"
 #include "include/defs.h"
 
-void saverecs(char *dirname, char *user, long long int nacc, char *url, long long int nbytes, char *ip, char *hora, char *dia, long long int nelap, long long int incache, long long int oucache);
+void saverecs(FILE *fp_ou, const struct userinfostruct *uinfo, long long int nacc, char *url, long long int nbytes, char *ip, char *hora, char *dia, long long int nelap, long long int incache, long long int oucache);
 
 void data_file(char *tmp)
 {
+       FileObject *fp_in;
+       FILE *fp_ou=NULL;
 
-   FILE *fp_in;
-
-   char accdia[11], acchora[9], accuser[MAXLEN], accip[MAXLEN], accurl[MAXLEN];
-   char oldaccdia[11], oldacchora[9], oldaccip[MAXLEN];
-   char dirname[MAXLEN], wdirname[MAXLEN], oldurl[MAXLEN], oldaccuser[MAXLEN];
-   char olduser[MAXLEN], oldmsg[50], acccode[50], oldacccode[50];
-   char ipantes[MAXLEN], nameantes[MAXLEN];
-   char accsmart[MAXLEN];
-   char crc2[50];
-   char *str;
-   DIR *dirp;
-   struct dirent *direntp;
-   long long int nbytes=0;
-   long long int nelap=0;
-   long long int nacc=0;
-   long long int rtotal=0;
-   long long int incache=0;
-   long long int oucache=0;
-   long long int accbytes;
-   long long int accelap;
-   int dlen;
-   struct getwordstruct gwarea;
-   const char logext[]=".log";
-
-   ipantes[0]='\0';
-   nameantes[0]='\0';
-
-   olduser[0]='\0';
-   strncat(tmp,"/sarg",5);
-
-   dirp = opendir(tmp);
-   while ( (direntp = readdir( dirp )) != NULL ) {
-      dlen=strlen(direntp->d_name)-(sizeof(logext)-1);
-      if (dlen<=0) continue;
-      if(strcmp(direntp->d_name+dlen,logext) != 0)
-         continue;
-
-      if (snprintf(tmp3,sizeof(tmp3),"%s/%s",tmp,direntp->d_name)>=sizeof(tmp3)) {
-         fprintf(stderr,"SARG: (datafile) directory path too long: %s/%s\n",tmp,direntp->d_name);
-         exit(1);
-      }
-
-      if((fp_in=MY_FOPEN(tmp3,"r"))==NULL){
-         fprintf(stderr, "SARG: (datafile) %s: %s\n",text[45],tmp);
-         exit(1);
-      }
-
-      ttopen=0;
-      while(fgets(buf,sizeof(buf),fp_in)!=NULL) {
-         getword_start(&gwarea,buf);
-         if (getword(accdia,sizeof(accdia),&gwarea,' ')<0 || getword(acchora,sizeof(acchora),&gwarea,' ')<0 ||
-             getword(accuser,sizeof(accuser),&gwarea,' ')<0 || getword(accip,sizeof(accip),&gwarea,' ')<0 ||
-             getword(accurl,sizeof(accurl),&gwarea,' ')<0 || getword_atoll(&accbytes,&gwarea,' ')<0 ||
-             getword(acccode,sizeof(acccode),&gwarea,' ')<0 || getword_atoll(&accelap,&gwarea,' ')<0 ||
-             getword_skip(20000,&gwarea,' ')<0 || getword(accsmart,sizeof(accsmart),&gwarea,'"')<0) {
-            printf("SARG: Maybe you have a broken record or garbage in your %s file.\n",tmp3);
-            exit(1);
-         }
-
-         if(Ip2Name) {
-            if(strcmp(accip,ipantes) != 0) {
-               strcpy(ipantes,accip);
-               ip2name(accip,sizeof(accip));
-               strcpy(nameantes,accip);
-            }
-            else strcpy(accip,nameantes);
-         }
-
-         if(!rtotal){
-            strcpy(oldurl,accurl);
-            strcpy(oldacccode,acccode);
-            strcpy(oldaccuser,accuser);
-            strcpy(oldaccip,accip);
-            strcpy(oldaccdia,accdia);
-            strcpy(oldacchora,acchora);
-            rtotal++;
-         }
-
-         if(strcmp(oldurl,accurl) != 0 || strcmp(oldaccuser,accuser) != 0){
-            strcpy(oldmsg,"OK");
-            if(strstr(oldacccode,"DENIED") != 0) strcpy(oldmsg,text[46]);
-            gravatmp(oldaccuser,oldurl,nacc,nbytes,oldmsg,nelap,indexonly,incache,oucache);
-            strcpy(wdirname,dirname);
-            saverecs(wdirname,oldaccuser,nacc,oldurl,nbytes,oldaccip,oldacchora,oldaccdia,nelap,incache,oucache);
-            nacc=0;
-            nbytes=0;
-            nelap=0;
-            incache=0;
-            oucache=0;
-            if(strcmp(oldaccuser,accuser) != 0) ind2=0;
-         }
-
-         nacc++;
-         nbytes+=accbytes;
-         nelap+=accelap;
-
-         strcpy(crc2,acccode);
-         str=strchr(crc2,'/');
-         if (str) *str='\0';
-
-         if(strstr(crc2,"MISS") != 0) oucache+=accbytes;
-         else incache+=accbytes;
-
-         strcpy(oldurl,accurl);
-         strcpy(oldaccuser,accuser);
-         strcpy(oldacccode,acccode);
-         strcpy(oldaccip,accip);
-         strcpy(oldaccdia,accdia);
-         strcpy(oldacchora,acchora);
-      }
-
-      fclose(fp_in);
-   }
-
-   (void)closedir( dirp );
-   if(debug)
-      debuga("Datafile %s successfully",DataFile);
+       char *buf;
+       char accdia[11], acchora[9], accip[MAXLEN], *accurl;
+       char oldaccdia[11], oldacchora[9], oldaccip[MAXLEN];
+       char *oldurl;
+       char acccode[50], oldacccode[50];
+       char ipantes[MAXLEN], nameantes[MAXLEN];
+       char accsmart[MAXLEN];
+       char crc2[50];
+       char *str;
+       char tmp3[MAXLEN];
+       char u2[MAX_USER_LEN];
+       char userlabel[MAX_USER_LEN];
+       userscan uscan;
+       long long int nbytes=0;
+       long long int nelap=0;
+       long long int nacc=0;
+       int rtotal=0;
+       long long int incache=0;
+       long long int oucache=0;
+       long long int accbytes;
+       long long int accelap;
+       int new_user;
+       int same_url;
+       int url_len;
+       int ourl_size;
+       struct getwordstruct gwarea;
+       struct userinfostruct *uinfo;
+       longline line;
+
+       ipantes[0]='\0';
+       nameantes[0]='\0';
+
+       oldurl=NULL;
+       ourl_size=0;
+
+       uscan=userinfo_startscan();
+       if (uscan == NULL) {
+               debuga(__FILE__,__LINE__,_("Cannot enumerate the user list\n"));
+               exit(EXIT_FAILURE);
+       }
+       while ( (uinfo = userinfo_advancescan(uscan)) != NULL ) {
+               strcpy(u2,uinfo->id);
+               if(Ip2Name && uinfo->id_is_ip) {
+                       strcpy(ipantes,u2);
+                       ip2name(u2,sizeof(u2));
+                       strcpy(nameantes,u2);
+               }
+               user_find(userlabel,MAX_USER_LEN, u2);
+               userinfo_label(uinfo,userlabel);
+               if(debug) debuga(__FILE__,__LINE__,_("Reading user file \"%s/%s\"\n"),tmp,uinfo->filename);
+
+               sort_users_log(tmp,debug,uinfo);
+               if (snprintf(tmp3,sizeof(tmp3),"%s/%s.user_log",tmp,uinfo->filename)>=sizeof(tmp3)) {
+                       debuga(__FILE__,__LINE__,_("Path too long: "));
+                       debuga_more("%s/%s.user_log\n",tmp,uinfo->filename);
+                       exit(EXIT_FAILURE);
+               }
+
+               if((fp_in=FileObject_Open(tmp3))==NULL){
+                       debuga(__FILE__,__LINE__,_("Cannot open file \"%s\": %s\n"),tmp3,FileObject_GetLastOpenError());
+                       exit(EXIT_FAILURE);
+               }
+
+               if ((line=longline_create())==NULL) {
+                       debuga(__FILE__,__LINE__,_("Not enough memory to read file \"%s\"\n"),tmp3);
+                       exit(EXIT_FAILURE);
+               }
+
+               ttopen=0;
+               new_user=1;
+               while((buf=longline_read(fp_in,line))!=NULL) {
+                       getword_start(&gwarea,buf);
+                       if (getword(accdia,sizeof(accdia),&gwarea,'\t')<0 || getword(acchora,sizeof(acchora),&gwarea,'\t')<0 ||
+                           getword(accip,sizeof(accip),&gwarea,'\t')<0 ||
+                           getword_ptr(buf,&accurl,&gwarea,'\t')<0 || getword_atoll(&accbytes,&gwarea,'\t')<0 ||
+                           getword(acccode,sizeof(acccode),&gwarea,'\t')<0 || getword_atoll(&accelap,&gwarea,'\t')<0) {
+                               debuga(__FILE__,__LINE__,_("Invalid record in file \"%s\"\n"),tmp3);
+                               exit(EXIT_FAILURE);
+                       }
+                       if (getword_skip(20000,&gwarea,'"')<0 || getword(accsmart,sizeof(accsmart),&gwarea,'"')<0) {
+                               debuga(__FILE__,__LINE__,_("Invalid smart info in file \"%s\"\n"),tmp3);
+                               exit(EXIT_FAILURE);
+                       }
+
+                       if(Ip2Name) {
+                               if(strcmp(accip,ipantes) != 0) {
+                                       strcpy(ipantes,accip);
+                                       ip2name(accip,sizeof(accip));
+                                       strcpy(nameantes,accip);
+                               }
+                               else strcpy(accip,nameantes);
+                       }
+
+                       if(!rtotal){
+                               url_len=strlen(accurl);
+                               if (!oldurl || url_len>=ourl_size) {
+                                       ourl_size=url_len+1;
+                                       oldurl=realloc(oldurl,ourl_size);
+                                       if (!oldurl) {
+                                               debuga(__FILE__,__LINE__,_("Not enough memory to store the url\n"));
+                                               exit(EXIT_FAILURE);
+                                       }
+                               }
+                               strcpy(oldurl,accurl);
+                               strcpy(oldacccode,acccode);
+                               strcpy(oldaccip,accip);
+                               strcpy(oldaccdia,accdia);
+                               strcpy(oldacchora,acchora);
+                               new_user=0;
+                               rtotal++;
+                       }
+                       same_url=(strcmp(oldurl,accurl) == 0);
+
+                       if(!same_url || new_user){
+                               if(!fp_ou && (fp_ou=MY_FOPEN(DataFile,"w"))==NULL){
+                                       debuga(__FILE__,__LINE__,_("Cannot open file \"%s\": %s\n"),DataFile,strerror(errno));
+                                       exit(EXIT_FAILURE);
+                               }
+                               saverecs(fp_ou,uinfo,nacc,oldurl,nbytes,oldaccip,oldacchora,oldaccdia,nelap,incache,oucache);
+                               nacc=0;
+                               nbytes=0;
+                               nelap=0;
+                               incache=0;
+                               oucache=0;
+                               new_user=0;
+                       }
+
+                       nacc++;
+                       nbytes+=accbytes;
+                       nelap+=accelap;
+
+                       strcpy(crc2,acccode);
+                       str=strchr(crc2,'/');
+                       if (str) *str='\0';
+
+                       if(strstr(crc2,"MISS") != 0) oucache+=accbytes;
+                       else incache+=accbytes;
+
+                       if (!same_url) {
+                               url_len=strlen(accurl);
+                               if (url_len>=ourl_size) {
+                                       ourl_size=url_len+1;
+                                       oldurl=realloc(oldurl,ourl_size);
+                                       if (!oldurl) {
+                                               debuga(__FILE__,__LINE__,_("Not enough memory to store the url\n"));
+                                               exit(EXIT_FAILURE);
+                                       }
+                               }
+                               strcpy(oldurl,accurl);
+                       }
+                       new_user=0;
+                       strcpy(oldacccode,acccode);
+                       strcpy(oldaccip,accip);
+                       strcpy(oldaccdia,accdia);
+                       strcpy(oldacchora,acchora);
+               }
+
+               if (FileObject_Close(fp_in)) {
+                       debuga(__FILE__,__LINE__,_("Read error in \"%s\": %s\n"),tmp3,FileObject_GetLastCloseError());
+                       exit(EXIT_FAILURE);
+               }
+               longline_destroy(&line);
+       }
+       userinfo_stopscan(uscan);
+       if (oldurl) free(oldurl);
+       if (fp_ou && fclose(fp_ou)==EOF) {
+               debuga(__FILE__,__LINE__,_("Write error in \"%s\": %s\n"),DataFile,strerror(errno));
+               exit(EXIT_FAILURE);
+       }
+
+       if(debug)
+               debuga(__FILE__,__LINE__,_("Datafile %s written successfully\n"),DataFile);
 }
 
-void saverecs(char *dirname, char *user, long long int nacc, char *url, long long int nbytes, char *ip, char *hora, char *dia, long long int nelap, long long int incache, long long int oucache)
+void saverecs(FILE *fp_ou, const struct userinfostruct *uinfo, long long int nacc, char *url, long long int nbytes, char *ip, char *hora, char *dia, long long int nelap, long long int incache, long long int oucache)
 {
-   FILE *fp_ou;
-   char reg[MAXLEN];
-   char val[20];
-
-   if((fp_ou=MY_FOPEN(DataFile,"a"))==NULL){
-      fprintf(stderr, "SARG: (datafile) %s: %s\n",text[45],DataFile);
-      exit(1);
-   }
-
-   if((DataFileFields & DATA_FIELD_USER) != 0) {
-      strcpy(reg,user);
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_DATE) != 0) {
-      strncat(reg,dia,strlen(dia));
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_TIME) != 0) {
-      strncat(reg,hora,strlen(hora));
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_URL) != 0) {
-      strcpy(name,url);
-      if (strcmp(DataFileUrl,"ip") == 0) name2ip(name);
-      strncat(reg,name,strlen(name));
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_CONNECT) != 0) {
-      my_lltoa(nacc,val,sizeof(val),0);
-      strcat(reg,val);
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_BYTES) != 0) {
-      my_lltoa(nbytes,val,sizeof(val),0);
-      strcat(reg,val);
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_IN_CACHE) != 0) {
-      my_lltoa(incache,val,sizeof(val),0);
-      strcat(reg,val);
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_OUT_CACHE) != 0) {
-      my_lltoa(oucache,val,sizeof(val),0);
-      strcat(reg,val);
-      strncat(reg,DataFileDelimiter,1);
-   }
-   if((DataFileFields & DATA_FIELD_ELAPSED) != 0) {
-      my_lltoa(nelap,val,sizeof(val),0);
-      strcat(reg,val);
-      strncat(reg,DataFileDelimiter,1);
-   }
-
-   reg[strlen(reg)-1]='\n';
-   fputs(reg,fp_ou);
-
-   fclose(fp_ou);
+       char val[20];
+       char name[512];
+
+       if((DataFileFields & DATA_FIELD_USER) != 0) {
+               fputs(uinfo->label,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_DATE) != 0) {
+               fputs(dia,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_TIME) != 0) {
+               fputs(hora,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_URL) != 0) {
+               url_hostname(url,name,sizeof(name));
+               if (DataFileUrl == DATAFILEURL_IP) name2ip(name,sizeof(name));
+               fputs(name,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_CONNECT) != 0) {
+               my_lltoa(nacc,val,sizeof(val),0);
+               fputs(val,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_BYTES) != 0) {
+               my_lltoa(nbytes,val,sizeof(val),0);
+               fputs(val,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_IN_CACHE) != 0) {
+               my_lltoa(incache,val,sizeof(val),0);
+               fputs(val,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_OUT_CACHE) != 0) {
+               my_lltoa(oucache,val,sizeof(val),0);
+               fputs(val,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+       if((DataFileFields & DATA_FIELD_ELAPSED) != 0) {
+               my_lltoa(nelap,val,sizeof(val),0);
+               fputs(val,fp_ou);
+               fputc(DataFileDelimiter[0],fp_ou);
+       }
+
+       fputc('\n',fp_ou);
 }