    001    // This file is part of the Attempto Java Packages.
    002    // Copyright 2008, Attempto Group, University of Zurich (see http://attempto.ifi.uzh.ch).
    003    //
    004    // The Attempto Java Packages is free software: you can redistribute it and/or modify it under the
    005    // terms of the GNU Lesser General Public License as published by the Free Software Foundation,
    006    // either version 3 of the License, or (at your option) any later version.
    007    //
    008    // The Attempto Java Packages is distributed in the hope that it will be useful, but WITHOUT ANY
    009    // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
    010    // PURPOSE. See the GNU Lesser General Public License for more details.
    011    //
    012    // You should have received a copy of the GNU Lesser General Public License along with the Attempto
    013    // Java Packages. If not, see http://www.gnu.org/licenses/.
    014
    015    package ch.uzh.ifi.attempto.ape;
    016
    017    import java.io.BufferedReader;
    018    import java.io.IOException;
    019    import java.io.InputStream;
    020    import java.io.InputStreamReader;
    021
    022    import org.apache.commons.httpclient.HttpClient;
    023    import org.apache.commons.httpclient.HttpStatus;
    024    import org.apache.commons.httpclient.NameValuePair;
    025    import org.apache.commons.httpclient.methods.PostMethod;
    026
    027    // TODO Why don't we use GET instead of POST (as least for shorter queries)?
    028
    029    /**
    030     * This class provides an interface to the Attempto Parsing Engine (APE) webservice
    031     * (i.e. HTTP server).
    032     * The HTTP server implementation is provided by <code>ape.exe</code>. To start
    033     * a server, execute for example:
    034     *
    035     * <pre>
    036     * ./ape.exe -httpserver -port 8000
    037     * </pre>
    038     *
    039     * @author Kaarel Kaljurand
    040     * @author Tobias Kuhn
    041     */
    042    public class APEWebservice extends ACEParser {
    043
    044            private String wsUrl;
    045            private NameValuePair uri = new NameValuePair("uri", "");
    046            private NameValuePair text = new NameValuePair("text", "");
    047            private NameValuePair ulextext = new NameValuePair("ulextext", "");
    048            private NameValuePair solo = new NameValuePair("solo", "owlxml");
    049            private NameValuePair guess = new NameValuePair("guess", "off");
    050            private NameValuePair noclex = new NameValuePair("noclex", "off");
    051
    052            /**
    053             * Creates a new parser object based on the URL of a running APE webservice.
    054             *
    055             * @param wsUrl The URL of the APE webservice.
    056             */
    057            public APEWebservice(String wsUrl) {
    058                    this.wsUrl = wsUrl;
    059            }
    060
    061            /**
    062             * Sets the URL of the APE webservice to be used.
    063             *
    064             * @param wsUrl The URL of the APE webservice.
    065             */
    066            public void setWebserviceUrl(String wsUrl) {
    067                    this.wsUrl = wsUrl;
    068            }
    069
    070            public String getSoloOutput(String aceText, Lexicon lexicon, OutputType outputType) throws ACEParserException {
    071                    setText(aceText);
    072                    setUlex(lexicon);
    073                    setSolo(outputType);
    074                    return checkForErrors(getParserResponseAsString(new NameValuePair[] {text, ulextext, solo, uri, guess, noclex}));
    075            }
    076
    077
    078            public ACEParserResult getMultiOutput(String aceText, Lexicon lexicon, OutputType... outputTypes) {
    079                    NameValuePair[] params = new NameValuePair[outputTypes.length + 5];
    080                    setText(aceText);
    081                    setUlex(lexicon);
    082                    params[0] = text;
    083                    params[1] = ulextext;
    084                    params[2] = uri;
    085                    params[3] = guess;
    086                    params[4] = noclex;
    087                    int counter = 5;
    088                    for (OutputType t : outputTypes) {
    089                            params[counter] = new NameValuePair(t.toMultiFlag(), "on");
    090                            counter++;
    091                    }
    092                    return new ACEParserResult(getParserResponseAsString(params));
    093            }
    094
    095
    096            public void setURI(String uri) {
    097                    super.setURI(uri);
    098                    this.uri.setValue(getURI());
    099            }
    100
    101
    102            public void setGuessingEnabled(boolean guessing) {
    103                    super.setGuessingEnabled(guessing);
    104                    if (isGuessingEnabled()) {
    105                            this.guess.setValue("on");
    106                    }
    107                    else {
    108                            this.guess.setValue("off");
    109                    }
    110            }
    111
    112
    113            public void setClexEnabled(boolean clexEnabled) {
    114                    super.setClexEnabled(clexEnabled);
    115
    116                    if (isClexEnabled()) {
    117                            this.noclex.setValue("off");
    118                    }
    119                    else {
    120                            this.noclex.setValue("on");
    121                    }
    122            }
    123
    124
    125            private void setUlex(Lexicon lexicon) {
    126                    if (lexicon == null) {
    127                            this.ulextext.setValue("");
    128                    }
    129                    else {
    130                            this.ulextext.setValue(lexicon.toString());
    131                    }
    132            }
    133
    134            private void setText(String text) {
    135                    this.text.setValue(text);
    136            }
    137
    138
    139            private void setSolo(OutputType solo) {
    140                    this.solo.setValue(solo.toSoloFlag());
    141            }
    142
    143            private String getParserResponseAsString(NameValuePair[] parameters) {
    144                    HttpClient client = new HttpClient();
    145                    PostMethod method = new PostMethod(wsUrl);
    146                    method.setRequestBody(parameters);
    147                    String response = null;
    148
    149                    try {
    150                            int statusCode = client.executeMethod(method);
    151
    152                            if (statusCode == HttpStatus.SC_OK) {
    153                                    response = inputStreamAsString(method.getResponseBodyAsStream());
    154                            }
    155                            else {
    156                                    throw new RuntimeException("HTTP request failed: " + method.getStatusLine() + ": " + wsUrl);
    157                            }
    158                    } catch (Exception e) {
    159                            throw new RuntimeException("Accessing APE webservice failed: " + e.getMessage());
    160                    } finally {
    161                            method.releaseConnection();
    162                    }
    163
    164                    return response;
    165            }
    166
    167            private String inputStreamAsString(InputStream stream) throws IOException {
    168                    BufferedReader br = new BufferedReader(new InputStreamReader(stream));
    169                    StringBuffer sb = new StringBuffer();
    170                    String line = null;
    171
    172                    while ((line = br.readLine()) != null) {
    173                            sb.append(line);
    174                            sb.append('\n');
    175                    }
    176
    177                    br.close();
    178                    return sb.toString();
    179            }
    180    }