Rails custom validation based on a regex? - ruby-on-rails

I have the following regex that I use in my routes.rb for /type-in-something-here
# A-Z, a-z, 0-9, _ in the middle but never starting or ending in a _
# At least 5, no more than 500 characters
In the routes this works well as:
match ':uuid' => 'room#show', :constraints => { :uuid => /[A-Za-z\d]([-\w]{,498}[A-Za-z\d])?/ }
I want to have this also as a validation so invalid records aren't created. So I added the following to room.rb:
validates_format_of :uuid, :with => /[A-Za-z\d]([-\w]{,498}[A-Za-z\d])?/i, :message => "Invalid! Alphanumerics only."
But this validates_format_of isn't working, and instead of adding an error it's allow the record to save.
Any ideas what's wrong?
Thanks

For validation purposes, remember to add the beginning and end of string markers \A and \Z:
validates_format_of :uuid, :with => /\A[A-Za-z\d]([-\w]{,498}[A-Za-z\d])?\Z/i
Otherwise your regex will happily match any string that contains at least a letter or a digit. For some reason Rails implicitly adds the boundaries in the routes. (Probably because it embeds the regex inside a larger one to match the entire URL, with explicit checks for / and the end of the URL.)

using something like this
validates :uuid, :format => {:with => /[A-Za-z\d]([-\w]{,498}[A-Za-z\d])?/i},
:message => "your message"
For more check this

validates :name, format: { with: /\A[a-zA-Z]+\z/,
message: "Only letters are allowed" }

Related

The provided regular expression is using multiline anchors (^ or $)

I trying to write a Image validation format that makes sure url ends with either .png, .jpg or .gif .
class Product < ActiveRecord::Base
mount_uploader :image_url
validates :title, :presence => true,
:uniqueness => true
validates :image_url, :presence => true,
:format => {
:with => %r{\.(gif|jpg|png)$}i,
:message => 'must be a URL for GIF, JPG or PNG image.'
}
end
But when i start my server. seeing this:
The provided regular expression is using multiline anchors (^ or $), which may present a security risk. Did you mean to use \A and \z, or forgot to add the :multiline => true option?
^ and $ are both line anchors. If a user were to pass in a string with http://www.foo.com/bar.png\nfoo_bar_baz!, then your regex is going say that the input is valid because it will match .png to the newline, which is not what you want.
Change your regex above to be %r{\.(gif|jpg|png)\z}i instead. The \z is an end of string anchor, which is what you want instead of the end of line anchor.
There are some great answers on another, very similar question: Difference between \A \z and ^ $ in Ruby regular expressions.

Model validation, validate a string is an integer

Hi I have a model called users, and they have a cell phone attribute that must be entered as a 12 digit string leading with "+". I want to validate that the attribute they entered from a form is in fact in the correct format. Example "+11234567890" should save to the model, but "1232h" will not.
This is what I have in my model, but it does not work:
validates :cell, :format => { :with => /^[-+]?[0-9]+$/,
:message => "Only numbers allowed" }, :length => { :is => 10 }
Try this:
validates :cell, :format => { :with => /\A(\+1)?[0-9]{10}\z/, :message => "Not a valid 10-digit telephone number" }
I think the problem is that you're trying to do two different kinds of validations on a single validates line. The above combines the length constraint with the number constraint, and allows the variable +/- without messing up the length constraint.

Simple rails format validation not firing

I'm building an app where users can create url slugs for their profile. To make sure the slugs are valid I've added a validation in the User model for slugs:
validates :slug, :uniqueness => true, :format => { :with => /[a-z]+/ }, :allow_nil => true, :allow_blank => true
However, validation seems to pass, regardless of what format the slug string is, for example:
u.slug = 'jlskdf .jc oi/slkdjfie\*asdf&(*&*ss%&'
=> "jlskdf .jc oi/slkdjfie\\*asdf&(*&*ss%&"
u.save
=> true
Apparently it doesn't matter what I change the regex to either, everything passes. I've tried this format as well:
validates_format_of :slug, :with => /[a-z]+/
which gives the same results. Anyone have any ideas of what could be happening?
Your regular expression isn't anchored, so the pattern matches as long as it contains at least one letter a-z. Anything else is valid. Add \A and \z to the beginning and end to prevent matching any substring within the larger input.
:with => /\A[a-z]+\z/

Why is this Rails regex matching this string?

I'm using the following regex to validate one of my models
validates :login,
:format => {:with => /[A-Za-z][A-Za-z0-9_]+/}
And one of my tests is failing because this regex is matching this string, passing it as valid
a+df
What am I missing here?
It matches the df substring. Use anchors to force the regex to match the string in its entirety:
validates :login,
:format => {:with => /\A[A-Za-z][A-Za-z0-9_]+\Z/}
Try this regex
^[A-Za-z][A-Za-z0-9_]+$

How do you validate against more than one regex?

I have this validation:
validates :url, :uniqueness => true,
:format => { :with => /^(http:\/\/)?(www\.)?youtube\.com\/watch\?v=([a-zA-Z0-9_-]*)/}
I want to let url match either the regex above or another regex. How do I add this second regex?
You put both regexes into one regex using the 'bar' operator which does an 'or' for you:
/(^(http:\/\/)?(www\.)?youtube\.com\/watch\?v=([a-zA-Z0-9_-]*)|helloworld)/
Matches a URL or a string containing "helloworld"

Resources