diff --git a/src/config.h b/src/config.h index e5725e39..31873d65 100644 --- a/src/config.h +++ b/src/config.h @@ -13,7 +13,7 @@ #define VERSION "0.1.20" -#define BUILD 687 +#define BUILD 691 #define HOSTID "mailarchiver" @@ -76,6 +76,7 @@ #define SQL_SPHINX_TABLE "sph_index" #define SQL_METADATA_TABLE "metadata" #define SQL_ATTACHMENT_TABLE "attachment" +#define SQL_FOLDER_TABLE "folder" #define SQL_RECIPIENT_TABLE "rcpt" #define SQL_ARCHIVING_RULE_TABLE "archiving_rule" #define SQL_RETENTION_RULE_TABLE "retention_rule" diff --git a/src/defs.h b/src/defs.h index fd1b17e9..3902d306 100644 --- a/src/defs.h +++ b/src/defs.h @@ -225,7 +225,7 @@ struct memcached_server { struct __data { - char *folder; + int folder; #ifdef HAVE_TRE struct rule *archiving_rules; diff --git a/src/import.c b/src/import.c index 77835463..4fc0c02d 100644 --- a/src/import.c +++ b/src/import.c @@ -118,3 +118,101 @@ ENDE: return rc; } + +unsigned long get_folder_id(struct session_data *sdata, char *foldername){ + unsigned long id=0; + char s[SMALLBUFSIZE]; + MYSQL_STMT *stmt; + MYSQL_BIND bind[1]; + unsigned long len[1]; + + + snprintf(s, SMALLBUFSIZE-1, "SELECT `id` FROM %s WHERE `name`=?", SQL_FOLDER_TABLE); + + if(prepare_a_mysql_statement(sdata, &stmt, s) == ERR) goto ENDE; + + memset(bind, 0, sizeof(bind)); + + bind[0].buffer_type = MYSQL_TYPE_STRING; + bind[0].buffer = foldername; + bind[0].is_null = 0; + len[0] = strlen(foldername); bind[0].length = &len[0]; + + + if(mysql_stmt_bind_param(stmt, bind)){ + goto CLOSE; + } + + + if(mysql_stmt_execute(stmt)){ + goto CLOSE; + } + + memset(bind, 0, sizeof(bind)); + + bind[0].buffer_type = MYSQL_TYPE_LONG; + bind[0].buffer = (char *)&id; + bind[0].is_null = 0; + bind[0].length = 0; + + if(mysql_stmt_bind_result(stmt, bind)){ + goto CLOSE; + } + + + if(mysql_stmt_store_result(stmt)){ + goto CLOSE; + } + + mysql_stmt_fetch(stmt); + +CLOSE: + mysql_stmt_close(stmt); + +ENDE: + + return id; +} + + +unsigned long add_new_folder(struct session_data *sdata, char *foldername){ + unsigned long id=0; + char s[SMALLBUFSIZE]; + MYSQL_STMT *stmt; + MYSQL_BIND bind[2]; + unsigned long len[2]; + + + snprintf(s, sizeof(s)-1, "INSERT INTO %s (`name`) VALUES(?)", SQL_FOLDER_TABLE); + + if(prepare_a_mysql_statement(sdata, &stmt, s) == ERR) goto ENDE; + + memset(bind, 0, sizeof(bind)); + + bind[0].buffer_type = MYSQL_TYPE_STRING; + bind[0].buffer = foldername; + bind[0].is_null = 0; + len[0] = strlen(foldername); bind[0].length = &len[0]; + + if(mysql_stmt_bind_param(stmt, bind)){ + syslog(LOG_PRIORITY, "%s: %s.mysql_stmt_bind_param() error: %s", sdata->ttmpfile, SQL_FOLDER_TABLE, mysql_stmt_error(stmt)); + goto CLOSE; + } + + if(mysql_stmt_execute(stmt)){ + syslog(LOG_PRIORITY, "%s: %s.mysql_stmt_execute error: *%s*", sdata->ttmpfile, SQL_RECIPIENT_TABLE, mysql_error(&(sdata->mysql))); + goto CLOSE; + } + + + id = mysql_stmt_insert_id(stmt); + +CLOSE: + mysql_stmt_close(stmt); + +ENDE: + + return id; +} + + diff --git a/src/message.c b/src/message.c index f415a3a8..77154806 100644 --- a/src/message.c +++ b/src/message.c @@ -122,7 +122,7 @@ int is_body_digest_already_stored(struct session_data *sdata, struct _state *sta } -int store_index_data(struct session_data *sdata, struct _state *state, uint64 id, struct __config *cfg){ +int store_index_data(struct session_data *sdata, struct _state *state, struct __data *data, uint64 id, struct __config *cfg){ int rc=ERR; char *subj, s[SMALLBUFSIZE]; @@ -134,7 +134,7 @@ int store_index_data(struct session_data *sdata, struct _state *state, uint64 id if(*subj == ' ') subj++; - snprintf(s, sizeof(s)-1, "INSERT INTO %s (`id`, `from`, `to`, `fromdomain`, `todomain`, `subject`, `body`, `arrived`, `sent`, `size`, `direction`, `attachments`, `attachment_types`) values(%llu,?,?,?,?,?,?,%ld,%ld,%d,%d,%d,?)", SQL_SPHINX_TABLE, id, sdata->now, sdata->sent, sdata->tot_len, sdata->direction, state->n_attachments); + snprintf(s, sizeof(s)-1, "INSERT INTO %s (`id`, `from`, `to`, `fromdomain`, `todomain`, `subject`, `body`, `arrived`, `sent`, `size`, `direction`, `folder`, `attachments`, `attachment_types`) values(%llu,?,?,?,?,?,?,%ld,%ld,%d,%d,%d,%d,?)", SQL_SPHINX_TABLE, id, sdata->now, sdata->sent, sdata->tot_len, sdata->direction, data->folder, state->n_attachments); if(prepare_a_mysql_statement(sdata, &stmt, s) == ERR) return rc; @@ -264,7 +264,7 @@ CLOSE: } -int store_meta_data(struct session_data *sdata, struct _state *state, struct __config *cfg){ +int store_meta_data(struct session_data *sdata, struct _state *state, struct __data *data, struct __config *cfg){ int rc, ret=ERR; char *subj, *p, s[MAXBUFSIZE], s2[SMALLBUFSIZE], vcode[2*DIGEST_LENGTH+1], ref[2*DIGEST_LENGTH+1]; @@ -356,7 +356,7 @@ int store_meta_data(struct session_data *sdata, struct _state *state, struct __c if(rc == OK){ - rc = store_index_data(sdata, state, id, cfg); + rc = store_index_data(sdata, state, data, id, cfg); if(cfg->verbosity >= _LOG_DEBUG) syslog(LOG_PRIORITY, "%s: stored indexdata, rc=%d", sdata->ttmpfile, rc); @@ -385,7 +385,7 @@ int process_message(struct session_data *sdata, struct _state *state, struct __d /* check for existing body digest */ - rc = is_body_digest_already_stored(sdata, state, cfg); + //rc = is_body_digest_already_stored(sdata, state, cfg); /* * TODO: check if the bodydigest were stored, then we should @@ -415,7 +415,7 @@ int process_message(struct session_data *sdata, struct _state *state, struct __d sdata->retained += query_retain_period(data->retention_rules, state, sdata->tot_len, sdata->spam_message, cfg); - rc = store_meta_data(sdata, state, cfg); + rc = store_meta_data(sdata, state, data, cfg); if(cfg->verbosity >= _LOG_DEBUG) syslog(LOG_PRIORITY, "%s: stored metadata, rc=%d", sdata->ttmpfile, rc); if(rc == ERR_EXISTS){ diff --git a/src/piler.c b/src/piler.c index cd53dde7..2ef5ef60 100644 --- a/src/piler.c +++ b/src/piler.c @@ -288,7 +288,7 @@ void initialise_configuration(){ free_rule(data.archiving_rules); free_rule(data.retention_rules); - data.folder = NULL; + data.folder = 0; data.archiving_rules = NULL; data.retention_rules = NULL; @@ -342,7 +342,7 @@ int main(int argc, char **argv){ (void) openlog(PROGNAME, LOG_PID, LOG_MAIL); - data.folder = NULL; + data.folder = 0; data.archiving_rules = NULL; data.retention_rules = NULL; diff --git a/src/piler.h b/src/piler.h index 21d78cb0..d1b10266 100644 --- a/src/piler.h +++ b/src/piler.h @@ -52,8 +52,10 @@ int retrieve_email_from_archive(struct session_data *sdata, FILE *dest, struct _ int prepare_a_mysql_statement(struct session_data *sdata, MYSQL_STMT **stmt, char *s); int import_message(char *filename, struct session_data *sdata, struct __data *data, struct __config *cfg); +unsigned long get_folder_id(struct session_data *sdata, char *foldername); +unsigned long add_new_folder(struct session_data *sdata, char *foldername); -int store_index_data(struct session_data *sdata, struct _state *state, uint64 id, struct __config *cfg); +int store_index_data(struct session_data *sdata, struct _state *state, struct __data *data, uint64 id, struct __config *cfg); #endif /* _PILER_H */ diff --git a/src/pilerimport.c b/src/pilerimport.c index 4d587986..10ace8ec 100644 --- a/src/pilerimport.c +++ b/src/pilerimport.c @@ -253,19 +253,17 @@ void usage(){ int main(int argc, char **argv){ int i, c, rc=0, n_mbox=0, tot_msgs=0; char *configfile=CONFIG_FILE, *emlfile=NULL, *mboxdir=NULL, *mbox[MBOX_ARGS], *directory=NULL; - char *imapserver=NULL, *username=NULL, *password=NULL, *skiplist=SKIPLIST; + char *imapserver=NULL, *username=NULL, *password=NULL, *skiplist=SKIPLIST, *folder=NULL; struct session_data sdata; struct __config cfg; struct __data data; for(i=0; inow = strtoul(row[2], NULL, 10); sdata->sent = strtoul(row[3], NULL, 10); - rc = store_index_data(sdata, &state, stored_id, cfg); + rc = store_index_data(sdata, &state, data, stored_id, cfg); if(rc == OK) reindexed++; else printf("failed to add to %s table: %s\n", SQL_SPHINX_TABLE, filename); @@ -113,13 +113,14 @@ uint64 retrieve_email_by_metadata_id(struct session_data *sdata, uint64 from_id, int main(int argc, char **argv){ int c; uint64 from_id=0, to_id=0, n=0; - char *configfile=CONFIG_FILE; + char *configfile=CONFIG_FILE, *folder=NULL; struct session_data sdata; + struct __data data; struct __config cfg; while(1){ - c = getopt(argc, argv, "c:f:t:phv?"); + c = getopt(argc, argv, "c:f:t:F:phv?"); if(c == -1) break; @@ -137,6 +138,11 @@ int main(int argc, char **argv){ to_id = strtoull(optarg, NULL, 10); break; + case 'F' : + folder = optarg; + break; + + case 'p' : progressbar = 1; break; @@ -163,6 +169,18 @@ int main(int argc, char **argv){ return 1; } + data.folder = 0; + data.archiving_rules = NULL; + data.retention_rules = NULL; + + if(folder){ + data.folder = get_folder_id(&sdata, folder); + if(data.folder == 0){ + printf("error: could not get folder id for '%s'\n", folder); + return 0; + } + } + init_session_data(&sdata); @@ -176,7 +194,7 @@ int main(int argc, char **argv){ mysql_real_query(&(sdata.mysql), "SET CHARACTER SET utf8", strlen("SET CHARACTER SET utf8")); - n = retrieve_email_by_metadata_id(&sdata, from_id, to_id, &cfg); + n = retrieve_email_by_metadata_id(&sdata, &data, from_id, to_id, &cfg); printf("put %llu messages to %s table for reindexing\n", n, SQL_SPHINX_TABLE); diff --git a/src/test.c b/src/test.c index 238c34f3..c70d9f98 100644 --- a/src/test.c +++ b/src/test.c @@ -53,7 +53,7 @@ int main(int argc, char **argv){ printf("build: %d\n", get_build()); - data.folder = NULL; + data.folder = 0; data.archiving_rules = NULL; data.retention_rules = NULL; diff --git a/util/db-mysql.sql b/util/db-mysql.sql index 7f35211f..1f783520 100644 --- a/util/db-mysql.sql +++ b/util/db-mysql.sql @@ -23,6 +23,7 @@ create table if not exists `sph_index` ( `body` text, `size` int default '0', `direction` int default 0, + `folder` int default 0, `attachments` int default 0, `attachment_types` text(512) default null, primary key (`id`) @@ -61,6 +62,14 @@ create index metadata_idx5 on metadata(`deleted`); create index metadata_idx6 on metadata(`arrived`); create index metadata_idx7 on metadata(`retained`); +drop table if exists `folder`; +create table if not exists `folder` ( + `id` int not null auto_increment, + `parent_id` int default 0, + `name` char(64) not null unique, + primary key (`id`) +) Engine=InnoDB; + drop table if exists `rcpt`; create table if not exists `rcpt` ( diff --git a/util/db-upgrade-0.20-vs-0.21.sql b/util/db-upgrade-0.20-vs-0.21.sql new file mode 100644 index 00000000..4f7257c3 --- /dev/null +++ b/util/db-upgrade-0.20-vs-0.21.sql @@ -0,0 +1,11 @@ +alter table `sph_index` add column `folder` int default 0; + +drop table if exists `folder`; +create table if not exists `folder` ( + `id` int not null auto_increment, + `parent_id` int default 0, + `name` char(64) not null unique, + primary key (`id`) +) Engine=InnoDB; + +