skylight-core 4.1.2 → 4.2.0.beta
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 +4 -4
- data/lib/skylight/core/instrumentable.rb +29 -3
- data/lib/skylight/core/instrumenter.rb +82 -16
- data/lib/skylight/core/middleware.rb +1 -1
- data/lib/skylight/core/normalizers.rb +1 -0
- data/lib/skylight/core/normalizers/graphql/base.rb +93 -0
- data/lib/skylight/core/probes/action_controller.rb +16 -11
- data/lib/skylight/core/probes/active_job.rb +1 -1
- data/lib/skylight/core/probes/delayed_job.rb +1 -1
- data/lib/skylight/core/sidekiq.rb +1 -1
- data/lib/skylight/core/subscriber.rb +6 -8
- data/lib/skylight/core/trace.rb +52 -8
- data/lib/skylight/core/version.rb +1 -1
- metadata +5 -4
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA256:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: 7836c1098f49c2f7b0f8581656367354e1ccec3c148f593a96df4deef011e9c9
         | 
| 4 | 
            +
              data.tar.gz: 390b30be3374c7bcb827806c230d36772a96bef0f5692c83a2730d4face3f162
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: ab419f49f172e95c075796d849ad643eb84032a98fe392b38101d93a3c6a7c2477d381f224752b0ae20ad607a7f883fdcbda4485f34f03e2ffaace66a8c1e18b
         | 
| 7 | 
            +
              data.tar.gz: f1db03e7f479a3853036f6c7d3f94b7081cd5545cf4286d83393f8b19ff4e350f29cd91a869d93f0cb505d8a22dd4439165f477c27290aa5ce14b13649dc34f0
         | 
| @@ -92,7 +92,7 @@ module Skylight | |
| 92 92 | 
             
                    end
         | 
| 93 93 |  | 
| 94 94 | 
             
                    # Start a trace
         | 
| 95 | 
            -
                    def trace(endpoint = nil, cat = nil, title = nil, meta: nil, segment: nil)
         | 
| 95 | 
            +
                    def trace(endpoint = nil, cat = nil, title = nil, meta: nil, segment: nil, component: nil)
         | 
| 96 96 | 
             
                      unless instrumenter
         | 
| 97 97 | 
             
                        return yield if block_given?
         | 
| 98 98 | 
             
                        return
         | 
| @@ -101,9 +101,9 @@ module Skylight | |
| 101 101 | 
             
                      cat ||= DEFAULT_CATEGORY
         | 
| 102 102 |  | 
| 103 103 | 
             
                      if block_given?
         | 
| 104 | 
            -
                        instrumenter.trace(endpoint, cat, title, nil, meta: meta, segment: segment) { |tr| yield tr }
         | 
| 104 | 
            +
                        instrumenter.trace(endpoint, cat, title, nil, meta: meta, segment: segment, component: component) { |tr| yield tr }
         | 
| 105 105 | 
             
                      else
         | 
| 106 | 
            -
                        instrumenter.trace(endpoint, cat, title, nil, meta: meta, segment: segment)
         | 
| 106 | 
            +
                        instrumenter.trace(endpoint, cat, title, nil, meta: meta, segment: segment, component: component)
         | 
| 107 107 | 
             
                      end
         | 
| 108 108 | 
             
                    end
         | 
| 109 109 |  | 
| @@ -132,6 +132,32 @@ module Skylight | |
| 132 132 | 
             
                      instrumenter.instrument(category, title, desc, meta, &block)
         | 
| 133 133 | 
             
                    end
         | 
| 134 134 |  | 
| 135 | 
            +
                    def mute
         | 
| 136 | 
            +
                      unless instrumenter
         | 
| 137 | 
            +
                        return yield if block_given?
         | 
| 138 | 
            +
                        return
         | 
| 139 | 
            +
                      end
         | 
| 140 | 
            +
             | 
| 141 | 
            +
                      instrumenter.mute do
         | 
| 142 | 
            +
                        yield if block_given?
         | 
| 143 | 
            +
                      end
         | 
| 144 | 
            +
                    end
         | 
| 145 | 
            +
             | 
| 146 | 
            +
                    def unmute
         | 
| 147 | 
            +
                      unless instrumenter
         | 
| 148 | 
            +
                        return yield if block_given?
         | 
| 149 | 
            +
                        return
         | 
| 150 | 
            +
                      end
         | 
| 151 | 
            +
             | 
| 152 | 
            +
                      instrumenter.unmute do
         | 
| 153 | 
            +
                        yield if block_given?
         | 
| 154 | 
            +
                      end
         | 
| 155 | 
            +
                    end
         | 
| 156 | 
            +
             | 
| 157 | 
            +
                    def muted?
         | 
| 158 | 
            +
                      instrumenter&.muted?
         | 
| 159 | 
            +
                    end
         | 
| 160 | 
            +
             | 
