talons

Fork of Claws Mail https://www.claws-mail
Log | Files | Refs | README | LICENSE

commit c3167bf1a4bf76a75813856d48e9d3c00f6c3849
parent b088e814322445b334ba74c1e872f9a29146b7e1
Author: Andrej Kacian <ticho@claws-mail.org>
Date:   Sun,  6 Aug 2017 18:43:43 +0200

Handle config_version update separately for accounts.

Instead of loading entire configuration from all the
files in rcdir and doing an update at the end, we
now upgrade each "part" right after we load it.

This is to allow greater flexibility during the time
not all of the configuration is loaded yet, e.g. folders
using correct folderclass functions, based on protocol
of account owning a particular folder.

This is currently affecting clawsrc and accountrc, but
it will be trivial to extend it to other rcdir files
as needed.

Diffstat:
Msrc/account.c | 2++
Msrc/main.c | 25++++++++++++++++---------
Msrc/prefs_account.c | 3+++
Msrc/prefs_account.h | 2++
Msrc/prefs_common.c | 1+
Msrc/prefs_gtk.c | 2++
Msrc/prefs_migration.c | 159+++++++++++++++++++++++++++++++++++++++++++++++++++++++------------------------
Msrc/prefs_migration.h | 3++-
8 files changed, 139 insertions(+), 58 deletions(-)

