public async Task MaintainOnlyOldIndexesWithPartialAliasesAsync()
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(SystemClock.UtcNow.EndOfYear());

                var index = new MonthlyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.SubtractMonths(12).StartOfMonth()
                };

                await index.EnsureIndexAsync(SystemClock.UtcNow.SubtractMonths(11));

                await index.EnsureIndexAsync(SystemClock.UtcNow.SubtractMonths(12));

                var existsResponse = await _client.IndexExistsAsync(index.GetIndex(SystemClock.UtcNow.SubtractMonths(12)));

                _logger.Trace(() => existsResponse.GetRequest());
                Assert.True(existsResponse.IsValid);
                Assert.True(existsResponse.Exists);

                index.MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.StartOfMonth();
                await DeleteAliasesAsync(index.GetVersionedIndex(SystemClock.UtcNow.SubtractMonths(12)));

                await index.MaintainAsync();

                existsResponse = await _client.IndexExistsAsync(index.GetIndex(SystemClock.UtcNow.SubtractMonths(12)));

                _logger.Trace(() => existsResponse.GetRequest());
                Assert.True(existsResponse.IsValid);
                Assert.False(existsResponse.Exists);
            }
        }
        public async Task GetDateOffsetAggregationsAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(utcNow);

                var today = SystemClock.OffsetNow.Floor(TimeSpan.FromMilliseconds(1));

                await _employeeRepository.AddAsync(new List <Employee> {
                    EmployeeGenerator.Generate(nextReview: today.SubtractDays(2)),
                    EmployeeGenerator.Generate(nextReview: today.SubtractDays(1)),
                    EmployeeGenerator.Generate(nextReview: today)
                }, o => o.ImmediateConsistency());

                const string aggregations = "min:nextReview max:nextReview date:nextReview";
                var          result       = await _employeeRepository.GetCountByQueryAsync(q => q.AggregationsExression(aggregations));

                Assert.Equal(3, result.Total);
                Assert.Equal(3, result.Aggregations.Count);

                // Dates are always returned in utc.
                AssertEqual(DateTime.SpecifyKind(today.UtcDateTime.SubtractDays(2), DateTimeKind.Utc), result.Aggregations.Min <DateTime>("min_nextReview")?.Value);
                AssertEqual(DateTime.SpecifyKind(today.UtcDateTime, DateTimeKind.Utc), result.Aggregations.Max <DateTime>("max_nextReview")?.Value);

                var dateHistogramAgg = result.Aggregations.DateHistogram("date_nextReview");
                Assert.Equal(3, dateHistogramAgg.Buckets.Count);
                var oldestDate = DateTime.SpecifyKind(today.UtcDateTime.Date.SubtractDays(2), DateTimeKind.Utc);
                foreach (var bucket in dateHistogramAgg.Buckets)
                {
                    AssertEqual(oldestDate, bucket.Date);
                    Assert.Equal(1, bucket.Total);
                    oldestDate = oldestDate.AddDays(1);
                }
            }
        }
        public async Task MaintainOnlyOldIndexesWithNoExistingAliasesAsync()
        {
            using (TestSystemClock.Install()) {
                TestSystemClock.SetFrozenTime(SystemClock.UtcNow.EndOfYear());

                var index = new MonthlyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.SubtractMonths(12).StartOfMonth()
                };

                await index.EnsureIndexAsync(SystemClock.UtcNow.SubtractMonths(12));

                var existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(SystemClock.UtcNow.SubtractMonths(12)));

                _logger.LogRequest(existsResponse);
                Assert.True(existsResponse.ApiCall.Success);
                Assert.True(existsResponse.Exists);

                index.MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.StartOfMonth();
                await DeleteAliasesAsync(index.GetVersionedIndex(SystemClock.UtcNow.SubtractMonths(12)));

                await index.MaintainAsync();

                existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(SystemClock.UtcNow.SubtractMonths(12)));

                _logger.LogRequest(existsResponse);
                Assert.True(existsResponse.ApiCall.Success);
                Assert.False(existsResponse.Exists);
            }
        }
        public virtual async Task CanSetMinMaxExpirationAsync()
        {
            var cache = GetCacheClient();

            if (cache == null)
            {
                return;
            }

            using (cache) {
                await cache.RemoveAllAsync();

                using (TestSystemClock.Install()) {
                    var now = DateTime.UtcNow;
                    TestSystemClock.SetFrozenTime(now);

                    var expires = DateTime.MaxValue - now.AddDays(1);
                    Assert.True(await cache.SetAsync("test1", 1, expires));
                    Assert.False(await cache.SetAsync("test2", 1, DateTime.MinValue));
                    Assert.True(await cache.SetAsync("test3", 1, DateTime.MaxValue));
                    Assert.True(await cache.SetAsync("test4", 1, DateTime.MaxValue - now.AddDays(-1)));

                    Assert.Equal(1, (await cache.GetAsync <int>("test1")).Value);
                    Assert.InRange((await cache.GetExpirationAsync("test1")).Value, expires.Subtract(TimeSpan.FromSeconds(10)), expires);

                    Assert.False(await cache.ExistsAsync("test2"));
                    Assert.Equal(1, (await cache.GetAsync <int>("test3")).Value);
                    Assert.False((await cache.GetExpirationAsync("test3")).HasValue);
                    Assert.Equal(1, (await cache.GetAsync <int>("test4")).Value);
                    Assert.False((await cache.GetExpirationAsync("test4")).HasValue);
                }
            }
        }
 public void CanGetTime()
 {
     using (TestSystemClock.Install()) {
         var now = DateTime.UtcNow;
         TestSystemClock.SetFrozenTime(now);
         Assert.Equal(now, SystemClock.UtcNow);
         Assert.Equal(now.ToLocalTime(), SystemClock.Now);
         Assert.Equal(now, SystemClock.OffsetUtcNow);
         Assert.Equal(now.ToLocalTime(), SystemClock.OffsetNow);
         Assert.Equal(DateTimeOffset.Now.Offset, SystemClock.TimeZoneOffset);
     }
 }