| 135 161 | 
             
                    def span_correlation_header(span)
         | 
| 136 162 | 
             
                      return unless instrumenter
         | 
| 137 163 | 
             
                      instrumenter.span_correlation_header(span)
         | 
| @@ -13,6 +13,7 @@ module Skylight::Core | |
| 13 13 | 
             
                class TraceInfo
         | 
| 14 14 | 
             
                  def initialize(key = KEY)
         | 
| 15 15 | 
             
                    @key = key
         | 
| 16 | 
            +
                    @muted_key = "#{key}_muted"
         | 
| 16 17 | 
             
                  end
         | 
| 17 18 |  | 
| 18 19 | 
             
                  def current
         | 
| @@ -22,9 +23,20 @@ module Skylight::Core | |
| 22 23 | 
             
                  def current=(trace)
         | 
| 23 24 | 
             
                    Thread.current[@key] = trace
         | 
| 24 25 | 
             
                  end
         | 
| 26 | 
            +
             | 
| 27 | 
            +
                  # NOTE: This should only be set by the instrumenter, and only
         | 
| 28 | 
            +
                  # in the context of a `mute` block. Do not try to turn this
         | 
| 29 | 
            +
                  # flag on and off directly.
         | 
| 30 | 
            +
                  def muted=(val)
         | 
| 31 | 
            +
                    Thread.current[@muted_key] = val
         | 
| 32 | 
            +
                  end
         | 
| 33 | 
            +
             | 
| 34 | 
            +
                  def muted?
         | 
| 35 | 
            +
                    !!Thread.current[@muted_key]
         | 
| 36 | 
            +
                  end
         | 
| 25 37 | 
             
                end
         | 
| 26 38 |  | 
| 27 | 
            -
                attr_reader :uuid, :config, :gc | 
| 39 | 
            +
                attr_reader :uuid, :config, :gc
         | 
| 28 40 |  | 
| 29 41 | 
             
                def self.trace_class
         | 
| 30 42 | 
             
                  Trace
         | 
| @@ -51,6 +63,7 @@ module Skylight::Core | |
| 51 63 |  | 
| 52 64 | 
             
                  key = "#{KEY}_#{self.class.trace_class.name}".gsub(/\W/, "_")
         | 
| 53 65 | 
             
                  @trace_info = @config[:trace_info] || TraceInfo.new(key)
         | 
| 66 | 
            +
                  @mutex = Mutex.new
         | 
| 54 67 | 
             
                end
         | 
| 55 68 |  | 
| 56 69 | 
             
                def log_context
         | 
| @@ -86,6 +99,45 @@ module Skylight::Core | |
| 86 99 | 
             
                  true
         | 
| 87 100 | 
             
                end
         | 
| 88 101 |  | 
| 102 | 
            +
                def muted=(val)
         | 
| 103 | 
            +
                  @trace_info.muted = val
         | 
| 104 | 
            +
                end
         | 
| 105 | 
            +
             | 
| 106 | 
            +
                def muted?
         | 
| 107 | 
            +
                  @trace_info.muted?
         | 
| 108 | 
            +
                end
         | 
| 109 | 
            +
             | 
| 110 | 
            +
                def mute
         | 
| 111 | 
            +
                  old_muted = muted?
         | 
| 112 | 
            +
                  self.muted = true
         | 
| 113 | 
            +
                  yield if block_given?
         | 
| 114 | 
            +
                ensure
         | 
| 115 | 
            +
                  self.muted = old_muted
         | 
| 116 | 
            +
                end
         | 
| 117 | 
            +
             | 
| 118 | 
            +
                def unmute
         | 
| 119 | 
            +
                  old_muted = muted?
         | 
| 120 | 
            +
                  self.muted = false
         | 
| 121 | 
            +
                  yield if block_given?
         | 
| 122 | 
            +
                ensure
         | 
| 123 | 
            +
                  self.muted = old_muted
         | 
| 124 | 
            +
                end
         | 
| 125 | 
            +
             | 
| 126 | 
            +
                def silence_warnings(context)
         | 
| 127 | 
            +
                  @warnings_silenced || @mutex.synchronize do
         | 
| 128 | 
            +
                    @warnings_silenced ||= {}
         | 
| 129 | 
            +
                  end
         | 
| 130 | 
            +
             | 
| 131 | 
            +
                  @warnings_silenced[context] = true
         | 
| 132 | 
            +
                end
         | 
| 133 | 
            +
             | 
| 134 | 
            +
                def warnings_silenced?(context)
         | 
| 135 | 
            +
                  @warnings_silenced && @warnings_silenced[context]
         | 
| 136 | 
            +
                end
         | 
| 137 | 
            +
             | 
| 138 | 
            +
                alias_method :disable, :mute
         | 
| 139 | 
            +
                alias_method :disabled?, :muted?
         | 
| 140 | 
            +
             | 
| 89 141 | 
             
                def start!
         | 
