Ejemplo n.º 1
0
        public void PreAuthenticate(IRequest req, IResponse res)
        {
            //The API Key is sent in the Basic Auth Username and Password is Empty
            var userPass = req.GetBasicAuthUserAndPassword();

            if (userPass != null && string.IsNullOrEmpty(userPass.Value.Value))
            {
                if (RequireSecureConnection && !req.IsSecureConnection)
                {
                    throw HttpError.Forbidden(ErrorMessages.ApiKeyRequiresSecureConnection);
                }

                var apiKey = userPass.Value.Key;

                PreAuthenticateWithApiKey(req, res, apiKey);
            }
            var bearerToken = req.GetBearerToken();

            if (bearerToken != null)
            {
                var authRepo = (IManageApiKeys)req.TryResolve <IAuthRepository>().AsUserAuthRepository(req);
                if (authRepo.ApiKeyExists(bearerToken))
                {
                    if (RequireSecureConnection && !req.IsSecureConnection)
                    {
                        throw HttpError.Forbidden(ErrorMessages.ApiKeyRequiresSecureConnection);
                    }

                    PreAuthenticateWithApiKey(req, res, bearerToken);
                }
            }
        }
Ejemplo n.º 2
0
        public object Put(UpdateOrganizationMember request)
        {
            var user = GetUser();

            AssertOrganizationModerator(Db, request.OrganizationId, user, out var org, out var orgMember);

            var member = Db.Single <OrganizationMember>(x =>
                                                        x.UserId == request.UserId && x.OrganizationId == request.OrganizationId);

            if (member == null)
            {
                throw HttpError.NotFound("Member does not exist");
            }

            var requiresOwner = member.IsOwner || member.IsModerator ||
                                member.IsModerator != request.IsModerator ||
                                member.IsOwner != request.IsOwner;

            if (requiresOwner && !user.IsOrganizationOwner(orgMember))
            {
                throw HttpError.Forbidden("This action is limited to Organization Owners");
            }

            member.PopulateWith(request);

            Db.Update(member);

            ClearOrganizationCaches();

            return(new UpdateOrganizationMemberResponse());
        }
Ejemplo n.º 3
0
        public async Task PreAuthenticateWithApiKeyAsync(IRequest req, IResponse res, ApiKey apiKey)
        {
            if (RequireSecureConnection && !req.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.ApiKeyRequiresSecureConnection.Localize(req));
            }

            ValidateApiKey(req, apiKey);

            var apiSessionKey = GetSessionKey(apiKey.Id);

            if (await HasCachedSessionAsync(req, apiSessionKey).ConfigAwait())
            {
                req.Items[Keywords.ApiKey] = apiKey;
                return;
            }

            //Need to run SessionFeature filter since its not executed before this attribute (Priority -100)
            SessionFeature.AddSessionIdToRequestFilter(req, res, null); //Required to get req.GetSessionId()

            using var authService = HostContext.ResolveService <AuthenticateService>(req);
            var response = await authService.PostAsync(new Authenticate
            {
                provider = Name,
                UserName = "******",
                Password = apiKey.Id,
            }).ConfigAwait();

            await CacheSessionAsync(req, apiSessionKey);
        }
        public CreateLayerTokenResponse Post(CreateLayerIdentityToken request)
        {
            // validate if the user is authenticated
            if (!_validator.Validate(request.UserId))
            {
                throw HttpError.Forbidden("This user is not allowed to create a validation token for the requested user.");
            }

            var feature = HostContext.GetPlugin <LayerTokenProviderFeature>();

            var header = new JsonObject
            {
                { "typ", "JWT" },
                { "alg", "RS256" },
                { "cty", "layer-eit;v=1" }, // String - Express a Content Type of Layer External Identity Token, version 1
                { "kid", feature.KeyName }
            };

            var body = new JsonObject
            {
                { "iss", feature.ProviderId },
                { "prn", request.UserId },
                { "iat", DateTime.UtcNow.ToUnixTime().ToString() },
                { "exp", DateTime.UtcNow.Add(feature.ExpiresIn).ToUnixTime().ToString() },
                { "nce", request.Nonce }
            };

            var headerBytes   = header.ToJson().ToUtf8Bytes();
            var headerEncoded = headerBytes.ToBase64UrlSafe();

            var payloadBytes   = body.ToJson().ToUtf8Bytes();
            var payloadEncoded = payloadBytes.ToBase64UrlSafe();

            var base64Header  = headerBytes.ToBase64UrlSafe();
            var base64Payload = payloadBytes.ToBase64UrlSafe();

            var stringToSign = base64Header + "." + base64Payload;

            using (var sr = new StreamReader(feature.PemPath))
            {
                var pr         = new PemReader(sr);
                var keyPair    = (AsymmetricCipherKeyPair)pr.ReadObject();
                var rsaPrivate = DotNetUtilities.ToRSAParameters((RsaPrivateCrtKeyParameters)keyPair.Private);

                var rsa = new RSACryptoServiceProvider();
                rsa.ImportParameters(rsaPrivate);
                var inputBytes         = Encoding.UTF8.GetBytes(stringToSign);
                var signatureBytesTemp = rsa.SignData(inputBytes, new SHA256CryptoServiceProvider());

                var token = string.Join(".", headerEncoded, payloadEncoded, signatureBytesTemp.ToBase64UrlSafe());

                return(new CreateLayerTokenResponse()
                {
                    IdentityToken = token
                });
            }
        }
