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     */
017    package org.apache.camel.language.tokenizer;
018    
019    import org.apache.camel.Expression;
020    import org.apache.camel.IsSingleton;
021    import org.apache.camel.Predicate;
022    import org.apache.camel.builder.ExpressionBuilder;
023    import org.apache.camel.spi.Language;
024    import org.apache.camel.util.ExpressionToPredicateAdapter;
025    import org.apache.camel.util.ObjectHelper;
026    
027    /**
028     * A language for tokenizer expressions.
029     * <p/>
030     * This tokenizer language can operator in the following modes:
031     * <ul>
032     *     <li>default - using a single tokenizer</li>
033     *     <li>pair - using both start and end tokens</li>
034     *     <li>xml - using both start and end tokens in XML mode, support inheriting namespaces</li>
035     * </ul>
036     * The default mode supports the <tt>headerName</tt> and <tt>regex</tt> options.
037     * Where as the pair mode only supports <tt>token</tt> and <tt>endToken</tt>.
038     * And the <tt>xml</tt> mode supports the <tt>inheritNamespaceTagName</tt> option.
039     */
040    public class TokenizeLanguage implements Language, IsSingleton {
041    
042        private String token;
043        private String endToken;
044        private String inheritNamespaceTagName;
045        private String headerName;
046        private boolean regex;
047        private boolean xml;
048        private boolean includeTokens;
049        private int group;
050    
051        public static Expression tokenize(String token) {
052            return tokenize(token, false);
053        }
054    
055        public static Expression tokenize(String token, boolean regex) {
056            TokenizeLanguage language = new TokenizeLanguage();
057            language.setToken(token);
058            language.setRegex(regex);
059            return language.createExpression(null);
060        }
061    
062        public static Expression tokenize(String headerName, String token) {
063            return tokenize(headerName, token, false);
064        }
065    
066        public static Expression tokenize(String headerName, String token, boolean regex) {
067            TokenizeLanguage language = new TokenizeLanguage();
068            language.setHeaderName(headerName);
069            language.setToken(token);
070            language.setRegex(regex);
071            return language.createExpression(null);
072        }
073    
074        public static Expression tokenizePair(String startToken, String endToken, boolean includeTokens) {
075            TokenizeLanguage language = new TokenizeLanguage();
076            language.setToken(startToken);
077            language.setEndToken(endToken);
078            language.setIncludeTokens(includeTokens);
079            return language.createExpression(null);
080        }
081    
082        public static Expression tokenizeXML(String tagName, String inheritNamespaceTagName) {
083            TokenizeLanguage language = new TokenizeLanguage();
084            language.setToken(tagName);
085            language.setInheritNamespaceTagName(inheritNamespaceTagName);
086            language.setXml(true);
087            language.setIncludeTokens(true);
088            return language.createExpression(null);
089        }
090    
091        public Predicate createPredicate(String expression) {
092            return ExpressionToPredicateAdapter.toPredicate(createExpression(expression));
093        }
094    
095        /**
096         * Creates a tokenize expression.
097         */
098        public Expression createExpression() {
099            ObjectHelper.notNull(token, "token");
100    
101            Expression answer = null;
102            if (isXml()) {
103                answer = ExpressionBuilder.tokenizeXMLExpression(token, inheritNamespaceTagName);
104            } else if (endToken != null) {
105                answer = ExpressionBuilder.tokenizePairExpression(token, endToken, includeTokens);
106            }
107    
108            if (answer == null) {
109                // use the regular tokenizer
110                Expression exp = headerName == null ? ExpressionBuilder.bodyExpression() : ExpressionBuilder.headerExpression(headerName);
111                if (regex) {
112                    answer = ExpressionBuilder.regexTokenizeExpression(exp, token);
113                } else {
114                    answer = ExpressionBuilder.tokenizeExpression(exp, token);
115                }
116            }
117    
118            // if group then wrap answer in group expression
119            if (group > 0) {
120                // only include group token if not xml
121                String groupToken = isXml() ? null : token;
122                answer = ExpressionBuilder.groupIteratorExpression(answer, groupToken, group);
123            }
124    
125            return answer;
126        }
127    
128        public Expression createExpression(String expression) {
129            if (ObjectHelper.isNotEmpty(expression)) {
130                this.token = expression;
131            }
132            return createExpression();
133        }
134    
135        public String getToken() {
136            return token;
137        }
138    
139        public void setToken(String token) {
140            this.token = token;
141        }
142    
143        public String getEndToken() {
144            return endToken;
145        }
146    
147        public void setEndToken(String endToken) {
148            this.endToken = endToken;
149        }
150    
151        public String getHeaderName() {
152            return headerName;
153        }
154    
155        public void setHeaderName(String headerName) {
156            this.headerName = headerName;
157        }
158    
159        public boolean isRegex() {
160            return regex;
161        }
162    
163        public void setRegex(boolean regex) {
164            this.regex = regex;
165        }
166    
167        public String getInheritNamespaceTagName() {
168            return inheritNamespaceTagName;
169        }
170    
171        public void setInheritNamespaceTagName(String inheritNamespaceTagName) {
172            this.inheritNamespaceTagName = inheritNamespaceTagName;
173        }
174    
175        public boolean isXml() {
176            return xml;
177        }
178    
179        public void setXml(boolean xml) {
180            this.xml = xml;
181        }
182    
183        public boolean isIncludeTokens() {
184            return includeTokens;
185        }
186    
187        public void setIncludeTokens(boolean includeTokens) {
188            this.includeTokens = includeTokens;
189        }
190    
191        public int getGroup() {
192            return group;
193        }
194    
195        public void setGroup(int group) {
196            this.group = group;
197        }
198    
199        public boolean isSingleton() {
200            return false;
201        }
202    }