| 90 142 | 
             
                  # We do this here since we can't report these issues via Gem install without stopping install entirely.
         | 
| 91 143 | 
             
                  check_install!
         | 
| @@ -120,7 +172,7 @@ module Skylight::Core | |
| 120 172 | 
             
                  native_stop
         | 
| 121 173 | 
             
                end
         | 
| 122 174 |  | 
| 123 | 
            -
                def trace(endpoint, cat, title = nil, desc = nil, meta: nil, segment: nil)
         | 
| 175 | 
            +
                def trace(endpoint, cat, title = nil, desc = nil, meta: nil, segment: nil, component: nil)
         | 
| 124 176 | 
             
                  # If a trace is already in progress, continue with that one
         | 
| 125 177 | 
             
                  if (trace = @trace_info.current)
         | 
| 126 178 | 
             
                    return yield(trace) if block_given?
         | 
| @@ -128,7 +180,7 @@ module Skylight::Core | |
| 128 180 | 
             
                  end
         | 
| 129 181 |  | 
| 130 182 | 
             
                  begin
         | 
| 131 | 
            -
                    trace = self.class.trace_class.new(self, endpoint, Util::Clock.nanos, cat, title, desc, meta: meta, segment: segment)
         | 
| 183 | 
            +
                    trace = self.class.trace_class.new(self, endpoint, Util::Clock.nanos, cat, title, desc, meta: meta, segment: segment, component: component)
         | 
| 132 184 | 
             
                  rescue Exception => e
         | 
| 133 185 | 
             
                    log_error e.message
         | 
| 134 186 | 
             
                    t { e.backtrace.join("\n") }
         | 
| @@ -147,17 +199,6 @@ module Skylight::Core | |
| 147 199 | 
             
                  end
         | 
| 148 200 | 
             
                end
         | 
| 149 201 |  | 
| 150 | 
            -
                def disable
         | 
| 151 | 
            -
                  @disabled = true
         | 
| 152 | 
            -
                  yield
         | 
| 153 | 
            -
                ensure
         | 
| 154 | 
            -
                  @disabled = false
         | 
| 155 | 
            -
                end
         | 
| 156 | 
            -
             | 
| 157 | 
            -
                def disabled?
         | 
| 158 | 
            -
                  defined?(@disabled) && @disabled
         | 
| 159 | 
            -
                end
         | 
| 160 | 
            -
             | 
| 161 202 | 
             
                def self.match?(string, regex)
         | 
| 162 203 | 
             
                  @scanner ||= StringScanner.new("")
         | 
| 163 204 | 
             
                  @scanner.string = string
         | 
| @@ -171,6 +212,11 @@ module Skylight::Core | |
| 171 212 | 
             
                def instrument(cat, title = nil, desc = nil, meta = nil)
         | 
| 172 213 | 
             
                  raise ArgumentError, "cat is required" unless cat
         | 
| 173 214 |  | 
| 215 | 
            +
                  if muted?
         | 
| 216 | 
            +
                    return yield if block_given?
         | 
| 217 | 
            +
                    return
         | 
| 218 | 
            +
                  end
         | 
| 219 | 
            +
             | 
| 174 220 | 
             
                  unless (trace = @trace_info.current)
         | 
| 175 221 | 
             
                    return yield if block_given?
         | 
| 176 222 | 
             
                    return
         | 
| @@ -259,9 +305,29 @@ module Skylight::Core | |
| 259 305 | 
             
                  [nil, sql]
         | 
| 260 306 | 
             
                end
         | 
| 261 307 |  | 
| 308 | 
            +
                # Because GraphQL can return multiple results, each of which
         | 
| 309 | 
            +
                # may have their own success/error states, we need to set the
         | 
| 310 | 
            +
                # skylight segment as follows:
         | 
| 311 | 
            +
                #
         | 
| 312 | 
            +
                # - when all queries have errors: "error"
         | 
| 313 | 
            +
                # - when some queries have errors: "<rendered format>+error"
         | 
| 314 | 
            +
                # - when no queries have errors: "<rendered format>"
         | 
| 315 | 
            +
                #
         | 
| 316 | 
            +
                # <rendered format> will be determined by the Rails controller as usual.
         | 
| 317 | 
            +
                # See Instrumenter#finalize_endpoint_segment for the actual segment/error assignment.
         | 
| 262 318 | 
             
                def finalize_endpoint_segment(trace)
         | 
| 263 | 
            -
                  return unless trace.segment
         | 
| 264 | 
            -
             | 
| 319 | 
            +
                  return unless (segment = trace.segment)
         | 
| 320 | 
            +
             | 
| 321 | 
            +
                  segment = case trace.compound_response_error_status
         | 
| 322 | 
            +
                            when :all
         | 
| 323 | 
            +
                              "error"
         | 
| 324 | 
            +
                            when :partial
         | 
| 325 | 
            +
                              "#{segment}+error"
         | 
