1# Copyright 2018 The Chromium Authors. All rights reserved.
2# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4import datetime
5
6from tracing.value.diagnostics import diagnostic
7
8
9class DateRange(diagnostic.Diagnostic):
10  __slots__ = '_range',
11
12  def __init__(self, ms):
13    from tracing.value import histogram
14    super(DateRange, self).__init__()
15    self._range = histogram.Range()
16    self._range.AddValue(ms)
17
18  def __eq__(self, other):
19    if not isinstance(other, DateRange):
20      return False
21    return self._range == other._range
22
23  def __hash__(self):
24    return id(self)
25
26  @property
27  def min_date(self):
28    return datetime.datetime.utcfromtimestamp(self._range.min / 1000)
29
30  @property
31  def max_date(self):
32    return datetime.datetime.utcfromtimestamp(self._range.max / 1000)
33
34  @property
35  def min_timestamp(self):
36    return self._range.min
37
38  @property
39  def max_timestamp(self):
40    return self._range.max
41
42  @property
43  def duration_ms(self):
44    return self._range.duration
45
46  def __str__(self):
47    min_date = self.min_date.isoformat().replace('T', ' ')[:19]
48    if self.duration_ms == 0:
49      return min_date
50    max_date = self.max_date.isoformat().replace('T', ' ')[:19]
51    return min_date + ' - ' + max_date
52
53  def _AsDictInto(self, dct):
54    dct['min'] = self._range.min
55    if self.duration_ms == 0:
56      return
57    dct['max'] = self._range.max
58
59  def _AsProto(self):
60    raise NotImplementedError()
61
62  def Serialize(self, unused_serializer):
63    if self.duration_ms == 0:
64      return self._range.min
65    return [self._range.min, self._range.max]
66
67  @staticmethod
68  def Deserialize(data, unused_deserializer):
69    if isinstance(data, list):
70      dr = DateRange(data[0])
71      dr._range.AddValue(data[1])
72      return dr
73    return DateRange(data)
74
75  @staticmethod
76  def FromDict(dct):
77    dr = DateRange(dct['min'])
78    if 'max' in dct:
79      dr._range.AddValue(dct['max'])
80    return dr
81
82  @staticmethod
83  def FromProto(d):
84    raise NotImplementedError()
85
86  def CanAddDiagnostic(self, other_diagnostic):
87    return isinstance(other_diagnostic, DateRange)
88
89  def AddDiagnostic(self, other_diagnostic):
90    self._range.AddRange(other_diagnostic._range)
91
92