Skip to content
This repository has been archived by the owner on Aug 1, 2022. It is now read-only.

Commit

Permalink
Merge pull request #17 from anthonytsavdaridis/develop
Browse files Browse the repository at this point in the history
Add async methods + tests
  • Loading branch information
peters authored Sep 15, 2020
2 parents 25cc675 + a2c7bb2 commit 66d7a39
Show file tree
Hide file tree
Showing 7 changed files with 368 additions and 4 deletions.
52 changes: 50 additions & 2 deletions src/BrakePedal.NETStandard.Redis/RedisThrottleRepository.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

using StackExchange.Redis;

namespace BrakePedal.NETStandard.Redis
Expand All @@ -27,6 +29,17 @@ public RedisThrottleRepository(IDatabase database)
return null;
}

public async Task<long?> GetThrottleCountAsync(IThrottleKey key, Limiter limiter)
{
string id = CreateThrottleKey(key, limiter);
RedisValue value = await _db.StringGetAsync(id);
long convert;
if (long.TryParse(value, out convert))
return convert;

return null;
}

public void AddOrIncrementWithExpiration(IThrottleKey key, Limiter limiter)
{
string id = CreateThrottleKey(key, limiter);
Expand All @@ -39,12 +52,32 @@ public void AddOrIncrementWithExpiration(IThrottleKey key, Limiter limiter)
_db.KeyExpire(id, limiter.Period);
}

public async Task AddOrIncrementWithExpirationAsync(IThrottleKey key, Limiter limiter)
{
string id = CreateThrottleKey(key, limiter);

long result = await _db.StringIncrementAsync(id);

// If we get back 1, that means the key was incremented as it
// was expiring or it's a new key. Ensure we set the expiration.
if (result == 1)
{
await _db.KeyExpireAsync(id, limiter.Period);
}
}

public bool LockExists(IThrottleKey key, Limiter limiter)
{
string id = CreateLockKey(key, limiter);
return _db.KeyExists(id);
}

public Task<bool> LockExistsAsync(IThrottleKey key, Limiter limiter)
{
string id = CreateLockKey(key, limiter);
return _db.KeyExistsAsync(id);
}

public void SetLock(IThrottleKey key, Limiter limiter)
{
string id = CreateLockKey(key, limiter);
Expand All @@ -54,12 +87,27 @@ public void SetLock(IThrottleKey key, Limiter limiter)
trans.Execute();
}

public async Task SetLockAsync(IThrottleKey key, Limiter limiter)
{
string id = CreateLockKey(key, limiter);
ITransaction trans = _db.CreateTransaction();
await trans.StringIncrementAsync(id);
await trans.KeyExpireAsync(id, limiter.LockDuration);
await trans.ExecuteAsync();
}

public void RemoveThrottle(IThrottleKey key, Limiter limiter)
{
string id = CreateThrottleKey(key, limiter);
_db.KeyDelete(id);
}

public Task RemoveThrottleAsync(IThrottleKey key, Limiter limiter)
{
string id = CreateThrottleKey(key, limiter);
return _db.KeyDeleteAsync(id);
}

public string CreateThrottleKey(IThrottleKey key, Limiter limiter)
{
List<object> values = CreateBaseKeyValues(key, limiter);
Expand All @@ -75,7 +123,7 @@ public string CreateThrottleKey(IThrottleKey key, Limiter limiter)
string id = string.Join(":", values);
return id;
}

public string CreateLockKey(IThrottleKey key, Limiter limiter)
{
List<object> values = CreateBaseKeyValues(key, limiter);
Expand All @@ -86,7 +134,7 @@ public string CreateLockKey(IThrottleKey key, Limiter limiter)

string id = string.Join(":", values);
return id;
}
}

private List<object> CreateBaseKeyValues(IThrottleKey key, Limiter limiter)
{
Expand Down
101 changes: 101 additions & 0 deletions src/BrakePedal.NETStandard.Tests/MemoryThrottleRepositoryTests.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
using System;
using System.Threading.Tasks;

using Microsoft.Extensions.Caching.Memory;

using Xunit;

namespace BrakePedal.NETStandard.Tests
Expand Down Expand Up @@ -32,6 +35,30 @@ public void NewObject_SetsCountToOneWithExpiration()
Assert.Equal(new DateTime(2030, 1, 1, 0, 1, 40), item.Expiration);
}