| 326 | 
            +
                            else
         | 
| 327 | 
            +
                              segment
         | 
| 328 | 
            +
                            end
         | 
| 329 | 
            +
             | 
| 330 | 
            +
                  trace.endpoint += "<sk-segment>#{segment}</sk-segment>"
         | 
| 265 331 | 
             
                end
         | 
| 266 332 | 
             
              end
         | 
| 267 333 | 
             
            end
         | 
| @@ -78,7 +78,7 @@ module Skylight::Core | |
| 78 78 | 
             
                  else
         | 
| 79 79 | 
             
                    begin
         | 
| 80 80 | 
             
                      t { "middleware beginning trace" }
         | 
| 81 | 
            -
                      trace = instrumentable.trace(endpoint_name(env), "app.rack.request", nil, meta: endpoint_meta(env))
         | 
| 81 | 
            +
                      trace = instrumentable.trace(endpoint_name(env), "app.rack.request", nil, meta: endpoint_meta(env), component: :web)
         | 
| 82 82 | 
             
                      t { "middleware began trace=#{trace ? trace.uuid : nil}" }
         | 
| 83 83 |  | 
| 84 84 | 
             
                      resp = @app.call(env)
         | 
| @@ -0,0 +1,93 @@ | |
| 1 | 
            +
            # frozen_string_literal: true
         | 
| 2 | 
            +
             | 
| 3 | 
            +
            module Skylight::Core::Normalizers::GraphQL
         | 
| 4 | 
            +
              # Some AS::N events in GraphQL are not super useful.
         | 
| 5 | 
            +
              # We are purposefully ignoring the following keys (and you probably shouldn't add them):
         | 
| 6 | 
            +
              #  - "graphql.analyze_multiplex"
         | 
| 7 | 
            +
              #  - "graphql.execute_field" (very frequently called)
         | 
| 8 | 
            +
              #  - "graphql.execute_field_lazy"
         | 
| 9 | 
            +
             | 
| 10 | 
            +
              class Base < Skylight::Core::Normalizers::Normalizer
         | 
| 11 | 
            +
                ANONYMOUS = "[anonymous]".freeze
         | 
| 12 | 
            +
                CAT = "app.graphql".freeze
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                def normalize(_trace, name, _payload)
         | 
| 15 | 
            +
                  [CAT, name, nil]
         | 
| 16 | 
            +
                end
         | 
| 17 | 
            +
              end
         | 
| 18 | 
            +
             | 
| 19 | 
            +
              class Lex < Base
         | 
| 20 | 
            +
                register "graphql.lex"
         | 
| 21 | 
            +
              end
         | 
| 22 | 
            +
             | 
| 23 | 
            +
              class Parse < Base
         | 
| 24 | 
            +
                register "graphql.parse"
         | 
| 25 | 
            +
              end
         | 
| 26 | 
            +
             | 
| 27 | 
            +
              class Validate < Base
         | 
| 28 | 
            +
                register "graphql.validate"
         | 
| 29 | 
            +
              end
         | 
| 30 | 
            +
             | 
| 31 | 
            +
              class ExecuteMultiplex < Base
         | 
| 32 | 
            +
                register "graphql.execute_multiplex"
         | 
| 33 | 
            +
                def normalize_after(trace, _span, _name, payload)
         | 
| 34 | 
            +
                  # This is in normalize_after because the queries may not have
         | 
| 35 | 
            +
                  # an assigned operation name before they are executed.
         | 
| 36 | 
            +
                  # For example, if you send a single query with a defined operation name, e.g.:
         | 
| 37 | 
            +
                  # ```graphql
         | 
| 38 | 
            +
                  #   query MyNamedQuery { user(id: 1) { name } }
         | 
| 39 | 
            +
                  # ```
         | 
| 40 | 
            +
                  # ... but do _not_ send the operationName request param, the GraphQL docs[1]
         | 
| 41 | 
            +
                  # specify that the executor should use the operation name from the definition.
         | 
| 42 | 
            +
                  #
         | 
| 43 | 
            +
                  # In graphql-ruby's case, the calculation of the operation name is lazy, and
         | 
| 44 | 
            +
                  # has not been done yet at the point where execute_multiplex starts.
         | 
| 45 | 
            +
                  # [1] https://graphql.org/learn/serving-over-http/#post-request
         | 
| 46 | 
            +
                  queries, has_errors = payload[:multiplex].queries.each_with_object([Set.new, Set.new]) do |query, (names, errors)|
         | 
| 47 | 
            +
                    names << (query.operation_name || ANONYMOUS)
         | 
| 48 | 
            +
                    errors << query.static_errors.any?
         | 
| 49 | 
            +
                  end
         | 
| 50 | 
            +
             | 
| 51 | 
            +
                  trace.endpoint = "graphql:#{queries.sort.join('+')}"
         | 
