public async Task StoreRefreshTokenAsync_should_update_entity()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            var token = new RefreshToken
            {
                AccessToken = new Token
                {
                    ClientId = "test"
                }
            };

            using var s1 = store.OpenAsyncSession();
            await s1.StoreAsync(new Entity.RefreshToken
            {
                Id       = "test",
                ClientId = "test",
                Data     = serializer.Serialize(token)
            }, $"{nameof(Entity.RefreshToken)}/test");

            await s1.SaveChangesAsync();

            using var session = store.OpenAsyncSession();
            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(session), serializer, loggerMock.Object);

            var code = await sut.StoreRefreshTokenAsync(token);

            Assert.Equal("test", code);
        }
        public async Task RevokeAsync()
        {
            //Arrange
            var sut = new RefreshTokenStore(NhibernateSession, ScopeStoreMock.Object, ClientStoreMock.Object);
            var subjectIdToRevoke = Guid.NewGuid().ToString();
            var clientIdToRevoke  = Guid.NewGuid().ToString();

            var testKey  = Guid.NewGuid().ToString();
            var testCode = ObjectCreator.GetRefreshToken();

            var tokenHandle = new Token
            {
                Key       = testKey,
                SubjectId = testCode.SubjectId,
                ClientId  = testCode.ClientId,
                JsonCode  = ConvertToJson(testCode),
                Expiry    = testCode.CreationTime.UtcDateTime.AddSeconds(testCode.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            var testKeyToRevoke  = Guid.NewGuid().ToString();
            var testCodeToRevoke = ObjectCreator.GetRefreshToken(subjectIdToRevoke, clientIdToRevoke);

            var tokenHandleToRevoke = new Token
            {
                Key       = testKeyToRevoke,
                SubjectId = testCodeToRevoke.SubjectId,
                ClientId  = testCodeToRevoke.ClientId,
                JsonCode  = ConvertToJson(testCodeToRevoke),
                Expiry    = testCodeToRevoke.CreationTime.UtcDateTime.AddSeconds(testCodeToRevoke.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            ExecuteInTransaction(session =>
            {
                session.Save(tokenHandle);
                session.Save(tokenHandleToRevoke);
            });

            //Act
            await sut.RevokeAsync(subjectIdToRevoke, clientIdToRevoke);

            ExecuteInTransaction(session =>
            {
                //Assert
                var tokenRevoked = session.Query <Token>()
                                   .SingleOrDefault(t => t.TokenType == TokenType.RefreshToken &&
                                                    t.Key == testKeyToRevoke);

                var tokenNotRevoked = session.Query <Token>()
                                      .SingleOrDefault(t => t.TokenType == TokenType.RefreshToken &&
                                                       t.Key == testKey);

                Assert.Null(tokenRevoked);
                Assert.NotNull(tokenNotRevoked);

                //CleanUp
                session.Delete(tokenNotRevoked);
            });
        }
        public void GetAsync_WhenCalled_ExpectResponse()
        {
            // Arrange
            var mockCacheManager = new Mock<ICacheManager<RefreshToken>>();
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();

            mockCacheConfiguration.Setup(r => r.Get).Returns(new RedisCacheConfigurationEntity { CacheDuration = 1 });

            var keyCallback = default(string);
            mockCacheManager.Setup(r => r.GetAsync(It.IsAny<string>()))
                .Callback((string s) => keyCallback = s)
                .ReturnsAsync(new RefreshToken());

            var refreshTokenStore = new RefreshTokenStore(
                mockCacheManager.Object,
                mockCacheConfiguration.Object);

            // Act
            var stopwatch = Stopwatch.StartNew();

            var authorizationCode = refreshTokenStore.GetAsync("string").Result;

            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            Assert.That(authorizationCode, Is.Not.Null);
            Assert.That(keyCallback, Is.EqualTo("RTS_string"));
        }
        public async Task GetRefreshTokenAsync_should_return_grant_by_hamlder()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            using var s1 = store.OpenAsyncSession();
            await s1.StoreAsync(new Entity.RefreshToken
            {
                Id       = "test",
                ClientId = "test",
                Data     = serializer.Serialize(new Token
                {
                    ClientId = "test"
                })
            }, $"{nameof(Entity.RefreshToken)}/test");

            await s1.SaveChangesAsync();

            using var session = store.OpenAsyncSession();
            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(session), serializer, loggerMock.Object);

            var result = await sut.GetRefreshTokenAsync("test");

            Assert.NotNull(result);
        }
        public async Task RemoveRefreshTokenAsync_by_subjectId_clientId_should_delete_entity()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            using var s1 = store.OpenAsyncSession();
            await s1.StoreAsync(new Entity.RefreshToken
            {
                Id       = "test",
                ClientId = "test",
                UserId   = "test",
                Data     = serializer.Serialize(new Token
                {
                    ClientId = "test"
                })
            }, $"{nameof(Entity.RefreshToken)}/test");

            await s1.SaveChangesAsync();

            using var session = store.OpenAsyncSession();
            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(session), serializer, loggerMock.Object);

            await sut.RemoveRefreshTokensAsync("test", "test");

            using var s2 = store.OpenAsyncSession();

            var result = await s2.LoadAsync <Entity.RefreshToken>($"{nameof(Entity.RefreshToken)}/test");

            Assert.Null(result);
        }
