001/**
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.camel.builder;
018
019import org.apache.camel.CamelContext;
020import org.apache.camel.Expression;
021import org.apache.camel.Predicate;
022import org.apache.camel.model.language.ExpressionDefinition;
023import org.apache.camel.model.validator.CustomValidatorDefinition;
024import org.apache.camel.model.validator.EndpointValidatorDefinition;
025import org.apache.camel.model.validator.PredicateValidatorDefinition;
026import org.apache.camel.model.validator.ValidatorDefinition;
027import org.apache.camel.spi.AsPredicate;
028import org.apache.camel.spi.DataType;
029import org.apache.camel.spi.Validator;
030
031/**
032 * A <a href="http://camel.apache.org/dsl.html">Java DSL</a> which is
033 * used to build a {@link org.apache.camel.spi.Validator} and register into {@link org.apache.camel.CamelContext}.
034 * It requires a 'type' to be specified by type() method.
035 * And then you can choose a type of validator by withUri(), withPredicate(), withJava() or withBean() method.
036 */
037public class ValidatorBuilder {
038
039    private String type;
040    private String uri;
041    private ExpressionDefinition expression;
042    private Class<? extends Validator> clazz;
043    private String beanRef;
044
045    /**
046     * Set the data type name.
047     * If you specify 'xml:XYZ', the validator will be picked up if source type is
048     * 'xml:XYZ'. If you specify just 'xml', the validator matches with all of
049     * 'xml' source type like 'xml:ABC' or 'xml:DEF'.
050     *
051     * @param type 'from' data type name
052     */
053    public ValidatorBuilder type(String type) {
054        this.type = type;
055        return this;
056    }
057
058    /**
059     * Set the data type using Java class.
060     *
061     * @param type Java class represents data type
062     */
063    public ValidatorBuilder type(Class<?> type) {
064        this.type = new DataType(type).toString();
065        return this;
066    }
067
068    /**
069     * Set the URI to be used for the endpoint {@link Validator}.
070     * @see EndpointValidatorDefinition, ProcessorValidator
071     * 
072     * @param uri endpoint URI
073     */
074    public ValidatorBuilder withUri(String uri) {
075        resetType();
076        this.uri = uri;
077        return this;
078    }
079
080    /**
081     * Set the {@link Expression} to be used for the predicate {@link Validator}.
082     * @see PredicateValidatorDefinition, ProcessorValidator
083     * 
084     * @param expression validation expression
085     */
086    public ValidatorBuilder withExpression(@AsPredicate Expression expression) {
087        resetType();
088        this.expression = new ExpressionDefinition(expression);
089        return this;
090    }
091
092    /**
093     * Set the {@link Predicate} to be used for the predicate {@link Validator}.
094     * @see PredicateValidatorDefinition, ProcessorValidator
095     * 
096     * @param predicate validation predicate
097     */
098    public ValidatorBuilder withExpression(@AsPredicate Predicate predicate) {
099        resetType();
100        this.expression = new ExpressionDefinition(predicate);
101        return this;
102    }
103
104    /**
105     * Set the Java {@code Class} represents a custom {@code Validator} implementation class.
106     * @see CustomValidatorDefinition
107     * 
108     * @param clazz {@code Class} object represents custom validator implementation
109     */
110    public ValidatorBuilder withJava(Class<? extends Validator> clazz) {
111        resetType();
112        this.clazz = clazz;
113        return this;
114    }
115
116    /**
117     * Set the Java Bean name to be used for custom {@code Validator}.
118     * @see CustomValidatorDefinition
119     * 
120     * @param ref bean name for the custom {@code Validator}
121     */
122    public ValidatorBuilder withBean(String ref) {
123        resetType();
124        this.beanRef = ref;
125        return this;
126    }
127
128    private void resetType() {
129        this.uri = null;
130        this.expression = null;
131        this.clazz = null;
132        this.beanRef = null;
133    }
134
135    /**
136     * Configures a new Validator according to the configurations built on this builder
137     * and register it into the given {@code CamelContext}.
138     * 
139     * @param camelContext the given CamelContext
140     */
141    public void configure(CamelContext camelContext) {
142        ValidatorDefinition validator;
143        if (uri != null) {
144            EndpointValidatorDefinition etd = new EndpointValidatorDefinition();
145            etd.setUri(uri);
146            validator = etd;
147        } else if (expression != null) {
148            PredicateValidatorDefinition dtd = new PredicateValidatorDefinition();
149            dtd.setExpression(expression);
150            validator = dtd;
151        } else if (clazz != null) {
152            CustomValidatorDefinition ctd = new CustomValidatorDefinition();
153            ctd.setClassName(clazz.getName());
154            validator = ctd;
155        } else if (beanRef != null) {
156            CustomValidatorDefinition ctd = new CustomValidatorDefinition();
157            ctd.setRef(beanRef);
158            validator = ctd;
159        } else {
160            throw new IllegalArgumentException("No Validator type was specified");
161        }
162        
163        validator.setType(type);
164        camelContext.getValidators().add(validator);
165    }
166}