Ejemplo n.º 5
0
        public static void AssertOrganizationModerator(IDbConnection db, int orgId, AuthUserSession user,
                                                       out Organization organization, out OrganizationMember orgMember)
        {
            AssertCanViewOrganization(db, orgId, user, out organization, out orgMember);

            if (!user.IsOrganizationModerator(orgMember))
            {
                throw HttpError.Forbidden("This action is limited to Organization Moderators");
            }
        }
Ejemplo n.º 6
0
        public virtual void ValidateApiKey(IRequest req, ApiKey apiKey)
        {
            if (apiKey == null)
                throw HttpError.NotFound(ErrorMessages.ApiKeyDoesNotExist.Localize(req));

            if (apiKey.CancelledDate != null)
                throw HttpError.Forbidden(ErrorMessages.ApiKeyHasBeenCancelled.Localize(req));

            if (apiKey.ExpiryDate != null && DateTime.UtcNow > apiKey.ExpiryDate.Value)
                throw HttpError.Forbidden(ErrorMessages.ApiKeyHasExpired.Localize(req));
        }
Ejemplo n.º 7
0
        public object Any(ConvertSessionToToken request)
        {
            var jwtAuthProvider = (JwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
            }

            if (Request.ResponseContentType.MatchesContentType(MimeTypes.Html))
            {
                Request.ResponseContentType = MimeTypes.Json;
            }

            var          token   = Request.GetJwtToken();
            IAuthSession session = null;
            var          includeTokensInResponse = jwtAuthProvider.IncludeJwtInConvertSessionToTokenResponse;
            var          createFromSession       = string.IsNullOrEmpty(token);

            if (createFromSession || includeTokensInResponse)
            {
                session = Request.GetSession();

                if (createFromSession)
                {
                    token = jwtAuthProvider.CreateJwtBearerToken(Request, session);
                }

                if (!request.PreserveSession)
                {
                    Request.RemoveSession(session.Id);
                }
            }

            return(new HttpResult(new ConvertSessionToTokenResponse {
                AccessToken = includeTokensInResponse
                    ? token
                    : null,
                RefreshToken = createFromSession && includeTokensInResponse && !request.PreserveSession
                    ? jwtAuthProvider.CreateJwtRefreshToken(Request, session.UserAuthId, jwtAuthProvider.ExpireRefreshTokensIn)
                    : null
            })
            {
                Cookies =
                {
                    new Cookie(Keywords.TokenCookie, token, Cookies.RootPath)
                    {
                        HttpOnly = true,
                        Secure = Request.IsSecureConnection,
                        Expires = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
                    }
                }
            });
        }
Ejemplo n.º 8
0
        private void ValidateAccessRights()
        {
            if (Request.TryResolve <IDbConnectionFactory>() == null ||
                Request.GetSession().HasRole("Admin", null))
            {
                // all good
                return;
            }

            throw HttpError.Forbidden("Forbidden");
        }
Ejemplo n.º 9
0
        public async Task LoginUserAsync(LoginDto dto)
        {
            HttpContext context = _httpContextAccessor.HttpContext;

            if (context.User.Identity.IsAuthenticated)
            {
                throw HttpError.Forbidden("User is still authenticated");
            }

            if (dto.Name == null || dto.Password == null)
            {
                throw HttpError.InternalServerError("Username or password is null");
            }

            User user = (await _userRepository.Find(x => x.Name == dto.Name)).FirstOrDefault();

            if (user == null)
            {
                throw HttpError.Unauthorized("Wrong username or password");
            }

            string savedPasswordHash = (await _hashRepository.Get(user.Id))?.PasswordHash;

            if (savedPasswordHash == null)
            {
                throw HttpError.InternalServerError("User has no password");
            }

            if (!HashHelpers.CheckPasswordWithHash(dto.Password, savedPasswordHash))
            {
                throw HttpError.Unauthorized("Wrong username or password");
            }

            string[]     roles  = user.CredentialLevel.GetAllPossibleRoles();
            List <Claim> claims = new List <Claim>
            {
                new Claim(ClaimTypes.Name, user.Name),
                new Claim(ClaimTypes.NameIdentifier, user.Name)
            };

            claims.AddRange(roles.Select(x => new Claim(ClaimTypes.Role, x)));

            var identity       = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
            var principal      = new ClaimsPrincipal(identity);
            var authProperties = new AuthenticationProperties
            {
                AllowRefresh = true,
                ExpiresUtc   = DateTimeOffset.Now.AddDays(1),
                IsPersistent = dto.RememberMe
            };

            await context.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme, principal, authProperties);
        }
        public void PreAuthenticate(IRequest req, IResponse res)
        {
            if (req.OperationName != null && JwtAuthProviderReader.IgnoreForOperationTypes.Contains(req.OperationName))
            {
                return;
            }

            var bearerToken = req.GetBearerToken()
                              ?? req.GetCookieValue(Keywords.TokenCookie);

            if (bearerToken != null)
            {
                var parts = bearerToken.Split('.');
                if (parts.Length != 3)
                {
                    throw new TokenException("Azure AD jwt token should have 3 parts.");
                }


                if (RequireSecureConnection && !req.IsSecureConnection)
                {
                    throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection);
                }

                var header         = parts[0];
                var payload        = parts[1];
                var signatureBytes = parts[2].FromBase64UrlSafe();

                var headerJson   = header.FromBase64UrlSafe().FromUtf8Bytes();
                var payloadBytes = payload.FromBase64UrlSafe();

                var headerData = headerJson.FromJson <Dictionary <string, string> >();

                var bytesToSign = string.Concat(header, ".", payload).ToUtf8Bytes();

                var algorithm = headerData["alg"];

                //Potential Security Risk for relying on user-specified algorithm: https://auth0.com/blog/2015/03/31/critical-vulnerabilities-in-json-web-token-libraries/
                //if (RequireHashAlgorithm && algorithm != HashAlgorithm)
                //	throw new NotSupportedException("Invalid algoritm '{0}', expected '{1}'".Fmt(algorithm, HashAlgorithm));

                if (!VerifyPayload(algorithm, bytesToSign, signatureBytes))
                {
                    return;
                }

                var payloadJson = payloadBytes.FromUtf8Bytes();
                var jwtPayload  = JsonObject.Parse(payloadJson);

                var session = CreateSessionFromPayload(req, jwtPayload);
                req.Items[Keywords.Session] = session;
            }
        }