Beispiel #6
0
        /// <summary>
        /// Creates the refresh token.
        /// </summary>
        /// <param name="subject">The subject.</param>
        /// <param name="accessToken">The access token.</param>
        /// <param name="client">The client.</param>
        /// <returns>
        /// The refresh token handle
        /// </returns>
        public virtual async Task <string> CreateRefreshTokenAsync(ClaimsPrincipal subject, Token accessToken, Client client)
        {
            _logger.LogDebug("Creating refresh token");

            int lifetime;

            if (client.RefreshTokenExpiration == TokenExpiration.Absolute)
            {
                _logger.LogDebug("Setting an absolute lifetime: {absoluteLifetime}", client.AbsoluteRefreshTokenLifetime);
                lifetime = client.AbsoluteRefreshTokenLifetime;
            }
            else
            {
                lifetime = client.SlidingRefreshTokenLifetime;
                if (client.AbsoluteRefreshTokenLifetime > 0 && lifetime > client.AbsoluteRefreshTokenLifetime)
                {
                    _logger.LogWarning("Client {clientId}'s configured " + nameof(client.SlidingRefreshTokenLifetime) + " of {slidingLifetime} exceeds its " + nameof(client.AbsoluteRefreshTokenLifetime) + " of {absoluteLifetime}. The refresh_token's sliding lifetime will be capped to the absolute lifetime", client.ClientId, lifetime, client.AbsoluteRefreshTokenLifetime);
                    lifetime = client.AbsoluteRefreshTokenLifetime;
                }

                _logger.LogDebug("Setting a sliding lifetime: {slidingLifetime}", lifetime);
            }

            var refreshToken = new RefreshToken
            {
                CreationTime = Clock.UtcNow.UtcDateTime,
                Lifetime     = lifetime,
                AccessToken  = accessToken
            };

            var handle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshToken);

            return(handle);
        }
 public void Setup()
 {
     base.Setup();
     _clientStore             = new ClientStore(StoreSettings.UsingFolder(TargetFolder));
     _tokenHandleStore        = new TokenHandleStore(StoreSettings.UsingFolder(TargetFolder));
     _refreshTokenHandleStore = new RefreshTokenStore(StoreSettings.UsingFolder(TargetFolder));
     _scopeStore = new ScopeStore(StoreSettings.UsingFolder(TargetFolder));
 }
        private static void CreateSut(out Mock <IAdminStore <RefreshToken> > storeMock,
                                      out RefreshTokenStore sut)
        {
            storeMock = new Mock <IAdminStore <RefreshToken> >();
            var serializerMock = new Mock <IPersistentGrantSerializer>();

            sut = new RefreshTokenStore(storeMock.Object, serializerMock.Object);
        }
        public async Task UpdateByUserCodeAsync_should_throw_when_handle_not_found()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(store.OpenAsyncSession()), serializer, loggerMock.Object);

            await Assert.ThrowsAsync <InvalidOperationException>(() => sut.UpdateRefreshTokenAsync("handle", new RefreshToken()));
        }
Beispiel #10
0
        public override async Task <string> CreateRefreshTokenAsync(RefreshTokenCreationRequest request)
        {
            Logger.LogDebug("Creating refresh token");

            int lifetime;

            if (request.Client.RefreshTokenExpiration == TokenExpiration.Absolute)
            {
                Logger.LogDebug("Setting an absolute lifetime: {absoluteLifetime}",
                                request.Client.AbsoluteRefreshTokenLifetime);
                lifetime = request.Client.AbsoluteRefreshTokenLifetime;
            }
            else
            {
                lifetime = request.Client.SlidingRefreshTokenLifetime;
                if (request.Client.AbsoluteRefreshTokenLifetime > 0 && lifetime > request.Client.AbsoluteRefreshTokenLifetime)
                {
                    Logger.LogWarning(
                        "Client {clientId}'s configured " + nameof(request.Client.SlidingRefreshTokenLifetime) +
                        " of {slidingLifetime} exceeds its " + nameof(request.Client.AbsoluteRefreshTokenLifetime) +
                        " of {absoluteLifetime}. The refresh_token's sliding lifetime will be capped to the absolute lifetime",
                        request.Client.ClientId, lifetime, request.Client.AbsoluteRefreshTokenLifetime);
                    lifetime = request.Client.AbsoluteRefreshTokenLifetime;
                }

                Logger.LogDebug("Setting a sliding lifetime: {slidingLifetime}", lifetime);
            }
            var formCollection = await _scopedHttpContextRequestForm.GetFormCollectionAsync();

            var originGrantType = formCollection["grant_type"];

            var refreshToken = new RefreshTokenExtra()
            {
                Subject                      = request.Subject,
                ClientId                     = request.Client.ClientId,
                Description                  = request.Description,
                AuthorizedScopes             = request.AuthorizedScopes,
                AuthorizedResourceIndicators = request.AuthorizedResourceIndicators,

                CreationTime    = Clock.UtcNow.UtcDateTime,
                Lifetime        = lifetime,
                OriginGrantType = originGrantType
            };

            refreshToken.SetAccessToken(request.AccessToken, request.RequestedResourceIndicator);

            var handle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshToken);

            return(handle);
        }
    /// <summary>
    /// Creates the refresh token.
    /// </summary>
    /// <returns>
    /// The refresh token handle
    /// </returns>
    public virtual async Task <string> CreateRefreshTokenAsync(RefreshTokenCreationRequest request)
    {
        using var activity = Tracing.ServiceActivitySource.StartActivity("DefaultRefreshTokenService.CreateRefreshToken");

        Logger.LogDebug("Creating refresh token");

        int lifetime;

        if (request.Client.RefreshTokenExpiration == TokenExpiration.Absolute)
        {
            Logger.LogDebug("Setting an absolute lifetime: {absoluteLifetime}",
                            request.Client.AbsoluteRefreshTokenLifetime);
            lifetime = request.Client.AbsoluteRefreshTokenLifetime;
        }
        else
        {
            lifetime = request.Client.SlidingRefreshTokenLifetime;
            if (request.Client.AbsoluteRefreshTokenLifetime > 0 && lifetime > request.Client.AbsoluteRefreshTokenLifetime)
            {
                Logger.LogWarning(
                    "Client {clientId}'s configured " + nameof(request.Client.SlidingRefreshTokenLifetime) +
                    " of {slidingLifetime} exceeds its " + nameof(request.Client.AbsoluteRefreshTokenLifetime) +
                    " of {absoluteLifetime}. The refresh_token's sliding lifetime will be capped to the absolute lifetime",
                    request.Client.ClientId, lifetime, request.Client.AbsoluteRefreshTokenLifetime);
                lifetime = request.Client.AbsoluteRefreshTokenLifetime;
            }

            Logger.LogDebug("Setting a sliding lifetime: {slidingLifetime}", lifetime);
        }

        var refreshToken = new RefreshToken
        {
            Subject                      = request.Subject,
            SessionId                    = request.AccessToken.SessionId,
            ClientId                     = request.Client.ClientId,
            Description                  = request.Description,
            AuthorizedScopes             = request.AuthorizedScopes,
            AuthorizedResourceIndicators = request.AuthorizedResourceIndicators,

            CreationTime = Clock.UtcNow.UtcDateTime,
            Lifetime     = lifetime,
        };

        refreshToken.SetAccessToken(request.AccessToken, request.RequestedResourceIndicator);

        var handle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshToken);

        return(handle);
    }
        public async Task RemoveRefreshTokenAsync_should_not_throw_when_entity_not_exist()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            using var session = store.OpenAsyncSession();
            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(session), serializer, loggerMock.Object);

            await sut.RemoveRefreshTokenAsync("test");

            using var s2 = store.OpenAsyncSession();

            var result = await s2.LoadAsync <Entity.RefreshToken>($"{nameof(Entity.RefreshToken)}/test");

            Assert.Null(result);
        }
