如何在Xamarin中安全存储密钥?

时间:2016-06-29 04:47:27

标签: android ios xamarin xamarin.forms

说,我想在移动设备上本地保存几个键值条目,安全。看起来,我可以使用Android的KeyStore和iOS的Keychain,并将ILocalStorage实现注入PCL。但是,我没有找到任何使用这两个的例子。你能告诉我如何做到这一点或提供资源吗?或者告诉我一个更好的方法来实现我想要实现的目标?提前谢谢。

2 个答案:

答案 0 :(得分:4)

您好请参阅https://developer.xamarin.com/recipes/cross-platform/xamarin-forms/general/store-credentials/中的示例 它利用Android中的kestore和iOS中的密钥链

除了我在MVVM交叉

中完成了这个实现
public class PersistantStorageHelper<T>
    {
        IMvxFileStoreAsync _mvxFileStoreAsync;
        IMvxFileStore _mvxFileStore;
        EDEngine bcEngine = new EDEngine(new AesEngine(), Encoding.UTF8);
        string currentkey_temp_dev = "AthulHarikumar00";//This static key is not being used it is a just a place holder

        public PersistantStorageHelper() {
            this._mvxFileStore = Mvx.Resolve<IMvxFileStore>();
            this._mvxFileStoreAsync = Mvx.Resolve<IMvxFileStoreAsync>();
            bcEngine.SetPadding(new Pkcs7Padding());
            currentkey_temp_dev = Constants.PassPhrase.Substring(4, 12)+"Road";
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="obj"></param>
        /// <returns></returns>
        public async Task<T> GetPersistantObject(T obj)
        {
            var fileName = (typeof(T).ToString().Replace(".", "_"));
           var x= await GetPersistantObject(obj, fileName);
            return x;
        }
        /// <summary>
        /// If object exists returns the object else saves a plain object and returns it
        /// </summary>
        /// <param name="obj">empty placeholder object</param>
        /// <returns>Filesystem object</returns>
        public async Task<T> GetPersistantObject( T obj,string fileName) {

            List<string> files = new List<string>(_mvxFileStore.GetFilesIn(_mvxFileStore.NativePath("")));
            fileName = _mvxFileStore.NativePath(fileName);

            if (!files.Contains(fileName))
            {
                var objJson = Newtonsoft.Json.JsonConvert.SerializeObject(obj);

                objJson= bcEngine.Encrypt(objJson, currentkey_temp_dev);
                await _mvxFileStoreAsync.WriteFileAsync(fileName,objJson);
            }
            else {
                try
                {

                    var temp = await _mvxFileStoreAsync.TryReadTextFileAsync(fileName);
                    var str = bcEngine.Decrypt(temp.Result, currentkey_temp_dev);
                    obj = Newtonsoft.Json.JsonConvert.DeserializeObject<T>(str);
                }
                catch(Exception e) {
                    var objJson = Newtonsoft.Json.JsonConvert.SerializeObject(obj);

                    objJson = bcEngine.Encrypt(objJson, currentkey_temp_dev);
                    await _mvxFileStoreAsync.WriteFileAsync(fileName, objJson);
                }
            }

            return obj;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="obj"></param>
        /// <returns></returns>
        public async Task<T> SetPersistantObject(T obj)
        {
            var fileName = _mvxFileStore.NativePath(typeof(T).ToString().Replace(".", "_"));
            var temp = await SetPersistantObject(obj, fileName);
            return temp;

        }
        /// <summary>
        /// Saves object to persistant storage with encryption
        /// </summary>
        /// <param name="obj">object to be stored</param>
        /// <returns>Saved object</returns>
        public async Task<T> SetPersistantObject(T obj,string fileName)
        {

            List<string> files = new List<string>(_mvxFileStore.GetFilesIn(_mvxFileStore.NativePath("")));
             fileName = _mvxFileStore.NativePath(fileName);


                var objJson = Newtonsoft.Json.JsonConvert.SerializeObject(obj);
            objJson = bcEngine.Encrypt(objJson, currentkey_temp_dev);
            await _mvxFileStoreAsync.WriteFileAsync(fileName, objJson);



            return obj;
        }
    }

在初始创建时将密码短语注入GUID,保存在Keystore / Keychain / Vault中,这将加密数据并使用密码存储提供您提供的任何对象

答案 1 :(得分:2)

你有两个选择。

Sq Lite。此选项是跨平台的,如果您有大量数据,则可以正常运行。您还获得了事务支持和异步支持的额外奖励。这里有详细记录:https://github.com/oysteinkrog/SQLite.Net-PCL

在Xamarin.Forms中也实现了Application properties,允许简单的Key-Value数据对。 你必须调查并找出最符合你需求的路线。

就安全性而言,这取决于您将数据放在每台设备上的位置。 Android默认情况下将应用数据存储在安全的应用程序文件夹中(如果您已植根,则不安全)。 iOS根据不同的需求为数据存储提供了几个不同的文件夹。