首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >过期后不会删除ServiceStack Ormlite缓存项

过期后不会删除ServiceStack Ormlite缓存项
EN

Stack Overflow用户
提问于 2017-06-13 14:41:36
回答 2查看 136关注 0票数 1

我们将serviceStack缓存与OrmLite提供者(MySql)结合使用。我们注意到,当我们创建带有到期日期的缓存密钥时,这些密钥在到期日期之后不会被删除。相反,它们在“ExpiryDate”列中获得空值。因此,在计算Cache.GetTimeToLive()时会产生奇怪的值。

这是serviceStack中的一个bug,还是键创建代码中的错误?我们使用的是ServiceStack版本(4.5.4)和OrmLite版本(4.5.4)

代码语言:javascript
复制
        IAppSettings appSettings = new AppSettings();

        var userConsultsPerHourLimit = appSettings.Get<int>("throttling:consultations:requests:perHourLimit");
        var userConsultsPerDayLimit = appSettings.Get<int>("throttling:consultations:requests:perDayLimit");
        var userConsultsPerMonthLimit = appSettings.Get<int>("throttling:consultations:requests:perMonthLimit");

        var userConsultsMadePerHour = Cache.GetOrCreate<int>(UserConsultPerHourCacheKey, TimeSpan.FromHours(1), () => { return 0; });
        var userConsultsMadePerDay = Cache.GetOrCreate<int>(UserConsultPerDayCacheKey, TimeSpan.FromDays(1), () => { return 0; });
        var userConsultsMadePerMonth = Cache.GetOrCreate<int>(UserConsultPerMonthCacheKey, (new DateTime(DateTime.UtcNow.Year, DateTime.UtcNow.Month, 1).AddMonths(1).AddDays(-1) - DateTime.UtcNow), () => { return 0; });

        string retryAfter = System.Threading.Thread.CurrentThread.CurrentCulture.Name == "ar-SA" ? "يوم" : "day";

        bool shouldThrottleRequest = false;
        bool didExceedMonthlyLimit = false;

        if (userConsultsMadePerHour >= userConsultsPerHourLimit)
        {
            shouldThrottleRequest = true;
            TimeSpan? timeToLive = Cache.GetTimeToLive(UserConsultPerHourCacheKey);
            if (timeToLive.HasValue)
                retryAfter = Humanizer.TimeSpanHumanizeExtensions.Humanize(timeToLive.Value, 2, System.Threading.Thread.CurrentThread.CurrentUICulture);
        }
        else if (userConsultsMadePerDay >= userConsultsPerDayLimit)
        {
            shouldThrottleRequest = true;
            TimeSpan? timeToLive = Cache.GetTimeToLive(UserConsultPerDayCacheKey);
            if (timeToLive.HasValue)
                retryAfter = Humanizer.TimeSpanHumanizeExtensions.Humanize(timeToLive.Value, 2, System.Threading.Thread.CurrentThread.CurrentUICulture);
        }
        else if (userConsultsMadePerMonth >= userConsultsPerMonthLimit)
        {
            shouldThrottleRequest = true;
            TimeSpan? timeToLive = Cache.GetTimeToLive(UserConsultPerMonthCacheKey);
            if (timeToLive.HasValue)
                retryAfter = Humanizer.TimeSpanHumanizeExtensions.Humanize(timeToLive.Value, 3, System.Threading.Thread.CurrentThread.CurrentUICulture);
            didExceedMonthlyLimit = true;
        }
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2017-06-19 20:37:24

我想我们找到了真相..。这是由于我们一方对缓存API的误用造成的。我们在其他不同的地方发现了对"Increment“和”deleted“API的API调用,导致删除密钥(那些已经超过到期日期的密钥)(通过内部调用验证方法),然后从头重新创建(但没有终止日期)。解决方案是在调用Increment/ date之前调用GetOrCreate,以确保密钥确实存在,如果不存在,则使用新的过期日期值重新创建它。

票数 1
EN

Stack Overflow用户

发布于 2017-06-13 17:44:31

这是按预期工作,在ServiceStack的最新版本中,在获取过期的缓存条目后删除行:

代码语言:javascript
复制
var ormliteCache = Cache as OrmLiteCacheClient;
var key = "int:key";

var value = Cache.GetOrCreate(key, TimeSpan.FromMilliseconds(100), () => 1);
var ttl = Cache.GetTimeToLive(key);

using (var db = ormliteCache.DbFactory.OpenDbConnection())
{
    var row = db.SingleById<CacheEntry>(key);
    Assert.That(row, Is.Not.Null);
    Assert.That(row.ExpiryDate, Is.Not.Null);
}

Assert.That(value, Is.EqualTo(1));
Assert.That(ttl.Value.TotalMilliseconds, Is.GreaterThan(0));

Thread.Sleep(200);
value = Cache.Get<int>(key);
ttl = Cache.GetTimeToLive(key);

Assert.That(value, Is.EqualTo(0));
Assert.That(ttl, Is.Null);

using (var db = ormliteCache.DbFactory.OpenDbConnection())
{
    var row = db.SingleById<CacheEntry>(key);
    Assert.That(row, Is.Null);
}

我们注意到,当我们创建带有到期日期的缓存密钥时,这些密钥在到期日期之后不会被删除。

关系数据库管理系统不会按日期自动过期缓存条目,但是当解析缓存条目时,OrmLiteCacheClient将自动删除过期条目(如上文所示),因此它将永远不会返回过期的条目。

相反,它们在“ExpiryDate”列中获得空值。

这是不可能的只有在创建或替换现有条目时才填充ExpiryDate,它在过期时从未设置为null。当条目过期时,整个条目将被删除。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/44524688

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档