| 52 | 
            +
                  trace.compound_response_error_status = if has_errors.all?
         | 
| 53 | 
            +
                                                           :all
         | 
| 54 | 
            +
                                                         elsif !has_errors.none?
         | 
| 55 | 
            +
                                                           :partial
         | 
| 56 | 
            +
                                                         end
         | 
| 57 | 
            +
                end
         | 
| 58 | 
            +
              end
         | 
| 59 | 
            +
             | 
| 60 | 
            +
              class AnalyzeQuery < Base
         | 
| 61 | 
            +
                register "graphql.analyze_query"
         | 
| 62 | 
            +
              end
         | 
| 63 | 
            +
             | 
| 64 | 
            +
              class ExecuteQuery < Base
         | 
| 65 | 
            +
                register "graphql.execute_query"
         | 
| 66 | 
            +
             | 
| 67 | 
            +
                def normalize(trace, name, payload)
         | 
| 68 | 
            +
                  query_name = payload[:query]&.operation_name || ANONYMOUS
         | 
| 69 | 
            +
             | 
| 70 | 
            +
                  if query_name == ANONYMOUS
         | 
| 71 | 
            +
                    meta = { mute_children: true }
         | 
| 72 | 
            +
                  end
         | 
| 73 | 
            +
             | 
| 74 | 
            +
                  # This is probably always overriden by execute_multiplex#normalize_after,
         | 
| 75 | 
            +
                  # but in the case of a single query, it will be the same value anyway.
         | 
| 76 | 
            +
                  trace.endpoint = "graphql:#{query_name}"
         | 
| 77 | 
            +
             | 
| 78 | 
            +
                  [CAT, "#{name}: #{query_name}", nil, meta]
         | 
| 79 | 
            +
                end
         | 
| 80 | 
            +
              end
         | 
| 81 | 
            +
             | 
| 82 | 
            +
              class ExecuteQueryLazy < ExecuteQuery
         | 
| 83 | 
            +
                register "graphql.execute_query_lazy"
         | 
| 84 | 
            +
             | 
| 85 | 
            +
                def normalize(trace, name, payload)
         | 
| 86 | 
            +
                  if payload[:query]
         | 
| 87 | 
            +
                    super
         | 
| 88 | 
            +
                  elsif payload[:multiplex]
         | 
| 89 | 
            +
                    [CAT, "#{name}.multiplex", nil]
         | 
| 90 | 
            +
                  end
         | 
| 91 | 
            +
                end
         | 
| 92 | 
            +
              end
         | 
| 93 | 
            +
            end
         | 
| @@ -9,19 +9,24 @@ module Skylight::Core | |
| 9 9 | 
             
                          def append_info_to_payload(payload)
         | 
| 10 10 | 
             
                            append_info_to_payload_without_sk(payload)
         | 
| 11 11 |  | 
| 12 | 
            -
                             | 
| 13 | 
            -
             | 
| 14 | 
            -
             | 
| 15 | 
            -
             | 
| 16 | 
            -
             | 
| 17 | 
            -
             | 
| 18 | 
            -
                               | 
| 19 | 
            -
             | 
| 20 | 
            -
                              end
         | 
| 12 | 
            +
                            payload[:sk_rendered_format] = sk_rendered_mime.try(:ref)
         | 
| 13 | 
            +
                            payload[:sk_variant] = request.respond_to?(:variant) ? request.variant : nil
         | 
| 14 | 
            +
                          end
         | 
| 15 | 
            +
             | 
| 16 | 
            +
                          def sk_rendered_mime
         | 
| 17 | 
            +
                            if respond_to?(:media_type)
         | 
| 18 | 
            +
                              mt = media_type
         | 
| 19 | 
            +
                              return mt && Mime::Type.lookup(mt)
         | 
| 21 20 | 
             
                            end
         | 
| 22 21 |  | 
| 23 | 
            -
                             | 
| 24 | 
            -
             | 
| 22 | 
            +
                            if content_type.is_a?(Mime::Type)
         | 
| 23 | 
            +
                              content_type
         | 
| 24 | 
            +
                            elsif content_type.respond_to?(:to_s)
         | 
| 25 | 
            +
                              type_str = content_type.to_s.split(';').first
         | 
| 26 | 
            +
                              Mime::Type.lookup(type_str) unless type_str.blank?
         | 
| 27 | 
            +
                            elsif respond_to?(:rendered_format) && rendered_format
         | 
| 28 | 
            +
                              rendered_format
         | 
| 29 | 
            +
                            end
         | 
| 25 30 | 
             
                          end
         | 
| 26 31 | 
             
                      end
         | 
| 27 32 | 
             
                    end
         | 
| @@ -9,7 +9,7 @@ module Skylight::Core | |
| 9 9 | 
             
                        alias execute_without_sk execute
         | 
| 10 10 |  | 
| 11 11 | 
             
                        def execute(*args)
         | 
