Lickety-split custom validations in Rails

how-to
Jun 12, 20133 mins

Have a highly specific, yet custom validation for a particular field on one of your Rails model objects? Don’t want to create a ActiveModel::Validator type? Not a problem!

You can just as easily create a method that can be invoked as part of the validation process. For example, imagine a field dubbed uri in some model object; this field must begin with a protocol (i.e. http or https). You can create a validation method like so:

Custom validator
<span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
<code class='ruby'><span class='line'><span class="k">def</span> <span class="nf">uri_should_start_with_protocol</span>
</span><span class='line'>  <span class="k">if</span> <span class="o">!</span><span class="n">uri</span><span class="o">.</span><span class="n">start_with?</span><span class="p">(</span><span class="s1">'http://'</span><span class="p">)</span> <span class="o">&&</span> <span class="o">!</span><span class="n">uri</span><span class="o">.</span><span class="n">start_with?</span><span class="p">(</span><span class="s1">'https://'</span><span class="p">)</span>
</span><span class='line'>    <span class="n">errors</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="ss">:uri</span><span class="p">,</span> <span class="s1">'Web Address should start with http:// or https://'</span><span class="p">)</span>
</span><span class='line'>  <span class="k">end</span>
</span><span class='line'><span class="k">end</span>
</span>

This method resides in your model. You can then register this method as a validation for your model like so:

Wiring the validation
<span class='line-number'>1</span>
<code class='ruby'><span class='line'><span class="n">validate</span> <span class="ss">:uri_should_start_with_protocol</span>
</span>

Now if the uri field doesn’t contain http or https, model.save will return false. Done!

andrew_glover

When Andrew Glover isn't listening to “Funkytown” or “Le Freak” he enjoys speaking on the No Fluff Just Stuff Tour. He also writes articles for multiple online publications including IBM's developerWorks and O'Reilly’s ONJava and ONLamp portals. Andrew is also the co-author of Java Testing Patterns, which was published by Wiley in September 2004; Addison-Wesley’s Continuous Integration; and Manning’s Groovy in Action.

More from this author