Example #6
0
        public async Task CanCancelContinuousJobs()
        {
            using (TestSystemClock.Install()) {
                var job = new HelloWorldJob();
                job.RunContinuous(TimeSpan.FromSeconds(1), 5, TimeSpan.FromMilliseconds(100).ToCancellationToken());
                Assert.Equal(1, job.RunCount);

                var runnerTask = new JobRunner(job, Log, instanceCount: 5, iterationLimit: 10000, interval: TimeSpan.FromMilliseconds(1)).RunAsync(TimeSpan.FromMilliseconds(500).ToCancellationToken());
                await SystemClock.SleepAsync(TimeSpan.FromSeconds(1));

                await runnerTask;
            }
        }
Example #7
0
        public void CanSetUtcFixedTime()
        {
            using (TestSystemClock.Install()) {
                var utcNow = DateTime.UtcNow;
                var now    = utcNow.ToLocalTime();
                SystemClock.Test.SetFixedTime(utcNow);

                Assert.Equal(now, SystemClock.Now);
                Assert.Equal(now, SystemClock.OffsetNow);
                Assert.Equal(utcNow, SystemClock.UtcNow);
                Assert.Equal(utcNow, SystemClock.OffsetUtcNow);
                Assert.Equal(DateTimeOffset.Now.Offset, SystemClock.TimeZoneOffset);
            }
        }
        public void CanSetLocalFixedTime()
        {
            using (TestSystemClock.Install()) {
                var now    = DateTime.Now;
                var utcNow = now.ToUniversalTime();
                TestSystemClock.SetFrozenTime(now);

                Assert.Equal(now, SystemClock.Now);
                Assert.Equal(now, SystemClock.OffsetNow);
                Assert.Equal(utcNow, SystemClock.UtcNow);
                Assert.Equal(utcNow, SystemClock.OffsetUtcNow);
                Assert.Equal(DateTimeOffset.Now.Offset, SystemClock.TimeZoneOffset);
            }
        }
        public void CanSetTimeZone()
        {
            using (TestSystemClock.Install()) {
                var utcNow = DateTime.UtcNow;
                var now    = new DateTime(utcNow.AddHours(1).Ticks, DateTimeKind.Local);
                TestSystemClock.SetFrozenTime(utcNow);
                TestSystemClock.SetTimeZoneOffset(TimeSpan.FromHours(1));

                Assert.Equal(utcNow, SystemClock.UtcNow);
                Assert.Equal(utcNow, SystemClock.OffsetUtcNow);
                Assert.Equal(now, SystemClock.Now);
                Assert.Equal(new DateTimeOffset(now.Ticks, TimeSpan.FromHours(1)), SystemClock.OffsetNow);
                Assert.Equal(TimeSpan.FromHours(1), SystemClock.TimeZoneOffset);
            }
        }
