Merge character validators
authorTom Hughes <tom@compton.nu>
Mon, 5 Nov 2018 18:54:19 +0000 (18:54 +0000)
committerTom Hughes <tom@compton.nu>
Mon, 5 Nov 2018 18:54:19 +0000 (18:54 +0000)
26 files changed:
app/models/changeset_comment.rb
app/models/changeset_tag.rb
app/models/diary_comment.rb
app/models/diary_entry.rb
app/models/issue_comment.rb
app/models/message.rb
app/models/node_tag.rb
app/models/note_comment.rb
app/models/old_node_tag.rb
app/models/old_relation_tag.rb
app/models/old_way_tag.rb
app/models/redaction.rb
app/models/relation_tag.rb
app/models/report.rb
app/models/trace.rb
app/models/tracetag.rb
app/models/user.rb
app/models/user_block.rb
app/models/user_preference.rb
app/models/way_tag.rb
app/validators/characters_validator.rb [new file with mode: 0644]
app/validators/invalid_chars_validator.rb [deleted file]
app/validators/invalid_url_chars_validator.rb [deleted file]
test/validators/characters_validator_test.rb [new file with mode: 0644]
test/validators/invalid_chars_validator_test.rb [deleted file]
test/validators/invalid_url_chars_validator_test.rb [deleted file]

index 0b84409..a0ad6f2 100644 (file)
@@ -28,7 +28,7 @@ class ChangesetComment < ActiveRecord::Base
   validates :changeset, :presence => true, :associated => true
   validates :author, :presence => true, :associated => true
   validates :visible, :inclusion => [true, false]
-  validates :body, :invalid_chars => true
+  validates :body, :characters => true
 
   # Return the comment text
   def body
index 7cfea1e..942fafb 100644 (file)
@@ -21,6 +21,6 @@ class ChangesetTag < ActiveRecord::Base
   belongs_to :changeset
 
   validates :changeset, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => :changeset_id }
 end
index 475872b..ade7a64 100644 (file)
@@ -28,7 +28,7 @@ class DiaryComment < ActiveRecord::Base
 
   scope :visible, -> { where(:visible => true) }
 
-  validates :body, :presence => true, :invalid_chars => true
+  validates :body, :presence => true, :characters => true
   validates :diary_entry, :user, :associated => true
 
   after_save :spam_check
index c49c2d4..d612419 100644 (file)
@@ -37,8 +37,8 @@ class DiaryEntry < ActiveRecord::Base
 
   scope :visible, -> { where(:visible => true) }
 
-  validates :title, :presence => true, :length => 1..255, :invalid_chars => true
-  validates :body, :presence => true, :invalid_chars => true
+  validates :title, :presence => true, :length => 1..255, :characters => true
+  validates :body, :presence => true, :characters => true
   validates :latitude, :allow_nil => true,
                        :numericality => { :greater_than_or_equal_to => -90,
                                           :less_than_or_equal_to => 90 }
index 2fe96f4..0841295 100644 (file)
@@ -24,7 +24,7 @@ class IssueComment < ActiveRecord::Base
   belongs_to :issue
   belongs_to :user
 
-  validates :body, :presence => true, :invalid_chars => true
+  validates :body, :presence => true, :characters => true
   validates :user, :presence => true
   validates :issue, :presence => true
 end
index 889137d..4e89cb2 100644 (file)
@@ -32,7 +32,7 @@ class Message < ActiveRecord::Base
 
   validates :title, :presence => true, :utf8 => true, :length => 1..255
   validates :body, :sent_on, :sender, :recipient, :presence => true
-  validates :title, :body, :invalid_chars => true
+  validates :title, :body, :characters => true
 
   def self.from_mail(mail, from, to)
     if mail.multipart?
index cdc1130..43915bc 100644 (file)
@@ -18,6 +18,6 @@ class NodeTag < ActiveRecord::Base
   belongs_to :node
 
   validates :node, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => :node_id }
 end
index 2347d43..f94032e 100644 (file)
@@ -33,7 +33,7 @@ class NoteComment < ActiveRecord::Base
   validates :visible, :inclusion => [true, false]
   validates :author, :associated => true
   validates :event, :inclusion => %w[opened closed reopened commented hidden]
-  validates :body, :length => { :maximum => 2000 }, :invalid_chars => true
+  validates :body, :length => { :maximum => 2000 }, :characters => true
 
   # Return the comment text
   def body
