banned_words 0.1.0 → 0.1.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.
data/.travis.yml ADDED
@@ -0,0 +1,7 @@
1
+ language: ruby
2
+ rvm:
3
+ - 1.8.7
4
+ - 1.9.2
5
+ - 1.9.3
6
+ # uncomment this line if your project needs to run something other than `rake`:
7
+ script: bundle exec rspec spec
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2012 Razvan Secara
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md CHANGED
@@ -1,6 +1,8 @@
1
1
  # Banned Words
2
2
  Detects and masks banned words within a text
3
3
 
4
+ [![Build Status](https://secure.travis-ci.org/razvan-sv/banned_words.png?branch=master)](http://travis-ci.org/razvan-sv/banned_words)
5
+
4
6
  ## Installation
5
7
 
6
8
  Add this line in your Gemfile:
@@ -8,17 +10,60 @@ Add this line in your Gemfile:
8
10
  ```ruby
9
11
  gem 'banned_words'
10
12
  ```
13
+ Then you need to run:
14
+
15
+ ```ruby
16
+ rails g banned_words
17
+ ```
18
+ to generate the banned_words.yml file.
11
19
 
12
20
  ## Usage
13
21
 
22
+ ### Masking
14
23
  ```ruby
24
+ # Single banned word
15
25
  BannedWords.create!('dog')
26
+ phrase = 'Red d-o-g'
27
+ BannedWords.mask(phrase)
28
+ > 'Red *Buzz*'
29
+
30
+ # With an array of banned words
31
+ BannedWords.create!(['fox', 'over'])
16
32
  phrase = 'The quick brown fox jumps over the lazy dog'
17
33
  BannedWords.mask(phrase)
18
- > 'The quick brown fox jumps over the lazy *Buzz*'
34
+ > 'The quick brown *Buzz* jumps *Buzz* the lazy *Buzz*'
35
+
36
+ # Override the masking word
37
+ BannedWords.mask(phrase, "*Bad Word*")
38
+ > 'The quick brown *Bad Word* jumps *Bad Word* the lazy *Bad Word*'
39
+ ```
40
+
41
+ ### Detecting
42
+ ```ruby
43
+ BannedWords.create!(['quick', 'jumps'])
44
+ phrase = 'The q-u#-_^i!c~k brown fox j=u m p?s over the lazy dog'
45
+ BannedWords.detect(phrase)
46
+ > ['q-u#-_^i!c~k', 'j=u m p?s']
47
+ ```
48
+
49
+ ### Listing
50
+ ```ruby
51
+ BannedWords.list
52
+ > ['dog', 'fox', 'over']
53
+ ```
54
+
55
+ ### Removing
56
+ ```ruby
57
+ BannedWords.remove('dog')
58
+ BannedWords.list
59
+ > ['fox', 'over']
19
60
 
20
61
  # Another example:
21
- phrase = 'Red d-o-g'
22
- BannedWords.mask(phrase)
23
- > 'Red *Buzz*'
24
- ```
62
+ BannedWords.remove(['fox', 'over'])
63
+ BannedWords.list
64
+ > []
65
+ ```
66
+
67
+ ## Copyright
68
+
69
+ See LICENSE for details.
data/banned_words.gemspec CHANGED
@@ -3,10 +3,10 @@ $:.push File.expand_path("../lib", __FILE__)
3
3
 
4
4
  Gem::Specification.new do |s|
5
5
  s.name = "banned_words"
6
- s.version = "0.1.0"
6
+ s.version = "0.1.1"
7
7
  s.authors = ["Razvan Secara", "Pop Sabina"]
8
8
  s.email = ["secara.razvan@yahoo.com"]
9
- s.homepage = ""
9
+ s.homepage = "https://github.com/razvan-sv/banned_words"
10
10
  s.summary = %q{Detects and masks banned words within a text}
11
11
  s.description = %q{Detects and masks banned words within a text}
12
12
 
@@ -5,27 +5,30 @@ module Core
5
5
  BW_REGEX = "[^a-zA-Z0-9]*"
6
6
 
7
7
  #
8
- # Create a banned word. The supplied word is transformed into a banned word
9
- # and stored into the storage file. The banned word is returned.
8
+ # Create banned words. The supplied words are transformed into a banned words
9
+ # and stored into the storage file. An array of banned words is returned.
10
10
  #
11
11
  # ==== Parameters
12
12
  #
13
- # word<String>::
14
- # Contains no more than a word.
15
- # Returns nil if the word failed to be converted into a banned word.
13
+ # words<String> or <Array>::
14
+ # Contains a word or an array of words. The words should not contain spaces.
16
15
  #
17
- def create!(word)
16
+ def create!(words)
18
17
 
19
18
  Storage::FileStore.ensure_storage_file
20
- word = word.downcase.strip
19
+ words = words_to_array(words)
21
20
 
22
- if regexed_word = word_to_regex(word)
21
+ if words.present?
23
22
  bw_file = Storage::FileStore.load_storage
24
- bw_file[word] = regexed_word
23
+ regexed_words = words.map do |word|
24
+ if regexed_word = word_to_regex(word)
25
+ bw_file[word] = regexed_word
26
+ end
27
+ end
25
28
  Storage::FileStore.write_to_storage(bw_file)
26
29
  end
27
30
 
28
- regexed_word
31
+ regexed_words || []
29
32
  end
30
33
 
31
34
  #
@@ -43,7 +46,7 @@ module Core
43
46
  # Don't bother verifying if the text isn't present
44
47
  return nil unless text.present?
45
48
 
46
- if banned_words = YAML.load_file(Storage::FileStore.file_path)
49
+ if banned_words = Storage::FileStore.load_storage
47
50
  bw = banned_words.values.join("|")
48
51
  text.gsub!(/#{bw}/i, replace_with)
49
52
  end
@@ -59,14 +62,54 @@ module Core
59
62
  end
60
63
 
61
64
  #
62
- # Removes all banned words. If the storage file isn't found an error is raised.
65
+ # Detects the banned words in the supplied text.
66
+ # It returnes an array containing the found banned words.
67
+ # An empty array is returned if no banned words are found.
68
+ #
69
+ # ==== Parameters
70
+ #
71
+ # text<String>::
72
+ # The text which is checked for banned words.
73
+ #
74
+ def detect(text)
75
+ # Don't bother verifying if the text isn't present
76
+ return [] unless text.present?
77
+
78
+ if banned_words = Storage::FileStore.load_storage
79
+ bw = banned_words.values.join("|")
80
+ return text.scan(/#{bw}/i)
81
+ end
82
+
83
+ []
84
+ end
85
+
86
+ #
87
+ # Removes all banned words from the storage fild.
88
+ # If the storage file isn't found an error is raised.
63
89
  #
64
90
  def clear
65
91
  Storage::FileStore.empty_storage!
66
92
  end
67
93
 
94
+ #
95
+ # Removes the supplied banned words from the list.
96
+ #
97
+ # ==== Parameters
98
+ #
99
+ # words<String> or <Array>::
100
+ # Contains a word or an array of words.
101
+ #
102
+ def remove(words)
103
+ words = words_to_array(words)
104
+
105
+ if (bw_list = Storage::FileStore.load_storage).present?
106
+ new_bw = bw_list.reject { |name, regexed_name| words.include?(name) }
107
+ Storage::FileStore.write_to_storage(new_bw) if new_bw != bw_list
108
+ end
109
+ end
110
+
68
111
  private
69
-
112
+
70
113
  #
71
114
  # Transforms the word into a banned word. The BW_REGEX gets attached between every char.
72
115
  #
@@ -75,6 +118,7 @@ module Core
75
118
  return nil if word.blank? || word[" "]
76
119
 
77
120
  regexed_word = ""
121
+ word = word.downcase.strip
78
122
  word.chars.each_with_index do |char, i|
79
123
  regexed_word += char
80
124
  # Don't attach the regex after the last char.
@@ -84,4 +128,11 @@ module Core
84
128
  regexed_word
85
129
  end
86
130
 
131
+ #
132
+ # TODO
133
+ #
134
+ def words_to_array(words)
135
+ words.is_a?(Array) ? words : [words]
136
+ end
137
+
87
138
  end
@@ -15,7 +15,7 @@ module Storage
15
15
  def storage_exists?
16
16
  File.exists?(file_path)
17
17
  end
18
-
18
+
19
19
  #
20
20
  # Write new data to storage. The supplied hash value will overwrite the
21
21
  # exising data from the storage.
@@ -30,18 +30,26 @@ module Storage
30
30
  YAML.dump(value, file)
31
31
  end
32
32
  end
33
-
33
+
34
34
  #
35
- # Returns a hash containing the banned words.
36
- # If no banned words are present the returned has is empty.
35
+ # Returns a hash containing the banned words along with their regexes.
36
+ # If no banned words are present the returned hash is empty.
37
37
  #
38
- def list_contents
38
+ def load_storage
39
39
  YAML.load_file(file_path) || {}
40
40
  end
41
- alias_method :load_storage, :list_contents
42
-
41
+
43
42
  #
44
- # Returns a hash containing the banned words if the storage file exists.
43
+ # Returns an array containing the banned words.
44
+ # If no banned words are present the returned array is empty.
45
+ #
46
+ def list_contents
47
+ list = load_storage
48
+ list.is_a?(Hash) ? list.keys.sort : [list]
49
+ end
50
+
51
+ #
52
+ # Returns an array containing the banned words if the storage file exists.
45
53
  # Otherwise an error is raised.
46
54
  #
47
55
  def list_contents!
@@ -51,7 +59,7 @@ module Storage
51
59
  raise IOError, "No banned words file!"
52
60
  end
53
61
  end
54
-
62
+
55
63
  #
56
64
  # Clear the storage.
57
65
  #
@@ -59,7 +67,7 @@ module Storage
59
67
  write_to_storage
60
68
  end
61
69
  alias_method :new_storage, :empty_storage
62
-
70
+
63
71
  #
64
72
  # Clear storage file if it exists.
65
73
  # Otherwise an error is raised.
@@ -71,14 +79,14 @@ module Storage
71
79
  raise IOError, "No banned words file!"
72
80
  end
73
81
  end
74
-
82
+
75
83
  #
76
84
  # Creates the storage file if it's not present
77
85
  #
78
86
  def ensure_storage_file
79
87
  new_storage if !storage_exists?
80
88
  end
81
-
89
+
82
90
  #
83
91
  # Mostly used in specs
84
92
  #
@@ -2,15 +2,27 @@ require "spec_helper"
2
2
 
3
3
  describe Core do
4
4
  let(:banned_words) { ["quick", "jumps", "dog"] }
5
+ let(:cart_regex) { "c[^a-zA-Z0-9]*a[^a-zA-Z0-9]*r[^a-zA-Z0-9]*t" }
6
+ let(:phrase) { "The q-u#-_^i!c~k brown fox j=u m p?s over the lazy dog" }
5
7
 
6
8
  context ".create!" do
7
9
  context "with success" do
8
- it "adds a banned word to the storage file" do
10
+ it "single banned word" do
9
11
  BannedWords.list.size.should == 0
10
- BannedWords.create!("punk")
11
- list = BannedWords.list
12
+ BannedWords.create!("cart").should == [cart_regex]
13
+ list = Storage::FileStore.load_storage
12
14
  list.size.should == 1
13
- list["punk"].should == "p[^a-zA-Z0-9]*u[^a-zA-Z0-9]*n[^a-zA-Z0-9]*k"
15
+ list["cart"].should == cart_regex
16
+ end
17
+ it "array of banned words" do
18
+ BannedWords.list.size.should == 0
19
+ result = BannedWords.create!(banned_words)
20
+ result.should == [
21
+ "q[^a-zA-Z0-9]*u[^a-zA-Z0-9]*i[^a-zA-Z0-9]*c[^a-zA-Z0-9]*k",
22
+ "j[^a-zA-Z0-9]*u[^a-zA-Z0-9]*m[^a-zA-Z0-9]*p[^a-zA-Z0-9]*s",
23
+ "d[^a-zA-Z0-9]*o[^a-zA-Z0-9]*g"
24
+ ]
25
+ BannedWords.list.size.should == 3
14
26
  end
15
27
  end
16
28
 
@@ -25,9 +37,7 @@ describe Core do
25
37
 
26
38
  context ".mask" do
27
39
  before do
28
- banned_words.each do |word|
29
- BannedWords.create!(word)
30
- end
40
+ BannedWords.create!(banned_words)
31
41
  end
32
42
 
33
43
  context "success" do
@@ -37,15 +47,17 @@ describe Core do
37
47
  new_phrase.should == "The *Buzz* is purple"
38
48
  new_phrase.should_not include "dog"
39
49
  end
40
-
41
50
  it "detects & masks more banned words - dog, jumps, quick" do
42
- phrase = "The quick brown fox jumps over the lazy dog"
43
51
  new_phrase = BannedWords.mask(phrase)
44
52
  new_phrase.should == "The *Buzz* brown fox *Buzz* over the lazy *Buzz*"
45
53
  banned_words.each do |bw|
46
54
  new_phrase.should_not include bw
47
55
  end
48
56
  end
57
+ it "mask with *Bad Word*" do
58
+ new_phrase = BannedWords.mask(phrase, "*Bad Word*")
59
+ new_phrase.should == "The *Bad Word* brown fox *Bad Word* over the lazy *Bad Word*"
60
+ end
49
61
  end
50
62
 
51
63
  context "no changes" do
@@ -55,21 +67,32 @@ describe Core do
55
67
  new_phrase.should == phrase
56
68
  end
57
69
  end
70
+ end
58
71
 
72
+ context ".detect" do
73
+ it "returns banned words within a text" do
74
+ BannedWords.create!(banned_words)
75
+ BannedWords.detect(phrase).should == ["q-u#-_^i!c~k", "j=u m p?s", "dog"]
76
+ end
77
+ it "doesn't find any banned words" do
78
+ BannedWords.create!(banned_words)
79
+ BannedWords.detect("How do you do").should == []
80
+ end
81
+ it "no text is supplied" do
82
+ BannedWords.detect("").should == []
83
+ end
59
84
  end
60
85
 
61
86
  context ".list" do
62
87
  it "no banned words in list" do
63
88
  BannedWords.list.size.should == 0
64
89
  end
65
-
66
90
  it "displays 2 banned words" do
67
- ["jack", "black"].map {|word| BannedWords.create!(word)}
91
+ BannedWords.create!(["jack", "black"])
68
92
  list = BannedWords.list
69
93
  list.size.should == 2
70
- list.keys.should == ["jack", "black"]
94
+ list.should == ["black", "jack"]
71
95
  end
72
-
73
96
  it "raises an error if the banned words file isn't found" do
74
97
  Storage::FileStore.remove_storage_file
75
98
  expect { BannedWords.list }.to raise_error(IOError, "No banned words file!")
@@ -83,11 +106,27 @@ describe Core do
83
106
  BannedWords.clear
84
107
  BannedWords.list.size.should == 0
85
108
  end
86
-
87
109
  it "raises NoBannedWordsFile" do
88
110
  Storage::FileStore.remove_storage_file
89
111
  expect { BannedWords.clear }.to raise_error(IOError, "No banned words file!")
90
112
  end
91
113
  end
92
114
 
115
+ context ".remove" do
116
+ before do
117
+ BannedWords.create!(banned_words)
118
+ end
119
+ it "one banned word" do
120
+ BannedWords.remove("dog")
121
+ BannedWords.list.should == ["jumps", "quick"]
122
+ end
123
+ it "many banned words" do
124
+ BannedWords.remove(["dog", "quick"])
125
+ BannedWords.list.should == ["jumps"]
126
+ end
127
+ it "banned word not found" do
128
+ BannedWords.remove(["ringo"])
129
+ BannedWords.list.should == ["dog", "jumps", "quick"]
130
+ end
131
+ end
93
132
  end
@@ -20,7 +20,7 @@ describe Storage::FileStore do
20
20
 
21
21
  context ".list_contents" do
22
22
  it "returns no elements" do
23
- Storage::FileStore.list_contents.should == {}
23
+ Storage::FileStore.list_contents.should == []
24
24
  end
25
25
  it "returns one element" do
26
26
  add_and_check("cat")
@@ -30,7 +30,7 @@ describe Storage::FileStore do
30
30
  context ".list_contents!" do
31
31
  it "returns one element" do
32
32
  Storage::FileStore.write_to_storage("cat")
33
- Storage::FileStore.list_contents!.should == "cat"
33
+ Storage::FileStore.list_contents!.should == ["cat"]
34
34
  end
35
35
 
36
36
  it "raises IOError" do
@@ -44,7 +44,7 @@ describe Storage::FileStore do
44
44
  it "cleares all data" do
45
45
  add_and_check("cat")
46
46
  Storage::FileStore.empty_storage
47
- Storage::FileStore.list_contents.should == {}
47
+ Storage::FileStore.list_contents.should == []
48
48
  end
49
49
  end
50
50
 
@@ -52,7 +52,7 @@ describe Storage::FileStore do
52
52
  it "cleares all data" do
53
53
  add_and_check("cat")
54
54
  Storage::FileStore.empty_storage!
55
- Storage::FileStore.list_contents.should == {}
55
+ Storage::FileStore.list_contents.should == []
56
56
  end
57
57
 
58
58
  it "raises IOError" do
@@ -68,23 +68,16 @@ describe Storage::FileStore do
68
68
  ["new_storage", "empty_storage"].each do |method|
69
69
  add_and_check("cat")
70
70
  Storage::FileStore.send(method)
71
- Storage::FileStore.list_contents.should == {}
71
+ Storage::FileStore.list_contents.should == []
72
72
  end
73
73
  end
74
74
  end
75
-
76
- context ".load_storage" do
77
- it "behaves like .list_contents" do
78
- Storage::FileStore.write_to_storage("mouse")
79
- Storage::FileStore.load_storage.should == Storage::FileStore.list_contents
80
- end
81
- end
82
75
  end
83
76
 
84
77
  private
85
78
 
86
79
  def add_and_check(word)
87
80
  Storage::FileStore.write_to_storage(word)
88
- Storage::FileStore.list_contents.should == word
81
+ Storage::FileStore.list_contents.should == [word]
89
82
  end
90
83
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: banned_words
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.1.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -10,11 +10,11 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2012-03-21 00:00:00.000000000Z
13
+ date: 2012-03-23 00:00:00.000000000Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rspec
17
- requirement: &20016960 !ruby/object:Gem::Requirement
17
+ requirement: &16334280 !ruby/object:Gem::Requirement
18
18
  none: false
19
19
  requirements:
20
20
  - - ! '>='
@@ -22,10 +22,10 @@ dependencies:
22
22
  version: '0'
23
23
  type: :development
24
24
  prerelease: false
25
- version_requirements: *20016960
25
+ version_requirements: *16334280
26
26
  - !ruby/object:Gem::Dependency
27
27
  name: rails
28
- requirement: &20015860 !ruby/object:Gem::Requirement
28
+ requirement: &16333760 !ruby/object:Gem::Requirement
29
29
  none: false
30
30
  requirements:
31
31
  - - ! '>='
@@ -33,10 +33,10 @@ dependencies:
33
33
  version: '3.0'
34
34
  type: :development
35
35
  prerelease: false
36
- version_requirements: *20015860
36
+ version_requirements: *16333760
37
37
  - !ruby/object:Gem::Dependency
38
38
  name: rails
39
- requirement: &20015360 !ruby/object:Gem::Requirement
39
+ requirement: &16333260 !ruby/object:Gem::Requirement
40
40
  none: false
41
41
  requirements:
42
42
  - - ! '>='
@@ -44,7 +44,7 @@ dependencies:
44
44
  version: '3.0'
45
45
  type: :runtime
46
46
  prerelease: false
47
- version_requirements: *20015360
47
+ version_requirements: *16333260
48
48
  description: Detects and masks banned words within a text
49
49
  email:
50
50
  - secara.razvan@yahoo.com
@@ -54,7 +54,9 @@ extra_rdoc_files: []
54
54
  files:
55
55
  - .gitignore
56
56
  - .rspec
57
+ - .travis.yml
57
58
  - Gemfile
59
+ - LICENSE
58
60
  - README.md
59
61
  - Rakefile
60
62
  - banned_words.gemspec
@@ -68,7 +70,7 @@ files:
68
70
  - spec/lib/storage_spec.rb
69
71
  - spec/spec_helper.rb
70
72
  - spec/yamls/banned_words.yml
71
- homepage: ''
73
+ homepage: https://github.com/razvan-sv/banned_words
72
74
  licenses: []
73
75
  post_install_message:
74
76
  rdoc_options: []