├── .gitignore ├── .rspec ├── MIT-LICENSE ├── README.markdown ├── Rakefile ├── VERSION.yml ├── init.rb ├── install.rb ├── lib ├── locale │ ├── en.yml │ └── gd.yml └── validate_email.rb ├── spec ├── resources │ ├── user.rb │ ├── user_with_ar.rb │ ├── user_with_ar_legacy.rb │ ├── user_with_blank.rb │ ├── user_with_legacy.rb │ └── user_with_nil.rb ├── spec_helper.rb └── validate_email_spec.rb └── validate_email.gemspec /.gitignore: -------------------------------------------------------------------------------- 1 | coverage 2 | pkg 3 | rdoc 4 | test/tmp 5 | tmp 6 | .idea 7 | .rvmrc -------------------------------------------------------------------------------- /.rspec: -------------------------------------------------------------------------------- 1 | --colour 2 | --format documentation -------------------------------------------------------------------------------- /MIT-LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2010 PerfectLine LLC (www.perfectline.co.uk) 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining 4 | a copy of this software and associated documentation files (the 5 | "Software"), to deal in the Software without restriction, including 6 | without limitation the rights to use, copy, modify, merge, publish, 7 | distribute, sublicense, and/or sell copies of the Software, and to 8 | permit persons to whom the Software is furnished to do so, subject to 9 | the following conditions: 10 | 11 | The above copyright notice and this permission notice shall be 12 | included in all copies or substantial portions of the Software. 13 | 14 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 15 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 17 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 18 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 19 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 20 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /README.markdown: -------------------------------------------------------------------------------- 1 | # ValidateEmail 2 | 3 | This gem adds the capability of validating email addresses to `ActiveModel`. 4 | The gem only supports Rails 3 (has dependencies in ActiveModel and ActiveSupport 3.0) 5 | 6 | ### Installation 7 | # add this to your Gemfile 8 | gem "validate_email" 9 | 10 | # and then run 11 | rake gems:install 12 | 13 | # or just run 14 | sudo gem install validate_email 15 | 16 | ### Usage 17 | 18 | #### With ActiveRecord 19 | class Pony < ActiveRecord::Base 20 | # standard validation 21 | validates :email_address, :email => true 22 | 23 | # with allow_nil 24 | validates :email_address, :email => {:allow_nil => true} 25 | 26 | # with allow_blank 27 | validates :email_address, :email => {:allow_blank => true} 28 | end 29 | 30 | #### With ActiveModel 31 | class Unicorn 32 | include ActiveModel::Validations 33 | 34 | attr_accessor :email_address 35 | 36 | # with legacy syntax (the syntax above works also) 37 | validates_email :email_address, :allow_blank => true 38 | end 39 | 40 | #### I18n 41 | 42 | The error message will be looked up according to the standard ActiveModel::Errors scheme. 43 | For the above Unicorn class this would be: 44 | 45 | * activemodel.errors.models.unicorn.attributes.email_address.email 46 | * activemodel.errors.models.unicorn.email 47 | * activemodel.errors.messages.email 48 | * errors.attributes.email_address.email 49 | * errors.messages.email 50 | 51 | A default errors.messages.email of `is not a valid email address` is provided. 52 | You can also pass the `:message => "my custom error"` option to your validation to define your own custom message. 53 | 54 | ## Authors 55 | 56 | **Tanel Suurhans** () 57 | **Tarmo Lehtpuu** () 58 | 59 | ## License 60 | Copyright 2010 by PerfectLine LLC () and is released under the MIT license. 61 | -------------------------------------------------------------------------------- /Rakefile: -------------------------------------------------------------------------------- 1 | require 'rake' 2 | require 'rake/clean' 3 | require 'rdoc/task' 4 | require 'rspec/core/rake_task' 5 | require 'jeweler' 6 | 7 | desc 'Default: run specs.' 8 | task :default => :spec 9 | 10 | Jeweler::Tasks.new do |jewel| 11 | jewel.name = 'validate_email' 12 | jewel.summary = 'Library for validating email addresses in Rails 3 models.' 13 | jewel.email = ['tanel.suurhans@perfectline.ee', 'tarmo.lehtpuu@perfectline.ee'] 14 | jewel.homepage = 'http://github.com/perfectline/validates_email/tree/master' 15 | jewel.description = 'Library for validating email addresses in Rails 3 models.' 16 | jewel.authors = ["Tanel Suurhans", "Tarmo Lehtpuu"] 17 | jewel.files = FileList["lib/**/*.rb", "lib/locale/*.yml", "*.rb", "MIT-LICENCE", "README.markdown"] 18 | 19 | jewel.add_development_dependency 'rspec' 20 | jewel.add_development_dependency 'diff-lcs', '>= 1.1.2' 21 | jewel.add_development_dependency 'active_record', '>= 3.0.0' 22 | jewel.add_development_dependency 'sqlite3-ruby' 23 | 24 | jewel.add_dependency 'mail', '>= 2.2.5' 25 | jewel.add_dependency 'activemodel', '>= 3.0' 26 | end 27 | 28 | desc 'Generate documentation plugin.' 29 | Rake::RDocTask.new(:rdoc) do |rdoc| 30 | rdoc.rdoc_dir = 'rdoc' 31 | rdoc.title = 'ValidatesEmail' 32 | rdoc.options << '--line-numbers' << '--inline-source' 33 | rdoc.rdoc_files.include('README.markdown') 34 | rdoc.rdoc_files.include('lib/**/*.rb') 35 | end 36 | 37 | desc 'Run all rspec tests' 38 | RSpec::Core::RakeTask.new 39 | -------------------------------------------------------------------------------- /VERSION.yml: -------------------------------------------------------------------------------- 1 | --- 2 | :major: 0 3 | :minor: 1 4 | :patch: 6 5 | :build: 6 | -------------------------------------------------------------------------------- /init.rb: -------------------------------------------------------------------------------- 1 | require 'validate_email' 2 | -------------------------------------------------------------------------------- /install.rb: -------------------------------------------------------------------------------- 1 | puts IO.read(File.join(File.dirname(__FILE__), 'README.markdown')) 2 | -------------------------------------------------------------------------------- /lib/locale/en.yml: -------------------------------------------------------------------------------- 1 | en: 2 | errors: 3 | messages: 4 | email: is not a valid email address 5 | -------------------------------------------------------------------------------- /lib/locale/gd.yml: -------------------------------------------------------------------------------- 1 | gd: 2 | errors: 3 | messages: 4 | email: – chan eil seo ’na sheòladh puist-d dligheach 5 | -------------------------------------------------------------------------------- /lib/validate_email.rb: -------------------------------------------------------------------------------- 1 | require 'active_support/i18n' 2 | I18n.load_path << File.dirname(__FILE__) + '/locale/en.yml' 3 | require 'active_model' 4 | require 'mail' 5 | 6 | module ActiveModel 7 | module Validations 8 | class EmailValidator < ActiveModel::EachValidator 9 | 10 | def initialize(options) 11 | options.reverse_merge!(:message => :email) 12 | super(options) 13 | end 14 | 15 | def validate_each(record, attribute, value) 16 | 17 | begin 18 | mail = Mail::Address.new(value) 19 | 20 | unless mail.address == value && mail.domain.split(".").length > 1 21 | record.errors.add(attribute, options[:message]) 22 | end 23 | rescue 24 | record.errors.add(attribute, options[:message]) 25 | end 26 | end 27 | end 28 | 29 | module ClassMethods 30 | def validates_email(*attr_names) 31 | validates_with EmailValidator, _merge_attributes(attr_names) 32 | end 33 | end 34 | end 35 | end 36 | 37 | -------------------------------------------------------------------------------- /spec/resources/user.rb: -------------------------------------------------------------------------------- 1 | class User 2 | include ActiveModel::Validations 3 | 4 | attr_accessor :email_address 5 | 6 | validates :email_address, :email => true 7 | end -------------------------------------------------------------------------------- /spec/resources/user_with_ar.rb: -------------------------------------------------------------------------------- 1 | class UserWithAr < ActiveRecord::Base 2 | self.table_name = "users" 3 | 4 | validates :email_address, :email => { :message => "is not right" } 5 | end -------------------------------------------------------------------------------- /spec/resources/user_with_ar_legacy.rb: -------------------------------------------------------------------------------- 1 | class UserWithArLegacy < ActiveRecord::Base 2 | self.table_name = "users" 3 | 4 | validates_email :email_address 5 | end -------------------------------------------------------------------------------- /spec/resources/user_with_blank.rb: -------------------------------------------------------------------------------- 1 | class UserWithBlank 2 | include ActiveModel::Validations 3 | 4 | attr_accessor :email_address 5 | 6 | validates :email_address, :email => {:allow_blank => true} 7 | end -------------------------------------------------------------------------------- /spec/resources/user_with_legacy.rb: -------------------------------------------------------------------------------- 1 | class UserWithLegacy 2 | include ActiveModel::Validations 3 | 4 | attr_accessor :email_address 5 | 6 | validates_email :email_address, :allow_blank => true, :message => "is just wrong!" 7 | end -------------------------------------------------------------------------------- /spec/resources/user_with_nil.rb: -------------------------------------------------------------------------------- 1 | class UserWithNil 2 | include ActiveModel::Validations 3 | 4 | attr_accessor :email_address 5 | 6 | validates :email_address, :email => {:allow_nil => true} 7 | end -------------------------------------------------------------------------------- /spec/spec_helper.rb: -------------------------------------------------------------------------------- 1 | $LOAD_PATH.unshift(File.dirname(__FILE__) + '/../lib') 2 | $LOAD_PATH.unshift(File.dirname(__FILE__) + '/resources') 3 | $LOAD_PATH.unshift(File.dirname(__FILE__)) 4 | 5 | require 'validate_email' 6 | require 'rspec' 7 | require 'sqlite3' 8 | require 'active_record' 9 | require 'active_record/base' 10 | require 'active_record/migration' 11 | 12 | ActiveRecord::Migration.verbose = false 13 | ActiveRecord::Base.establish_connection( 14 | "adapter" => "sqlite3", 15 | "database" => ":memory:" 16 | ) 17 | 18 | require File.join(File.dirname(__FILE__), '..', 'init') 19 | 20 | autoload :User, 'resources/user' 21 | autoload :UserWithNil, 'resources/user_with_nil' 22 | autoload :UserWithBlank, 'resources/user_with_blank' 23 | autoload :UserWithLegacy, 'resources/user_with_legacy' 24 | autoload :UserWithAr, 'resources/user_with_ar' 25 | autoload :UserWithArLegacy, 'resources/user_with_ar_legacy' -------------------------------------------------------------------------------- /spec/validate_email_spec.rb: -------------------------------------------------------------------------------- 1 | require 'spec_helper' 2 | 3 | describe "Email validation" do 4 | 5 | before(:all) do 6 | ActiveRecord::Schema.define(:version => 1) do 7 | 8 | create_table :users, :force => true do |t| 9 | t.column :email_address, :string 10 | end 11 | 12 | end 13 | end 14 | 15 | after(:all) do 16 | ActiveRecord::Base.connection.drop_table(:users) 17 | end 18 | 19 | context "with regular validator" do 20 | before do 21 | @user = User.new 22 | end 23 | 24 | it "should not allow nil as email" do 25 | @user.email_address = nil 26 | @user.should_not be_valid 27 | end 28 | 29 | it "should not allow blank as email" do 30 | @user.email_address = "" 31 | @user.should_not be_valid 32 | end 33 | 34 | it "should not allow an email without domain extension" do 35 | @user.email_address = "user@example" 36 | @user.should_not be_valid 37 | end 38 | 39 | it "should not allow an email without @" do 40 | @user.email_address = "user" 41 | @user.should_not be_valid 42 | end 43 | 44 | it "should not allow an email without prefix" do 45 | @user.email_address = "@example.com" 46 | @user.should_not be_valid 47 | end 48 | 49 | it "should not allow an email without domain" do 50 | @user.email_address = "user@.com" 51 | @user.should_not be_valid 52 | end 53 | 54 | it "should accept a valid email address" do 55 | @user.email_address = "user@example.com" 56 | @user.should be_valid 57 | end 58 | 59 | it "should return an error message" do 60 | @user.email_address = "bad" 61 | @user.valid? 62 | @user.errors[:email_address].should == ["is not a valid email address"] 63 | end 64 | end 65 | 66 | context "with allow nil" do 67 | before do 68 | @user = UserWithNil.new 69 | end 70 | 71 | it "should allow nil as email" do 72 | @user.email_address = nil 73 | @user.should be_valid 74 | end 75 | 76 | it "should not allow blank as email" do 77 | @user.email_address = "" 78 | @user.should_not be_valid 79 | end 80 | 81 | it "should allow a valid email address" do 82 | @user.email_address = "user@example.com" 83 | @user.should be_valid 84 | end 85 | 86 | it "should return an error message" do 87 | @user.email_address = "bad" 88 | @user.valid? 89 | @user.errors[:email_address].should == ["is not a valid email address"] 90 | end 91 | end 92 | 93 | context "with allow blank" do 94 | before do 95 | @user = UserWithBlank.new 96 | end 97 | 98 | it "should allow nil as email" do 99 | @user.email_address = nil 100 | @user.should be_valid 101 | end 102 | 103 | it "should allow blank as email" do 104 | @user.email_address = "" 105 | @user.should be_valid 106 | end 107 | 108 | it "should allow a valid email address" do 109 | @user.email_address = "user@example.com" 110 | @user.should be_valid 111 | end 112 | 113 | it "should return an error message" do 114 | @user.email_address = "bad" 115 | @user.valid? 116 | @user.errors[:email_address].should == ["is not a valid email address"] 117 | end 118 | end 119 | 120 | context "with legacy syntax" do 121 | before do 122 | @user = UserWithLegacy.new 123 | end 124 | 125 | it "should allow nil as email" do 126 | @user.email_address = nil 127 | @user.should be_valid 128 | end 129 | 130 | it "should allow blank as email" do 131 | @user.email_address = "" 132 | @user.should be_valid 133 | end 134 | 135 | it "should allow a valid email address" do 136 | @user.email_address = "user@example.com" 137 | @user.should be_valid 138 | end 139 | 140 | it "should not allow invalid email" do 141 | @user.email_address = "random" 142 | @user.should_not be_valid 143 | end 144 | 145 | it "should return an error message" do 146 | @user.email_address = "bad" 147 | @user.valid? 148 | @user.errors[:email_address].should == ["is just wrong!"] 149 | end 150 | end 151 | 152 | context "with ActiveRecord" do 153 | before do 154 | @user = UserWithAr.new 155 | end 156 | 157 | it "should not allow invalid email" do 158 | @user.email_address = "" 159 | @user.should_not be_valid 160 | end 161 | 162 | it "should return an error message" do 163 | @user.email_address = "bad" 164 | @user.valid? 165 | @user.errors[:email_address].should == ["is not right"] 166 | end 167 | end 168 | 169 | context "with ActiveRecord and legacy syntax" do 170 | before do 171 | @user = UserWithArLegacy.new 172 | end 173 | 174 | it "should not allow invalid email" do 175 | @user.email_address = "" 176 | @user.should_not be_valid 177 | end 178 | 179 | it "should return an error message" do 180 | @user.email_address = "bad" 181 | @user.valid? 182 | @user.errors[:email_address].should == ["is not a valid email address"] 183 | end 184 | end 185 | 186 | end -------------------------------------------------------------------------------- /validate_email.gemspec: -------------------------------------------------------------------------------- 1 | # Generated by jeweler 2 | # DO NOT EDIT THIS FILE DIRECTLY 3 | # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec' 4 | # -*- encoding: utf-8 -*- 5 | 6 | Gem::Specification.new do |s| 7 | s.name = "validate_email" 8 | s.version = "0.1.6" 9 | 10 | s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version= 11 | s.authors = ["Tanel Suurhans", "Tarmo Lehtpuu"] 12 | s.date = "2012-07-12" 13 | s.description = "Library for validating email addresses in Rails 3 models." 14 | s.email = ["tanel.suurhans@perfectline.ee", "tarmo.lehtpuu@perfectline.ee"] 15 | s.extra_rdoc_files = [ 16 | "README.markdown" 17 | ] 18 | s.files = [ 19 | "README.markdown", 20 | "init.rb", 21 | "install.rb", 22 | "lib/locale/en.yml", 23 | "lib/validate_email.rb" 24 | ] 25 | s.homepage = "http://github.com/perfectline/validates_email/tree/master" 26 | s.require_paths = ["lib"] 27 | s.rubygems_version = "1.8.24" 28 | s.summary = "Library for validating email addresses in Rails 3 models." 29 | s.license = "MIT" 30 | 31 | if s.respond_to? :specification_version then 32 | s.specification_version = 3 33 | 34 | if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then 35 | s.add_development_dependency(%q, [">= 0"]) 36 | s.add_development_dependency(%q, [">= 1.1.2"]) 37 | s.add_development_dependency(%q, [">= 3.0.0"]) 38 | s.add_development_dependency(%q, [">= 0"]) 39 | s.add_runtime_dependency(%q, [">= 2.2.5"]) 40 | s.add_runtime_dependency(%q, [">= 3.0"]) 41 | else 42 | s.add_dependency(%q, [">= 0"]) 43 | s.add_dependency(%q, [">= 1.1.2"]) 44 | s.add_dependency(%q, [">= 3.0.0"]) 45 | s.add_dependency(%q, [">= 0"]) 46 | s.add_dependency(%q, [">= 2.2.5"]) 47 | s.add_dependency(%q, [">= 3.0"]) 48 | end 49 | else 50 | s.add_dependency(%q, [">= 0"]) 51 | s.add_dependency(%q, [">= 1.1.2"]) 52 | s.add_dependency(%q, [">= 3.0.0"]) 53 | s.add_dependency(%q, [">= 0"]) 54 | s.add_dependency(%q, [">= 2.2.5"]) 55 | s.add_dependency(%q, [">= 3.0"]) 56 | end 57 | end 58 | 59 | --------------------------------------------------------------------------------