logister-ruby 0.2.6 → 0.2.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 63dccd6fdb12e5417bcca918c033a19e421087e188eac57f994939aa2eb4732f
4
- data.tar.gz: 825d77d1304622efc28380e3e26167df40b411be97aa23219cce9d7f89944e6c
3
+ metadata.gz: bbdcfea4a9984f610510aa30780b8d94a54059bf329c387e5b47997f805ecafb
4
+ data.tar.gz: 242e70a27ab5bcebcc11b1c99ce6f3acf7164a5a0ad5e482afd107bfa4fb705f
5
5
  SHA512:
6
- metadata.gz: 663bc90bcba5cfd300d1875536350131a5c1c2c540269168f910b648aa9a93ef98a301579389900cec0cbf135471c6078261a9a045b7be14b23987c9eef477c2
7
- data.tar.gz: e0f8d74a0eff0434b7884ba945ffe96f752724c18cc3bc9b332651c02cde83e8e36a9f619e1dfe356116c6c63ef154bb79c667188cd23cf74f62b28e7d5a8361
6
+ metadata.gz: 58f9a2d891eec80c14c18a40ced354cdd3b19c98e88b583d709943c3b2aeab73d5af208d050566cf1ef9fc023f547972180f381a4648d585c5cd841622d145d3
7
+ data.tar.gz: 8175e3a5b27a40ced8c9844acd56ff460e0c9655bd514e14feb94ee9edec02cbdb1b6021ef9deb6411a3fb837891c935d812d032707124c5f32147ed52ca3083
data/CHANGELOG.md CHANGED
@@ -1,5 +1,9 @@
1
1
  # Changelog
2
2
 
3
+ ## v0.2.7 - 2026-05-22
4
+
5
+ - Added `Logister.report_span` and opt-in Rails request span capture for request load waterfall charts.
6
+
3
7
  ## v0.2.6 - 2026-05-22
4
8
 
5
9
  - Added README guidance for using Ruby reports with the Logister project Insights beta, including practical metric, transaction, log, check-in, and custom attribute examples.
data/README.md CHANGED
@@ -1,12 +1,13 @@
1
1
  # logister-ruby
2
2
 
3
- `logister-ruby` is the Ruby and Rails client for sending errors, logs, metrics, transactions, and check-ins to Logister.
3
+ `logister-ruby` is the Ruby and Rails client for sending errors, logs, metrics, transactions, spans, and check-ins to Logister.
4
4
 
5
5
  Install it from RubyGems as `logister-ruby`.
6
6
 
7
7
  ## Table Of Contents
8
8
 