Example #10
0
        public async Task CanRunJobsWithIntervalBetweenFailingJob()
        {
            using (TestSystemClock.Install()) {
                var time = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);

                TestSystemClock.SetFrozenTime(time);
                TestSystemClock.UseFakeSleep();

                var job      = new FailingJob(Log);
                var interval = TimeSpan.FromHours(.75);

                await job.RunContinuousAsync(iterationLimit : 2, interval : interval);

                Assert.Equal(2, job.RunCount);
                Assert.Equal(interval, (SystemClock.UtcNow - time));
            }
        }
        public async Task CanRoundTripById()
        {
            using var _ = TestSystemClock.Install();
            TestSystemClock.SetFrozenTime(new DateTime(2020, 6, 16, 20, 0, 0, DateTimeKind.Local));

            Assert.Equal(0, await _dailyRepository.CountAsync());

            var utcNow   = SystemClock.UtcNow;
            var logEvent = await _dailyRepository.AddAsync(LogEventGenerator.Generate(createdUtc: utcNow, date: utcNow.SubtractDays(1)), o => o.ImmediateConsistency());

            Assert.NotNull(logEvent?.Id);

            var ev = await _dailyRepository.GetByIdAsync(logEvent.Id);

            Assert.NotNull(ev);
            Assert.Equal(ev.Date, ObjectId.Parse(ev.Id).CreationTime);
            Assert.NotEqual(ev.Date, ev.CreatedUtc);
        }
Example #12
0
        public async Task CanCancelContinuousJobs()
        {
            using (TestSystemClock.Install()) {
                var job = new HelloWorldJob(Log);
                using (var timeoutCancellationTokenSource = new CancellationTokenSource(100)) {
                    await job.RunContinuousAsync(TimeSpan.FromSeconds(1), 5, timeoutCancellationTokenSource.Token);
                }

                Assert.Equal(1, job.RunCount);

                using (var timeoutCancellationTokenSource = new CancellationTokenSource(500)) {
                    var runnerTask = new JobRunner(job, Log, instanceCount: 5, iterationLimit: 10000, interval: TimeSpan.FromMilliseconds(1)).RunAsync(timeoutCancellationTokenSource.Token);
                    await SystemClock.SleepAsync(TimeSpan.FromSeconds(1));

                    await runnerTask;
                }
            }
        }
        public async Task MonthlyIndexMaxAgeAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(utcNow);

                var index = new MonthlyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.StartOfMonth()
                };
                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    await index.EnsureIndexAsync(utcNow);

                    var existsResponse = await _client.IndexExistsAsync(index.GetIndex(utcNow));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    await index.EnsureIndexAsync(utcNow.Subtract(index.MaxIndexAge.GetValueOrDefault()));

                    existsResponse = await _client.IndexExistsAsync(index.GetIndex(utcNow.Subtract(index.MaxIndexAge.GetValueOrDefault())));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    var endOfTwoMonthsAgo = utcNow.SubtractMonths(2).EndOfMonth();
                    if (utcNow - endOfTwoMonthsAgo >= index.MaxIndexAge.GetValueOrDefault())
                    {
                        await Assert.ThrowsAsync <ArgumentException>(async() => await index.EnsureIndexAsync(endOfTwoMonthsAgo));

                        existsResponse = await _client.IndexExistsAsync(index.GetIndex(endOfTwoMonthsAgo));

                        _logger.Trace(() => existsResponse.GetRequest());
                        Assert.True(existsResponse.IsValid);
                        Assert.False(existsResponse.Exists);
                    }
                }
            }
        }
        public async Task SetCreatedAndModifiedTimesAsync()
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SubtractTime(TimeSpan.FromMilliseconds(100));
                var nowUtc   = SystemClock.UtcNow;
                var employee = await _employeeRepository.AddAsync(EmployeeGenerator.Default);

                Assert.True(employee.CreatedUtc >= nowUtc);
                Assert.True(employee.UpdatedUtc >= nowUtc);

                var createdUtc = employee.CreatedUtc;
                var updatedUtc = employee.UpdatedUtc;

                employee.Name = Guid.NewGuid().ToString();
                SystemClock.Test.AddTime(TimeSpan.FromMilliseconds(100));
                employee = await _employeeRepository.SaveAsync(employee);

                Assert.Equal(createdUtc, employee.CreatedUtc);
                Assert.True(updatedUtc < employee.UpdatedUtc, $"Previous UpdatedUtc: {updatedUtc} Current UpdatedUtc: {employee.UpdatedUtc}");
            }
        }
