001    /***************************************************************************/
002    /*  Copyright (C) 2010-2011, Sebastian Hellmann                            */
003    /*  Note: If you need parts of NLP2RDF in another licence due to licence   */
004    /*  incompatibility, please mail hellmann@informatik.uni-leipzig.de        */
005    /*                                                                         */
006    /*  This file is part of NLP2RDF.                                          */
007    /*                                                                         */
008    /*  NLP2RDF is free software; you can redistribute it and/or modify        */
009    /*  it under the terms of the GNU General Public License as published by   */
010    /*  the Free Software Foundation; either version 3 of the License, or      */
011    /*  (at your option) any later version.                                    */
012    /*                                                                         */
013    /*  NLP2RDF is distributed in the hope that it will be useful,             */
014    /*  but WITHOUT ANY WARRANTY; without even the implied warranty of         */
015    /*  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the           */
016    /*  GNU General Public License for more details.                           */
017    /*                                                                         */
018    /*  You should have received a copy of the GNU General Public License      */
019    /*  along with this program. If not, see <http://www.gnu.org/licenses/>.   */
020    /***************************************************************************/
021    
022    package org.nlp2rdf.webservice;
023    
024    import com.hp.hpl.jena.ontology.*;
025    import com.hp.hpl.jena.rdf.model.ModelFactory;
026    import com.hp.hpl.jena.rdf.model.RDFWriter;
027    import com.hp.hpl.jena.util.iterator.ExtendedIterator;
028    import com.hp.hpl.jena.vocabulary.OWL;
029    import com.jamonapi.Monitor;
030    import com.jamonapi.MonitorFactory;
031    import org.slf4j.Logger;
032    import org.slf4j.LoggerFactory;
033    
034    import javax.servlet.ServletException;
035    import javax.servlet.http.HttpServlet;
036    import javax.servlet.http.HttpServletRequest;
037    import javax.servlet.http.HttpServletResponse;
038    import java.io.IOException;
039    import java.io.PrintWriter;
040    import java.security.InvalidParameterException;
041    
042    
043    public abstract class NIFServlet extends HttpServlet {
044        private static Logger log = LoggerFactory.getLogger(NIFServlet.class);
045    
046        @Override
047        protected void doGet(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws ServletException, IOException {
048            handle(httpServletRequest, httpServletResponse);
049        }
050    
051        @Override
052        protected void doPost(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws ServletException, IOException {
053            handle(httpServletRequest, httpServletResponse);
054        }
055    
056        public abstract void execute(NIFParameters nifParameters, OntModel diff) throws Exception;
057    
058        /**
059         * this method answers GET and POST requests, which are treated the same.
060         * - Validates parameters
061         * - does the work (execute)
062         *
063         * @param httpServletRequest
064         * @param httpServletResponse
065         * @throws ServletException
066         * @throws IOException
067         */
068        private void handle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws ServletException, IOException {
069    
070            try {
071    
072                //Validate and normalize input
073                Monitor mon = MonitorFactory.getTimeMonitor("NIFParameters.getInstance").start();
074                NIFParameters nifParameters = NIFParameters.getInstance(httpServletRequest);
075                log.debug("NIFParameters Object created: " + logMonitor(mon.stop()));
076    
077                //execute the task
078                mon = MonitorFactory.getTimeMonitor("NIFServlet.execute").start();
079                OntModel diff = ModelFactory.createOntologyModel(OntModelSpec.OWL_DL_MEM, ModelFactory.createDefaultModel());
080                execute(nifParameters, diff);
081                log.debug("NIF Component executed task: " + logMonitor(mon.stop()));
082    
083    
084                //output is an inofficial parameter, full merges input and output
085                OntModel ret = ModelFactory.createOntologyModel(OntModelSpec.OWL_DL_MEM, ModelFactory.createDefaultModel());
086                if (nifParameters.getOutput().equals("full")) {
087                    //merge
088                    ret.add(nifParameters.getInputModel());
089                }
090                ret.add(diff);
091    
092                write(httpServletResponse, ret, nifParameters.getFormat());
093                log.info("output (" + nifParameters.getFormat() + ", " + nifParameters.getOutput() + ") written. before: " + (nifParameters.getInputModel().size()) + " triples, added: " + diff.size() + " after: " + ret.size());
094    
095            } catch (IllegalArgumentException e) {
096                String msg = e.getMessage() + printParameterMap(httpServletRequest);
097                log.error(msg);
098                httpServletResponse.setContentType("text/plain");
099                PrintWriter out = httpServletResponse.getWriter();
100                out.println(msg);
101                out.close();
102    
103            } catch (Exception e) {
104                String msg = "An error occured: " + e.getMessage() + printParameterMap(httpServletRequest);
105                log.error(msg, e);
106                httpServletResponse.setContentType("text/plain");
107                PrintWriter out = httpServletResponse.getWriter();
108                out.println(msg);
109                out.close();
110            }
111        }
112    
113        protected static String logMonitor(Monitor m) {
114            return "needed: " + m.getLastValue() + " ms. (" + m.getTotal() + " total)";
115        }
116    
117        protected void write(HttpServletResponse httpServletResponse, OntModel out, String format) throws IOException {
118            if (format.equalsIgnoreCase("rdfxml")) {
119                write(httpServletResponse, out, "RDF/XML", "application/rdf+xml");
120            } else if (format.equalsIgnoreCase("turtle")) {
121                write(httpServletResponse, out, "TURTLE", "text/rdf+n3");
122            } else if (format.equalsIgnoreCase("n3")) {
123                write(httpServletResponse, out, "N3", "text/rdf+n3");
124            } else if (format.equalsIgnoreCase("ntriples")) {
125                write(httpServletResponse, out, "N-TRIPLE", "text/rdf+n3");
126            } else if (format.equalsIgnoreCase("json")) {
127                throw new InvalidParameterException("There is no JSON output implemented at the moment. Sorry!");
128            }
129    
130        }
131    
132        protected void write(HttpServletResponse httpServletResponse, OntModel out, String jenaFormat, String contentType) throws IOException {
133            httpServletResponse.setContentType(contentType);
134            httpServletResponse.setCharacterEncoding("UTF-8");
135    
136            //there are some problems with dl-learner, if individuals are not typed correctly
137            /*for (ExtendedIterator<Individual> it = out.listIndividuals(); it.hasNext(); ) {
138                it.next().addOntClass(OWL.Thing);
139            }
140            for (ExtendedIterator<ObjectProperty> it = out.listObjectProperties(); it.hasNext(); ) {
141                it.next().addRDFType(OWL.ObjectProperty);
142            }
143            for (ExtendedIterator<DatatypeProperty> it = out.listDatatypeProperties(); it.hasNext(); ) {
144                it.next().addRDFType(OWL.DatatypeProperty);
145            }
146            for (ExtendedIterator<OntClass> it = out.listClasses(); it.hasNext(); ) {
147                it.next().addRDFType(OWL.Class);
148            } */
149    
150            out.setNsPrefix("rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");
151            out.setNsPrefix("rdfs", "http://www.w3.org/2000/01/rdf-schema#");
152            out.setNsPrefix("owl", "http://www.w3.org/2002/07/owl#");
153    
154    
155            out.setNsPrefix("sso", "http://nlp2rdf.lod2.eu/schema/sso/");
156            out.setNsPrefix("str", "http://nlp2rdf.lod2.eu/schema/string/");
157            out.setNsPrefix("topic", "http://nlp2rdf.lod2.eu/schema/topic/");
158    
159    
160            out.setNsPrefix("olia", "http://purl.org/olia/olia.owl#");
161            out.setNsPrefix("olia-top", "http://purl.org/olia/olia-top.owl#");
162            out.setNsPrefix("olia_system", "http://purl.org/olia/system.owl#");
163    
164            out.setNsPrefix("penn", "http://purl.org/olia/penn.owl#");
165            out.setNsPrefix("penn-syntax", "http://purl.org/olia/penn-syntax.owl#");
166            out.setNsPrefix("stanford", "http://purl.org/olia/stanford.owl#");
167    
168            out.setNsPrefix("brown", "http://purl.org/olia/brown.owl#");
169    
170    
171            //this is the printer where the output has to be on
172            PrintWriter pw = httpServletResponse.getWriter();
173            RDFWriter writer = out.getWriter(jenaFormat);
174            writer.setProperty("showXmlDeclaration", "true");
175            //writer.setProperty("showDoctypeDeclaration", "true");
176            writer.write(out, pw, "");
177            pw.close();
178        }
179    
180    
181        public static String printParameterMap(HttpServletRequest httpServletRequest) {
182    
183            log.error("printing map");
184            log.error(httpServletRequest+"");
185            log.error(httpServletRequest.getParameterMap()+"");
186            log.error(httpServletRequest.getParameterMap().keySet()+"");
187            StringBuffer buf = new StringBuffer();
188            for (Object key : httpServletRequest.getParameterMap().keySet()) {
189                buf.append("\nParameter: " + key + " Values: ");
190                for (String s : httpServletRequest.getParameterValues((String) key)) {
191                    buf.append(((s.length() > 200) ? s.substring(0, 200) + "..." : s) + " ");
192                }
193            }
194            return buf.toString();
195        }
196    
197    }