[Fact]
public async Task NewObject_SetsCountToOneWithExpirationAsync()
{
// Arrange
var key = new SimpleThrottleKey("test", "key");
var limiter = new Limiter()
.Limit(1)
.Over(100);
var cache = new MemoryCache(new MemoryCacheOptions());
var repository = new MemoryThrottleRepository(cache);
repository.CurrentDate = () => new DateTime(2030, 1, 1);

string id = await repository.CreateThrottleKeyAsync(key, limiter);

// Act
await repository.AddOrIncrementWithExpirationAsync(key, limiter);

// Assert
var item = (MemoryThrottleRepository.ThrottleCacheItem)cache.Get(id);
Assert.Equal(1L, item.Count);
// We're testing a future date by 100 seconds which is 40 seconds + 1 minute
Assert.Equal(new DateTime(2030, 1, 1, 0, 1, 40), item.Expiration);
}

[Fact]
public void ExistingObject_IncrementByOneAndSetExpirationDate()
{
Expand Down Expand Up @@ -62,6 +89,35 @@ public void ExistingObject_IncrementByOneAndSetExpirationDate()
Assert.Equal(new DateTime(2030, 1, 1), item.Expiration);
}

[Fact]
public async Task ExistingObject_IncrementByOneAndSetExpirationDateAsync()
{
// Arrange
var key = new SimpleThrottleKey("test", "key");
var limiter = new Limiter()
.Limit(1)
.Over(100);
var cache = new MemoryCache(new MemoryCacheOptions());
var repository = new MemoryThrottleRepository(cache);
string id = repository.CreateThrottleKey(key, limiter);

var cacheItem = new MemoryThrottleRepository.ThrottleCacheItem()
{
Count = 1,
Expiration = new DateTime(2030, 1, 1)
};

cache
.Set(id, cacheItem, cacheItem.Expiration);

// Act
await repository.AddOrIncrementWithExpirationAsync(key, limiter);

// Assert
var item = (MemoryThrottleRepository.ThrottleCacheItem)cache.Get(id);
Assert.Equal(2L, item.Count);
Assert.Equal(new DateTime(2030, 1, 1), item.Expiration);
}

[Fact]
public void RetrieveValidThrottleCountFromRepostitory()
Expand Down Expand Up @@ -90,6 +146,33 @@ public void RetrieveValidThrottleCountFromRepostitory()
Assert.Equal(1, count);
}

[Fact]
public async Task RetrieveValidThrottleCountFromRepostitoryAsync()
{
// Arrange
var key = new SimpleThrottleKey("test", "key");
var limiter = new Limiter()
.Limit(1)
.Over(100);
var cache = new MemoryCache(new MemoryCacheOptions());
var repository = new MemoryThrottleRepository(cache);
string id = repository.CreateThrottleKey(key, limiter);

var cacheItem = new MemoryThrottleRepository.ThrottleCacheItem()
{
Count = 1,
Expiration = new DateTime(2030, 1, 1)
};

await repository.AddOrIncrementWithExpirationAsync(key, limiter);

// Act
var count = await repository.GetThrottleCountAsync(key, limiter);

// Assert
Assert.Equal(1, count);
}

[Fact]
public void ThrottleCountReturnsNullWhenUsingInvalidKey()
{
Expand All @@ -107,6 +190,24 @@ public void ThrottleCountReturnsNullWhenUsingInvalidKey()
// Assert
Assert.Null(count);
}

[Fact]
public async Task ThrottleCountReturnsNullWhenUsingInvalidKeyAsync()
{
// Arrange
var key = new SimpleThrottleKey("test", "key");
var limiter = new Limiter()
.Limit(1)
.Over(100);
var cache = new MemoryCache(new MemoryCacheOptions());
var repository = new MemoryThrottleRepository(cache);

// Act
var count = await repository.GetThrottleCountAsync(key, limiter);

// Assert
Assert.Null(count);
}
}

public class ThrottleCacheItemTests
Expand Down
Loading

0 comments on commit 66d7a39

Please sign in to comment.