Пример #1
0
        public ActionResult Add(int organizationId, AddUserModel model)
        {
            var organization = new OrganizationEntity(organizationId);

            if (organization.IsNew)
            {
                throw new HttpException(404, SharedRes.Error.NotFound_Organization);
            }

            var restrictionKey = EpicMembershipProvider.CreateSalt(16);

            if (ModelState.IsValid)
            {
                if (!Permissions.UserHasPermission("Edit", organization))
                {
                    throw new HttpException(401, SharedRes.Error.Unauthorized_OrganizationEdit);
                }

                // Validate submitted role.
                if (!model.Role.HasValue || !(OrganizationUtils.GetAllowedRoles(organizationId).Any(r => r.RoleId == model.Role)))
                {
                    throw new HttpException(417, ControllerRes.Account.Invalid_RoleSpecified);
                }

                // Locations are only valid for non-admin users.
                bool isAdmin = RoleUtils.IsRoleForAdmin(model.Role.Value);
                if (!isAdmin)
                {
                    // Validate submitted locations are locations of the organization.
                    if (model.Locations.Except(new LinqMetaData().Location.Where(l => l.OrganizationId == organizationId).Select(l => l.LocationId).ToList()).Any())
                    {
                        throw new HttpException(404, SharedRes.Error.NotFound_Location);
                    }
                }

                Transaction transaction = new Transaction(IsolationLevel.ReadCommitted, "user add");

                try
                {
                    UserEntity user = new UserEntity
                    {
                        OrganizationId = organizationId,
                        FirstName      = model.FirstName,
                        LastName       = model.LastName,
                        EmailAddress   = model.EmailAddress,
                        Username       = string.Empty,
                        Password       = string.Empty
                    };
                    transaction.Add(user);

                    // If role is non-admin, set up locations.
                    if (!isAdmin)
                    {
                        foreach (var loc in model.Locations)
                        {
                            var assignedLocation = user.UserAssignedLocations.AddNew();
                            assignedLocation.LocationId = loc;
                        }
                    }

                    var userRole = user.Roles.AddNew();
                    userRole.RoleId = model.Role.Value;

                    var accountRestriction = new AccountRestrictionEntity
                    {
                        AccountRestrictionType = AccountRestrictionType.NewUser,
                        RestrictionKey         = restrictionKey,
                        EmailAddress           = model.EmailAddress,
                        Parameters             = string.IsNullOrWhiteSpace(model.Pin) ? string.Empty : model.Pin,
                        CreatedBy = Membership.GetUser().GetUserId().Id,
                        IPAddress = Request.ServerVariables["REMOTE_ADDR"]
                    };
                    transaction.Add(accountRestriction);
                    accountRestriction.Save();

                    var userRestriction = user.UserAccountRestrictions.AddNew();
                    userRestriction.AccountRestrictionId = accountRestriction.AccountRestrictionId;

                    // Save recursively ... so assigned locations, role and restriction are saved, too.
                    user.Save(true);

                    transaction.Commit();
                }
                catch (Exception)
                {
                    transaction.Rollback();
                    throw new HttpException(500, SharedRes.Error.Error_DatabaseUnknown);
                }
                finally
                {
                    transaction.Dispose();
                }

                // Send email for registration validation.
                SendRegistrationEmail(model, restrictionKey);

                // Add user complete. Modal dialog will close, so no response except "success".
                return(new EmptyResult());
            }

            Response.StatusCode             = 417;
            Response.TrySkipIisCustomErrors = true;

            return(PartialView(model));
        }