Beispiel #13
0
        public async Task <string> CreateRefreshTokenAsync(
            ClaimsPrincipal subject, Token accessToken, Client client)
        {
            Logger.LogDebug("Creating refresh token");

            int lifetime;

            if (client.RefreshTokenExpiration == TokenExpiration.Absolute)
            {
                Logger.LogDebug("Setting an absolute lifetime: {absoluteLifetime}",
                                client.AbsoluteRefreshTokenLifetime);
                lifetime = client.AbsoluteRefreshTokenLifetime;
            }
            else
            {
                lifetime = client.SlidingRefreshTokenLifetime;
                if (client.AbsoluteRefreshTokenLifetime > 0 && lifetime > client.AbsoluteRefreshTokenLifetime)
                {
                    Logger.LogWarning(
                        "Client {clientId}'s configured " + nameof(client.SlidingRefreshTokenLifetime) +
                        " of {slidingLifetime} exceeds its " + nameof(client.AbsoluteRefreshTokenLifetime) +
                        " of {absoluteLifetime}. The refresh_token's sliding lifetime will be capped to the absolute lifetime",
                        client.ClientId, lifetime, client.AbsoluteRefreshTokenLifetime);
                    lifetime = client.AbsoluteRefreshTokenLifetime;
                }

                Logger.LogDebug("Setting a sliding lifetime: {slidingLifetime}", lifetime);
            }

            var formCollection = await _scopedHttpContextRequestForm.GetFormCollectionAsync();

            var originGrantType = formCollection["grant_type"];
            var refreshToken    = new RefreshTokenExtra
            {
                CreationTime    = Clock.UtcNow.UtcDateTime,
                Lifetime        = lifetime,
                AccessToken     = accessToken,
                OriginGrantType = originGrantType
            };

            var handle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshToken);

            return(handle);
        }
        public async Task UpdateByUserCodeAsync_should_update_token()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            var token = new RefreshToken
            {
                AccessToken = new Token
                {
                    ClientId = "test"
                }
            };

            using var s1 = store.OpenAsyncSession();
            await s1.StoreAsync(new Entity.RefreshToken
            {
                Id       = "test",
                ClientId = "test",
                Data     = serializer.Serialize(token)
            }, $"{nameof(Entity.RefreshToken)}/test");

            await s1.SaveChangesAsync();

            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(store.OpenAsyncSession()), serializer, loggerMock.Object);

            await sut.UpdateRefreshTokenAsync("test", new RefreshToken
            {
                AccessToken = new Token
                {
                    ClientId    = "test",
                    Description = "test"
                }
            });

            using var s2 = store.OpenAsyncSession();

            var updated = await s2.LoadAsync <Entity.RefreshToken>($"{nameof(Entity.RefreshToken)}/test");

            var data = serializer.Deserialize <RefreshToken>(updated.Data);

            Assert.Equal("test", data.AccessToken.Description);
        }
        public void GetAllAsync_WhenCalled_ExpectThrows()
        {
            // Arrange
            var mockCacheManager = new Mock<ICacheManager<RefreshToken>>();
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();

            mockCacheConfiguration.Setup(r => r.Get).Returns(new RedisCacheConfigurationEntity { CacheDuration = 1 });

            var refreshTokenStore = new RefreshTokenStore(
                mockCacheManager.Object,
                mockCacheConfiguration.Object);

            // Act and Assert
            var stopwatch = Stopwatch.StartNew();

            Assert.Throws<NotImplementedException>(
                () => refreshTokenStore.GetAllAsync("string").GetAwaiter().GetResult());

            stopwatch.Stop();
            this.WriteTimeElapsed(stopwatch);
        }
        public void GetAsync_WhenCalled_ExpectResponse()
        {
            // Arrange
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();
            mockCacheConfiguration.Setup(r => r.Get).Returns(
                new RedisCacheConfigurationEntity
                {
                    CacheDuration = 10,
                    RedisCacheDefaultPrefix = "DEFAULT",
                    UseObjectCompression = false
                });

            var jsonSettingsFactory = new JsonSettingsFactory(new CustomMappersConfiguration());

            var cacheManager = new RedisCacheManager<RefreshToken>(
                RedisHelpers.ConnectionMultiplexer,
                mockCacheConfiguration.Object,
                jsonSettingsFactory.Create());

            var refreshTokenStore = new RefreshTokenStore(
                cacheManager,
                mockCacheConfiguration.Object);

            // Act
            var stopwatch = Stopwatch.StartNew();
            var refreshToken = refreshTokenStore.GetAsync("Existing").Result;
            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            Assert.That(refreshToken, Is.Not.Null);

            Assert.That(refreshToken.Subject, Is.Not.Null);
            Assert.That(refreshToken.AccessToken, Is.Not.Null);
            Assert.That(refreshToken.CreationTime, Is.EqualTo(new DateTimeOffset(new DateTime(2016, 1, 1))));
            Assert.That(refreshToken.LifeTime, Is.EqualTo(1600));
            Assert.That(refreshToken.Scopes, Is.Not.Null);
            Assert.That(refreshToken.Version, Is.EqualTo(1));
        }
        public async Task StoreRefreshTokenAsync_should_create_entity()
        {
            using var store = new RavenDbTestDriverWrapper().GetDocumentStore();
            var serializer = new PersistentGrantSerializer();
            var loggerMock = new Mock <ILogger <RefreshTokenStore> >();

            using var session = store.OpenAsyncSession();
            var sut = new RefreshTokenStore(new ScopedAsynDocumentcSession(session), serializer, loggerMock.Object);

            var code = await sut.StoreRefreshTokenAsync(new RefreshToken
            {
                AccessToken = new Token
                {
                    ClientId = "test"
                }
            });

            using var s2 = store.OpenAsyncSession();

            var result = await s2.LoadAsync <Entity.RefreshToken>($"{nameof(Entity.RefreshToken)}/{code}");

            Assert.NotNull(result);
        }
