001/* Copyright (C) 2014 konik.io 002 * 003 * This file is part of the Konik library. 004 * 005 * The Konik library is free software: you can redistribute it and/or modify 006 * it under the terms of the GNU Affero General Public License as 007 * published by the Free Software Foundation, either version 3 of the 008 * License, or (at your option) any later version. 009 * 010 * The Konik library is distributed in the hope that it will be useful, 011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 013 * GNU Affero General Public License for more details. 014 * 015 * You should have received a copy of the GNU Affero General Public License 016 * along with the Konik library. If not, see <http://www.gnu.org/licenses/>. 017 */ 018package io.konik.validation; 019 020import io.konik.validator.annotation.Comfort; 021import io.konik.validator.annotation.Extended; 022import io.konik.zugferd.Invoice; 023import io.konik.zugferd.profile.ConformanceLevel; 024 025import java.util.Set; 026 027import javax.inject.Inject; 028import javax.inject.Named; 029import javax.inject.Singleton; 030import javax.validation.ConstraintViolation; 031import javax.validation.Validation; 032import javax.validation.Validator; 033import javax.validation.ValidatorFactory; 034import javax.validation.groups.Default; 035 036import org.apache.bval.jsr.DefaultMessageInterpolator; 037 038/** 039 * Validates the invoice against the declared invoice profile. 040 */ 041@Named 042@Singleton 043public class InvoiceValidator { 044 045 private final Validator validator; 046 private final MonetarySummationValidator monetarySummationValidator; 047 048 /** 049 * Instantiates a new invoice validator. 050 * 051 * @param validator the validator 052 * @param monetarySummationValidator 053 */ 054 @Inject 055 public InvoiceValidator(Validator validator, MonetarySummationValidator monetarySummationValidator) { 056 super(); 057 this.validator = validator; 058 this.monetarySummationValidator = monetarySummationValidator; 059 } 060 061 /** 062 * Instantiates a new invoice validator. 063 * 064 * @param validator the validator 065 */ 066 public InvoiceValidator(Validator validator) { 067 super(); 068 this.validator = validator; 069 this.monetarySummationValidator = new MonetarySummationValidator(new DefaultMessageInterpolator()); 070 } 071 072 /** 073 * Instantiates a new default invoice validator, based on the Bean Validation provider 074 */ 075 public InvoiceValidator() { 076 ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); 077 this.validator = factory.getValidator(); 078 this.monetarySummationValidator = new MonetarySummationValidator(new DefaultMessageInterpolator()); 079 } 080 081 082 /** 083 * Validate the invoice 084 * 085 * @param invoice the invoice 086 * @return the sets the 087 */ 088 public Set<ConstraintViolation<Invoice>> validate(Invoice invoice) { 089 ConformanceLevel conformanceLevel = invoice.getContext().getGuideline().getConformanceLevel(); 090 Class<?>[] validationGroups = resolveIntoValidationGroups(conformanceLevel); 091 Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice, validationGroups); 092 if (monetarySummationValidator != null) { 093 violations.addAll(monetarySummationValidator.validate(invoice, validationGroups)); 094 } 095 return violations; 096 } 097 098 /** 099 * Resolve the given profile into bean validation groups. 100 * 101 * @param conformanceLevel the given profile 102 * @return the class[] list of validation group classes 103 */ 104 public static Class<?>[] resolveIntoValidationGroups(ConformanceLevel conformanceLevel) { 105 switch (conformanceLevel) { 106 case BASIC: 107 return new Class[]{Default.class}; 108 case COMFORT: 109 return new Class[]{Default.class, Comfort.class}; 110 case EXTENDED: 111 return new Class[]{Default.class, Comfort.class, Extended.class}; 112 default: 113 throw new IllegalArgumentException("Provided Profile:" + conformanceLevel + "not covered"); 114 } 115 } 116}