OLD | NEW |
1 # Copyright 2013 The Chromium Authors. All rights reserved. | 1 # Copyright 2013 The Chromium Authors. All rights reserved. |
2 # Use of this source code is governed by a BSD-style license that can be | 2 # Use of this source code is governed by a BSD-style license that can be |
3 # found in the LICENSE file. | 3 # found in the LICENSE file. |
4 | 4 |
5 # These tests access private methods in the speedindex module. | 5 # These tests access private methods in the speedindex module. |
6 # pylint: disable=W0212 | 6 # pylint: disable=W0212 |
7 | 7 |
8 import json | 8 import json |
9 import os | 9 import os |
10 import unittest | 10 import unittest |
11 | 11 |
12 from telemetry.core import bitmap | 12 from telemetry.core import bitmap |
13 from telemetry.timeline import inspector_timeline_data | |
14 from telemetry.timeline import model | 13 from telemetry.timeline import model |
| 14 from telemetry.value import trace as trace_value_module |
15 from metrics import speedindex | 15 from metrics import speedindex |
16 | 16 |
17 # Sample timeline data in the json format provided by devtools. | 17 # Sample timeline data in the json format provided by devtools. |
18 # The sample events will be used in several tests below. | 18 # The sample events will be used in several tests below. |
| 19 |
19 _TEST_DIR = os.path.join(os.path.dirname(__file__), 'unittest_data') | 20 _TEST_DIR = os.path.join(os.path.dirname(__file__), 'unittest_data') |
20 _SAMPLE_DATA = json.load(open(os.path.join(_TEST_DIR, 'sample_timeline.json'))) | 21 |
21 _SAMPLE_TIMELINE_DATA = inspector_timeline_data.InspectorTimelineData( | 22 def _GetSampleEvents(): |
22 _SAMPLE_DATA) | 23 with open(os.path.join(_TEST_DIR, 'sample_timeline.json') as f: |
23 _SAMPLE_EVENTS = model.TimelineModel( | 24 data = json.load(f) |
24 timeline_data=_SAMPLE_TIMELINE_DATA).GetAllEvents() | 25 builder = trace_value_module.TraceValueBuilder() |
| 26 builder.AddEventsTo(trace_value_module.INSPECTOR_TRACE_PART, data) |
| 27 model = model.TimelineModel(builder.AsValue()) |
| 28 return model.GetAllEvents() |
25 | 29 |
26 | 30 |
27 class FakeTimelineModel(object): | 31 class FakeTimelineModel(object): |
28 | 32 |
29 def __init__(self): | 33 def __init__(self): |
30 self._events = [] | 34 self._events = [] |
31 | 35 |
32 def SetAllEvents(self, events): | 36 def SetAllEventsOnFake(self, events): |
33 self._events = events | 37 self._events = events |
34 | 38 |
35 def GetAllEvents(self, recursive=True): | 39 def GetAllEvents(self, recursive=True): |
36 assert recursive == True | 40 assert recursive == True |
37 return self._events | 41 return self._events |
38 | 42 |
39 | 43 |
40 class FakeVideo(object): | 44 class FakeVideo(object): |
41 | 45 |
42 def __init__(self, frames): | 46 def __init__(self, frames): |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
87 | 91 |
88 def Highlight(self, _): | 92 def Highlight(self, _): |
89 pass | 93 pass |
90 | 94 |
91 | 95 |
92 class IncludedPaintEventsTest(unittest.TestCase): | 96 class IncludedPaintEventsTest(unittest.TestCase): |
93 def testNumberPaintEvents(self): | 97 def testNumberPaintEvents(self): |
94 impl = speedindex.PaintRectSpeedIndexImpl() | 98 impl = speedindex.PaintRectSpeedIndexImpl() |
95 # In the sample data, there's one event that occurs before the layout event, | 99 # In the sample data, there's one event that occurs before the layout event, |
96 # and one paint event that's not a leaf paint event. | 100 # and one paint event that's not a leaf paint event. |
97 events = impl._IncludedPaintEvents(_SAMPLE_EVENTS) | 101 events = impl._IncludedPaintEvents(_GetSampleEvents()) |
98 self.assertEqual(len(events), 5) | 102 self.assertEqual(len(events), 5) |
99 | 103 |
100 | 104 |
101 class SpeedIndexImplTest(unittest.TestCase): | 105 class SpeedIndexImplTest(unittest.TestCase): |
102 def testAdjustedAreaDict(self): | 106 def testAdjustedAreaDict(self): |
103 impl = speedindex.PaintRectSpeedIndexImpl() | 107 impl = speedindex.PaintRectSpeedIndexImpl() |
104 paint_events = impl._IncludedPaintEvents(_SAMPLE_EVENTS) | 108 paint_events = impl._IncludedPaintEvents(_GetSampleEvents()) |
105 viewport = 1000, 1000 | 109 viewport = 1000, 1000 |
106 time_area_dict = impl._TimeAreaDict(paint_events, viewport) | 110 time_area_dict = impl._TimeAreaDict(paint_events, viewport) |
107 self.assertEqual(len(time_area_dict), 4) | 111 self.assertEqual(len(time_area_dict), 4) |
108 # The event that ends at time 100 is a fullscreen; it's discounted by half. | 112 # The event that ends at time 100 is a fullscreen; it's discounted by half. |
109 self.assertEqual(time_area_dict[100], 500000) | 113 self.assertEqual(time_area_dict[100], 500000) |
110 self.assertEqual(time_area_dict[300], 100000) | 114 self.assertEqual(time_area_dict[300], 100000) |
111 self.assertEqual(time_area_dict[400], 200000) | 115 self.assertEqual(time_area_dict[400], 200000) |
112 self.assertEqual(time_area_dict[800], 200000) | 116 self.assertEqual(time_area_dict[800], 200000) |
113 | 117 |
114 def testVideoCompleteness(self): | 118 def testVideoCompleteness(self): |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
169 viewport = 1000, 1000 | 173 viewport = 1000, 1000 |
170 # Add up the parts of the speed index for each time interval. | 174 # Add up the parts of the speed index for each time interval. |
171 # Each part is the time interval multiplied by the proportion of the | 175 # Each part is the time interval multiplied by the proportion of the |
172 # total area value that is not yet painted for that interval. | 176 # total area value that is not yet painted for that interval. |
173 parts = [] | 177 parts = [] |
174 parts.append(100 * 1.0) | 178 parts.append(100 * 1.0) |
175 parts.append(200 * 0.5) | 179 parts.append(200 * 0.5) |
176 parts.append(100 * 0.4) | 180 parts.append(100 * 0.4) |
177 parts.append(400 * 0.2) | 181 parts.append(400 * 0.2) |
178 expected = sum(parts) # 330.0 | 182 expected = sum(parts) # 330.0 |
179 tab.timeline_model.SetAllEvents(_SAMPLE_EVENTS) | 183 tab.timeline_model.SetAllEventsOnFake(_GetSampleEvents()) |
180 tab.SetEvaluateJavaScriptResult(viewport) | 184 tab.SetEvaluateJavaScriptResult(viewport) |
181 actual = impl.CalculateSpeedIndex(tab) | 185 actual = impl.CalculateSpeedIndex(tab) |
182 self.assertEqual(actual, expected) | 186 self.assertEqual(actual, expected) |
183 | 187 |
184 | 188 |
185 class WPTComparisonTest(unittest.TestCase): | 189 class WPTComparisonTest(unittest.TestCase): |
186 """Compare the speed index results with results given by webpagetest.org. | 190 """Compare the speed index results with results given by webpagetest.org. |
187 | 191 |
188 Given the same timeline data, both this speedindex metric and webpagetest.org | 192 Given the same timeline data, both this speedindex metric and webpagetest.org |
189 should both return the same results. Fortunately, webpagetest.org also | 193 should both return the same results. Fortunately, webpagetest.org also |
190 provides timeline data in json format along with the speed index results. | 194 provides timeline data in json format along with the speed index results. |
191 """ | 195 """ |
192 | 196 |
193 def _TestJsonTimelineExpectation(self, filename, viewport, expected): | 197 def _TestJsonTimelineExpectation(self, filename, viewport, expected): |
194 """Check whether the result for some timeline data is as expected. | 198 """Check whether the result for some timeline data is as expected. |
195 | 199 |
196 Args: | 200 Args: |
197 filename: Filename of a json file which contains a | 201 filename: Filename of a json file which contains a |
198 expected: The result expected based on the WPT result. | 202 expected: The result expected based on the WPT result. |
199 """ | 203 """ |
200 tab = FakeTab() | 204 tab = FakeTab() |
201 impl = speedindex.PaintRectSpeedIndexImpl() | 205 impl = speedindex.PaintRectSpeedIndexImpl() |
202 file_path = os.path.join(_TEST_DIR, filename) | 206 file_path = os.path.join(_TEST_DIR, filename) |
203 with open(file_path) as json_file: | 207 with open(file_path) as json_file: |
204 raw_events = json.load(json_file) | 208 raw_events = json.load(json_file) |
205 timeline_data = inspector_timeline_data.InspectorTimelineData(raw_events) | 209 builder = trace_value_module.TraceValueBuilder() |
206 tab.timeline_model.SetAllEvents( | 210 builder.AddEventsTo(trace_value_module.INSPECTOR_TRACE_PART, raw_events) |
207 model.TimelineModel(timeline_data=timeline_data).GetAllEvents()) | 211 all_events = model.TimelineModel(builder.AsValue()).GetAllEvents() |
| 212 tab.timeline_model.SetAllEventsOnFake() |
208 tab.SetEvaluateJavaScriptResult(viewport) | 213 tab.SetEvaluateJavaScriptResult(viewport) |
209 actual = impl.CalculateSpeedIndex(tab) | 214 actual = impl.CalculateSpeedIndex(tab) |
210 # The result might differ by 1 or more milliseconds due to rounding, | 215 # The result might differ by 1 or more milliseconds due to rounding, |
211 # so compare to the nearest 10 milliseconds. | 216 # so compare to the nearest 10 milliseconds. |
212 self.assertAlmostEqual(actual, expected, places=-1) | 217 self.assertAlmostEqual(actual, expected, places=-1) |
213 | 218 |
214 def testCern(self): | 219 def testCern(self): |
215 # Page: http://info.cern.ch/hypertext/WWW/TheProject.html | 220 # Page: http://info.cern.ch/hypertext/WWW/TheProject.html |
216 # This page has only one paint event. | 221 # This page has only one paint event. |
217 self._TestJsonTimelineExpectation( | 222 self._TestJsonTimelineExpectation( |
218 'cern_repeat_timeline.json', (1014, 650), 379.0) | 223 'cern_repeat_timeline.json', (1014, 650), 379.0) |
219 | 224 |
220 def testBaidu(self): | 225 def testBaidu(self): |
221 # Page: http://www.baidu.com/ | 226 # Page: http://www.baidu.com/ |
222 # This page has several paint events, but no nested paint events. | 227 # This page has several paint events, but no nested paint events. |
223 self._TestJsonTimelineExpectation( | 228 self._TestJsonTimelineExpectation( |
224 'baidu_repeat_timeline.json', (1014, 650), 1761.43) | 229 'baidu_repeat_timeline.json', (1014, 650), 1761.43) |
225 | 230 |
226 def test2ch(self): | 231 def test2ch(self): |
227 # Page: http://2ch.net/ | 232 # Page: http://2ch.net/ |
228 # This page has several paint events, including nested paint events. | 233 # This page has several paint events, including nested paint events. |
229 self._TestJsonTimelineExpectation( | 234 self._TestJsonTimelineExpectation( |
230 '2ch_repeat_timeline.json', (997, 650), 674.58) | 235 '2ch_repeat_timeline.json', (997, 650), 674.58) |
231 | 236 |
232 | 237 |
233 if __name__ == "__main__": | 238 if __name__ == "__main__": |
234 unittest.main() | 239 unittest.main() |
OLD | NEW |