|
1 |
| -OpenTelemetry Prometheus Remote Write Exporter |
2 |
| -============================================== |
| 1 | +OpenTelemetry Python SDK Prometheus Remote Write Exporter |
| 2 | +========================================================= |
3 | 3 |
|
4 |
| -This library allows exporting metric data to `Prometheus Remote Write Integrated Backends |
5 |
| -<https://prometheus.io/docs/operating/integrations/>`_. Latest `types.proto |
6 |
| -<https://github.com/prometheus/prometheus/blob/master/prompb/types.proto>` and `remote.proto |
7 |
| -<https://github.com/prometheus/prometheus/blob/master/prompb/remote.proto>` Protocol Buffers |
8 |
| -used to create WriteRequest objects were taken from Prometheus repository. Development is |
9 |
| -currently in progress. |
| 4 | +This package contains an exporter to send `OTLP`_ metrics from the |
| 5 | +Python SDK directly to a Prometheus Remote Write integrated backend |
| 6 | +(such as Cortex or Thanos) without having to run an instance of the |
| 7 | +Prometheus server. The image below shows the two Prometheus exporters in |
| 8 | +the OpenTelemetry Python SDK. |
| 9 | + |
| 10 | +Pipeline 1 illustrates the setup required for a Prometheus "pull" |
| 11 | +exporter. |
| 12 | + |
| 13 | +Pipeline 2 illustrates the setup required for the Prometheus Remote |
| 14 | +Write exporter. |
| 15 | + |
| 16 | +|Prometheus SDK pipelines| |
| 17 | + |
| 18 | +The Prometheus Remote Write Exporter is a "push" based exporter and only |
| 19 | +works with the OpenTelemetry `push controller`_. The controller |
| 20 | +periodically collects data and passes it to the exporter. This exporter |
| 21 | +then converts the data into `timeseries`_ and sends it to the Remote |
| 22 | +Write integrated backend through HTTP POST requests. The metrics |
| 23 | +collection datapath is shown below: |
| 24 | + |
| 25 | +|controller_datapath_final| |
| 26 | + |
| 27 | +See the ``example`` folder for a demo usage of this exporter |
| 28 | + |
| 29 | +Table of Contents |
| 30 | +================= |
| 31 | + |
| 32 | +- `Summary`_ |
| 33 | +- `Table of Contents`_ |
| 34 | + |
| 35 | + - `Installation`_ |
| 36 | + - `Quickstart`_ |
| 37 | + - `Configuring the Exporter`_ |
| 38 | + - `Securing the Exporter`_ |
| 39 | + |
| 40 | + - `Authentication`_ |
| 41 | + - `TLS`_ |
| 42 | + |
| 43 | + - `Supported Aggregators`_ |
| 44 | + - `Error Handling`_ |
| 45 | + - `Retry Logic`_ |
| 46 | + - `Contributing`_ |
| 47 | + |
| 48 | + - `Design Doc`_ |
10 | 49 |
|
11 | 50 | Installation
|
12 | 51 | ------------
|
| 52 | +Prerequisite |
| 53 | +~~~~~~~~~~~~ |
| 54 | +1. Install the snappy c-library |
| 55 | + **DEB**: `sudo apt-get install libsnappy-dev` |
| 56 | + **RPM**: `sudo yum install libsnappy-devel` |
| 57 | + **OSX/Brew**: `brew install snappy` |
| 58 | +2. Install python-snappy |
| 59 | + `pip install python-snappy` |
| 60 | + |
| 61 | +Exporter |
| 62 | +~~~~~~~~ |
| 63 | + |
| 64 | +- To install from the latest PyPi release, run |
| 65 | + ``pip install opentelemetry-exporter-prometheus-remote-write`` |
| 66 | +- To install from the local repository, run |
| 67 | + ``pip install -e exporter/opentelemetry-exporter-prometheus-remote-write/`` |
| 68 | + in the project root |
| 69 | + |
| 70 | +Quickstart |
| 71 | +---------- |
| 72 | + |
| 73 | +.. code:: python |
| 74 | +
|
| 75 | + from opentelemetry import metrics |
| 76 | + from opentelemetry.sdk.metrics import MeterProvider |
| 77 | + from opentelemetry.exporter.prometheus_remote_write import ( |
| 78 | + PrometheusRemoteWriteMetricsExporter |
| 79 | + ) |
| 80 | +
|
| 81 | + # Sets the global MeterProvider instance |
| 82 | + metrics.set_meter_provider(MeterProvider()) |
| 83 | +
|
| 84 | + # The Meter is responsible for creating and recording metrics. Each meter has a unique name, which we set as the module's name here. |
| 85 | + meter = metrics.get_meter(__name__) |
| 86 | +
|
| 87 | + exporter = PrometheusRemoteWriteMetricsExporter(endpoint="endpoint_here") # add other params as needed |
| 88 | +
|
| 89 | + metrics.get_meter_provider().start_pipeline(meter, exporter, 5) |
| 90 | +
|
| 91 | +Configuring the Exporter |
| 92 | +------------------------ |
| 93 | + |
| 94 | +The exporter can be configured through parameters passed to the |
| 95 | +constructor. Here are all the options: |
| 96 | + |
| 97 | +- ``endpoint``: url where data will be sent **(Required)** |
| 98 | +- ``basic_auth``: username and password for authentication |
| 99 | + **(Optional)** |
| 100 | +- ``headers``: additional headers for remote write request as |
| 101 | + determined by the remote write backend's API **(Optional)** |
| 102 | +- ``timeout``: timeout for requests to the remote write endpoint in |
| 103 | + seconds **(Optional)** |
| 104 | +- ``proxies``: dict mapping request proxy protocols to proxy urls |
| 105 | + **(Optional)** |
| 106 | +- ``tls_config``: configuration for remote write TLS settings |
| 107 | + **(Optional)** |
| 108 | + |
| 109 | +Example with all the configuration options: |
| 110 | + |
| 111 | +.. code:: python |
| 112 | +
|
| 113 | + exporter = PrometheusRemoteWriteMetricsExporter( |
| 114 | + endpoint="http://localhost:9009/api/prom/push", |
| 115 | + timeout=30, |
| 116 | + basic_auth={ |
| 117 | + "username": "user", |
| 118 | + "password": "pass123", |
| 119 | + }, |
| 120 | + headers={ |
| 121 | + "X-Scope-Org-ID": "5", |
| 122 | + "Authorization": "Bearer mytoken123", |
| 123 | + }, |
| 124 | + proxies={ |
| 125 | + "http": "http://10.10.1.10:3000", |
| 126 | + "https": "http://10.10.1.10:1080", |
| 127 | + }, |
| 128 | + tls_config={ |
| 129 | + "cert_file": "path/to/file", |
| 130 | + "key_file": "path/to/file", |
| 131 | + "ca_file": "path_to_file", |
| 132 | + "insecure_skip_verify": true, # for developing purposes |
| 133 | + } |
| 134 | + ) |
| 135 | +
|
| 136 | +Securing the Exporter |
| 137 | +--------------------- |
| 138 | + |
| 139 | +Authentication |
| 140 | +~~~~~~~~~~~~~~ |
| 141 | + |
| 142 | +The exporter provides two forms of authentication which are shown below. |
| 143 | +Users can add their own custom authentication by setting the appropriate |
| 144 | +values in the ``headers`` dictionary |
| 145 | + |
| 146 | +1. Basic Authentication Basic authentication sets a HTTP Authorization |
| 147 | + header containing a base64 encoded username/password pair. See `RFC |
| 148 | + 7617`_ for more information. This |
| 149 | + |
| 150 | +.. code:: python |
| 151 | +
|
| 152 | + exporter = PrometheusRemoteWriteMetricsExporter( |
| 153 | + basic_auth={"username": "base64user", "password": "base64pass"} |
| 154 | + ) |
| 155 | +
|
| 156 | +2. Bearer Token Authentication This custom configuration can be achieved |
| 157 | + by passing in a custom ``header`` to the constructor. See `RFC 6750`_ |
| 158 | + for more information. |
| 159 | + |
| 160 | +.. code:: python |
| 161 | +
|
| 162 | + header = { |
| 163 | + "Authorization": "Bearer mytoken123" |
| 164 | + } |
| 165 | +
|
| 166 | +TLS |
| 167 | +~~~ |
| 168 | + |
| 169 | +Users can add TLS to the exporter's HTTP Client by providing certificate |
| 170 | +and key files in the ``tls_config`` parameter. |
| 171 | + |
| 172 | +Supported Aggregators |
| 173 | +--------------------- |
| 174 | + |
| 175 | +- Sum |
| 176 | +- MinMaxSumCount |
| 177 | +- Histogram |
| 178 | +- LastValue |
| 179 | +- ValueObserver |
| 180 | + |
| 181 | +Error Handling |
| 182 | +-------------- |
| 183 | + |
| 184 | +In general, errors are raised by the calling function. The exception is |
| 185 | +for failed requests where any error status code is logged as a warning |
| 186 | +instead. |
| 187 | + |
| 188 | +This is because the exporter does not implement any retry logic as it |
| 189 | +sends cumulative metrics data. This means that data will be preserved |
| 190 | +even if some exports fail. |
| 191 | + |
| 192 | +For example, consider a situation where a user increments a Counter |
| 193 | +instrument 5 times and an export happens between each increment. If the |
| 194 | +exports happen like so: |
13 | 195 |
|
14 | 196 | ::
|
15 | 197 |
|
16 |
| - pip install opentelemetry-exporter-prometheus-remote-write |
| 198 | + SUCCESS FAIL FAIL SUCCESS SUCCESS |
| 199 | + 1 2 3 4 5 |
17 | 200 |
|
| 201 | +Then the recieved data will be: |
18 | 202 |
|
19 |
| -.. _Prometheus: https://prometheus.io/ |
20 |
| -.. _OpenTelemetry: https://github.com/open-telemetry/opentelemetry-python/ |
| 203 | +:: |
21 | 204 |
|
| 205 | + 1 4 5 |
22 | 206 |
|
23 |
| -References |
24 |
| ----------- |
| 207 | +The end result is the same since the aggregations are cumulative |
| 208 | +Contributing |
| 209 | +------------ |
| 210 | + |
| 211 | +This exporter's datapath is as follows: |
| 212 | + |
| 213 | +|Exporter datapath| *Entites with ``*`` after their name are not actual |
| 214 | +classes but rather logical groupings of functions within the exporter.* |
| 215 | + |
| 216 | +If you would like to learn more about the exporter's structure and |
| 217 | +design decisions please view the design document below |
| 218 | + |
| 219 | +Design Doc |
| 220 | +~~~~~~~~~~ |
| 221 | + |
| 222 | +`Design Document`_ |
| 223 | + |
| 224 | +This document is stored elsewhere as it contains large images which will |
| 225 | +significantly increase the size of this repo. |
25 | 226 |
|
26 |
| -* `Prometheus <https://prometheus.io/>`_ |
27 |
| -* `OpenTelemetry Project <https://opentelemetry.io/>`_ |
| 227 | +.. _Design Document: https://github.com/open-o11y/docs/tree/master/python-prometheus-remote-write |
| 228 | +.. |Exporter datapath| image:: https://user-images.githubusercontent.com/20804975/100285717-604c7280-2f3f-11eb-9b73-bdf70afce9dd.png |
| 229 | +.. _OTLP: https://github.com/open-telemetry/opentelemetry-specification/blob/master/specification/protocol/otlp.md |
| 230 | +.. _push controller: https://github.com/open-telemetry/opentelemetry-python/blob/master/opentelemetry-sdk/src/opentelemetry/sdk/metrics/export/controller.py |
| 231 | +.. _`timeseries`: https://prometheus.io/docs/concepts/data_model/ |
| 232 | +.. _Summary: #opentelemetry-python-sdk-prometheus-remote-write-exporter |
| 233 | +.. _Table of Contents: #table-of-contents |
| 234 | +.. _Installation: #installation |
| 235 | +.. _Quickstart: #quickstart |
| 236 | +.. _Configuring the Exporter: #configuring-the-exporter |
| 237 | +.. _Securing the Exporter: #securing-the-exporter |
| 238 | +.. _Authentication: #authentication |
| 239 | +.. _TLS: #tls |
| 240 | +.. _Supported Aggregators: #supported-aggregators |
| 241 | +.. _Error Handling: #error-handling |
| 242 | +.. _Retry Logic: #retry-logic |
| 243 | +.. _Contributing: #contributing |
| 244 | +.. _Design Doc: #design-doc |
| 245 | +.. |Prometheus SDK pipelines| image:: https://user-images.githubusercontent.com/20804975/100285430-e320fd80-2f3e-11eb-8217-a562c559153c.png |
| 246 | +.. |controller_datapath_final| image:: https://user-images.githubusercontent.com/20804975/100486582-79d1f380-30d2-11eb-8d17-d3e58e5c34e9.png |
| 247 | +.. _RFC 7617: https://tools.ietf.org/html/rfc7617 |
| 248 | +.. _RFC 6750: https://tools.ietf.org/html/rfc6750 |
0 commit comments