forked from open-telemetry/opentelemetry-python
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add initial overall structure and classes for logs sdk (open-telemetr…
- Loading branch information
1 parent
c7c249f
commit b41c6e3
Showing
3 changed files
with
283 additions
and
0 deletions.
There are no files selected for viewing
174 changes: 174 additions & 0 deletions
174
opentelemetry-sdk/src/opentelemetry/sdk/logs/__init__.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,174 @@ | ||
# Copyright The OpenTelemetry Authors | ||
# | ||
# Licensed under the Apache License, Version 2.0 (the "License"); | ||
# you may not use this file except in compliance with the License. | ||
# You may obtain a copy of the License at | ||
# | ||
# http://www.apache.org/licenses/LICENSE-2.0 | ||
# | ||
# Unless required by applicable law or agreed to in writing, software | ||
# distributed under the License is distributed on an "AS IS" BASIS, | ||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
# See the License for the specific language governing permissions and | ||
# limitations under the License. | ||
|
||
import abc | ||
import atexit | ||
from typing import Any, Optional | ||
|
||
from opentelemetry.sdk.logs.severity import SeverityNumber | ||
from opentelemetry.sdk.resources import Resource | ||
from opentelemetry.sdk.util.instrumentation import InstrumentationInfo | ||
from opentelemetry.trace.span import TraceFlags | ||
from opentelemetry.util.types import Attributes | ||
|
||
|
||
class LogRecord: | ||
"""A LogRecord instance represents an event being logged. | ||
LogRecord instances are created and emitted via `LogEmitter` | ||
every time something is logged. They contain all the information | ||
pertinent to the event being logged. | ||
""" | ||
|
||
def __init__( | ||
self, | ||
timestamp: Optional[int] = None, | ||
trace_id: Optional[int] = None, | ||
span_id: Optional[int] = None, | ||
trace_flags: Optional[TraceFlags] = None, | ||
severity_text: Optional[str] = None, | ||
severity_number: Optional[SeverityNumber] = None, | ||
name: Optional[str] = None, | ||
body: Optional[Any] = None, | ||
resource: Optional[Resource] = None, | ||
attributes: Optional[Attributes] = None, | ||
): | ||
self.timestamp = timestamp | ||
self.trace_id = trace_id | ||
self.span_id = span_id | ||
self.trace_flags = trace_flags | ||
self.severity_text = severity_text | ||
self.severity_number = severity_number | ||
self.name = name | ||
self.body = body | ||
self.resource = resource | ||
self.attributes = attributes | ||
|
||
def __eq__(self, other: object) -> bool: | ||
if not isinstance(other, LogRecord): | ||
return NotImplemented | ||
return self.__dict__ == other.__dict__ | ||
|
||
|
||
class LogData: | ||
"""Readable LogRecord data plus associated InstrumentationLibrary.""" | ||
|
||
def __init__( | ||
self, | ||
log_record: LogRecord, | ||
instrumentation_info: InstrumentationInfo, | ||
): | ||
self.log_record = log_record | ||
self.instrumentation_info = instrumentation_info | ||
|
||
|
||
class LogProcessor(abc.ABC): | ||
"""Interface to hook the log record emitting action. | ||
Log processors can be registered directly using | ||
:func:`LogEmitterProvider.add_log_processor` and they are invoked | ||
in the same order as they were registered. | ||
""" | ||
|
||
@abc.abstractmethod | ||
def emit(self, log_data: LogData): | ||
"""Emits the `LogData`""" | ||
|
||
@abc.abstractmethod | ||
def shutdown(self): | ||
"""Called when a :class:`opentelemetry.sdk.logs.LogEmitter` is shutdown""" | ||
|
||
@abc.abstractmethod | ||
def force_flush(self, timeout_millis: int = 30000): | ||
"""Export all the received logs to the configured Exporter that have not yet | ||
been exported. | ||
Args: | ||
timeout_millis: The maximum amount of time to wait for logs to be | ||
exported. | ||
Returns: | ||
False if the timeout is exceeded, True otherwise. | ||
""" | ||
|
||
|
||
class LogEmitter: | ||
# TODO: Add multi_log_processor | ||
def __init__( | ||
self, | ||
resource: Resource, | ||
instrumentation_info: InstrumentationInfo, | ||
): | ||
self._resource = resource | ||
self._instrumentation_info = instrumentation_info | ||
|
||
def emit(self, record: LogRecord): | ||
# TODO: multi_log_processor.emit | ||
pass | ||
|
||
def flush(self): | ||
# TODO: multi_log_processor.force_flush | ||
pass | ||
|
||
|
||
class LogEmitterProvider: | ||
# TODO: Add multi_log_processor | ||
def __init__( | ||
self, | ||
resource: Resource = Resource.create(), | ||
shutdown_on_exit: bool = True, | ||
): | ||
self._resource = resource | ||
self._at_exit_handler = None | ||
if shutdown_on_exit: | ||
self._at_exit_handler = atexit.register(self.shutdown) | ||
|
||
def get_log_emitter( | ||
self, | ||
instrumenting_module_name: str, | ||
instrumenting_module_verison: str = "", | ||
) -> LogEmitter: | ||
return LogEmitter( | ||
self._resource, | ||
InstrumentationInfo( | ||
instrumenting_module_name, instrumenting_module_verison | ||
), | ||
) | ||
|
||
def add_log_processor(self, log_processor: LogProcessor): | ||
"""Registers a new :class:`LogProcessor` for this `LogEmitterProvider` instance. | ||
The log processors are invoked in the same order they are registered. | ||
""" | ||
# TODO: multi_log_processor.add_log_processor. | ||
|
||
def shutdown(self): | ||
"""Shuts down the log processors.""" | ||
# TODO: multi_log_processor.shutdown | ||
if self._at_exit_handler is not None: | ||
atexit.unregister(self._at_exit_handler) | ||
self._at_exit_handler = None | ||
|
||
def force_flush(self, timeout_millis: int = 30000) -> bool: | ||
"""Force flush the log processors. | ||
Args: | ||
timeout_millis: The maximum amount of time to wait for logs to be | ||
exported. | ||
Returns: | ||
True if all the log processors flushes the logs within timeout, | ||
False otherwise. | ||
""" | ||
# TODO: multi_log_processor.force_flush |
53 changes: 53 additions & 0 deletions
53
opentelemetry-sdk/src/opentelemetry/sdk/logs/export/__init__.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,53 @@ | ||
# Copyright The OpenTelemetry Authors | ||
# | ||
# Licensed under the Apache License, Version 2.0 (the "License"); | ||
# you may not use this file except in compliance with the License. | ||
# You may obtain a copy of the License at | ||
# | ||
# http://www.apache.org/licenses/LICENSE-2.0 | ||
# | ||
# Unless required by applicable law or agreed to in writing, software | ||
# distributed under the License is distributed on an "AS IS" BASIS, | ||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
# See the License for the specific language governing permissions and | ||
# limitations under the License. | ||
|
||
import abc | ||
import enum | ||
from typing import Sequence | ||
|
||
from opentelemetry.sdk.logs import LogData | ||
|
||
|
||
class LogExportResult(enum.Enum): | ||
SUCCESS = 0 | ||
FAILURE = 1 | ||
|
||
|
||
class LogExporter(abc.ABC): | ||
"""Interface for exporting logs. | ||
Interface to be implemented by services that want to export logs received | ||
in their own format. | ||
To export data this MUST be registered to the :class`opentelemetry.sdk.logs.LogEmitter` using a | ||
log processor. | ||
""" | ||
|
||
@abc.abstractmethod | ||
def export(self, batch: Sequence[LogData]): | ||
"""Exports a batch of logs. | ||
Args: | ||
batch: The list of `LogData` objects to be exported | ||
Returns: | ||
The result of the export | ||
""" | ||
|
||
@abc.abstractmethod | ||
def shutdown(self): | ||
"""Shuts down the exporter. | ||
Called when the SDK is shut down. | ||
""" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
# Copyright The OpenTelemetry Authors | ||
# | ||
# Licensed under the Apache License, Version 2.0 (the "License"); | ||
# you may not use this file except in compliance with the License. | ||
# You may obtain a copy of the License at | ||
# | ||
# http://www.apache.org/licenses/LICENSE-2.0 | ||
# | ||
# Unless required by applicable law or agreed to in writing, software | ||
# distributed under the License is distributed on an "AS IS" BASIS, | ||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
# See the License for the specific language governing permissions and | ||
# limitations under the License. | ||
|
||
import enum | ||
|
||
|
||
class SeverityNumber(enum.Enum): | ||
"""Numerical value of severity. | ||
Smaller numerical values correspond to less severe events | ||
(such as debug events), larger numerical values correspond | ||
to more severe events (such as errors and critical events). | ||
See the `Log Data Model`_ spec for more info and how to map the | ||
severity from source format to OTLP Model. | ||
.. _Log Data Model: | ||
https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/logs/data-model.md#field-severitynumber | ||
""" | ||
|
||
UNSPECIFIED = 0 | ||
TRACE = 1 | ||
TRACE2 = 2 | ||
TRACE3 = 3 | ||
TRACE4 = 4 | ||
DEBUG = 5 | ||
DEBUG2 = 6 | ||
DEBUG3 = 7 | ||
DEBUG4 = 8 | ||
INFO = 9 | ||
INFO2 = 10 | ||
INFO3 = 11 | ||
INFO4 = 12 | ||
WARN = 13 | ||
WARN2 = 14 | ||
WARN3 = 15 | ||
WARN4 = 16 | ||
ERROR = 17 | ||
ERROR2 = 18 | ||
ERROR3 = 19 | ||
ERROR4 = 20 | ||
FATAL = 21 | ||
FATAL2 = 22 | ||
FATAL3 = 23 | ||
FATAL4 = 24 |