Why validation occurs on attribute read instead of write?

I have what I think is a simple question.

Validation appears to occur upon the read of an ActiveRecord attribute,
not on the write of that attribute.

Assuming a case where you may have some transformation that needs to
happen to the data on the way in, this can create situations where if
your inbound transformation inadventertently changes your data such that
it “becomes” valid, then unless you are careful to validate that data on
the write, a form could appear to allow invalid data.

Granted, I do believe this can only occur if the inbound transformation
itself allows successful data tranformation in cases that should have
been rejected by the validation. Basically, the setters need to be
aware of the validations as well.

A concrete example is for fax numbers that are stored internally as only
digits. The form may accept a few formatting characters however. The
validation should reject any invalid characters. If the setter for the
fax number strips out all of the character data before the call to
write_attribute(), then the validation, which is looking for invalid
characters doesn’t get tripped on the read back out and the object
updates. It then appears that the user can successfully input fax
numbers with invalid data.

So my question is, why aren’t the validation rules applied whenever an
AR setter is invoked instead of when the getter is invoked? It seems
that you would have to assume that all of the setters were of the form:

def set_method=(new_set_value)

end

meaning only one input parameter, and then this input parameter would be
what is validated.

What am I missing here?

Thanks,
Wes

So my question is, why aren’t the validation rules applied whenever an
AR setter is invoked instead of when the getter is invoked? It seems
that you would have to assume that all of the setters were of the form:

def set_method=(new_set_value)

end

meaning only one input parameter, and then this input parameter would be
what is validated.

Just to clarify:

def attr_name=(new_attr_value)

end

is the default attribute setter for a given AR attribute.

It seems like you could apply the validation to the input to this method
instead of to the output of the related getter method.

Thoughts?
Wes

Oh, and of course if you need to check whether an object is valid, you
can call the valid? method.

Fred

Validation occurs when the record is saved. Validating as each attribute
is updated could be quite limiting.

Sure you could still express things like email_address needs to match a
certain format and blah needs to be a number but you couldn’t have more
complex rules where various attributes interact, for example a business
rule that states that if attribute x is set then y must be a positive
integer, and if x is not set then y should be nil.

I guess what I’m trying to say is that being valid or not is a property
of the object as a whole, not of any individual attribute and so it will
not always be the case that changing a series of attributes produces an
object which is valid at each intermediate stage

Fred