Esempio n. 1
0
        private UserBE SetContextAndAuthenticate(DreamMessage request, uint serviceid, bool autoCreateExternalUser, bool allowAnon, bool touchUser, out bool altPassword)
        {
            UserBE user = AuthBL.Authenticate(DreamContext.Current, request, serviceid, autoCreateExternalUser, allowAnon, out altPassword);

            // check if we should touch the user
            bool update = false;

            if (touchUser)
            {
                update = true;
            }
            else if (user.UserActive)
            {
                double?updateTimespan = DekiContext.Current.Instance.StatsUpdateUserOnAccess;
                if (updateTimespan.HasValue && (user.Touched.AddSeconds(updateTimespan.Value) <= DateTime.UtcNow))
                {
                    update = true;
                }
            }

            // update user's last logged time column
            if (update)
            {
                user = UserBL.UpdateUserTimestamp(user);
            }
            DekiContext.Current.User = user;

            // check that a user token is set (it might not be set if a user logs-in directly using HTTP authentication)
            if (!UserBL.IsAnonymous(user) && (DekiContext.Current.AuthToken == null))
            {
                DekiContext.Current.AuthToken = AuthBL.CreateAuthTokenForUser(user);
            }
            BanningBL.PerformBanCheckForCurrentUser();
            return(user);
        }
Esempio n. 2
0
        public Yield PostUserAuth(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            uint serviceId = context.GetParam <uint>("authprovider", 0);
            bool altPassword;

            //This will internally fail with a 501 response if credentials are invalid.
            //Anonymous accounts (no credentials/authtoken) are not allowed -> 401
            UserBE u = SetContextAndAuthenticate(request, serviceId, context.Verb == Verb.POST, false, true, out altPassword);

            PermissionsBL.CheckUserAllowed(u, Permissions.LOGIN);


            string token = AuthBL.CreateAuthTokenForUser(u);

            try {
                PageBL.CreateUserHomePage(DekiContext.Current.User);
            } catch { }
            XUri         redirectUri = XUri.TryParse(context.GetParam("redirect", null));
            DreamMessage ret         = BuildSetAuthTokenResponse(token, redirectUri);

            DekiContext.Current.Instance.EventSink.UserLogin(DekiContext.Current.Now, DekiContext.Current.User);

            //TODO Max: Set a response header or status to indicate that an alt password was used.
            response.Return(ret);
            yield break;
        }
Esempio n. 3
0
        private static string CreatePrinceHtml(XDoc content)
        {
            // use authtoken for embedded images
            string authtoken = AuthBL.CreateAuthTokenForUser(DekiContext.Current.User);

            foreach (XDoc img in content["//img"])
            {
                string src = img["@src"].AsText;
                if (StringUtil.StartsWithInvariant(src, "/"))
                {
                    src = DekiContext.Current.UiUri.Uri.SchemeHostPort + src;
                }

                if (StringUtil.StartsWithInvariantIgnoreCase(src, DekiContext.Current.UiUri.Uri.SchemeHostPort + "/") ||
                    StringUtil.StartsWithInvariantIgnoreCase(src, Utils.MKS_PATH))
                {
                    img["@src"].ReplaceValue(new XUri(src).With("authtoken", authtoken));
                }
            }

            // prepend doctype so prince uses xhtml parser
            // need to use strings instead of XDoc since XDoc doesn't allow you to set a doctype
            string doctype = "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">";

            return(doctype + content.ToXHtml());
        }
Esempio n. 4
0
        public Yield PutPasswordChange(DreamContext context, DreamMessage request, Result <DreamMessage> response)
        {
            UserBE targetUser = GetUserFromUrlMustExist();
            string password   = request.AsText();

            if (string.IsNullOrEmpty(password))
            {
                throw new UserNewPasswordNotProvidedInvalidArgumentException();
            }
            if (password.Length < 4)
            {
                throw new UserNewPasswordTooShortInvalidArgumentException();
            }

            // Ensure that the password is being set only on local accounts
            ServiceBE s = ServiceBL.GetServiceById(targetUser.ServiceId);

            if (s != null && !ServiceBL.IsLocalAuthService(s))
            {
                throw new UserCanOnlyChangeLocalUserPasswordInvalidOperationException();
            }
            if (UserBL.IsAnonymous(targetUser))
            {
                throw new UserCannotChangeAnonPasswordInvalidOperationException();
            }

            // Admins can always change anyones password.
            if (PermissionsBL.IsUserAllowed(DekiContext.Current.User, Permissions.ADMIN))
            {
                //For admins a currentpassword is option but if given then it should be validated
                string currentPwd = context.GetParam("currentpassword", string.Empty);
                if (!string.IsNullOrEmpty(currentPwd))
                {
                    if (!AuthBL.IsValidAuthenticationForLocalUser(targetUser, currentPwd))
                    {
                        throw new UserCurrentPasswordIncorrectForbiddenException();
                    }
                }
            }
            else if (DekiContext.Current.User.ID == targetUser.ID)
            {
                if (context.GetParam("altpassword", false))
                {
                    throw new UserCannotChangeOwnAltPasswordInvalidOperationException();
                }

                // User changing their own password requires knowledge of their current password
                string currentPwd = context.GetParam("currentpassword");
                if (!AuthBL.IsValidAuthenticationForLocalUser(DekiContext.Current.User, currentPwd))
                {
                    throw new UserCurrentPasswordIncorrectForbiddenException();
                }
            }
            else
            {
                throw new UserMustBeTargetOrAdminForbiddenException();
            }
            bool altPassword = context.GetParam <bool>("altpassword", false);

            targetUser = UserBL.SetPassword(targetUser, password, altPassword);
            if (DekiContext.Current.User.ID == targetUser.ID)
            {
                response.Return(BuildSetAuthTokenResponse(AuthBL.CreateAuthTokenForUser(targetUser), null));
            }
            else
            {
                response.Return(DreamMessage.Ok());
            }
            yield break;
        }