Skip to content
This repository has been archived by the owner on Oct 19, 2023. It is now read-only.

Commit

Permalink
Handle time conversion between OT and OTel
Browse files Browse the repository at this point in the history
Handle time format differences between OpenTracing and OpenTelemetry.
OpenTracing expects time values in seconds since the epoch represented
as floats. OpenTelemetry expects time values in nanoseconds since the
epoch represented as ints.
  • Loading branch information
johananl committed Oct 7, 2019
1 parent 4de4324 commit e60e605
Show file tree
Hide file tree
Showing 4 changed files with 67 additions and 9 deletions.
20 changes: 13 additions & 7 deletions opentracing-shim/src/opentracingshim/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,12 +61,11 @@ def set_operation_name(self, operation_name):
self._otel_span.update_name(operation_name)
return self

def finish(self, finish_time=None):
self._otel_span.end()
# TODO: Handle finish_time. The OpenTelemetry API doesn't currently
# support setting end time on a span and we cannot assume that all
# OpenTelemetry Tracer implementations have an `end_time` field.
# https://github.com/open-telemetry/opentelemetry-python/issues/134
def finish(self, finish_time: float = None):
end_time = finish_time
if end_time is not None:
end_time = util.time_seconds_to_ns(finish_time)
self._otel_span.end(end_time=end_time)

def set_tag(self, key, value):
self._otel_span.set_attribute(key, value)
Expand Down Expand Up @@ -233,7 +232,14 @@ def start_span(
for key, value in tags.items():
span.set_attribute(key, value)

span.start(start_time=start_time)
# The OpenTracing API expects time values to be `float` values which
# represent the number of seconds since the epoch. OpenTelemetry
# represents time values as nanoseconds since the epoch.
start_time_ns = start_time
if start_time_ns is not None:
start_time_ns = util.time_seconds_to_ns(start_time)

span.start(start_time=start_time_ns)
context = SpanContextWrapper(span.get_context())
return SpanWrapper(self, context, span)

Expand Down
26 changes: 26 additions & 0 deletions opentracing-shim/src/opentracingshim/util.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,32 @@ def time_ns():
DEFAULT_EVENT_NAME = "log"


def time_seconds_to_ns(time_seconds: float) -> int:
"""Converts a time value in seconds to a time value in nanoseconds.
`time_seconds` is a `float` as returned by `time.time()` which represents
the number of seconds since the epoch.
The returned value is an `int` representing the number of nanoseconds since
the epoch.
"""

return int(time_seconds * 1e9)


def time_seconds_from_ns(time_nanoseconds: int) -> float:
"""Converts a time value in nanoseconds to a time value in seconds.
`time_nanoseconds` is an `int` representing the number of nanoseconds since
the epoch.
The returned value is a `float` representing the number of seconds since
the epoch.
"""

return time_nanoseconds / 1e9


def event_name_from_kv(key_values: dict) -> str:
"""A helper function which returns an event name from the given dict, or a
default event name.
Expand Down
17 changes: 15 additions & 2 deletions opentracing-shim/tests/test_shim.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,15 @@
# See the License for the specific language governing permissions and
# limitations under the License.

import time
import unittest

import opentracing

import opentracingshim
from opentelemetry import trace
from opentelemetry.sdk.trace import Tracer
from opentracingshim import util


class TestShim(unittest.TestCase):
Expand Down Expand Up @@ -112,9 +114,20 @@ def test_explicit_span_finish(self):
def test_explicit_start_time(self):
"""Test `start_time` argument."""

now = opentracingshim.util.time_ns()
now = time.time()
with self.shim.start_active_span("TestSpan", start_time=now) as scope:
self.assertEqual(scope.span.unwrap().start_time, now)
result = util.time_seconds_from_ns(scope.span.unwrap().start_time)
self.assertEqual(result, now)

def test_explicit_end_time(self):
"""Test `end_time` argument of `finish()` method."""

span = self.shim.start_span("TestSpan")
now = time.time()
span.finish(now)

end_time = util.time_seconds_from_ns(span.unwrap().end_time)
self.assertEqual(end_time, now)

def test_explicit_span_activation(self):
"""Test manual activation and deactivation of a span."""
Expand Down
13 changes: 13 additions & 0 deletions opentracing-shim/tests/test_util.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
# See the License for the specific language governing permissions and
# limitations under the License.

import time
import unittest

from opentracingshim import util
Expand All @@ -35,3 +36,15 @@ def test_event_name_from_kv(self):
# Test missing `event` field.
res = util.event_name_from_kv({"foo": "bar"})
self.assertEqual(res, util.DEFAULT_EVENT_NAME)

def test_time_seconds_to_ns(self):
time_seconds = time.time()
result = util.time_seconds_to_ns(time_seconds)

self.assertEqual(result, int(time_seconds * 1e9))

def test_time_seconds_from_ns(self):
time_nanoseconds = util.time_ns()
result = util.time_seconds_from_ns(time_nanoseconds)

self.assertEqual(result, time_nanoseconds / 1e9)

0 comments on commit e60e605

Please sign in to comment.