diff options
author | Jason Parker <jparker@digium.com> | 2008-01-14 22:19:40 +0000 |
---|---|---|
committer | Jason Parker <jparker@digium.com> | 2008-01-14 22:19:40 +0000 |
commit | b875d0df01ea6fc407eb84d6a292e2a2303b43d8 (patch) | |
tree | e86d2917cbc3fdbf23f64ccb696b09ebc4797d72 /apps | |
parent | e34fc8282c4509e8b8636c3a30be5baef9da5151 (diff) |
Add backupdeleted option to app_voicemail
(closes issue #10740)
Reported by: ruffle
Patches:
app_voicemail.diff uploaded by ruffle (license 201)
10740-voicemail.diff uploaded by qwell (license 4)
20080113_bug10740.diff.txt uploaded by mvanbaak (license 7)
Tested by: blitzrage, mvanbaak, qwell
git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@98889 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'apps')
-rw-r--r-- | apps/app_voicemail.c | 79 |
1 files changed, 71 insertions, 8 deletions
diff --git a/apps/app_voicemail.c b/apps/app_voicemail.c index 4ca73a418..8c483b9e2 100644 --- a/apps/app_voicemail.c +++ b/apps/app_voicemail.c @@ -380,6 +380,7 @@ struct ast_vm_user { unsigned int flags; /*!< VM_ flags */ int saydurationm; int maxmsg; /*!< Maximum number of msgs per folder for this mailbox */ + int maxdeletedmsg; /*!< Maximum number of deleted msgs saved for this mailbox */ int maxsecs; /*!< Maximum number of seconds per message for this mailbox */ #ifdef IMAP_STORAGE char imapuser[80]; /*!< IMAP server login */ @@ -563,6 +564,7 @@ static AST_LIST_HEAD_STATIC(users, ast_vm_user); static AST_LIST_HEAD_STATIC(zones, vm_zone); static int maxsilence; static int maxmsg; +static int maxdeletedmsg; static int silencethreshold = 128; static char serveremail[80]; static char mailcmd[160]; /* Configurable mail cmd */ @@ -683,6 +685,8 @@ static void populate_defaults(struct ast_vm_user *vmu) vmu->maxsecs = vmmaxsecs; if (maxmsg) vmu->maxmsg = maxmsg; + if (maxdeletedmsg) + vmu->maxdeletedmsg = maxdeletedmsg; vmu->volgain = volgain; } @@ -757,6 +761,21 @@ static void apply_option(struct ast_vm_user *vmu, const char *var, const char *v ast_log(LOG_WARNING, "Maximum number of messages per folder is %d. Cannot accept value maxmsg=%s\n", MAXMSGLIMIT, value); vmu->maxmsg = MAXMSGLIMIT; } + } else if (!strcasecmp(var, "backupdeleted")) { + if (sscanf(value, "%d", &x) == 1) + vmu->maxdeletedmsg = x; + else if (ast_true(value)) + vmu->maxdeletedmsg = MAXMSG; + else + vmu->maxdeletedmsg = 0; + + if (vmu->maxdeletedmsg < 0) { + ast_log(LOG_WARNING, "Invalid number of deleted messages saved per mailbox backupdeleted=%s. Using default value %d\n", value, MAXMSG); + vmu->maxdeletedmsg = MAXMSG; + } else if (vmu->maxdeletedmsg > MAXMSGLIMIT) { + ast_log(LOG_WARNING, "Maximum number of deleted messages saved per mailbox is %d. Cannot accept value backupdeleted=%s\n", MAXMSGLIMIT, value); + vmu->maxdeletedmsg = MAXMSGLIMIT; + } } else if (!strcasecmp(var, "volgain")) { sscanf(value, "%lf", &vmu->volgain); } else if (!strcasecmp(var, "options")) { @@ -2286,6 +2305,7 @@ static const char *mbox(int id) "Cust3", "Cust4", "Cust5", + "Deleted", }; return (id >= 0 && id < (sizeof(msgs)/sizeof(msgs[0]))) ? msgs[id] : "Unknown"; } @@ -2319,6 +2339,8 @@ static int folder_int(const char *folder) return 8; else if (!strcasecmp(folder, "Cust5")) return 9; + else if (!strcasecmp(folder, "Deleted")) + return 10; else /*assume they meant INBOX if folder is not found otherwise*/ return 0; } @@ -3456,20 +3478,33 @@ static int save_to_folder(struct ast_vm_user *vmu, struct vm_state *vms, int msg char dfn[PATH_MAX]; char ddir[PATH_MAX]; const char *dbox = mbox(box); - int x; - make_file(sfn, sizeof(sfn), dir, msg); + int x, i; create_dirpath(ddir, sizeof(ddir), context, username, dbox); if (vm_lock_path(ddir)) return ERROR_LOCK_PATH; x = last_message_index(vmu, ddir) + 1; - make_file(dfn, sizeof(dfn), ddir, x); - if (x >= vmu->maxmsg) { - ast_unlock_path(ddir); - return -1; + if (box == 10 && x >= vmu->maxdeletedmsg) { /* "Deleted" folder*/ + x--; + for (i = 1; i <= x; i++) { + /* Push files down a "slot". The oldest file (msg0000) will be deleted. */ + make_file(sfn, sizeof(sfn), ddir, i); + make_file(dfn, sizeof(dfn), ddir, i - 1); + if (EXISTS(ddir, i, sfn, NULL)) { + RENAME(ddir, i, vmu->mailbox, vmu->context, ddir, i - 1, sfn, dfn); + } else + break; + } + } else { + if (x >= vmu->maxmsg) { + ast_unlock_path(ddir); + return -1; + } } + make_file(sfn, sizeof(sfn), dir, msg); + make_file(dfn, sizeof(dfn), ddir, x); if (strcmp(sfn, dfn)) { COPY(dir, msg, ddir, x, username, context, sfn, dfn); } @@ -5251,14 +5286,23 @@ static int close_mailbox(struct vm_state *vms, struct ast_vm_user *vmu) vms->deleted[x] = 0; vms->heard[x] = 0; --x; - } + } + } else if (vms->deleted[x] && vmu->maxdeletedmsg) { + /* Move to deleted folder */ + res = save_to_folder(vmu, vms, x, 10); + if (res == ERROR_LOCK_PATH) { + /* If save failed do not delete the message */ + vms->deleted[x] = 0; + vms->heard[x] = 0; + --x; + } } else if (vms->deleted[x] && ast_check_realtime("voicemail_data")) { /* If realtime storage enabled - we should explicitly delete this message, cause RENAME() will overwrite files, but will keep duplicate records in RT-storage */ make_file(vms->fn, sizeof(vms->fn), vms->curdir, x); if (EXISTS(vms->curdir, x, vms->fn, NULL)) DELETE(vms->curdir, x, vms->fn); - } + } } /* Delete ALL remaining messages */ @@ -8177,6 +8221,25 @@ static int load_config(int reload) } } + if (!(val = ast_variable_retrieve(cfg, "general", "backupdeleted"))) { + maxdeletedmsg = 0; + } else { + if (sscanf(val, "%d", &x) == 1) + maxdeletedmsg = x; + else if (ast_true(val)) + maxdeletedmsg = MAXMSG; + else + maxdeletedmsg = 0; + + if (maxdeletedmsg < 0) { + ast_log(LOG_WARNING, "Invalid number of deleted messages saved per mailbox '%s'. Using default value %i\n", val, MAXMSG); + maxdeletedmsg = MAXMSG; + } else if (maxdeletedmsg > MAXMSGLIMIT) { + ast_log(LOG_WARNING, "Maximum number of deleted messages saved per mailbox is %i. Cannot accept value '%s'\n", MAXMSGLIMIT, val); + maxdeletedmsg = MAXMSGLIMIT; + } + } + /* Load date format config for voicemail mail */ if ((val = ast_variable_retrieve(cfg, "general", "emaildateformat"))) { ast_copy_string(emaildateformat, val, sizeof(emaildateformat)); |