Example #15
0
        public void CanSleep()
        {
            using (TestSystemClock.Install()) {
                var sw = Stopwatch.StartNew();
                SystemClock.Sleep(250);
                sw.Stop();
                Assert.InRange(sw.ElapsedMilliseconds, 225, 400);

                TestSystemClock.UseFakeSleep();

                var now = SystemClock.UtcNow;
                sw.Restart();
                SystemClock.Sleep(1000);
                sw.Stop();
                var afterSleepNow = SystemClock.UtcNow;

                Assert.InRange(sw.ElapsedMilliseconds, 0, 30);
                Assert.True(afterSleepNow > now);
                Assert.InRange(afterSleepNow.Subtract(now).TotalMilliseconds, 950, 1100);
            }
        }
        public async Task CanCreateMonthlyAliasesAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(utcNow);

                var index = new MonthlyEmployeeIndex(_configuration, 1);
                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    var repository = new EmployeeRepository(index.Employee);

                    for (int i = 0; i < 4; i++)
                    {
                        var employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractMonths(i)));

                        Assert.NotNull(employee?.Id);

                        Assert.Equal(1, await index.GetCurrentVersionAsync());
                        var existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                        _logger.Trace(() => existsResponse.GetRequest());
                        Assert.True(existsResponse.IsValid);
                        Assert.True(existsResponse.Exists);

                        var aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                        _logger.Trace(() => aliasesResponse.GetRequest());
                        Assert.True(aliasesResponse.IsValid);
                        Assert.Equal(1, aliasesResponse.Indices.Count);

                        var aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                        aliases.Sort();

                        Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                    }
                }
            }
        }
        public async Task DailyIndexMaxAgeAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(utcNow);

                var index = new DailyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = TimeSpan.FromDays(1)
                };
                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    await index.EnsureIndexAsync(utcNow);

                    var existsResponse = await _client.IndexExistsAsync(index.GetIndex(utcNow));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    await index.EnsureIndexAsync(utcNow.SubtractDays(1));

                    existsResponse = await _client.IndexExistsAsync(index.GetIndex(utcNow.SubtractDays(1)));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    await Assert.ThrowsAsync <ArgumentException>(async() => await index.EnsureIndexAsync(utcNow.SubtractDays(2)));

                    existsResponse = await _client.IndexExistsAsync(index.GetIndex(utcNow.SubtractDays(2)));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.False(existsResponse.Exists);
                }
            }
        }
        public async Task CanCreateDailyAliasesAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                TestSystemClock.SetFrozenTime(utcNow);
                var index = new DailyEmployeeIndex(_configuration, 1);
                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    IEmployeeRepository repository = new EmployeeRepository(index);

                    for (int i = 0; i < 35; i += 5)
                    {
                        var employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractDays(i)));

                        Assert.NotNull(employee?.Id);

                        Assert.Equal(1, await index.GetCurrentVersionAsync());
                        var existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(employee.CreatedUtc));

                        _logger.LogRequest(existsResponse);
                        Assert.True(existsResponse.ApiCall.Success);
                        Assert.True(existsResponse.Exists);

                        var aliasesResponse = await _client.Indices.GetAliasAsync(index.GetIndex(employee.CreatedUtc));

                        _logger.LogRequest(aliasesResponse);
                        Assert.True(aliasesResponse.IsValid);
                        Assert.Equal(1, aliasesResponse.Indices.Count);

                        var aliases = aliasesResponse.Indices.Values.Single().Aliases.Select(s => s.Key).ToList();
                        aliases.Sort();

                        Assert.Equal(GetExpectedEmployeeDailyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                    }
                }
            }
        }
