我正在用spring boot、spring security和thymeleaf制作一个小api。我已经做了工作登录,安全角色,现在我正在尝试注册。如果我添加了新的(正确的数据库)数据,那么就正确地创建了用户,但是我在crmuser中做了一些经典的验证,比如@notnull和我自己的电子邮件验证和密码匹配。它们都不起作用。我不知道为什么。唯一有效的是我的控制器方法中的“用户名已经存在”。有人能帮忙吗?
import com.marcinha.stylist.validation.FieldMatch;
import com.marcinha.stylist.validation.ValidEmail;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
@FieldMatch.List({
@FieldMatch(first = "password", second = "matchingPassword", message = "The password fields must match")
})
public class CrmUser {
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String userName;
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String password;
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String matchingPassword;
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String firstName;
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String lastName;
@ValidEmail
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String email;
@NotNull(message = "is required")
@Size(min = 1, message = "is required")
private String country;
public CrmUser() {
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getMatchingPassword() {
return matchingPassword;
}
public void setMatchingPassword(String matchingPassword) {
this.matchingPassword = matchingPassword;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getCountry() {
return country;
}
public void setCountry(String country) {
this.country = country;
}
}
import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class EmailValidator implements ConstraintValidator<ValidEmail, String> {
private Pattern pattern;
private Matcher theMatcher;
private final static String EMAIL_PATTERN = "^[_A-Za-z0-9-\\\\+]+(\\\\.[_A-Za-z0-9-]+)*@\"\n" +
"\t\t\t+ \"[A-Za-z0-9-]+(\\\\.[A-Za-z0-9]+)*(\\\\.[A-Za-z]{2,})$";
@Override
public boolean isValid(String email, ConstraintValidatorContext constraintValidatorContext) {
pattern = Pattern.compile(EMAIL_PATTERN);
if (email == null) {
return false;
}
theMatcher = pattern.matcher(email);
return theMatcher.matches();
}
}
import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.*;
@Constraint(validatedBy = EmailValidator.class)
@Target({ElementType.TYPE, ElementType.FIELD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface ValidEmail {
String message() default "Invalid email";
Class<?>[] groups() default{};
Class<? extends Payload>[] payload() default {};
}
import org.springframework.beans.BeanWrapperImpl;
import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
public class FieldMatchValidator implements ConstraintValidator<FieldMatch, Object> {
private String firstFieldName;
private String secondFieldName;
private String message;
@Override
public void initialize(FieldMatch constraintAnnotation) {
firstFieldName = constraintAnnotation.first();
secondFieldName = constraintAnnotation.second();
message = constraintAnnotation.message();
}
@Override
public boolean isValid(Object o, ConstraintValidatorContext constraintValidatorContext) {
boolean valid = true;
try{
Object firstObj = new BeanWrapperImpl(o).getPropertyValue(firstFieldName);
Object secondObj = new BeanWrapperImpl(o).getPropertyValue(secondFieldName);
valid = firstObj == null && secondObj == null || firstObj != null && secondObj.equals(firstObj);
}
catch (Exception ignore){
}
if(!valid){
constraintValidatorContext.buildConstraintViolationWithTemplate(message)
.addPropertyNode(firstFieldName)
.addConstraintViolation()
.disableDefaultConstraintViolation();
}
return valid;
}
}
import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.*;
@Documented
@Constraint(validatedBy = FieldMatchValidator.class)
@Target({ElementType.ANNOTATION_TYPE, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
public @interface FieldMatch {
String message() default "";
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
String first();
String second();
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@interface List {
FieldMatch[] value();
}
}
@Controller
@RequestMapping("/registry")
public class RegistrationController {
@Autowired
private UserService service;
private Logger logger = Logger.getLogger(getClass().getName());
@GetMapping("/showRegistrationForm")
public String showRegistration(Model model) {
model.addAttribute("crmUser", new CrmUser());
return "registration-from";
}
@PostMapping("/processingRegistrationForm")
public String registry(@Valid @ModelAttribute("crmUser") CrmUser theCrmUser,
BindingResult theBindingResult,
Model theModel) {
String username = theCrmUser.getUserName();
logger.info("Processing registration form for: " + username);
if (theBindingResult.hasErrors()) {
return "registration-form";
}
User existingUser = service.findByUserName(username);
if (existingUser != null) {
theModel.addAttribute("crmUser", new CrmUser());
theModel.addAttribute("registrationError", "User already exist in database");
logger.warning("User name already exists.");
return "registration-form";
}
service.save(theCrmUser);
logger.info("Successfully created user: " + username);
return "registration-confirmation";
}
}
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<Title> Registration form </Title>
<link rel="stylesheet"
href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
</head>
<body>
<form th:action="@{/registry/processingRegistrationForm}"
th:object="${crmUser}" method="POST">
<!-- Check for registration error -->
<div th:if="${registrationError}">
<span th:text="${registrationError}"></span>
</div>
<!-- User name -->
<div>
<input type="text" th:field="*{userName}" placeholder="Username (*)">
</div>
<div th:if="${#fields.hasErrors('userName')}">
<ul>
<li th:each="err : ${#fields.errors('userName')}" th:text="'User name ' + ${err}" />
</ul>
</div>
<!-- Password -->
<div>
<input type="password" th:field="*{password}" placeholder="Password (*)">
</div>
<div th:if="${#fields.hasErrors('password')}">
<ul>
<li th:each="err : ${#fields.errors('password')}" th:text="'Password ' + ${err}" />
</ul>
</div>
<!-- Confirm Password -->
<div>
<input type="password" th:field="*{matchingPassword}" placeholder="confirm password (*)">
</div>
<div th:if="${#fields.hasErrors('matchingPassword')}">
<ul>
<li th:each="err : ${#fields.errors('matchingPassword')}" th:text="'Password ' + ${err}" />
</ul>
</div>
<!--First Name -->
<div>
<input type="text" th:field="*{firstName}" placeholder="First name (*)">
</div>
<div th:if="${#fields.hasErrors('firstName')}">
<ul>
<li th:each="err : ${#fields.errors('firstName')}" th:text="'First name ' + ${err}" />
</ul>
</div>
<!-- Last Name -->
<div>
<input type="text" th:field="*{lastName}" placeholder="Last name (*)">
</div>
<div th:if="${#fields.hasErrors('lastName')}">
<ul>
<li th:each="err : ${#fields.errors('lastName')}" th:text="'Last name ' + ${err}" />
</ul>
</div>
<!-- Email -->
<div>
<input type="text" th:field="*{email}" placeholder="Email (*)">
</div>
<div th:if="${#fields.hasErrors('email')}">
<ul>
<li th:each="err : ${#fields.errors('email')}" th:text="'Email ' + ${err}" />
</ul>
</div>
<!-- Register Button -->
<div class="col-sm-6 controls">
<button type="submit" class="btn btn-primary">Register</button>
</div>
</form>
</body>
</html>
1条答案
按热度按时间9o685dep1#
没关系:我在pom中漏掉了一个依赖项: