public Task <bool> IsInRoleAsync(TUser user, string roleName, CancellationToken cancellationToken)
        {
            var inRole = NameValue.Parse(user.Claims)
                         .Any(c => c.Name == JwtClaimTypes.Role && c.Value == roleName);

            return(Task.FromResult(inRole));
        }
        public Task <IList <Claim> > GetClaimsAsync(TUser user, CancellationToken cancellationToken)
        {
            var nameValues = NameValue.Parse(user.Claims);

            var claims = (IList <Claim>)nameValues.Select(nv => new Claim(nv.Name, nv.Value)).ToList();

            return(Task.FromResult(claims));
        }
        public Task <IList <string> > GetRolesAsync(TUser user, CancellationToken cancellationToken)
        {
            var roles = NameValue.Parse(user.Claims)
                        .Where(c => c.Name == JwtClaimTypes.Role)
                        .Select(c => c.Value)
                        .ToList();

            return(Task.FromResult((IList <string>)roles));
        }
        public Task RemoveFromRoleAsync(TUser user, string roleName, CancellationToken cancellationToken)
        {
            var existing = NameValue.Parse(user.Claims).ToList();

            existing.RemoveAll(r => r.Name == JwtClaimTypes.Role && r.Value == roleName);

            user.Claims = NameValue.Generate(existing);

            return(Task.FromResult(0));
        }
        public Task AddToRoleAsync(TUser user, string roleName, CancellationToken cancellationToken)
        {
            var existing = NameValue.Parse(user.Claims).ToList();

            existing.Add(new NameValue {
                Name = JwtClaimTypes.Role, Value = roleName
            });

            user.Claims = NameValue.Generate(existing);

            return(Task.FromResult(0));
        }
        public Task RemoveClaimsAsync(TUser user, IEnumerable <Claim> claims, CancellationToken cancellationToken)
        {
            var existingClaims = NameValue.Parse(user.Claims).ToList();

            // TODO: This isn't efficient but it works.
            foreach (var claim in claims)
            {
                existingClaims.RemoveAll(c => c.Name == claim.Type && c.Value == claim.Value);
            }

            user.Claims = NameValue.Generate(existingClaims);

            return(Task.FromResult(0));
        }
        public Task AddClaimsAsync(TUser user, IEnumerable <Claim> claims, CancellationToken cancellationToken)
        {
            var nvs = claims.Select(c => new NameValue {
                Name = c.Type, Value = c.Value
            });

            var existingClaims = NameValue.Parse(user.Claims)
                                 .ToList();

            existingClaims.AddRange(nvs);

            user.Claims = NameValue.Generate(existingClaims);

            return(Task.FromResult(0));
        }
        public Task ReplaceClaimAsync(TUser user, Claim claim, Claim newClaim, CancellationToken cancellationToken)
        {
            var existingClaims = NameValue.Parse(user.Claims).ToList();

            existingClaims.RemoveAll(c => c.Name == claim.Type && c.Value == claim.Value);

            // TODO: should the add only happen if claim was removed?
            existingClaims.Add(new NameValue {
                Name = claim.Type, Value = claim.Value
            });

            user.Claims = NameValue.Generate(existingClaims);

            return(Task.FromResult(0));
        }