Ejemplo n.º 11
0
        public static void AssertCanPostToOrganization(IDbConnection db, int organizationId, AuthUserSession user,
                                                       out Organization org, out OrganizationMember orgMember)
        {
            AssertCanViewOrganization(db, organizationId, user, out org, out orgMember);

            if (orgMember?.DenyPosts == true || orgMember?.DenyAll == true)
            {
                throw HttpError.Forbidden("Access has been suspended");
            }

            if (org.Locked != null && orgMember == null)
            {
                throw HttpError.NotFound("Organization is locked to members only");
            }
        }
Ejemplo n.º 12
0
        public void PreAuthenticateWithApiKey(IRequest req, IResponse res, ApiKey apiKey)
        {
            if (RequireSecureConnection && !req.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.ApiKeyRequiresSecureConnection.Localize(req));
            }

            ValidateApiKey(req, apiKey);

            var apiSessionKey = GetSessionKey(apiKey.Id);

            if (SessionCacheDuration != null)
            {
                var session = req.GetCacheClient().Get <IAuthSession>(apiSessionKey);

                if (session != null)
                {
                    session = HostContext.AppHost.OnSessionFilter(req, session, session.Id);
                }

                if (session != null)
                {
                    req.Items[Keywords.ApiKey]  = apiKey;
                    req.Items[Keywords.Session] = session;
                    return;
                }
            }

            //Need to run SessionFeature filter since its not executed before this attribute (Priority -100)
            SessionFeature.AddSessionIdToRequestFilter(req, res, null); //Required to get req.GetSessionId()

            using (var authService = HostContext.ResolveService <AuthenticateService>(req))
            {
                var response = authService.Post(new Authenticate
                {
                    provider = Name,
                    UserName = "******",
                    Password = apiKey.Id,
                });
            }

            if (SessionCacheDuration != null)
            {
                var session = req.GetSession();
                req.GetCacheClient().Set(apiSessionKey, session, SessionCacheDuration);
            }
        }
Ejemplo n.º 13
0
        public virtual void ValidateApiKey(ApiKey apiKey)
        {
            if (apiKey == null)
            {
                throw HttpError.NotFound("ApiKey does not exist");
            }

            if (apiKey.CancelledDate != null)
            {
                throw HttpError.Forbidden("ApiKey has been cancelled");
            }

            if (apiKey.ExpiryDate != null && DateTime.UtcNow > apiKey.ExpiryDate.Value)
            {
                throw HttpError.Forbidden("ApiKey has expired");
            }
        }
        public void PreAuthenticate(IRequest req, IResponse res)
        {
            var signature = req.Headers[WebhookEventConstants.SecretSignatureHeaderName];

            if (signature.HasValue())
            {
                if (RequireSecureConnection && !req.IsSecureConnection)
                {
                    throw HttpError.Forbidden(Resources.HmacAuthProvider_NotHttps);
                }

                var eventName = req.Headers[WebhookEventConstants.EventNameHeaderName];
                if (OnGetSecret != null)
                {
                    Secret = OnGetSecret(req, eventName);
                }
                if (!Secret.HasValue())
                {
                    throw HttpError.Unauthorized(Resources.HmacAuthProvider_IncorrectlyConfigured);
                }

                var isValidSecret = req.VerifySignature(signature, Secret);
                if (!isValidSecret)
                {
                    throw new HttpError(HttpStatusCode.Unauthorized);
                }

                var requestId = req.Headers[WebhookEventConstants.RequestIdHeaderName];
                var userId    = requestId.HasValue() ? requestId : Guid.NewGuid().ToString("N");
                var username  = req.GetUrlHostName();

                var sessionId = SessionExtensions.CreateRandomSessionId();
                var session   = SessionFeature.CreateNewSession(req, sessionId);
                session.UserAuthId      = userId;
                session.UserAuthName    = username;
                session.UserName        = username;
                session.IsAuthenticated = true;
                session.CreatedAt       = SystemTime.UtcNow;

                HostContext.AppHost.OnSessionFilter(req, session, sessionId);

                req.Items[Keywords.Session] = session;
            }
        }
