java-topology/defects/rails/patch/rails-0012-options-for-select-selected-set.patch

40 lines
2 KiB
Diff
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# UNDF: UNDF-2026-000000251
Fixes rails-0012: options_for_select — Array(selected).include? and Array(disabled).include? inside container.map loop O(N×S) per select render.
--- a/actionview/lib/action_view/helpers/form_options_helper.rb
+++ b/actionview/lib/action_view/helpers/form_options_helper.rb
@@ DEFECT rails-0012: lines 357-374
def options_for_select(container, selected = nil)
return container if String === container
selected, disabled = extract_selected_and_disabled(selected).map do |r|
- Array(r).map(&:to_s) # O(S), O(D) — still Arrays
+ Array(r).map(&:to_s).to_set # FIX: O(1) include? below
end
container.map do |element|
html_attributes = option_html_attributes(element)
text, value = option_text_and_value(element).map(&:to_s)
- html_attributes[:selected] ||= option_value_selected?(value, selected) # O(S) per option
- html_attributes[:disabled] ||= disabled && option_value_selected?(value, disabled) # O(D) per option
+ html_attributes[:selected] ||= option_value_selected?(value, selected)
+ html_attributes[:disabled] ||= disabled && option_value_selected?(value, disabled)
html_attributes[:value] = value
tag_builder.option(text, **html_attributes)
end.join("\n").html_safe
end
# NOTE: option_value_selected? already calls Array(selected).include? — the fix is
# to ensure selected/disabled are Sets before the loop so include? is O(1).
# BEFORE: selected/disabled are Arrays; include? is O(S) or O(D) per option element
# container has N options: total O(N×S + N×D) per render
# AFTER: selected/disabled converted to Set before loop: O(1) include? per option
# total O(N) per render
# Severity: HIGH — every select tag with a pre-selected value hits this path
# Speedup: ~S× where S = number of selected values (multi-select: up to 100+)
# At N=500 options, S=50 selected: 25,000 comparisons → 500