Class: Salopulse::Client
- Inherits:
-
Object
- Object
- Salopulse::Client
- Includes:
- Singleton
- Defined in:
- lib/salopulse/client.rb
Instance Attribute Summary collapse
-
#buffer ⇒ Object
readonly
Returns the value of attribute buffer.
-
#configuration ⇒ Object
readonly
Returns the value of attribute configuration.
-
#dsn ⇒ Object
readonly
Returns the value of attribute dsn.
-
#flusher ⇒ Object
readonly
Returns the value of attribute flusher.
-
#transport ⇒ Object
readonly
Returns the value of attribute transport.
Instance Method Summary collapse
- #capture_exception(error, user_context: nil, environment_data: nil) ⇒ Object
- #capture_message(message, level: :info) ⇒ Object
- #capture_performance(endpoint:, http_method:, duration_ms:, status_code:, cpu_usage: nil, memory_usage: nil) ⇒ Object
-
#capture_sql(query:, duration_ms:, rows_returned: nil) ⇒ Object
— Capture API ———————————————————.
- #close ⇒ Object
- #disabled? ⇒ Boolean
-
#flush(timeout: 5) ⇒ Object
— Lifecycle ———————————————————–.
-
#flush_request_scope_events ⇒ Object
— Request scope ——————————————————-.
- #init(options = {}) ⇒ Object
-
#initialize ⇒ Client
constructor
A new instance of Client.
- #initialized? ⇒ Boolean
-
#reset! ⇒ Object
Used by tests to wipe singleton state.
- #set_tag(key, value) ⇒ Object
-
#set_user(attrs) ⇒ Object
— Context helpers —————————————————–.
- #uninitialized? ⇒ Boolean
Constructor Details
#initialize ⇒ Client
Returns a new instance of Client.
19 20 21 22 23 |
# File 'lib/salopulse/client.rb', line 19 def initialize @initialized = false @mutex = Mutex.new @pid = nil end |
Instance Attribute Details
#buffer ⇒ Object (readonly)
Returns the value of attribute buffer.
17 18 19 |
# File 'lib/salopulse/client.rb', line 17 def buffer @buffer end |
#configuration ⇒ Object (readonly)
Returns the value of attribute configuration.
17 18 19 |
# File 'lib/salopulse/client.rb', line 17 def configuration @configuration end |
#dsn ⇒ Object (readonly)
Returns the value of attribute dsn.
17 18 19 |
# File 'lib/salopulse/client.rb', line 17 def dsn @dsn end |
#flusher ⇒ Object (readonly)
Returns the value of attribute flusher.
17 18 19 |
# File 'lib/salopulse/client.rb', line 17 def flusher @flusher end |
#transport ⇒ Object (readonly)
Returns the value of attribute transport.
17 18 19 |
# File 'lib/salopulse/client.rb', line 17 def transport @transport end |
Instance Method Details
#capture_exception(error, user_context: nil, environment_data: nil) ⇒ Object
90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 |
# File 'lib/salopulse/client.rb', line 90 def capture_exception(error, user_context: nil, environment_data: nil) return if disabled? return unless sample? ctx = RequestContext.current data = { "error_class" => error.class.name, "message" => error..to_s, "stack_trace" => Array(error.backtrace).join("\n"), "endpoint" => ctx&.dig(:endpoint), "http_method" => ctx&.dig(:http_method) } user = user_context || ctx&.dig(:user) data["user_context"] = Sanitizer.scrub_hash(user) if user data["environment_data"] = Sanitizer.scrub_hash(environment_data) if environment_data enqueue(build_event(type: "error", data: data.compact, ctx: ctx)) end |
#capture_message(message, level: :info) ⇒ Object
109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 |
# File 'lib/salopulse/client.rb', line 109 def (, level: :info) return if disabled? return unless sample? ctx = RequestContext.current data = { "error_class" => "Salopulse::Message", "message" => .to_s, "stack_trace" => "", "endpoint" => ctx&.dig(:endpoint), "http_method" => ctx&.dig(:http_method), "level" => level.to_s }.compact enqueue(build_event(type: "error", data: data, ctx: ctx)) end |
#capture_performance(endpoint:, http_method:, duration_ms:, status_code:, cpu_usage: nil, memory_usage: nil) ⇒ Object
125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 |
# File 'lib/salopulse/client.rb', line 125 def capture_performance(endpoint:, http_method:, duration_ms:, status_code:, cpu_usage: nil, memory_usage: nil) return if disabled? return unless sample? ctx = RequestContext.current data = { "endpoint" => endpoint, "http_method" => http_method, "duration_ms" => duration_ms.to_i, "status_code" => status_code.to_i } data["cpu_usage"] = cpu_usage if cpu_usage data["memory_usage"] = memory_usage if memory_usage enqueue(build_event(type: "performance", data: data, ctx: ctx)) end |
#capture_sql(query:, duration_ms:, rows_returned: nil) ⇒ Object
— Capture API ———————————————————
61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 |
# File 'lib/salopulse/client.rb', line 61 def capture_sql(query:, duration_ms:, rows_returned: nil) return if disabled? return if RequestContext.suppressed? return unless sample? ctx = RequestContext.current fingerprint = LocalFingerprint.for(query) event = build_event( type: "sql", data: { "query" => query, "duration_ms" => duration_ms.to_i, "endpoint" => ctx&.dig(:endpoint), "http_method" => ctx&.dig(:http_method), "rows_returned" => rows_returned, "n1_detected" => false }.compact, ctx: ctx, extra_envelope: { "database_dialect" => detect_dialect } ) if ctx RequestContext.record_sql_event(event, fingerprint) else enqueue(event) end end |
#close ⇒ Object
177 178 179 180 181 182 183 |
# File 'lib/salopulse/client.rb', line 177 def close return unless @initialized ensure_runtime_ready! @flusher&.stop(timeout: 5) @pid = nil @initialized = false end |
#disabled? ⇒ Boolean
55 56 57 |
# File 'lib/salopulse/client.rb', line 55 def disabled? !@initialized || !@configuration&.enabled end |
#flush(timeout: 5) ⇒ Object
— Lifecycle ———————————————————–
171 172 173 174 175 |
# File 'lib/salopulse/client.rb', line 171 def flush(timeout: 5) return 0 if disabled? ensure_runtime_ready! @flusher.flush_all(timeout: timeout) end |
#flush_request_scope_events ⇒ Object
— Request scope ——————————————————-
144 145 146 147 148 149 150 151 152 153 154 155 156 157 |
# File 'lib/salopulse/client.rb', line 144 def flush_request_scope_events ctx = RequestContext.current return unless ctx threshold = @configuration.n1_threshold counts = ctx[:sql_fingerprint_counts] ctx[:sql_events].each do |event, fingerprint| if counts[fingerprint] >= threshold event[:data]["n1_detected"] = true end enqueue(event) end end |
#init(options = {}) ⇒ Object
25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
# File 'lib/salopulse/client.rb', line 25 def init( = {}) @mutex.synchronize do if @initialized build_runtime!(reset_buffer: forked_process?) unless runtime_ready? return self end @configuration = Configuration.new .each { |k, v| @configuration.public_send("#{k}=", v) if @configuration.respond_to?("#{k}=") } return self unless @configuration.enabled @dsn = DSN.new(@configuration.dsn) build_runtime!(reset_buffer: true) install_at_exit_hook @initialized = true self end end |
#initialized? ⇒ Boolean
47 48 49 |
# File 'lib/salopulse/client.rb', line 47 def initialized? @initialized end |
#reset! ⇒ Object
Used by tests to wipe singleton state.
186 187 188 189 190 191 192 193 194 195 |
# File 'lib/salopulse/client.rb', line 186 def reset! close if @initialized @configuration = nil @buffer = nil @transport = nil @flusher = nil @dsn = nil @pid = nil @initialized = false end |
#set_tag(key, value) ⇒ Object
165 166 167 |
# File 'lib/salopulse/client.rb', line 165 def set_tag(key, value) RequestContext.set_tag(key, value) end |
#set_user(attrs) ⇒ Object
— Context helpers —————————————————–
161 162 163 |
# File 'lib/salopulse/client.rb', line 161 def set_user(attrs) RequestContext.set_user(attrs) end |
#uninitialized? ⇒ Boolean
51 52 53 |
# File 'lib/salopulse/client.rb', line 51 def uninitialized? !@initialized end |