All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.atlassian.bamboo.specs.codegen.BambooSpecsGenerator Maven / Gradle / Ivy

There is a newer version: 6.8.1
Show newest version
package com.atlassian.bamboo.specs.codegen;

import com.atlassian.bamboo.specs.api.BambooSpec;
import com.atlassian.bamboo.specs.api.codegen.CodeEmitter;
import com.atlassian.bamboo.specs.api.codegen.CodeGenerationContext;
import com.atlassian.bamboo.specs.api.codegen.CodeGenerationException;
import com.atlassian.bamboo.specs.api.exceptions.PropertiesValidationException;
import com.atlassian.bamboo.specs.api.model.EntityProperties;
import com.atlassian.bamboo.specs.api.validators.common.ImporterUtils;
import com.atlassian.bamboo.specs.codegen.emitters.value.ValueEmitterFactory;
import com.atlassian.bamboo.specs.util.BambooServer;
import com.atlassian.bamboo.specs.util.BambooSpecProperties;
import com.atlassian.bamboo.specs.util.Yamlizator;
import org.jetbrains.annotations.NotNull;

import javax.annotation.concurrent.Immutable;
import java.io.File;
import java.io.FileInputStream;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Objects;

/**
 * Code generator for any Bamboo Spec entities, such us plan or deployment project.
 */
public class BambooSpecsGenerator {

    private final Map entityByName = new LinkedHashMap<>();
    private final CodeGenerationContext context = new CodeGenerationContext();

    public BambooSpecsGenerator() {
    }

    public BambooSpecsGenerator(final EntityProperties entityProperties) throws PropertiesValidationException {
        this();
        addEntity("rootObject", entityProperties);
    }


    public BambooSpecsGenerator addEntity(final String entityName, final EntityProperties entityProperties) throws PropertiesValidationException {
        ImporterUtils.checkNotNull("entity name", entityName);
        ImporterUtils.checkNotNull("entity", entityProperties);
        if (entityByName.putIfAbsent(entityName, entityProperties) != null) {
            throw new PropertiesValidationException(String.format("Entity with name %s already defined.", entityName));
        }
        return this;
    }

    private String buildCode(String url) throws CodeGenerationException {
        StringBuilder builder = new StringBuilder();
        //open class
        context.importClassName(BambooSpec.class);
        builder.append("@BambooSpec");
        builder.append(context.newLine());
        builder.append("public class PlanSpec {");
        context.incIndentation();
        builder.append(context.newLine());
        builder.append("public static void main(String... argv) {");
        context.incIndentation();
        builder.append(context.newLine());
        builder.append("//By default credentials are read from the '.credentials' file.").append(context.newLine());
        builder.append(context.importClassName(BambooServer.class))
                .append(" bambooServer = new BambooServer(\"")
                .append(url)
                .append("\");");

        for (final String entityName : entityByName.keySet()) {
            builder.append(context.newLine()).append(context.newLine());
            insertCode(builder, entityName, entityByName.get(entityName));
        }

        //close class
        context.decIndentation();
        builder.append(context.newLine());
        builder.append("}");
        context.decIndentation();
        builder.append(context.newLine());
        builder.append("}");

        return builder.toString();
    }


    private void insertCode(final StringBuilder builder,
                            final String entityName,
                            final EntityProperties entity) throws CodeGenerationException {

        if (entity instanceof Comment) {
            final Comment comment = (Comment)entity;
            if (comment.newLineBefore) {
                builder.append(context.newLine());
            }
            builder.append("// ").append(comment.comment);
            if (comment.newLineAfter) {
                builder.append(context.newLine());
            }
        } else {
            final CodeEmitter codeEmitter = ValueEmitterFactory.emitterFor(entity);

            final String entityCodeRightSide = codeEmitter.emitCode(context, entity);
            builder.append(context.importClassName(BuilderClassProvider.findBuilderClass(entity.getClass())));
            builder.append(String.format(" %s = %s;", entityName, entityCodeRightSide));
            builder.append(context.newLine());
            builder.append(context.newLine());

            builder.append(String.format("bambooServer.publish(%s);", entityName));
        }

    }

    public String emitCode() throws CodeGenerationException {
        return emitCode("http://localhost:8085");
    }

    public String emitCode(@NotNull String bambooServerUrl) throws CodeGenerationException {
        String main = buildCode(bambooServerUrl);

        StringBuilder codeBuilder = new StringBuilder();
        //imports
        for (String anImport : context.getImports()) {
            codeBuilder.append("import ").append(anImport).append(";\n");
        }
        codeBuilder.append("\n");
        codeBuilder.append(main);
        return codeBuilder.toString();
    }

    /**
     * Represents a comment in Bamboo Specs.
     * Note: Only to be used with {@link BambooSpecsGenerator#addEntity(String, EntityProperties)}
     */
    @Immutable
    public static class Comment implements EntityProperties {

        private String comment;
        private boolean newLineBefore;
        private boolean newLineAfter;

        private Comment() {
        }

        public Comment(final String comment) {
            this(comment, true, true);
        }

        public Comment(final String comment, final boolean newLineBefore, final boolean newLineAfter) {
            this.comment = comment;
            this.newLineBefore = newLineBefore;
            this.newLineAfter = newLineAfter;
        }

        @Override
        public String toString() {
            return comment;
        }

        @Override
        public void validate() {
        }

        @Override
        public boolean equals(Object o) {
            if (this == o) return true;
            if (o == null || getClass() != o.getClass()) return false;
            Comment comment1 = (Comment) o;
            return newLineBefore == comment1.newLineBefore &&
                    newLineAfter == comment1.newLineAfter &&
                    Objects.equals(comment, comment1.comment);
        }

        @Override
        public int hashCode() {
            return Objects.hash(comment, newLineBefore, newLineAfter);
        }
    }

    public static void main(String... argv) {
        if (argv.length < 1) {
            System.out.println("File argument missing");
            return;
        }
        String filePath = argv[0];
        try {
            BambooSpecProperties o = (BambooSpecProperties) Yamlizator.getYaml().load(new FileInputStream(new File(filePath)));

            String javaCode = new BambooSpecsGenerator(o.getRootEntity()).emitCode();
            System.out.print(javaCode);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy