<commit_before>module SmartRspec
  module Support
    module Assertions
      private_class_method

      def validates_email_of(attr, validation)
        it 'has an invalid format' do
          %w(foobar foobar@ @foobar foo@bar).each do |e|
            assert_validation(attr, e)
          end
        end
      end

      def validates_exclusion_of(attr, validation)
        it 'has a reserved value' do
          assert_validation(attr, validation[:in].sample)
        end
      end

      def validates_format_of(attr, validation)
        it 'does not match the required pattern' do
          value = validation[:sample]

          if validation.has_key?(:with) && (value.nil? || validation[:with] =~ value)
            begin
              value = SecureRandom.hex
            end while validation[:with] =~ value
          end

          assert_validation(attr, value)
        end
      end

      def validates_inclusion_of(attr, validation)
        it 'is out of the scope of possible values' do
          begin
            value = SecureRandom.hex
          end while validation[:in].include?(value)
          assert_validation(attr, value)
        end
      end

      def validates_length_of(attr, validation)
        validation.keys.each do |key|
          next unless %i(in is maximum minimum within).include?(key)
          txt, value = build_length_validation(key, validation[key])
          it txt do
            assert_validation(attr, 'x' * value)
          end
        end
      end

      def validates_presence_of(attr, validation)
        it 'is blank' do
          assert_validation(attr, nil)
        end
      end

      def validates_uniqueness_of(attr, validation)
        it 'is already in use' do
          assert_validation(attr, subject.send(attr), subject.dup)
        end
      end

      def assert_has_attributes(attrs, options)
        type_str = build_type_str(options) 
        type = options[:type] rescue nil
        default = options[:default] rescue nil

        attrs.each do |attr|
          it %Q(has an attribute named "#{attr}"#{type_str}) do
            expect(subject).to respond_to(attr)
            expect(subject.send(attr)).to eq(default) if default.present?
            assert_attr_type(attr, type, options) if type.present?
          end
        end
      end

      def assert_association(assoc_type, associations)
        associations.each do |association|
          it "#{assoc_type.to_s.gsub('_', ' ')} #{association}" do
            expect(subject).to respond_to(association)
            case assoc_type
            when :belongs_to
              %W(#{association}= #{association}_id #{association}_id=).each do |method|
                expect(subject).to respond_to(method)
              end<commit_msg>Add scope option to the uniqueness validation<commit_after>module SmartRspec
  module Support
    module Assertions
      private_class_method

      def validates_email_of(attr, validation)
        it 'has an invalid format' do
          %w(foobar foobar@ @foobar foo@bar).each do |e|
            assert_validation(attr, e)
          end
        end
      end

      def validates_exclusion_of(attr, validation)
        it 'has a reserved value' do
          assert_validation(attr, validation[:in].sample)
        end
      end

      def validates_format_of(attr, validation)
        it 'does not match the required pattern' do
          value = validation[:sample]

          if validation.has_key?(:with) && (value.nil? || validation[:with] =~ value)
            begin
              value = SecureRandom.hex
            end while validation[:with] =~ value
          end

          assert_validation(attr, value)
        end
      end

      def validates_inclusion_of(attr, validation)
        it 'is out of the scope of possible values' do
          begin
            value = SecureRandom.hex
          end while validation[:in].include?(value)
          assert_validation(attr, value)
        end
      end

      def validates_length_of(attr, validation)
        validation.keys.each do |key|
          next unless %i(in is maximum minimum within).include?(key)
          txt, value = build_length_validation(key, validation[key])
          it txt do
            assert_validation(attr, 'x' * value)
          end
        end
      end

      def validates_presence_of(attr, validation)
        it 'is blank' do
          assert_validation(attr, nil)
        end
      end

      def validates_uniqueness_of(attr, validation)
        it 'is already in use' do
          if validation.is_a?(Hash)
            mock, scope = validation[:mock] || subject.dup, validation[:scope]
            !scope.nil? && mock.send("#{scope}=", subject.send(scope))
          else
            mock = subject.dup
          end

          assert_validation(attr, subject.send(attr), mock)
        end
      end

      def assert_has_attributes(attrs, options)
        type_str = build_type_str(options) 
        type = options[:type] rescue nil
        default = options[:default] rescue nil

        attrs.each do |attr|
          it %Q(has an attribute named "#{attr}"#{type_str}) do
            expect(subject).to respond_to(attr)
            expect(subject.send(attr)).to eq(default) if default.present?
            assert_attr_type(attr, type, options) if type.present?
          end
        end
      end

      def assert_association(assoc_type, associations)
        associations.each do |association|
          it "#{assoc_type.to_s.gsub('_', ' ')} #{association}" do
            expect(subject).to respond_to(association)
            case assoc_type
            when :belongs_to
              %W(#{association}= #{association}_id #{association}_id=).each do |method|
                expect(subject).to respond_to(method)
              end
{'fraction_non_alphanumeric': 0.08675405312176612, 'fraction_numerical': 0.0, 'mean_word_length': 2.0281984334203655, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1197188', 'n_tokens_mistral': 1600, 'n_tokens_neox': 1569, 'n_words': 429}