{"id":23081027,"url":"https://github.com/tel-io/tel","last_synced_at":"2025-08-15T23:31:09.238Z","repository":{"id":61626590,"uuid":"543302827","full_name":"tel-io/tel","owner":"tel-io","description":"Cloud log framework easily helps to handle 3 log pillars (Logging, tracing and monitoring). All-In-One. Inspired by open telemetry.","archived":false,"fork":false,"pushed_at":"2024-09-11T19:00:20.000Z","size":959,"stargazers_count":13,"open_issues_count":1,"forks_count":2,"subscribers_count":5,"default_branch":"main","last_synced_at":"2025-04-04T00:33:44.627Z","etag":null,"topics":["distributed-logging-system","logging","monitoring","opentelemetry","opentracing","tracing"],"latest_commit_sha":null,"homepage":"","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/tel-io.png","metadata":{"files":{"readme":"README.adoc","changelog":"CHANGELOG.adoc","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"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":"2022-09-29T20:14:12.000Z","updated_at":"2024-09-30T05:27:58.000Z","dependencies_parsed_at":"2024-06-19T15:55:48.946Z","dependency_job_id":"2739ac80-cb05-4096-99c9-98c1cf9f27e3","html_url":"https://github.com/tel-io/tel","commit_stats":{"total_commits":206,"total_committers":5,"mean_commits":41.2,"dds":0.1747572815533981,"last_synced_commit":"2a2efd93b8e53b55dcdb24e23cf89f11d4b99835"},"previous_names":[],"tags_count":31,"template":false,"template_full_name":null,"purl":"pkg:github/tel-io/tel","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tel-io%2Ftel","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tel-io%2Ftel/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tel-io%2Ftel/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tel-io%2Ftel/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/tel-io","download_url":"https://codeload.github.com/tel-io/tel/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tel-io%2Ftel/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":270644764,"owners_count":24621332,"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-08-15T02:00:12.559Z","response_time":110,"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":["distributed-logging-system","logging","monitoring","opentelemetry","opentracing","tracing"],"created_at":"2024-12-16T13:45:05.973Z","updated_at":"2025-08-15T23:31:08.841Z","avatar_url":"https://github.com/tel-io.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"= Telemetry.V2 Otel Protocol\n\nFramework which aims to ease logging affair: `Logs`, `Traces` and `Metrics` .\n\nV2 version launch usage of OpenTelemetry specification for all logging directions.\nThis mean that all logging propagators uses `OTEL` protocol.\n\nTel use `zap.Logger` as the heart of system.\nThat why it's pass all zap functions through.\n\n== Motto\n\nOny context all logs.\n\nDecrease external dependencies as match as possible.\n\n== Features\n\n.All-In-One\nLibrary establish connection via GRPC OTLP protocol with `opentelemetry-collector-contrib` (official OTEL server) and send `logs`, `traces` and `metrics`.\nCollector by the way distribute them to `Loki`, `Tempo` and `Prometheus` or any other services which you prefer and which collector support.\nFurthermore, we prepared for you working `dashboards` in `./__grafana` folder which created for our `middlewares` for most popular servers and clients.\n\n.Logs\nOur goal to support https://grafana.com/docs/loki/latest/logql/log_queries/#logfmt[logfmt] format for `Loki` viewing.\nVia simple `zap` library interface.\n\nBy the way, you can enrich log attributes which should be written only when whey would really need\n\n[source,go]\n----\n// create copy of ctx which we enrich with log attributes\ncxt := tel.Global().Copy().Ctx()\n\n// pass ctx in controller-\u003estore-\u003eroot layers and enrich information\nerr := func (ctx context.Context) error{\n\ttel.FromCtx(ctx).PutAttr(extract...)\n\treturn return fmt.Errorf(\"some error\")\n}(ctx)\n\n// and you write log message only when it really needed\n// with all putted attribute via ctx from ALL layers earlier\n// No need to look previous info/debug messages\n// All needed information in one message with all attributes which you already added, but which would be writen only when you really do call `Error()`, `Info()`, `Debug()` and so on\n//\n// for example: only when you got error\nif err != nil{\n\ttel.FromCtx(ctx).Error(\"error happened\", tel.Error(err))\n}\n\n----\n\n.Trace\nLibrary simplify usage with creating `Spans` of trace\n\nAlso, you can send not only logs and also encroach `trace events`\n\n[source,go]\n----\n\tspan, ctx := tel.StartSpanFromContext(req.Context(), \"my trace\")\n\tdefer span.End()\n\n\ttel.FromCtx(ctx).Info(\"this message will be saved both in LogInstance and trace\",\n\t\t// and this will come to the trace as attribute\n\t\ttel.Int(\"code\", errCode))\n----\n\n.Metrics\nSimplify working with metrics\n[source,go]\n\n----\n\tm := tel.Global().Meter(\"github.com/MyRepo/MyLib/myInstrumenation\")\n\n\trequestLatency, err := m.SyncFloat64().Histogram(\"demo_client.request_latency\",\n\t\tinstrument.WithDescription(\"The latency of requests processed\"))\n\tif err != nil {\n\t\tt.Fatal(\"metric load error\", tel.Error(err))\n\t}\n\n    ...\n    start := time.Now()\n    ....\n\n    ms := float64(time.Now().Sub(start).Microseconds())\n\n    requestLatency.Record(ctx, ms,\n        attribute.String(\"userID\", \"e64916d9-bfd0-4f79-8ee3-847f2d034d20\"),\n        attribute.Int(\"orderID\", 1),\n    )\n----\n\n.Middleware\n\n* Recovery flow\n* Instantiate new copy of `tel` for further handler\n* Basic metrics with respective dashboard for grafana\n* Trace propagation\n** client part - send (inject) current trace span to the server\n** server part - read (extract) trace and create new trace child one (or absolutly new if no trace info was provided or this info where not properly wrapped via propagator protocol of OTEL specification)\n\n== Logging stack\n\nLogging data exported via `OTEL's` GRPC protocol. `tel` developed to trespass it via https://github.com/open-telemetry/opentelemetry-collector[open-telemetry collector] which should route log data up to any desired log receivers.\n\nKeep in mind that collector has plugin version https://github.com/open-telemetry/opentelemetry-collector-contrib[collector contrib] - this is gateway-adapter to numerous protocols which not yet support `OTEL`, for example grafana loki.\n\nFor instance, you can use `opentelemetry-collector-contrib` as `tel` receiver and route logging data to `Grafana Loki`, trace data to `Grafana Tempo` and metric data to `Prometheus + Grafana ;)`\n\n=== Grafana references feature\n\n==== loki to tempo\n\n`tel` approach to put `traceID` field with actual trace ID.\nAll our middlewares should do that or developer should do it by himself\n\nJust call `UpdateTraceFields` before write some logs\n[source,go]\n\n----\ntel.UpdateTraceFields(ctx)\n----\n\nunderstood grafana should setup `derivedFields` for Loki data source\n[source,yaml]\n\n----\n  - name: Loki\n    type: loki\n    url: http://loki:3100\n    uid: loki\n    jsonData:\n      derivedFields:\n        - datasourceUid: tempo\n          matcherRegex: \"traceID=(\\\\w+)\"\n          name: trace\n          url: '$${__value.raw}'\n----\n\n==== tempo to loki\n\nWe match `tempo` with `loki` by `service_name` label.\nAll logs should contain traceID by any key form and `service_name`.\nIn grafana tempo datasource should be configured with `tracesToLogs`\n\n==== prometheus to loki\n[source,yaml]\n\n----\n  - name: Tempo\n    type: tempo\n    access: proxy\n    orgId: 1\n    url: http://tempo:3200\n    basicAuth: false\n    isDefault: false\n    version: 1\n    editable: false\n    apiVersion: 1\n    uid: tempo\n    jsonData:\n      nodeGraph:\n        enabled: true\n      tracesToLogs:\n        datasourceUid: loki\n        filterBySpanID: false\n        filterByTraceID: true\n        mapTagNamesEnabled: false\n        tags:\n          - service_name\n----\n\n== Install\n\n[source,bash]\n----\ngo get github.com/tel-io/tel/v2@latest\n----\n\n=== collector\n\nOTEL collector configuration (labels) part of setup, this mean if you not properly setup it - you wouldn't be able to see appropriate result\n\n[source,yaml]\n----\ninclude::docker/otel-collector-config.yaml[]\n----\n\n== Features\n\n* `OTEL` logs implementation\n\n== Env\n\n.OTEL_SERVICE_NAME\nservice name\n\n`type`: string\n\n.NAMESPACE\nproject namespace\n\n`type`: string\n\n.DEPLOY_ENVIRONMENT\nENUM: dev, stage, prod\n\n`type`: string\n\n.LOG_LEVEL\ninfo log\n\n`type`: string\nNOTE:  debug, info, warn, error, dpanic, panic, fatal\n\n\n.LOG_ENCODE\nvalid options: `console` and `json` or \"none\"\n\nnone - disable print to console (only OTEL or critical errors)\n\n.DEBUG\nfor IsDebug() function\n\n`type`: bool\n\n\n.MONITOR_ENABLE\ndefault: `true`\n\n.MONITOR_ADDR\naddress where `health`, `prometheus` would be listen\n\nNOTE: address logic represented in net.Listen description\n\n.OTEL_ENABLE\ndefault: `true`\n\n.OTEL_COLLECTOR_GRPC_ADDR\nAddress to otel collector server via GRPC protocol\n\n.OTEL_EXPORTER_WITH_INSECURE\nWith insecure ...\n\n.OTEL_ENABLE_COMPRESSION\ndefault: `true`\n\nEnables gzip compression for grpc connections\n\n.OTEL_METRIC_PERIODIC_INTERVAL_SEC\ndefault: \"15\"\n\nInterval metrics gathered\n\n.OTEL_COLLECTOR_TLS_SERVER_NAME\nCheck server certificate DNS name given from server.\n\nDisable `OTEL_EXPORTER_WITH_INSECURE` if set\n\n.LOGGING_OTEL_CLIENT\ndefault: `false`\n\nrequired `OTEL_ENABLE` = true\n\nInject logger adapter to otel library related to grpc client and get log information related to this transport\n\n.LOGGING_OTEL_PROCESSOR\ndefault: `false`\n\nrequired `OTEL_ENABLE` = true\n\nInject logger adapter to otel processor library related to collectors behaviour\n\n.LOGS_ENABLE_RETRY\ndefault: `false`\n\nEnable retrying to send logs to collector.\n\n.LOGS_SYNC_INTERVAL\ndefault: `1s`\n\nLimit how often logs are flushed with level.Error.\n\nExample: 1s means allowed 1 flush per second if logs have level.Error.\n\n.LOGS_MAX_MESSAGE_SIZE\ndefault: `256`\n\nLimit message size. If limit is exceeded, message is truncated.\n\n.LOGS_MAX_MESSAGES_PER_SECOND\ndefault: `100`\n\nLimit rate of messages per second. If limit is exceeded, warning is logged and messages are dropped. Value 0 disables limit.\n\n.LOGS_MAX_LEVEL_MESSAGES_PER_SECOND\ndefault: ``\n\nThe same as LOGS_MAX_MESSAGES_PER_SECOND but allows to configure limit per level.\n\nValue format: \u003clevel1\u003e=\u003cn\u003e,\u003clevel2\u003e=\u003cn\u003e. Ex: LOGS_MAX_LEVEL_MESSAGES_PER_SECOND=\"error=0,info=100\"\n\n.TRACES_ENABLE_RETRY\ndefault: `false`\n\nEnable retrying to send traces to collector.\n\n.TRACES_SAMPLER\ndefault: `statustraceidratio:0.1`\n\nSet sampling strategy. There are options:\n- never\n- always\n- traceidratio:\u003cfloat64\u003e\n- statustraceidratio:\u003cfloat64\u003e\n\nwhere \u003cfloat64\u003e is required and valid floating point number from 0.0 to 1.0\n\n.TRACES_ENABLE_SPAN_TRACK_LOG_MESSAGE\ndefault: `false`\n\nEnable adding all log messages to active span as event.\n\n.TRACES_ENABLE_SPAN_TRACK_LOG_FIELDS\ndefault: `true`\n\nEnable adding all log fields to active span as attributes.\n\n.TRACES_CARDINALITY_DETECTOR_ENABLE\ndefault: `true`\n\nEnable cardinality check for span names.\n\n.TRACES_CARDINALITY_DETECTOR_MAX_CARDINALITY\ndefault: `0`\n\nLimit cardinality of span's attributes. Not used, so default value is 0.\n\n.TRACES_CARDINALITY_DETECTOR_MAX_INSTRUMENTS\ndefault: `500`\n\nLimit the number of unique span names.\n\n.TRACES_CARDINALITY_DETECTOR_DIAGNOSTIC_INTERVAL\ndefault: `10m`\n\nEnable diagnostic loop that checks for cardinality violations and logs a warning.\n\nYou can disable it by setting the value to 0.\n\n.METRICS_ENABLE_RETRY\ndefault: `false`\n\nEnable retrying to send metrics to collector.\n\n.METRICS_CARDINALITY_DETECTOR_ENABLE\ndefault: `true`\n\nEnable cardinality check for metrics' labels.\n\n.METRICS_CARDINALITY_DETECTOR_MAX_CARDINALITY\ndefault: `100`\n\nLimit cardinality of metric's labels. If limit is exceeded, metric is ignored, but the previous metrics work as before\n\n.METRICS_CARDINALITY_DETECTOR_MAX_INSTRUMENTS\ndefault: `500`\n\nLimit the number of unique metric names (without labels. only name).\n\n.METRICS_CARDINALITY_DETECTOR_DIAGNOSTIC_INTERVAL\ndefault: `10m`\n\nEnable diagnostic loop that checks for cardinality violations and logs a warning.\n\nYou can disable it by setting the value to 0.\n\n.OTEL_COLLECTOR_TLS_CA_CERT\nTLS CA certificate body\n\n.OTEL_COLLECTOR_TLS_CLIENT_CERT\nTLS client certificate\n\n.OTEL_COLLECTOR_TLS_CLIENT_KEY\nTLS client key\n\n.OTEL_RESOURCE_ATTRIBUTES\nThis optional variable, handled by open-telemetry SDK.\nSeparator is semicolon.\nPut additional resources variables, very suitable!\n\n\n== ToDo\n\n* [ ] Expose health check to specific metric\n* [ ] Duplicate trace messages for root - ztrace.New just add to chain tree\n\n== Usage\n\nTale look in `example/demo` folder.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftel-io%2Ftel","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ftel-io%2Ftel","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftel-io%2Ftel/lists"}