package com.atlassian.bitbucket.mesh.git.builder.archive;

import com.atlassian.bitbucket.mesh.git.builder.AbstractGitProcessBuilder;
import com.atlassian.bitbucket.mesh.git.builder.GitProcessBuilder;

import javax.annotation.Nonnull;
import java.util.LinkedHashSet;
import java.util.Set;

import static java.util.Objects.requireNonNull;
import static org.apache.commons.lang3.StringUtils.trimToNull;

public class DefaultGitArchiveBuilder
        extends AbstractGitProcessBuilder<GitArchiveBuilder>
        implements GitArchiveBuilder {

    private final Set<String> paths;

    private GitArchiveFormat format;
    private String prefix;
    private String rev;

    public DefaultGitArchiveBuilder(GitProcessBuilder builder) {
        super(builder.command("archive"));

        paths = new LinkedHashSet<>();
        rev = "HEAD"; //Archive the default branch if no explicit rev is specified
    }

    @Nonnull
    @Override
    public GitArchiveBuilder clearPaths() {
        paths.clear();

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder format(GitArchiveFormat value) {
        format = value;

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder path(String value) {
        addIfNotBlank(paths, value);

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder paths(String value, String... values) {
        addIfNotBlank(paths, value, values);

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder paths(Iterable<String> values) {
        if (values != null) {
            addIfNotBlank(paths, values);
        }

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder prefix(String value) {
        prefix = trimToNull(value);

        return self();
    }

    @Nonnull
    @Override
    public GitArchiveBuilder rev(@Nonnull String value) {
        rev = requireNonNull(value, "rev");

        return self();
    }

    @Override
    protected void applyArguments() {
        if (format != null) {
            builder.argument("--format=" + format.getExtension());
        }
        if (prefix != null) {
            builder.argument("--prefix=" + prefix);
        }
        builder.argument("--") //Ensure the rev and paths are never treated as options
                .argument(rev);
        paths.forEach(builder::rawArgument);
    }

    @Nonnull
    @Override
    protected GitArchiveBuilder self() {
        return this;
    }
}
