use of io.automatiko.engine.workflow.compiler.canonical.UserTaskModelMetaData in project automatiko-engine by automatiko-io.
the class AbstractResourceGenerator method generateCompilationUnit.
public CompilationUnit generateCompilationUnit() {
CompilationUnit clazz = parse(this.getClass().getResourceAsStream(getResourceTemplate()));
clazz.setPackageDeclaration(process.getPackageName());
clazz.addImport(modelfqcn);
ClassOrInterfaceDeclaration template = clazz.findFirst(ClassOrInterfaceDeclaration.class).orElseThrow(() -> new NoSuchElementException("Compilation unit doesn't contain a class or interface declaration!"));
template.setName(resourceClazzName);
AtomicInteger index = new AtomicInteger(0);
AtomicInteger uindex = new AtomicInteger(0);
// Generate signals endpoints
Optional.ofNullable(signals).ifPresent(signalsMap -> {
// using template class to the endpoints generation
CompilationUnit signalClazz = parse(this.getClass().getResourceAsStream(getSignalResourceTemplate()));
ClassOrInterfaceDeclaration signalTemplate = signalClazz.findFirst(ClassOrInterfaceDeclaration.class).orElseThrow(() -> new NoSuchElementException("SignalResourceTemplate class not found!"));
signalsMap.entrySet().stream().filter(e -> Objects.nonNull(e.getKey())).forEach(entry -> {
String signalName = entry.getKey();
String signalType = entry.getValue();
String methodName = sanitizeName(signalName) + "_" + index.getAndIncrement();
signalTemplate.findAll(MethodDeclaration.class).forEach(md -> {
MethodDeclaration cloned = md.clone();
BlockStmt body = cloned.getBody().get();
if (signalType == null) {
body.findAll(NameExpr.class, nameExpr -> "data".equals(nameExpr.getNameAsString())).forEach(name -> name.replace(new NullLiteralExpr()));
}
template.addMethod(cloned.getNameAsString() + "_" + methodName, Keyword.PUBLIC).setType(cloned.getType()).setParameters(signalType == null ? removeLastParam(cloned) : cloned.getParameters()).setBody(body).setAnnotations(cloned.getAnnotations());
});
if (signalType != null) {
template.findAll(ClassOrInterfaceType.class).forEach(name -> {
String identifier = name.getNameAsString();
name.setName(identifier.replace("$signalType$", signalType));
});
}
template.findAll(StringLiteralExpr.class).forEach(vv -> {
String s = vv.getValue();
String interpolated = s.replace("$signalName$", signalName);
interpolated = interpolated.replace("$signalPath$", sanitizeName(signalName));
vv.setString(interpolated);
});
});
});
if (userTasks != null) {
CompilationUnit userTaskClazz = parse(this.getClass().getResourceAsStream(getUserTaskResourceTemplate()));
ClassOrInterfaceDeclaration userTaskTemplate = userTaskClazz.findFirst(ClassOrInterfaceDeclaration.class).orElseThrow(() -> new NoSuchElementException("Compilation unit doesn't contain a class or interface declaration!"));
for (UserTaskModelMetaData userTask : userTasks) {
String methodSuffix = sanitizeName(userTask.getName()) + "_" + sanitizeName(processId) + "_" + uindex.getAndIncrement();
userTaskTemplate.findAll(MethodDeclaration.class).forEach(md -> {
MethodDeclaration cloned = md.clone();
template.addMethod(cloned.getName() + "_" + methodSuffix, Keyword.PUBLIC).setType(cloned.getType()).setParameters(cloned.getParameters()).setBody(cloned.getBody().get()).setAnnotations(cloned.getAnnotations());
});
template.findAll(StringLiteralExpr.class).forEach(s -> interpolateUserTaskStrings(s, userTask));
template.findAll(ClassOrInterfaceType.class).forEach(c -> interpolateUserTaskTypes(c, userTask.getInputModelClassSimpleName(), userTask.getOutputModelClassSimpleName()));
template.findAll(NameExpr.class).forEach(c -> interpolateUserTaskNameExp(c, userTask));
if (!userTask.isAdHoc()) {
template.findAll(MethodDeclaration.class).stream().filter(md -> md.getNameAsString().equals("signal_" + methodSuffix)).collect(Collectors.toList()).forEach(template::remove);
}
}
}
template.findAll(StringLiteralExpr.class).forEach(this::interpolateStrings);
Map<String, String> typeInterpolations = new HashMap<>();
typeInterpolations.put("$Clazz$", resourceClazzName);
typeInterpolations.put("$Type$", dataClazzName);
template.findAll(ClassOrInterfaceType.class).forEach(cls -> interpolateTypes(cls, typeInterpolations));
template.findAll(MethodDeclaration.class).forEach(this::interpolateMethods);
template.findAll(ConstructorDeclaration.class).forEach(this::interpolateConstructor);
template.findAll(FieldDeclaration.class).forEach(this::interpolateFields);
template.findAll(NameExpr.class).forEach(this::interpolateVariables);
template.findAll(MethodCallExpr.class).forEach(this::interpolateMethodCall);
if (useInjection()) {
template.findAll(FieldDeclaration.class, CodegenUtils::isProcessField).stream().filter(fd -> fd.getVariable(0).getNameAsString().startsWith("subprocess_")).forEach(fd -> annotator.withNamedInjection(fd, processId + version));
//
// template.findAll(FieldDeclaration.class, CodegenUtils::isApplicationField)
// .forEach(fd -> annotator.withInjection(fd));
// template.findAll(FieldDeclaration.class, CodegenUtils::isIdentitySupplierField)
// .forEach(fd -> annotator.withInjection(fd));
boolean tracingAvailable = context.getBuildContext().hasClassAvailable("org.eclipse.microprofile.opentracing.Traced");
if (tracingAvailable) {
FieldDeclaration tracerField = new FieldDeclaration().addVariable(new VariableDeclarator(new ClassOrInterfaceType(null, "io.automatiko.engine.service.tracing.TracingAdds"), "tracer"));
annotator.withInjection(tracerField);
template.addMember(tracerField);
template.findAll(MethodDeclaration.class, md -> md.getNameAsString().equals("tracing")).forEach(md -> {
BlockStmt body = new BlockStmt();
body.addStatement(new MethodCallExpr(new NameExpr("tracer"), "addTags").addArgument(new NameExpr("intance")));
md.setBody(body);
});
}
} else {
template.findAll(FieldDeclaration.class, CodegenUtils::isProcessField).forEach(this::initializeProcessField);
template.findAll(FieldDeclaration.class, CodegenUtils::isApplicationField).forEach(this::initializeApplicationField);
}
// trigger to start process instances
if (!startable || !isPublic()) {
Optional<MethodDeclaration> createResourceMethod = template.findAll(MethodDeclaration.class).stream().filter(md -> md.getNameAsString().equals("create_" + processName)).findFirst();
createResourceMethod.ifPresent(template::remove);
}
for (AbstractResourceGenerator resourceGenerator : subprocesses) {
resourceGenerator.withPathPrefix(parentProcess == null ? pathPrefix : pathPrefix + "/" + processId + "/{id_" + processId + "}");
CompilationUnit subunit = resourceGenerator.generateCompilationUnit();
subunit.findFirst(ClassOrInterfaceDeclaration.class).get().findAll(MethodDeclaration.class).forEach(md -> {
MethodDeclaration cloned = md.clone();
interpolateMethodParams(cloned);
Optional<AnnotationExpr> pathAnotation = cloned.getAnnotationByName("Path");
if (pathAnotation.isPresent()) {
String v = pathAnotation.get().toString().replaceAll("\\{id", "#{id");
Matcher matcher = PatternConstants.PARAMETER_MATCHER.matcher(v);
while (matcher.find()) {
String paramName = matcher.group(1);
if (cloned.getParameterByName(paramName).isEmpty()) {
cloned.addParameter(new Parameter().setName(paramName).setType(String.class).addAnnotation(new SingleMemberAnnotationExpr(new Name("javax.ws.rs.PathParam"), new StringLiteralExpr(paramName))));
}
}
}
cloned.getParameters().sort(new Comparator<Parameter>() {
@Override
public int compare(Parameter o1, Parameter o2) {
if (o1.getAnnotations().isEmpty() && o1.getAnnotations().isEmpty()) {
return 0;
} else if (o1.getAnnotations().isEmpty() && !o1.getAnnotations().isEmpty()) {
return -1;
} else {
return 1;
}
}
});
template.addMember(cloned);
});
subunit.findFirst(ClassOrInterfaceDeclaration.class).get().findAll(FieldDeclaration.class).forEach(fd -> {
FieldDeclaration cloned = fd.clone();
template.addMember(cloned);
});
if (subunit.getPackageDeclaration().isPresent() && !subunit.getPackageDeclaration().get().getNameAsString().equals(clazz.getPackageDeclaration().get().getNameAsString())) {
clazz.addImport(subunit.getPackageDeclaration().get().getNameAsString(), false, true);
}
}
collectSubProcessModels(modelfqcn.substring(modelfqcn.lastIndexOf('.') + 1), template, subprocesses);
enableValidation(template);
securityAnnotated(template);
template.getMembers().sort(new BodyDeclarationComparator());
return clazz;
}
Aggregations