Ejemplo n.º 15
0
        public object Put(PinPostComment request)
        {
            if (request.Id <= 0)
            {
                throw new ArgumentNullException(nameof(request.Id));
            }
            if (request.PostId <= 0)
            {
                throw new ArgumentNullException(nameof(request.PostId));
            }

            var user = GetUser();
            var post = AssertPost(request.PostId);

            AssertCanPostToOrganization(Db, post.OrganizationId, user, out var org, out var orgMember);
            AssertCanContributeToPost(post, user, orgMember);

            if (post.UserId != user.GetUserId() && !user.IsOrganizationModerator(orgMember))
            {
                throw HttpError.Forbidden("Only Post author can pin comments");
            }

            Db.UpdateOnly(() => new Post
            {
                PinCommentId = request.Pin ? request.Id : (long?)null,
                Modified     = DateTime.Now,
                ModifiedBy   = user.UserName
            },
                          where : x => x.Id == request.PostId);

            Db.ExecuteSql(
                @"update user_activity set 
                         pinned_comment_count = (select count(*) 
                                                   from post p 
                                                   join post_comment c on (p.pin_comment_id = c.id and p.user_id <> user_activity.id)
                                                  where c.user_id = user_activity.id)
                   where id = (select user_id from post_comment c where c.id = @id)",
                new { id = request.Id });

            ClearPostCaches();

            return(new PinPostCommentResponse());
        }
Ejemplo n.º 16
0
        public async Task Delete(string id)
        {
            User user = await _sessionService.GetUser();

            Post post = await _postRepository.GetById(id);

            if (post == null)
            {
                _logger.LogWarning($"Post {id} does not exist");
                throw HttpError.NotFound($"Post {id} does not exist");
            }

            if (post.AuthorId != user.Id)
            {
                _logger.LogWarning($"Post {id} does not belong to user");
                throw HttpError.Forbidden($"Post {id} does not belong to user");
            }

            await _postRepository.Delete(id);
        }
Ejemplo n.º 17
0
        public void Put(HidePost request)
        {
            var user = GetUser();
            var post = AssertPost(request.Id);

            AssertCanPostToOrganization(Db, post.OrganizationId, user, out var org, out var orgMember);

            if (!user.IsOrganizationModerator(orgMember))
            {
                throw HttpError.Forbidden("Access Denied");
            }

            var now = DateTime.Now;

            if (request.Hide)
            {
                post.Hidden   = now;
                post.HiddenBy = user.UserName;
                if (!string.IsNullOrEmpty(request.Reason))
                {
                    post.Notes = request.Reason;
                }
            }
            else
            {
                post.Hidden   = null;
                post.HiddenBy = null;
            }

            Db.Update(post);

            Db.Insert(new PostChangeHistory {
                ChangedName   = nameof(post.Hidden),
                ChangedValue  = request.Hide.ToString(),
                ChangedReason = request.Reason,
                Created       = now,
                CreatedBy     = user.UserName,
            });

            ClearPostCaches();
        }
Ejemplo n.º 18
0
        public async Task Update(string id, UpdatePostDto dto)
        {
            User user = await _sessionService.GetUser();

            Validate("modify", dto.Content, dto.Title, user);

            Post post = await _postRepository.GetById(id);

            if (post == null)
            {
                _logger.LogWarning($"Post {id} does not exist");
                throw HttpError.NotFound($"Post {id} does not exist");
            }

            if (post.AuthorId != user.Id)
            {
                _logger.LogWarning($"Post {id} does not belong to user");
                throw HttpError.Forbidden($"Post {id} does not belong to user");
            }

            post.Title          = dto.Title;
            post.Content        = dto.Content;
            post.LastUpdateTime = DateTime.Now;
            post.Tags           = TagHelpers.GetTagsFromText(dto.Content);

            bool success = await _postRepository.Update(post);

            if (!success)
            {
                _logger.LogWarning("Error during update post");
                throw HttpError.InternalServerError("");
            }

            await _tagRepository.Create(post.Tags.Select(x => new Tag
            {
                Name = x,
                PostsNumber = 1
            }).ToArray());

            _logger.LogInformation("Tags have been added");
        }
