diff --git a/specification/trace/api.md b/specification/trace/api.md index 114326a4112..15280db3a9f 100644 --- a/specification/trace/api.md +++ b/specification/trace/api.md @@ -25,6 +25,7 @@ Table of Contents * [Set Status](#set-status) * [UpdateName](#updatename) * [End](#end) + * [Record Exception](#record-exception) * [Span lifetime](#span-lifetime) * [Status](#status) * [StatusCanonicalCode](#statuscanonicalcode) @@ -515,6 +516,19 @@ Parameters: This API MUST be non-blocking. +#### Record Exception + +To facilitate recording an exception languages SHOULD provide a +`RecordException` convenience method. The signature of the method is to be +determined by each language and can be overloaded as appropriate. The method +MUST record an exception as an `Event` with the conventions outlined in the +[exception semantic conventions](semantic_conventions/exceptions.md) document. + +Examples: + +- `RecordException(exception: Exception)` +- `RecordException(type: String, message: String, stacktrace: String)` + ### Span lifetime Span lifetime represents the process of recording the start and the end diff --git a/specification/trace/semantic_conventions/exceptions.md b/specification/trace/semantic_conventions/exceptions.md new file mode 100644 index 00000000000..daa204690a8 --- /dev/null +++ b/specification/trace/semantic_conventions/exceptions.md @@ -0,0 +1,58 @@ +# Semantic Conventions for Exceptions + +This document defines semantic conventions for recording application +exceptions. + + + +- [Recording an Exception](#recording-an-exception) +- [Attributes](#attributes) + - [Stacktrace Representation](#stacktrace-representation) + + + +## Recording an Exception + +An exception SHOULD be recorded as an `Event` on the span during which it occurred. +The name of the event MUST be `"exception"`. + +## Attributes + +The table below indicates which attributes should be added to the `Event` and +their types. + +| Attribute name | Type | Notes and examples | Required? | +| :------------------- | :----- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :--------------------------------------------------------- | +| exception.type | String | The type of the exception (its fully-qualified class name, if applicable). The dynamic type of the exception should be preferred over the static type in languages that support it. E.g. "java.net.ConnectException", "OSError" | One of `exception.type` or `exception.message` is required | +| exception.message | String | The exception message. E.g. `"Division by zero"`, `"Can't convert 'int' object to str implicitly"` | One of `exception.type` or `exception.message` is required | +| exception.stacktrace | String | A stacktrace as a string in the natural representation for the language runtime. The representation is to be determined and documented by each language SIG. E.g. `"Exception in thread \"main\" java.lang.RuntimeException: Test exception\n at com.example.GenerateTrace.methodB(GenerateTrace.java:13)\n at com.example.GenerateTrace.methodA(GenerateTrace.java:9)\n at com.example.GenerateTrace.main(GenerateTrace.java:5)"`. | No | + +### Stacktrace Representation + +The table below, adapted from [Google Cloud][gcp-error-reporting], includes +possible representations of stacktraces in various languages. The table is not +meant to be a recommendation for any particular language, although SIGs are free +to adopt them if they see fit. + +| Language | Format | +| ---------- | ------------------------------------------------------------------- | +| C# | the return value of [Exception.ToString()][csharp-stacktrace] | +| Go | the return value of [runtime.Stack][go-stacktrace] | +| Java | the contents of [Throwable.printStackTrace()][java-stacktrace] | +| Javascript | the return value of [error.stack][js-stacktrace] as returned by V8 | +| Python | the return value of [traceback.format_exc()][python-stacktrace] | +| Ruby | the result of [Exception.backtrace][ruby-stacktrace] joined by "\n" | + +Backends can use the language specified methodology for generating a stacktrace +combined with platform information from the +[telemetry sdk resource][telemetry-sdk-resource] in order to extract more fine +grained information from a stacktrace, if necessary. + +[gcp-error-reporting]: https://cloud.google.com/error-reporting/reference/rest/v1beta1/projects.events/report +[java-stacktrace]: https://docs.oracle.com/javase/7/docs/api/java/lang/Throwable.html#printStackTrace%28%29 +[python-stacktrace]: https://docs.python.org/3/library/traceback.html#traceback.format_exc +[js-stacktrace]: https://v8.dev/docs/stack-trace-api +[ruby-stacktrace]: https://ruby-doc.org/core-2.7.1/Exception.html#method-i-backtrace +[csharp-stacktrace]: https://docs.microsoft.com/en-us/dotnet/api/system.exception.tostring +[go-stacktrace]: https://golang.org/pkg/runtime/debug/#Stack +[telemetry-sdk-resource]: https://github.com/open-telemetry/opentelemetry-specification/tree/master/specification/resource/semantic_conventions#telemetry-sdk