MIFOSX-1868
This commit is contained in:
@@ -30106,6 +30106,7 @@ GET https://DomainName/api/v1/users
|
||||
"firstname": "App",
|
||||
"lastname": "Administrator",
|
||||
"email": "demomfi@mifos.org",
|
||||
"passwordNeverExpire": false,
|
||||
"staff": {
|
||||
"id": 1,
|
||||
"firstname": "Test",
|
||||
@@ -30197,6 +30198,7 @@ GET https://DomainName/api/v1/users/{userId}
|
||||
"firstname": "App",
|
||||
"lastname": "Administrator",
|
||||
"email": "demomfi@mifos.org",
|
||||
"passwordNeverExpire": true,
|
||||
"staff": {
|
||||
"id": 1,
|
||||
"firstname": "Test",
|
||||
@@ -30246,7 +30248,7 @@ GET https://DomainName/api/v1/users/{userId}
|
||||
<td><div class="mifosXHeading2">Optional Fields</div></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>staffId</td>
|
||||
<td>staffId,passwordNeverExpire</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
|
||||
+10
-6
@@ -5,11 +5,6 @@
|
||||
*/
|
||||
package org.mifosplatform.infrastructure.security.service;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
import org.mifosplatform.commands.domain.CommandWrapper;
|
||||
import org.mifosplatform.commands.service.CommandWrapperBuilder;
|
||||
import org.mifosplatform.infrastructure.configuration.domain.ConfigurationDomainService;
|
||||
@@ -18,12 +13,19 @@ import org.mifosplatform.infrastructure.security.exception.NoAuthorizationExcept
|
||||
import org.mifosplatform.infrastructure.security.exception.ResetPasswordException;
|
||||
import org.mifosplatform.useradministration.domain.AppUser;
|
||||
import org.mifosplatform.useradministration.exception.UnAuthenticatedUserException;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.security.core.Authentication;
|
||||
import org.springframework.security.core.context.SecurityContext;
|
||||
import org.springframework.security.core.context.SecurityContextHolder;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Wrapper around spring security's {@link SecurityContext} for extracted the
|
||||
* current authenticated {@link AppUser}.
|
||||
@@ -32,6 +34,8 @@ import org.springframework.stereotype.Service;
|
||||
@Service
|
||||
public class SpringSecurityPlatformSecurityContext implements PlatformSecurityContext {
|
||||
|
||||
private final static Logger logger = LoggerFactory.getLogger(SpringSecurityPlatformSecurityContext.class);
|
||||
|
||||
private final ConfigurationDomainService configurationDomainService;
|
||||
|
||||
public static final List<CommandWrapper> EXEMPT_FROM_PASSWORD_RESET_CHECK = new ArrayList<CommandWrapper>() {
|
||||
@@ -124,7 +128,7 @@ public class SpringSecurityPlatformSecurityContext implements PlatformSecurityCo
|
||||
@Override
|
||||
public boolean doesPasswordHasToBeRenewed(AppUser currentUser) {
|
||||
|
||||
if (this.configurationDomainService.isPasswordForcedResetEnable()) {
|
||||
if (this.configurationDomainService.isPasswordForcedResetEnable() && !currentUser.getPasswordNeverExpire()) {
|
||||
|
||||
Long passwordDurationDays = this.configurationDomainService.retrievePasswordLiveTime();
|
||||
final Date passWordLastUpdateDate = currentUser.getLastTimePasswordUpdated();
|
||||
|
||||
+9
-7
@@ -22,6 +22,7 @@ public class AppUserData {
|
||||
private final String firstname;
|
||||
private final String lastname;
|
||||
private final String email;
|
||||
private final Boolean passwordNeverExpire;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private final Collection<OfficeData> allowedOffices;
|
||||
@@ -31,26 +32,26 @@ public class AppUserData {
|
||||
|
||||
public static AppUserData template(final AppUserData user, final Collection<OfficeData> officesForDropdown) {
|
||||
return new AppUserData(user.id, user.username, user.email, user.officeId, user.officeName, user.firstname, user.lastname,
|
||||
user.availableRoles, user.selectedRoles, officesForDropdown, user.staff);
|
||||
user.availableRoles, user.selectedRoles, officesForDropdown, user.staff,user.passwordNeverExpire);
|
||||
}
|
||||
|
||||
public static AppUserData template(final Collection<OfficeData> offices, final Collection<RoleData> availableRoles) {
|
||||
return new AppUserData(null, null, null, null, null, null, null, availableRoles, null, offices, null);
|
||||
return new AppUserData(null, null, null, null, null, null, null, availableRoles, null, offices, null,null);
|
||||
}
|
||||
|
||||
public static AppUserData dropdown(final Long id, final String username) {
|
||||
return new AppUserData(id, username, null, null, null, null, null, null, null, null, null);
|
||||
return new AppUserData(id, username, null, null, null, null, null, null, null, null, null,null);
|
||||
}
|
||||
|
||||
public static AppUserData instance(final Long id, final String username, final String email, final Long officeId,
|
||||
final String officeName, final String firstname, final String lastname, final Collection<RoleData> availableRoles,
|
||||
final Collection<RoleData> selectedRoles, final StaffData staff) {
|
||||
return new AppUserData(id, username, email, officeId, officeName, firstname, lastname, availableRoles, selectedRoles, null, staff);
|
||||
final Collection<RoleData> selectedRoles, final StaffData staff,final Boolean passwordNeverExpire) {
|
||||
return new AppUserData(id, username, email, officeId, officeName, firstname, lastname, availableRoles, selectedRoles, null, staff,passwordNeverExpire);
|
||||
}
|
||||
|
||||
private AppUserData(final Long id, final String username, final String email, final Long officeId, final String officeName,
|
||||
final String firstname, final String lastname, final Collection<RoleData> availableRoles,
|
||||
final Collection<RoleData> selectedRoles, final Collection<OfficeData> allowedOffices, final StaffData staff) {
|
||||
final String firstname, final String lastname, final Collection<RoleData> availableRoles,
|
||||
final Collection<RoleData> selectedRoles, final Collection<OfficeData> allowedOffices, final StaffData staff, final Boolean passwordNeverExpire) {
|
||||
this.id = id;
|
||||
this.username = username;
|
||||
this.officeId = officeId;
|
||||
@@ -62,6 +63,7 @@ public class AppUserData {
|
||||
this.availableRoles = availableRoles;
|
||||
this.selectedRoles = selectedRoles;
|
||||
this.staff = staff;
|
||||
this.passwordNeverExpire = passwordNeverExpire;
|
||||
}
|
||||
|
||||
public boolean hasIdentifyOf(final Long createdById) {
|
||||
|
||||
+26
-2
@@ -97,6 +97,9 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
@Temporal(TemporalType.DATE)
|
||||
private Date lastTimePasswordUpdated;
|
||||
|
||||
@Column(name = "password_never_expire", nullable = false)
|
||||
private boolean passwordNeverExpire;
|
||||
|
||||
public static AppUser fromJson(final Office userOffice, final Staff linkedStaff, final Set<Role> allRoles, final JsonCommand command) {
|
||||
|
||||
final String username = command.stringValueOfParameterNamed("username");
|
||||
@@ -107,6 +110,12 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
password = new RandomPasswordGenerator(13).generate();
|
||||
}
|
||||
|
||||
boolean passwordNeverExpire = false;
|
||||
|
||||
if(command.parameterExists("passwordNeverExpire")){
|
||||
passwordNeverExpire = command.booleanPrimitiveValueOfParameterNamed("passwordNeverExpire");
|
||||
}
|
||||
|
||||
final boolean userEnabled = true;
|
||||
final boolean userAccountNonExpired = true;
|
||||
final boolean userCredentialsNonExpired = true;
|
||||
@@ -122,7 +131,7 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
final String firstname = command.stringValueOfParameterNamed("firstname");
|
||||
final String lastname = command.stringValueOfParameterNamed("lastname");
|
||||
|
||||
return new AppUser(userOffice, user, allRoles, email, firstname, lastname, linkedStaff);
|
||||
return new AppUser(userOffice, user, allRoles, email, firstname, lastname, linkedStaff,passwordNeverExpire);
|
||||
}
|
||||
|
||||
protected AppUser() {
|
||||
@@ -132,7 +141,7 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
}
|
||||
|
||||
public AppUser(final Office office, final User user, final Set<Role> roles, final String email, final String firstname,
|
||||
final String lastname, final Staff staff) {
|
||||
final String lastname, final Staff staff, final boolean passwordNeverExpire) {
|
||||
this.office = office;
|
||||
this.email = email.trim();
|
||||
this.username = user.getUsername().trim();
|
||||
@@ -147,6 +156,7 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
this.firstTimeLoginRemaining = true;
|
||||
this.lastTimePasswordUpdated = DateUtils.getDateOfTenant();
|
||||
this.staff = staff;
|
||||
this.passwordNeverExpire = passwordNeverExpire;
|
||||
}
|
||||
|
||||
public EnumOptionData organisationalRoleData() {
|
||||
@@ -250,6 +260,16 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
this.email = newValue;
|
||||
}
|
||||
|
||||
final String passwordNeverExpire = "passwordNeverExpire";
|
||||
|
||||
if (command.hasParameter(passwordNeverExpire)) {
|
||||
if (command.isChangeInBooleanParameterNamed(passwordNeverExpire, this.passwordNeverExpire)) {
|
||||
final boolean newValue = command.booleanPrimitiveValueOfParameterNamed(passwordNeverExpire);
|
||||
actualChanges.put(passwordNeverExpire, newValue);
|
||||
this.passwordNeverExpire = newValue;
|
||||
}
|
||||
}
|
||||
|
||||
return actualChanges;
|
||||
}
|
||||
|
||||
@@ -351,6 +371,10 @@ public class AppUser extends AbstractPersistable<Long> implements PlatformUser {
|
||||
return this.staff;
|
||||
}
|
||||
|
||||
public boolean getPasswordNeverExpire() {
|
||||
return this.passwordNeverExpire;
|
||||
}
|
||||
|
||||
public Date getLastTimePasswordUpdated() {
|
||||
return this.lastTimePasswordUpdated;
|
||||
}
|
||||
|
||||
+4
-3
@@ -120,7 +120,7 @@ public class AppUserReadPlatformServiceImpl implements AppUserReadPlatformServic
|
||||
}
|
||||
|
||||
return AppUserData.instance(user.getId(), user.getUsername(), user.getEmail(), user.getOffice().getId(),
|
||||
user.getOffice().getName(), user.getFirstname(), user.getLastname(), availableRoles, selectedUserRoles, linkedStaff);
|
||||
user.getOffice().getName(), user.getFirstname(), user.getLastname(), availableRoles, selectedUserRoles, linkedStaff,user.getPasswordNeverExpire());
|
||||
}
|
||||
|
||||
private static final class AppUserMapper implements RowMapper<AppUserData> {
|
||||
@@ -144,6 +144,7 @@ public class AppUserReadPlatformServiceImpl implements AppUserReadPlatformServic
|
||||
final Long officeId = JdbcSupport.getLong(rs, "officeId");
|
||||
final String officeName = rs.getString("officeName");
|
||||
final Long staffId = JdbcSupport.getLong(rs, "staffId");
|
||||
final Boolean passwordNeverExpire = rs.getBoolean("passwordNeverExpire");
|
||||
final Collection<RoleData> selectedRoles = this.roleReadPlatformService.retrieveAppUserRoles(id);
|
||||
|
||||
final StaffData linkedStaff;
|
||||
@@ -152,11 +153,11 @@ public class AppUserReadPlatformServiceImpl implements AppUserReadPlatformServic
|
||||
} else {
|
||||
linkedStaff = null;
|
||||
}
|
||||
return AppUserData.instance(id, username, email, officeId, officeName, firstname, lastname, null, selectedRoles, linkedStaff);
|
||||
return AppUserData.instance(id, username, email, officeId, officeName, firstname, lastname, null, selectedRoles, linkedStaff,passwordNeverExpire);
|
||||
}
|
||||
|
||||
public String schema() {
|
||||
return " u.id as id, u.username as username, u.firstname as firstname, u.lastname as lastname, u.email as email,"
|
||||
return " u.id as id, u.username as username, u.firstname as firstname, u.lastname as lastname, u.email as email, u.password_never_expire as passwordNeverExpire, "
|
||||
+ " u.office_id as officeId, o.name as officeName, u.staff_id as staffId from m_appuser u "
|
||||
+ " join m_office o on o.id = u.office_id where o.hierarchy like ? and u.is_deleted=0 order by u.username";
|
||||
}
|
||||
|
||||
+11
-1
@@ -32,7 +32,7 @@ public final class UserDataValidator {
|
||||
* The parameters supported for this command.
|
||||
*/
|
||||
private final Set<String> supportedParameters = new HashSet<>(Arrays.asList("username", "firstname", "lastname", "password",
|
||||
"repeatPassword", "email", "officeId", "notSelectedRoles", "roles", "sendPasswordToEmail", "staffId"));
|
||||
"repeatPassword", "email", "officeId", "notSelectedRoles", "roles", "sendPasswordToEmail", "staffId","passwordNeverExpire"));
|
||||
|
||||
private final FromJsonHelper fromApiJsonHelper;
|
||||
|
||||
@@ -86,6 +86,11 @@ public final class UserDataValidator {
|
||||
baseDataValidator.reset().parameter("staffId").value(staffId).notNull().integerGreaterThanZero();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists("passwordNeverExpire", element)) {
|
||||
final boolean passwordNeverExpire = this.fromApiJsonHelper.extractBooleanNamed("passwordNeverExpire", element);
|
||||
baseDataValidator.reset().parameter("passwordNeverExpire").value(passwordNeverExpire).validateForBooleanValue();
|
||||
}
|
||||
|
||||
final String[] roles = this.fromApiJsonHelper.extractArrayNamed("roles", element);
|
||||
baseDataValidator.reset().parameter("roles").value(roles).arrayNotEmpty();
|
||||
|
||||
@@ -151,6 +156,11 @@ public final class UserDataValidator {
|
||||
}
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists("passwordNeverExpire", element)) {
|
||||
final boolean passwordNeverExpire = this.fromApiJsonHelper.extractBooleanNamed("passwordNeverExpire", element);
|
||||
baseDataValidator.reset().parameter("passwordNeverExpire").value(passwordNeverExpire).validateForBooleanValue();
|
||||
}
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
}
|
||||
+1
@@ -0,0 +1 @@
|
||||
ALTER TABLE `m_appuser` ADD `password_never_expire` TINYINT NOT NULL DEFAULT '0' COMMENT 'define if the password, should be check for validity period or not';
|
||||
Reference in New Issue
Block a user