about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
authorJames Booth <boothj5@gmail.com>2014-05-11 18:13:04 +0100
committerJames Booth <boothj5@gmail.com>2014-05-11 18:13:04 +0100
commit6d955609c56a2a303eb141cbd7ba0cc2a364ef37 (patch)
tree22320f6c509cc47bcc5a5425b361204f5c5af82c /src
parent2aa39fc362fd9ab681e86d87eeb7109973416a21 (diff)
downloadprofani-tty-6d955609c56a2a303eb141cbd7ba0cc2a364ef37.tar.gz
Added /otr policy for contacts in account preferences
Diffstat (limited to 'src')
-rw-r--r--src/command/commands.c43
-rw-r--r--src/config/accounts.c115
-rw-r--r--src/config/accounts.h1
3 files changed, 148 insertions, 11 deletions
diff --git a/src/command/commands.c b/src/command/commands.c
index d8721834..27b03c53 100644
--- a/src/command/commands.c
+++ b/src/command/commands.c
@@ -2656,15 +2656,18 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             cons_show("Usage: %s", help.usage);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "warn") == 0) {
         gboolean result =  _cmd_set_boolean_preference(args[1], help,
             "OTR warning message", PREF_OTR_WARN);
         ui_current_update_virtual();
         return result;
+
     } else if (strcmp(args[0], "libver") == 0) {
         char *version = otr_libotr_version();
         cons_show("Using libotr version %s", version);
         return TRUE;
+
     } else if (strcmp(args[0], "policy") == 0) {
         if (args[1] == NULL) {
             char *policy = prefs_get_string(PREF_OTR_POLICY);
@@ -2673,19 +2676,27 @@ cmd_otr(gchar **args, struct cmd_help_t help)
         }
 
         char *choice = args[1];
-        if (g_strcmp0(choice, "manual") == 0) {
-            prefs_set_string(PREF_OTR_POLICY, "manual");
-            cons_show("OTR policy is now set to: manual");
-        } else if (g_strcmp0(choice, "opportunistic") == 0) {
-            prefs_set_string(PREF_OTR_POLICY, "opportunistic");
-            cons_show("OTR policy is now set to: opportunistic");
-        } else if (g_strcmp0(choice, "always") == 0) {
-            prefs_set_string(PREF_OTR_POLICY, "always");
-            cons_show("OTR policy is now set to: always");
-        } else {
+        if ((g_strcmp0(choice, "manual") != 0) &&
+                (g_strcmp0(choice, "opportunistic") != 0) &&
+                (g_strcmp0(choice, "always") != 0)) {
             cons_show("OTR policy can be set to: manual, opportunistic or always.");
+            return TRUE;
+        }
+
+        char *contact = args[2];
+        if (contact == NULL) {
+            prefs_set_string(PREF_OTR_POLICY, choice);
+            cons_show("OTR policy is now set to: %s", choice);
+            return TRUE;
+        } else {
+            char *contact_jid = roster_barejid_from_name(contact);
+            if (contact_jid == NULL) {
+                contact_jid = contact;
+            }
+            accounts_add_otr_policy(jabber_get_account_name(), contact_jid, choice);
+            cons_show("OTR policy for %s set to: %s", contact_jid, choice);
+            return TRUE;
         }
-        return TRUE;
     }
 
     if (jabber_get_connection_status() != JABBER_CONNECTED) {
@@ -2697,6 +2708,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
         ProfAccount *account = accounts_get_account(jabber_get_account_name());
         otr_keygen(account);
         return TRUE;
+
     } else if (strcmp(args[0], "myfp") == 0) {
         if (!otr_key_loaded()) {
             ui_current_print_formatted_line('!', 0, "You have not generated or loaded a private key, use '/otr gen'");
@@ -2706,6 +2718,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             free(fingerprint);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "theirfp") == 0) {
         win_type_t win_type = ui_current_win_type();
 
@@ -2720,6 +2733,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             free(fingerprint);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "start") == 0) {
         if (args[1] != NULL) {
             char *contact = args[1];
@@ -2766,6 +2780,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             }
         }
         return TRUE;
+
     } else if (strcmp(args[0], "end") == 0) {
         win_type_t win_type = ui_current_win_type();
 
@@ -2779,6 +2794,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             otr_end_session(recipient);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "trust") == 0) {
         win_type_t win_type = ui_current_win_type();
 
@@ -2792,6 +2808,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             otr_trust(recipient);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "untrust") == 0) {
         win_type_t win_type = ui_current_win_type();
 
@@ -2805,6 +2822,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             otr_untrust(recipient);
         }
         return TRUE;
+
     } else if (strcmp(args[0], "secret") == 0) {
         win_type_t win_type = ui_current_win_type();
         if (win_type != WIN_CHAT) {
@@ -2821,6 +2839,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             }
         }
         return TRUE;
+
     } else if (strcmp(args[0], "question") == 0) {
         char *question = args[1];
         char *answer = args[2];
@@ -2840,6 +2859,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             }
             return TRUE;
         }
+
     } else if (strcmp(args[0], "answer") == 0) {
         win_type_t win_type = ui_current_win_type();
         if (win_type != WIN_CHAT) {
@@ -2856,6 +2876,7 @@ cmd_otr(gchar **args, struct cmd_help_t help)
             }
         }
         return TRUE;