Example #19
0
 public override Task WorkItemsWillTimeoutAsync()
 {
     using (TestSystemClock.Install()) {
         return(base.WorkItemsWillTimeoutAsync());
     }
 }
 public override Task CanAcquireAndReleaseLockAsync()
 {
     using (TestSystemClock.Install()) {
         return(base.CanAcquireAndReleaseLockAsync());
     }
 }
Example #21
0
        public async Task VerifyCacheKeysAreCorrectAfterAbandon()
        {
            var queue = GetQueue(retries: 2, workItemTimeout: TimeSpan.FromMilliseconds(100), retryDelay: TimeSpan.Zero, runQueueMaintenance: false) as RedisQueue <SimpleWorkItem>;

            if (queue == null)
            {
                return;
            }

            using (TestSystemClock.Install()) {
                using (queue) {
                    var    muxer      = SharedConnection.GetMuxer();
                    var    db         = muxer.GetDatabase();
                    string listPrefix = muxer.IsCluster() ? "{q:SimpleWorkItem}" : "q:SimpleWorkItem";

                    string id = await queue.EnqueueAsync(new SimpleWorkItem {
                        Data = "blah",
                        Id   = 1
                    });

                    _logger.LogTrace("SimpleWorkItem Id: {0}", id);

                    var workItem = await queue.DequeueAsync();

                    await workItem.AbandonAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(1, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.Equal(4, await muxer.CountAllKeysAsync());

                    workItem = await queue.DequeueAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(1, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.Equal(6, await muxer.CountAllKeysAsync());

                    // let the work item timeout and become auto abandoned.
                    TestSystemClock.AddTime(TimeSpan.FromMilliseconds(250));
                    await queue.DoMaintenanceWorkAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(2, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.Equal(1, (await queue.GetQueueStatsAsync()).Timeouts);
                    Assert.InRange(await muxer.CountAllKeysAsync(), 3, 4);

                    // should go to deadletter now
                    workItem = await queue.DequeueAsync();

                    await workItem.AbandonAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:dead"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(3, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.InRange(await muxer.CountAllKeysAsync(), 4, 5);
                }
            }
        }
Example #22
0
        public async Task VerifyCacheKeysAreCorrectAfterAbandonWithRetryDelay()
        {
            var queue = GetQueue(retries: 2, workItemTimeout: TimeSpan.FromMilliseconds(100), retryDelay: TimeSpan.FromMilliseconds(250), runQueueMaintenance: false) as RedisQueue <SimpleWorkItem>;

            if (queue == null)
            {
                return;
            }

            using (TestSystemClock.Install()) {
                using (queue) {
                    var    muxer      = SharedConnection.GetMuxer();
                    var    db         = muxer.GetDatabase();
                    string listPrefix = muxer.IsCluster() ? "{q:SimpleWorkItem}" : "q:SimpleWorkItem";

                    string id = await queue.EnqueueAsync(new SimpleWorkItem {
                        Data = "blah",
                        Id   = 1
                    });

                    var workItem = await queue.DequeueAsync();

                    await workItem.AbandonAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:wait"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(1, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":wait"));
                    Assert.Equal(5, await muxer.CountAllKeysAsync());

                    TestSystemClock.AddTime(TimeSpan.FromSeconds(1));
                    await queue.DoMaintenanceWorkAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:wait"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(1, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":wait"));
                    Assert.InRange(await muxer.CountAllKeysAsync(), 4, 5);

                    workItem = await queue.DequeueAsync();

                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(1, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.True(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":renewed"));
                    Assert.Equal(1, await db.StringGetAsync("q:SimpleWorkItem:" + id + ":attempts"));
                    Assert.InRange(await muxer.CountAllKeysAsync(), 6, 7);

                    await workItem.CompleteAsync();

                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":enqueued"));
                    Assert.False(await db.KeyExistsAsync("q:SimpleWorkItem:" + id + ":dequeued"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:in"));
                    Assert.Equal(0, await db.ListLengthAsync($"{listPrefix}:work"));
                    Assert.InRange(await muxer.CountAllKeysAsync(), 0, 1);
                }
            }
        }
        public async Task MonthlyAliasMaxAgeAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                TestSystemClock.SetFrozenTime(utcNow);

                var index = new MonthlyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = TimeSpan.FromDays(90)
                };
                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    IEmployeeRepository repository = new EmployeeRepository(index);

                    var employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    var existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(existsResponse);
                    Assert.True(existsResponse.ApiCall.Success);
                    Assert.True(existsResponse.Exists);

                    var aliasesResponse = await _client.Indices.GetAliasAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(aliasesResponse);
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    var aliases = aliasesResponse.Indices.Values.Single().Aliases.Select(s => s.Key).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));

                    employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractDays(2)), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(existsResponse);
                    Assert.True(existsResponse.ApiCall.Success);
                    Assert.True(existsResponse.Exists);

                    aliasesResponse = await _client.Indices.GetAliasAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(aliasesResponse);
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    aliases = aliasesResponse.Indices.Values.Single().Aliases.Select(s => s.Key).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));

                    employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractDays(35)), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    existsResponse = await _client.Indices.ExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(existsResponse);
                    Assert.True(existsResponse.ApiCall.Success);
                    Assert.True(existsResponse.Exists);

                    aliasesResponse = await _client.Indices.GetAliasAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.LogRequest(aliasesResponse);
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    aliases = aliasesResponse.Indices.Values.Single().Aliases.Select(s => s.Key).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                }
            }
        }
