Bug 1517909 - Format build telemetry time correctly when seconds has no fractional component. r=nalexander a=NPOTB
authorTed Mielczarek <ted@mielczarek.org>
Tue, 08 Jan 2019 21:29:26 +0000
changeset 509472 c4617240dec57c705301dad0044afb5b2a319a12
parent 509471 d5596809608eeb558c6327379e4c1b17829a08f7
child 509473 2d63cb7c2cccb8e0884a3ce2de06b43d9b6990ef
push id1905
push userffxbld-merge
push dateMon, 21 Jan 2019 12:33:13 +0000
treeherdermozilla-release@c2fca1944d8c [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersnalexander, NPOTB
bugs1517909
milestone65.0
Bug 1517909 - Format build telemetry time correctly when seconds has no fractional component. r=nalexander a=NPOTB It turns out that Python's `datetime.isoformat` method will leave off the fractional component of seconds if it would be all zeroes, but the voluptuous `Datetime` validator wants it to be present, so it's possible to hit an error if you run mach at exactly an integer second. This patch switches from `isoformat` to `strftime` with an explicit format string instead. Differential Revision: https://phabricator.services.mozilla.com/D15981
python/mach/mach/test/test_telemetry.py
python/mach/mach/test/zero_microseconds.py
python/mozbuild/mozbuild/telemetry.py
--- a/python/mach/mach/test/test_telemetry.py
+++ b/python/mach/mach/test/test_telemetry.py
@@ -135,10 +135,17 @@ def test_registrar_dispatch(run_mach):
     # from within the same interpreter as the `mach python` command.
     data = run_mach('python', '--exec-file',
                     os.path.join(os.path.dirname(__file__), 'registrar_dispatch.py'))
     assert len(data) == 1
     d = data[0]
     assert d['command'] == 'python'
 
 
+def test_zero_microseconds(run_mach):
+    data = run_mach('python', '--exec-file',
+                    os.path.join(os.path.dirname(__file__), 'zero_microseconds.py'))
+    d = data[0]
+    assert d['command'] == 'python'
+
+
 if __name__ == '__main__':
     mozunit.main()
new file mode 100644
--- /dev/null
+++ b/python/mach/mach/test/zero_microseconds.py
@@ -0,0 +1,14 @@
+# This code is loaded via `mach python --exec-file`, so it runs in the scope of
+# the `mach python` command.
+old = self._mach_context.post_dispatch_handler  # noqa: F821
+
+
+def handler(context, handler, instance, result,
+            start_time, end_time, depth, args):
+    global old
+    # Round off sub-second precision.
+    old(context, handler, instance, result,
+        int(start_time), end_time, depth, args)
+
+
+self._mach_context.post_dispatch_handler = handler  # noqa: F821
--- a/python/mozbuild/mozbuild/telemetry.py
+++ b/python/mozbuild/mozbuild/telemetry.py
@@ -251,18 +251,18 @@ def gather_telemetry(command='', success
     `paths` is a dict whose keys are pathnames and values are sigils that should be used to
     replace those pathnames.
 
     Any absolute paths on the command line will be made relative to `paths` or replaced
     with a placeholder to avoid including paths from developer's machines.
     '''
     data = {
         'client_id': get_client_id(mach_context.state_dir),
-        # Simplest way to get an rfc3339 datetime string, AFAICT.
-        'time': datetime.utcfromtimestamp(start_time).isoformat(b'T') + 'Z',
+        # Get an rfc3339 datetime string.
+        'time': datetime.utcfromtimestamp(start_time).strftime('%Y-%m-%dT%H:%M:%S.%fZ'),
         'command': command,
         'argv': filter_args(command, sys.argv, paths),
         'success': success,
         # TODO: use a monotonic clock: https://bugzilla.mozilla.org/show_bug.cgi?id=1481624
         'duration_ms': int((end_time - start_time) * 1000),
         'build_opts': get_build_opts(substs),
         'system': get_system_info(),
         # TODO: exception: https://bugzilla.mozilla.org/show_bug.cgi?id=1481617