[StreamingAlgorithms] result() returns None if data is missing
Make StreamingAlgorithm.result() returning None instead of raising RallyException in case if no (or not enough) data has been processed. This change was discussed at Dec' 21st on Rally weekly meeting. Change-Id: I5c1eec47a0e190ec6ccd351b0c3bd866f4544b35
This commit is contained in:
parent
d188a5ba3b
commit
339adba2a9
@ -18,8 +18,6 @@ import math
|
||||
|
||||
import six
|
||||
|
||||
from rally.common.i18n import _
|
||||
from rally import exceptions
|
||||
from rally.task.processing import utils
|
||||
|
||||
|
||||
@ -62,11 +60,9 @@ class MeanComputation(StreamingAlgorithm):
|
||||
self.total += other.total
|
||||
|
||||
def result(self):
|
||||
if self.count == 0:
|
||||
message = _("Unable to calculate the mean: "
|
||||
"no values processed so far.")
|
||||
raise exceptions.RallyException(message)
|
||||
return self.total / self.count
|
||||
if self.count:
|
||||
return self.total / self.count
|
||||
return None
|
||||
|
||||
|
||||
class StdDevComputation(StreamingAlgorithm):
|
||||
@ -90,6 +86,8 @@ class StdDevComputation(StreamingAlgorithm):
|
||||
self.dev_sum = self.dev_sum + (value - mean_prev) * (value - self.mean)
|
||||
|
||||
def merge(self, other):
|
||||
if not other.mean_computation.count:
|
||||
return
|
||||
dev_sum1 = self.dev_sum
|
||||
count1 = self.count
|
||||
mean1 = self.mean
|
||||
@ -107,10 +105,9 @@ class StdDevComputation(StreamingAlgorithm):
|
||||
self.count * self.mean ** 2)
|
||||
|
||||
def result(self):
|
||||
# NOTE(amaretskiy): Need at least two values to be processed
|
||||
if self.count < 2:
|
||||
message = _("Unable to calculate the standard deviation: "
|
||||
"need at least two values to be processed.")
|
||||
raise exceptions.RallyException(message)
|
||||
return None
|
||||
return math.sqrt(self.dev_sum / (self.count - 1))
|
||||
|
||||
|
||||
@ -131,9 +128,6 @@ class MinComputation(StreamingAlgorithm):
|
||||
self.add(other._value)
|
||||
|
||||
def result(self):
|
||||
if self._value is None:
|
||||
raise exceptions.RallyException(
|
||||
_("No values have been processed"))
|
||||
return self._value
|
||||
|
||||
|
||||
@ -154,9 +148,6 @@ class MaxComputation(StreamingAlgorithm):
|
||||
self.add(other._value)
|
||||
|
||||
def result(self):
|
||||
if self._value is None:
|
||||
raise exceptions.RallyException(
|
||||
_("No values have been processed"))
|
||||
return self._value
|
||||
|
||||
|
||||
@ -185,10 +176,9 @@ class PercentileComputation(StreamingAlgorithm):
|
||||
def result(self):
|
||||
results = list(
|
||||
map(lambda x: x[1], self._graph_zipper.get_zipped_graph()))
|
||||
if not results:
|
||||
raise exceptions.RallyException(
|
||||
_("No values have been processed"))
|
||||
return utils.percentile(results, self._percent)
|
||||
if results:
|
||||
return utils.percentile(results, self._percent)
|
||||
return None
|
||||
|
||||
|
||||
class IncrementComputation(StreamingAlgorithm):
|
||||
|
@ -44,7 +44,7 @@ class MaxAverageDuration(sla.SLA):
|
||||
|
||||
def merge(self, other):
|
||||
self.avg_comp.merge(other.avg_comp)
|
||||
self.avg = self.avg_comp.result()
|
||||
self.avg = self.avg_comp.result() or 0.0
|
||||
self.success = self.avg <= self.criterion_value
|
||||
return self.success
|
||||
|
||||
|
@ -21,7 +21,6 @@ import six
|
||||
|
||||
from rally.common import costilius
|
||||
from rally.common import streaming_algorithms as streaming
|
||||
from rally import exceptions
|
||||
from rally.task.processing import utils
|
||||
|
||||
|
||||
@ -324,10 +323,7 @@ class MainStatsTable(Chart):
|
||||
for i in range(len(self.table)):
|
||||
row = [self.table[i][0][1]]
|
||||
# no results if all iterations failed
|
||||
try:
|
||||
no_result = self.table[i][-2][1].result() == 0.0
|
||||
except exceptions.RallyException:
|
||||
no_result = True
|
||||
no_result = not self.table[i][-2][1].result()
|
||||
row.extend(x[2](x[1], no_result) for x in self.table[i][1:])
|
||||
rows.append(row)
|
||||
|
||||
|
@ -19,7 +19,6 @@ import ddt
|
||||
import six
|
||||
|
||||
from rally.common import streaming_algorithms as algo
|
||||
from rally import exceptions
|
||||
from tests.unit import test
|
||||
|
||||
|
||||
@ -27,7 +26,7 @@ class MeanComputationTestCase(test.TestCase):
|
||||
|
||||
def test_empty_stream(self):
|
||||
mean_computation = algo.MeanComputation()
|
||||
self.assertRaises(exceptions.RallyException, mean_computation.result)
|
||||
self.assertIsNone(mean_computation.result())
|
||||
|
||||
def test_one_value(self):
|
||||
mean_computation = algo.MeanComputation()
|
||||
@ -68,12 +67,12 @@ class StdDevComputationTestCase(test.TestCase):
|
||||
|
||||
def test_empty_stream(self):
|
||||
std_computation = algo.StdDevComputation()
|
||||
self.assertRaises(exceptions.RallyException, std_computation.result)
|
||||
self.assertIsNone(std_computation.result())
|
||||
|
||||
def test_one_value(self):
|
||||
std_computation = algo.StdDevComputation()
|
||||
std_computation.add(10.0)
|
||||
self.assertRaises(exceptions.RallyException, std_computation.result)
|
||||
self.assertIsNone(std_computation.result())
|
||||
|
||||
def test_two_values(self):
|
||||
std_computation = algo.StdDevComputation()
|
||||
@ -127,10 +126,10 @@ class MinComputationTestCase(test.TestCase):
|
||||
self.assertRaises(TypeError, comp.add, None)
|
||||
self.assertRaises(TypeError, comp.add, "str")
|
||||
|
||||
def test_result_raises(self):
|
||||
def test_result_empty(self):
|
||||
comp = algo.MinComputation()
|
||||
self.assertRaises(TypeError, comp.result, 1)
|
||||
self.assertRaises(exceptions.RallyException, comp.result)
|
||||
self.assertIsNone(comp.result())
|
||||
|
||||
def test_merge(self):
|
||||
single_min_algo = algo.MinComputation()
|
||||
@ -166,10 +165,10 @@ class MaxComputationTestCase(test.TestCase):
|
||||
self.assertRaises(TypeError, comp.add, None)
|
||||
self.assertRaises(TypeError, comp.add, "str")
|
||||
|
||||
def test_result_raises(self):
|
||||
def test_result_empty(self):
|
||||
comp = algo.MaxComputation()
|
||||
self.assertRaises(TypeError, comp.result, 1)
|
||||
self.assertRaises(exceptions.RallyException, comp.result)
|
||||
self.assertIsNone(comp.result())
|
||||
|
||||
def test_merge(self):
|
||||
single_max_algo = algo.MaxComputation()
|
||||
@ -241,10 +240,10 @@ class PercentileComputationTestCase(test.TestCase):
|
||||
comp = algo.PercentileComputation(0.50, 100)
|
||||
self.assertRaises(TypeError, comp.add)
|
||||
|
||||
def test_result_raises(self):
|
||||
def test_result_empty(self):
|
||||
self.assertRaises(TypeError, algo.PercentileComputation)
|
||||
comp = algo.PercentileComputation(0.50, 100)
|
||||
self.assertRaises(exceptions.RallyException, comp.result)
|
||||
self.assertIsNone(comp.result())
|
||||
|
||||
|
||||
class IncrementComputationTestCase(test.TestCase):
|
||||
|
Loading…
Reference in New Issue
Block a user