KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > cocoon > components > validation > jaxp > JaxpSchemaParser


1 /*
2  * Copyright 1999-2005 The Apache Software Foundation.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.apache.cocoon.components.validation.jaxp;
17
18 import java.io.IOException JavaDoc;
19 import java.util.HashSet JavaDoc;
20 import java.util.Set JavaDoc;
21
22 import javax.xml.XMLConstants JavaDoc;
23 import javax.xml.transform.sax.SAXSource JavaDoc;
24 import javax.xml.validation.SchemaFactory JavaDoc;
25
26 import org.apache.avalon.framework.configuration.Configurable;
27 import org.apache.avalon.framework.configuration.Configuration;
28 import org.apache.avalon.framework.configuration.ConfigurationException;
29 import org.apache.avalon.framework.thread.ThreadSafe;
30 import org.apache.cocoon.components.validation.Schema;
31 import org.apache.cocoon.components.validation.SchemaParser;
32 import org.apache.cocoon.components.validation.Validator;
33 import org.apache.cocoon.components.validation.impl.AbstractSchemaParser;
34 import org.apache.cocoon.components.validation.impl.DraconianErrorHandler;
35 import org.apache.excalibur.source.Source;
36 import org.xml.sax.ErrorHandler JavaDoc;
37 import org.xml.sax.SAXException JavaDoc;
38
39 /**
40  * <p>An implementation of the {@link SchemaParser} interface wrapping JAXP
41  * {@link SchemaFactory} instances.</p>
42  *
43  * @author <a HREF="mailto:pier@betaversion.org">Pier Fumagalli</a>
44  */

45 public class JaxpSchemaParser extends AbstractSchemaParser
46 implements Configurable, ThreadSafe {
47
48     /** <p>The class name of the {@link SchemaFactory} to use.</p> */
49     private String JavaDoc className = null;
50     /** <p>The list of grammars supported by this instance.</p> */
51     private String JavaDoc[] grammars = null;
52
53     /**
54      * <p>Create a new {@link JaxpSchemaParser} instance.</p>
55      */

56     public JaxpSchemaParser() {
57         super();
58     }
59
60     /**
61      * <p>Configure this instance.</p>
62      *
63      * <p>The {@link JaxpSchemaParser} requires at least one configuration element:
64      * <code>&lt;factory-class&gt;<i>class name</i>&lt;/factory-class&gt;</code>.
65      * This specifies the JAXP {@link SchemaFactory} class to be used by this
66      * instance.</p>
67      *
68      * <p>Grammars will be automatically detected if the {@link SchemaFactory}
69      * supports one of the {@link XMLConstants#RELAXNG_NS_URI RELAX-NG} grammar,
70      * {@link XMLConstants#W3C_XML_SCHEMA_NS_URI XML-Schema} grammar, or the
71      * {@link XMLConstants#XML_DTD_NS_URI XML-DTD} grammar.</p>
72      *
73      * <p>If the factory is known to support different grammars, the default
74      * detection can be overridden specifying in the configuration something similar
75      * to the following:</p>
76      *
77      * <pre>
78      * &lt;grammars&gt;
79      * &lt;grammar&gt;... a first grammar identifier ...&lt;/grammar&gt;
80      * &lt;grammar&gt;... another grammar identifier ...&lt;/grammar&gt;
81      * &lt;/grammars&gt;
82      * </pre>
83      */

84     public void configure(Configuration conf)
85     throws ConfigurationException {
86         this.className = conf.getChild("factory-class").getValue();
87         final SchemaFactory JavaDoc fact;
88         try {
89             fact = (SchemaFactory JavaDoc) Class.forName(this.className).newInstance();
90         } catch (Exception JavaDoc exception) {
91             String JavaDoc message = "Unable to instantiate factory " + this.className;
92             throw new ConfigurationException(message, conf, exception);
93         }
94
95         /* Detect languages or use the supplied ones */
96         Configuration languages[] = conf.getChild("grammars").getChildren("grammar");
97         Set JavaDoc grammars = new HashSet JavaDoc();
98         if (languages.length > 0) {
99
100             /* If the configuration specified (formally) a list of grammars use it */
101             for (int x = 0; x < languages.length; x++) {
102                 String JavaDoc language = languages[x].getValue();
103                 if (fact.isSchemaLanguageSupported(language)) {
104                     grammars.add(language);
105                     continue;
106                 }
107                 /* If the configured language is not supported throw an exception */
108                 String JavaDoc message = "JAXP SchemaFactory \"" + this.className + "\" " +
109                                  "does not support configured grammar " + language;
110                 throw new ConfigurationException(message, languages[x]);
111             }
112         } else {
113
114             /* Attempt to detect the languages directly using the JAXP factory */
115             if (fact.isSchemaLanguageSupported(XMLConstants.W3C_XML_SCHEMA_NS_URI)) {
116                 grammars.add(Validator.GRAMMAR_XML_SCHEMA);
117             }
118             if (fact.isSchemaLanguageSupported(XMLConstants.RELAXNG_NS_URI)) {
119                 grammars.add(Validator.GRAMMAR_RELAX_NG);
120             }
121             if (fact.isSchemaLanguageSupported(XMLConstants.XML_DTD_NS_URI)) {
122                 grammars.add(Validator.GRAMMAR_XML_DTD);
123             }
124         }
125         
126         /* Store our grammars */
127         this.grammars = (String JavaDoc[]) grammars.toArray(new String JavaDoc[grammars.size()]);
128     }
129
130     /**
131      * <p>Parse the specified {@link Source} and return a new {@link Schema}.</p>
132      *
133      * <p>The returned {@link Schema} must be able to validate multiple documents
134      * via multiple invocations of {@link Schema#createValidator(ErrorHandler)}.</p>
135      *
136      * @param source the {@link Source} associated with the {@link Schema} to return.
137      * @return a <b>non-null</b> {@link Schema} instance.
138      * @throws SAXException if a grammar error occurred parsing the schema.
139      * @throws IOException if an I/O error occurred parsing the schema.
140      * @throws IllegalArgumentException if the specified grammar type is not one
141      * of the grammar types returned by the
142      * {@link #getSupportedGrammars()} method.
143      */

144     public Schema parseSchema(Source JavaDoc source, String JavaDoc grammar)
145     throws SAXException JavaDoc, IOException JavaDoc {
146         final SchemaFactory JavaDoc factory;
147         try {
148             factory = (SchemaFactory JavaDoc) Class.forName(this.className).newInstance();
149         } catch (Exception JavaDoc exception) {
150             String JavaDoc message = "Unable to instantiate factory " + this.className;
151             throw new SAXException JavaDoc(message, exception);
152         }
153         
154         JaxpResolver r = new JaxpResolver(this.sourceResolver, this.entityResolver);
155         SAXSource JavaDoc s = new SAXSource JavaDoc(r.resolveSource(source));
156         factory.setErrorHandler(DraconianErrorHandler.INSTANCE);
157         factory.setResourceResolver(r);
158         
159         return new JaxpSchema(factory.newSchema(s), r.close());
160     }
161
162     public String JavaDoc[] getSupportedGrammars() {
163         return this.grammars;
164     }
165 }
166
Popular Tags