Commit cd361af8 authored by Yorick Peterse's avatar Yorick Peterse

Merge branch 'add-metrics-initializer-spec' into 'master'

Add metric initializer spec

See merge request !8714
parents 21f53806 a96765e6
if Gitlab::Metrics.enabled? # Autoload all classes that we want to instrument, and instrument the methods we
require 'pathname' # need. This takes the Gitlab::Metrics::Instrumentation module as an argument so
require 'influxdb' # that we can stub it for testing, as it is only called when metrics are
require 'connection_pool' # enabled.
require 'method_source' #
# rubocop:disable Metrics/AbcSize
# These are manually require'd so the classes are registered properly with def instrument_classes(instrumentation)
# ActiveSupport. instrumentation.instrument_instance_methods(Gitlab::Shell)
require 'gitlab/metrics/subscribers/action_view'
require 'gitlab/metrics/subscribers/active_record'
require 'gitlab/metrics/subscribers/rails_cache'
Gitlab::Application.configure do |config|
config.middleware.use(Gitlab::Metrics::RackMiddleware)
config.middleware.use(Gitlab::Middleware::RailsQueueDuration)
end
Sidekiq.configure_server do |config|
config.server_middleware do |chain|
chain.add Gitlab::Metrics::SidekiqMiddleware
end
end
# This instruments all methods residing in app/models that (appear to) use any
# of the ActiveRecord methods. This has to take place _after_ initializing as
# for some unknown reason calling eager_load! earlier breaks Devise.
Gitlab::Application.config.after_initialize do
Rails.application.eager_load!
models = Rails.root.join('app', 'models').to_s
regex = Regexp.union(
ActiveRecord::Querying.public_instance_methods(false).map(&:to_s)
)
Gitlab::Metrics::Instrumentation.
instrument_class_hierarchy(ActiveRecord::Base) do |klass, method|
# Instrumenting the ApplicationSetting class can lead to an infinite
# loop. Since the data is cached any way we don't really need to
# instrument it.
if klass == ApplicationSetting
false
else
loc = method.source_location
loc && loc[0].start_with?(models) && method.source =~ regex instrumentation.instrument_methods(Gitlab::Git)
end
end
end
Gitlab::Metrics::Instrumentation.configure do |config|
config.instrument_instance_methods(Gitlab::Shell)
config.instrument_methods(Gitlab::Git)
Gitlab::Git.constants.each do |name| Gitlab::Git.constants.each do |name|
const = Gitlab::Git.const_get(name) const = Gitlab::Git.const_get(name)
next unless const.is_a?(Module) next unless const.is_a?(Module)
config.instrument_methods(const) instrumentation.instrument_methods(const)
config.instrument_instance_methods(const) instrumentation.instrument_instance_methods(const)
end end
# Path to search => prefix to strip from constant # Path to search => prefix to strip from constant
...@@ -80,13 +36,13 @@ if Gitlab::Metrics.enabled? ...@@ -80,13 +36,13 @@ if Gitlab::Metrics.enabled?
path = Pathname.new(file_path).relative_path_from(prefix) path = Pathname.new(file_path).relative_path_from(prefix)
const = path.to_s.sub('.rb', '').camelize.constantize const = path.to_s.sub('.rb', '').camelize.constantize
config.instrument_methods(const) instrumentation.instrument_methods(const)
config.instrument_instance_methods(const) instrumentation.instrument_instance_methods(const)
end end
end end
config.instrument_methods(Premailer::Adapter::Nokogiri) instrumentation.instrument_methods(Premailer::Adapter::Nokogiri)
config.instrument_instance_methods(Premailer::Adapter::Nokogiri) instrumentation.instrument_instance_methods(Premailer::Adapter::Nokogiri)
[ [
:Blame, :Branch, :BranchCollection, :Blob, :Commit, :Diff, :Repository, :Blame, :Branch, :BranchCollection, :Blob, :Commit, :Diff, :Repository,
...@@ -94,8 +50,8 @@ if Gitlab::Metrics.enabled? ...@@ -94,8 +50,8 @@ if Gitlab::Metrics.enabled?
].each do |name| ].each do |name|
const = Rugged.const_get(name) const = Rugged.const_get(name)
config.instrument_methods(const) instrumentation.instrument_methods(const)
config.instrument_instance_methods(const) instrumentation.instrument_instance_methods(const)
end end
# Instruments all Banzai filters and reference parsers # Instruments all Banzai filters and reference parsers
...@@ -107,52 +63,107 @@ if Gitlab::Metrics.enabled? ...@@ -107,52 +63,107 @@ if Gitlab::Metrics.enabled?
klass = File.basename(file, File.extname(file)).camelize klass = File.basename(file, File.extname(file)).camelize
const = Banzai.const_get(const_name).const_get(klass) const = Banzai.const_get(const_name).const_get(klass)
config.instrument_methods(const) instrumentation.instrument_methods(const)
config.instrument_instance_methods(const) instrumentation.instrument_instance_methods(const)
end end
end end
config.instrument_methods(Banzai::Renderer) instrumentation.instrument_methods(Banzai::Renderer)
config.instrument_methods(Banzai::Querying) instrumentation.instrument_methods(Banzai::Querying)
config.instrument_instance_methods(Banzai::ObjectRenderer) instrumentation.instrument_instance_methods(Banzai::ObjectRenderer)
config.instrument_instance_methods(Banzai::Redactor) instrumentation.instrument_instance_methods(Banzai::Redactor)
config.instrument_methods(Banzai::NoteRenderer) instrumentation.instrument_methods(Banzai::NoteRenderer)
[Issuable, Mentionable, Participable].each do |klass| [Issuable, Mentionable, Participable].each do |klass|
config.instrument_instance_methods(klass) instrumentation.instrument_instance_methods(klass)
config.instrument_instance_methods(klass::ClassMethods) instrumentation.instrument_instance_methods(klass::ClassMethods)
end end
config.instrument_methods(Gitlab::ReferenceExtractor) instrumentation.instrument_methods(Gitlab::ReferenceExtractor)
config.instrument_instance_methods(Gitlab::ReferenceExtractor) instrumentation.instrument_instance_methods(Gitlab::ReferenceExtractor)
# Instrument the classes used for checking if somebody has push access. # Instrument the classes used for checking if somebody has push access.
config.instrument_instance_methods(Gitlab::GitAccess) instrumentation.instrument_instance_methods(Gitlab::GitAccess)
config.instrument_instance_methods(Gitlab::GitAccessWiki) instrumentation.instrument_instance_methods(Gitlab::GitAccessWiki)
config.instrument_instance_methods(API::Helpers) instrumentation.instrument_instance_methods(API::Helpers)
config.instrument_instance_methods(RepositoryCheck::SingleRepositoryWorker) instrumentation.instrument_instance_methods(RepositoryCheck::SingleRepositoryWorker)
config.instrument_instance_methods(Rouge::Plugins::Redcarpet) instrumentation.instrument_instance_methods(Rouge::Plugins::Redcarpet)
config.instrument_instance_methods(Rouge::Formatters::HTMLGitlab) instrumentation.instrument_instance_methods(Rouge::Formatters::HTMLGitlab)
[:XML, :HTML].each do |namespace| [:XML, :HTML].each do |namespace|
namespace_mod = Nokogiri.const_get(namespace) namespace_mod = Nokogiri.const_get(namespace)
config.instrument_methods(namespace_mod) instrumentation.instrument_methods(namespace_mod)
config.instrument_methods(namespace_mod::Document) instrumentation.instrument_methods(namespace_mod::Document)
end end
config.instrument_methods(Rinku) instrumentation.instrument_methods(Rinku)
config.instrument_instance_methods(Repository) instrumentation.instrument_instance_methods(Repository)
config.instrument_methods(Gitlab::Highlight) instrumentation.instrument_methods(Gitlab::Highlight)
config.instrument_instance_methods(Gitlab::Highlight) instrumentation.instrument_instance_methods(Gitlab::Highlight)
# This is a Rails scope so we have to instrument it manually. # This is a Rails scope so we have to instrument it manually.
config.instrument_method(Project, :visible_to_user) instrumentation.instrument_method(Project, :visible_to_user)
end
# rubocop:enable Metrics/AbcSize
if Gitlab::Metrics.enabled?
require 'pathname'
require 'influxdb'
require 'connection_pool'
require 'method_source'
# These are manually require'd so the classes are registered properly with
# ActiveSupport.
require 'gitlab/metrics/subscribers/action_view'
require 'gitlab/metrics/subscribers/active_record'
require 'gitlab/metrics/subscribers/rails_cache'
Gitlab::Application.configure do |config|
config.middleware.use(Gitlab::Metrics::RackMiddleware)
config.middleware.use(Gitlab::Middleware::RailsQueueDuration)
end
Sidekiq.configure_server do |config|
config.server_middleware do |chain|
chain.add Gitlab::Metrics::SidekiqMiddleware
end
end
# This instruments all methods residing in app/models that (appear to) use any
# of the ActiveRecord methods. This has to take place _after_ initializing as
# for some unknown reason calling eager_load! earlier breaks Devise.
Gitlab::Application.config.after_initialize do
Rails.application.eager_load!
models = Rails.root.join('app', 'models').to_s
regex = Regexp.union(
ActiveRecord::Querying.public_instance_methods(false).map(&:to_s)
)
Gitlab::Metrics::Instrumentation.
instrument_class_hierarchy(ActiveRecord::Base) do |klass, method|
# Instrumenting the ApplicationSetting class can lead to an infinite
# loop. Since the data is cached any way we don't really need to
# instrument it.
if klass == ApplicationSetting
false
else
loc = method.source_location
loc && loc[0].start_with?(models) && method.source =~ regex
end
end
end
Gitlab::Metrics::Instrumentation.configure do |config|
instrument_classes(config)
end end
GC::Profiler.enable GC::Profiler.enable
......
require 'spec_helper'
require_relative '../../config/initializers/metrics'
describe 'instrument_classes', lib: true do
let(:config) { double(:config) }
before do
allow(config).to receive(:instrument_method)
allow(config).to receive(:instrument_methods)
allow(config).to receive(:instrument_instance_methods)
end
it 'can autoload and instrument all files' do
expect { instrument_classes(config) }.not_to raise_error
end
end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment