Class: Autotuner::Heuristic::HeapSizeWarmup
- Defined in:
- lib/autotuner/heuristic/heap_size_warmup.rb
Constant Summary collapse
- SUPPORT_MULTI_HEAP_P =
Ruby 3.3.0 and later have support for RUBY_GC_HEAP_%d_INIT_SLOTS
RUBY_VERSION >= "3.3.0"
- HEAP_NAMES =
if SUPPORT_MULTI_HEAP_P GC.stat_heap.keys.map(&:to_s).freeze else [nil] end
- HEAP_SIZE_CONFIGURATION_DELTA_RATIO =
0.01
- HEAP_SIZE_CONFIGURATION_DELTA =
1_000
- REPORT_ASSIST_MESSAGE =
<<~MSG The following suggestions adjust the size of the heap at boot time, which can improve bootup speed and reduce the time taken for the app to reach peak performance. MSG
Class Method Summary collapse
Instance Method Summary collapse
- #call(request_context) ⇒ Object
- #debug_state ⇒ Object
- #env_name_for_heap(heap_name) ⇒ Object
-
#initialize(_system_context) ⇒ HeapSizeWarmup
constructor
A new instance of HeapSizeWarmup.
- #name ⇒ Object
- #tuning_report ⇒ Object
Methods inherited from Base
Constructor Details
#initialize(_system_context) ⇒ HeapSizeWarmup
Returns a new instance of HeapSizeWarmup.
32 33 34 35 36 37 38 39 40 41 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 32 def initialize(_system_context) super @heaps_data = Array.new(HEAP_NAMES.length) HEAP_NAMES.length.times do |i| @heaps_data[i] = DataStructure::DataPoints.new(Configuration::DATA_POINTS_COUNT) end @given_suggestion = false end |
Class Method Details
.supported? ⇒ Boolean
7 8 9 10 11 12 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 7 def supported? # Ruby 3.2 uses multiple heaps but does not support the # RUBY_GC_HEAP_%d_INIT_SLOTS environment variables, so we cannot # accurately tune the heap size. !RUBY_VERSION.start_with?("3.2.") end |
Instance Method Details
#call(request_context) ⇒ Object
47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 47 def call(request_context) # We only want to collect data at boot until plateau return if @given_suggestion @heaps_data.each_with_index do |data, i| value = if SUPPORT_MULTI_HEAP_P request_context.after_gc_context.stat_heap[i][:heap_eden_slots] else request_context.after_gc_context.stat[:heap_available_slots] end data.insert(value) end end |
#debug_state ⇒ Object
103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 103 def debug_state state = { given_suggestion: @given_suggestion, } # Don't output @heaps_data because there is too much data. HEAP_NAMES.each do |heap_name| env_var = env_name_for_heap(heap_name) env_val = ENV[env_var] state[:"ENV[#{env_var}]"] = env_val if env_val end state end |
#env_name_for_heap(heap_name) ⇒ Object
119 120 121 122 123 124 125 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 119 def env_name_for_heap(heap_name) if SUPPORT_MULTI_HEAP_P "RUBY_GC_HEAP_#{heap_name}_INIT_SLOTS" else "RUBY_GC_HEAP_INIT_SLOTS" end end |
#name ⇒ Object
43 44 45 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 43 def name "HeapSizeWarmup" end |
#tuning_report ⇒ Object
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 89 90 91 92 93 94 95 96 97 98 99 100 101 |
# File 'lib/autotuner/heuristic/heap_size_warmup.rb', line 63 def tuning_report # Don't give suggestions twice return if @given_suggestion # The request time should plateau return unless @system_context.request_time_data.plateaued? @given_suggestion = true env_names = [] suggested_values = [] configured_values = [] HEAP_NAMES.each_with_index do |heap_name, i| env_name = env_name_for_heap(heap_name) data = @heaps_data[i] suggested_value = data.samples[data.length - 1].to_i env_val = ENV[env_name] configured_value = env_val&.to_i if configured_value diff = (suggested_value - configured_value).abs # Don't report this if it's within the ratio next if diff <= configured_value * HEAP_SIZE_CONFIGURATION_DELTA_RATIO # Don't report this if it's within the delta next if diff <= HEAP_SIZE_CONFIGURATION_DELTA end env_names << env_name suggested_values << suggested_value configured_values << configured_value end # Don't generate report if there is nothing to report return if suggested_values.empty? Report::MultipleEnvironmentVariables.new(REPORT_ASSIST_MESSAGE, env_names, suggested_values, configured_values) end |