001/*
002 * Licensed to DuraSpace under one or more contributor license agreements.
003 * See the NOTICE file distributed with this work for additional information
004 * regarding copyright ownership.
005 *
006 * DuraSpace licenses this file to you under the Apache License,
007 * Version 2.0 (the "License"); you may not use this file except in
008 * compliance with the License.  You may obtain a copy of the License at
009 *
010 *     http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software
013 * distributed under the License is distributed on an "AS IS" BASIS,
014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 * See the License for the specific language governing permissions and
016 * limitations under the License.
017 */
018package org.fcrepo.http.api.repository;
019
020import static com.google.common.io.Files.createTempDir;
021import static java.util.stream.Collectors.joining;
022import static javax.ws.rs.core.Response.ok;
023import static javax.ws.rs.core.Response.serverError;
024import static org.slf4j.LoggerFactory.getLogger;
025
026import java.io.File;
027import java.io.IOException;
028import java.io.InputStream;
029import java.util.Collection;
030
031import javax.inject.Inject;
032import javax.ws.rs.POST;
033import javax.ws.rs.Path;
034import javax.ws.rs.WebApplicationException;
035import javax.ws.rs.core.Response;
036
037import org.apache.commons.io.IOUtils;
038import org.fcrepo.http.commons.AbstractResource;
039import org.fcrepo.http.commons.session.HttpSession;
040import org.fcrepo.kernel.api.services.RepositoryService;
041import org.slf4j.Logger;
042import org.springframework.context.annotation.Scope;
043
044/**
045 * Repository-wide backup endpoint
046 *
047 * @author cbeer
048 */
049@Scope("prototype")
050@Path("/fcr:backup")
051@Deprecated
052public class FedoraRepositoryBackup extends AbstractResource {
053
054    private static final Logger LOGGER = getLogger(FedoraRepositoryBackup.class);
055
056    @Inject
057    protected HttpSession session;
058
059    /**
060     * The fcrepo repository service
061     */
062    @Inject
063    protected RepositoryService repositoryService;
064
065    /**
066     * This method runs a repository backup.
067     *
068     * @param bodyStream the input body stream
069     * @return path to the backup
070     * @throws IOException if IO exception occurred
071     */
072    @POST
073    public Response runBackup(final InputStream bodyStream) throws IOException {
074
075        File backupDirectory;
076        if (null != bodyStream) {
077            final String body = IOUtils.toString(bodyStream).trim();
078
079            backupDirectory = new File(body.trim());
080            if (body.isEmpty()) {
081                // Backup to a temp directory
082                backupDirectory = createTempDir();
083
084            } else if (!backupDirectory.exists() || !backupDirectory.canWrite()) {
085                throw new WebApplicationException(
086                        serverError().entity(
087                                "Backup directory does not exist or is not writable: " +
088                                        backupDirectory.getAbsolutePath())
089                                .build());
090            }
091
092        } else {
093            // Backup to a temp directory
094            backupDirectory = createTempDir();
095        }
096
097        LOGGER.debug("Backing up to: {}", backupDirectory.getAbsolutePath());
098        final Collection<Throwable> problems = repositoryService.backupRepository(session.getFedoraSession(),
099                backupDirectory);
100
101        if (!problems.isEmpty()) {
102            LOGGER.error("Problems backing up the repository:");
103
104            // Report the problems (we'll just print them out) ...
105            final String output = problems.stream().map(Throwable::getMessage).peek(LOGGER::error)
106                    .collect(joining("\n"));
107
108            throw new WebApplicationException(serverError().entity(output).build());
109
110        }
111        return ok()
112            .header("Warning", "This endpoint will be moving to an extension module in a future release of Fedora")
113            .entity(backupDirectory.getCanonicalPath()).build();
114    }
115}