jmasterx
jmasterx

Reputation: 54173

Safe way to store web api credentials?

My web application logs into a web api. This needs an email and password. I cannot hash these in my database because the api requires the password in plain text.

How can I store my web api credentials in a safer way than plain text, xor, or base64? Is there a 'proper' solution for this sort of thing?

Upvotes: 1

Views: 2327

Answers (1)

Scott Chamberlain
Scott Chamberlain

Reputation: 127603

Yes there is, the ProtectedData class, it lets you encrypt a object tied to a windows user acount, so if the user.config file is copied to another user/computer it will not work

In your Settings file, create two string properties named ApiUsername and ApiPassword, then click "View Code at the top and add the following functions

internal sealed partial class Settings {

    private MD5 md5 = MD5.Create();
    public global::System.Net.NetworkCredential ApiLogin
    {
        get
        {
            global::System.Net.NetworkCredential tmp = null;
            if (ApiPassword != "")
            {
                tmp = new System.Net.NetworkCredential();
                tmp.UserName = ApiUsername;
                try
                {
                    tmp.Password = System.Text.Encoding.UTF8.GetString(ProtectedData.Unprotect(Convert.FromBase64String(ApiPassword), md5.ComputeHash(System.Text.Encoding.UTF8.GetBytes(ApiUsername.ToUpper())), DataProtectionScope.CurrentUser));
                }
                catch
                {
                    tmp.Password = "";
                }
            }
            return tmp;
        }
        set
        {
            global::System.Net.NetworkCredential tmp2 = value;
            ApiUsername = tmp2.UserName;
            ApiPassword = Convert.ToBase64String(ProtectedData.Protect(System.Text.Encoding.UTF8.GetBytes(tmp2.Password), md5.ComputeHash(System.Text.Encoding.UTF8.GetBytes(tmp2.UserName.ToUpper())), DataProtectionScope.CurrentUser));

        }
    }
}

This will add a accessable property called ApiLogin which will contain a NetworkCredential with the decrpted password, when you save the credentials to the disk it stores it in that encrpted protected form that can't be copied to other users.

If the decryption fails it sets the password to blank in the returned credential. If you want the decrption to work on any useraccount on that single machine change the ProtectionScope to DataProtectionScope.LocalMachine.

Upvotes: 2

Related Questions