org.apache.manifoldcf.agents.output.opensearchserver.OpenSearchServerIndex.java Source code

Java tutorial

Introduction

Here is the source code for org.apache.manifoldcf.agents.output.opensearchserver.OpenSearchServerIndex.java

Source

/**
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package org.apache.manifoldcf.agents.output.opensearchserver;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.io.FilenameUtils;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang.StringEscapeUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPut;
import org.apache.http.message.BasicHeader;
import org.apache.http.util.EntityUtils;
import org.apache.manifoldcf.agents.interfaces.IOutputAddActivity;
import org.apache.manifoldcf.agents.interfaces.IOutputHistoryActivity;
import org.apache.manifoldcf.agents.interfaces.RepositoryDocument;
import org.apache.manifoldcf.core.common.Base64;
import org.apache.manifoldcf.core.interfaces.ManifoldCFException;

public class OpenSearchServerIndex extends OpenSearchServerConnection {

    private static class Acls {
        private String[] acls = null;
        private String[] denyAcls = null;
        private String[] shareAcls = null;
        private String[] shareDenyAcls = null;

        private void setDocument(String[] acls, String[] denyAcls) {
            this.acls = acls;
            this.denyAcls = denyAcls;
        }

        private void setShare(String[] acls, String[] denyAcls) {
            this.shareAcls = acls;
            this.shareDenyAcls = denyAcls;
        }
    }

    private static class IndexRequestEntity implements HttpEntity {

        private final String documentURI;
        private final RepositoryDocument document;
        private final String fileName;
        private final Acls acls;

        public IndexRequestEntity(String documentURI, RepositoryDocument document, Acls acls) {
            this.documentURI = documentURI;
            this.document = document;
            this.fileName = FilenameUtils.getName(documentURI);
            this.acls = acls;
        }

        @Override
        public boolean isChunked() {
            return false;
        }

        @Override
        @Deprecated
        public void consumeContent() throws IOException {
            EntityUtils.consume(this);
        }

        @Override
        public boolean isRepeatable() {
            return false;
        }

        @Override
        public boolean isStreaming() {
            return true;
        }

        @Override
        public InputStream getContent() throws IOException, IllegalStateException {
            return null;
        }

        private static final void writeFieldCdata(String fieldName, Collection<String> values, PrintWriter pw) {
            if (CollectionUtils.isEmpty(values))
                return;
            pw.print("<field name=\"");
            pw.print(StringEscapeUtils.escapeXml(fieldName));
            pw.print("\">");
            for (String value : values) {
                pw.print("<value><![CDATA[");
                pw.print(value);
                pw.print("]]></value>");
            }
            pw.println("</field>");
        }

        private static final void writeField(String fieldName, String value, PrintWriter pw) {
            if (StringUtils.isEmpty(value))
                return;
            pw.print("<field name=\"");
            pw.print(fieldName);
            pw.print("\"><value>");
            pw.print(value);
            pw.println("</value></field>");
        }

        private static final void writeFieldValues(String fieldName, String[] values, PrintWriter pw) {
            if (values == null || values.length == 0)
                return;
            pw.print("<field name=\"");
            pw.print(fieldName);
            pw.println("\">");
            for (String value : values) {
                pw.print("<value>");
                pw.print(value);
                pw.println("</value>");
            }
            pw.println("</field>");
        }

        @Override
        public void writeTo(OutputStream out) throws IOException {
            PrintWriter pw = new PrintWriter(out);
            try {
                pw.println("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>");
                pw.println("<index>);");
                pw.print("<document>");
                List<String> values = new ArrayList<String>(1);
                Iterator<String> iter = document.getFields();
                if (iter != null) {
                    while (iter.hasNext()) {
                        String fieldName = iter.next();
                        if ("uri".equals(fieldName))
                            continue;
                        Object[] fieldValues = document.getField(fieldName);
                        if (fieldValues != null && fieldValues.length > 0) {
                            values.clear();
                            for (Object fieldValue : fieldValues)
                                if (fieldValue != null)
                                    values.add(fieldValue.toString());
                            writeFieldCdata(fieldName, values, pw);
                        }
                    }
                }
                writeField("uri", documentURI, pw);
                if (document.getBinaryLength() > 0) {
                    Base64 base64 = new Base64();
                    pw.print("<binary fileName=\"");
                    pw.print(fileName);
                    pw.println("\">");
                    base64.encodeStream(document.getBinaryStream(), pw);
                    pw.println("</binary>");
                }
                if (acls != null) {
                    writeFieldValues("userAllow", acls.acls, pw);
                    writeFieldValues("userDeny", acls.denyAcls, pw);
                    writeFieldValues("groupAllow", acls.shareAcls, pw);
                    writeFieldValues("groupDeny", acls.shareDenyAcls, pw);
                }
                pw.println("</document>");
                pw.println("</index>");
            } catch (ManifoldCFException e) {
                throw new IOException(e.getMessage(), e);
            } finally {
                IOUtils.closeQuietly(pw);
            }
        }

        @Override
        public long getContentLength() {
            // Unknown (chunked) length
            return -1L;
        }

        @Override
        public Header getContentType() {
            return new BasicHeader("Content-type", "text/xml; charset=utf-8");
        }

        @Override
        public Header getContentEncoding() {
            return null;
        }
    }

    /**
     * Convert an unqualified ACL to qualified form.
     * 
     * @param acl
     *          is the initial, unqualified ACL.
     * @param authorityNameString
     *          is the name of the governing authority for this document's acls,
     *          or null if none.
     * @param activities
     *          is the activities object, so we can report what's happening.
     * @return the modified ACL.
     */
    protected static String[] convertACL(String[] acl, String authorityNameString, IOutputAddActivity activities)
            throws ManifoldCFException {
        if (acl != null) {
            String[] rval = new String[acl.length];
            int i = 0;
            while (i < rval.length) {
                rval[i] = activities.qualifyAccessToken(authorityNameString, acl[i]);
                i++;
            }
            return rval;
        }
        return new String[0];
    }

    public OpenSearchServerIndex(HttpClient client, String documentURI, OpenSearchServerConfig config,
            RepositoryDocument document, String authorityNameString, IOutputAddActivity activities)
            throws ManifoldCFException {
        super(client, config);

        Acls acls = new Acls();
        Iterator<String> a = document.securityTypesIterator();
        if (a != null) {
            while (a.hasNext()) {
                String securityType = a.next();
                String[] convertedAcls = convertACL(document.getSecurityACL(securityType), authorityNameString,
                        activities);
                String[] convertedDenyAcls = convertACL(document.getSecurityDenyACL(securityType),
                        authorityNameString, activities);
                if (securityType.equals(RepositoryDocument.SECURITY_TYPE_DOCUMENT)) {
                    acls.setDocument(convertedAcls, convertedDenyAcls);
                } else if (securityType.equals(RepositoryDocument.SECURITY_TYPE_SHARE)) {
                    acls.setShare(convertedAcls, convertedDenyAcls);
                } else {
                    // Don't know how to deal with it
                    setResult(activities.UNKNOWN_SECURITY, Result.ERROR,
                            "Unhandled security type: " + securityType);
                    return;
                }
            }
        }

        StringBuffer url = getApiUrl("update");
        HttpPut put = new HttpPut(url.toString());
        put.setEntity(new IndexRequestEntity(documentURI, document, acls));
        call(put);
        if ("OK".equals(checkXPath(xPathStatus)))
            return;
        String error = checkXPath(xPathException);
        setResult("XPATHEXCEPTION", Result.ERROR, error);
        throw new ManifoldCFException("Error, unexpected response: " + error);
    }

}