Skip to content

Commit

Permalink
Break class attributes at line width instead of using one class per line
Browse files Browse the repository at this point in the history
Co-Authored-By: Azeem Ahmed <[email protected]>
  • Loading branch information
elia and Azeem838 committed Dec 1, 2023
1 parent abb40fc commit ca0c16e
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 12 deletions.
33 changes: 23 additions & 10 deletions lib/erb/formatter.rb
Original file line number Diff line number Diff line change
Expand Up @@ -56,13 +56,6 @@ class Error < StandardError; end

RUBOCOP_STDIN_MARKER = "===================="

# Override the max line length to account from already indented ERB
module RubocopForcedMaxLineLength
def max
Thread.current['RuboCop::Cop::Layout::LineLength#max'] || super
end
end

module DebugShovel
def <<(string)
puts "ADDING: #{string.inspect} FROM:\n #{caller(1, 5).join("\n ")}"
Expand All @@ -74,13 +67,14 @@ def self.format(source, filename: nil)
new(source, filename: filename).html
end

def initialize(source, line_width: 80, filename: nil, debug: $DEBUG)
def initialize(source, line_width: 80, single_class_per_line: false, filename: nil, debug: $DEBUG)
@original_source = source
@filename = filename || '(erb)'
@line_width = line_width
@source = remove_front_matter source.dup
@html = +""
@debug = debug
@single_class_per_line = single_class_per_line

html.extend DebugShovel if @debug

Expand Down Expand Up @@ -127,6 +121,7 @@ def format_attributes(tag_name, attrs, tag_closing)

attr_html = ""
tag_stack_push(['attr='], attrs)

attrs.scan(ATTR).flatten.each do |attr|
attr.strip!
full_attr = indented(attr)
Expand All @@ -135,15 +130,33 @@ def format_attributes(tag_name, attrs, tag_closing)
if full_attr.size > line_width && MULTILINE_ATTR_NAMES.include?(name) && attr.match?(QUOTED_ATTR)
attr_html << indented("#{name}=#{value[0]}")
tag_stack_push('attr"', value)
value[1...-1].strip.split(/\s+/).each do |value_part|
attr_html << indented(value_part)

value_parts = value[1...-1].strip.split(/\s+/)

if !@single_class_per_line && name == 'class'
line = value_parts.shift
value_parts.each do |value_part|
if (line.size + value_part.size + 1) <= line_width
line << " #{value_part}"
else
attr_html << indented(line)
line = value_part
end
end
attr_html << indented(line) if line
else
value_parts.each do |value_part|
attr_html << indented(value_part)
end
end

tag_stack_pop('attr"', value)
attr_html << indented(value[-1])
else
attr_html << full_attr
end
end

tag_stack_pop(['attr='], attrs)
attr_html << indented("")
attr_html
Expand Down
8 changes: 6 additions & 2 deletions lib/erb/formatter/command_line.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ def initialize(argv, stdin: $stdin)
@argv = argv.dup
@stdin = stdin

@write, @filename, @read_stdin, @code = nil
@write, @filename, @read_stdin, @code, @single_class_per_line = nil

OptionParser.new do |parser|
parser.banner = "Usage: #{$0} FILENAME... --write"
Expand All @@ -37,6 +37,10 @@ def initialize(argv, stdin: $stdin)
@width = value
end

parser.on("--single-class-per-line", "Print each class on a separate line") do |value|
@single_class_per_line = value
end

parser.on("--[no-]debug", "Enable debug mode") do |value|
$DEBUG = value
end
Expand Down Expand Up @@ -77,7 +81,7 @@ def run
if ignore_list.should_ignore_file? filename
print code unless write
else
html = ERB::Formatter.new(code, filename: filename, line_width: @width || 80)
html = ERB::Formatter.new(code, filename: filename, line_width: @width || 80, single_class_per_line: @single_class_per_line)

if write
File.write(filename, html)
Expand Down
3 changes: 3 additions & 0 deletions test/fixtures/multiline_attributes.html.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<button class="text-gray-700 bg-transparent hover:bg-gray-50 active:bg-gray-100 focus:bg-gray-50 focus:ring-gray-300 focus:ring-2
disabled:text-gray-300 disabled:bg-transparent disabled:border-gray-300 disabled:cursor-not-allowed
aria-disabled:text-gray-300 aria-disabled:bg-transparent aria-disabled:border-gray-300 aria-disabled:cursor-not-allowed">Button</button>
9 changes: 9 additions & 0 deletions test/fixtures/multiline_attributes.html.expected.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<button
class="
text-gray-700 bg-transparent hover:bg-gray-50 active:bg-gray-100
focus:bg-gray-50 focus:ring-gray-300 focus:ring-2 disabled:text-gray-300
disabled:bg-transparent disabled:border-gray-300 disabled:cursor-not-allowed
aria-disabled:text-gray-300 aria-disabled:bg-transparent
aria-disabled:border-gray-300 aria-disabled:cursor-not-allowed
"
>Button</button>

0 comments on commit ca0c16e

Please sign in to comment.