rails_mini_profiler 0

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.
Files changed (146) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +20 -0
  3. data/README.md +302 -0
  4. data/app/assets/config/rails_mini_profiler_manifest.js +1 -0
  5. data/app/assets/javascripts/rails_mini_profiler.js +15 -0
  6. data/app/assets/stylesheets/rails_mini_profiler/application.css +16 -0
  7. data/app/controllers/rails_mini_profiler/application_controller.rb +33 -0
  8. data/app/controllers/rails_mini_profiler/flamegraphs_controller.rb +23 -0
  9. data/app/controllers/rails_mini_profiler/profiled_requests_controller.rb +68 -0
  10. data/app/helpers/rails_mini_profiler/application_helper.rb +23 -0
  11. data/app/helpers/rails_mini_profiler/profiled_requests_helper.rb +16 -0
  12. data/app/javascript/images/bookmark.svg +10 -0
  13. data/app/javascript/images/chart.svg +12 -0
  14. data/app/javascript/images/check.svg +3 -0
  15. data/app/javascript/images/chevron.svg +3 -0
  16. data/app/javascript/images/delete.svg +9 -0
  17. data/app/javascript/images/filter.svg +1 -0
  18. data/app/javascript/images/graph.svg +11 -0
  19. data/app/javascript/images/logo.svg +18 -0
  20. data/app/javascript/images/logo_variant.svg +32 -0
  21. data/app/javascript/images/search.svg +9 -0
  22. data/app/javascript/images/setting.svg +10 -0
  23. data/app/javascript/images/show.svg +11 -0
  24. data/app/javascript/js/checklist_controller.js +48 -0
  25. data/app/javascript/js/enable_controller.js +24 -0
  26. data/app/javascript/js/filter_controller.js +44 -0
  27. data/app/javascript/js/search_controller.js +18 -0
  28. data/app/javascript/js/select_controller.js +47 -0
  29. data/app/javascript/packs/rails-mini-profiler.js +88 -0
  30. data/app/javascript/stylesheets/components/page_header/page_header.scss +3 -0
  31. data/app/javascript/stylesheets/components/pagination.scss +55 -0
  32. data/app/javascript/stylesheets/components/profiled_request_table/placeholder.scss +33 -0
  33. data/app/javascript/stylesheets/components/profiled_request_table/profiled_request_table.scss +179 -0
  34. data/app/javascript/stylesheets/flamegraph.scss +10 -0
  35. data/app/javascript/stylesheets/flashes.scss +15 -0
  36. data/app/javascript/stylesheets/navbar.scss +44 -0
  37. data/app/javascript/stylesheets/profiled_requests.scss +89 -0
  38. data/app/javascript/stylesheets/rails-mini-profiler.scss +205 -0
  39. data/app/javascript/stylesheets/traces.scss +82 -0
  40. data/app/models/rails_mini_profiler/application_record.rb +17 -0
  41. data/app/models/rails_mini_profiler/controller_trace.rb +37 -0
  42. data/app/models/rails_mini_profiler/flamegraph.rb +37 -0
  43. data/app/models/rails_mini_profiler/instantiation_trace.rb +37 -0
  44. data/app/models/rails_mini_profiler/profiled_request.rb +65 -0
  45. data/app/models/rails_mini_profiler/render_partial_trace.rb +37 -0
  46. data/app/models/rails_mini_profiler/render_template_trace.rb +37 -0
  47. data/app/models/rails_mini_profiler/rmp_trace.rb +35 -0
  48. data/app/models/rails_mini_profiler/sequel_trace.rb +37 -0
  49. data/app/models/rails_mini_profiler/trace.rb +46 -0
  50. data/app/presenters/rails_mini_profiler/base_presenter.rb +25 -0
  51. data/app/presenters/rails_mini_profiler/controller_trace_presenter.rb +18 -0
  52. data/app/presenters/rails_mini_profiler/instantiation_trace_presenter.rb +14 -0
  53. data/app/presenters/rails_mini_profiler/profiled_request_presenter.rb +38 -0
  54. data/app/presenters/rails_mini_profiler/render_partial_trace_presenter.rb +11 -0
  55. data/app/presenters/rails_mini_profiler/render_template_trace_presenter.rb +15 -0
  56. data/app/presenters/rails_mini_profiler/rmp_trace_presenter.rb +9 -0
  57. data/app/presenters/rails_mini_profiler/sequel_trace_presenter.rb +69 -0
  58. data/app/presenters/rails_mini_profiler/trace_presenter.rb +61 -0
  59. data/app/search/rails_mini_profiler/base_search.rb +67 -0
  60. data/app/search/rails_mini_profiler/profiled_request_search.rb +34 -0
  61. data/app/views/layouts/rails_mini_profiler/application.html.erb +15 -0
  62. data/app/views/layouts/rails_mini_profiler/flamegraph.html.erb +11 -0
  63. data/app/views/models/_flamegraph.json.jb +3 -0
  64. data/app/views/models/_profiled_request.jb +3 -0
  65. data/app/views/models/_trace.jb +3 -0
  66. data/app/views/rails_mini_profiler/badge.html.erb +37 -0
  67. data/app/views/rails_mini_profiler/flamegraphs/show.html.erb +13 -0
  68. data/app/views/rails_mini_profiler/flamegraphs/show.json.jb +3 -0
  69. data/app/views/rails_mini_profiler/profiled_requests/index.html.erb +9 -0
  70. data/app/views/rails_mini_profiler/profiled_requests/index.json.jb +3 -0
  71. data/app/views/rails_mini_profiler/profiled_requests/shared/_trace.html.erb +40 -0
  72. data/app/views/rails_mini_profiler/profiled_requests/shared/header/_header.erb +20 -0
  73. data/app/views/rails_mini_profiler/profiled_requests/shared/table/_placeholder.erb +12 -0
  74. data/app/views/rails_mini_profiler/profiled_requests/shared/table/_table.erb +14 -0
  75. data/app/views/rails_mini_profiler/profiled_requests/shared/table/_table_head.erb +125 -0
  76. data/app/views/rails_mini_profiler/profiled_requests/shared/table/_table_row.erb +21 -0
  77. data/app/views/rails_mini_profiler/profiled_requests/show.html.erb +40 -0
  78. data/app/views/rails_mini_profiler/profiled_requests/show.json.jb +5 -0
  79. data/app/views/rails_mini_profiler/shared/_flashes.html.erb +8 -0
  80. data/app/views/rails_mini_profiler/shared/_head.erb +13 -0
  81. data/app/views/rails_mini_profiler/shared/_navbar.html.erb +15 -0
  82. data/config/routes.rb +11 -0
  83. data/db/migrate/20210621185018_create_rmp.rb +46 -0
  84. data/lib/generators/rails_mini_profiler/USAGE +2 -0
  85. data/lib/generators/rails_mini_profiler/install_generator.rb +40 -0
  86. data/lib/generators/rails_mini_profiler/templates/rails_mini_profiler.js.erb +13 -0
  87. data/lib/generators/rails_mini_profiler/templates/rails_mini_profiler.rb.erb +29 -0
  88. data/lib/rails_mini_profiler/badge.rb +84 -0
  89. data/lib/rails_mini_profiler/configuration/storage.rb +47 -0
  90. data/lib/rails_mini_profiler/configuration/user_interface.rb +48 -0
  91. data/lib/rails_mini_profiler/configuration.rb +65 -0
  92. data/lib/rails_mini_profiler/engine.rb +34 -0
  93. data/lib/rails_mini_profiler/flamegraph_guard.rb +47 -0
  94. data/lib/rails_mini_profiler/guard.rb +57 -0
  95. data/lib/rails_mini_profiler/logger.rb +25 -0
  96. data/lib/rails_mini_profiler/middleware.rb +74 -0
  97. data/lib/rails_mini_profiler/models/base_model.rb +23 -0
  98. data/lib/rails_mini_profiler/redirect.rb +33 -0
  99. data/lib/rails_mini_profiler/request_context.rb +86 -0
  100. data/lib/rails_mini_profiler/request_wrapper.rb +69 -0
  101. data/lib/rails_mini_profiler/response_wrapper.rb +32 -0
  102. data/lib/rails_mini_profiler/tracing/controller_tracer.rb +15 -0
  103. data/lib/rails_mini_profiler/tracing/null_trace.rb +7 -0
  104. data/lib/rails_mini_profiler/tracing/sequel_tracer.rb +37 -0
  105. data/lib/rails_mini_profiler/tracing/sequel_tracker.rb +37 -0
  106. data/lib/rails_mini_profiler/tracing/subscriptions.rb +34 -0
  107. data/lib/rails_mini_profiler/tracing/trace.rb +45 -0
  108. data/lib/rails_mini_profiler/tracing/trace_factory.rb +37 -0
  109. data/lib/rails_mini_profiler/tracing/tracer.rb +31 -0
  110. data/lib/rails_mini_profiler/tracing/view_tracer.rb +12 -0
  111. data/lib/rails_mini_profiler/tracing.rb +11 -0
  112. data/lib/rails_mini_profiler/user.rb +40 -0
  113. data/lib/rails_mini_profiler/version.rb +5 -0
  114. data/lib/rails_mini_profiler.rb +79 -0
  115. data/lib/tasks/rails_mini_profiler_tasks.rake +8 -0
  116. data/public/rails_mini_profiler/speedscope/LICENSE +21 -0
  117. data/public/rails_mini_profiler/speedscope/demangle-cpp.1768f4cc.js +4 -0
  118. data/public/rails_mini_profiler/speedscope/demangle-cpp.1768f4cc.js.map +1 -0
  119. data/public/rails_mini_profiler/speedscope/favicon-16x16.f74b3187.png +0 -0
  120. data/public/rails_mini_profiler/speedscope/favicon-32x32.bc503437.png +0 -0
  121. data/public/rails_mini_profiler/speedscope/file-format-schema.json +324 -0
  122. data/public/rails_mini_profiler/speedscope/import.e3a73ef4.js +117 -0
  123. data/public/rails_mini_profiler/speedscope/import.e3a73ef4.js.map +1 -0
  124. data/public/rails_mini_profiler/speedscope/index.html +2 -0
  125. data/public/rails_mini_profiler/speedscope/release.txt +3 -0
  126. data/public/rails_mini_profiler/speedscope/reset.8c46b7a1.css +2 -0
  127. data/public/rails_mini_profiler/speedscope/reset.8c46b7a1.css.map +1 -0
  128. data/public/rails_mini_profiler/speedscope/source-map.438fa06b.js +24 -0
  129. data/public/rails_mini_profiler/speedscope/source-map.438fa06b.js.map +1 -0
  130. data/public/rails_mini_profiler/speedscope/speedscope.026f36b0.js +200 -0
  131. data/public/rails_mini_profiler/speedscope/speedscope.026f36b0.js.map +1 -0
  132. data/vendor/assets/images/bookmark.svg +10 -0
  133. data/vendor/assets/images/chart.svg +12 -0
  134. data/vendor/assets/images/check.svg +3 -0
  135. data/vendor/assets/images/chevron.svg +3 -0
  136. data/vendor/assets/images/delete.svg +9 -0
  137. data/vendor/assets/images/filter.svg +1 -0
  138. data/vendor/assets/images/graph.svg +11 -0
  139. data/vendor/assets/images/logo.svg +18 -0
  140. data/vendor/assets/images/logo_variant.svg +32 -0
  141. data/vendor/assets/images/search.svg +9 -0
  142. data/vendor/assets/images/setting.svg +10 -0
  143. data/vendor/assets/images/show.svg +11 -0
  144. data/vendor/assets/javascripts/rails-mini-profiler.css +1 -0
  145. data/vendor/assets/javascripts/rails-mini-profiler.js +1 -0
  146. metadata +248 -0
