class ERBLint::Utils::BlockMap
Attributes
connections[R]
Public Class Methods
new(processed_source)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 13 def initialize(processed_source) @processed_source = processed_source @entries = [] @connections = [] @ruby_code = "" build_map end
Public Instance Methods
find_connected_nodes(other)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 21 def find_connected_nodes(other) connection = @connections.find { |conn| conn.include?(other) } connection&.nodes end
Private Instance Methods
append(code)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 187 def append(code) @ruby_code += code end
block?(source)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 130 def block?(source) # taken from: action_view/template/handlers/erb/erubi.rb /\s*((\s+|\))do|\{)(\s*\|[^|]*\|)?\s*\Z/.match?(source) end
build_map()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 79 def build_map erb_nodes.each do |erb_node| indicator_node, _, code_node, _ = *erb_node length = code_node.loc.size start = current_pos if indicator_node.nil? append("#{code_node.loc.source}\n") elsif block?(code_node.loc.source) append("src= #{code_node.loc.source}\n") start += 5 else append("src=(#{code_node.loc.source});\n") start += 5 end ruby_range = Range.new(start, start + length) @entries << Entry.new(erb_node, ruby_range) end ruby_node = BetterHtml::TestHelper::RubyNode.parse(@ruby_code) raise ParseError unless ruby_node ruby_node.descendants(:block, :if, :for).each do |node| @connections << ConnectedErbNodes.new( node.type, extract_map_locations(node) .map { |loc| find_entry(loc) } .compact.map(&:node) ) end ruby_node.descendants(:kwbegin).each do |node| @connections << ConnectedErbNodes.new( :begin, (extract_map_locations(node) + rescue_locations(node)) .map { |loc| find_entry(loc) } .compact.map(&:node) ) end ruby_node.descendants(:case).each do |node| @connections << ConnectedErbNodes.new( node.type, (extract_map_locations(node) + when_locations(node)) .map { |loc| find_entry(loc) } .compact.map(&:node) ) end group_overlapping_connections end
current_pos()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 183 def current_pos @ruby_code.size end
erb_ast()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 222 def erb_ast parser.ast end
erb_nodes()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 28 def erb_nodes erb_ast.descendants(:erb).sort { |a, b| a.loc.begin_pos <=> b.loc.begin_pos } end
extract_map_locations(node)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 152 def extract_map_locations(node) ( case node.loc when Parser::Source::Map::Collection [node.loc.begin, node.loc.end] when Parser::Source::Map::Condition [node.loc.keyword, node.loc.begin, node.loc.else, node.loc.end] when Parser::Source::Map::Constant [node.loc.double_colon, node.loc.name, node.loc.operator] when Parser::Source::Map::Definition [node.loc.keyword, node.loc.operator, node.loc.name, node.loc.end] when Parser::Source::Map::For [node.loc.keyword, node.loc.in, node.loc.begin, node.loc.end] when Parser::Source::Map::Heredoc [node.loc.heredoc_body, node.loc.heredoc_end] when Parser::Source::Map::Keyword [node.loc.keyword, node.loc.begin, node.loc.end] when Parser::Source::Map::ObjcKwarg [node.loc.keyword, node.loc.operator, node.loc.argument] when Parser::Source::Map::RescueBody [node.loc.keyword, node.loc.assoc, node.loc.begin] when Parser::Source::Map::Send [node.loc.dot, node.loc.selector, node.loc.operator, node.loc.begin, node.loc.end] when Parser::Source::Map::Ternary [node.loc.question, node.loc.colon] when Parser::Source::Map::Variable [node.loc.name, node.loc.operator] end + [node.loc.expression] ).compact end
find_entry(range)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 195 def find_entry(range) return unless range @entries.find do |entry| entry.contains_ruby_range?(Range.new(range.begin_pos, range.end_pos)) end end
find_overlapping_pair()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 212 def find_overlapping_pair @connections.each do |first| @connections.each do |second| next if first == second return [first, second] if (first & second).any? end end nil end
group_overlapping_connections()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 202 def group_overlapping_connections loop do first, second = find_overlapping_pair break unless first && second @connections.delete(second) first.concat(second) end end
parser()
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 191 def parser @processed_source.parser end
rescue_locations(node)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 142 def rescue_locations(node) node.child_nodes .select { |child| child.type?(:rescue) } .map(&:child_nodes) .flatten .select { |child| child.type?(:resbody) } .map { |child| extract_map_locations(child) } .flatten end
when_locations(node)
click to toggle source
# File lib/erb_lint/utils/block_map.rb, line 135 def when_locations(node) node.child_nodes .select { |child| child.type?(:when) } .map { |child| extract_map_locations(child) } .flatten end