0

I have 3 fields of an entity class which I don't want to be unique but instead i want them to be used as composite fields for a key which must itself be unique. My class POJO:

    @Entity
        @Table(name="EMPLOYEE")
        public class Employee {

            @Id
            @GeneratedValue(strategy = GenerationType.IDENTITY)
            private int id;

            @Size(min=3, max=50)
            @Column(name = "NAME", nullable = false)
            private String name;

            @Size(min=3, max=50)
            @Column(name = "A", nullable = false)
            private String a;
            @Size(min=3, max=50)
            @Column(name = "B", nullable = false)
            private String b;
            @Size(min=3, max=50)
            @Column(name = "C", nullable = false)
            private String c;

            @NotNull
            @DateTimeFormat(pattern="dd/MM/yyyy") 
            @Column(name = "JOINING_DATE", nullable = false)
            @Type(type="org.jadira.usertype.dateandtime.joda.PersistentLocalDate")
            private LocalDate joiningDate;

            @NotNull
            @Digits(integer=8, fraction=2)
            @Column(name = "SALARY", nullable = false)
            private BigDecimal salary;

            @NotEmpty
            @Column(name = "SSN", unique=true, nullable = false)
            private String ssn;
    }

Im working with form submission, validating user input via JSR303 annotations.In case of validation failure, default error messages are shown.I configured a ResourceBundleMessageSource:

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "com.fussa.fyby")
public class AppConfig {

    @Bean
    public ViewResolver viewResolver() {
        InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
        viewResolver.setViewClass(JstlView.class);
        viewResolver.setPrefix("/WEB-INF/views/");
        viewResolver.setSuffix(".jsp");
        return viewResolver;
    }

    @Bean
    public MessageSource messageSource() {
        ResourceBundleMessageSource messageSource = new ResourceBundleMessageSource();
        messageSource.setBasename("messages");
        return messageSource;
    }
}

/src/main/resources/messages.properties

Size.employee.name=between {2} and {1} characters long
NotNull.employee.joiningDate=can not be blank
NotNull.employee.salary=are u working for free !
Digits.employee.salary=Only numeric data with max 8 digits and with max 2 precision is allowed
NotEmpty.employee.ssn=can not be blank
typeMismatch=Invalid format
non.unique.ssn=SSN {0} already exist.

i found this solution for creating an unique key:

@Table( name = "EMPLOYEE",
        uniqueConstraints = { @UniqueConstraint( columnNames = { "A", "B", "C" } ) } )

my question is how can i display a message using messages.properties if that uniqueconstraint has been violated ?

UPDATE 1

@Service("employeeService")
@Transactional
public class EmployeeServiceImpl implements EmployeeService {

    @Autowired
    private EmployeeDao dao;

    //....

    public void saveEmployee(Employee employee) {
        dao.saveEmployee(employee);
    }

}

Thanks for any advice..

FuSsA
  • 4,223
  • 7
  • 39
  • 60
  • is there an exception that's thrown when the uniqueconstraint is violated. if yes, you might be able to grab that exception and display whatever message you want. Just a sugesstion. – Grinish Nepal Apr 15 '16 at 00:21

2 Answers2

1

If you want to use Bean Validation you will need to write a custom constraint which validates that the three columns are unique. Mind you, there is a problem with that. Unless you would lock the whole table, you always have the problem that while your constraint validator checks for uniqueness, another concurrent transaction changes the database. See also this Stackoverflow question - Unique constraint with JPA and Bean Validation. There is a blog post on the Validator Wiki on how a Unique constraints could look like, but it comes with the just mentioned caveat. The validation might pass, but then during insertion time, you could still get a database level exception due to the fact that another transaction has modified the data in the meantime (so your code will need to handle this case as well). Also with Bean Validation 1.1 you probably can just inject the SessionFactory directly.

Community
  • 1
  • 1
Hardy
  • 18,659
  • 3
  • 49
  • 65
0

I managed to create a unique constraint validation for one field, folowing this steps:

1- Create the constraint annotation. 2-create The constraint validator. 3-The error message. 4-how to use the constraint.

i posted the code with the solution here: Link..

Community
  • 1
  • 1
FuSsA
  • 4,223
  • 7
  • 39
  • 60