$tab_size = 2 $tab_string = " " # indent regexp tests $indent_expression = [ /^module\b/, /(=\s*|^)if\b/, /(=\s*|^)until\b/, /(=\s*|^)for\b/, /(=\s*|^)unless\b/, /(=\s*|^)while\b/, /(=\s*|^)begin\b/, /(=\s*|^)case\b/, /\bthen\b/, /^class\b/, /^rescue\b/, /^def\b/, /\bdo\b/, /^else\b/, /^elsif\b/, /^ensure\b/, /\bwhen\b/, /\{[^\}]*$/, /\[[^\]]*$/ ] # outdent regexp tests $outdent_expression = [ /^rescue\b/, /^ensure\b/, /^elsif\b/, /^end\b/, /^else\b/, /\bwhen\b/, /^[^\{]*\}/, /^[^\[]*\]/ ] def make_tab(tab) # If the tab is negative, don't do anything return (tab < 0) ? "" : $tab_string * $tab_size * tab end def add_line line, tab line.strip! line = make_tab(tab) + line if line.length > 0 return line + "\n" end def format_ruby comment_block = false multi_line_array = Array.new multi_line_string = "" tab = 0 ############ #filename entered on command line as argument gets passed in Ruby's #special argument array ARGV. The ARGV[0] zeroth element has the filename ############ filename = ARGV[0] # Open the file for reading source = File.new(filename,'r').read new_file = "" # Read each line source.split("\n").each do |line| # SKIPPING THIS FOR NOW. NOT SURE WHY I'D NEED TO DO THIS YET. # Says: if it's not a comment line and has a \ (plus spaces) # combine continuing lines if(!(line =~ /^\s*#/) && line =~ /[^\\]\\\s*$/) multi_line_array.push line multi_line_string += line.sub(/^(.*)\\\s*$/,"\\1") next end # THIS GOES WITH THE PREVIOUS IF STATEMENT; SKIP FOR NOW. # add final line if(multi_line_string.length > 0) multi_line_array.push line multi_line_string += line.sub(/^(.*)\\\s*$/,"\\1") end # tab_line is really just the line to check tab_line = ((multi_line_string.length > 0) ? multi_line_string : line).strip # HE SKIPS CHECKING OF COMMENT BLOCKS; LET'S GO AHEAD AND CHECK THEM if(tab_line =~ /^=begin/) comment_block = true end if(comment_block) # add the line unchanged new_file += line + "\n" # THIS IS WHERE THE MAGIC STARTS else commentab_line = (tab_line =~ /^#/) # if(!commentab_line) # throw out sequences that will # only sow confusion tab_line.gsub!(/\/.*?\//,"") # Subs anything / stuff / with "" tab_line.gsub!(/%r\{.*?\}/,"") tab_line.gsub!(/%r(.).*?\1/,"") tab_line.gsub!(/\\\"/,"'") tab_line.gsub!(/".*?"/,"\"\"") tab_line.gsub!(/'.*?'/,"''") tab_line.gsub!(/#\{.*?\}/,"") $outdent_expression.each do |re| # Search each line for an outdent keyword # If the line contains one of the keywords, it's indented too far # so set it to be out 1 level if(tab_line =~ re) tab -= 1 break end end end if (multi_line_array.length > 0) # This will: # Set lines with indent keywords to not change their indenting. # Set lines without indent keywords to not change their indenting # since tab is still 0. multi_line_array.each do |ml| # He adds the line; I'd compare actual vs. proper. dest += add_line(ml,tab) end multi_line_array.clear multi_line_string = "" else dest += add_line(line,tab) end if(!commentab_line) # Check the line to see if it contains one of the indent keywords $indent_expression.each do |re| # If it does contain one of the keywords and doesn't contain the # 'end' keywords if(tab_line =~ re && !(tab_line =~ /\s+end\s*$/)) # Bump the level up 1 tab += 1 break end end end end if(tab_line =~ /^=end/) comment_block = false end end #STDOUT.write(dest) #File.open(filename, 'w') {|fw| fw.write(dest)} puts "File #{ARGV[0]} has been formatted." # uncomment this to complain about mismatched blocks if(tab != 0) STDERR.puts "Indentation error: #{tab}" end end format_ruby