Ejemplo n.º 19
0
        public object Any(ConvertSessionToToken request)
        {
            var jwtAuthProvider = AuthenticateService.GetAuthProvider(JwtAuthProvider.Name) as JwtAuthProvider;

            if (jwtAuthProvider == null)
            {
                throw new NotSupportedException("JwtAuthProvider is not registered");
            }

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection);
            }

            var session = Request.GetSession();

            if (session.FromToken)
            {
                return(new ConvertSessionToTokenResponse());
            }

            var token = jwtAuthProvider.CreateJwtBearerToken(session);

            if (!request.PreserveSession)
            {
                Request.RemoveSession(session.Id);
            }

            return(new HttpResult(new ConvertSessionToTokenResponse())
            {
                Cookies =
                {
                    new Cookie(Keywords.TokenCookie, token, Cookies.RootPath)
                    {
                        HttpOnly = true,
                        Secure = Request.IsSecureConnection,
                        Expires = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
                    }
                }
            });
        }
Ejemplo n.º 20
0
        public object Any(ConvertSessionToToken request)
        {
            var jwtAuthProvider = (JwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
            }

            if (Request.ResponseContentType.MatchesContentType(MimeTypes.Html))
            {
                Request.ResponseContentType = MimeTypes.Json;
            }

            var token = Request.GetJwtToken();

            if (string.IsNullOrEmpty(token))
            {
                var session = Request.GetSession();
                token = jwtAuthProvider.CreateJwtBearerToken(Request, session);

                if (!request.PreserveSession)
                {
                    Request.RemoveSession(session.Id);
                }
            }

            return(new HttpResult(new ConvertSessionToTokenResponse())
            {
                Cookies =
                {
                    new Cookie(Keywords.TokenCookie, token, Cookies.RootPath)
                    {
                        HttpOnly = true,
                        Secure = Request.IsSecureConnection,
                        Expires = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
                    }
                }
            });
        }
Ejemplo n.º 21
0
        public object Post(AddOrganizationMember request)
        {
            var user = GetUser();

            AssertOrganizationModerator(Db, request.OrganizationId, user, out var org, out var orgMember);

            var requiresOwner = request.IsModerator || request.IsOwner;

            if (requiresOwner && !user.IsOrganizationOwner(orgMember))
            {
                throw HttpError.Forbidden("This action is limited to Organization Owners");
            }

            var memberUser = Db.Single <CustomUserAuth>(x => x.UserName.ToLower() == request.UserName.ToLower());

            if (memberUser == null)
            {
                throw HttpError.NotFound("User does not exist");
            }

            var existingMember = Db.Exists <OrganizationMember>(x =>
                                                                x.OrganizationId == request.OrganizationId && x.UserId == memberUser.Id);

            if (existingMember)
            {
                throw new ArgumentException("Member has already been added", nameof(request.UserName));
            }

            var member = request.ConvertTo <OrganizationMember>();

            member.UserId    = memberUser.Id;
            member.UserName  = memberUser.UserName;
            member.Created   = member.Modified = DateTime.Now;
            member.CreatedBy = member.ModifiedBy = user.UserName;
            Db.Insert(member);

            ClearOrganizationCaches();

            return(new AddOrganizationMemberResponse());
        }
Ejemplo n.º 22
0
        public async Task <object> Any(GetAccessToken request)
        {
            var jwtAuthProvider = (JwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
            }

            var refreshTokenCookie = Request.Cookies.TryGetValue(Keywords.RefreshTokenCookie, out var refTok)
                ? refTok.Value
                : null;

            var refreshToken = request.RefreshToken ?? refreshTokenCookie;
            var accessToken  = await jwtAuthProvider.CreateAccessTokenFromRefreshToken(refreshToken, Request).ConfigAwait();

            var response = new GetAccessTokenResponse
            {
                AccessToken = accessToken
            };

            // Don't return JWT in Response Body if Refresh Token Cookie was used
            if (refreshTokenCookie == null && jwtAuthProvider.UseTokenCookie != true)
            {
                return(response);
            }

            var httpResult = new HttpResult(new GetAccessTokenResponse())
                             .AddCookie(Request,
                                        new Cookie(Keywords.TokenCookie, accessToken, Cookies.RootPath)
            {
                HttpOnly = true,
                Secure   = Request.IsSecureConnection,
                Expires  = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
            });

            return(httpResult);
        }
Ejemplo n.º 23
0
        public static void AssertCanPostTypeToOrganization(PostType postType, Organization org,
                                                           OrganizationMember orgMember, AuthUserSession user)
        {
            if (user.IsOrganizationModerator(orgMember))
            {
                if (!org.ModeratorPostTypes.IsEmpty())
                {
                    if (!org.ModeratorPostTypes.Contains(postType.ToString()))
                    {
                        throw HttpError.Forbidden(postType + " is not an allowed Type for Moderators");
                    }
                    return;
                }
            }

            if (!org.PostTypes.IsEmpty())
            {
                if (!org.PostTypes.Contains(postType.ToString()))
                {
                    throw HttpError.Forbidden($"You cannot submit {postType} posts here");
                }
            }
        }