| 12 | 
            -
                          Skylight.trace(TITLE, "app.job.execute") do |trace|
         | 
| 12 | 
            +
                          Skylight.trace(TITLE, "app.job.execute", component: :worker) do |trace|
         | 
| 13 13 | 
             
                            # See normalizers/active_job/perform for endpoint/segment assignment
         | 
| 14 14 | 
             
                            begin
         | 
| 15 15 | 
             
                              execute_without_sk(*args)
         | 
| @@ -24,7 +24,7 @@ module Skylight::Core | |
| 24 24 | 
             
                            UNKNOWN
         | 
| 25 25 | 
             
                          end
         | 
| 26 26 |  | 
| 27 | 
            -
                          Skylight.trace(handler_name, "app.delayed_job.worker", "Delayed::Worker#run", segment: job.queue) do
         | 
| 27 | 
            +
                          Skylight.trace(handler_name, "app.delayed_job.worker", "Delayed::Worker#run", component: :worker, segment: job.queue) do
         | 
| 28 28 | 
             
                            run_without_sk(job, *args)
         | 
| 29 29 | 
             
                          end
         | 
| 30 30 | 
             
                        end
         | 
| @@ -22,7 +22,7 @@ module Skylight | |
| 22 22 | 
             
                    def call(_worker, job, queue)
         | 
| 23 23 | 
             
                      t { "Sidekiq middleware beginning trace" }
         | 
| 24 24 | 
             
                      title = job["wrapped"] || job["class"]
         | 
| 25 | 
            -
                      @instrumentable.trace(title, "app.sidekiq.worker", title, segment: queue) do |trace|
         | 
| 25 | 
            +
                      @instrumentable.trace(title, "app.sidekiq.worker", title, segment: queue, component: :worker) do |trace|
         | 
| 26 26 | 
             
                        begin
         | 
| 27 27 | 
             
                          yield
         | 
| 28 28 | 
             
                        rescue Exception # includes Sidekiq::Shutdown
         | 
| @@ -50,14 +50,12 @@ module Skylight::Core | |
| 50 50 |  | 
| 51 51 | 
             
                  while (curr = trace.notifications.pop)
         | 
| 52 52 | 
             
                    next unless curr.name == name
         | 
| 53 | 
            -
             | 
| 54 | 
            -
             | 
| 55 | 
            -
                     | 
| 56 | 
            -
             | 
| 57 | 
            -
             | 
| 58 | 
            -
             | 
| 59 | 
            -
                      trace.done(curr.span, meta) if curr.span
         | 
| 60 | 
            -
                    end
         | 
| 53 | 
            +
             | 
| 54 | 
            +
                    meta = {}
         | 
| 55 | 
            +
                    meta[:exception] = payload[:exception] if payload[:exception]
         | 
| 56 | 
            +
                    meta[:exception_object] = payload[:exception_object] if payload[:exception_object]
         | 
| 57 | 
            +
                    trace.done(curr.span, meta) if curr.span
         | 
| 58 | 
            +
                    normalize_after(trace, curr.span, name, payload)
         | 
| 61 59 | 
             
                    return
         | 
| 62 60 | 
             
                  end
         | 
| 63 61 | 
             
                rescue Exception => e
         | 
    
        data/lib/skylight/core/trace.rb
    CHANGED
    
    | @@ -6,14 +6,14 @@ module Skylight::Core | |
| 6 6 |  | 
| 7 7 | 
             
                include Util::Logging
         | 
| 8 8 |  | 
| 9 | 
            -
                attr_reader :instrumenter, :endpoint, :notifications, :meta
         | 
| 10 | 
            -
                attr_accessor :uuid | 
| 9 | 
            +
                attr_reader :instrumenter, :endpoint, :segment, :notifications, :meta
         | 
| 10 | 
            +
                attr_accessor :uuid
         | 
| 11 11 |  | 
| 12 | 
            -
                def self.new(instrumenter, endpoint, start, cat, title = nil, desc = nil, meta: nil, segment: nil)
         | 
| 12 | 
            +
                def self.new(instrumenter, endpoint, start, cat, title = nil, desc = nil, meta: nil, segment: nil, component: nil)
         | 
| 13 13 | 
             
                  uuid = SecureRandom.uuid
         | 
| 14 14 | 
             
                  inst = native_new(normalize_time(start), uuid, endpoint, meta)
         | 
| 15 15 | 
             
                  inst.uuid = uuid
         | 
| 16 | 
            -
                  inst.send(:initialize, instrumenter, cat, title, desc, meta)
         | 
| 16 | 
            +
                  inst.send(:initialize, instrumenter, cat, title, desc, meta, component: component)
         | 
| 17 17 | 
             
                  inst.endpoint = endpoint
         | 
| 18 18 | 
             
                  inst.segment = segment
         | 
| 19 19 | 
             
                  inst
         | 
