1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.ldap.server.tools.schema;
18
19
20 import org.apache.ldap.common.util.ExceptionUtils;
21
22 import java.util.Map;
23 import java.text.ParseException;
24 import java.io.*;
25
26 import antlr.RecognitionException;
27 import antlr.TokenStreamException;
28
29
30 /***
31 * A reusable wrapper for antlr generated OpenLDAP schema parsers.
32 *
33 * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
34 * @version $Rev: 264732 $
35 */
36 public class OpenLdapSchemaParser
37 {
38 /*** the monitor to use for this parser */
39 private ParserMonitor monitor = new ParserMonitorAdapter();
40 /*** The antlr generated parser */
41 private antlrOpenLdapSchemaParser parser = null;
42 /*** A pipe into the parser */
43 private PipedOutputStream parserIn = null;
44
45
46 /***
47 * Creates a reusable instance of an OpenLdapSchemaParser.
48 *
49 * @throws IOException if the pipe cannot be formed
50 */
51 public OpenLdapSchemaParser() throws IOException
52 {
53 init();
54 }
55
56
57 /***
58 * Initializes a parser and its plumbing.
59 *
60 * @throws IOException if a pipe cannot be formed.
61 */
62 public void init() throws IOException
63 {
64 parserIn = new PipedOutputStream();
65 PipedInputStream in = new PipedInputStream();
66 parserIn.connect( in );
67 antlrOpenLdapSchemaLexer lexer = new antlrOpenLdapSchemaLexer( in );
68 parser = new antlrOpenLdapSchemaParser( lexer );
69 }
70
71
72 public synchronized void clear()
73 {
74 parser.clear();
75 }
76
77
78 public Map getAttributeTypes()
79 {
80 return parser.getAttributeTypes();
81 }
82
83
84 public Map getObjectClassTypes()
85 {
86 return parser.getObjectClasses();
87 }
88
89
90 /***
91 * Thread safe method parses an OpenLDAP schemaObject element/object.
92 *
93 * @param schemaObject the String image of a complete schema object
94 */
95 public synchronized void parse( String schemaObject ) throws IOException, ParseException
96 {
97 if ( schemaObject == null || schemaObject.trim().equals( "" ) )
98 {
99 throw new ParseException( "The schemaObject is either null or is "
100 + "the empty String!", 0 );
101 }
102
103 this.schemaIn = new ByteArrayInputStream( schemaObject.getBytes() );
104
105 if ( producerThread == null )
106 {
107 producerThread = new Thread( new DataProducer() );
108 }
109
110 producerThread.start();
111 invokeParser( schemaObject );
112 }
113
114
115 private void invokeParser( String subject ) throws IOException, ParseException
116 {
117 try
118 {
119 monitor.startedParse( "starting parse on:\n" + subject );
120 parser.parseSchema();
121 monitor.finishedParse( "Done parsing!" );
122 }
123 catch ( RecognitionException e )
124 {
125 String msg = "Parser failure on:\n\t" + subject ;
126 msg += "\nAntlr exception trace:\n" + ExceptionUtils.getFullStackTrace( e );
127 init();
128 throw new ParseException( msg, e.getColumn() );
129 }
130 catch ( TokenStreamException e2 )
131 {
132 String msg = "Parser failure on:\n\t" + subject ;
133 msg += "\nAntlr exception trace:\n" + ExceptionUtils.getFullStackTrace( e2 );
134 init();
135 throw new ParseException( msg, 0 );
136 }
137 }
138
139
140 byte[] buf = new byte[128];
141 private InputStream schemaIn;
142 private Thread producerThread;
143
144 /***
145 * Thread safe method parses a stream of OpenLDAP schemaObject elements/objects.
146 *
147 * @param schemaIn a stream of schema objects
148 */
149 public synchronized void parse( InputStream schemaIn ) throws IOException, ParseException
150 {
151 this.schemaIn = schemaIn;
152
153 if ( producerThread == null )
154 {
155 producerThread = new Thread( new DataProducer() );
156 }
157
158 producerThread.start();
159 invokeParser( "schema input stream ==> " + schemaIn.toString() );
160 }
161
162
163 /***
164 * Thread safe method parses a file of OpenLDAP schemaObject elements/objects.
165 *
166 * @param schemaFile a file of schema objects
167 */
168 public synchronized void parse( File schemaFile ) throws IOException, ParseException
169 {
170 this.schemaIn = new FileInputStream( schemaFile );
171
172 if ( producerThread == null )
173 {
174 producerThread = new Thread( new DataProducer() );
175 }
176
177 producerThread.start();
178 invokeParser( "schema file ==> " + schemaFile.getAbsolutePath() );
179 }
180
181
182 public void setParserMonitor( ParserMonitor monitor )
183 {
184 this.monitor = monitor ;
185 this.parser.setParserMonitor( monitor );
186 }
187
188
189 class DataProducer implements Runnable
190 {
191 public void run()
192 {
193 int count = -1;
194
195 try
196 {
197 while ( ( count = schemaIn.read( buf ) ) != -1 )
198 {
199 parserIn.write( buf, 0, count );
200 parserIn.flush();
201 }
202
203
204 parserIn.write( "END ".getBytes() );
205 }
206 catch ( IOException e )
207 {
208 e.printStackTrace();
209 }
210 }
211 }
212 }