Passed
Push — master ( 4bedd1...f49baa )
by Tomasz
03:35
created

dev.hltech.dredd.domain.validation.InterfaceContractValidator   A

Complexity

Total Complexity 11

Size/Duplication

Total Lines 144
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
eloc 89
c 1
b 0
f 1
dl 0
loc 144
rs 10
wmc 11

16 Methods

Rating   Name   Duplication   Size   Complexity  
A validateExpectations(E,ServiceContracts) 0 16 1
validate(E,C) 0 1 ?
A CapabilitiesValidationResult.isEmpty() 0 2 1
A validateExpectations(ServiceContracts,Collection) 0 6 1
A InteractionValidationResult.success(String) 0 2 1
asExpectations(String) 0 1 ?
A validateCapabilities(C,String,ServiceContracts) 0 10 1
A extractExpectations(ServiceContracts) 0 2 1
asCapabilities(String) 0 1 ?
A extractCapabilities(ServiceContracts) 0 2 1
A getCommunicationInterface() 0 2 1
A validateExpectations(E,String,Collection) 0 11 2
A validateCapabilities(ServiceContracts,Collection) 0 8 1
A InterfaceContractValidator(String) 0 2 1
A InteractionValidationResult.fail(String,List) 0 2 1
A createProviderNotAvailableResult(String) 0 5 1
1
package dev.hltech.dredd.domain.validation;
2
3
import dev.hltech.dredd.domain.contracts.ServiceContracts;
4
import lombok.AccessLevel;
5
import lombok.AllArgsConstructor;
6
import lombok.Getter;
7
8
import java.util.Collection;
9
import java.util.List;
10
import java.util.Map;
11
import java.util.Optional;
12
import java.util.stream.Stream;
13
14
import static com.google.common.collect.Lists.newArrayList;
15
import static dev.hltech.dredd.domain.validation.InterfaceContractValidator.InteractionValidationStatus.FAILED;
16
import static dev.hltech.dredd.domain.validation.InterfaceContractValidator.InteractionValidationStatus.OK;
17
import static java.util.Collections.emptyList;
18
import static java.util.stream.Collectors.toList;
19
20
public abstract class InterfaceContractValidator<C, E> {
21
22
    private String communicationInterface;
23
24
    public InterfaceContractValidator(String communicationInterface) {
25
        this.communicationInterface = communicationInterface;
26
    }
27
28
    public String getCommunicationInterface() {
29
        return this.communicationInterface;
30
    }
31
32
    public List<CapabilitiesValidationResult> validateCapabilities(ServiceContracts provider, Collection<ServiceContracts> allConsumers) {
33
        return extractCapabilities(provider)
34
            .map(capabilities -> allConsumers
35
                .stream()
36
                .map(consumer -> validateCapabilities(capabilities, provider.getName(), consumer))
37
                .filter(validationResult -> !validationResult.getInteractionValidationResults().isEmpty())
38
                .collect(toList())
39
            ).orElse(emptyList());
40
    }
41
42
    private CapabilitiesValidationResult validateCapabilities(C capabilities, String providerName, ServiceContracts consumer) {
43
        List<InteractionValidationResult> validatedInteractions = consumer
44
            .getMappedExpectations(providerName, this.communicationInterface, this::asExpectations)
45
            .map(expectations -> validate(expectations, capabilities))
46
            .orElse(emptyList());
47
48
        return new CapabilitiesValidationResult(
49
            consumer.getName(),
50
            consumer.getVersion(),
51
            validatedInteractions
52
        );
53
    }
54
55
    public List<ExpectationValidationResult> validateExpectations(ServiceContracts consumer, Collection<ServiceContracts> allProviders) {
56
        return extractExpectations(consumer)
57
            .entrySet()
58
            .stream()
59
            .flatMap(pe -> validateExpectations(pe.getValue(), pe.getKey(), allProviders))
60
            .collect(toList());
61
    }
62
63
    private Stream<? extends ExpectationValidationResult> validateExpectations(E expectations, String providerName, Collection<ServiceContracts> allProviders) {
64
        List<ServiceContracts> matchedProviders = allProviders
65
            .stream()
66
            .filter(it -> it.getName().equals(providerName))
67
            .collect(toList());
68
        if (matchedProviders.isEmpty()) {
69
            return Stream.of(createProviderNotAvailableResult(providerName));
70
        } else {
71
            return matchedProviders
72
                .stream()
73
                .map(matchedProvider -> validateExpectations(expectations, matchedProvider));
74
        }
75
    }
76
77
    private ExpectationValidationResult validateExpectations(E expectations, ServiceContracts provider) {
78
        List<InteractionValidationResult> validatedInteractions = provider
79
            .getMappedCapabilities(this.communicationInterface, this::asCapabilities)
80
            .map(capabilities -> validate(expectations, capabilities))
81
            .orElseGet(() -> newArrayList(
82
                new InteractionValidationResult(
83
                    "any",
84
                    FAILED,
85
                    newArrayList("provider was registered without any '" + this.communicationInterface + "' capabilities")
86
                )
87
            ));
88
89
        return new ExpectationValidationResult(
90
            provider.getName(),
91
            provider.getVersion(),
92
            validatedInteractions
93
        );
94
    }
95
96
    private ExpectationValidationResult createProviderNotAvailableResult(String providerName) {
97
        return new ExpectationValidationResult(
98
            providerName,
99
            null,
100
            newArrayList(new InteractionValidationResult("any", InteractionValidationStatus.FAILED, newArrayList("provider not available")))
101
        );
102
    }
103
104
    public Optional<C> extractCapabilities(ServiceContracts serviceContracts) {
105
        return serviceContracts.getMappedCapabilities(this.communicationInterface, this::asCapabilities);
106
    }
107
108
    public Map<String, E> extractExpectations(ServiceContracts testedServiceContracts) {
109
        return testedServiceContracts.getMappedExpectations(this.communicationInterface, this::asExpectations);
110
    }
111
112
    public abstract C asCapabilities(String rawCapabilities);
113
114
    public abstract E asExpectations(String rawExpectations);
115
116
    public abstract List<InteractionValidationResult> validate(E expectations, C capabilities);
117
118
    public enum InteractionValidationStatus {
119
120
        OK,
121
        FAILED
122
123
    }
124
125
    @Getter
126
    @AllArgsConstructor
127
    public static class CapabilitiesValidationResult {
128
129
        private String consumerName;
130
        private String consumerVersion;
131
        private List<InteractionValidationResult> interactionValidationResults;
132
133
        public boolean isEmpty() {
134
            return this.interactionValidationResults.isEmpty();
135
        }
136
137
    }
138
139
    @Getter
140
    @AllArgsConstructor
141
    public static class ExpectationValidationResult {
142
143
        private String providerName;
144
        private String providerVersion;
145
146
        private List<InteractionValidationResult> interactionValidationResults;
147
148
    }
149
150
    @Getter
151
    @AllArgsConstructor(access = AccessLevel.PRIVATE)
152
    public static class InteractionValidationResult {
153
154
        private final String name;
155
        private final InteractionValidationStatus status;
156
        private final List<String> errors;
157
158
        public static InteractionValidationResult success(String name) {
159
            return new InteractionValidationResult(name, OK, newArrayList());
160
        }
161
162
        public static InteractionValidationResult fail(String name, List<String> errors) {
163
            return new InteractionValidationResult(name, FAILED, errors);
164
        }
165
    }
166
}
167