| @@ -26,7 +26,7 @@ module Skylight::Core | |
| 26 26 | 
             
                  (time.to_i / 100_000).to_i
         | 
| 27 27 | 
             
                end
         | 
| 28 28 |  | 
| 29 | 
            -
                def initialize(instrumenter, cat, title, desc, meta)
         | 
| 29 | 
            +
                def initialize(instrumenter, cat, title, desc, meta, **)
         | 
| 30 30 | 
             
                  raise ArgumentError, "instrumenter is required" unless instrumenter
         | 
| 31 31 |  | 
| 32 32 | 
             
                  @instrumenter = instrumenter
         | 
| @@ -51,14 +51,32 @@ module Skylight::Core | |
| 51 51 | 
             
                end
         | 
| 52 52 |  | 
| 53 53 | 
             
                def endpoint=(value)
         | 
| 54 | 
            +
                  if muted?
         | 
| 55 | 
            +
                    maybe_warn(:endpoint_set_muted, "tried to set endpoint name while muted")
         | 
| 56 | 
            +
                    return
         | 
| 57 | 
            +
                  end
         | 
| 54 58 | 
             
                  @endpoint = value
         | 
| 55 59 | 
             
                  native_set_endpoint(value)
         | 
| 56 60 | 
             
                end
         | 
| 57 61 |  | 
| 62 | 
            +
                def segment=(value)
         | 
| 63 | 
            +
                  if muted?
         | 
| 64 | 
            +
                    maybe_warn(:segment_set_muted, "tried to set segment name while muted")
         | 
| 65 | 
            +
                    return
         | 
| 66 | 
            +
                  end
         | 
| 67 | 
            +
                  @segment = value
         | 
| 68 | 
            +
                end
         | 
| 69 | 
            +
             | 
| 70 | 
            +
                attr_accessor :compound_response_error_status
         | 
| 71 | 
            +
             | 
| 58 72 | 
             
                def config
         | 
| 59 73 | 
             
                  @instrumenter.config
         | 
| 60 74 | 
             
                end
         | 
| 61 75 |  | 
| 76 | 
            +
                def muted?
         | 
| 77 | 
            +
                  !!@child_instrumentation_muted_by || @instrumenter.muted?
         | 
| 78 | 
            +
                end
         | 
| 79 | 
            +
             | 
| 62 80 | 
             
                def broken?
         | 
| 63 81 | 
             
                  !!@broken
         | 
| 64 82 | 
             
                end
         | 
| @@ -69,7 +87,7 @@ module Skylight::Core | |
| 69 87 | 
             
                end
         | 
| 70 88 |  | 
| 71 89 | 
             
                def record(cat, title = nil, desc = nil)
         | 
| 72 | 
            -
                  return if broken?
         | 
| 90 | 
            +
                  return if muted? || broken?
         | 
| 73 91 |  | 
| 74 92 | 
             
                  title.freeze if title.is_a?(String)
         | 
| 75 93 | 
             
                  desc.freeze  if desc.is_a?(String)
         | 
| @@ -87,6 +105,7 @@ module Skylight::Core | |
| 87 105 | 
             
                end
         | 
| 88 106 |  | 
| 89 107 | 
             
                def instrument(cat, title = nil, desc = nil, meta = nil)
         | 
| 108 | 
            +
                  return if muted?
         | 
| 90 109 | 
             
                  return if broken?
         | 
| 91 110 | 
             
                  t { "instrument: #{cat}, #{title}" }
         | 
| 92 111 |  | 
| @@ -119,10 +138,9 @@ module Skylight::Core | |
| 119 138 | 
             
                  # `span` will be `nil` if we failed to start instrumenting, such as in
         | 
| 120 139 | 
             
                  # the case of too many spans in a request.
         | 
| 121 140 | 
             
                  return unless span
         | 
| 122 | 
            -
             | 
| 123 141 | 
             
                  return if broken?
         | 
| 124 142 |  | 
| 125 | 
            -
                  if meta | 
| 143 | 
            +
                  if meta&.[](:defer)
         | 
| 126 144 | 
             
                    deferred_spans[span] ||= (Util::Clock.nanos - gc_time)
         | 
| 127 145 | 
             
                    return
         | 
| 128 146 | 
             
                  end
         | 
| @@ -199,6 +217,8 @@ module Skylight::Core | |
| 199 217 | 
             
                  def start(time, cat, title, desc, meta, opts = {})
         | 
| 200 218 | 
             
                    time = self.class.normalize_time(time) unless opts[:normalize] == false
         | 
| 201 219 |  | 
| 220 | 
            +
                    mute_children = meta&.delete(:mute_children)
         | 
| 221 | 
            +
             | 
| 202 222 | 
             
                    sp = native_start_span(time, cat.to_s)
         | 
| 203 223 | 
             
                    native_span_set_title(sp, title.to_s) if title
         | 
| 204 224 | 
             
                    native_span_set_description(sp, desc.to_s) if desc
         | 