Example #24
0
        public async Task MaintainMonthlyIndexesAsync()
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(new DateTime(2016, 8, 31, 0, 0, 0, DateTimeKind.Utc));
                var index = new MonthlyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = SystemClock.UtcNow.EndOfMonth() - SystemClock.UtcNow.SubtractMonths(4).StartOfMonth()
                };
                await index.DeleteAsync();

                var utcNow = SystemClock.UtcNow;
                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    var repository = new EmployeeRepository(index.Employee);

                    for (int i = 0; i < 4; i++)
                    {
                        var created  = utcNow.SubtractMonths(i);
                        var employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: created));

                        Assert.NotNull(employee?.Id);

                        Assert.Equal(1, await index.GetCurrentVersionAsync());
                        var existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                        _logger.LogTraceRequest(existsResponse);
                        Assert.True(existsResponse.IsValid);
                        Assert.True(existsResponse.Exists);

                        var aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                        _logger.LogTraceRequest(aliasesResponse);
                        Assert.True(aliasesResponse.IsValid);
                        Assert.Equal(1, aliasesResponse.Indices.Count);

                        var aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                        aliases.Sort();

                        Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                    }

                    await index.MaintainAsync();

                    for (int i = 0; i < 4; i++)
                    {
                        var created  = utcNow.SubtractMonths(i);
                        var employee = await repository.AddAsync(EmployeeGenerator.Generate(createdUtc: created));

                        Assert.NotNull(employee?.Id);

                        Assert.Equal(1, await index.GetCurrentVersionAsync());
                        var existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                        _logger.LogTraceRequest(existsResponse);
                        Assert.True(existsResponse.IsValid);
                        Assert.True(existsResponse.Exists);

                        var aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                        _logger.LogTraceRequest(aliasesResponse);
                        Assert.True(aliasesResponse.IsValid);
                        Assert.Equal(1, aliasesResponse.Indices.Count);

                        var aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                        aliases.Sort();

                        Assert.Equal(GetExpectedEmployeeMonthlyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                    }
                }
            }
        }
 public override Task CanWaitForCounterAsync()
 {
     using (TestSystemClock.Install()) {
         return(base.CanWaitForCounterAsync());
     }
 }
        public async Task MaintainWillCreateAliasesOnTimeSeriesIndexAsync()
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(SystemClock.UtcNow);
                var version1Index = new DailyEmployeeIndex(_configuration, 1);
                await version1Index.DeleteAsync();

                var version2Index = new DailyEmployeeIndex(_configuration, 2);
                await version2Index.DeleteAsync();

                // Indexes don't exist yet so the current version will be the index version.
                Assert.Equal(1, await version1Index.GetCurrentVersionAsync());
                Assert.Equal(2, await version2Index.GetCurrentVersionAsync());

                using (new DisposableAction(() => version1Index.DeleteAsync().GetAwaiter().GetResult())) {
                    await version1Index.ConfigureAsync();

                    await version1Index.EnsureIndexAsync(SystemClock.UtcNow);

                    Assert.True(_client.IndexExists(version1Index.GetVersionedIndex(SystemClock.UtcNow)).Exists);
                    Assert.Equal(1, await version1Index.GetCurrentVersionAsync());

                    // delete all aliases
                    await _configuration.Cache.RemoveAllAsync();
                    await DeleteAliasesAsync(version1Index.GetVersionedIndex(SystemClock.UtcNow));

                    using (new DisposableAction(() => version2Index.DeleteAsync().GetAwaiter().GetResult())) {
                        await version2Index.ConfigureAsync();

                        await version2Index.EnsureIndexAsync(SystemClock.UtcNow);

                        Assert.True(_client.IndexExists(version2Index.GetVersionedIndex(SystemClock.UtcNow)).Exists);
                        Assert.Equal(2, await version2Index.GetCurrentVersionAsync());

                        // delete all aliases
                        await _configuration.Cache.RemoveAllAsync();
                        await DeleteAliasesAsync(version2Index.GetVersionedIndex(SystemClock.UtcNow));

                        await _client.RefreshAsync(Indices.All);

                        var aliasesResponse = await _client.GetAliasAsync(a => a.Index($"{version1Index.GetVersionedIndex(SystemClock.UtcNow)},{version2Index.GetVersionedIndex(SystemClock.UtcNow)}"));

                        Assert.Equal(0, aliasesResponse.Indices.SelectMany(i => i.Value).Count());

                        // Indexes exist but no alias so the oldest index version will be used.
                        Assert.Equal(1, await version1Index.GetCurrentVersionAsync());
                        Assert.Equal(1, await version2Index.GetCurrentVersionAsync());

                        await version1Index.MaintainAsync();

                        aliasesResponse = await _client.GetAliasAsync(a => a.Index(version1Index.GetVersionedIndex(SystemClock.UtcNow)));

                        Assert.Equal(version1Index.Aliases.Count + 1, aliasesResponse.Indices.Single().Value.Count);
                        aliasesResponse = await _client.GetAliasAsync(a => a.Index(version2Index.GetVersionedIndex(SystemClock.UtcNow)));

                        Assert.Equal(0, aliasesResponse.Indices.Single().Value.Count);

                        Assert.Equal(1, await version1Index.GetCurrentVersionAsync());
                        Assert.Equal(1, await version2Index.GetCurrentVersionAsync());
                    }
                }
            }
        }
        public async Task DailyAliasMaxAgeAsync(DateTime utcNow)
        {
            using (TestSystemClock.Install()) {
                SystemClock.Test.SetFixedTime(utcNow);
                var index = new DailyEmployeeIndex(_configuration, 1)
                {
                    MaxIndexAge = TimeSpan.FromDays(45)
                };

                await index.DeleteAsync();

                using (new DisposableAction(() => index.DeleteAsync().GetAwaiter().GetResult())) {
                    await index.ConfigureAsync();

                    var version1Repository = new EmployeeRepository(index.Employee);

                    var employee = await version1Repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    var existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    var aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                    _logger.Trace(() => aliasesResponse.GetRequest());
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    var aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeDailyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));

                    employee = await version1Repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractDays(2)), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                    _logger.Trace(() => aliasesResponse.GetRequest());
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeDailyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));

                    employee = await version1Repository.AddAsync(EmployeeGenerator.Generate(createdUtc: utcNow.SubtractDays(35)), o => o.ImmediateConsistency());

                    Assert.NotNull(employee?.Id);

                    existsResponse = await _client.IndexExistsAsync(index.GetIndex(employee.CreatedUtc));

                    _logger.Trace(() => existsResponse.GetRequest());
                    Assert.True(existsResponse.IsValid);
                    Assert.True(existsResponse.Exists);

                    aliasesResponse = await _client.GetAliasAsync(a => a.Index(index.GetIndex(employee.CreatedUtc)));

                    _logger.Trace(() => aliasesResponse.GetRequest());
                    Assert.True(aliasesResponse.IsValid);
                    Assert.Equal(1, aliasesResponse.Indices.Count);
                    aliases = aliasesResponse.Indices.Values.Single().Select(s => s.Name).ToList();
                    aliases.Sort();
                    Assert.Equal(GetExpectedEmployeeDailyAliases(index, utcNow, employee.CreatedUtc), String.Join(", ", aliases));
                }
            }
        }