naughty_or_nice 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/LICENSE.md +21 -0
- data/README.md +60 -0
- data/lib/naughty_or_nice.rb +112 -0
- metadata +49 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: cc80dcfb26cbb5c4c7eac6db2ac75d5a753c8b67
|
4
|
+
data.tar.gz: 3ca21738914b3859ce1cf48feeeb92ee83cc9372
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: b63b245920688a8b36b6b33bd2fd5d5bc18b558d5ca066882625da05aeb703dcaca9a1754a42cb30ead40f763b2425f9c40b2409934d3e27516946f5ea2f5cdc
|
7
|
+
data.tar.gz: b43c3c6c18074c5341c4d9185245580c276182ae845bc052c5587c6bfbe81aaed9a21c6ecb606f9245bc3366c455815ca3b6942ccc799ed09c1280889ab92b71
|
data/LICENSE.md
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2014 Ben Balter
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
13
|
+
copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
21
|
+
SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,60 @@
|
|
1
|
+
# Naughty or Nice
|
2
|
+
|
3
|
+
Naughty or Nice simplifies the process of extracting domain information from a domain-like string (an email, a URL, etc.) and checking whether it meets criteria you specify.
|
4
|
+
|
5
|
+
## Usage
|
6
|
+
|
7
|
+
Naughty or Nice doesn't do too much on its own. Out of the box, it can extract a domain from a domain-like string, and can verify that it is, in fact, a valid domain. It does this by leveraging the power of the [Public Suffix List](http://publicsuffix.org/), and the associated [Ruby Gem](https://github.com/weppos/publicsuffix-ruby).
|
8
|
+
|
9
|
+
The true power of Naughty or Nice comes when you extended it into a child class.
|
10
|
+
|
11
|
+
## Extending Naughty or Nice
|
12
|
+
|
13
|
+
Let's say you have a list of three domains, `foo.com`, `bar.com`, and `foobar.com`. You'd spec out a class like so:
|
14
|
+
|
15
|
+
```ruby
|
16
|
+
class Checker < NaughtyOrNice
|
17
|
+
DOMAINS = %w[foo.com bar.com foobar.com]
|
18
|
+
|
19
|
+
def valid?
|
20
|
+
DOMAINS.include? domain
|
21
|
+
end
|
22
|
+
end
|
23
|
+
```
|
24
|
+
|
25
|
+
That's it! Just overwrite the `valid?` method and Naughty or Nice takes care of the rest.
|
26
|
+
|
27
|
+
## Using the extended class
|
28
|
+
|
29
|
+
There are a handful of magic methods that your child class automatically gets. You can throw any domain-like string at your new `Checker` class, and figure out if it's on the list. Here's a few examples:
|
30
|
+
|
31
|
+
```ruby
|
32
|
+
Checker.valid? "foo.com" #=> true
|
33
|
+
Checker.valid? "foo.org" #=> false
|
34
|
+
```
|
35
|
+
|
36
|
+
Notice we're using the class method `valid?` That automatically calls `Checker.new(string).valid?` for you. Cool, huh?
|
37
|
+
|
38
|
+
But you don't just need to give Checker crisp, clean domains. Let's get a bit trickier:
|
39
|
+
|
40
|
+
```ruby
|
41
|
+
Checker.valid? "http://foo.bar.com" #=> true
|
42
|
+
Checker.valid? "foo@bar.com" #=> true
|
43
|
+
Checker.valid? "foobar" => false
|
44
|
+
```
|
45
|
+
|
46
|
+
## Extracting domain information
|
47
|
+
|
48
|
+
You can also you NaughtyOrNice to extract domain information for use elsewhere. Continuing our above example:
|
49
|
+
|
50
|
+
```ruby
|
51
|
+
address = Checker.new "baz@foo.bar.com"
|
52
|
+
address.valid? #=> true
|
53
|
+
address.domain #=> "foo.bar.com"
|
54
|
+
address.domain_parts.tld #=> "com"
|
55
|
+
address.domain_parts.sld #=> "bar"
|
56
|
+
```
|
57
|
+
|
58
|
+
## See it in action
|
59
|
+
|
60
|
+
Take a look at [Gman](https://github.com/benbalter/gman) to see Naughty or Nice in action. Gman uses a crowd-sourced list of government domains to check if a given email address is a government email.
|
@@ -0,0 +1,112 @@
|
|
1
|
+
require 'public_suffix'
|
2
|
+
require "addressable/uri"
|
3
|
+
|
4
|
+
class NaughtyOrNice
|
5
|
+
|
6
|
+
class << self
|
7
|
+
def valid?(text)
|
8
|
+
self.new(text).valid?
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
# Source: http://bit.ly/1n2X9iv
|
13
|
+
EMAIL_REGEX = %r{
|
14
|
+
^
|
15
|
+
(
|
16
|
+
[\w\!\#\$\%\&\'\*\+\-\/\=\?\^\`\{\|\}\~]+
|
17
|
+
\.
|
18
|
+
)
|
19
|
+
*
|
20
|
+
[\w\!\#\$\%\&\'\*\+\-\/\=\?\^\`\{\|\}\~]+
|
21
|
+
@
|
22
|
+
(
|
23
|
+
(
|
24
|
+
(
|
25
|
+
(
|
26
|
+
(
|
27
|
+
[a-z0-9]{1}
|
28
|
+
[a-z0-9\-]{0,62}
|
29
|
+
[a-z0-9]{1}
|
30
|
+
)
|
31
|
+
|
|
32
|
+
[a-z]
|
33
|
+
)
|
34
|
+
\.
|
35
|
+
)+
|
36
|
+
[a-z]{2,6}
|
37
|
+
)
|
38
|
+
|
|
39
|
+
(
|
40
|
+
\d{1,3}
|
41
|
+
\.
|
42
|
+
){3}
|
43
|
+
\d{1,3}
|
44
|
+
(
|
45
|
+
\:\d{1,5}
|
46
|
+
)?
|
47
|
+
)
|
48
|
+
$
|
49
|
+
}xi
|
50
|
+
|
51
|
+
def initialize(text)
|
52
|
+
@text = text.to_s.downcase.strip
|
53
|
+
end
|
54
|
+
|
55
|
+
# Parse the domain from the input string
|
56
|
+
#
|
57
|
+
# Can handle urls, domains, or emails
|
58
|
+
#
|
59
|
+
# Returns the domain string
|
60
|
+
def domain
|
61
|
+
@domain ||= begin
|
62
|
+
return nil if @text.empty?
|
63
|
+
|
64
|
+
uri = Addressable::URI.parse(@text)
|
65
|
+
|
66
|
+
if uri.host # valid https?://* URI
|
67
|
+
uri.host
|
68
|
+
elsif email?
|
69
|
+
@text.match(/@([\w\.\-]+)\Z/i)[1]
|
70
|
+
else # url sans http://
|
71
|
+
begin
|
72
|
+
uri = Addressable::URI.parse("http://#{@text}")
|
73
|
+
# properly parse http://foo edge cases
|
74
|
+
# see https://github.com/sporkmonger/addressable/issues/145
|
75
|
+
uri.host if uri.host =~ /\./
|
76
|
+
rescue Addressable::URI::InvalidURIError
|
77
|
+
nil
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
82
|
+
alias_method :to_s, :domain
|
83
|
+
|
84
|
+
# Checks if the input string represents a valid domain
|
85
|
+
#
|
86
|
+
# Returns boolean true if a valid domain, otherwise false
|
87
|
+
def valid?
|
88
|
+
PublicSuffix.valid?(domain)
|
89
|
+
end
|
90
|
+
|
91
|
+
# Is the input text in the form of a valid email address?
|
92
|
+
#
|
93
|
+
# Returns true if email, otherwise false
|
94
|
+
def email?
|
95
|
+
!!(@text =~ EMAIL_REGEX)
|
96
|
+
end
|
97
|
+
|
98
|
+
# Helper function to return the public suffix domain object
|
99
|
+
#
|
100
|
+
# Supports all domain strings (URLs, emails)
|
101
|
+
#
|
102
|
+
# Returns the domain object or nil, but no errors, never an error
|
103
|
+
def domain_parts
|
104
|
+
PublicSuffix.parse domain
|
105
|
+
rescue PublicSuffix::DomainInvalid
|
106
|
+
nil
|
107
|
+
end
|
108
|
+
|
109
|
+
def inspect
|
110
|
+
"#<#{self.class} domain=\"#{domain}\" valid=#{valid?}>"
|
111
|
+
end
|
112
|
+
end
|
metadata
ADDED
@@ -0,0 +1,49 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: naughty_or_nice
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Ben Balter
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2014-09-18 00:00:00.000000000 Z
|
12
|
+
dependencies: []
|
13
|
+
description: Naughty or Nice simplifies the process of extracting domain information
|
14
|
+
from a domain-like string (an email, a URL, etc.) and checking whether it meets
|
15
|
+
criteria you specify.
|
16
|
+
email: ben.balter@github.com
|
17
|
+
executables: []
|
18
|
+
extensions: []
|
19
|
+
extra_rdoc_files: []
|
20
|
+
files:
|
21
|
+
- LICENSE.md
|
22
|
+
- README.md
|
23
|
+
- lib/naughty_or_nice.rb
|
24
|
+
homepage: http://github.com/benbalter/naughty_or_nice
|
25
|
+
licenses:
|
26
|
+
- MIT
|
27
|
+
metadata: {}
|
28
|
+
post_install_message:
|
29
|
+
rdoc_options: []
|
30
|
+
require_paths:
|
31
|
+
- lib
|
32
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
33
|
+
requirements:
|
34
|
+
- - ">="
|
35
|
+
- !ruby/object:Gem::Version
|
36
|
+
version: '0'
|
37
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
38
|
+
requirements:
|
39
|
+
- - ">="
|
40
|
+
- !ruby/object:Gem::Version
|
41
|
+
version: '0'
|
42
|
+
requirements: []
|
43
|
+
rubyforge_project:
|
44
|
+
rubygems_version: 2.2.0
|
45
|
+
signing_key:
|
46
|
+
specification_version: 4
|
47
|
+
summary: You've made the list. We'll help you check it twice. Given a domain-like
|
48
|
+
string, verifies inclusion in a list you provide.
|
49
|
+
test_files: []
|