Ejemplo n.º 24
0
        public void Delete(RemoveOrganizationMember request)
        {
            var user = GetUser();

            AssertOrganizationModerator(Db, request.OrganizationId, user, out var org, out var orgMember);

            var member = Db.Single <OrganizationMember>(x =>
                                                        x.UserId == request.UserId && x.OrganizationId == request.OrganizationId);

            var requiresOwner = member.IsOwner || member.IsModerator;

            if (requiresOwner && !user.IsOrganizationOwner(orgMember))
            {
                throw HttpError.Forbidden("This action is limited to Organization Owners");
            }

            Db.Delete <OrganizationMember>(x => x.UserId == request.UserId && x.OrganizationId == request.OrganizationId);
            Db.Delete <OrganizationMemberInvite>(x => x.UserId == request.UserId && x.OrganizationId == request.OrganizationId);

            SendSystemEmail(nameof(RemoveOrganizationMember),
                            $"@{member.UserName} was removed from {org.Name} by {user.UserName}");

            ClearOrganizationCaches();
        }
Ejemplo n.º 25
0
        public async Task Update(string postId, string id, UpdateCommentDto dto)
        {
            User user = await _sessionService.GetUser();

            Validate("modify", dto.Content, user);

            Comment comment = await _commentRepository.GetById(id);

            if (comment == null)
            {
                _logger.LogWarning($"Comment {id} does not exist");
                throw HttpError.NotFound($"Comment {id} does not exist");
            }

            if (comment.PostId != postId)
            {
                throw HttpError.NotFound("");
            }

            if (comment.AuthorId != user.Id)
            {
                _logger.LogWarning($"Comment {id} does not belong to user");
                throw HttpError.Forbidden($"Comment {id} does not belong to user");
            }

            comment.Content        = dto.Content;
            comment.LastUpdateTime = DateTime.Now;

            bool success = await _commentRepository.Update(comment);

            if (!success)
            {
                _logger.LogWarning("Error during update comment");
                throw HttpError.InternalServerError("");
            }
        }
Ejemplo n.º 26
0
        public async Task Update(string commentId, string id, UpdateResponseDto dto)
        {
            User user = await _sessionService.GetUser();

            Validate("modify", dto.Content, user);

            Response response = await _responseRepository.GetById(id);

            if (response == null)
            {
                _logger.LogWarning($"Response {id} does not exist");
                throw HttpError.NotFound($"Response {id} does not exist");
            }

            if (response.CommentId != commentId)
            {
                throw HttpError.NotFound("");
            }

            if (response.AuthorId != user.Id)
            {
                _logger.LogWarning($"Response {id} does not belong to user");
                throw HttpError.Forbidden($"Response {id} does not belong to user");
            }

            response.Content        = dto.Content;
            response.LastUpdateTime = DateTime.Now;

            bool success = await _responseRepository.Update(response);

            if (!success)
            {
                _logger.LogWarning("Error during update response");
                throw HttpError.InternalServerError("");
            }
        }
Ejemplo n.º 27
0
        public object Any(GetAccessToken request)
        {
            var jwtAuthProvider = (JwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
            }

            if (string.IsNullOrEmpty(request.RefreshToken))
            {
                throw new ArgumentNullException(nameof(request.RefreshToken));
            }

            JsonObject jwtPayload;

            try
            {
                jwtPayload = jwtAuthProvider.GetVerifiedJwtPayload(Request, request.RefreshToken.Split('.'));
            }
            catch (ArgumentException)
            {
                throw;
            }
            catch (Exception ex)
            {
                throw new ArgumentException(ex.Message);
            }

            jwtAuthProvider.AssertJwtPayloadIsValid(jwtPayload);

            if (jwtAuthProvider.ValidateRefreshToken != null && !jwtAuthProvider.ValidateRefreshToken(jwtPayload, Request))
            {
                throw new ArgumentException(ErrorMessages.RefreshTokenInvalid.Localize(Request), nameof(request.RefreshToken));
            }

            var userId = jwtPayload["sub"];

            IAuthSession         session;
            IEnumerable <string> roles = null, perms = null;

            var userSessionSource = AuthenticateService.GetUserSessionSource();

            if (userSessionSource != null)
            {
                session = userSessionSource.GetUserSession(userId);
                if (session == null)
                {
                    throw HttpError.NotFound(ErrorMessages.UserNotExists.Localize(Request));
                }

                roles = session.Roles;
                perms = session.Permissions;
            }
            else if (AuthRepository is IUserAuthRepository userRepo)
            {
                var userAuth = userRepo.GetUserAuth(userId);
                if (userAuth == null)
                {
                    throw HttpError.NotFound(ErrorMessages.UserNotExists.Localize(Request));
                }

                if (jwtAuthProvider.IsAccountLocked(userRepo, userAuth))
                {
                    throw new AuthenticationException(ErrorMessages.UserAccountLocked.Localize(Request));
                }

                session = SessionFeature.CreateNewSession(Request, SessionExtensions.CreateRandomSessionId());
                session.PopulateSession(userAuth, userRepo);

                if (userRepo is IManageRoles manageRoles && session.UserAuthId != null)
                {
                    roles = manageRoles.GetRoles(session.UserAuthId);
                    perms = manageRoles.GetPermissions(session.UserAuthId);
                }
            }
            else
            {
                throw new NotSupportedException("JWT RefreshTokens requires a registered IUserAuthRepository or an AuthProvider implementing IUserSessionSource");
            }

            var accessToken = jwtAuthProvider.CreateJwtBearerToken(Request, session, roles, perms);

            var response = new GetAccessTokenResponse
            {
                AccessToken = accessToken
            };

            if (request.UseTokenCookie != true)
            {
                return(response);
            }

            return(new HttpResult(new GetAccessTokenResponse())
            {
                Cookies =
                {
                    new Cookie(Keywords.TokenCookie, accessToken, Cookies.RootPath)
                    {
                        HttpOnly = true,
                        Secure = Request.IsSecureConnection,
                        Expires = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
                    }
                }
            });
        }