Beispiel #18
0
        // revoke refresh token only if it belongs to client doing the request
        private async Task <bool> RevokeRefreshTokenAsync(TokenRevocationRequestValidationResult validationResult)
        {
            var token = await RefreshTokenStore.GetRefreshTokenAsync(validationResult.Token);

            if (token != null)
            {
                if (token.ClientId == validationResult.Client.ClientId)
                {
                    Logger.LogDebug("Refresh token revoked");
                    await RefreshTokenStore.RemoveRefreshTokensAsync(token.SubjectId, token.ClientId);

                    await ReferenceTokenStore.RemoveReferenceTokensAsync(token.SubjectId, token.ClientId);
                }
                else
                {
                    Logger.LogWarning("Client {clientId} tried to revoke a refresh token belonging to a different client: {clientId}", validationResult.Client.ClientId, token.ClientId);
                }

                return(true);
            }

            return(false);
        }
Beispiel #19
0
        public override async Task <TokenValidationResult> ValidateRefreshTokenAsync(
            string tokenHandle, Client client)
        {
            //////////////////////////////////////////////////
            // Calling the base ValidateRefreshTokenAsync
            // this covers the obvious failures like Lifetime checks.
            //////////////////////////////////////////////////

            var baseResult = await base.ValidateRefreshTokenAsync(tokenHandle, client);

            if (baseResult.IsError)
            {
                // await RefreshTokenStore.RemoveRefreshTokenAsync(tokenHandle);
                return(baseResult);
            }
            var invalidGrant = new TokenValidationResult
            {
                IsError = true,
                Error   = OidcConstants.TokenErrors.InvalidGrant
            };

            /////////////////////////////////////////////
            // check if refresh token has been consumed
            /////////////////////////////////////////////
            if (baseResult.RefreshToken.ConsumedTime.HasValue)
            {
                if (await AcceptConsumedTokenAsync(baseResult.RefreshToken, client) == false)
                {
                    Logger.LogWarning("Rejecting refresh token because it has been consumed already.");
                    await RefreshTokenStore.RemoveRefreshTokenAsync(tokenHandle);

                    return(invalidGrant);
                }
            }
            baseResult.Client = client;
            return(baseResult);
        }
        public async Task GetAsync()
        {
            //Arrange
            var sut      = new RefreshTokenStore(NhibernateSession, ScopeStoreMock.Object, ClientStoreMock.Object);
            var testKey  = Guid.NewGuid().ToString();
            var testCode = ObjectCreator.GetRefreshToken();

            var tokenHandle = new Token
            {
                Key       = testKey,
                SubjectId = testCode.SubjectId,
                ClientId  = testCode.ClientId,
                JsonCode  = ConvertToJson(testCode),
                Expiry    = testCode.CreationTime.UtcDateTime.AddSeconds(30),
                TokenType = TokenType.RefreshToken
            };

            SetupScopeStoreMock();

            ExecuteInTransaction(session =>
            {
                session.SaveOrUpdate(tokenHandle);
            });

            //Act
            var resultToken = await sut.GetAsync(testKey);

            //Assert
            Assert.NotNull(resultToken);

            //CleanUp
            ExecuteInTransaction(session =>
            {
                session.Delete(tokenHandle);
            });
        }
        public async Task StoreAsync()
        {
            //Arrange
            var sut = new RefreshTokenStore(NhibernateSession, ScopeStoreMock.Object, ClientStoreMock.Object);

            var testKey  = Guid.NewGuid().ToString();
            var testCode = ObjectCreator.GetRefreshToken();

            //Act
            await sut.StoreAsync(testKey, testCode);

            ExecuteInTransaction(session =>
            {
                //Assert
                var token = session.Query <Token>()
                            .SingleOrDefault(t => t.TokenType == TokenType.RefreshToken &&
                                             t.Key == testKey);

                Assert.NotNull(token);

                //CleanUp
                session.Delete(token);
            });
        }
