poussecafe.doc.model.DomainProcessStepsFactory Maven / Gradle / Ivy
package poussecafe.doc.model;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Optional;
import java.util.Set;
import poussecafe.doc.model.boundedcontextdoc.BoundedContextDocId;
import poussecafe.doc.model.domainprocessdoc.DomainProcessDoc;
import poussecafe.doc.model.domainprocessdoc.Step;
import poussecafe.doc.model.domainprocessdoc.StepName;
import poussecafe.doc.model.domainprocessdoc.ToStep;
import poussecafe.doc.model.processstepdoc.ProcessStepDoc;
import poussecafe.doc.model.processstepdoc.ProcessStepDocRepository;
import poussecafe.doc.model.processstepdoc.StepMethodSignature;
import poussecafe.domain.Service;
import static java.util.stream.Collectors.toList;
public class DomainProcessStepsFactory implements Service {
public DomainProcessSteps buildDomainProcessSteps(DomainProcessDoc domainProcessDoc) {
HashMap steps = new HashMap<>();
BoundedContextComponentDoc boundedContextComponentDoc = domainProcessDoc.attributes().boundedContextComponentDoc().value();
BoundedContextDocId boundedContextDocId = boundedContextComponentDoc.boundedContextDocId();
String processName = boundedContextComponentDoc.componentDoc().name();
HashMap> eventToStep = new HashMap<>();
List processStepDocs = messageListenerDocRepository.findByDomainProcess(boundedContextDocId, processName);
for(ProcessStepDoc processStepDoc : processStepDocs) {
Optional consumedEventName;
Optional optionalStepMethodSignature = processStepDoc.attributes().stepMethodSignature().value();
if(optionalStepMethodSignature.isPresent()) {
consumedEventName = optionalStepMethodSignature.get().consumedEventName();
} else {
consumedEventName = Optional.empty();
}
if(consumedEventName.isPresent()) {
String presentConsumedEventName = consumedEventName.get();
List signatures = eventToStep.get(presentConsumedEventName);
if(signatures == null) {
signatures = new ArrayList<>();
eventToStep.put(presentConsumedEventName, signatures);
}
signatures.add(processStepDoc.attributes().boundedContextComponentDoc().value().componentDoc().name());
}
}
for(ProcessStepDoc processStepDoc : processStepDocs) {
List toSteps = new ArrayList<>();
List tos = locateTos(processStepDoc, eventToStep);
toSteps.addAll(toDirectSteps(tos));
StepName currentStepName = new StepName(processStepDoc.attributes().boundedContextComponentDoc().value().componentDoc().name());
List toExternals = processStepDoc.attributes().toExternals().value().stream().map(StepName::new).collect(toList());
for(StepName toExternal : toExternals) {
Step toExternalStep = steps.get(toExternal);
if(toExternalStep == null) {
toExternalStep = new Step.Builder()
.componentDoc(new ComponentDoc.Builder()
.name(toExternal.stringValue())
.description("")
.build())
.external(true)
.build();
steps.put(toExternal, toExternalStep);
}
}
toSteps.addAll(toDirectSteps(toExternals));
String domainProcessName = domainProcessDoc.attributes().boundedContextComponentDoc().value().componentDoc().name();
List toDomainProcesses = otherDomainProcesses(boundedContextDocId, domainProcessName, processStepDoc.attributes().producedEvents().value());
for(StepName toDomainProcess : toDomainProcesses) {
Step toDomainProcessStep = steps.get(toDomainProcess);
if(toDomainProcessStep == null) {
toDomainProcessStep = new Step.Builder()
.componentDoc(new ComponentDoc.Builder()
.name(toDomainProcess.stringValue())
.description("")
.build())
.external(true)
.build();
steps.put(toDomainProcess, toDomainProcessStep);
}
}
toSteps.addAll(toDirectSteps(toDomainProcesses));
ComponentDoc processStepComponentDoc = processStepDoc.attributes().boundedContextComponentDoc().value().componentDoc();
steps.put(currentStepName, new Step.Builder()
.componentDoc(processStepComponentDoc)
.tos(toSteps)
.build());
List fromExternals = processStepDoc.attributes().fromExternals().value().stream().map(StepName::new).collect(toList());
ToStep additionalToStep = directStep(currentStepName);
for(StepName fromExternal : fromExternals) {
Step fromExternalStep = steps.get(fromExternal);
if(fromExternalStep == null) {
fromExternalStep = new Step.Builder()
.componentDoc(new ComponentDoc.Builder()
.name(fromExternal.stringValue())
.description("")
.build())
.external(true)
.to(additionalToStep)
.build();
} else {
fromExternalStep = new Step.Builder()
.step(fromExternalStep)
.to(additionalToStep)
.build();
}
steps.put(fromExternal, fromExternalStep);
}
Optional stepMethodSignature = processStepDoc.attributes().stepMethodSignature().value();
Optional consumedEvent = Optional.empty();
if(stepMethodSignature.isPresent()) {
consumedEvent = stepMethodSignature.get().consumedEventName();
}
List fromDomainProcesses = fromDomainProcesses(boundedContextDocId, domainProcessName, consumedEvent);
for(StepName fromDomainProcess : fromDomainProcesses) {
Step fromDomainProcessStep = steps.get(fromDomainProcess);
if(fromDomainProcessStep == null) {
fromDomainProcessStep = new Step.Builder()
.componentDoc(new ComponentDoc.Builder()
.name(fromDomainProcess.stringValue())
.description("")
.build())
.external(true)
.to(additionalToStep)
.build();
} else {
fromDomainProcessStep = new Step.Builder()
.step(fromDomainProcessStep)
.to(additionalToStep)
.build();
}
steps.put(fromDomainProcess, fromDomainProcessStep);
}
}
return new DomainProcessSteps(steps);
}
private ProcessStepDocRepository messageListenerDocRepository;
private List locateTos(ProcessStepDoc stepDoc,
HashMap> eventToStep) {
List tos = new ArrayList<>();
for(String producedEvent : stepDoc.attributes().producedEvents()) {
List signatures = eventToStep.get(producedEvent);
if(signatures != null) {
tos.addAll(signatures.stream().map(StepName::new).collect(toList()));
}
}
return tos;
}
private List toDirectSteps(List tos) {
List toSteps = new ArrayList<>();
for(StepName to : tos) {
toSteps.add(directStep(to));
}
return toSteps;
}
private ToStep directStep(StepName to) {
return new ToStep.Builder()
.name(to)
.directly(true)
.build();
}
private List otherDomainProcesses(BoundedContextDocId boundedContextDocId,
String domainProcessName,
Set producedEvents) {
Set otherDomainProcesses = new HashSet<>();
for(String producedEvent : producedEvents) {
for(ProcessStepDoc stepDoc : messageListenerDocRepository.findConsuming(boundedContextDocId, producedEvent)) {
Optional processName = stepDoc.attributes().processName().value();
if(processName.isPresent() && !domainProcessName.equals(processName.get())) {
otherDomainProcesses.add(processName.get());
}
}
}
return otherDomainProcesses.stream()
.map(StepName::new)
.collect(toList());
}
private List fromDomainProcesses(BoundedContextDocId boundedContextDocId,
String domainProcessName,
Optional consumedEvent) {
Set otherDomainProcesses = new HashSet<>();
if(consumedEvent.isPresent()) {
List stepsproducingEvent = messageListenerDocRepository.findProducing(boundedContextDocId, consumedEvent.get());
for(ProcessStepDoc stepDoc : stepsproducingEvent) {
Optional processName = stepDoc.attributes().processName().value();
if(processName.isPresent() && !domainProcessName.equals(processName.get())) {
otherDomainProcesses.add(processName.get());
}
}
}
return otherDomainProcesses.stream()
.map(StepName::new)
.collect(toList());
}
}