Apache CXF如何响应自定义验证错误

时间:2016-02-10 09:14:03

标签: java spring web-services cxf

我有简单的cxf 3.1.1 soap web服务。

@WebService
public interface MyService {
    @WebMethod
    public MyResponse addSomeModel(MyRequest req) throws SoapValidationException;
}

实施:

@Component
@WebService(endpointInterface = "com...MyService", serviceName="Myservice")
public class MyServiceImpl implements MyService {
@Override
    public MyResponse addSomeModel(MyRequest req) throws SoapValidationException {
        Errors errors = new BeanPropertyBindingResult(req, "myReq");
        addCampaignValidator.validate(req, errors);
        if(errors.hasErrors()){
            throw new SoapValidationException("Validation error.", errors);
        }
        //... save it the DB    
        return ...;
    }
}

SoapValidationException是:

@WebFault
@XmlAccessorType( XmlAccessType.PUBLIC_MEMBER )
public class SoapValidationException extends Exception implements Serializable{

    private static final long serialVersionUID = 1L;
    private Errors errors;

    public SoapValidationException(String message, Errors errors, Throwable cause) {
        super(message, cause);
        this.errors = errors;
    }

    public SoapValidationException(String message, Errors errors) {
        super(message);
        this.errors = errors;
    }

    public List<FieldError> getErrors() { // Here I have to use some complex type
        return errors.getFieldErrors();
    }

    public String getTargetObject(){
        return errors.getObjectName();
    }

    public int getErrorCount(){
        return errors.getErrorCount();
    }
}

当我使用像int或String这样的简单类型作为公共getter时,它可以正常对象被序列化并返回为xml。 但是我想使用一些复杂的类型,比如我在Spring验证中使用FieldError的示例。

我需要做什么,所以我可以使用复杂类型作为SoapValidationException的字段?

不需要使用FieldError,我也可以使用自己的包装并绘制地图。

1 个答案:

答案 0 :(得分:0)

由于CXF使用JAXB,因此自定义类型必须是有效的jaxb元素。

我最终得到了:

@WebFault
@XmlAccessorType( XmlAccessType.PUBLIC_MEMBER )
public class SoapValidationException extends Exception implements Serializable{

    private static final long serialVersionUID = 1L;
    private Errors errors;

    public SoapValidationException(String message, Errors errors, Throwable cause) {
        super(message, cause);
        this.errors = errors;
    }

    public SoapValidationException(String message, Errors errors) {
        super(message);
        this.errors = errors;
    }

    public String getErrors() {
        return errors.toString();
    }

    public List<ValidationExceptionDetails> getDetails(){
        List<ValidationExceptionDetails> details = new ArrayList<ValidationExceptionDetails>();
        for(FieldError fe : errors.getFieldErrors()) {
            details.add(new ValidationExceptionDetails(fe.getCode(), fe.getDefaultMessage(), fe.getRejectedValue().toString()));
        }
        return details;
    }
}

ValidationExceptionDetails的位置是:

@XmlRootElement
public class ValidationExceptionDetails {
    private String code;
    private String message;
    private String rejectedValue;

    public ValidationExceptionDetails(String code, String message, String rejectedValue) {
        this.code = code;
        this.message = message;
        this.rejectedValue = rejectedValue;
    }

    public ValidationExceptionDetails() {
    }

    public String getCode() {
        return code;
    }
    @XmlElement
    public void setCode(String code) {
        this.code = code;
    }
    public String getMessage() {
        return message;
    }
    @XmlElement
    public void setMessage(String message) {
        this.message = message;
    }
    public String getRejectedValue() {
        return rejectedValue;
    }
    @XmlElement
    public void setRejectedValue(String rejectedValue) {
        this.rejectedValue = rejectedValue;
    }


}