/* elmo - ELectronic Mail Operator Copyright (C) 2004 rzyjontko This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. ---------------------------------------------------------------------- */ /**************************************************************************** * IMPLEMENTATION HEADERS ****************************************************************************/ #include #include "stats.h" #include "wrapbox.h" #include "mail.h" #include "hash.h" #include "gettext.h" #include "error.h" /**************************************************************************** * IMPLEMENTATION PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS ****************************************************************************/ /**************************************************************************** * IMPLEMENTATION PRIVATE CLASS PROTOTYPES / EXTERNAL CLASS REFERENCES ****************************************************************************/ /**************************************************************************** * IMPLEMENTATION PRIVATE STRUCTURES / UTILITY CLASSES ****************************************************************************/ struct estats { htable_t *muas; htable_t *from; int no_mua; int no_from; }; /**************************************************************************** * IMPLEMENTATION REQUIRED EXTERNAL REFERENCES (AVOID) ****************************************************************************/ /**************************************************************************** * IMPLEMENTATION PRIVATE DATA ****************************************************************************/ static FILE *dump_fp = NULL; static int no_field = 0; /**************************************************************************** * INTERFACE DATA ****************************************************************************/ /**************************************************************************** * IMPLEMENTATION PRIVATE FUNCTION PROTOTYPES ****************************************************************************/ /**************************************************************************** * IMPLEMENTATION PRIVATE FUNCTIONS ****************************************************************************/ static void increment (htable_t *table, char *str) { entry_t *entry = htable_insert (table, str, 0); entry->content = (void *) ((int) entry->content + 1); } static void add_mua (struct estats *stats, char *mua) { increment (stats->muas, mua); } static void add_from (struct estats *stats, address_t *addr) { char *name = address_name (addr); if (name) increment (stats->from, name); else stats->no_from++; } static void process_mail (struct estats *stats, mail_t *mail) { if (mail->mua) add_mua (stats, mail->mua); else stats->no_mua++; if (mail->from) add_from (stats, mail->from); else stats->no_from++; } static void destroy_stats (struct estats *stats) { htable_destroy (stats->muas, NULL); htable_destroy (stats->from, NULL); } static void print_key (FILE *fp, char *str) { while (*str){ if (*str == '\r' || *str == '\n' || *str == '\t') fputc (' ', fp); else fputc (*str, fp); str++; } fputc ('\n', fp); } static void dump_stat (entry_t *entry) { float percent; percent = ((int) entry->content) / (float) (wrapbox_marray->count - no_field); fprintf (dump_fp, " %d (%.2f%%) - ", (int) entry->content, percent * 100.0); print_key (dump_fp, entry->key); } static void dump_stats (struct estats *stats, FILE *fp) { dump_fp = fp; fprintf (fp, "\nMUA statistics:\n"); no_field = stats->no_mua; htable_iterator (stats->muas, dump_stat); fprintf (fp, " %d (%.2f%%) - NULL\n", stats->no_mua, stats->no_mua / (float) wrapbox_marray->count); fprintf (fp, "\nFrom statistics:\n"); no_field = stats->no_from; htable_iterator (stats->from, dump_stat); fprintf (fp, " %d (%.2f%%) - NULL\n", stats->no_from, stats->no_from / (float) wrapbox_marray->count); dump_fp = NULL; no_field = 0; } /**************************************************************************** * INTERFACE FUNCTIONS ****************************************************************************/ void stats_dump (void) { int i; FILE *fp; mail_t *mail; struct estats stats; if (wrapbox_marray == NULL) return; stats.muas = htable_create (5); stats.from = htable_create (8); stats.no_mua = 0; stats.no_from = 0; for (i = 0; i < wrapbox_marray->count; i++){ mail = mail_array_get (wrapbox_marray, i); if (mail != NULL) process_mail (& stats, mail); } fp = fopen ("/tmp/elmostats", "w"); if (fp == NULL){ error_ (errno, _("couldn't open %s"), "/tmp/elmostats"); destroy_stats (& stats); return; } fprintf (fp, "box path: %s\n", wrapbox_marray->path); fprintf (fp, "count: %d\n\n", wrapbox_marray->count); dump_stats (& stats, fp); destroy_stats (& stats); fclose (fp); } /**************************************************************************** * INTERFACE CLASS BODIES ****************************************************************************/ /**************************************************************************** * * END MODULE stats.c * ****************************************************************************/