Beispiel #22
0
 /// <inheritdoc/>
 public virtual Task <RefreshToken> GetRefreshTokenAsync(string refreshTokenHandle) =>
 RefreshTokenStore.GetRefreshTokenAsync(refreshTokenHandle);
        public void RemoveAsync_WhenCalled_ExpectAction()
        {
            // Arrange
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();
            mockCacheConfiguration.Setup(r => r.Get).Returns(
                new RedisCacheConfigurationEntity
                {
                    CacheDuration = 10,
                    RedisCacheDefaultPrefix = "DEFAULT",
                    UseObjectCompression = false
                });

            var jsonSettingsFactory = new JsonSettingsFactory(new CustomMappersConfiguration());

            var cacheManager = new RedisCacheManager<RefreshToken>(
                RedisHelpers.ConnectionMultiplexer,
                mockCacheConfiguration.Object,
                jsonSettingsFactory.Create());

            var refreshTokenStore = new RefreshTokenStore(
                cacheManager,
                mockCacheConfiguration.Object);

            // Act
            var stopwatch = Stopwatch.StartNew();

            refreshTokenStore.RemoveAsync("Delete").Wait();

            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            var redisValue = RedisHelpers.ConnectionMultiplexer.GetDatabase().StringGet("DEFAULT_RTS_Delete");

            Assert.That(redisValue.HasValue, Is.False);
        }
        public void StoreAsync_WhenCalled_ExpectAction()
        {
            // Arrange
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();
            mockCacheConfiguration.Setup(r => r.Get).Returns(
                new RedisCacheConfigurationEntity
                {
                    CacheDuration = 10,
                    RedisCacheDefaultPrefix = "DEFAULT",
                    UseObjectCompression = false
                });

            var jsonSettingsFactory = new JsonSettingsFactory(new CustomMappersConfiguration());

            var cacheManager = new RedisCacheManager<RefreshToken>(
                RedisHelpers.ConnectionMultiplexer,
                mockCacheConfiguration.Object,
                jsonSettingsFactory.Create());

            var refreshTokenStore = new RefreshTokenStore(
                cacheManager,
                mockCacheConfiguration.Object);

            var refreshToken = new RefreshToken
            {
                AccessToken = new Token
                {
                    Client = new Client { ClientId = "cid", },
                    Claims = new List<Claim> { new Claim("SubjectId", "sid") }
                },
                CreationTime = new DateTimeOffset(new DateTime(2016, 1, 1)),
                LifeTime = 1600,
                Version = 1,
            };

            // Act
            var stopwatch = Stopwatch.StartNew();
            refreshTokenStore.StoreAsync("KeyToStore", refreshToken).Wait();
            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            var redisValue = RedisHelpers.ConnectionMultiplexer.GetDatabase().StringGet("DEFAULT_RTS_KeyToStore");

            Assert.That(redisValue.HasValue, Is.True);
            Console.WriteLine(redisValue);
        }
