org.jboss.loom.actions.FileAbstractAction.java Source code

Java tutorial

Introduction

Here is the source code for org.jboss.loom.actions.FileAbstractAction.java

Source

/**
 * Licensed 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.jboss.loom.actions;

import java.io.File;
import java.io.IOException;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import org.apache.commons.io.FileUtils;
import org.jboss.loom.ex.ActionException;
import org.jboss.loom.ex.MigrationException;
import org.jboss.loom.spi.IMigrator;
import org.jboss.loom.spi.ann.Property;
import org.jboss.loom.utils.DirScanner;
import org.jboss.loom.utils.Utils;

/**
 *  Base for file-based operations, like copying files, merging properties, or XSLT transformations.
 * 
 *  @author Ondrej Zizka, ozizka at redhat.com
 */
public abstract class FileAbstractAction extends AbstractStatefulAction {

    // First alternative: exact file.
    protected File src;

    // Second alternative: 
    protected String pathMask; // What to look for - Ant-style path mask.
    protected File baseDir; // Where to look for.    

    protected File dest;
    protected boolean failIfNotExist = true;
    private File temp;

    @Override
    public String toDescription() {
        return this.verb() + " file, " + addToDescription() + (this.failIfNotExist ? "" : " don't")
                + " fail if exists," + "\n    from " + (this.src != null ? this.src.getPath() : this.pathMask)
                + "\n      to " + (this.dest == null ? "null" : this.dest.getPath());
    }

    protected abstract String verb();

    protected String addToDescription() {
        return "";
    }

    public FileAbstractAction(Class<? extends IMigrator> fromMigrator, File src, File dest) {
        super(fromMigrator);
        this.src = src;
        this.dest = dest;
    }

    public FileAbstractAction(Class<? extends IMigrator> fromMigrator, File src, File dest,
            boolean failIfNotExist) {
        super(fromMigrator);
        this.src = src;
        this.dest = dest;
        this.failIfNotExist = failIfNotExist;
    }

    public FileAbstractAction(Class<? extends IMigrator> fromMigrator, String pathMask, File baseDir, File dest,
            boolean failIfNotExist) {
        super(fromMigrator);
        this.src = null;
        this.baseDir = baseDir;
        this.pathMask = pathMask;
        this.dest = dest;
        this.failIfNotExist = failIfNotExist;
    }

    @Override
    public void preValidate() throws MigrationException {
        if (src != null) {
            if (!src.exists() && failIfNotExist)
                throw new ActionException(this,
                        "File to " + verb().toLowerCase() + " doesn't exist: " + src.getPath());
        } else if (this.pathMask == null) {
            throw new ActionException(this, "Neither src nor pathMask is set.");
        }
        // Copy multiple files to a file?
        else {
            // We would have to scan for the files now.
        }
    }

    /**
     * Copies the dest file, if it exists, to a temp file.
     */
    @Override
    public void backup() throws MigrationException {

        if (!this.dest.exists())
            return;

        try {
            this.temp = File.createTempFile(this.dest.getName(), null);
            FileUtils.deleteQuietly(this.temp);
            Utils.copyFileOrDirectory(this.dest, this.temp);
        } catch (IOException ex) {
            throw new ActionException(this, "Creating a backup file failed: " + ex.getMessage(), ex);
        }
        setState(IMigrationAction.State.BACKED_UP);
    }

    @Override
    public void rollback() throws MigrationException {
        if (!this.isAfterPerform())
            return;

        // Delete the new file.
        FileUtils.deleteQuietly(this.dest);

        // Restore the backup file, if we created any.
        if (this.temp != null) {
            try {
                FileUtils.moveFile(this.temp, this.dest);
            } catch (IOException ex) {
                throw new ActionException(this, "Restoring the previous file failed: " + ex.getMessage(), ex);
            }
        }
        setState(IMigrationAction.State.ROLLED_BACK);
    }

    @Override
    public void postValidate() throws MigrationException {
        // Empty - JRE would give IOEx if something.
    }

    /**
     * Removes the temp file.
     */
    @Override
    public void cleanBackup() {

        if (this.temp == null)
            return;
        if (this.temp.exists()) {
            FileUtils.deleteQuietly(this.temp);
        }
        setState(IMigrationAction.State.FINISHED);
    }

    //<editor-fold defaultstate="collapsed" desc="hash/eq - use src and dest.">
    @Override
    public int hashCode() {
        int hash = 7;
        hash = 67 * hash + Objects.hashCode(this.src);
        hash = 67 * hash + Objects.hashCode(this.dest);
        return hash;
    }

    @Override
    public boolean equals(Object obj) {
        if (obj == null) {
            return false;
        }
        if (getClass() != obj.getClass()) {
            return false;
        }
        final FileAbstractAction other = (FileAbstractAction) obj;
        if (!Objects.equals(this.src, other.src)) {
            return false;
        }
        if (!Objects.equals(this.dest, other.dest)) {
            return false;
        }
        return true;
    }
    //</editor-fold>

    @Property(name = "src", style = "code", label = "From")
    public File getSrc() {
        return src;
    }

    @Property(name = "dest", style = "code", label = "To")
    public File getDest() {
        return dest;
    }

    /**
     *  Finds files according to this.pathMask and this.baseDir.
     */
    private List<File> findFilesForPattern() throws IOException {
        if (this.pathMask == null)
            throw new IllegalStateException("pathMask is null in " + this.toDescription());

        List<File> files = new DirScanner(this.pathMask).listAsFiles(this.baseDir);
        return files;
    }

    /**
     *  If $src is defined, returns that. Else returns findFilesForPattern().
     */
    public List<File> getFiles() throws IOException {
        if (this.src != null)
            return Arrays.asList(this.src);
        else if (this.pathMask != null)
            return findFilesForPattern();
        else
            return Collections.EMPTY_LIST;
    }

}