@@ -0,0 +1,13 @@
1
+ import "@rails-mini-profiler/assets"
2
+
3
+ // Import styles
4
+ import "@rails-mini-profiler/assets/dist/rails-mini-profiler.css";
5
+
6
+ // Import images
7
+ //
8
+ // You may simplify this when using a glob loader (e.g glob-import-loader)
9
+ <%- Dir.chdir(RailsMiniProfiler::Engine.root.join('app/javascript/images')) do -%>
10
+ <%- Dir.glob('**/*').each do |file| -%>
11
+ import "@rails-mini-profiler/assets/dist/images/<%= file %>";
12
+ <%- end -%>
13
+ <%- end -%>
@@ -0,0 +1,29 @@
1
+ # Rails Mini Profiler Initializer (<%= RailsMiniProfiler::VERSION %>)
2
+
3
+ # Customize to your hearts content. If you remove this file, Rails Mini Profiler will use sensible defaults.
4
+ # For more information see https://github.com/hschne/rails-mini-profiler#configuration
5
+ RailsMiniProfiler.configure do |config|
6
+ # Customize when Rails Mini Profiler should run
7
+ config.enabled = proc { |env| Rails.env.development? || env['HTTP_RMP_ENABLED'].present? }
8
+
9
+ # Configure Flamegraph generation
10
+ config.flamegraph_enabled = true
11
+ # config.flamegraph_sample_rate = 0.5
12
+
13
+ # Configure endpoints to profile
14
+ config.skip_paths = []
15
+
16
+ # Configure how Rails Mini Profiler stores profiling information
17
+ # config.storage.database = :rmp_database
18
+ # config.storage.profiled_requests_table = :rmp_profiled_requests
19
+ # config.storage.traces_table = :rmp_traces
20
+ # config.storage.flamegraphs_table = :rmp_flamegraphs
21
+
22
+ # Configure the Rails Mini Profiler User Interface
23
+ # config.ui.badge_enabled = true
24
+ # config.ui.badge_position = 'top-left'
25
+ # config.ui.page_size = 25
26
+
27
+ # Customize how users are detected
28
+ config.user_provider = proc { |env| Rack::Request.new(env).ip }
29
+ end
@@ -0,0 +1,84 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../../app/helpers/rails_mini_profiler/application_helper'
4
+
5
+ module RailsMiniProfiler
6
+ # Wraps functionality to render an interactive badge on top of HTML responses
7
+ #
8
+ # @api private
9
+ class Badge
10
+ include InlineSvg::ActionView::Helpers
11
+ include RailsMiniProfiler::ApplicationHelper
12
+ include Engine.routes.url_helpers
13
+
14
+ # @param request_context [RequestContext] The current request context
15
+ # @param configuration [Configuration] The current configuration
16
+ def initialize(request_context, configuration: RailsMiniProfiler.configuration)
17
+ @configuration = configuration
18
+ @profiled_request = request_context.profiled_request
19
+ @original_response = request_context.response
20
+ end
21
+
22
+ # Inject the badge into the response
23
+ #
24
+ # @return [ResponseWrapper] The modified response
25
+ def render
26
+ content_type = @original_response.headers['Content-Type']
27
+ return @original_response unless content_type =~ %r{text/html}
28
+
29
+ return @original_response unless @configuration.ui.badge_enabled
30
+
31
+ modified_response = Rack::Response.new([], @original_response.status, @original_response.headers)
32
+ modified_response.write(modified_body)
33
+ modified_response.finish
34
+
35
+ response = @original_response.response
36
+ response.close if response.respond_to?(:close)
37
+
38
+ ResponseWrapper.new(@original_response.status,
39
+ @original_response.headers,
40
+ modified_response)
41
+ end
42
+
43
+ private
44
+
45
+ # Modify the body of the original response
46
+ #
47
+ # @return String The modified body
48
+ def modified_body
49
+ body = @original_response.response.body
50
+ index = body.rindex(%r{</body>}i) || body.rindex(%r{</html>}i)
51
+ if index
52
+ body.dup.insert(index, badge_content)
53
+ else
54
+ body
55
+ end
56
+ end
57
+
58
+ # Render the badge template
59
+ #
60
+ # @return String The badge HTML content to be injected
61
+ def badge_content
62
+ html = IO.read(File.expand_path('../../app/views/rails_mini_profiler/badge.html.erb', __dir__))
63
+ @position = css_position
64
+ template = ERB.new(html)
65
+ template.result(binding)
66
+ end
67
+
68
+ # Transform the configuration position into CSS style positions
69
+ #
70
+ # @return String The badge position as CSS style
71
+ def css_position
72
+ case @configuration.ui.badge_position
73
+ when 'top-right'
74
+ 'top: 5px; right: 5px;'
75
+ when 'bottom-left'
76
+ 'bottom: 5px; left: 5px;'
77
+ when 'bottom-right'
78
+ 'bottom: 5px; right: 5px;'
79
+ else
80
+ 'top: 5px; left: 5px;'
81
+ end
82
+ end
83
+ end
84
+ end
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ # Configure how profiling data is stored within your Rails app.
5
+ #
6
+ # @!attribute database
7
+ # @return [Symbol] which database to connect to
8
+ # @!attribute profiled_requests_table
9
+ # @return [Symbol] where to store profiled requests
10
+ # @!attribute traces_table
11
+ # @return [Symbol] where to store traces
12
+ # @!attribute flamegraphs_table
13
+ # @return [Symbol] where to store flamegraphs
14
+ class Storage
15
+ class << self
16
+ # Construct a new configuration instance
17
+ #
18
+ # @return [Storage] a new storage configuration
19
+ def configuration
20
+ @configuration ||= new
21
+ end
22
+
23
+ # Configure how profiling data is stored
24
+ #
25
+ # @yieldreturn [Storage] a new storage configuration object
26
+ def configure
27
+ yield(configuration)
28
+ configuration
29
+ end
30
+ end
31
+
32
+ attr_accessor :database, :profiled_requests_table, :traces_table, :flamegraphs_table
33
+
34
+ def initialize(**kwargs)
35
+ defaults!
36
+ kwargs.each { |key, value| instance_variable_set("@#{key}", value) }
37
+ end
38
+
39
+ # Reset the configuration to default values
40
+ def defaults!
41
+ @database = nil
42
+ @profiled_requests_table = 'rmp_profiled_requests'
43
+ @flamegraphs_table = 'rmp_flamegraphs'
44
+ @traces_table = 'rmp_traces'
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,48 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ # Configure various aspects about Rails Mini Profilers UI.
5
+ #
6
+ # @!attribute badge_enabled
7
+ # @see Badge
8
+ # @return [Boolean] if the badge should be enabled
9
+ # @!attribute badge_position
10
+ # @see Badge
11
+ # @return [String] the position of the interactive HTML badge
12
+ # @!attribute page_size
13
+ # @return [Integer] how many items to render per page in list views
14
+ class UserInterface
15
+ class << self
16
+ # Construct a new UI configuration instance
17
+ #
18
+ # @return [UserInterface] a new storage configuration
19
+ def configuration
20
+ @configuration ||= new
21
+ end
22
+
23
+ # Configure how profiling data is shown to the user
24
+ #
25
+ # @yieldreturn [UserInterface] a new UI configuration object
26
+ def configure
27
+ yield(configuration)
28
+ configuration
29
+ end
30
+ end
31
+
32
+ attr_accessor :badge_enabled,
33
+ :badge_position,
34
+ :page_size
35
+
36
+ def initialize(**kwargs)
37
+ defaults!
38
+ kwargs.each { |key, value| instance_variable_set("@#{key}", value) }
39
+ end
40
+
41
+ # Reset the configuration to default values
42
+ def defaults!
43
+ @badge_enabled = true
44
+ @badge_position = 'top-left'
45
+ @page_size = 25
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'rails_mini_profiler/configuration/storage'
4
+ require 'rails_mini_profiler/configuration/user_interface'
5
+
6
+ module RailsMiniProfiler
7
+ # The main Rails Mini Profiler configuration object
8
+ #
9
+ # @!attribute [r] logger
10
+ # @return [Logger] the current logger
11
+ # @!attribute enabled
12
+ # @return [Boolean] if the profiler is enabled
13
+ # @!attribute flamegraph_enabled
14
+ # @return [Boolean] if Flamegraph recording is enabled
15
+ # @!attribute flamegraph_sample_rate
16
+ # @return [Float] the sample rate in samples per millisecond
17
+ # @!attribute skip_paths
18
+ # @return [Array<String>] a list of regex patterns for paths to skip
19
+ # @!attribute storage
20
+ # @return [Storage] the storage configuration
21
+ # @!attribute ui
22
+ # @return [UserInterface] the ui configuration
23
+ # @!attribute user_provider
24
+ # @return [Proc] a proc to identify a user based on a rack env
25
+ class Configuration
26
+ attr_reader :logger
27
+
28
+ attr_accessor :enabled,
29
+ :flamegraph_enabled,
30
+ :flamegraph_sample_rate,
31
+ :skip_paths,
32
+ :storage,
33
+ :ui,
34
+ :user_provider
35
+
36
+ def initialize(**kwargs)
37
+ reset
38
+ kwargs.each { |key, value| instance_variable_set("@#{key}", value) }
39
+ end
40
+
41
+ # Reset the configuration to default values
42
+ def reset
43
+ @enabled = proc { |_env| Rails.env.development? || Rails.env.test? }
44
+ @flamegraph_enabled = true
45
+ @flamegraph_sample_rate = 0.5
46
+ @logger = RailsMiniProfiler::Logger.new(Rails.logger)
47
+ @skip_paths = []
48
+ @storage = Storage.new
49
+ @ui = UserInterface.new
50
+ @user_provider = proc { |env| Rack::Request.new(env).ip }
51
+ end
52
+
53
+ # Set the logger
54
+ #
55
+ # @param logger [Logger]
56
+ # The logger to be used. If set to nil, the Rails default logger is used and the log level set to fatal
57
+ def logger=(logger)
58
+ if logger.nil?
59
+ @logger.level = Logger::FATAL
60
+ else
61
+ @logger = logger
62
+ end
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,34 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ # The Rails Mini Profiler engine
5
+ #
6
+ # Injects a a custom [Middleware] into an existing Rails app to record request profiling information.
7
+ class Engine < ::Rails::Engine
8
+ isolate_namespace RailsMiniProfiler
9
+
10
+ initializer 'rails_mini_profiler.add_middleware' do |app|
11
+ app.middleware.use(RailsMiniProfiler::Middleware)
12
+ end
13
+
14
+ config.generators do |g|
15
+ g.test_framework :rspec
16
+ end
17
+
18
+ initializer 'rails_mini_profiler_add_static assets' do |app|
19
+ app.middleware.insert_before(ActionDispatch::Static, ActionDispatch::Static, "#{root}/public")
20
+ end
21
+
22
+ # If sprockets is not being used then there is no need to hook into asset compilation. Calling config.assets
23
+ # without Sprockets installed breaks compilation.
24
+ if defined?(Sprockets::Rails)
25
+ initializer 'rails_mini_profiler.assets.precompile', group: :all do |app|
26
+ app.config.assets.precompile += %w[
27
+ rails_mini_profiler.js
28
+ rails_mini_profiler/application.css
29
+ vendor/assets/images
30
+ ]
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ class FlamegraphGuard
5
+ def initialize(request_context, configuration: RailsMiniProfiler.configuration)
6
+ @request_context = request_context
7
+ @request = request_context.request
8
+ @configuration = configuration
9
+ end
10
+
11
+ def record(&block)
12
+ return block.call unless enabled?
13
+
14
+ sample_rate = @configuration.flamegraph_sample_rate
15
+ if StackProf.running?
16
+ RailsMiniProfiler.logger.error('Stackprof is already running, cannot record Flamegraph')
17
+ return block.call
18
+ end
19
+
20
+ result = nil
21
+ flamegraph = StackProf.run(mode: :wall, raw: true, aggregate: false, interval: (sample_rate * 1000).to_i) do
22
+ result = block.call
23
+ end
24
+
25
+ unless flamegraph
26
+ RailsMiniProfiler.logger.error('Failed to record Flamegraph, possibly due to concurrent requests')
27
+ return result
28
+ end
29
+
30
+ @request_context.flamegraph = flamegraph.to_json
31
+ result
32
+ end
33
+
34
+ private
35
+
36
+ def enabled?
37
+ defined?(StackProf) && StackProf.respond_to?(:run) && config_enabled?
38
+ end
39
+
40
+ def config_enabled?
41
+ params = CGI.parse(@request.query_string).transform_values(&:first).with_indifferent_access
42
+ return params[:rmp_flamegraph] if params[:rmp_flamegraph]
43
+
44
+ RailsMiniProfiler.configuration.flamegraph_enabled
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,57 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ # Encapsulates guard conditions on whether or not to run certain parts of the profiler.
5
+ class Guard
6
+ # @param request_context [RequestContext] the current request context
7
+ # @param configuration [Configuration] the current configuration
8
+ def initialize(request_context, configuration: RailsMiniProfiler.configuration)
9
+ @request_context = request_context
10
+ @request = request_context.request
11
+ @configuration = configuration
12
+ end
13
+
14
+ # Whether or not to profile
15
+ #
16
+ # Profiling is disabled the profiler has been flat out disabled in the configuration or if the current request path
17
+ # matches on of the ignored paths.
18
+ #
19
+ # @return [Boolean] false if no profiling should be done
20
+ def profile?
21
+ return false unless enabled?
22
+
23
+ return false if ignored_path?
24
+
25
+ true
26
+ end
27
+
28
+ private
29
+
30
+ # Is the path of the current request an ignored one?
31
+ #
32
+ # @return [Boolean] true if the path is ignored. Per default, paths going to the engine itself are ignored, as are
33
+ # asset requests, and the paths the user has configured.
34
+ def ignored_path?
35
+ return true if /#{Engine.routes.find_script_name({})}/.match?(@request.path)
36
+
37
+ return true if /assets/.match?(@request.path)
38
+
39
+ ignored_paths = @configuration.skip_paths
40
+ return true if Regexp.union(ignored_paths).match?(@request.path)
41
+
42
+ false
43
+ end
44
+
45
+ # Is the profiler enabled?
46
+ #
47
+ # Takes into account the current request env to decide if the profiler is enabled.
48
+ #
49
+ # @return [Boolean] false if the profiler is disabled
50
+ def enabled?
51
+ enabled = @configuration.enabled
52
+ return enabled unless enabled.respond_to?(:call)
53
+
54
+ enabled.call(@request.env)
55
+ end
56
+ end
57
+ end
@@ -0,0 +1,25 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RailsMiniProfiler
4
+ # Construct a new custom logger to log from within the engine
5
+ module Logger
6
+ # Extends a logger with additional formatting
7
+ #
8
+ # @return [Logger] a customized logger
9
+ def self.new(logger)
10
+ logger = logger.dup
11
+
12
+ logger.formatter = logger.formatter ? logger.formatter.dup : ActiveSupport::Logger::SimpleFormatter.new
13
+
14
+ logger.formatter.extend Formatter
15
+ logger.extend(self)
16
+ end
17
+
18
+ # Custom formatter to add a RailsMiniProfiler tag to log messages
19
+ module Formatter
20
+ def call(severity, timestamp, progname, msg)
21
+ super(severity, timestamp, progname, "[RailsMiniProfiler] #{msg}")
22
+ end
23
+ end
24
+ end
25
+ end