Beispiel #25
0
        /// <summary>
        /// Updates the refresh token.
        /// </summary>
        /// <param name="handle">The handle.</param>
        /// <param name="refreshToken">The refresh token.</param>
        /// <param name="client">The client.</param>
        /// <returns>
        /// The refresh token handle
        /// </returns>
        public virtual async Task <string> UpdateRefreshTokenAsync(string handle, RefreshToken refreshToken, Client client)
        {
            _logger.LogDebug("Updating refresh token");

            bool needsCreate = false;
            bool needsUpdate = false;

            if (client.RefreshTokenUsage == TokenUsage.OneTimeOnly)
            {
                _logger.LogDebug("Token usage is one-time only. Generating new handle");

                // delete old one
                await RefreshTokenStore.RemoveRefreshTokenAsync(handle);

                // create new one
                needsCreate = true;
            }

            if (client.RefreshTokenExpiration == TokenExpiration.Sliding)
            {
                _logger.LogDebug("Refresh token expiration is sliding - extending lifetime");

                // if absolute exp > 0, make sure we don't exceed absolute exp
                // if absolute exp = 0, allow indefinite slide
                var currentLifetime = refreshToken.CreationTime.GetLifetimeInSeconds(Clock.UtcNow.UtcDateTime);
                _logger.LogDebug("Current lifetime: {currentLifetime}", currentLifetime.ToString());

                var newLifetime = currentLifetime + client.SlidingRefreshTokenLifetime;
                _logger.LogDebug("New lifetime: {slidingLifetime}", newLifetime.ToString());

                // zero absolute refresh token lifetime represents unbounded absolute lifetime
                // if absolute lifetime > 0, cap at absolute lifetime
                if (client.AbsoluteRefreshTokenLifetime > 0 && newLifetime > client.AbsoluteRefreshTokenLifetime)
                {
                    newLifetime = client.AbsoluteRefreshTokenLifetime;
                    _logger.LogDebug("New lifetime exceeds absolute lifetime, capping it to {newLifetime}", newLifetime.ToString());
                }

                refreshToken.Lifetime = newLifetime;
                needsUpdate           = true;
            }

            if (needsCreate)
            {
                handle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshToken);

                _logger.LogDebug("Created refresh token in store");
            }
            else if (needsUpdate)
            {
                await RefreshTokenStore.UpdateRefreshTokenAsync(handle, refreshToken);

                _logger.LogDebug("Updated refresh token in store");
            }
            else
            {
                _logger.LogDebug("No updates to refresh token done");
            }

            return(handle);
        }
        public async Task GetAllAsync()
        {
            //Arrange
            var sut        = new RefreshTokenStore(NhibernateSession, ScopeStoreMock.Object, ClientStoreMock.Object);
            var subjectId1 = Guid.NewGuid().ToString();
            var subjectId2 = Guid.NewGuid().ToString();

            var testKey1     = Guid.NewGuid().ToString();
            var testCode1    = ObjectCreator.GetRefreshToken(subjectId1);
            var tokenHandle1 = new Token
            {
                Key       = testKey1,
                SubjectId = testCode1.SubjectId,
                ClientId  = testCode1.ClientId,
                JsonCode  = ConvertToJson(testCode1),
                Expiry    = testCode1.CreationTime.UtcDateTime.AddSeconds(testCode1.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            var testKey2     = Guid.NewGuid().ToString();
            var testCode2    = ObjectCreator.GetRefreshToken(subjectId1);
            var tokenHandle2 = new Token
            {
                Key       = testKey2,
                SubjectId = testCode2.SubjectId,
                ClientId  = testCode2.ClientId,
                JsonCode  = ConvertToJson(testCode2),
                Expiry    = testCode2.CreationTime.UtcDateTime.AddSeconds(testCode2.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            var testKey3     = Guid.NewGuid().ToString();
            var testCode3    = ObjectCreator.GetRefreshToken(subjectId2);
            var tokenHandle3 = new Token
            {
                Key       = testKey3,
                SubjectId = testCode3.SubjectId,
                ClientId  = testCode3.ClientId,
                JsonCode  = ConvertToJson(testCode3),
                Expiry    = testCode3.CreationTime.UtcDateTime.AddSeconds(testCode3.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            var testKey4     = Guid.NewGuid().ToString();
            var testCode4    = ObjectCreator.GetRefreshToken(subjectId2);
            var tokenHandle4 = new Token
            {
                Key       = testKey4,
                SubjectId = testCode4.SubjectId,
                ClientId  = testCode4.ClientId,
                JsonCode  = ConvertToJson(testCode4),
                Expiry    = testCode4.CreationTime.UtcDateTime.AddSeconds(testCode4.LifeTime),
                TokenType = TokenType.RefreshToken
            };

            SetupScopeStoreMock();

            ExecuteInTransaction(session =>
            {
                session.SaveOrUpdate(tokenHandle1);
                session.SaveOrUpdate(tokenHandle2);
                session.SaveOrUpdate(tokenHandle3);
                session.SaveOrUpdate(tokenHandle4);
            });

            //Act
            var tokens = (await sut.GetAllAsync(subjectId1)).ToList();

            //Assert
            Assert.True(tokens.Count == 2);
            Assert.True(tokens.All(t => t.SubjectId == subjectId1));

            //CleanUp
            ExecuteInTransaction(session =>
            {
                session.Delete(tokenHandle1);
                session.Delete(tokenHandle2);
                session.Delete(tokenHandle3);
                session.Delete(tokenHandle4);
            });
        }
        public void RemoveAsync_WhenCalled_ExpectAction()
        {
            // Arrange
            var mockCacheManager = new Mock<ICacheManager<RefreshToken>>();
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();

            mockCacheConfiguration.Setup(r => r.Get).Returns(new RedisCacheConfigurationEntity { CacheDuration = 1 });

            var keyCallback = default(string);
            mockCacheManager.Setup(r => r.DeleteAsync(It.IsAny<string>()))
                .Callback((string s) => keyCallback = s)
                .Returns(Task.FromResult(0));

            var refreshTokenStore = new RefreshTokenStore(
                mockCacheManager.Object,
                mockCacheConfiguration.Object);

            // Act
            var stopwatch = Stopwatch.StartNew();

            refreshTokenStore.RemoveAsync("string").Wait();

            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            Assert.That(keyCallback, Is.EqualTo("RTS_string"));
            mockCacheManager.Verify(r => r.DeleteAsync(It.IsAny<string>()), Times.Once());
        }
Beispiel #28
0
        public async Task <string> UpdateRefreshTokenAsync(
            string handle,
            RefreshToken refreshToken,
            Client client)
        {
            Logger.LogDebug("Updating refresh token");

            var refreshTokenExtra = refreshToken as RefreshTokenExtra;
            var clientExtra       = client as ClientExtra;

            bool needsCreate = false;
            bool needsUpdate = false;

            if (client.RefreshTokenUsage == TokenUsage.OneTimeOnly)
            {
                Logger.LogDebug("Token usage is one-time only. Setting current handle as consumed, and generating new handle");

                // flag as consumed
                if (!refreshTokenExtra.ConsumedTime.HasValue)
                {
                    // only track the initial consumed time.
                    refreshTokenExtra.ConsumedTime = Clock.UtcNow.DateTime;
                }
                // increment the attempts used
                refreshTokenExtra.ConsumedAttempts += 1;
                if (!clientExtra.RefreshTokenGraceEnabled)
                {
                    await RefreshTokenStore.UpdateRefreshTokenAsync(handle, refreshTokenExtra);
                }

                // create new one
                needsCreate = true;
            }

            if (client.RefreshTokenExpiration == TokenExpiration.Sliding)
            {
                Logger.LogDebug("Refresh token expiration is sliding - extending lifetime");

                // if absolute exp > 0, make sure we don't exceed absolute exp
                // if absolute exp = 0, allow indefinite slide
                var currentLifetime = refreshTokenExtra.CreationTime.GetLifetimeInSeconds(Clock.UtcNow.UtcDateTime);
                Logger.LogDebug("Current lifetime: {currentLifetime}", currentLifetime.ToString());

                var newLifetime = currentLifetime + client.SlidingRefreshTokenLifetime;
                Logger.LogDebug("New lifetime: {slidingLifetime}", newLifetime.ToString());

                // zero absolute refresh token lifetime represents unbounded absolute lifetime
                // if absolute lifetime > 0, cap at absolute lifetime
                if (client.AbsoluteRefreshTokenLifetime > 0 && newLifetime > client.AbsoluteRefreshTokenLifetime)
                {
                    newLifetime = client.AbsoluteRefreshTokenLifetime;
                    Logger.LogDebug("New lifetime exceeds absolute lifetime, capping it to {newLifetime}",
                                    newLifetime.ToString());
                }

                refreshTokenExtra.Lifetime = newLifetime;
                needsUpdate = true;
            }

            if (needsCreate)
            {
                var oldChild          = refreshTokenExtra.RefeshTokenChild;
                var oldParent         = refreshTokenExtra.RefeshTokenParent;
                var savedConsumedTime = refreshTokenExtra.ConsumedTime;

                // set it to null so that we save non-consumed token
                refreshTokenExtra.ConsumedTime     = null;
                refreshTokenExtra.RefeshTokenChild = null;
                // carry forward the parent.
                refreshTokenExtra.RefeshTokenParent = handle;

                var newHandle = await RefreshTokenStore.StoreRefreshTokenAsync(refreshTokenExtra);

                refreshTokenExtra.ConsumedTime      = savedConsumedTime;
                refreshTokenExtra.RefeshTokenParent = null;
                if (client.RefreshTokenUsage == TokenUsage.OneTimeOnly)
                {
                    Logger.LogDebug("Token usage is one-time only. Setting current handle as consumed, and generating new handle");
                    if (clientExtra.RefreshTokenGraceEnabled)
                    {
                        refreshTokenExtra.RefeshTokenChild = newHandle;
                    }

                    await RefreshTokenStore.UpdateRefreshTokenAsync(
                        handle,
                        refreshTokenExtra);

                    if (clientExtra.RefreshTokenGraceEnabled)
                    {
                        if (!string.IsNullOrWhiteSpace(oldChild))
                        {
                            await RefreshTokenStore.RemoveRefreshTokenAsync(oldChild);
                        }
                        if (!string.IsNullOrWhiteSpace(oldParent))
                        {
                            await RefreshTokenStore.RemoveRefreshTokenAsync(oldParent);
                        }
                    }
                }
                handle = newHandle;
                Logger.LogDebug("Created refresh token in store");
            }
            else if (needsUpdate)
            {
                await RefreshTokenStore.UpdateRefreshTokenAsync(handle, refreshTokenExtra);

                Logger.LogDebug("Updated refresh token in store");
            }
            else
            {
                Logger.LogDebug("No updates to refresh token done");
            }

            return(handle);
        }
        /// <summary>
        /// Updates the refresh token.
        /// </summary>
        /// <returns>
        /// The refresh token handle
        /// </returns>
        public virtual async Task <string> UpdateRefreshTokenAsync(RefreshTokenUpdateRequest request)
        {
            Logger.LogDebug("Updating refresh token");

            var  handle      = request.Handle;
            bool needsCreate = false;
            bool needsUpdate = request.MustUpdate;

            if (request.Client.RefreshTokenUsage == TokenUsage.OneTimeOnly)
            {
                Logger.LogDebug("Token usage is one-time only. Setting current handle as consumed, and generating new handle");

                // flag as consumed
                if (request.RefreshToken.ConsumedTime == null)
                {
                    request.RefreshToken.ConsumedTime = Clock.UtcNow.UtcDateTime;
                    await RefreshTokenStore.UpdateRefreshTokenAsync(handle, request.RefreshToken);
                }

                // create new one
                needsCreate = true;
            }

            if (request.Client.RefreshTokenExpiration == TokenExpiration.Sliding)
            {
                Logger.LogDebug("Refresh token expiration is sliding - extending lifetime");

                // if absolute exp > 0, make sure we don't exceed absolute exp
                // if absolute exp = 0, allow indefinite slide
                var currentLifetime = request.RefreshToken.CreationTime.GetLifetimeInSeconds(Clock.UtcNow.UtcDateTime);
                Logger.LogDebug("Current lifetime: {currentLifetime}", currentLifetime.ToString());

                var newLifetime = currentLifetime + request.Client.SlidingRefreshTokenLifetime;
                Logger.LogDebug("New lifetime: {slidingLifetime}", newLifetime.ToString());

                // zero absolute refresh token lifetime represents unbounded absolute lifetime
                // if absolute lifetime > 0, cap at absolute lifetime
                if (request.Client.AbsoluteRefreshTokenLifetime > 0 && newLifetime > request.Client.AbsoluteRefreshTokenLifetime)
                {
                    newLifetime = request.Client.AbsoluteRefreshTokenLifetime;
                    Logger.LogDebug("New lifetime exceeds absolute lifetime, capping it to {newLifetime}",
                                    newLifetime.ToString());
                }

                request.RefreshToken.Lifetime = newLifetime;
                needsUpdate = true;
            }

            if (needsCreate)
            {
                // set it to null so that we save non-consumed token
                request.RefreshToken.ConsumedTime = null;
                handle = await RefreshTokenStore.StoreRefreshTokenAsync(request.RefreshToken);

                Logger.LogDebug("Created refresh token in store");
            }
            else if (needsUpdate)
            {
                await RefreshTokenStore.UpdateRefreshTokenAsync(handle, request.RefreshToken);

                Logger.LogDebug("Updated refresh token in store");
            }
            else
            {
                Logger.LogDebug("No updates to refresh token done");
            }

            return(handle);
        }
Beispiel #30
0
 /// <inheritdoc/>
 public Task RemoveRefreshTokenAsync(string refreshTokenHandle) =>
 RefreshTokenStore.RemoveRefreshTokenAsync(refreshTokenHandle);
Beispiel #31
0
        /// <summary>
        /// Validates a refresh token
        /// </summary>
        /// <param name="tokenHandle">The token handle.</param>
        /// <param name="client">The client.</param>
        /// <returns></returns>
        public virtual async Task <TokenValidationResult> ValidateRefreshTokenAsync(string tokenHandle, Client client)
        {
            var invalidGrant = new TokenValidationResult
            {
                IsError = true, Error = OidcConstants.TokenErrors.InvalidGrant
            };

            Logger.LogTrace("Start refresh token validation");

            /////////////////////////////////////////////
            // check if refresh token is valid
            /////////////////////////////////////////////
            var refreshToken = await RefreshTokenStore.GetRefreshTokenAsync(tokenHandle);

            if (refreshToken == null)
            {
                Logger.LogWarning("Invalid refresh token");
                return(invalidGrant);
            }

            /////////////////////////////////////////////
            // check if refresh token has expired
            /////////////////////////////////////////////
            if (refreshToken.CreationTime.HasExceeded(refreshToken.Lifetime, Clock.UtcNow.DateTime))
            {
                Logger.LogWarning("Refresh token has expired.");
                return(invalidGrant);
            }

            /////////////////////////////////////////////
            // check if client belongs to requested refresh token
            /////////////////////////////////////////////
            if (client.ClientId != refreshToken.ClientId)
            {
                Logger.LogError("{0} tries to refresh token belonging to {1}", client.ClientId, refreshToken.ClientId);
                return(invalidGrant);
            }

            /////////////////////////////////////////////
            // check if client still has offline_access scope
            /////////////////////////////////////////////
            if (!client.AllowOfflineAccess)
            {
                Logger.LogError("{clientId} does not have access to offline_access scope anymore", client.ClientId);
                return(invalidGrant);
            }

            /////////////////////////////////////////////
            // check if refresh token has been consumed
            /////////////////////////////////////////////
            if (refreshToken.ConsumedTime.HasValue && !await AcceptConsumedTokenAsync(refreshToken))
            {
                Logger.LogWarning("Rejecting refresh token because it has been consumed already.");
                return(invalidGrant);
            }

            /////////////////////////////////////////////
            // make sure user is enabled
            /////////////////////////////////////////////
            var isActiveCtx = new IsActiveContext(
                refreshToken.Subject,
                client,
                IdentityServerConstants.ProfileIsActiveCallers.RefreshTokenValidation);

            await Profile.IsActiveAsync(isActiveCtx);

            if (!isActiveCtx.IsActive)
            {
                Logger.LogError("{subjectId} has been disabled", refreshToken.Subject.GetSubjectId());
                return(invalidGrant);
            }

            return(new TokenValidationResult
            {
                IsError = false,
                RefreshToken = refreshToken,
                RefreshTokenHandle = tokenHandle,
                Client = client
            });
        }
        public void StoreAsync_WhenCalled_ExpectAction()
        {
            // Arrange
            var mockCacheManager = new Mock<ICacheManager<RefreshToken>>();
            var mockCacheConfiguration = new Mock<IConfiguration<RedisCacheConfigurationEntity>>();

            mockCacheConfiguration.Setup(r => r.Get).Returns(new RedisCacheConfigurationEntity { CacheDuration = 1 });

            var keyCallback = default(string);
            var timespanCallback = default(TimeSpan);
            mockCacheManager.Setup(r => r.SetAsync(It.IsAny<string>(), It.IsAny<RefreshToken>(), It.IsAny<TimeSpan>()))
                .Callback((string s, RefreshToken a, TimeSpan t) =>
                {
                    keyCallback = s;
                    timespanCallback = t;
                })
                .Returns(Task.FromResult(0));

            var refreshTokenStore = new RefreshTokenStore(
                mockCacheManager.Object,
                mockCacheConfiguration.Object);

            // Act
            var stopwatch = Stopwatch.StartNew();

            refreshTokenStore.StoreAsync("string", new RefreshToken { LifeTime = 100 }).Wait();

            stopwatch.Stop();

            // Assert
            this.WriteTimeElapsed(stopwatch);

            Assert.That(keyCallback, Is.EqualTo("RTS_string"));
            Assert.That(timespanCallback, Is.EqualTo(TimeSpan.FromSeconds(95)));
            mockCacheManager.Verify(r => r.SetAsync(It.IsAny<string>(), It.IsAny<RefreshToken>(), It.IsAny<TimeSpan>()), Times.Once());
        }
        public static List <RefreshTokenHandleRecord> InsertTestData(ClientStore clientStore, ScopeStore scopeStore, TokenHandleStore ths, RefreshTokenStore store, int count = 1)
        {
            List <RefreshTokenHandleRecord> result = new List <RefreshTokenHandleRecord>();
            var insert      = TokenHandleStoreTest.InsertTestData(clientStore, scopeStore, ths, count);
            var subjectSeed = Guid.NewGuid().ToString();
            var clientId    = insert[0].Record.ClientId;

            foreach (var item in insert)
            {
                RefreshTokenHandle tokenHandle = new RefreshTokenHandle
                {
                    ClientId     = clientId,
                    AccessToken  = item.Record,
                    CreationTime = DateTimeOffset.UtcNow,
                    Key          = Guid.NewGuid().ToString(),
                    Expires      = DateTimeOffset.UtcNow.AddMinutes(5),
                    LifeTime     = 5,
                    SubjectId    = item.Record.SubjectId,
                    Version      = 1
                };
                var tokenHandleRecord = new RefreshTokenHandleRecord(tokenHandle);
                store.CreateAsync(tokenHandleRecord.Record);
                result.Add(tokenHandleRecord);
            }
            return(result);
        }
        /// <summary>
        /// Initializes this instance.
        /// </summary>
        /// <returns>The <see cref="Caches"/></returns>
        private static Entities.Caches Initialize()
        {
            var jsonSettingsFactory = new JsonSettingsFactory(incomingMappers);

            var settings = jsonSettingsFactory.Create();

            var authorizationCacheManager = new RedisCacheManager<AuthorizationCode>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var authorizationCodeStore = new AuthorizationCodeStore(
                authorizationCacheManager,
                Configuration);

            var clientCacheManager = new RedisCacheManager<Client>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var clientCache = new ClientStoreCache(
                clientCacheManager,
                Configuration);

            var refreshTokenCacheManager = new RedisCacheManager<RefreshToken>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var refreshTokenStore = new RefreshTokenStore(
                refreshTokenCacheManager,
                Configuration);

            var scopeCacheManager = new RedisCacheManager<IEnumerable<Scope>>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var scopesCache = new ScopeStoreCache(
                scopeCacheManager,
                Configuration);

            var redisHandleCacheManager = new RedisCacheManager<Token>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var tokenHandleStore = new TokenHandleStore(
                redisHandleCacheManager,
                Configuration);

            var userServiceCacheManager = new RedisCacheManager<IEnumerable<Claim>>(
                ConnectionMultiplexer,
                Configuration,
                settings);

            var userServiceCache = new UserServiceCache(
                userServiceCacheManager,
                Configuration);

            var caches = new Entities.Caches
            {
                AuthorizationCodeStore = authorizationCodeStore,
                ClientCache = clientCache,
                RefreshTokenStore = refreshTokenStore,
                ScopesCache = scopesCache,
                TokenHandleStore = tokenHandleStore,
                UserServiceCache = userServiceCache
            };

            return caches;
        }