I'm using the given regex expression to validate the username:
validates_format_of :username, with: /^[a-zA-Z0-9_\.]*$/, :multiline => true
By running brakeman gem i'm having the following warning.
== Warnings ==
Confidence: High
Category: Format Validation
Check: ValidationRegex
Message: Insufficient validation for `username` using `/^[a-zA-Z0-9_\.]*$/`. Use `\A` and `\z` as anchors
File: app/models/user.rb
Line: 16
What would be the optimal regex expression to correctly assign those anchors and keeping the same character permissions?
Regex is yet a myth for me!
Best regards.
From ruby on rails guides regular expressions
To fix the regular expression, \A and \z should be used instead of ^ and $, like
/\A[a-zA-Z0-9_\.]*\z/
Related
I want to validate U.S. phone numbers. On Rubular, the regex:
/^\(?([2-9][0-8][0-9])\)?[-.●]?([2-9][0-9]{2})[-.●]?([0-9]{4})$/
does not match the string:
'6463976583!'
as I expect. However, my Rails validator that uses the regex:
validates :phone, presence: true, format: {with: /^\(?([2-9][0-8][0-9])\)?[-.●]?([2-9][0-9]{2})[-.●]?([0-9]{4})$/}
seems to allow the same string.
Any thoughts as to where I'm going wrong?
pry(main)> '6463976583!'[/^\(?([2-9][0-8][0-9])\)?[-.]?([2-9][0-9]{2})[-.]?([0-9]{4})$/]?([0-9]{4})$/]
=> nil
pry(main)> '6463976583'[/^\(?([2-9][0-8][0-9])\)?[-.]?([2-9][0-9]{2})[-.]?([0-9]{4})$/]
=> "6463976583"
Perhaps try \A and \Z for your ActiveRecord validation: https://apidock.com/rails/ActiveModel/Validations/ClassMethods/validates_format_of
The documentation mentions it matches start and end of a string versus start and end of a line. I believe that Rails or Rubocop one, throws warnings if you don't use ^ and $ instead of \A or \Z
If you can't get the Rails validator to work, you can create a custom validator method and call your regex there
I've the following regex in my model
validates :profile_name, presence:true,
uniqueness:true,
format:
{
with: /^[a-zA-Z0-9_-]+$/,
message: "Must be formatted correctly"
}
My tests are not passing because of regex. I am validating the profile name.
Here is my error log:
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? (ArgumentError)
I think am doing right, still it is not passing. Please Help me to fix this.
Use, \A and \z instead of ^ and $ for regex:
validates :profile_name, presence:true,
uniqueness:true,
format:
{
with: /\A[a-zA-Z0-9_-]+\z/,
message: "Must be formatted correctly"
}
Read more on Regular Expressions as to why.
There is the following code:
class Product < ActiveRecord::Base
validates :title, :description, :image_url, presence: true
validates :price, numericality: {greater_than_or_equal_to: 0.01}
validates :title, uniqueness: true
validates :image_url, allow_blank: true, format: {
with: %r{\.(gif|jpg|png)$}i,
message: 'URL must point to GIT/JPG/PNG pictures'
}
end
It works, but when I try to test it using "rake test" I'll catch this message:
rake aborted!
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?
What does it mean? How can I fix it?
^ and $ are Start of Line and End of Line anchors. While \A and \z are Permanent Start of String and End of String anchors.
See the difference:
string = "abcde\nzzzz"
# => "abcde\nzzzz"
/^abcde$/ === string
# => true
/\Aabcde\z/ === string
# => false
So Rails is telling you, "Are you sure you want to use ^ and $? Don't you want to use \A and \z instead?"
There is more on the rails security concern that generates this warning here.
This warning raises because your validation rule is vulnerable for javascript injection.
In your case \.(gif|jpg|png)$ matches till the end of the line. So your rule will validate this value pic.png\nalert(1); as true:
"test.png\n<script>alert(1)</script>" === /\.(gif|jpg|png)$/i
# => true
"test.png\n<script>alert(1)</script>" === /\.(gif|jpg|png)\z/i
# => false
Read the acticles:
http://caiustheory.com/validating-data-with-regular-expressions-in-ruby
http://guides.rubyonrails.org/security.html#regular-expressions
The problem regexp is not in devise, but rather lives in config/initializers/devise.rb. Change:
# Regex to use to validate the email address
config.email_regexp = /^([\w\.%\+\-]+)#([\w\-]+\.)+([\w]{2,})$/i
to:
# Regex to use to validate the email address
config.email_regexp = /\A([\w\.%\+\-]+)#([\w\-]+\.)+([\w]{2,})\Z/i
The warning is telling you that strings like the following will pass validation, but it is probably not what you want:
test = "image.gif\nthis is not an image"
re = /\.(gif|jpg|png)$/i
re.match(test) #=> #<MatchData ".gif" 1:"gif">
Both ^ and $ matches the start/end of any line, not the start/end of the string. \A and \z matches the start and the end of the full string, respectively.
re = /\.(gif|jpg|png)\z/i
re.match(test) #=> nil
The second part of the warning (“or forgot to add the :multiline => true option”) is telling you that if you actually want the behaviour of ^ and $ you can simply silence the warning passing the :multiline option.
If Ruby wants to see \z instead of the $ symbol sign, for security, you need to give it to him, then the code would look like this :
validates :image_url, allow_blank: true, format: {with: %r{\.(gif|jpg|png)\z}i, message: 'URL must point to GIF, JPG, PNG.'}
In a Rails app, I have this current Regex validator below:
validates :characters, format: {with: /\A(([a-z0-9])+(-?[a-z0-9]+)*\s?)+\Z/, message: "can't be blank. Characters can only be [a-z 0-9 . # - +]" }
My validation for Characters initially only allowed lowercase letters and digits. Now I would like to allow for extra characters . # - + how do I structure my Regex now?
As per your question if you want to allow a-z , 0-9 and .#-+ only the regex for that would be:
/[a-z0-9.#+\-]/ and your validation will look something like this:
validates :characters, format: {with: /[a-z0-9.#+\-]/, message: "can't be blank. Characters can only be [a-z 0-9 . # - +]" }
you can even try that out at http://rubular.com/ . imho thats the best place to go for ruby regex.
I'm creating a model in Rails 3 as follows:
class Foo < ActiveRecord::Base
attr_accessible :bar
type_regex = /(dog)|(cat)|(bird)/
validates :bar, :presence => true,
:format => { :with => type_regex }
end
I need the type to match either dog, cat or bird exactly. In the above class, however, type_regex will match doggy, cathrine, etc.
How do I make the validation match those strings exactly?
Thank you
You'll need to add anchors to the regex. Specifically you need to add \A to the beginning and \Z to the end of the regex (\A and \Z meaning beginning- and end-of-string respectively).
Be careful with precedence though: due to the low precedence of | you'll either have to put a non-capturing group around the alternation or anchor each of the words separately. I.e. you have to do /\A(?:(dog)|(cat)|(bird))\Z/. Doing /\A(dog)|(cat)|(bird)\Z/ will not work because that way the \A will only apply to dog and the \Z only to bird.
The same is true if you use ^ and $ instead of \A and \Z. On that subject let me explain the difference between those: ^ and $ match the beginning and end of a line, not the string. So the string "dog\ngy" would still match the regex /^dog$/, but not the regex /\Adog\Z/.
The regex you need is:
type_regex = /(^dog$)|(^cat$)|(^bird$)/
The other suggestion by Augusto's will still match 'catherine', 'doggie'.
add $ at the end. For example:
type_regex = /[(dog)|(cat)|(bird)]$/
(you might need to escape the $). And to validate the start of string use ^
type_regex = /^[(dog)|(cat)|(bird)]/
so this is what you want... I think :)
type_regex = /^[(dog)|(cat)|(bird)]$/