Пример #2
0
        public ActionResult Edit(int userId, EditUserModel model)
        {
            var user = new UserEntity(userId);

            if (user.IsNew)
            {
                throw new HttpException(404, SharedRes.Error.NotFound_User);
            }

            if (!RoleUtils.IsUserServiceAdmin() && !RoleUtils.IsUserOrgAdmin())
            {
                throw new HttpException(401, SharedRes.Error.Unauthorized_UserEdit);
            }

            if (RoleUtils.IsUserOrgAdmin() && user.OrganizationId != Membership.GetUser().GetUserId().OrganizationId)
            {
                throw new HttpException(401, SharedRes.Error.Unauthorized_OrganizationEdit);
            }

            if (ModelState.IsValid)
            {
                // Validate submitted role.
                if (!model.Role.HasValue || !(OrganizationUtils.GetAllowedRoles(model.OrganizationId).Any(r => r.RoleId == model.Role)))
                {
                    throw new HttpException(417, ControllerRes.Account.Invalid_RoleSpecified);
                }

                // Locations are only valid for non-admin users.
                bool isAdmin = RoleUtils.IsRoleForAdmin(model.Role.Value);
                if (!isAdmin)
                {
                    // Validate submitted locations are locations of the organization.
                    if (model.Locations.Except(new LinqMetaData().Location.Where(l => l.OrganizationId == model.OrganizationId).Select(l => l.LocationId).ToList()).Any())
                    {
                        throw new HttpException(404, SharedRes.Error.NotFound_Location);
                    }
                }

                // Set flag to indicate whether or not it's a pending registration.
                // Not using the posted back value in the model for security reasons.
                bool isPendingRegistration = user.UserAccountRestrictions.Count > 0 && user.UserAccountRestrictions[0].AccountRestriction.AccountRestrictionType == AccountRestrictionType.NewUser;

                // If not pending registration and username changed, validate username is unique.
                // Also, set flag to indicate if it's the current user changing own username.
                bool isCurrentUsernameChange = false;
                if (!isPendingRegistration && user.Username != model.UserName)
                {
                    if (UserUtils.IsUsernameUsed(model.UserName))
                    {
                        throw new HttpException(417, ControllerRes.Account.Invalid_DuplicateUsername);
                    }

                    isCurrentUsernameChange = Membership.GetUser().GetUserId().Id == userId;
                }

                // Set flag to indicate whether or not the email address in a registration
                // has changed.
                bool isRegistrationChange = isPendingRegistration && user.EmailAddress != model.EmailAddress;

                Transaction transaction = new Transaction(IsolationLevel.ReadCommitted, "user add");

                try
                {
                    transaction.Add(user);

                    // Username is empty in pending registrations and can't be changed.
                    // And current user username change isn't a simple change; don't do here.
                    if (!isPendingRegistration && !isCurrentUsernameChange)
                    {
                        user.Username = model.UserName;
                    }

                    user.EmailAddress = model.EmailAddress;
                    user.FirstName    = model.FirstName;
                    user.LastName     = model.LastName;

                    if (RoleUtils.IsUserServiceAdmin())
                    {
                        user.IsActive = model.IsActive;
                    }

                    // Did role change?
                    if (user.Roles.Count == 0 || user.Roles[0].RoleId != model.Role.Value)
                    {
                        user.Roles.DeleteMulti();
                        var userRole = user.Roles.AddNew();
                        userRole.RoleId = model.Role.Value;
                    }

                    int[] newLocations = new int[0];
                    int[] oldLocations;

                    if (!isAdmin)
                    {
                        // User is not an admin. So find the set of locations user has been added to,
                        // and the set of location user has been removed from.
                        newLocations = model.Locations.Except(user.UserAssignedLocations.Select(l => l.LocationId)).ToArray();
                        oldLocations = user.UserAssignedLocations.Select(l => l.LocationId).Except(model.Locations).ToArray();
                    }
                    else
                    {
                        // User is admin. So user will be removed from all locations (admins aren't
                        // assigned to locations).
                        oldLocations = user.UserAssignedLocations.Select(l => l.LocationId).ToArray();
                    }

                    if (oldLocations.Length > 0)
                    {
                        user.UserAssignedLocations.DeleteMulti(UserAssignedLocationFields.UserId == user.UserId & UserAssignedLocationFields.LocationId == oldLocations);
                    }

                    if (newLocations.Length > 0)
                    {
                        foreach (var loc in newLocations)
                        {
                            var assignedLocation = user.UserAssignedLocations.AddNew();
                            assignedLocation.LocationId = loc;
                        }
                    }

                    // If the registration email has changed, update the email address in the account
                    // restriction.
                    if (isRegistrationChange)
                    {
                        user.UserAccountRestrictions[0].AccountRestriction.EmailAddress = model.EmailAddress;
                    }

                    // Is current user changing own username?
                    if (isCurrentUsernameChange)
                    {
                        // Changing the current user's username requres special handling because the
                        // forms-auth cookies must be updated with the new username. The delegate will
                        // be invoked to save the new username updating the datbase. In this case, it
                        // needs to be done within the transaction created here.
                        //
                        // Have already validated the username as unique. So the only reason for this
                        // to fail is with some exception thrown, which will be handled in the "catch".
                        Membership.GetUser().ChangeUsername(model.UserName,
                                                            delegate(string username)
                        {
                            user.Username = username;
                            user.Save(true);
                            // ReSharper disable AccessToDisposedClosure
                            transaction.Commit();
                            // ReSharper restore AccessToDisposedClosure
                        });
                    }
                    else
                    {
                        user.Save(true);
                        transaction.Commit();
                    }
                }
                catch (Exception)
                {
                    transaction.Rollback();
                    throw new HttpException(500, SharedRes.Error.Error_DatabaseUnknown);
                }
                finally
                {
                    transaction.Dispose();
                }

                // If registration email has changed, need to re-send the registration email.
                if (isRegistrationChange)
                {
                    SendRegistrationEmail(model, user.UserAccountRestrictions[0].AccountRestriction.RestrictionKey);
                }
            }

            return((Request.IsAjaxRequest() || ControllerContext.IsChildAction)
                                           ? (ActionResult) new EmptyResult()
                                           : View(GetEditModel(userId)));
        }