index 365841d..77b7875 100644 (file)
@@ -19,6 +19,6 @@ class OldNodeTag < ActiveRecord::Base
   belongs_to :old_node, :foreign_key => [:node_id, :version]
 
   validates :old_node, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => [:node_id, :version] }
 end
index 801ca7c..4a24794 100644 (file)
@@ -19,6 +19,6 @@ class OldRelationTag < ActiveRecord::Base
   belongs_to :old_relation, :foreign_key => [:relation_id, :version]
 
   validates :old_relation, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => [:relation_id, :version] }
 end
index 3662b1b..5832f6d 100644 (file)
@@ -19,6 +19,6 @@ class OldWayTag < ActiveRecord::Base
   belongs_to :old_way, :foreign_key => [:way_id, :version]
 
   validates :old_way, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => [:way_id, :version] }
 end
index e99460c..e6d7487 100644 (file)
@@ -31,8 +31,8 @@ class Redaction < ActiveRecord::Base
   has_many :old_ways
   has_many :old_relations
 
-  validates :title, :presence => true, :invalid_chars => true
-  validates :description, :presence => true, :invalid_chars => true
+  validates :title, :presence => true, :characters => true
+  validates :description, :presence => true, :characters => true
   validates :description_format, :inclusion => { :in => %w[text html markdown] }
 
   # this method overrides the AR default to provide the rich
index fc0ecdd..151615f 100644 (file)
@@ -18,6 +18,6 @@ class RelationTag < ActiveRecord::Base
   belongs_to :relation
 
   validates :relation, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => :relation_id }
 end
index ac00f1c..9bbf221 100644 (file)
@@ -27,7 +27,7 @@ class Report < ActiveRecord::Base
 
   validates :issue, :presence => true
   validates :user, :presence => true
-  validates :details, :presence => true, :invalid_chars => true
+  validates :details, :presence => true, :characters => true
   validates :category, :presence => true
 
   def self.categories_for(reportable)
index 942d160..1d0b11d 100644 (file)
@@ -38,8 +38,8 @@ class Trace < ActiveRecord::Base
   scope :tagged, ->(t) { joins(:tags).where(:gpx_file_tags => { :tag => t }) }
 
   validates :user, :presence => true, :associated => true
-  validates :name, :presence => true, :length => 1..255, :invalid_chars => true
-  validates :description, :presence => { :on => :create }, :length => 1..255, :invalid_chars => true
+  validates :name, :presence => true, :length => 1..255, :characters => true
+  validates :description, :presence => { :on => :create }, :length => 1..255, :characters => true
   validates :timestamp, :presence => true
   validates :visibility, :inclusion => %w[private public trackable identifiable]
 
index 0a59ba2..75fcb48 100644 (file)
@@ -22,5 +22,5 @@ class Tracetag < ActiveRecord::Base
   belongs_to :trace, :foreign_key => "gpx_id"
 
   validates :trace, :associated => true
-  validates :tag, :length => 1..255, :format => %r{\A[^/;.,?]*\z}, :invalid_chars => true
+  validates :tag, :length => 1..255, :format => %r{\A[^/;.,?]*\z}, :characters => true
 end
index a57c883..27ed7b6 100644 (file)
@@ -93,10 +93,9 @@ class User < ActiveRecord::Base
   validates :display_name, :if => proc { |u| u.display_name_changed? },
                            :uniqueness => { :case_sensitive => false }
   validates :display_name, :if => proc { |u| u.display_name_changed? },
-                           :invalid_chars => true,
-                           :invalid_url_chars => true,
+                           :characters => { :url_safe => true },
                            :whitespace => { :leading => false, :trailing => false }
-  validates :email, :presence => true, :confirmation => true, :invalid_chars => true
+  validates :email, :presence => true, :confirmation => true, :characters => true
   validates :email, :if => proc { |u| u.email_changed? },
                     :uniqueness => { :case_sensitive => false }
   validates :pass_crypt, :confirmation => true, :length => 8..255
index 5f313c6..02af385 100644 (file)
@@ -26,7 +26,7 @@
 
 class UserBlock < ActiveRecord::Base
   validate :moderator_permissions
-  validates :reason, :invalid_chars => true
+  validates :reason, :characters => true
 
   belongs_to :user, :class_name => "User", :foreign_key => :user_id
   belongs_to :creator, :class_name => "User", :foreign_key => :creator_id
