001: /*
002: (c) Copyright 2005, 2006, 2007, 2008 Hewlett-Packard Development Company, LP
003: All rights reserved - see end of file.
004: $Id: ReasonerFactoryAssembler.java,v 1.11 2008/01/02 12:09:36 andy_seaborne Exp $
005: */
006:
007: package com.hp.hpl.jena.assembler.assemblers;
008:
009: import java.util.*;
010:
011: import com.hp.hpl.jena.assembler.*;
012: import com.hp.hpl.jena.assembler.exceptions.*;
013: import com.hp.hpl.jena.rdf.model.*;
014: import com.hp.hpl.jena.reasoner.*;
015: import com.hp.hpl.jena.reasoner.rulesys.*;
016:
017: /**
018: The ReasonerFactoryAssembler constructs a ReasonerFactory from the
019: description. The factory class may be specified by a URL (which looks
020: the class up in the registry) or by class name; otherwise it defaults to
021: the GenericRuleReasonerFactory.
022: <p>
023: If the class is specified by class name then an instance of that class
024: is acquired by calling its <code>theInstance</code> method if it
025: has one. Otherwise a fresh instance is constructed by calling its
026: zero-argument constructor (and exploding if it hasn't got one).
027: <p>
028: Thanks to Adam Cimarosti for provoking this code and providing an
029: example implementation.
030:
031: @author kers
032: */
033: public class ReasonerFactoryAssembler extends AssemblerBase implements
034: Assembler {
035: public Object open(Assembler a, Resource root, Mode irrelevant) {
036: checkType(root, JA.ReasonerFactory);
037: return addRules(root, a, getReasonerFactory(root));
038: }
039:
040: private ReasonerFactory addRules(Resource root, Assembler a,
041: final ReasonerFactory r) {
042: final List rules = RuleSetAssembler.addRules(new ArrayList(),
043: a, root);
044: if (rules.size() > 0)
045: if (r instanceof GenericRuleReasonerFactory) {
046: return new ReasonerFactory() {
047: public Reasoner create(Resource configuration) {
048: GenericRuleReasoner result = (GenericRuleReasoner) r
049: .create(configuration);
050: result.addRules(rules);
051: return result;
052: }
053:
054: public Model getCapabilities() {
055: return r.getCapabilities();
056: }
057:
058: public String getURI() {
059: return r.getURI();
060: }
061: };
062: } else
063: throw new CannotHaveRulesException(root);
064: return r;
065: }
066:
067: protected Reasoner getReasoner(Resource root) {
068: return getReasonerFactory(root).create(root);
069: }
070:
071: protected static ReasonerFactory getReasonerFactory(Resource root) {
072: Resource reasonerURL = getUniqueResource(root, JA.reasonerURL);
073: String className = getOptionalClassName(root);
074: return className != null ? getReasonerFactoryByClassName(root,
075: className)
076: : reasonerURL == null ? GenericRuleReasonerFactory
077: .theInstance() : getReasonerFactoryByURL(root,
078: reasonerURL);
079: }
080:
081: private static ReasonerFactory getReasonerFactoryByClassName(
082: Resource root, String className) {
083: Class c = loadClass(root, className);
084: mustBeReasonerFactory(root, c);
085: ReasonerFactory theInstance = resultFromStatic(c, "theInstance");
086: return theInstance == null ? createInstance(root, c)
087: : theInstance;
088: }
089:
090: private static ReasonerFactory createInstance(Resource root, Class c) {
091: try {
092: return (ReasonerFactory) c.newInstance();
093: } catch (Exception e) {
094: throw new AssemblerException(root,
095: "could not create instance of " + c.getName(), e);
096: }
097: }
098:
099: private static ReasonerFactory resultFromStatic(Class c,
100: String methodName) {
101: try {
102: return (ReasonerFactory) c.getMethod(methodName, null)
103: .invoke(null, null);
104: } catch (Exception e) {
105: return null;
106: }
107: }
108:
109: /**
110: Throw a <code>NotExpectedTypeException</code> if <code>c</code>
111: isn't a subclass of <code>ReasonerFactory</code>.
112: */
113: private static void mustBeReasonerFactory(Resource root, Class c) {
114: if (!ReasonerFactory.class.isAssignableFrom(c))
115: throw new NotExpectedTypeException(root,
116: ReasonerFactory.class, c);
117: }
118:
119: /**
120: Answer the string described by the value of the unique optional
121: <code>JA.reasonerClass</code> property of <code>root</code>,
122: or null if there's no such property. The value may be a URI, in which case
123: it must be a <b>java:</b> URI with content the class name; or it may
124: be a literal, in which case its lexical form is its class name; otherwise,
125: BOOM.
126: */
127: private static String getOptionalClassName(Resource root) {
128: return getOptionalClassName(root, JA.reasonerClass);
129: }
130:
131: /**
132: Answer a ReasonerFactory which delivers reasoners with the given
133: URL <code>reasonerURL</code>. If there is no such reasoner, throw
134: an <code>UnknownreasonerException</code>.
135: */
136: public static ReasonerFactory getReasonerFactoryByURL(
137: Resource root, Resource reasonerURL) {
138: String url = reasonerURL.getURI();
139: ReasonerFactory factory = ReasonerRegistry.theRegistry()
140: .getFactory(url);
141: if (factory == null)
142: throw new UnknownReasonerException(root, reasonerURL);
143: return factory;
144: }
145: }
146:
147: /*
148: * (c) Copyright 2005, 2006, 2007, 2008 Hewlett-Packard Development Company, LP
149: * All rights reserved.
150: *
151: * Redistribution and use in source and binary forms, with or without
152: * modification, are permitted provided that the following conditions
153: * are met:
154: * 1. Redistributions of source code must retain the above copyright
155: * notice, this list of conditions and the following disclaimer.
156: * 2. Redistributions in binary form must reproduce the above copyright
157: * notice, this list of conditions and the following disclaimer in the
158: * documentation and/or other materials provided with the distribution.
159: * 3. The name of the author may not be used to endorse or promote products
160: * derived from this software without specific prior written permission.
161: *
162: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
163: * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
164: * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
165: * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
166: * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
167: * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
168: * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
169: * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
170: * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
171: * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
172: */
|