9
9
  - [What this gem is for](#what-this-gem-is-for)
10
+ - [Package Links](#package-links)
10
11
  - [Self-hosted backend](#self-hosted-backend)
11
12
  - [Install From RubyGems](#install-from-rubygems)
12
13
  - [Configuration](#configuration)
@@ -30,6 +31,13 @@ Use this gem when you want a Ruby or Rails app to send telemetry into the Logist
30
31
  - Product docs: https://docs.logister.org/
31
32
  - RubyGems package: https://rubygems.org/gems/logister-ruby
32
33
 
34
+ ## Package Links
35
+
36
+ - RubyGems package: https://rubygems.org/gems/logister-ruby
37
+ - GitHub releases: https://github.com/taimoorq/logister-ruby/releases
38
+ - Source repository: https://github.com/taimoorq/logister-ruby
39
+ - Integration docs: https://docs.logister.org/integrations/ruby/
40
+
33
41
  ## Self-hosted backend
34
42
 
35
43
  Use the open source Logister app repository to self-host the ingestion UI/API backend:
@@ -78,6 +86,7 @@ Logister.configure do |config|
78
86
  config.max_dependencies = 20
79
87
  config.capture_sql_breadcrumbs = true
80
88
  config.sql_breadcrumb_min_duration_ms = 25.0
89
+ config.capture_request_spans = true
81
90
 
82
91
  config.feature_flags_resolver = lambda do |request:, user:, **|
83
92
  { new_checkout: user&.respond_to?(:beta?) && user.beta? }
@@ -121,6 +130,7 @@ end
121
130
 
122
131
  If Rails is present, the gem installs middleware that reports unhandled exceptions automatically.
123
132
  It also attaches richer context such as trace IDs, route/response/performance info, breadcrumbs, dependency calls, and user metadata when available.
133
+ Set `config.capture_request_spans = true` to emit root `server` spans for request load waterfall charts while keeping existing transaction events.
124
134
  Manual `Logister.report_error` calls use the same shared enrichment path, so Ruby apps get runtime, deployment, breadcrumb, dependency, user, and nested exception cause context even when an error is reported outside the Rails middleware.
125
135
 
126
136
  ## Database load metrics (ActiveRecord)
@@ -189,6 +199,16 @@ Logister.report_transaction(
189
199
  context: { trace_id: "trace-123", request_id: "req-123" }
190
200
  )
191
201
 
202
+ Logister.report_span(
203
+ name: "render checkout",
204
+ duration_ms: 82.1,
205
+ trace_id: "trace-123",
206
+ parent_span_id: "span-root",
207
+ kind: "render",
208
+ status: "ok",
209
+ context: { route: "POST /checkout" }
210
+ )
211
+
192
212
  Logister.report_log(
193
213
  message: "payment provider timeout",
194
214
  level: "warn",
@@ -269,7 +289,7 @@ Practical Insights recipes:
269
289
  - Release validation: send `release`, then filter the Insights tab to the new release and compare errors, transaction P95, database query timing, and custom metrics.
270
290
  - Queue monitoring: report metrics such as `queue.depth`, `queue.latency`, and `jobs.retry_count` with a stable `queue` context key.
271
291
  - Performance triage: send transaction events with `route`, `service`, and `tenant_tier` so slow routes can be filtered beside errors and logs.
272
- - Instrumentation audit: open Insights after deploy and confirm errors, logs, metrics, transactions, and check-ins all appear in the recent stream.
292
+ - Instrumentation audit: open Insights after deploy and confirm errors, logs, metrics, transactions, spans, and check-ins all appear in the recent stream.
273
293
 
274
294
  Keep dashboard dimensions stable and low-cardinality. Good custom attribute keys include `service`, `region`, `queue`, `route`, `tenant_tier`, `provider`, and `feature_flag`. Avoid raw IDs, emails, request bodies, SQL text, and per-user values as top-level Insights dimensions.
275
295
 
@@ -292,8 +312,8 @@ This repo runs CI on commits and pull requests. Version tags run the release wor
292
312
  # 2) update CHANGELOG.md
293
313
  # 3) commit changes
294
314
  # 4) push a matching tag, for example:
295
- git tag -a v0.2.6 -m "Release logister-ruby v0.2.6"
296
- git push origin main v0.2.6
315
+ git tag -a v0.2.7 -m "Release logister-ruby v0.2.7"
316
+ git push origin main v0.2.7
297
317
  ```
298
318
 
299
319
  The `.github/workflows/release.yml` workflow verifies the tag matches `Logister::VERSION`, runs tests, builds the gem, publishes to RubyGems with trusted publishing, and then creates or updates the matching GitHub release from `CHANGELOG.md`.
@@ -7,7 +7,7 @@ module Logister
7
7
  :async, :queue_size, :max_retries, :retry_base_interval,
8
8
  :capture_db_metrics, :db_metric_min_duration_ms, :db_metric_sample_rate,
9
9
  :feature_flags_resolver, :dependency_resolver, :anonymize_ip,
10
- :max_breadcrumbs, :max_dependencies,
10
+ :max_breadcrumbs, :max_dependencies, :capture_request_spans,
11
11
  :capture_sql_breadcrumbs, :sql_breadcrumb_min_duration_ms
12
12
 
13
13
  def initialize
@@ -40,6 +40,7 @@ module Logister
40
40
  @anonymize_ip = false
41
41
  @max_breadcrumbs = 40
42
42
  @max_dependencies = 20
43
+ @capture_request_spans = false
43
44
  @capture_sql_breadcrumbs = true
44
45
  @sql_breadcrumb_min_duration_ms = 25.0
45
46
  end
@@ -30,6 +30,7 @@ module Logister
30
30
  copy_setting(app, config, :anonymize_ip)
31
31
  copy_setting(app, config, :max_breadcrumbs)
32
32
  copy_setting(app, config, :max_dependencies)
33
+ copy_setting(app, config, :capture_request_spans)
33
34
  copy_setting(app, config, :capture_sql_breadcrumbs)
34
35
  copy_setting(app, config, :sql_breadcrumb_min_duration_ms)
35
36
  end
@@ -3,6 +3,7 @@
3
3
  require 'digest'
4
4
  require 'time'
5
5
  require 'set'
6
+ require 'securerandom'
6
7
  require_relative 'context_helpers'
7
8
  require_relative 'context_store'
8
9
 
@@ -118,6 +119,65 @@ module Logister
118
119
  @client.publish(payload)
119
120
  end
120
121
 
122
+ def report_span(
123
+ name:,
124
+ duration_ms:,
125
+ trace_id: nil,
126
+ request_id: nil,
127
+ span_id: nil,
128
+ parent_span_id: nil,
129
+ kind: 'internal',
130
+ status: nil,
131
+ started_at: nil,
132
+ ended_at: nil,
133
+ context: {},
134
+ tags: {},
135
+ fingerprint: nil
136
+ )
137
+ return false if ignored_environment?
138
+ return false if ignored_path?(context)
139
+
140
+ started_at ||= Time.now.utc - (duration_ms.to_f / 1000.0)
141
+ span_id ||= SecureRandom.hex(8)
142
+ trace_id ||= span_id
143
+
144
+ payload = build_payload(
145
+ event_type: 'span',
146
+ level: status.to_s == 'error' ? 'error' : 'info',
147
+ message: name,
148
+ fingerprint: fingerprint || metric_fingerprint("span:#{kind}:#{name}"),
149
+ context: context.merge(
150
+ name: name,
151
+ trace_id: trace_id,
152
+ request_id: request_id,
153
+ span_id: span_id,
154
+ parent_span_id: parent_span_id,
155
+ span_kind: kind,
156
+ kind: kind,
157
+ status: status,
158
+ duration_ms: duration_ms,
159
+ started_at: normalize_timestamp(started_at),
160
+ ended_at: ended_at && normalize_timestamp(ended_at),
161
+ tags: tags
162
+ ).compact
163
+ )
164
+
165
+ payload[:started_at] = normalize_timestamp(started_at)
166
+ payload[:ended_at] = normalize_timestamp(ended_at) if ended_at
167
+ payload[:duration_ms] = duration_ms
168
+ payload[:trace_id] = trace_id
169
+ payload[:request_id] = request_id if request_id
170
+ payload[:span_id] = span_id
171
+ payload[:parent_span_id] = parent_span_id if parent_span_id
172
+ payload[:kind] = kind
173
+ payload[:status] = status if status
174
+
175
+ payload = apply_before_notify(payload)
176
+ return false unless payload
177
+
178
+ @client.publish(payload)
179
+ end
180
+
121
181
  def report_log(message:, level: 'info', context: {}, tags: {}, fingerprint: nil)
122
182
  return false if ignored_environment?
123
183
  return false if ignored_path?(context)
@@ -53,10 +53,41 @@ module Logister
53
53
  viewRuntimeMs: numeric(payload[:view_runtime])
54
54
  }.compact
55
55
  )
56
+
57
+ report_request_span(payload, request_id) if capture_request_spans?
56
58
  rescue StandardError => e
57
59
  logger.warn("logister request subscriber (process_action) failed: #{e.class} #{e.message}")
58
60
  end
59
61
 
62
+ def report_request_span(payload, request_id)
63
+ duration_ms = numeric(payload[:duration])
64
+ return unless duration_ms&.positive?
65
+
66
+ route = "#{payload[:controller]}##{payload[:action]}"
67
+ started_at = Time.now.utc - (duration_ms / 1000.0)
68
+
69
+ Logister.report_span(
70
+ name: route,
71
+ kind: "server",
72
+ status: payload[:status].to_i >= 500 ? "error" : "ok",
73
+ trace_id: request_id,
74
+ request_id: request_id,
75
+ duration_ms: duration_ms,
76
+ started_at: started_at,
77
+ context: {
78
+ route: route,
79
+ request_id: request_id,
80
+ method: payload[:method],
81
+ path: payload[:path],
82
+ status: payload[:status],
83
+ timing_breakdown: {
84
+ db: numeric(payload[:db_runtime]),
85
+ render: numeric(payload[:view_runtime])
86
+ }.compact
87
+ }
88
+ )
89
+ end
90
+
60
91
  def handle_sql_breadcrumb(started, finished, payload)
61
92
  config = configuration
62
93
  return unless config&.capture_sql_breadcrumbs
@@ -94,6 +125,12 @@ module Logister
94
125
  nil
95
126
  end
96
127
 
128
+ def capture_request_spans?
129
+ configuration&.capture_request_spans
130
+ rescue StandardError
131
+ false
132
+ end
133
+
97
134
  def logger
98
135
  configuration&.logger || Logger.new($stdout)
99
136
  rescue StandardError
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Logister
4
- VERSION = '0.2.6'
4
+ VERSION = '0.2.7'
5
5
  end
data/lib/logister.rb CHANGED
@@ -35,6 +35,10 @@ module Logister
35
35
  reporter.report_transaction(**kwargs)
36
36
  end
37
37
 
38
+ def report_span(**kwargs)
39
+ reporter.report_span(**kwargs)
40
+ end
41
+
38
42
  def report_log(**kwargs)
39
43
  reporter.report_log(**kwargs)
40
44
  end
@@ -7,7 +7,7 @@ Gem::Specification.new do |spec|
7
7
  spec.email = ['support@logister.org']
8
8
 
9
9
  spec.summary = 'Ruby and Rails client for sending events to Logister'
10
- spec.description = 'Ruby and Rails client for reporting errors, logs, metrics, transactions, and check-ins to the Logister backend, including self-hosted installs.'
10
+ spec.description = 'Ruby and Rails client for reporting errors, logs, metrics, transactions, spans, and check-ins to the Logister backend, including self-hosted installs.'
11
11
  spec.homepage = 'https://github.com/taimoorq/logister-ruby'
12
12
  spec.license = 'MIT'
13
13
  spec.required_ruby_version = '>= 3.1.0'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: logister-ruby
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.6
4
+ version: 0.2.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Logister
@@ -52,7 +52,7 @@ dependencies:
52
52
  - !ruby/object:Gem::Version
53
53
  version: '13.0'
54
54
  description: Ruby and Rails client for reporting errors, logs, metrics, transactions,
55
- and check-ins to the Logister backend, including self-hosted installs.
55
+ spans, and check-ins to the Logister backend, including self-hosted installs.
56
56
  email:
57
57
  - support@logister.org
58
58
  executables: []