我正在使用Windows 10& Visual Studio 2015用于开发和定位Android,iOS,Windows Phone,Windows Universal。
我想使用 XLabs SecureStorage服务。
我正在使用XLabs.Platform包2.3.0-pre02。
此行我正在异常(仅适用于UWP)
secureStorage.Store(key, Encoding.UTF8.GetBytes(value));
并且例外详情为:
FileName :System.Runtime.WindowsRuntime,Version = 4.0.11.0,Culture = neutral,PublicKeyToken = b77a5c561934e089
HResult : - 2146234304
HelpLink :null
InnerException :null
消息:无法加载文件或程序集“System.Runtime.WindowsRuntime,Version = 4.0.11.0,Culture = neutral,PublicKeyToken = b77a5c561934e089”或其中一个依赖项。定位的程序集的清单定义与程序集引用不匹配。 (HRESULT异常:0x80131040)
来源:XLabs.Platform.UWP
SourceTrack :位于XLabs.Platform.Services.SecureStorage.d__6.MoveNext()
在System.Runtime.CompilerServices.AsyncVoidMethodBuilder.StartTStateMachine
在XLabs.Platform.Services.SecureStorage.Store(String key, Byte[] dataBytes)
在UWPTest.SecureStorageService.Store(String key, String value, Boolean overwrite)
答案 0 :(得分:1)
经过一些试验和错误后,我能够在Xamarin UWP上成功运行SecureStorage服务。
<强> SecureStorage.cs(代码)强>
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ABC.UWP.Common
{
using System;
using System.IO;
using Windows.Storage;
using System.Threading;
using System.Runtime.InteropServices.WindowsRuntime;
using XLabs.Platform.Services;
using Windows.Security.Cryptography.DataProtection;
/// <summary>
/// Implements <see cref="ISecureStorage"/> for WP using <see cref="IsolatedStorageFile"/> and <see cref="ProtectedData"/>.
/// </summary>
public class SecureStorage : ISecureStorage
{
private static Windows.Storage.ApplicationData AppStorage { get { return ApplicationData.Current; } }
private static Windows.Security.Cryptography.DataProtection.DataProtectionProvider _dataProtectionProvider = new DataProtectionProvider();
private readonly byte[] _optionalEntropy;
/// <summary>
/// Initializes a new instance of <see cref="SecureStorage"/>.
/// </summary>
/// <param name="optionalEntropy">Optional password for additional entropy to make encyption more complex.</param>
public SecureStorage(byte[] optionalEntropy)
{
this._optionalEntropy = optionalEntropy;
}
/// <summary>
/// Initializes a new instance of <see cref="SecureStorage"/>.
/// </summary>
public SecureStorage() : this(null)
{
}
#region ISecureStorage Members
/// <summary>
/// Stores the specified key.
/// </summary>
/// <param name="key">The key.</param>
/// <param name="dataBytes">The data bytes.</param>
public async void Store(string key, byte[] dataBytes)
{
//var mutex = new Mutex(false, key);
using (var mutex = new Mutex(false, key))
{
try
{
mutex.WaitOne();
var buffer = dataBytes.AsBuffer();
if (_optionalEntropy != null)
{
buffer = await _dataProtectionProvider.ProtectAsync(buffer);
}
var file = await AppStorage.LocalFolder.CreateFileAsync(key, CreationCollisionOption.ReplaceExisting);
await FileIO.WriteBufferAsync(file, buffer);
}
catch (Exception ex)
{
throw new Exception(string.Format("No entry found for key {0}.", key), ex);
}
}
//finally
//{
// mutex.ReleaseMutex();
//}
}
/// <summary>
/// Retrieves the specified key.
/// </summary>
/// <param name="key">The key.</param>
/// <returns>System.Byte[].</returns>
/// <exception cref="System.Exception"></exception>
public byte[] Retrieve(string key)
{
var mutex = new Mutex(false, key);
try
{
mutex.WaitOne();
return Task.Run(async () =>
{
var file = await AppStorage.LocalFolder.GetFileAsync(key);
var buffer = await FileIO.ReadBufferAsync(file);
if (_optionalEntropy != null)
{
buffer = _dataProtectionProvider.UnprotectAsync(buffer).GetResults();
}
return buffer.ToArray();
}).Result;
}
catch (Exception ex)
{
throw new Exception(string.Format("No entry found for key {0}.", key), ex);
}
finally
{
mutex.ReleaseMutex();
}
}
/// <summary>
/// Deletes the specified key.
/// </summary>
/// <param name="key">The key.</param>
public void Delete(string key)
{
var mutex = new Mutex(false, key);
try
{
mutex.WaitOne();
Task.Run(async () =>
{
var file = await AppStorage.LocalFolder.GetFileAsync(key);
await file.DeleteAsync();
});
}
finally
{
mutex.ReleaseMutex();
}
}
/// <summary>
/// Checks if the storage contains a key.
/// </summary>
/// <param name="key">The key to search.</param>
/// <returns>True if the storage has the key, otherwise false. </returns>
public bool Contains(string key)
{
try
{
return Task.Run(async() => await AppStorage.LocalFolder.GetFileAsync(key)).Result.IsAvailable;
}
catch
{
return false;
}
}
#endregion
}
}