blob: e3801ad64f43bd6203ef760f14ad383c911a579e (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
|
package com.yahoo.search.dispatch;
import com.yahoo.search.result.Coverage;
import static com.yahoo.container.handler.Coverage.*;
/**
* Aggregates coverage as responses are added.
*
* @author baldersheim
*/
public class CoverageAggregator {
private final int askedNodes;
private int answeredNodes = 0;
private int answeredNodesParticipated = 0;
private int failedNodes = 0;
private long answeredDocs = 0;
private long answeredActiveDocs = 0;
private long answeredTargetActiveDocs = 0;
private boolean timedOut = false;
private boolean degradedByMatchPhase = false;
CoverageAggregator(int askedNodes) {
this.askedNodes = askedNodes;
}
CoverageAggregator(CoverageAggregator rhs) {
askedNodes = rhs.askedNodes;
answeredNodes = rhs.answeredNodes;
answeredNodesParticipated = rhs.answeredNodesParticipated;
failedNodes = rhs.failedNodes;
answeredDocs = rhs.answeredDocs;
answeredActiveDocs = rhs.answeredActiveDocs;
answeredTargetActiveDocs = rhs.answeredTargetActiveDocs;
timedOut = rhs.timedOut;
degradedByMatchPhase = rhs.degradedByMatchPhase;
}
void add(Coverage source) {
answeredDocs += source.getDocs();
answeredActiveDocs += source.getActive();
answeredTargetActiveDocs += source.getTargetActive();
answeredNodesParticipated += source.getNodes();
answeredNodes++;
degradedByMatchPhase |= source.isDegradedByMatchPhase();
timedOut |= source.isDegradedByTimeout();
}
public int getAskedNodes() {
return askedNodes;
}
public int getAnsweredNodes() {
return answeredNodes;
}
public boolean hasNoAnswers() { return answeredNodes == 0; }
public void setTimedOut() { timedOut = true; }
public void setFailedNodes(int failedNodes) {
this.failedNodes = failedNodes;
}
public Coverage createCoverage(TimeoutHandler timeoutHandler) {
Coverage coverage = new Coverage(answeredDocs, answeredActiveDocs, answeredNodesParticipated, 1);
coverage.setNodesTried(askedNodes);
coverage.setTargetActive(answeredTargetActiveDocs);
int degradedReason = 0;
if (timedOut) {
degradedReason |= timeoutHandler.reason();
}
if (degradedByMatchPhase) {
degradedReason |= DEGRADED_BY_MATCH_PHASE;
}
coverage.setDegradedReason(degradedReason);
return coverage;
}
public CoverageAggregator adjustedDegradedCoverage(int redundancy, TimeoutHandler timeoutHandler) {
int askedAndFailed = askedNodes + failedNodes;
if (askedAndFailed == answeredNodesParticipated) {
return this;
}
int notAnswered = askedAndFailed - answeredNodesParticipated;
if (timeoutHandler.reason() == DEGRADED_BY_ADAPTIVE_TIMEOUT) {
CoverageAggregator clone = new CoverageAggregator(this);
return clone.adjustActiveDocs(notAnswered);
} else {
if (askedAndFailed > answeredNodesParticipated) {
CoverageAggregator clone = new CoverageAggregator(this);
int missingNodes = notAnswered - (redundancy - 1);
if (missingNodes > 0) {
clone.adjustActiveDocs(missingNodes);
}
clone.timedOut = true;
return clone;
}
}
return this;
}
private CoverageAggregator adjustActiveDocs(int numMissingNodes) {
if (answeredNodesParticipated > 0) {
answeredActiveDocs += (numMissingNodes * answeredActiveDocs / answeredNodesParticipated);
answeredTargetActiveDocs += (numMissingNodes * answeredTargetActiveDocs / answeredNodesParticipated);
}
return this;
}
}
|