我有UWP应用程序并使用Akavache.添加MobileCenter NuGet包后,我在构建应用程序时遇到了这个问题:
Payload contains two or more files with the same destination path 'SQLitePCLRaw.batteries_v2.dll'.
Source files:C:\Users\user\.nuget\packages\SQLitePCLRaw.bundle_e_sqlite3\1.1.0\lib\uap10.0\SQLitePCLRaw.batteries_v2.dll
C:\Users\user\.nuget\packages\SQLitePCLRaw.bundle_green\1.1.2\lib\uap10.0\SQLitePCLRaw.batteries_v2.dll
Run Code Online (Sandbox Code Playgroud)
如何在不删除Akavache或VSMC的情况下修复它?
我有一个Xamarin.iOS应用程序,它使用Akavache缓存数据并减少不必要的服务器请求数据的数量.一切都像预期的那样运作得很好BlobCache.LocalMachine,喜欢它.
现在我想确保加密后的数据处于静止状态.从在线研究和阅读文档,我发现默认实现并没有实际加密iOS上的缓存,我实际上需要提供自定义实现IEncryptionProvider.
我跟着这篇文章:http://kent-boogaart.com/blog/password-protected-encryption-provider-for-akavache
添加了此线程的输入:https://github.com/akavache/Akavache/issues/190
结束了这个实现:
public interface IPasswordProtectedEncryptionProvider : IEncryptionProvider
{
void SetPassword(string password);
}
public sealed class MyEncryptionProvider : IPasswordProtectedEncryptionProvider
{
static readonly byte[] salt = Encoding.ASCII.GetBytes("dVBZMQWyFRcJOIas");
readonly IScheduler scheduler;
readonly SymmetricAlgorithm symmetricAlgorithm;
ICryptoTransform decryptTransform;
ICryptoTransform encryptTransform;
public MyEncryptionProvider()
{
scheduler = BlobCache.TaskpoolScheduler ?? throw new ArgumentNullException(nameof(scheduler), "Scheduler instance is null");
symmetricAlgorithm = new RijndaelManaged();
var securePassword = "kadhaskdhsakhaskjdhaskjdhaskdjashdkjahkfghkjhew";
SetPassword(securePassword);
}
public void SetPassword(string password)
{
if(password == null) …Run Code Online (Sandbox Code Playgroud) 我有一个Xamarin Android项目,使用共享的PCL库,我决定使用Akavache作为临时数据存储(存储一些简单的登录状态信息,以便每次都保存重新启动).
所以我将Akavache和Akavache.Sqlite3 nuget包添加到共享库(以及Xamarin.Android项目).我设置了BlobCache.ApplicationName,甚至调用EnsureInitialized(这似乎不仅仅是记录消息).
我将应用程序部署到了设备上.手动启动它(因此不会擦除数据和首选项等).只要应用程序正在运行,就会缓存(并检索)数据.如果缺少键,它会抛出异常(如预期的那样).一切都很完美.
然后我关闭了应用程序(在一个阶段我甚至重新启动了手机).当我重新启动它时,缓存是空的,或重新初始化.无论哪种方式,我缓存的一切都消失了.
我在调试器中查看了存储缓存sqlite3文件的位置,该应用程序告诉我他们显然是在 data/data/packagename/cache/xyzblobs.db.我看不到那些文件,因为它们位于内部系统缓存/应用程序文件目录中,因此我不知道它们是否被擦除.
我已经打开了WRITE_EXTERNAL_STORAGE(和READ_)权限.没有骰子.我已经尝试使用Secure,UserAccount和LocalMachine目标.纳达.他们都没有工作.
只要应用程序正在运行(或在内存中),它就会按预期运行.应用消失的那一刻,缓存也是如此.
我唯一没做过的就是调用BlobStorage.Shutdown()方法.那是因为我不知道在哪里调用它.我有多个活动,不想被引用计数因为愚蠢.
编辑:后来我强行打电话.Shutdown().Wait(),这似乎也没有帮助.
还有其他人经历过这个吗?我知道至少有一个人遇到了完全相同的问题,详见Xamarin论坛.
我真的不想把所有的Akavache东西拉出来,因为我之前使用过它,在其他地方没有-Xamarin-Android,它真棒.否则我将不得不开始寻找某种xplat共享偏好管理器,我宁愿不这样做,因为Akavache应该做Just That.
编辑:这是一些代码:
初始化(我有一个静态共享的"AppGlobal"类,用于保存单例类型的东西)
public static class SharedAppGlobal
{
static SharedAppGlobal()
{
BlobCache.ApplicationName = SharedAppConstants.SharedAkavacheCacheName;
BlobCache.EnsureInitialized();
}
}
Run Code Online (Sandbox Code Playgroud)
一切正常,如果我在调试器中启动并查看 BlobCache它告诉我我正在使用Sqlite3存储及其路径(在非root用户的情况下我无法访问sqlite3 .db文件)设备)
我可以通过类似的方式调用缓存获取/设置
currentCookie = await BlobCache.LocalMachine.GetObject<Cookie>("authCookie");
然后用它们写回来
await BlobCache.LocalMachine.InsertObject("authCookie", cookie);
所有Akavache调用都在共享库中进行.我使用哪个商店(Secure,UserAccount或LocalMachine)并不重要,行为是一样的.
一切都很完美.然后我退出应用程序.重新打开应用程序(我可以重新启动手机以确保它已消失),并且缓存为空.或重置.或重新制作.我不知道是哪个,因为我看不到.db文件.
我不是在调试器下运行并且每次都重新部署.因此,部署目录不会被破坏.即使我安装了apk,也会发生这种情况.我认为它可能与那些不是它们所在的db文件有关,但我完全失去了.
我是否需要在特定于平台的级别实现某些功能并将其传递给共享库?我不这么认为,因为所有的依赖关系和路径似乎都得到了解决.
我浪费了几个小时.
谢谢 :)
我有一个Xamarin.Forms应用程序,在我的App类中使用此代码(是的,这只是一个演示问题的示例):
public App()
{
BlobCache.ApplicationName = "MyApp";
BlobCache.EnsureInitialized();
// The root page of your application
MainPage = GetMainPage();
}
public object BlockingGetExternalUser()
{
return GetExternalUser().Result;
}
private async Task<object> GetExternalUser()
{
try
{
return await BlobCache.LocalMachine.GetObject<object>("user");
}
catch (KeyNotFoundException)
{
return null;
}
}
Run Code Online (Sandbox Code Playgroud)
密钥"用户"不存在,所以我希望得到一个KeyNotFoundException.但是我从来没有看到过抛出这个异常.相反,它只是"挂起",永远不会从await GetObject调用返回.
我在Android 5.0手机上运行此功能.
任何想法如何解决这一问题?我做了一些根本错误的事吗?
更新:旁注:不是立即尝试GetObject,而是可以尝试检查密钥是否实际存在于缓存中,然后才从缓存中检索它.但是,如果我没有弄错的话,除了调用GetObject并捕获异常之外没有其他方法可以进行检查,就像上面的示例一样.对于一个人只想知道项目是否存在的情况,这似乎并不理想.也许在Akavache中使用"存在()"方法会很好吗?或许我错过了什么?
Update2:更改示例以在构造函数中不使用async方法.只是为了证明这不是问题.
Update3:从构造函数中删除调用.当我从代码中的任何地方调用BlockingGetExternalUser时,await仍会挂起.
是否有任何人愿意并且愿意分享Akavache在Xamarin.iOS项目中使用自定义实例的理想情况(理想情况下,没有在ui框架上添加任何其他内容,尽可能地做到无骨),EncryptionProvider以便对安全缓存进行实际加密。
为了澄清,我希望该示例显示以下内容:
Xamarin.iOS构建简单的iOS应用Akavache缓存数据Akavache的BlobCache.Secure或SQLiteEncryptedBlobCache用自定义EncryptionProvider执行,以保持加密的缓存数据时,数据是在休息谢谢你的帮助。
在下面的示例的帮助下,我使我的测试解决方案正常工作,并在此与任何可能对将来有所帮助的人共享:https : //github.com/dmitrysamuylov/xamarin-ios-akavache-secure-example
我为JSON.NET设置了全局转换器默认值,如下所示:
var jsonSerializerSettings = new JsonSerializerSettings
{
Converters = new JsonConverter[] { new QuestionTypeConverter() }
};
JsonConvert.DefaultSettings = () => jsonSerializerSettings;
Run Code Online (Sandbox Code Playgroud)
这适用于我的其余代码("QuestionTypeConverter"正在使用并按预期工作),但是,当从Akavache缓存中检索对象时,我的"QuestionTypeConverter"被忽略,因此我的对象无法正确反序列化.如何使用Akavache强制使用我的自定义类型转换器,或者让Akavache使用JSON.NET的默认设置?
我正在使用Akavache缓存本地对象。我希望能够删除数据库中的所有内容(就像是第一次运行该程序一样)。我已经看到了Vacuum方法,但是只能删除过期的旧项目。清理所有内容的简便方法是什么?
我现在已经苦苦挣扎了4个小时,现在我正在转圈.我正在尝试让Akavache为我的项目运行.该项目是开箱即用的Xamarin Forms(Portable)类型.然后使用Nuget我添加了Akavache 4.1.2(它还添加了Akavache Core和SqlLite3以及ReactiveUI和Splat).然后我更新了Splat,因为nuget包中的依赖是错误的(1.3.3但应该是1.6.0).但是,当我添加你应该具有的第一行(BlobCache.ApplicationName ="MyApp")时,我仍然在启动此应用程序时出错(现在定位到iOS):
System.TypeInitializationException: The type initializer for 'Akavache.BlobCache' threw an exception. ---> System.Exception: Failed to initialize Akavache properly. Do you have a reference to Akavache.dll?
at Akavache.Sqlite3.Registrations.Register (IMutableDependencyResolver resolver) [0x0001f] in <filename unknown>:0
at Akavache.DependencyResolverMixin.InitializeAkavache (IMutableDependencyResolver This) [0x000c0] in <filename unknown>:0
at Akavache.BlobCache.<.cctor>b__0 () [0x0000d] in <filename unknown>:0
at Splat.Locator.RegisterResolverCallbackChanged (System.Action callback) [0x00039] in <filename unknown>:0
at Akavache.BlobCache..cctor () [0x00018] in <filename unknown>:0
Run Code Online (Sandbox Code Playgroud)
PS使用Xamarin 4.1.0运行VS 2015社区
所以我试图在使用Akavache的应用程序中测试缓存行为.我的测试看起来像这样:
using Akavache;
using Microsoft.Reactive.Testing;
using Moq;
using NUnit.Framework;
using ReactiveUI.Testing;
using System;
using System.Threading.Tasks;
[TestFixture]
public class CacheFixture
{
[Test]
public async Task CachingTest()
{
var scheduler = new TestScheduler();
// replacing the TestScheduler with the scheduler below works
// var scheduler = CurrentThreadScheduler.Instance;
var cache = new InMemoryBlobCache(scheduler);
var someApi = new Mock<ISomeApi>();
someApi.Setup(s => s.GetSomeStrings())
.Returns(Task.FromResult("helloworld")).Verifiable();
var apiWrapper = new SomeApiWrapper(someApi.Object, cache,
TimeSpan.FromSeconds(10));
var string1 = await apiWrapper.GetSomeStrings();
someApi.Verify(s => s.GetSomeStrings(), Times.Once());
StringAssert.AreEqualIgnoringCase("helloworld", string1);
scheduler.AdvanceToMs(5000);
// without …Run Code Online (Sandbox Code Playgroud) 我应该使用 akavache 作为我的 xamarin 表单应用程序中的主要本地数据库还是另一个 sqlite 数据库之上的缓存数据库?因为我找不到任何关于如何在 akavache 对象中更新、插入、删除数据的示例。例如,
CacheItems= await BlobCache.LocalMachine.GetOrFetchObject<List<Item>>("CacheItems",
async () => await getdatafromAzure(recursive));
Run Code Online (Sandbox Code Playgroud)
我从 azure 获取项目并存储在本地机器中,这些项目是可编辑/可删除的,或者用户可以添加新项目。我该怎么做?
我正在尝试在Xamarin.Forms项目中使用Akavache GetAndFetchLatest方法,但它没有按照我的预期工作,并希望有人能够找到我出错的地方.
我正在调用这样的方法:
BlobCache.Secure.GetAndFetchLatest (cacheId, FetchOrganizations, dt => true);
Run Code Online (Sandbox Code Playgroud)
我的应用程序第一次启动时,FetchOrganizations方法按预期调用,我可以看到我的本地服务器处理请求.但是,只要Akavache缓存了数据,它就只返回缓存,并且再也不会调用FetchOrganizations方法.我的服务器从未看到另一个请求 如果我使用短暂超时,则在缓存过期时将调用FetchOrganizations方法.我已经尝试过使用fetchPredicate参数,但这似乎没有帮助.
还有另一种方法可以让GetAndFetchLatest总是尝试获取新数据吗?我误解了fetchPredicate是如何工作的吗?
akavache ×12
c# ×3
xamarin.ios ×3
android ×2
ios ×2
xamarin ×2
encryption ×1
json ×1
security ×1
unit-testing ×1
uwp ×1