Ejemplo n.º 28
0
        public void PreAuthenticate(IRequest req, IResponse res)
        {
            if (req.OperationName != null && IgnoreForOperationTypes.Contains(req.OperationName))
            {
                return;
            }

            var bearerToken = req.GetBearerToken()
                              ?? req.GetCookieValue(Keywords.TokenCookie);

            if (bearerToken != null)
            {
                var parts = bearerToken.Split('.');
                if (parts.Length == 3)
                {
                    if (RequireSecureConnection && !req.IsSecureConnection)
                    {
                        throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection);
                    }

                    var header         = parts[0];
                    var payload        = parts[1];
                    var signatureBytes = parts[2].FromBase64UrlSafe();

                    var headerJson   = header.FromBase64UrlSafe().FromUtf8Bytes();
                    var payloadBytes = payload.FromBase64UrlSafe();

                    var headerData = headerJson.FromJson <Dictionary <string, string> >();

                    var bytesToSign = string.Concat(header, ".", payload).ToUtf8Bytes();

                    var algorithm = headerData["alg"];

                    //Potential Security Risk for relying on user-specified algorithm: https://auth0.com/blog/2015/03/31/critical-vulnerabilities-in-json-web-token-libraries/
                    if (RequireHashAlgorithm && algorithm != HashAlgorithm)
                    {
                        throw new NotSupportedException("Invalid algoritm '{0}', expected '{1}'".Fmt(algorithm, HashAlgorithm));
                    }

                    if (!VerifyPayload(algorithm, bytesToSign, signatureBytes))
                    {
                        return;
                    }

                    var payloadJson = payloadBytes.FromUtf8Bytes();
                    var jwtPayload  = JsonObject.Parse(payloadJson);

                    var session = CreateSessionFromPayload(req, jwtPayload);
                    req.Items[Keywords.Session] = session;
                }
                else if (parts.Length == 5) //Encrypted JWE Token
                {
                    if (RequireSecureConnection && !req.IsSecureConnection)
                    {
                        throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection);
                    }

                    if (PrivateKey == null || PublicKey == null)
                    {
                        throw new NotSupportedException("PrivateKey is required to DecryptPayload");
                    }

                    var jweHeaderBase64Url  = parts[0];
                    var jweEncKeyBase64Url  = parts[1];
                    var ivBase64Url         = parts[2];
                    var cipherTextBase64Url = parts[3];
                    var tagBase64Url        = parts[4];

                    var sentTag    = tagBase64Url.FromBase64UrlSafe();
                    var aadBytes   = (jweHeaderBase64Url + "." + jweEncKeyBase64Url).ToUtf8Bytes();
                    var iv         = ivBase64Url.FromBase64UrlSafe();
                    var cipherText = cipherTextBase64Url.FromBase64UrlSafe();

                    var jweEncKey        = jweEncKeyBase64Url.FromBase64UrlSafe();
                    var cryptAuthKeys256 = RsaUtils.Decrypt(jweEncKey, PrivateKey.Value, UseRsaKeyLength);

                    var authKey  = new byte[128 / 8];
                    var cryptKey = new byte[128 / 8];
                    Buffer.BlockCopy(cryptAuthKeys256, 0, authKey, 0, authKey.Length);
                    Buffer.BlockCopy(cryptAuthKeys256, authKey.Length, cryptKey, 0, cryptKey.Length);

                    using (var hmac = new HMACSHA256(authKey))
                        using (var encryptedStream = new MemoryStream())
                        {
                            using (var writer = new BinaryWriter(encryptedStream))
                            {
                                writer.Write(aadBytes);
                                writer.Write(iv);
                                writer.Write(cipherText);
                                writer.Flush();

                                var calcTag = hmac.ComputeHash(encryptedStream.ToArray());

                                if (!calcTag.EquivalentTo(sentTag))
                                {
                                    return;
                                }
                            }
                        }

                    JsonObject jwtPayload;
                    var        aes = Aes.Create();
                    aes.KeySize   = 128;
                    aes.BlockSize = 128;
                    aes.Mode      = CipherMode.CBC;
                    aes.Padding   = PaddingMode.PKCS7;
                    using (aes)
                        using (var decryptor = aes.CreateDecryptor(cryptKey, iv))
                            using (var ms = MemoryStreamFactory.GetStream(cipherText))
                                using (var cryptStream = new CryptoStream(ms, decryptor, CryptoStreamMode.Read))
                                {
                                    var jwtPayloadBytes = cryptStream.ReadFully();
                                    jwtPayload = JsonObject.Parse(jwtPayloadBytes.FromUtf8Bytes());
                                }

                    var session = CreateSessionFromPayload(req, jwtPayload);
                    req.Items[Keywords.Session] = session;
                }
            }
        }
