Storing Passwords in Gnome Keyring
Multiple keyrings are present on a users system. All users will have a default keyring, and another which is only stored in memory. The following constants represent those keyrings:
GNOME_KEYRING_SESSION /* A keyring only stored in memory */ GNOME_KEYRING_DEFAULT /* Stored on disk, and usually unlocked automatically on login */
Each password in a keyring has a set of attributes. These attributes used to find that specific password later. Attributes are either a string or a unsigned integer. See below for examples on how to pass attributes to gnome-keyring.
The names and types of attributes for a given type of password are defined in a schema. Certain schemas are predefined, and by using such a schema other programs will be able to interoperate with yours. Additional schemas can be defined via a GnomeKeyringPasswordSchema structure.
The predefined schemas are:
GNOME_KEYRING_NETWORK_PASSWORD
- user: A string for the user login.
- server: A string for the server being connected to.
- protocol: A string for the protocol used to access the server, such as 'http' or 'smb'.
- domain: A string for the realm or domain, such as a Windows login domain.
- port: An integer describing the network port to used to connect to the server.
Almost every function in gnome-keyring comes in synchronous and asynchronous styles. The synchronous types may block your application for an indefinite amount of time (usually due to user prompts). It's usually best to use the asynchronous versions.
More info on keyrings is available here.
Saving a password
Use the gnome_keyring_store_password() function to save a password.
Make sure that the set of attributes you associate with the password are unique. If another password is already stored in the keyring with the same attributes, it will be replaced.
If you want to store a password for the users current session only, use the keyring GNOME_KEYRING_SESSION.
Here's an example:
/* A callback called when operation completes */ static void stored_password (GnomeKeyringResult res, gpointer user_data) { /* user_data will be the same as was passed to gnome_keyring_store_password() */ if (res == GNOME_KEYRING_RESULT_OK) g_print ("password saved successfully!\n"); else g_print ("couldn't save password: %s", gnome_keyring_result_to_message (res)); } static void save_my_password() { gnome_keyring_store_password (GNOME_KEYRING_NETWORK_PASSWORD, /* The password type */ GNOME_KEYRING_DEFAULT, /* Where to save it */ _("My special password"), /* Password description, displayed to user */ "the-password", /* The password itself */ stored_password, /* A function called when complete */ NULL, NULL, /* User data for callback, and destroy notify */ /* These are the attributes */ "user", "me", "server", "gnome.org", NULL); /* Always end with NULL */ }
There are other more powerful APIs for creating items in keyrings (ie: gnome_keyring_item_create()).
Finding a password
Use the gnome_keyring_find_password() function to lookup a password.
All the users keyrings will be searched for a password that matches the given set of attributes. This includes keyrings in memory, on disk or perhaps on removable media. If more than one password matches the set of attributes, any of them can be returned.
Here's an example:
/* A callback called when the operation completes */ static void found_password (GnomeKeyringResult res, const gchar* password, gpointer user_data) { /* user_data will be the same as was passed to gnome_keyring_find_password() */ if (res == GNOME_KEYRING_RESULT_OK) g_print ("password found was: %s\n", password); else g_print ("couldn't find password: %s", gnome_keyring_result_to_message (res)); /* Once this function returns |password| will be freed */ } static void find_my_password() { gnome_keyring_find_password (GNOME_KEYRING_NETWORK_PASSWORD, /* The password type */ found_password, /* A function called when complete */ NULL, NULL, /* User data for callback, and destroy notify */ /* These are the attributes */ "user", "me", "server", "gnome.org", NULL); /* Always end with NULL */ }
There are other more powerful APIs for finding items in keyrings (ie: gnome_keyring_find_items()).
Deleting a password
Use the gnome_keyring_delete_password() function to delete a password.
The first password in any of the users keyrings that matches the given set of attributes will be deleted. In addition any matching passwords in memory only keyring will be deleted.
Here's an example:
/* A callback called when the operation completes */ static void deleted_password (GnomeKeyringResult res, gpointer user_data) { /* user_data will be the same as was passed to gnome_keyring_delete_password() */ if (res == GNOME_KEYRING_RESULT_OK) g_print ("password was deleted!\n"); else g_print ("couldn't delete password: %s", gnome_keyring_result_to_message (res)); } static void delete_my_password() { gnome_keyring_delete_password (GNOME_KEYRING_NETWORK_PASSWORD, /* The password type */ deleted_password, /* A function called when complete */ NULL, NULL, /* User data for callback, and destroy notify */ /* These are the attributes */ "user", "me", "server", "gnome.org", NULL); /* Always end with NULL */ }
There are other more powerful APIs for deleting items from keyrings (ie: gnome_keyring_item_delete()).