index 639bbc0..3963bd0 100644 (file)
@@ -17,7 +17,7 @@ class UserPreference < ActiveRecord::Base
   belongs_to :user
 
   validates :user, :presence => true, :associated => true
-  validates :k, :v, :length => 1..255, :invalid_chars => true
+  validates :k, :v, :length => 1..255, :characters => true
 
   # Turn this Node in to an XML Node without the <osm> wrapper.
   def to_xml_node
index 7a5d9e7..c4df0ab 100644 (file)
@@ -18,6 +18,6 @@ class WayTag < ActiveRecord::Base
   belongs_to :way
 
   validates :way, :presence => true, :associated => true
-  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :invalid_chars => true
+  validates :k, :v, :allow_blank => true, :length => { :maximum => 255 }, :characters => true
   validates :k, :uniqueness => { :scope => :way_id }
 end
diff --git a/app/validators/characters_validator.rb b/app/validators/characters_validator.rb
new file mode 100644 (file)
index 0000000..cbcd03a
--- /dev/null
@@ -0,0 +1,12 @@
+class CharactersValidator < ActiveModel::EachValidator
+  INVALID_CHARS = "\x00-\x08\x0b-\x0c\x0e-\x1f\x7f\ufffe\uffff".freeze
+  INVALID_URL_CHARS = "/;.,?%#".freeze
+
+  def validate_each(record, attribute, value)
+    record.errors[attribute] << (options[:message] || I18n.t("validations.invalid_chars")) if value =~ /[#{INVALID_CHARS}]/
+
+    if options[:url_safe]
+      record.errors[attribute] << (options[:message] || I18n.t("validations.invalid_url_chars", :invalid_url_chars => INVALID_URL_CHARS)) if value =~ /[#{INVALID_URL_CHARS}]/
+    end
+  end
+end
diff --git a/app/validators/invalid_chars_validator.rb b/app/validators/invalid_chars_validator.rb
deleted file mode 100644 (file)
index f21f5a7..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-class InvalidCharsValidator < ActiveModel::EachValidator
-  INVALID_CHARS = "\x00-\x08\x0b-\x0c\x0e-\x1f\x7f\ufffe\uffff".freeze
-
-  def validate_each(record, attribute, value)
-    record.errors[attribute] << (options[:message] || I18n.t("validations.invalid_chars")) if value =~ /[#{INVALID_CHARS}]/
-  end
-end
diff --git a/app/validators/invalid_url_chars_validator.rb b/app/validators/invalid_url_chars_validator.rb
deleted file mode 100644 (file)
index a93f6c6..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-class InvalidUrlCharsValidator < ActiveModel::EachValidator
-  INVALID_URL_CHARS = "/;.,?%#".freeze
-
-  def validate_each(record, attribute, value)
-    record.errors[attribute] << (options[:message] || I18n.t("validations.invalid_url_chars", :invalid_url_chars => INVALID_URL_CHARS)) if value =~ /[#{INVALID_URL_CHARS}]/
-  end
-end
diff --git a/test/validators/characters_validator_test.rb b/test/validators/characters_validator_test.rb
new file mode 100644 (file)
index 0000000..e1409a5
--- /dev/null
@@ -0,0 +1,66 @@
+require "test_helper"
+
+class InvalidCharsValidatable
+  include ActiveModel::Validations
+  validates :chars, :characters => true
+  attr_accessor :chars
+end
+
+class InvalidUrlCharsValidatable
+  include ActiveModel::Validations
+  validates :chars, :characters => { :url_safe => true }
+  attr_accessor :chars
+end
+
+class CharactersValidatorTest < ActiveSupport::TestCase
+  include Rails::Dom::Testing::Assertions::SelectorAssertions
+
+  def test_with_valid_chars
+    c = InvalidCharsValidatable.new
+
+    valid = ["Name.", "'me", "he\"", "<hr>", "*ho", "\"help\"@",
+             "vergrößern", "ルシステムにも対応します", "輕觸搖晃的遊戲", "/;.,?%#"]
+
+    valid.each do |v|
+      c.chars = v
+      assert c.valid?, "'#{v}' should be valid"
+    end
+  end
+
+  def test_with_invalid_chars
+    c = InvalidCharsValidatable.new
+
+    invalid = ["\x7f<hr/>", "test@example.com\x0e-", "s/\x1ff", "aa/\ufffe",
+               "aa\x0b-,", "aa?\x08", "/;\uffff.,?", "\x00-も対応します/", "\x0c#ping",
+               "foo\x1fbar", "foo\x7fbar", "foo\ufffebar", "foo\uffffbar"]
+
+    invalid.each do |v|
+      c.chars = v
+      assert_not c.valid?, "'#{v}' should not be valid"
+    end
+  end
+
+  def test_with_valid_url_chars
+    c = InvalidUrlCharsValidatable.new
+
+    valid = ["Name", "'me", "he\"", "<hr>", "*ho", "\"help\"@",
+             "vergrößern", "ルシステムにも対応します", "輕觸搖晃的遊戲"]
+
+    valid.each do |v|
+      c.chars = v
+      assert c.valid?, "'#{v}' should be valid"
+    end
+  end
+
+  def test_with_invalid_url_chars
+    c = InvalidUrlCharsValidatable.new
+
+    invalid = ["Name.", "you;me", "he\"#", "<hr/>", "50%", "good?",
+               "vergrößern,deutsche", "ルシステムに;.も対応します", "輕觸搖/晃的遊戲", "/;.,?%#"]
+
+    invalid.each do |v|
+      c.chars = v
+      assert_not c.valid?, "'#{v}' should not be valid"
+    end
+  end
+end
diff --git a/test/validators/invalid_chars_validator_test.rb b/test/validators/invalid_chars_validator_test.rb
deleted file mode 100644 (file)
index 1e46269..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-require "test_helper"
-
-class InvalidCharsValidatable
-  include ActiveModel::Validations
-  validates :chars, :invalid_chars => true
-  attr_accessor :chars
-end
-
-class InvalidCharsValidatorTest < ActiveSupport::TestCase
-  include Rails::Dom::Testing::Assertions::SelectorAssertions
-
-  def test_with_valid_chars
-    c = InvalidCharsValidatable.new
-
-    valid = ["Name.", "'me", "he\"", "<hr>", "*ho", "\"help\"@",
-             "vergrößern", "ルシステムにも対応します", "輕觸搖晃的遊戲", "/;.,?%#"]
-
-    valid.each do |v|
-      c.chars = v
-      assert c.valid?, "'#{v}' should be valid"
-    end
-  end
-
-  def test_with_invalid_chars
-    c = InvalidCharsValidatable.new
-
-    invalid = ["\x7f<hr/>", "test@example.com\x0e-", "s/\x1ff", "aa/\ufffe",
-               "aa\x0b-,", "aa?\x08", "/;\uffff.,?", "\x00-も対応します/", "\x0c#ping",
-               "foo\x1fbar", "foo\x7fbar", "foo\ufffebar", "foo\uffffbar"]
-
-    invalid.each do |v|
-      c.chars = v
-      assert_not c.valid?, "'#{v}' should not be valid"
-    end
-  end
-end
diff --git a/test/validators/invalid_url_chars_validator_test.rb b/test/validators/invalid_url_chars_validator_test.rb
deleted file mode 100644 (file)
index ac35dcd..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-require "test_helper"
-
-class InvalidUrlCharsValidatable
-  include ActiveModel::Validations
-  validates :chars, :invalid_url_chars => true
-  attr_accessor :chars
-end
-
-class InvalidUrlCharsValidatorTest < ActiveSupport::TestCase
-  include Rails::Dom::Testing::Assertions::SelectorAssertions
-
-  def test_with_valid_url_chars
-    c = InvalidUrlCharsValidatable.new
-
-    valid = ["\x7f<hr>", "test@examplecom\x0e-", "s\x1ff", "aa\ufffe",
-             "aa\x0b-", "aa\x08", "\uffff::", "\x00-も対応します", "\x0c*ping",
-             "foo\x1fbar", "foo\x7fbar", "foo\ufffebar", "foo\uffffbar"]
-
-    valid.each do |v|
-      c.chars = v
-      assert c.valid?, "'#{v}' should be valid"
-    end
-  end
-
-  def test_with_invalid_url_chars
-    c = InvalidUrlCharsValidatable.new
-
-    invalid = ["Name.", "you;me", "he\"#", "<hr/>", "50%", "good?",
-               "vergrößern,deutsche", "ルシステムに;.も対応します", "輕觸搖/晃的遊戲", "/;.,?%#"]
-
-    invalid.each do |v|
-      c.chars = v
-      assert_not c.valid?, "'#{v}' should not be valid"
-    end
-  end
-end