Ejemplo n.º 29
0
        public async Task <object> Any(GetAccessToken request)
        {
            var jwtAuthProvider = (JwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

            if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
            {
                throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
            }

            if (string.IsNullOrEmpty(request.RefreshToken))
            {
                throw new ArgumentNullException(nameof(request.RefreshToken));
            }

            JsonObject jwtPayload;

            try
            {
                jwtPayload = jwtAuthProvider.GetVerifiedJwtPayload(Request, request.RefreshToken.Split('.'));
            }
            catch (ArgumentException)
            {
                throw;
            }
            catch (Exception ex)
            {
                throw new ArgumentException(ex.Message);
            }

            if (jwtPayload == null)
            {
                throw new ArgumentException(ErrorMessages.TokenInvalid.Localize(Request));
            }

            jwtAuthProvider.AssertJwtPayloadIsValid(jwtPayload);

            if (jwtAuthProvider.ValidateRefreshToken != null && !jwtAuthProvider.ValidateRefreshToken(jwtPayload, Request))
            {
                throw new ArgumentException(ErrorMessages.RefreshTokenInvalid.Localize(Request), nameof(request.RefreshToken));
            }

            var userId = jwtPayload["sub"];

            var result = await Request.GetSessionFromSourceAsync(userId, async (authRepo, userAuth) => {
                if (await jwtAuthProvider.IsAccountLockedAsync(authRepo, userAuth))
                {
                    throw new AuthenticationException(ErrorMessages.UserAccountLocked.Localize(Request));
                }
            }).ConfigAwait();

            if (result == null)
            {
                throw new NotSupportedException("JWT RefreshTokens requires a registered IUserAuthRepository or an AuthProvider implementing IUserSessionSource");
            }

            var accessToken = jwtAuthProvider.CreateJwtBearerToken(Request,
                                                                   session: result.Session, roles: result.Roles, perms: result.Permissions);

            var response = new GetAccessTokenResponse
            {
                AccessToken = accessToken
            };

            if (request.UseTokenCookie.GetValueOrDefault(jwtAuthProvider.UseTokenCookie) != true)
            {
                return(response);
            }

            return(new HttpResult(new GetAccessTokenResponse())
            {
                Cookies =
                {
                    new Cookie(Keywords.TokenCookie, accessToken, Cookies.RootPath)
                    {
                        HttpOnly = true,
                        Secure = Request.IsSecureConnection,
                        Expires = DateTime.UtcNow.Add(jwtAuthProvider.ExpireTokensIn),
                    }
                }
            });
        }
            public object Any(GetAccessToken request)
            {
                var jwtAuthProvider = (MyJwtAuthProvider)AuthenticateService.GetRequiredJwtAuthProvider();

                if (jwtAuthProvider.RequireSecureConnection && !Request.IsSecureConnection)
                {
                    throw HttpError.Forbidden(ErrorMessages.JwtRequiresSecureConnection.Localize(Request));
                }

                if (string.IsNullOrEmpty(request.RefreshToken))
                {
                    throw new ArgumentNullException(nameof(request.RefreshToken));
                }

                JsonObject jwtPayload;

                try
                {
                    jwtPayload = jwtAuthProvider.GetVerifiedJwtPayload(Request, request.RefreshToken.Split(CharConstants.DOT));
                }
                catch (ArgumentException)
                {
                    throw;
                }
                catch (Exception ex)
                {
                    throw new ArgumentException(ex.Message);
                }

                jwtAuthProvider.AssertJwtPayloadIsValid(jwtPayload);

                if (jwtAuthProvider.ValidateRefreshToken != null && !jwtAuthProvider.ValidateRefreshToken(jwtPayload, Request))
                {
                    throw new ArgumentException(ErrorMessages.RefreshTokenInvalid.Localize(Request), nameof(request.RefreshToken));
                }

                var userId = jwtPayload[TokenConstants.SUB];

                CustomUserSession session;

                if (AuthRepository is IUserAuthRepository userRepo)
                {
                    var userAuth = userRepo.GetUserAuth(userId);
                    if (userAuth == null)
                    {
                        throw HttpError.NotFound(ErrorMessages.UserNotExists.Localize(Request));
                    }

                    if (jwtAuthProvider.IsAccountLocked(userRepo, userAuth))
                    {
                        throw new AuthenticationException(ErrorMessages.UserAccountLocked.Localize(Request));
                    }

                    session = SessionFeature.CreateNewSession(Request, SessionExtensions.CreateRandomSessionId()) as CustomUserSession;
                    PopulateSession(userRepo, userAuth, session, userId);
                }
                else
                {
                    throw new NotSupportedException("JWT RefreshTokens requires a registered IUserAuthRepository or an AuthProvider implementing IUserSessionSource");
                }

                var accessToken = jwtAuthProvider.CreateJwtBearerToken(Request, session);

                return(new GetAccessTokenResponse
                {
                    AccessToken = accessToken
                });
            }