
com.atlassian.bamboo.specs.codegen.BambooSpecsGenerator Maven / Gradle / Ivy
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