diff --git a/src/account.c b/src/account.c @@ -1052,6 +1052,8 @@ static void account_clone(GtkWidget *widget, gpointer data) ac_clon->is_default = FALSE; ACP_FASSIGN(folder); + ACP_FASSIGN(config_version); + account_list = g_list_append(account_list, ac_clon); account_list_view_set(); } diff --git a/src/main.c b/src/main.c @@ -1250,6 +1250,14 @@ int main(int argc, char *argv[]) folder_system_init(); prefs_common_read_config(); + if (prefs_update_config_version_common() < 0) { + debug_print("Main configuration file version upgrade failed, exiting\n"); +#ifdef G_OS_WIN32 + win32_close_log(); +#endif + exit(200); + } + prefs_themes_init(); prefs_fonts_init(); prefs_ext_prog_init(); @@ -1326,6 +1334,14 @@ int main(int argc, char *argv[]) prefs_account_init(); account_read_config_all(); + if (prefs_update_config_version_accounts() < 0) { + debug_print("Accounts configuration file version upgrade failed, exiting\n"); +#ifdef G_OS_WIN32 + win32_close_log(); +#endif + exit(201); + } + #ifdef HAVE_LIBETPAN imap_main_init(prefs_common.skip_ssl_cert_check); imap_main_set_timeout(prefs_common.io_timeout_secs); @@ -1478,17 +1494,8 @@ int main(int argc, char *argv[]) } if (never_ran) { - prefs_common_get_prefs()->config_version = CLAWS_CONFIG_VERSION; prefs_common_write_config(); plugin_load_standard_plugins (); - } else { - if (prefs_update_config_version() < 0) { - exit_claws(mainwin); -#ifdef G_OS_WIN32 - win32_close_log(); -#endif - exit(0); - } } /* if not crashed, show window now */ diff --git a/src/prefs_account.c b/src/prefs_account.c @@ -435,6 +435,9 @@ static PrefParam basic_param[] = { {"password", NULL, &tmp_ac_prefs.passwd, P_PASSWORD, NULL, NULL, NULL}, + {"config_version", "-1", &tmp_ac_prefs.config_version, P_INT, + NULL, NULL, NULL}, + {NULL, NULL, NULL, P_OTHER, NULL, NULL, NULL} }; diff --git a/src/prefs_account.h b/src/prefs_account.h @@ -207,6 +207,8 @@ struct _PrefsAccount struct _Folder *folder; GHashTable *privacy_prefs; SMTPSession *session; + + gint config_version; }; void prefs_account_init (void); diff --git a/src/prefs_common.c b/src/prefs_common.c @@ -41,6 +41,7 @@ #include "prefs_display_header.h" #include "prefs_summary_column.h" #include "prefs_folder_column.h" +#include "prefs_migration.h" #include "mainwindow.h" #include "summaryview.h" #include "folderview.h" diff --git a/src/prefs_gtk.c b/src/prefs_gtk.c @@ -440,6 +440,8 @@ void prefs_set_default(PrefParam *param) if (param[i].defval != NULL) *((gint *)param[i].data) = (gint)atoi(param[i].defval); + else if (!strcmp(param[i].name, "config_version")) + *((gint *)param[i].data) = CLAWS_CONFIG_VERSION; else *((gint *)param[i].data) = 0; break; diff --git a/src/prefs_migration.c b/src/prefs_migration.c @@ -34,14 +34,70 @@ #include "prefs_common.h" #include "alertpanel.h" -static void _update_config(gint version) +static gint starting_config_version = 0; + +gboolean _version_check(gint ver) { - GList *cur; - PrefsAccount *ac_prefs; + if (ver > CLAWS_CONFIG_VERSION) { + gchar *msg; + gchar *markup; + AlertValue av; + + markup = g_strdup_printf( + "<a href=\"%s\"><span underline=\"none\">", + CONFIG_VERSIONS_URI); + msg = g_strdup_printf( + _("Your Claws Mail configuration is from a newer " + "version than the version which you are currently " + "using.\n\n" + "This is not recommended.\n\n" + "For further information see the %sClaws Mail " + "website%s.\n\n" + "Do you want to exit now?"), + markup, "</span></a>"); + g_free(markup); + av = alertpanel_full(_("Configuration warning"), msg, + GTK_STOCK_NO, GTK_STOCK_YES, NULL, + FALSE, NULL, + ALERT_ERROR, G_ALERTALTERNATE); + g_free(msg); + + if (av != G_ALERTDEFAULT) + return FALSE; /* abort startup */ + + return TRUE; /* hic sunt dracones */ + } + + return TRUE; +} +static void _update_config_common(gint version) +{ debug_print("Updating config version %d to %d.\n", version, version + 1); switch (version) { + case 1: + + /* The autochk_interval preference is now + * interpreted as seconds instead of minutes */ + prefs_common.autochk_itv *= 60; + + break; + + default: + + /* NOOP */ + + break; + } +} + +static void _update_config_account(PrefsAccount *ac_prefs, gint version) +{ + debug_print("Account '%s': Updating config version from %d to %d.\n", + ac_prefs->account_name, version, version + 1); + + switch (version) { case 0: /* Removing A_APOP and A_RPOP from RecvProtocol enum, @@ -54,64 +110,35 @@ static void _update_config(gint version) * A_IMAP and the rest are from 3 up. * We can't use the macros, since they may change in the * future. Numbers do not change. :) */ - for (cur = account_get_list(); cur != NULL; cur = cur->next) { - ac_prefs = (PrefsAccount *)cur->data; - if (ac_prefs->protocol == 1) { - ac_prefs->protocol = 0; - } else if (ac_prefs->protocol > 2) { - /* A_IMAP and above gets bumped down by 2. */ - ac_prefs->protocol -= 2; - } + if (ac_prefs->protocol == 1) { + ac_prefs->protocol = 0; + } else if (ac_prefs->protocol > 2) { + /* A_IMAP and above gets bumped down by 2. */ + ac_prefs->protocol -= 2; } break; - case 1: + default: - /* The autochk_interval preference is now - * interpreted as seconds instead of minutes */ - prefs_common.autochk_itv *= 60; + /* NOOP */ break; - - default: - break; } + + ac_prefs->config_version = version + 1; } -int prefs_update_config_version() +int prefs_update_config_version_common() { gint ver = prefs_common_get_prefs()->config_version; - if (ver > CLAWS_CONFIG_VERSION) { - gchar *msg; - gchar *markup; - AlertValue av; - - markup = g_strdup_printf( - "<a href=\"%s\"><span underline=\"none\">", - CONFIG_VERSIONS_URI); - msg = g_strdup_printf( - _("Your Claws Mail configuration is from a newer " - "version than the version which you are currently " - "using.\n\n" - "This is not recommended.\n\n" - "For further information see the %sClaws Mail " - "website%s.\n\n" - "Do you want to exit now?"), - markup, "</span></a>"); - g_free(markup); - av = alertpanel_full(_("Configuration warning"), msg, - GTK_STOCK_NO, GTK_STOCK_YES, NULL, - FALSE, NULL, - ALERT_ERROR, G_ALERTALTERNATE); - g_free(msg); - - if (av != G_ALERTDEFAULT) - return -1; /* abort startup */ + /* Store the starting version number for other components' + * migration functions. */ + starting_config_version = ver; - return 0; /* hic sunt dracones */ - } + if (!_version_check(ver)) + return -1; debug_print("Starting config update at config_version %d.\n", ver); if (ver == CLAWS_CONFIG_VERSION) { @@ -120,10 +147,46 @@ int prefs_update_config_version() } while (ver < CLAWS_CONFIG_VERSION) { - _update_config(ver++); + _update_config_common(ver++); prefs_common_get_prefs()->config_version = ver; } debug_print("Config update done.\n"); return 1; /* update done */ } + +int prefs_update_config_version_accounts() +{ + GList *cur; + PrefsAccount *ac_prefs; + + for (cur = account_get_list(); cur != NULL; cur = cur->next) { + ac_prefs = (PrefsAccount *)cur->data; + + if (ac_prefs->config_version == -1) { + /* There was no config_version stored in accountrc, let's assume + * config_version same as clawsrc started at, to avoid breaking + * this account by "upgrading" it unnecessarily. */ + debug_print("Account '%s': config_version not saved, using one from clawsrc: %d\n", ac_prefs->account_name, starting_config_version); + ac_prefs->config_version = starting_config_version; + } + + gint ver = ac_prefs->config_version; + + debug_print("Account '%s': Starting config update at config_version %d.\n", ac_prefs->account_name, ver); + + if (!_version_check(ver)) + return -1; + + if (ver == CLAWS_CONFIG_VERSION) { + debug_print("Account '%s': No update necessary, already at latest config_version.\n", ac_prefs->account_name); + continue; + } + + while (ver < CLAWS_CONFIG_VERSION) { + _update_config_account(ac_prefs, ver++); + } + } + + return 1; +} diff --git a/src/prefs_migration.h b/src/prefs_migration.h @@ -19,6 +19,7 @@ #ifndef __PREFS_MIGRATION_H__ #define __PREFS_MIGRATION_H__ -int prefs_update_config_version(); +int prefs_update_config_version_common(); +int prefs_update_config_version_accounts(); #endif /* __PREFS_MIGRATION_H__ */