com.sonicle.webtop.core.app.servlet.DocEditor.java Source code

Java tutorial

Introduction

Here is the source code for com.sonicle.webtop.core.app.servlet.DocEditor.java

Source

/*
 * Copyright (C) 2018 Sonicle S.r.l.
 *
 * This program is free software; you can redistribute it and/or modify it under
 * the terms of the GNU Affero General Public License version 3 as published by
 * the Free Software Foundation with the addition of the following permission
 * added to Section 15 as permitted in Section 7(a): FOR ANY PART OF THE COVERED
 * WORK IN WHICH THE COPYRIGHT IS OWNED BY SONICLE, SONICLE DISCLAIMS THE
 * WARRANTY OF NON INFRINGEMENT OF THIRD PARTY RIGHTS.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 * FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
 * details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program; if not, see http://www.gnu.org/licenses or write to
 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
 * MA 02110-1301 USA.
 *
 * You can contact Sonicle S.r.l. at email address sonicle[at]sonicle[dot]com
 *
 * The interactive user interfaces in modified source and object code versions
 * of this program must display Appropriate Legal Notices, as required under
 * Section 5 of the GNU Affero General Public License version 3.
 *
 * In accordance with Section 7(b) of the GNU Affero General Public License
 * version 3, these Appropriate Legal Notices must retain the display of the
 * Sonicle logo and Sonicle copyright notice. If the display of the logo is not
 * reasonably feasible for technical reasons, the Appropriate Legal Notices must
 * display the words "Copyright (C) 2018 Sonicle S.r.l.".
 */
package com.sonicle.webtop.core.app.servlet;

import com.sonicle.commons.URIUtils;
import com.sonicle.commons.http.HttpClientUtils;
import com.sonicle.commons.web.ServletUtils;
import com.sonicle.commons.web.json.MapItem;
import com.sonicle.commons.web.json.Payload;
import com.sonicle.webtop.core.app.sdk.BaseDocEditorDocumentHandler;
import com.sonicle.webtop.core.app.AbstractServlet;
import com.sonicle.webtop.core.app.DocEditorManager;
import com.sonicle.webtop.core.app.WT;
import com.sonicle.webtop.core.app.WebTopApp;
import com.sonicle.webtop.core.app.sdk.WTServletException;
import com.sonicle.webtop.core.app.servlet.js.DocEditorCallbackPayload;
import com.sonicle.webtop.core.app.servlet.js.DocEditorCallbackResponse;
import com.sonicle.webtop.core.sdk.DomainURIPath;
import java.io.IOException;
import java.io.InputStream;
import java.net.URI;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.client.HttpClient;
import org.apache.shiro.subject.support.SubjectThreadState;
import org.apache.shiro.util.ThreadState;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 *
 * @author malbinola
 */
public class DocEditor extends AbstractServlet {
    private static final Logger logger = LoggerFactory.getLogger(DocEditor.class);
    public static final String URL = "/doc-editor"; // Shiro.ini must reflect this URI!
    public static final String DOWNLOAD_PATH = "/oo/download";
    public static final String TRACK_PATH = "/oo/track";
    public static final String SESSION_ID_PARAM = "sid";
    public static final String EDITING_ID_PARAM = "eid";

    @Override
    protected void processRequest(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        WebTopApp wta = WebTopApp.get(request);

        ThreadState threadState = new SubjectThreadState(wta.getAdminSubject());
        threadState.bind();
        try {
            processRequestAsAdmin(request, response);
        } catch (Throwable t) {
            logger.error("Error fulfilling request", t);
            throw t;
        } finally {
            threadState.clear();
        }
    }