| @@ -208,9 +228,18 @@ module Skylight::Core | |
| 208 228 | 
             
                    @spans << sp
         | 
| 209 229 | 
             
                    t { "started span: #{sp} - #{cat}, #{title}" }
         | 
| 210 230 |  | 
| 231 | 
            +
                    if mute_children
         | 
| 232 | 
            +
                      t { "muting child instrumentation for span=#{sp}" }
         | 
| 233 | 
            +
                      mute_child_instrumentation(sp)
         | 
| 234 | 
            +
                    end
         | 
| 235 | 
            +
             | 
| 211 236 | 
             
                    sp
         | 
| 212 237 | 
             
                  end
         | 
| 213 238 |  | 
| 239 | 
            +
                  def mute_child_instrumentation(span)
         | 
| 240 | 
            +
                    @child_instrumentation_muted_by = span
         | 
| 241 | 
            +
                  end
         | 
| 242 | 
            +
             | 
| 214 243 | 
             
                  # Middleware spans that were interrupted by a throw/catch should be cached here.
         | 
| 215 244 | 
             
                  # keys: span ids
         | 
| 216 245 | 
             
                  # values: nsec timestamp at which the span was cached here.
         | 
| @@ -237,6 +266,10 @@ module Skylight::Core | |
| 237 266 | 
             
                  def normalized_stop(span, time)
         | 
| 238 267 | 
             
                    time = self.class.normalize_time(time)
         | 
| 239 268 | 
             
                    native_stop_span(span, time)
         | 
| 269 | 
            +
             | 
| 270 | 
            +
                    if @child_instrumentation_muted_by == span
         | 
| 271 | 
            +
                      @child_instrumentation_muted_by = nil # restart instrumenting
         | 
| 272 | 
            +
                    end
         | 
| 240 273 | 
             
                  end
         | 
| 241 274 |  | 
| 242 275 | 
             
                  # Originally extracted from `stop`.
         | 
| @@ -271,5 +304,16 @@ module Skylight::Core | |
| 271 304 | 
             
                    @gc.update
         | 
| 272 305 | 
             
                    @gc.time
         | 
| 273 306 | 
             
                  end
         | 
| 307 | 
            +
             | 
| 308 | 
            +
                  def maybe_warn(context, msg)
         | 
| 309 | 
            +
                    return if warnings_silenced?(context)
         | 
| 310 | 
            +
                    instrumenter.silence_warnings(context)
         | 
| 311 | 
            +
             | 
| 312 | 
            +
                    warn(msg)
         | 
| 313 | 
            +
                  end
         | 
| 314 | 
            +
             | 
| 315 | 
            +
                  def warnings_silenced?(context)
         | 
| 316 | 
            +
                    instrumenter.warnings_silenced?(context)
         | 
| 317 | 
            +
                  end
         | 
| 274 318 | 
             
              end
         | 
| 275 319 | 
             
            end
         | 
    
        metadata
    CHANGED
    
    | @@ -1,14 +1,14 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: skylight-core
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 4. | 
| 4 | 
            +
              version: 4.2.0.beta
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Tilde, Inc.
         | 
| 8 8 | 
             
            autorequire: 
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date: 2019- | 
| 11 | 
            +
            date: 2019-08-19 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 14 | 
             
              name: activesupport
         | 
| @@ -204,6 +204,7 @@ files: | |
| 204 204 | 
             
            - lib/skylight/core/normalizers/grape/format_response.rb
         | 
| 205 205 | 
             
            - lib/skylight/core/normalizers/graphiti/render.rb
         | 
| 206 206 | 
             
            - lib/skylight/core/normalizers/graphiti/resolve.rb
         | 
| 207 | 
            +
            - lib/skylight/core/normalizers/graphql/base.rb
         | 
| 207 208 | 
             
            - lib/skylight/core/normalizers/moped/query.rb
         | 
| 208 209 | 
             
            - lib/skylight/core/normalizers/render.rb
         | 
| 209 210 | 
             
            - lib/skylight/core/normalizers/sequel/sql.rb
         | 
| @@ -263,9 +264,9 @@ required_ruby_version: !ruby/object:Gem::Requirement | |
| 263 264 | 
             
                  version: '2.3'
         | 
| 264 265 | 
             
            required_rubygems_version: !ruby/object:Gem::Requirement
         | 
| 265 266 | 
             
              requirements:
         | 
| 266 | 
            -
              - - " | 
| 267 | 
            +
              - - ">"
         | 
| 267 268 | 
             
                - !ruby/object:Gem::Version
         | 
| 268 | 
            -
                  version:  | 
| 269 | 
            +
                  version: 1.3.1
         | 
| 269 270 | 
             
            requirements: []
         | 
| 270 271 | 
             
            rubygems_version: 3.0.3
         | 
| 271 272 | 
             
            signing_key: 
         |