From: Wes Gamble Date: 2006-08-12T08:49:07+09:00 Subject: Re: Crazy gsub/regex scheme - can this be done better? [ INSANE COMMENT: I just want to say that the black magic that is regexes is so powerful and alluring that I can't resist it and at the same time so repulsive that I never want to do it again. :) :) :) ] Update - my original scheme would fail when there was an attribute like content="text/html; charset=UTF-8" because the latter half would be seen as needing to be charset="UTF-8". Thus, I became intimate with negative zero-width lookahead. Here's what I believe to be a more correct solution (I apologize for the formatting but I wanted to leave the comments in here). Wes #Make sure that every tag attribute is contained within either single or double quotes. #The initial regex is to find at least one "bad" attribute value pair #The "inner" regex is to actually fix ALL of the "bad" attribute value pairs private def ensure_quoted_attributes @html.gsub!(/<(?!!)[a-zA-Z0-9]+\s+ #Non-comment tag name, followed by whitespace (?:[a-zA-Z-]+?=(['"]).*?\1\s*)*? #Any number of valid attribute-value pairs (attribute="value"), not-greedy [a-zA-Z-]+?=[^"'\s>]+\s*? #An unquoted attribute-value pair (attribute=value) .*?> #Rest of tag /mix) { |s| #For each tag gotten from the first regex, globally substitute into it based on... s.gsub(/(\s+[a-zA-Z-]+=) #Attribute name (?!(['"])[^'"]*?\2[\s>]) #If the value looks like "stuff", then don't match, it's fine (?![^'"]*?['"][\s>]) #If the value looks like stuff", then don't match, it must be the tail end of another attribute-value pair ([^'"\s>]+) #Get the no-whitespace, no-'>', no quote text /mix) { |sub_s| "#{$1}\"#{$3}\"" } #Substitute attribute name="attribute value" } end -- Posted via http://www.ruby-forum.com/.