    protected void processRequestAsAdmin(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        DomainURIPath path = new DomainURIPath(URIUtils.removeTrailingSeparator(request.getPathInfo()));
        WebTopApp wta = WebTopApp.get(request);
        DocEditorManager docEdMgr = wta.getDocEditorManager();

        String domainId = WT.findDomainIdByPublicName(path.getDomainPublicName());
        if (domainId == null)
            throw new WTServletException("Invalid domain public name [{0}]", path.getDomainPublicName());
        if (!wta.getDocumentServerEnabled(domainId))
            throw new WTServletException("DocumentServer not enabled for domain [{}]", domainId);

        String remainingPath = path.getRemainingPath();
        if (StringUtils.equalsIgnoreCase(remainingPath, DOWNLOAD_PATH)) {
            String editingId = ServletUtils.getStringParameter(request, EDITING_ID_PARAM, true);

            BaseDocEditorDocumentHandler docHandler = docEdMgr.getDocumentHandler(editingId);
            if (docHandler == null)
                throw new WTServletException("Missing DocumentHandler [{}]", editingId);

            ServletUtils.setContentTypeHeader(response, "application/octet-stream");
            IOUtils.copy(docHandler.readDocument(), response.getOutputStream());

        } else if (StringUtils.equalsIgnoreCase(remainingPath, TRACK_PATH)) {
            String editingId = ServletUtils.getStringParameter(request, EDITING_ID_PARAM, true);
            Payload<MapItem, DocEditorCallbackPayload> payload = ServletUtils.getPayload(request,
                    DocEditorCallbackPayload.class);

            if (payload.data.status == 1) {
                logger.debug("Document is being edited [{}, {}]", editingId, payload.data.key);

                ServletUtils.writeJsonResponse(response, new DocEditorCallbackResponse(0));

            } else if ((payload.data.status == 2) || (payload.data.status == 6)) {
                BaseDocEditorDocumentHandler docHandler = docEdMgr.getDocumentHandler(editingId);
                if (docHandler == null)
                    throw new WTServletException("Missing DocumentHandler [{}]", editingId);

                if (payload.data.status == 2) {
                    logger.debug("Document is ready for saving [{}, {}]", editingId, payload.data.key);
                } else if (payload.data.status == 6) {
                    logger.debug("Document is being edited, but the current document state is saved [{}, {}]",
                            editingId, payload.data.key);
                }
                if (!docHandler.isWriteSupported())
                    throw new WTServletException("Write is not supported here [{}]", editingId);

                URI url = URIUtils.createURIQuietly(payload.data.url);
                if (url == null)
                    throw new WTServletException("Invalid URL [{}]", payload.data.url);

                /*
                if (true) {
                   long lastModified = docHandler.getLastModifiedTime();
                   if (lastModified != -1) {
                      String key = docEdMgr.buildDocumentKey(docHandler.getDocumentUniqueId(), lastModified);
                      if (!StringUtils.equals(payload.data.key, key)) {
                 throw new WTServletException("Original file was modified outside this session [{}]", editingId);
                      }
                   }
                }
                */

                InputStream is = null;
                try {
                    HttpClient httpCli = HttpClientUtils
                            .createBasicHttpClient(HttpClientUtils.configureSSLAcceptAll(), url);
                    is = HttpClientUtils.getContent(httpCli, url);
                    docHandler.writeDocument(is);
                } catch (IOException ex) {
                    throw new WTServletException("Unable to save edited content [{}]", editingId, ex);
                } finally {
                    IOUtils.closeQuietly(is);
                }

                //UserProfileId profileId = new UserProfileId(payload.data.users.get(0));
                if (payload.data.status == 2) {
                    docEdMgr.unregisterDocumentHandler(editingId);
                }
                ServletUtils.writeJsonResponse(response, new DocEditorCallbackResponse(0));

            } else if ((payload.data.status == 3) || (payload.data.status == 7)) {
                if (payload.data.status == 3) {
                    logger.error("Document saving error has occurred [{}, {}]", editingId, payload.data.key);
                    logger.error("Changes URL: {}", payload.data.changesurl);

                } else if (payload.data.status == 7) {
                    logger.error("Error has occurred while force saving the document [{}, {}]", editingId,
                            payload.data.key);
                }
                docEdMgr.unregisterDocumentHandler(editingId);
                ServletUtils.writeJsonResponse(response, new DocEditorCallbackResponse(0));

            } else if (payload.data.status == 4) {
                logger.debug("Document is closed with no changes [{}, {}]", editingId, payload.data.key);
                docEdMgr.unregisterDocumentHandler(editingId);
                ServletUtils.writeJsonResponse(response, new DocEditorCallbackResponse(0));
            }
        }
    }
}