Skip to content

Commit

Permalink
Merge pull request phatworx#19 from cluesque/plain_ruby_validator
Browse files Browse the repository at this point in the history
Add a class method for simpler validation
  • Loading branch information
balexand committed Dec 8, 2014
2 parents 7a6004e + d1631ab commit 9c884aa
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 2 deletions.
17 changes: 17 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,23 @@ Or you can do this in a specific `validates` call:
validates :my_email_attribute, :email => {:strict_mode => true}
```

## Validation outside a model

If you need to validate an email outside a model, you can get the regexp :

### Normal mode

```ruby
EmailValidator.regexp # returns the regex
EmailValidator.valid?('[email protected]') # boolean
```

### Strict mode

```ruby
EmailValidator.regexp(:strict_mode => true)
```

## Thread safety

This gem is thread safe, with one caveat: `EmailValidator.default_options` must be configured before use in a multi-threaded environment. If you configure `default_options` in a Rails initializer file, then you're good to go since initializers are run before worker threads are spawned.
Expand Down
16 changes: 14 additions & 2 deletions lib/email_validator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,26 @@
class EmailValidator < ActiveModel::EachValidator
@@default_options = {}

def self.regexp(options = {})
options = default_options.merge(options)

name_validation = options[:strict_mode] ? "-a-z0-9+._" : "^@\\s"

/\A\s*([#{name_validation}]{1,64})@((?:[-a-z0-9]+\.)+[a-z]{2,})\s*\z/i
end

def self.valid?(value, options = {})
!!(value =~ regexp(options))
end

def self.default_options
@@default_options
end

def validate_each(record, attribute, value)
options = @@default_options.merge(self.options)
name_validation = options[:strict_mode] ? "-a-z0-9+._" : "^@\\s"
unless value =~ /\A\s*([#{name_validation}]{1,64})@((?:[-a-z0-9]+\.)+[a-z]{2,})\s*\z/i

unless self.class.valid?(value, self.options)
record.errors.add(attribute, options[:message] || :invalid)
end
end
Expand Down
32 changes: 32 additions & 0 deletions spec/email_validator_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,18 @@ class TestUserWithMessage < TestModel
StrictUser.new(:email => email).should be_valid
end

it "#{email.inspect} should match the regexp" do
(!!(email =~ EmailValidator.regexp)).should be_truthy
end

it "#{email.inspect} should match the strict regexp" do
(!!(email =~ EmailValidator.regexp(:strict_mode => true))).should be_truthy
end

it "#{email.inspect} should pass the class tester" do
expect(EmailValidator.valid?(email)).to be_truthy
end

end

end
Expand Down Expand Up @@ -96,6 +108,18 @@ class TestUserWithMessage < TestModel
StrictUser.new(:email => email).should_not be_valid
end

it "#{email.inspect} should not match the regexp" do
expect(email =~ EmailValidator.regexp).to be_falsy
end

it "#{email.inspect} should not match the strict regexp" do
expect(email =~ EmailValidator.regexp(:strict_mode => true)).to be_falsy
end

it "#{email.inspect} should fail the class tester" do
expect(EmailValidator.valid?(email)).to be_falsy
end

end
end

Expand All @@ -117,6 +141,14 @@ class TestUserWithMessage < TestModel
StrictUser.new(:email => email).should_not be_valid
end

it "#{email.inspect} should match the regexp" do
expect(email =~ EmailValidator.regexp).to be_truthy
end

it "#{email.inspect} should not match the strict regexp" do
expect(email =~ EmailValidator.regexp(:strict_mode => true)).to be_falsy
end

end
end
end
Expand Down

0 comments on commit 9c884aa

Please sign in to comment.