Rails 3.0.9 usability problem: password/confirmation highlighting

If there is an error with the submitted password on a form, then both
the password and password confirmation text fields should be highlighted
in red. The default seems to be to highlight only the password field.

Any suggestions on how to correct that? Because rails magically handles
the highlighting, I’m not sure how to intercept that. It looks to me
like I would have to create a partial for the confirmation field. I
tried this:

views/users/new.html.erb:

Sign up

<%= form_for(@user) do |f| %>
<%= render ‘shared/error_messages’ %>

<%= f.label :name, "Name:"%>
<%= f.text_field :name %>
<%= f.label :email, "Email:" %>
<%= f.text_field :email %>
<%= f.label :password, "Password (at least 6 characters):" %>
<%= f.password_field :password %>

<%= render ‘users/password_confirmation’ %>

<%= f.submit "Sign up" %>
<% end %>

views/users/_password_confirmation.html.erb:

<%
css_class = ‘’

@user.errors.any? do |error|
if error.match /password/
css_class = ‘field_with_errors’
end
end
%>

<%= f.label :password_confirmation, "Password confirmation:" %>
<%= f.password_field :password_confirmation %>

but I got the error:

undefined local variable or method `f’ for
#<#Class:0x00000105023270:0x000001050211c8>
Extracted source (around line #14):

11:
12:


13:

14: <%= f.label :password_confirmation, “Password confirmation:” %>
15:

16:

17: <%= f.password_field :password_confirmation %>

So it looks like a partial creates a new scope, and therefore ‘f’ from
the view page isn’t visible in the partial.

I can get some code to work in the view, but it makes the view pretty
messy:

views/users/new.htmt.erb:

Sign up

<%= form_for(@user) do |f| %>
<%= render ‘shared/error_messages’ %>

<%= f.label :name, "Name:"%>
<%= f.text_field :name %>
<%= f.label :email, "Email:" %>
<%= f.text_field :email %>
<%= f.label :password, "Password (at least 6 characters):" %>
<%= f.password_field :password %>

<%
password_error = false

@user.errors.full_messages.any? do |error|
if error.match /password/i
password_error = true
end
end
%>

<% if password_error %>

<% end %>
<%= f.label :password_confirmation, "Password confirmation:" %>
<%= f.password_field :password_confirmation %>
<% if password_error %>
<% end %>
<%= f.submit "Sign up" %>
<% end %>

To move that code to a partial, is the solution to use @f in form_for()?

This is what I did:

views/users/new.html.erb:

Sign up

<%= form_for(@user) do |f| %>
<% @f_for_partial = f %>

<%= render ‘shared/error_messages’ %>

<%= f.label :name, "Name:"%>
<%= f.text_field :name %>
<%= f.label :email, "Email:" %>
<%= f.text_field :email %>
<%= f.label :password, "Password (at least 6 characters):" %>
<%= f.password_field :password %>

<%= render ‘users/password_confirmation_fix’ %>

<%= f.submit "Sign up" %>
<% end %>

views/users/_password_confirmation_fix.html.erb:

<%
password_error = @user.errors.full_messages.any? do |error|
error.match /password/i
end
%>

<% if password_error %>

<% end %>
<div class="field ">
  <%= @f_for_partial.label :password_confirmation, "Password 

confirmation:" %>



<%= @f_for_partial.password_field :password_confirmation %>

<% if password_error %>

<% end %>

And in the action I did this:

def create # POST requests to ‘/users’ routes here
@user = User.new(params[:user])

if @user.save
  flash[:success] = "Welcome to the website."
  redirect_to @user #goes to user 'show' page
else
  @title = 'Sign up'

  #If password errors, then erase passwords.
  #If no password errors, redisplay passwords.
  if @user.errors.full_messages.any? {|error| error.match 

/password/i}
@user.password = ‘’
@user.password_confirmation = ‘’
end
render ‘new’
end
end