diff --git a/lib/diaspora_federation/validators/rules/guid.rb b/lib/diaspora_federation/validators/rules/guid.rb index 73077fa..821f0a5 100644 --- a/lib/diaspora_federation/validators/rules/guid.rb +++ b/lib/diaspora_federation/validators/rules/guid.rb @@ -7,6 +7,21 @@ module Validation # * Numbers: 0-9 # * Special chars: '-', '_', '@', '.' and ':' class Guid + # This rule can have a +nilable+ param + # @return [Hash] params + attr_reader :params + + # create a new rule for guid validation + # @param [Hash] params + # @option params [Boolean] :nilable guid allowed to be nil + def initialize(params={}) + if params.include?(:nilable) && !params[:nilable].is_a?(TrueClass) && !params[:nilable].is_a?(FalseClass) + raise ArgumentError, ":nilable needs to be a boolean" + end + + @params = params + end + # The error key for this rule # @return [Symbol] error key def error_key @@ -15,13 +30,7 @@ module Validation # Determines if value is a valid +GUID+ def valid_value?(value) - value.is_a?(String) && value.downcase =~ /\A[0-9a-z\-_@.:]{16,}\z/ - end - - # This rule has no params - # @return [Hash] params - def params - {} + params[:nilable] && value.nil? || value.is_a?(String) && value.downcase =~ /\A[0-9a-z\-_@.:]{16,}\z/ end end end diff --git a/spec/lib/diaspora_federation/validators/rules/guid_spec.rb b/spec/lib/diaspora_federation/validators/rules/guid_spec.rb index ea63bef..e2d48f8 100644 --- a/spec/lib/diaspora_federation/validators/rules/guid_spec.rb +++ b/spec/lib/diaspora_federation/validators/rules/guid_spec.rb @@ -1,9 +1,25 @@ describe Validation::Rule::Guid do - it "will not accept parameters" do + it "allows a nilable parameter" do validator = Validation::Validator.new({}) expect { - validator.rule(:guid, guid: {param: true}) - }.to raise_error ArgumentError + validator.rule(:guid, guid: {nilable: false}) + }.not_to raise_error + end + + it "doesn't require a nilable parameter" do + validator = Validation::Validator.new({}) + expect { + validator.rule(:guid, :guid) + }.not_to raise_error + end + + it "requires a boolean as parameter" do + validator = Validation::Validator.new({}) + [nil, "", 42, 5.5].each do |val| + expect { + validator.rule(:guid, guid: {nilable: val}) + }.to raise_error ArgumentError, ":nilable needs to be a boolean" + end end it "has an error key" do @@ -28,6 +44,14 @@ describe Validation::Rule::Guid do expect(validator.errors).to be_empty end + it "validates a nil guid if nilable is true" do + validator = Validation::Validator.new(OpenStruct.new(guid: nil)) + validator.rule(:guid, guid: {nilable: true}) + + expect(validator).to be_valid + expect(validator.errors).to be_empty + end + it "fails if the string is too short" do validator = Validation::Validator.new(OpenStruct.new(guid: "012345")) validator.rule(:guid, :guid) @@ -44,6 +68,14 @@ describe Validation::Rule::Guid do expect(validator.errors).to include(:guid) end + it "fails if the string contains invalid chars if nilable is true" do + validator = Validation::Validator.new(OpenStruct.new(guid: "ghijklmnopqrstuvwxyz++")) + validator.rule(:guid, guid: {nilable: true}) + + expect(validator).not_to be_valid + expect(validator.errors).to include(:guid) + end + it "fails if the string is empty" do [nil, ""].each do |val| validator = Validation::Validator.new(OpenStruct.new(guid: val))