class ERBLint::Linters::TwoColumnLayoutMigrationCounter
Counts the number of times a two column layout using col-* CSS classes is used instead of the layout component.
def classes_from(tag)
def classes_from(tag) tag.attributes["class"]&.value&.split(" ") || [] end
def columns_from(tag_tree)
def columns_from(tag_tree) tag_tree[:children].each_with_object([]) do |tag_data, tags_memo| next unless tag_data.is_a?(Hash) next unless tag_data[:tag].name == "div" classes = classes_from(tag_data[:tag]) widths = Breakpoints.new classes.each do |cls| match = cls.match(/\Acol(?:-(xl|lg|md|sm))?-(\d{1,2})(?:-max)?\z/) next unless match breakpoint, width = match.captures breakpoint ||= :all widths.set(breakpoint.to_sym, width.to_i) end tags_memo << Column.new(widths, tag_data) end end
def container_from(columns_tag_tree)
def container_from(columns_tag_tree) columns = columns_from(columns_tag_tree) return unless columns.size == 2 container = Container.new(columns) main_min = container.main.widths.min_value sidebar_min = container.sidebar.widths.min_value return unless sidebar_min && main_min return unless WIDTH_RANGE.include?(main_min) return unless SIDEBAR_WIDTH_RANGE.include?(sidebar_min) container end
def d_flex?(tags)
def d_flex?(tags) tags.size == 1 && classes_from(tags.first[:tag]).include?("d-flex") end
def metadata_from(tag_tree)
def metadata_from(tag_tree) tags = tag_tree[:children].select { |c| c.is_a?(Hash) } if d_flex?(tags) container_from(tags.first) else container_from(tag_tree) end end
def run(processed_source)
def run(processed_source) @total_offenses = 0 @offenses_not_corrected = 0 tags, tag_tree = build_tag_tree(processed_source) tags.each do |tag| next if tag.closing? next unless tag.name == "div" classes = classes_from(tag) next if (CONTAINER_CLASSES & classes).empty? next unless metadata_from(tag_tree[tag]) @total_offenses += 1 @offenses_not_corrected += 1 generate_offense(self.class, processed_source, tag, MESSAGE) end counter_correct?(processed_source) end