KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > schema2beansdev > DocDefParser


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.modules.schema2beansdev;
21
22 import java.util.*;
23 import java.io.*;
24
25 import org.netbeans.modules.schema2beans.*;
26
27 /**
28  *
29  * This class implement the Document Definition handler in order to build
30  * the internal tree representation of the DD DTD.
31  *
32  */

33 public class DocDefParser extends GeneralParser implements SchemaParser {
34
35     static class MissingEndOfEltException extends RuntimeException JavaDoc {
36         String JavaDoc propName;
37
38         public MissingEndOfEltException(String JavaDoc propName) {
39             this.propName = propName;
40         }
41     }
42     
43     static private final int WORD_NO_CONTEXT = 0;
44     static private final int WORD_CHECK = 1;
45     static private final int WORD_COMMENT = 2;
46     static private final int WORD_ELEMENT1 = 3;
47     static private final int WORD_ELEMENT = 4;
48     static private final int WORD_ATTLIST1 = 5;
49     static private final int WORD_ATTLIST = 6;
50     static private final int WORD_PI = 7;
51     static private final int WORD_ENTITY1 = 10;
52     static private final int WORD_ENTITY = 11;
53     
54     static String JavaDoc errHeader = "DTD parsing failed: "; // NOI18N
55

56     // Buffer used to read the file by chunks
57
private char buffer[] = new char[BUFFER_SIZE];
58     
59     // Current size of the buffer
60
private int bufSize;
61     
62     // Reading offset in the buffer while parsing
63
private int bufScan;
64     
65     protected static int BUFFER_SIZE = 4096;
66     
67     // Handler to callback with the tokens found in the DTD.
68
private DocDefHandler handler;
69     
70     private GenBeans.Config config = null;
71     
72     public DocDefParser() {
73     }
74     
75     public DocDefParser(GenBeans.Config config, DocDefHandler handler) {
76         this.config = config;
77         this.filename = config.getFilename();
78         this.schemaIn = config.getFileIn();
79         this.handler = handler;
80     }
81     
82     protected void startupReader() throws java.io.IOException JavaDoc {;
83         if (schemaIn == null) {
84             EntityParser entityParser = new EntityParser(filename);
85             entityParser.parse();
86             reader=entityParser.getReader();
87         }
88         else
89             reader = new InputStreamReader(schemaIn);
90     }
91     
92     public void setFilename(File filename) {
93         this.filename = filename;
94     }
95     
96     public File getFilename() {
97         return filename;
98     }
99     
100     public void setHandler(DocDefHandler handler) {
101         this.handler = handler;
102     }
103     
104     public DocDefHandler getHandler() {
105         return this.handler;
106     }
107     
108     protected boolean checkBuffer() throws IOException {
109         if (this.bufScan >= this.bufSize) {
110             // Buffer either empty or already parsed - get more from the file
111
this.bufSize = reader.read(this.buffer);
112             if (this.bufSize == -1)
113                 return false;
114             this.bufScan = 0;
115         }
116         return true;
117     }
118     
119     /**
120      * Returns the next character of the parsed file.
121      */

122     protected char getNext() throws IOException {
123         if (this.checkBuffer())
124             return this.buffer[this.bufScan++];
125         else
126             return '\0';
127     }
128     
129     /**
130      * Get the next character without moving the parser offset.
131      */

132     protected char peekNext() throws IOException {
133         if (this.checkBuffer())
134             return this.buffer[this.bufScan];
135         else
136             return '\0';
137     }
138     
139     /**
140      * Return the instance value associated with an element
141      */

142     private static int getInstanceValue(char c) {
143         switch(c) {
144             case '*':
145                 return Common.TYPE_0_N;
146             case '+':
147                 return Common.TYPE_1_N;
148             case '?':
149                 return Common.TYPE_0_1;
150             default:
151                 // We assume this default value if nothing is specified
152
return Common.TYPE_1;
153         }
154     }
155     
156     /**
157      * Find out the type of the current word
158      */

159     private int processWord(StringBuffer JavaDoc curWord, int wordContext) throws SchemaParseException{
160         String JavaDoc word = curWord.toString();
161         int len = word.length();
162         
163         if (len >0) {
164             // We have some word to play with
165
switch (wordContext) {
166                 case WORD_CHECK:
167                     if (word.startsWith("--")) { // NOI18N
168
if (len > 2)
169                             word = curWord.substring(2);
170                         else
171                             word = ""; // NOI18N
172

173                         this.handler.startElement(word, word, Common.COMMENT);
174                         wordContext = WORD_COMMENT;
175                     } else if (word.equals("ELEMENT")) // NOI18N
176
wordContext = WORD_ELEMENT1;
177                     else if (word.equals("ATTLIST")) // NOI18N
178
wordContext = WORD_ATTLIST1;
179                     else if (word.equals("ENTITY")) // NOI18N
180
wordContext = WORD_ENTITY1;
181                     else {
182                         //System.err.println("Error: found an unknown '<!' sequence (" + word + ")"); // NOI18N
183
throw new SchemaParseException("Error: found an unknown '<!' sequence (" + word + ")"); // NOI18N
184
}
185                     break;
186                 case WORD_COMMENT:
187                     this.handler.element(word, word, 0);
188                     break;
189                 case WORD_ELEMENT1:
190                     this.handler.startElement(word, word, Common.ELEMENT);
191                     wordContext = WORD_ELEMENT;
192                     break;
193                 case WORD_ATTLIST1:
194                     this.handler.startElement(word, word, Common.ATTLIST);
195                     wordContext = WORD_ATTLIST;
196                     break;
197                 case WORD_ENTITY1:
198                     wordContext = WORD_ENTITY;
199                     break;
200                 case WORD_ENTITY:
201                     break;
202                 case WORD_ELEMENT:
203                 case WORD_ATTLIST:
204                     // Find out the instance value (*, ? or +)
205
int instance = this.getInstanceValue(word.charAt(len-1));
206                     // Get rid of the extra character
207
if (instance != Common.TYPE_1)
208                         word = curWord.substring(0, len-1);
209                     
210                     try {
211                         this.handler.element(word, word, instance);
212                     } catch(MissingEndOfEltException e) {
213                         if (wordContext == WORD_ATTLIST) {
214                             //
215
// The TreeBuilder is done with the previous
216
// attribute and would expect an end of ATTLIST
217
// declaration.
218
// We might have several attributes declared on the
219
// same ATTLIST declaration.
220
// Let's continue assuming so, the TreeBuilder
221
// checks the attribute semantic and will throw
222
// if this is not the case.
223
//
224
this.handler.startElement(e.propName, e.propName,
225                                     Common.ATTLIST);
226                             this.handler.element(word, word, instance);
227                         }
228                     }
229                     
230                     break;
231                 default:
232             }
233             curWord.delete(0, len);
234         }
235         return wordContext;
236     }
237     
238     /**
239      * Parse the document, calling back the handler
240      */

241     void parse() throws IOException, SchemaParseException {
242         char c;
243         StringBuffer JavaDoc curWord = new StringBuffer JavaDoc();
244         int wordContext = WORD_NO_CONTEXT;
245         int level = 0;
246         
247         while ((c=this.getNext()) != '\0') {
248             switch(c) {
249                 case '<':
250                     // Check if we have <! or <--
251
char c1 = this.getNext();
252                     if (c1 == '!') {
253                         // Check if the next word is reserved
254
if (wordContext != WORD_NO_CONTEXT
255                                 && wordContext != WORD_COMMENT) {
256                             System.err.println("Error: found a '<!' sequence within another '<!' sequence"); // NOI18N
257
throw new SchemaParseException("Warning: found a '<!' sequence within another '<!' sequence"); // NOI18N
258
}
259                         if (wordContext != WORD_COMMENT)
260                             wordContext = WORD_CHECK;
261                     } else if (c1 == '?') {
262                         wordContext = WORD_PI;
263                     } else {
264                         curWord.append(c);
265                         curWord.append(c1);
266                     }
267                     break;
268                 case '>':
269                     // Might be the end of a comment or <!element
270
switch (wordContext) {
271                         case WORD_NO_CONTEXT:
272                             //System.err.println("Error: Found '>' without '<!'");// NOI18N
273
throw new SchemaParseException("Error: Found '>' without '<!'"); // NOI18N
274
case WORD_PI:
275                             String JavaDoc word = curWord.toString();
276                             int len = word.length();
277                             if (word.endsWith("?")) { // NOI18N
278
// Ignore any PI
279
curWord.delete(0, len);
280                                 wordContext = WORD_NO_CONTEXT;
281                             } else
282                                 curWord.append(c);
283                             break;
284                         case WORD_COMMENT:
285                             word = curWord.toString();
286                             len = word.length();
287                             if (word.endsWith("--")) { // NOI18N
288
this.handler.endElement();
289                                 curWord.delete(0, len);
290                                 wordContext = WORD_NO_CONTEXT;
291                             } else
292                                 curWord.append(c);
293                             break;
294                         case WORD_ENTITY:
295                             wordContext = WORD_NO_CONTEXT;
296                             break;
297                         default:
298                             wordContext = this.processWord(curWord,
299                                     wordContext);
300                             this.handler.endElement();
301                             wordContext = WORD_NO_CONTEXT;
302                     }
303                     break;
304                 case '(':
305                     if (wordContext == WORD_ELEMENT
306                             || wordContext == WORD_ATTLIST) {
307                         wordContext = this.processWord(curWord, wordContext);
308                         this.handler.startGroupElements();
309                     } else
310                         curWord.append(c);
311                     break;
312                 case ')':
313                     wordContext = this.processWord(curWord, wordContext);
314                     if (wordContext == WORD_ELEMENT
315                             || wordContext == WORD_ATTLIST) {
316                         int instance = this.getInstanceValue(this.peekNext());
317                         // Get rid of the extra character
318
if (instance != Common.TYPE_1)
319                             this.getNext();
320                         this.handler.endGroupElements(instance);
321                     } else
322                         curWord.append(c);
323                     break;
324                 case '|':
325                     wordContext = this.processWord(curWord, wordContext);
326                     if (wordContext == WORD_ELEMENT
327                             || wordContext == WORD_ATTLIST)
328                         this.handler.character(c);
329                     else
330                         curWord.append(c);
331                     break;
332                 case '\n':
333                 case '\r':
334                 case '\t':
335                 case ' ':
336                 case ',':
337                     wordContext = this.processWord(curWord, wordContext);
338                     break;
339                     //
340
default:
341                     curWord.append(c);
342             }
343         }
344         
345         if (wordContext != WORD_NO_CONTEXT)
346             System.out.println("Warning: unexpected EOF"); // NOI18N
347
}
348     
349     /**
350      * Start the DTD parsing (called by GenBeans class)
351      */

352     public void process() throws java.io.IOException JavaDoc, Schema2BeansException {
353         if (this.filename == null && this.schemaIn == null)
354             throw new IllegalArgumentException JavaDoc(Common.getMessage(
355                     "FilenameNotSpecified_msg", errHeader));
356         
357         if (this.handler == null)
358             throw new IllegalArgumentException JavaDoc(Common.getMessage(
359                     "HandlerNotSpecified_msg", errHeader));
360         
361         if (config.isTraceParse()) {
362             config.messageOut.println("Parsing file " + this.filename.toString() + // NOI18N
363
" with handler " + this.handler.getClass()); // NOI18N
364
}
365         
366         try {
367             startupReader();
368             this.handler.startDocument(config.getDocRoot());
369             this.parse();
370             shutdownReader();
371             this.handler.endDocument();
372         } catch(FileNotFoundException e) {
373             config.messageOut.println("Error: file " + this.filename.toString() + " not found"); // NOI18N
374
throw e;
375         /*
376         } catch (IllegalStateException e) {
377         throw e;
378     } catch (RuntimeException e) {
379             TraceLogger.error(e);
380         throw e;
381          */

382         }
383     }
384 }
385
Popular Tags