{"id":18000167,"url":"https://github.com/sumup-oss/ot","last_synced_at":"2025-10-20T06:04:42.139Z","repository":{"id":62430219,"uuid":"392612868","full_name":"sumup-oss/ot","owner":"sumup-oss","description":"Opentracing support for Elixir applications","archived":false,"fork":false,"pushed_at":"2024-01-29T12:48:08.000Z","size":59,"stargazers_count":1,"open_issues_count":1,"forks_count":1,"subscribers_count":4,"default_branch":"main","last_synced_at":"2025-04-07T04:12:28.482Z","etag":null,"topics":["elixir","opentracing"],"latest_commit_sha":null,"homepage":"","language":"Elixir","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/sumup-oss.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-08-04T08:38:43.000Z","updated_at":"2022-11-12T08:44:53.000Z","dependencies_parsed_at":"2024-10-29T23:20:07.861Z","dependency_job_id":null,"html_url":"https://github.com/sumup-oss/ot","commit_stats":null,"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/sumup-oss/ot","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sumup-oss%2Fot","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sumup-oss%2Fot/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sumup-oss%2Fot/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sumup-oss%2Fot/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sumup-oss","download_url":"https://codeload.github.com/sumup-oss/ot/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sumup-oss%2Fot/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":280026466,"owners_count":26260076,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-20T02:00:06.978Z","response_time":62,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["elixir","opentracing"],"created_at":"2024-10-29T23:09:59.332Z","updated_at":"2025-10-20T06:04:42.090Z","avatar_url":"https://github.com/sumup-oss.png","language":"Elixir","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Ot\n\n[![License](https://img.shields.io/github/license/sumup-oss/ot)](./LICENSE)\n\nOpentracing for elixir applications.\n\nPlug into your app via just a few lines of code, orchestrate span trees and send them to Jaeger, Zipkin, NewRelic, or any other tracing system.\n\n\n\u003c!-- MarkdownTOC --\u003e\n\n- [Prerequisites](#prerequisites)\n- [Installation](#installation)\n- [Quick start](#quick-start)\n    - [Example usage in a Phoenix app](#example-usage-in-a-phoenix-app)\n  - [Configuration](#configuration)\n- [Plug](#plug)\n- [Module overview and functions](#module-overview-and-functions)\n- [Contributing](#contributing)\n- [Code of conduct \\(CoC\\)](#code-of-conduct-coc)\n- [About SumUp](#about-sumup)\n\n\u003c!-- /MarkdownTOC --\u003e\n\n\u003ca id=\"prerequisites\"\u003e\u003c/a\u003e\n## Prerequisites\n\n1. You will need a general understanding of opentracing's concepts. You can find a good starting point [here](https://opentracing.io/docs/overview/)\n1. [Install](https://elixir-lang.org/install.html) Elixir v1.9 or higher\n1. This project depends on [tesla](https://github.com/teamon/tesla). Check out their [documentation](https://github.com/teamon/tesla) to learn more about Tesla and how middlewares work there.\n1. Throughout the examples of this readme we have used excerpts of a sample [Phoenix](https://phoenixframework.org/) web app, it is a good idea to get familiar with it first.\n\n\u003ca id=\"installation\"\u003e\u003c/a\u003e\n## Installation\n\nAdd this line to your `mix.exs`:\n\n```elixir\ndefp deps do\n  [{:ot, \"~\u003e 3.0\"}]\nend\n```\n\nThen run `mix deps.get` and you are good to go!\n\n\u003ca id=\"quick-start\"\u003e\u003c/a\u003e\n## Quick start\n\n```elixir\n# See \"Configuration\" section\nOt.start_link(config)\n\n# See \"Module overview and functions\" section\nOt.start_span(\"my-test-span\", nil)  # \u003c- span is initialized\nOt.tag(\"my-tag\", \"tag-value\")       #\nOt.log(\"log message\")               #\nOt.end_span()                       # \u003c- span will be sent to jaeger\n```\n\n\u003ca id=\"example-usage-in-a-phoenix-app\"\u003e\u003c/a\u003e\n#### Example usage in a Phoenix app\n\nIn `config/dev.exs`:\n\n```elixir\n# See \"Configuration\" section\nconfig :my_app, :ot_config,\n  service_name: \"my-app\",\n  collectors: [\n    jaeger: [\n      url: \"http://127.0.0.1:9411/api/v2/spans\",\n      adapter: Tesla.Adapter.Hackney,\n      stringify_tags: true\n    ]\n  ]\n```\n\nIn `application.ex`:\n\n```elixir\ndefmodule MyApp.Application do\n  def start(_type, _args) do\n    children = [\n      {Ot, Application.fetch_env!(:my_app, :ot_config)}\n      # ... other children\n```\n\nIn `endpoint.ex`:\n\n```elixir\ndefmodule MyAppWeb.Endpoint do\n  use Phoenix.Endpoint, otp_app: :my_app\n\n  # See \"Plug\" section\n  plug Ot.Plug\n\n  # ... other plugs\n```\n\n\u003ca id=\"configuration\"\u003e\u003c/a\u003e\n### Configuration\n\nExample with all supported configuration options:\n\n```elixir\n# Tesla adapter to use in collectors (can be different for each collector)\n# If you use this one, you must add :hackney to your deps\nadapter = {Tesla.Adapter.Hackney, connect_timeout: 5000, recv_timeout: 5000}\n\not_config = [\n  service_name: \"my-app\",       # (required)\n  ignored_exceptions: [         # (optional) don't set \"error=true\" for these\n    Phoenix.Router.NoRouteError\n  ],\n  plug: [                                      # (optional) config for Ot.Plug\n    paths: [\"/v0.1/*\"],                        # (optional) paths to work with; default: [\"*\"]\n    response_body_tag: \"http.response_body\",   # (optional) tag resp body as \"http.resp_body\"; default: nil (no tag)\n    conn_private_tags: [                       # (optional) list of conn-private fields to tag; default: []\n      req_body: \"http.request_body\",           #    tag conn.private.req_body as \"http.request_body\"\n      req_id: \"http.request_id\"                #    tag conn.private.req_id as \"http.request_id\"\n    ]\n  ],\n  collectors: [\n    jaeger: [\n      url: \"...\",               # (required) span endpoint (Zipkin JSON v2 format)\n      adapter: tesla_adapter,   # (required) tesla adapter to use\n      flush_interval: 500,      # (optional) buffer flush interval in ms; default: 1000\n      flush_retries: 1,         # (optional) flush retry attempts; default: 5 *\n      stringify_tags: true,     # (optional) convert tag values to strings (required for jaeger)\n      middlewares: []           # (optional) Tesla middlewares; default: []\n    ],\n    newrelic: [\n      url: \"https://trace-api.newrelic.com/trace/v1\",\n      adapter: tesla_adapter,\n      middlewares: [\n        Tesla.Middleware.Logger,\n        {Tesla.Middleware.Headers, [\n          {\"api-key\", \"...\"},\n          {\"data-format\", \"zipkin\"},\n          {\"data-format-version\", \"2\"}\n        ]}\n      ]\n    ]\n  ]\n]\n```\n\n\\* tracing data is stored in a local buffer and sent to the tracing backends\n(jaeger, zipkin, etc.) in a batch, every X ms. On failure, the buffer is\npreserved and continues to accumulate spans till the next flush (retry).\nIf the retry limit is exceeded, the buffer is discarded to prevent memory leaks.\n\n\u003ca id=\"plug\"\u003e\u003c/a\u003e\n## Plug\n\nWeb applications can use `Ot.Plug` to automatically have a span created for each incoming request.\n\nLet's take a simple ping-pong web app and try this simple request:\n\n```bash\ncurl 'http://localhost:4000/v0.1/ping?player=just_me'\n```\n\nThe controller:\n\n```elixir\ndef MyAppWeb.MyController do\n  def ping(conn, params) do\n    Ot.tag(\"opponent\", params[\"player\"])\n    send_resp(conn, 200, \"pong\")\n  end\nend\n```\n\nwill produce this span, sent to the collector(s):\n\n```json\n{\n  \"annotations\": [],\n  \"duration\": 1375,\n  \"id\": \"d98f95a2d087a665\",\n  \"kind\": \"SERVER\",\n  \"localEndpoint\":\n  {\n    \"ipv4\": \"127.0.0.1\",\n    \"port\": 0,\n    \"serviceName\": \"my-app\"\n  },\n  \"name\": \"request\",\n  \"parentId\": null,\n  \"tags\":\n  {\n    \"component\": \"my-app\",\n    \"author\": \"just_me\",\n    \"http.method\": \"GET\",\n    \"http.path\": \"/v0.1/ping\",\n    \"http.query_string\": \"player=just_me\",\n    \"http.status_code\": \"200\"\n  },\n  \"timestamp\": 1628150108323753,\n  \"traceId\": \"0a922fbb7df193916b283610bcc516ff\"\n}\n```\n\nNote that the values of `ipv4` and `port` are hard-coded (could be made configurable in a later release).\n\n\u003ca id=\"module-overview-and-functions\"\u003e\u003c/a\u003e\n## Module overview and functions\n\nCheck out the [Module overview](./docs/module_overview.md) docs.\n\n\u003ca id=\"contributing\"\u003e\u003c/a\u003e\n## Contributing\n\nCheck out [CONTRIBUTING.md](./CONTRIBUTING.md)\n\n\u003ca id=\"code-of-conduct-coc\"\u003e\u003c/a\u003e\n## Code of conduct (CoC)\n\nWe want to foster an inclusive and friendly community around our Open Source efforts. Like all SumUp Open Source projects, this project follows the Contributor Covenant Code of Conduct. Please, [read it and follow it](CODE_OF_CONDUCT.md).\n\nIf you feel another member of the community violated our CoC or you are experiencing problems participating in our community because of another individual's behavior, please get in touch with our maintainers. We will enforce the CoC.\n\n\u003ca id=\"about-sumup\"\u003e\u003c/a\u003e\n## About SumUp\n\n![SumUp logo](https://raw.githubusercontent.com/sumup-oss/assets/master/sumup-logo.svg?sanitize=true)\n\nIt is our mission to make easy and fast card payments a reality across the *entire* world. You can pay with SumUp in more than 30 countries, already. Our engineers work in Berlin, Cologne, Sofia and Sāo Paulo. They write code in JavaScript, Swift, Ruby, Go, Java, Erlang, Elixir and more. Want to come work with us? [Head to our careers page](https://sumup.com/careers) to find out more.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsumup-oss%2Fot","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsumup-oss%2Fot","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsumup-oss%2Fot/lists"}