+
     } else {
         cons_show("Usage: %s", help.usage);
         return TRUE;
diff --git a/src/config/accounts.c b/src/config/accounts.c
index cf7c4c93..79b9eceb 100644
--- a/src/config/accounts.c
+++ b/src/config/accounts.c
@@ -57,6 +57,8 @@ static gchar *string_keys[] = {
 static void _fix_legacy_accounts(const char * const account_name);
 static void _save_accounts(void);
 static gchar * _get_accounts_file(void);
+static void _remove_from_list(GKeyFile *accounts, const char * const account_name, const char * const key, const char * const contact_jid);
+
 
 static void
 _accounts_load(void)
@@ -399,6 +401,118 @@ _accounts_clear_otr(const char * const account_name)
 }
 
 static void
+_accounts_add_otr_policy(const char * const account_name, const char * const contact_jid, const char * const policy)
+{
+    if (accounts_account_exists(account_name)) {
+        GString *key = g_string_new("otr.");
+        g_string_append(key, policy);
+        gsize length;
+        gchar **list = g_key_file_get_string_list(accounts, account_name, key->str, &length, NULL);
+        GList *glist = NULL;
+
+        // list found
+        if (list != NULL) {
+            int i = 0;
+            for (i = 0; i < length; i++) {
+                // item already in list, exit function
+                if (strcmp(list[i], contact_jid) == 0) {
+                    g_list_free_full(glist, g_free);
+                    g_strfreev(list);
+                    return;
+                }
+                // add item to our g_list
+                glist = g_list_append(glist, strdup(list[i]));
+            }
+
+            // item not found, add to our g_list
+            glist = g_list_append(glist, strdup(contact_jid));
+
+            // create the new list entry
+            const gchar* new_list[g_list_length(glist)+1];
+            GList *curr = glist;
+            i = 0;
+            while (curr != NULL) {
+                new_list[i++] = strdup(curr->data);
+                curr = g_list_next(curr);
+            }
+            new_list[i] = NULL;
+            g_key_file_set_string_list(accounts, account_name, key->str, new_list, g_list_length(glist));
+
+        // list not found
+        } else {
+            const gchar* new_list[2];
+            new_list[0] = strdup(contact_jid);
+            new_list[1] = NULL;
+            g_key_file_set_string_list(accounts, account_name, key->str, new_list, 1);
+        }
+
+        g_strfreev(list);
+        g_list_free_full(glist, g_free);
+        g_string_free(key, TRUE);
+
+        // check for and remove from other lists
+        if (strcmp(policy, "manual") == 0) {
+            _remove_from_list(accounts, account_name, "otr.opportunistic", contact_jid);
+            _remove_from_list(accounts, account_name, "otr.always", contact_jid);
+        }
+        if (strcmp(policy, "opportunistic") == 0) {
+            _remove_from_list(accounts, account_name, "otr.manual", contact_jid);
+            _remove_from_list(accounts, account_name, "otr.always", contact_jid);
+        }
+        if (strcmp(policy, "always") == 0) {
+            _remove_from_list(accounts, account_name, "otr.opportunistic", contact_jid);
+            _remove_from_list(accounts, account_name, "otr.manual", contact_jid);
+        }
+
+        _save_accounts();
+    }
+}
+
+static void
+_remove_from_list(GKeyFile *accounts, const char * const account_name, const char * const key, const char * const contact_jid)
+{
+    gsize length;
+    gchar **list = g_key_file_get_string_list(accounts, account_name, key, &length, NULL);
+
+    if (list != NULL) {
+        int i = 0;
+        GList *glist = NULL;
+        gboolean deleted = FALSE;
+
+        for (i = 0; i < length; i++) {
+            // item found, mark as deleted
+            if (strcmp(list[i], contact_jid) == 0) {
+                deleted = TRUE;
+            } else {
+                // add item to our g_list
+                glist = g_list_append(glist, strdup(list[i]));
+            }
+        }
+
+        if (deleted) {
+            if (g_list_length(glist) == 0) {
+                g_key_file_remove_key(accounts, account_name, key, NULL);
+            } else {
+                // create the new list entry
+                const gchar* new_list[g_list_length(glist)+1];
+                GList *curr = glist;
+                i = 0;
+                while (curr != NULL) {
+                    new_list[i++] = strdup(curr->data);
+                    curr = g_list_next(curr);
+                }
+                new_list[i] = NULL;
+                g_key_file_set_string_list(accounts, account_name, key, new_list, g_list_length(glist));
+            }
+        }
+
+        g_list_free_full(glist, g_free);
+    }
+
+    g_strfreev(list);
+}
+
+static void
 _accounts_set_muc_service(const char * const account_name, const char * const value)
 {
     if (accounts_account_exists(account_name)) {
@@ -699,5 +813,6 @@ accounts_init_module(void)
     accounts_get_priority_for_presence_type = _accounts_get_priority_for_presence_type;
     accounts_clear_password = _accounts_clear_password;
     accounts_clear_otr = _accounts_clear_otr;
+    accounts_add_otr_policy = _accounts_add_otr_policy;
 }
 
diff --git a/src/config/accounts.h b/src/config/accounts.h
index 60f8aa04..e2a75a46 100644
--- a/src/config/accounts.h
+++ b/src/config/accounts.h
@@ -67,5 +67,6 @@ gint (*accounts_get_priority_for_presence_type)(const char * const account_name,
     resource_presence_t presence_type);
 void (*accounts_clear_password)(const char * const account_name);
 void (*accounts_clear_otr)(const char * const account_name);
+void (*accounts_add_otr_policy)(const char * const account_name, const char * const contact_jid, const char * const policy);
 
 #endif