KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > hp > hpl > jena > rdf > arp > JenaReader


1 /*
2  (c) Copyright 2001, 2002, 2003, 2004, 2005 Hewlett-Packard Development Company, LP
3  [See end of file]
4  */

5
6 package com.hp.hpl.jena.rdf.arp;
7
8 import com.hp.hpl.jena.rdf.model.*;
9 import com.hp.hpl.jena.rdf.model.impl.*;
10 import com.hp.hpl.jena.graph.*;
11 import com.hp.hpl.jena.shared.*;
12 import com.hp.hpl.jena.datatypes.*;
13
14 import java.io.*;
15 import java.net.*;
16
17 import org.xml.sax.InputSource JavaDoc;
18 import org.xml.sax.SAXNotSupportedException JavaDoc;
19 import org.xml.sax.SAXException JavaDoc;
20 import org.xml.sax.SAXNotRecognizedException JavaDoc;
21
22 /**
23  * Interface between Jena and ARP.
24  *
25  * @author jjc
26  */

27 public class JenaReader implements RDFReader, ARPErrorNumbers {
28
29     static private final int BULK_UPDATE_SIZE = 1000;
30
31     /**
32      * Sets the reader for the languages RDF/XML and RDF/XML-ABBREV to be
33      * JenaReader.
34      *
35      * @param m
36      * The Model on which to set the reader properties.
37      */

38     static public void useMe(Model m) {
39         m.setReaderClassName("RDF/XML", JenaReader.class.getName());
40         m.setReaderClassName("RDF/XML-ABBREV", JenaReader.class.getName());
41     }
42
43     static private final String JavaDoc saxFeaturesURL = "http://xml.org/sax/features/";
44
45     static private final String JavaDoc saxPropertiesURL = "http://xml.org/sax/properties/";
46
47     static private final String JavaDoc apacheFeaturesURL = "http://apache.org/xml/features/";
48
49     static private final String JavaDoc apachePropertiesURL = "http://apache.org/xml/properties/";
50
51     static final String JavaDoc arpPropertiesURL = "http://jena.hpl.hp.com/arp/properties/";
52
53     static final int arpPropertiesURLLength = arpPropertiesURL.length();
54
55     /**
56      * Creates new JenaReader
57      */

58     public JenaReader() {
59         arpf = SingleThreadedParser.create();
60     }
61
62     final private SingleThreadedParser arpf;
63
64     private Model model;
65
66     public void read(Model model, String JavaDoc url) throws JenaException {
67         try {
68             URLConnection conn = new URL(url).openConnection();
69             String JavaDoc encoding = conn.getContentEncoding();
70             if (encoding == null)
71                 read(model, conn.getInputStream(), url);
72             else
73                 read(model, new InputStreamReader(conn.getInputStream(),
74                         encoding), url);
75         } catch (FileNotFoundException e) {
76             throw new DoesNotExistException(url);
77         } catch (IOException e) {
78             throw new JenaException(e);
79         }
80     }
81
82     /**
83      * Converts an ARP literal into a Jena Literal.
84      *
85      * @param lit
86      * The ARP literal.
87      * @return The Jena Literal.
88      * @deprecated Should never have been public.
89      */

90     static public Literal translate(ALiteral lit) {
91         return new LiteralImpl(lit.toString(), lit.getLang(), lit
92                 .isWellFormedXML(), null);
93     }
94
95     static Node convert(ALiteral lit) {
96         String JavaDoc dtURI = lit.getDatatypeURI();
97         if (dtURI == null)
98             return Node.createLiteral(lit.toString(), lit.getLang(), false);
99         else {
100             if (lit.isWellFormedXML()) {
101                 return Node.createLiteral(lit.toString(), null, true);
102             } else {
103                 RDFDatatype dt = TypeMapper.getInstance().getSafeTypeByName(
104                         dtURI);
105
106                 return Node.createLiteral(lit.toString(), null, dt);
107             }
108         }
109     }
110
111     static Node convert(AResource r) {
112         if (r.isAnonymous()) {
113             String JavaDoc id = r.getAnonymousID();
114             Node rr = (Node) r.getUserData();
115             if (rr == null) {
116                 rr = Node.createAnon();
117                 r.setUserData(rr);
118             }
119             return rr;
120         } else {
121             return Node.createURI(r.getURI());
122         }
123     }
124
125     static Triple convert(AResource s, AResource p, AResource o) {
126         return Triple.create(convert(s), convert(p), convert(o));
127     }
128
129     static Triple convert(AResource s, AResource p, ALiteral o) {
130         return Triple.create(convert(s), convert(p), convert(o));
131     }
132
133     /**
134      * Converts an ARP resource into a Jena property.
135      *
136      * @param r
137      * The ARP resource.
138      * @throws JenaException
139      * If r is anonymous, or similarly ill-formed.
140      * @return The Jena property.
141      * @deprecated Should never have been public.
142      */

143     static public Property translatePred(AResource r) throws JenaException {
144         return new PropertyImpl(r.getURI());
145     }
146
147     /**
148      * Reads from reader, using base URI xmlbase, adding triples to model. If
149      * xmlbase is "" then relative URIs may be added to model.
150      *
151      * @param model
152      * A model to add triples to.
153      * @param reader
154      * The RDF/XML document.
155      * @param xmlBase
156      * The base URI of the document or "".
157      */

158     private void read(Model m, InputSource JavaDoc inputS, String JavaDoc xmlBase)
159             throws JenaException {
160         model = m;
161         if (xmlBase != null && !xmlBase.equals("")) {
162             try {
163                 URI uri = new URI(xmlBase);
164             } catch (MalformedURIException e) {
165                 errorHandler.error(e);
166             }
167         }
168         /*
169          * arpf.getHandlers().setNamespaceHandler(new NamespaceHandler() {
170          *
171          *
172          * });
173          */

174         read(model.getGraph(), inputS, xmlBase, model);
175     }
176
177     private JenaHandler handler;
178
179     synchronized private void read(final Graph g, InputSource JavaDoc inputS,
180             String JavaDoc xmlBase, Model m) {
181
182         try {
183             g.getEventManager().notifyEvent(g, GraphEvents.startRead);
184             inputS.setSystemId(xmlBase);
185             handler = new JenaHandler(g, m, errorHandler);
186             handler.useWith(arpf.getHandlers());
187             arpf.parse(inputS, xmlBase);
188             handler.bulkUpdate();
189         } catch (IOException e) {
190             throw new WrappedIOException(e);
191         } catch (SAXException JavaDoc e) {
192             throw new JenaException(e);
193         } finally {
194             g.getEventManager().notifyEvent(g, GraphEvents.finishRead);
195             handler = null;
196         }
197     }
198
199     /**
200      * Reads from reader, using base URI xmlbase, adding triples to model. If
201      * xmlbase is "" then relative URIs may be added to model.
202      *
203      * @param model
204      * A model to add triples to.
205      * @param reader
206      * The RDF/XML document.
207      * @param xmlBase
208      * The base URI of the document or "".
209      */

210     public void read(final Model model, Reader reader, String JavaDoc xmlBase)
211             throws JenaException {
212         read(model, new InputSource JavaDoc(reader), xmlBase);
213     }
214
215     /**
216      * Reads from reader, using base URI xmlbase, adding triples to graph. If
217      * xmlbase is "" then relative URIs may be added to graph.
218      *
219      * @param g
220      * A graph to add triples to.
221      * @param reader
222      * The RDF/XML document.
223      * @param xmlBase
224      * The base URI of the document or "".
225      */

226     public void read(Graph g, Reader reader, String JavaDoc xmlBase)
227             throws JenaException {
228         read(g, new InputSource JavaDoc(reader), xmlBase, null);
229     }
230
231     /**
232      * Reads from inputStream, using base URI xmlbase, adding triples to model.
233      * If xmlbase is "" then relative URIs may be added to model.
234      *
235      * @param model
236      * A model to add triples to.
237      * @param in
238      * The RDF/XML document stream.
239      * @param xmlBase
240      * The base URI of the document or "".
241      */

242     public void read(final Model model, InputStream in, String JavaDoc xmlBase)
243             throws JenaException {
244         read(model, new InputSource JavaDoc(in), xmlBase);
245     }
246
247     /**
248      * Reads from inputStream, using base URI xmlbase, adding triples to graph.
249      * If xmlbase is "" then relative URIs may be added to graph.
250      *
251      * @param g
252      * A graph to add triples to.
253      * @param in
254      * The RDF/XML document stream.
255      * @param xmlBase
256      * The base URI of the document or "".
257      */

258     public void read(Graph g, InputStream in, String JavaDoc xmlBase) {
259         read(g, new InputSource JavaDoc(in), xmlBase, null);
260     }
261
262     private RDFErrorHandler errorHandler = new RDFDefaultErrorHandler();
263
264     /**
265      * Change the error handler.
266      * <p>
267      * Note that errors of class {@link ParseException}can be promoted using
268      * the {@link ParseException#promote}method. See ARP documentation for
269      * {@link org.xml.sax.ErrorHandler}for the details of error promotion.
270      *
271      * @param errHandler
272      * The new error handler.
273      * @return The old error handler.
274      */

275     public RDFErrorHandler setErrorHandler(RDFErrorHandler errHandler) {
276         RDFErrorHandler old = this.errorHandler;
277         this.errorHandler = errHandler;
278         JenaHandler h = handler;
279         if (h != null) {
280             h.setErrorHandler(errHandler);
281         }
282         return old;
283     }
284
285     /**
286      *
287      * Change a property of the RDF or XML parser.
288      * <p>
289      * This method is untested.
290      * <p>
291      * I do not believe that many of the XML features or properties are in fact
292      * useful for ARP users. The ARP properties allow fine-grained control over
293      * error reporting.
294      * <p>
295      * This interface can be used to set and get:
296      * <dl>
297      * <dt>SAX2 features</dt>
298      * <dd>See <a HREF="http://xml.apache.org/xerces-j/features.html">Xerces
299      * features </a>. Value should be given as a String "true" or "false" or a
300      * Boolean.</dd>
301      * <dt>SAX2 properties</dt>
302      * <dd>See <a HREF="http://xml.apache.org/xerces-j/properties.html">Xerces
303      * properties </a>.</dd>
304      * <dt>Xerces features</dt>
305      * <dd>See <a HREF="http://xml.apache.org/xerces-j/features.html">Xerces
306      * features </a>. Value should be given as a String "true" or "false" or a
307      * Boolean.</dd>
308      * <dt>Xerces properties</dt>
309      * <dd>See <a HREF="http://xml.apache.org/xerces-j/properties.html">Xerces
310      * properties </a>.</dd>
311      * <dt>ARP properties</dt>
312      * <dd>These are referred to either by their property name, (see below) or
313      * by an absolute URL of the form
314      * <code>http://jena.hpl.hp.com/arp/properties/&lt;PropertyName&gt;</code>.
315      * The value should be a String, an Integer or a Boolean depending on the
316      * property. <br>
317      * ARP property names and string values are case insensitive. <br>
318      * <TABLE BORDER="1" CELLPADDING="3" CELLSPACING="0">
319      * <TR BGCOLOR="#CCCCFF" CLASS="TableHeadingColor">
320      * <TD COLSPAN=4><FONT SIZE="+2"> <B>ARP Properties </B> </FONT></TD>
321      * </TR>
322      * <tr BGCOLOR="#EEEEFF" CLASS="TableSubHeadingColor">
323      * <th>Property Name</th>
324      * <th>Description</th>
325      * <th>Value class</th>
326      * <th>Legal Values</th>
327      * </tr>
328      * <tr BGCOLOR="white" CLASS="TableRowColor">
329      * <td><CODE>error-mode</CODE></td>
330      * <td>{@link ARP#setDefaultErrorMode}<br>
331      * {@link ARP#setLaxErrorMode}<br>
332      * {@link ARP#setStrictErrorMode}<br>
333      * {@link ARP#setStrictErrorMode(int)}<br>
334      * </td>
335      * <td>String</td>
336      * <td><CODE>default</CODE><br>
337      * <CODE>lax</CODE><br>
338      * <CODE>strict</CODE><br>
339      * <CODE>strict-ignore</CODE><br>
340      * <CODE>strict-warning</CODE><br>
341      * <CODE>strict-error</CODE><br>
342      * <CODE>strict-fatal</CODE><br>
343      * </td>
344      * </tr>
345      * <tr BGCOLOR="white" CLASS="TableRowColor">
346      * <td><CODE>embedding</CODE></td>
347      * <td>{@link ARP#setEmbedding}</td>
348      * <td>String or Boolean</td>
349      * <td><CODE>true</CODE> or <CODE>false</CODE></td>
350      * </tr>
351      * <tr BGCOLOR="white" CLASS="TableRowColor">
352      * <td><code>ERR_&lt;XXX&gt;</code><br>
353      * <code>WARN_&lt;XXX&gt;</code><br>
354      * <code>IGN_&lt;XXX&gt;</code></td>
355      * <td>{@link ARPErrorNumbers}<br>
356      * Any of the error condition numbers listed. <br>
357      * {@link ARP#setErrorMode(int, int)}</td>
358      * <td>String or Integer</td>
359      * <td>{@link ARPErrorNumbers#EM_IGNORE EM_IGNORE}<br>
360      * {@link ARPErrorNumbers#EM_WARNING EM_WARNING}<br>
361      * {@link ARPErrorNumbers#EM_ERROR EM_ERROR}<br>
362      * {@link ARPErrorNumbers#EM_FATAL EM_FATAL}<br>
363      * </td>
364      * </tr>
365      * </table></dd>
366      * </dl>
367      *
368      * @param str
369      * The property to set.
370      * @param value
371      * The new value; values of class String will be converted into
372      * appropriate classes. Values of class Boolean or Integer will
373      * be used for appropriate properties.
374      * @throws JenaException
375      * For bad values.
376      * @return The old value, or null if none, or old value is inaccesible.
377      */

378     public Object JavaDoc setProperty(String JavaDoc str, Object JavaDoc value) throws JenaException {
379         Object JavaDoc obj = value;
380         if (str.startsWith("http:")) {
381             if (str.startsWith(arpPropertiesURL)) {
382                 return setArpProperty(str.substring(arpPropertiesURLLength),
383                         obj);
384             }
385             if (str.startsWith(saxPropertiesURL)
386                     || str.startsWith(apachePropertiesURL)) {
387                 Object JavaDoc old;
388                 try {
389                     old = arpf.getSAXParser().getProperty(str);
390                 } catch (SAXNotSupportedException JavaDoc ns) {
391                     old = null;
392                 } catch (SAXNotRecognizedException JavaDoc nr) {
393                     errorHandler.error(new UnknownPropertyException(str));
394                     return null;
395                 }
396                 try {
397                     arpf.getSAXParser().setProperty(str, obj);
398                 } catch (SAXNotSupportedException JavaDoc ns) {
399                     errorHandler.error(new JenaException(ns));
400                 } catch (SAXNotRecognizedException JavaDoc nr) {
401                     errorHandler.error(new UnknownPropertyException(str));
402                     return null;
403                 }
404                 return old;
405             }
406
407             if (str.startsWith(saxFeaturesURL)
408                     || str.startsWith(apacheFeaturesURL)) {
409                 Boolean JavaDoc old;
410                 try {
411                     old = new Boolean JavaDoc(arpf.getSAXParser().getFeature(str));
412                 } catch (SAXNotSupportedException JavaDoc ns) {
413                     old = null;
414                 } catch (SAXNotRecognizedException JavaDoc nr) {
415                     errorHandler.error(new UnknownPropertyException(str));
416                     return null;
417                 }
418                 try {
419                     arpf.getSAXParser().setFeature(str,
420                             ((Boolean JavaDoc) obj).booleanValue());
421                 } catch (SAXNotSupportedException JavaDoc ns) {
422                     errorHandler.error(new JenaException(ns));
423                 } catch (SAXNotRecognizedException JavaDoc nr) {
424                     errorHandler.error(new UnknownPropertyException(str));
425                     return null;
426                 } catch (ClassCastException JavaDoc cc) {
427                     errorHandler.error(new JenaException(
428                             new SAXNotSupportedException JavaDoc("Feature: '" + str
429                                     + "' can only have a boolean value.")));
430                 }
431                 return old;
432             }
433         }
434         return setArpProperty(str, obj);
435     }
436
437     static public int errorCode(String JavaDoc upper) {
438         Class JavaDoc c = ARPErrorNumbers.class;
439         try {
440             java.lang.reflect.Field JavaDoc fld = c.getField(upper);
441             return fld.getInt(null);
442         } catch (Exception JavaDoc e) {
443             return -1;
444         }
445     }
446
447     static public String JavaDoc errorCodeName(int errNo) {
448         Class JavaDoc c = ARPErrorNumbers.class;
449         java.lang.reflect.Field JavaDoc flds[] = c.getDeclaredFields();
450         for (int i = 0; i < flds.length; i++) {
451             try {
452                 if (flds[i].getInt(null) == errNo)
453                     return flds[i].getName();
454             } catch (Exception JavaDoc e) {
455             }
456         }
457         return null;
458     }
459
460     private Object JavaDoc setArpProperty( String JavaDoc str, Object JavaDoc v) {
461         return setArpProperty(arpf.getOptions(),str,v,errorHandler);
462     }
463     /**
464      * Supported proprties: error-mode (String) default, lax, strict,
465      * strict-ignore, strict-warning, strict-error, strict-fatal embedding
466      * (String/Boolean) true, false ERR_* (String/Integer) em_warning, em_fatal,
467      * em_ignore, em_error IGN_* ditto WARN_* ditto
468      */

469     static Object JavaDoc setArpProperty(ARPOptions options, String JavaDoc str, Object JavaDoc v,
470             RDFErrorHandler eh ) {
471         //ARPOptions options = arpf.getOptions();
472
str = str.toUpperCase();
473         if (v == null)
474             v = "";
475         if (v instanceof String JavaDoc) {
476             v = ((String JavaDoc) v).toUpperCase();
477         }
478         if (str.equals("ERROR-MODE")) {
479             if (v instanceof String JavaDoc) {
480                 String JavaDoc val = (String JavaDoc) v;
481                 if (val.equals("LAX")) {
482                     options.setLaxErrorMode();
483                     return null;
484                 }
485                 if (val.equals("DEFAULT")) {
486                     options.setDefaultErrorMode();
487                     return null;
488                 }
489                 if (val.equals("STRICT")) {
490                     options.setStrictErrorMode();
491                     return null;
492                 }
493                 if (val.equals("STRICT-WARNING")) {
494                     options.setStrictErrorMode(EM_WARNING);
495                     return null;
496                 }
497                 if (val.equals("STRICT-FATAL")) {
498                     options.setStrictErrorMode(EM_FATAL);
499                     return null;
500                 }
501                 if (val.equals("STRICT-IGNORE")) {
502                     options.setStrictErrorMode(EM_IGNORE);
503                     return null;
504                 }
505                 if (val.equals("STRICT-ERROR")) {
506                     options.setStrictErrorMode(EM_ERROR);
507                     return null;
508                 }
509             }
510             eh
511                     .error(new IllegalArgumentException JavaDoc(
512                             "Property \"ERROR-MODE\" takes the following values: "
513                                     + "\"default\", \"lax\", \"strict\", \"strict-ignore\", \"strict-warning\", \"strict-error\", \"strict-fatal\"."));
514             return null;
515         }
516         if (str.equals("EMBEDDING")) {
517             if (v instanceof String JavaDoc) {
518                 v = Boolean.valueOf((String JavaDoc) v);
519             }
520             if (!(v instanceof Boolean JavaDoc)) {
521                 // Illegal value.
522
eh.error(new IllegalArgumentException JavaDoc(
523                         "Property \"EMBEDDING\" requires a boolean value."));
524                 boolean old = options.setEmbedding(false);
525                 options.setEmbedding(old);
526                 return new Boolean JavaDoc(old);
527             } else {
528                 return new Boolean JavaDoc(options.setEmbedding(((Boolean JavaDoc) v)
529                         .booleanValue()));
530             }
531         }
532         if (str.startsWith("ERR_") || str.startsWith("IGN_")
533                 || str.startsWith("WARN_")) {
534             int cond = errorCode(str);
535             if (cond == -1) {
536                 // error, see end of function.
537
} else {
538                 if (v instanceof String JavaDoc) {
539                     if (!((String JavaDoc) v).startsWith("EM_")) {
540                         // error, see below.
541
} else {
542                         int val = errorCode((String JavaDoc) v);
543                         if (val == -1) {
544                             // error, see below.
545
} else {
546                             int rslt = options.setErrorMode(cond, val);
547                             return new Integer JavaDoc(rslt);
548                         }
549                     }
550                 } else if (v instanceof Integer JavaDoc) {
551                     int val = ((Integer JavaDoc) v).intValue();
552                     switch (val) {
553                     case EM_IGNORE:
554                     case EM_WARNING:
555                     case EM_ERROR:
556                     case EM_FATAL:
557                         int rslt = options.setErrorMode(cond, val);
558                         return new Integer JavaDoc(rslt);
559                     default:
560                     // error, see below.
561
}
562                 }
563                 // Illegal value.
564
eh.error(new IllegalArgumentException JavaDoc("Property \""
565                         + str + "\" cannot have value: " + v.toString()));
566                 int old = options.setErrorMode(cond, EM_ERROR);
567                 options.setErrorMode(cond, old);
568                 return new Integer JavaDoc(old);
569             }
570         }
571         eh.error(new UnknownPropertyException(str));
572         return null;
573     }
574
575     /**
576      * Create a instance of ModelMem() and set it to use JenaReader as its
577      * default reader.
578      *
579      * @deprecated This Reader is now the default.
580      * @return A new in-memory Jena model.
581      */

582     static public Model memModel() {
583         Model rslt = ModelFactory.createDefaultModel();
584         useMe(rslt);
585         return rslt;
586     }
587
588 }
589
590 /*
591  * (c) Copyright 2001, 2002, 2003, 2004, 2005 Hewlett-Packard Development Company, LP All rights
592  * reserved.
593  *
594  * Redistribution and use in source and binary forms, with or without
595  * modification, are permitted provided that the following conditions are met:
596  * 1. Redistributions of source code must retain the above copyright notice,
597  * this list of conditions and the following disclaimer. 2. Redistributions in
598  * binary form must reproduce the above copyright notice, this list of
599  * conditions and the following disclaimer in the documentation and/or other
600  * materials provided with the distribution. 3. The name of the author may not
601  * be used to endorse or promote products derived from this software without
602  * specific prior written permission.
603  *
604  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
605  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
606  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
607  * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
608  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
609  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
610  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
611  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
612  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
613  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
614  * * $Id: JenaReader.java,v 1.30 2005/02/21 12:09:09 andy_seaborne Exp $
615  *
616  * AUTHOR: Jeremy J. Carroll
617  */
Popular Tags