diff --git a/.github/workflows/rspec.yml b/.github/workflows/rspec.yml index eb8c926..c640102 100644 --- a/.github/workflows/rspec.yml +++ b/.github/workflows/rspec.yml @@ -9,16 +9,32 @@ jobs: - uses: actions/checkout@v2 - uses: ruby/setup-ruby@v1 with: - ruby-version: 2.4 + ruby-version: 2.5 bundler-cache: true - name: Run tests run: bundle exec rspec - - name: Code Coverage - uses: paambaati/codeclimate-action@v2.7.5 - env: - CC_TEST_REPORTER_ID: ${{ secrets.CC_TEST_REPORTER_ID }} + - name: 'Upload Coverage Report' + uses: actions/upload-artifact@v4 with: - coverageLocations: | - ${{github.workspace}}/coverage/.resultset.json:simplecov + name: coverage-report + path: ./coverage + + coverage: + needs: [ test ] + name: coverage + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - name: Download Coverage Report + uses: actions/download-artifact@v4 + with: + name: coverage-report + path: ./coverage + - uses: paambaati/codeclimate-action@v9.0.0 + env: + # Set CC_TEST_REPORTER_ID as secret of your repo + CC_TEST_REPORTER_ID: ${{secrets.CC_TEST_REPORTER_ID}} + with: + debug: true diff --git a/class_kit.gemspec b/class_kit.gemspec index 4f78289..e060739 100644 --- a/class_kit.gemspec +++ b/class_kit.gemspec @@ -19,10 +19,10 @@ Gem::Specification.new do |spec| spec.require_paths = ['lib'] spec.add_development_dependency 'bundler', '~> 2' - spec.add_development_dependency 'pry' spec.add_development_dependency 'rake', '~> 10.0' spec.add_development_dependency 'rspec' - spec.add_development_dependency 'simplecov', '< 0.18.0' + spec.add_development_dependency 'simplecov', ' ~> 0.22.0' + spec.add_development_dependency 'simplecov_json_formatter' spec.add_dependency 'hash_kit' spec.add_dependency 'json' diff --git a/lib/class_kit/class_methods.rb b/lib/class_kit/class_methods.rb index 761277b..e96506f 100644 --- a/lib/class_kit/class_methods.rb +++ b/lib/class_kit/class_methods.rb @@ -56,15 +56,27 @@ def attr_accessor_type( raise ClassKit::Exceptions::InvalidAttributeValueError, "Attribute: #{name}, must not be nil." end - if !cka[:one_of].nil? && !value.nil? && ([Hash, String].any? { |t| value.is_a?(t) }) - type = cka[:one_of].detect { |t| value.is_a?(t) } - value = ClassKit::ValueHelper.instance.parse(type: type, value: value) - end + if !cka[:one_of].nil? && !value.nil? + parsed_value = + if value == true || value == false + value + elsif(/(true|t|yes|y|1)$/i === value.to_s.downcase) + true + elsif (/(false|f|no|n|0)$/i === value.to_s.downcase) + false + end - puts '-' * 50 - puts "#{cka}" - puts "Value: #{value}" - puts '-' * 50 + if parsed_value != nil + value = parsed_value + else + begin + type = cka[:one_of].detect {|t| value.is_a?(t) } + value = ClassKit::ValueHelper.instance.parse(type: type, value: value) + rescue => e + raise ClassKit::Exceptions::InvalidAttributeValueError, "Attribute: #{name}, must be of type: #{type}. Error: #{e}" + end + end + end if !cka[:type].nil? && !value.nil? && (cka[:type] == :bool || !value.is_a?(cka[:type])) begin diff --git a/spec/class_kit/class_methods_spec.rb b/spec/class_kit/class_methods_spec.rb index 4fcda1a..1535437 100644 --- a/spec/class_kit/class_methods_spec.rb +++ b/spec/class_kit/class_methods_spec.rb @@ -20,7 +20,7 @@ end context 'when a child entity is empty' do - it 'class_kit_attributes are avaiable' do + it 'class_kit_attributes are available' do expect{ empty_child_entity.base1 }.not_to raise_error end end @@ -35,6 +35,7 @@ expect(test_entity.int).to be 10 end end + context 'when an attribute is NOT allowed to be nil' do context 'when attempting to set the value to nil' do it 'should raise an invalid attribute value error' do @@ -42,6 +43,7 @@ end end end + context 'when an attribute is allowed to be nil' do it 'should not raise an error when setting to nil' do expect{ test_entity.int_nil = nil }.not_to raise_error @@ -57,6 +59,7 @@ expect(test_entity.int).to eq(20) end end + context 'from a string' do context 'that can be parsed' do it 'should parse and set the value' do @@ -64,6 +67,7 @@ expect(test_entity.int).to eq(20) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.int = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -81,6 +85,7 @@ expect(test_entity.float).to eq(0.05) end end + context 'from a string' do context 'that can be parsed' do it 'should parse and set the value' do @@ -88,6 +93,7 @@ expect(test_entity.float).to eq(0.05) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.float = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -106,6 +112,7 @@ expect(test_entity.date).to eq(date) end end + context 'from a string' do context 'that can be parsed' do let(:date) { Date.today } @@ -114,6 +121,7 @@ expect(test_entity.date).to eq(date) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.date = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -132,6 +140,7 @@ expect(test_entity.datetime).to eq(datetime) end end + context 'from a string' do context 'that can be parsed' do let(:datetime) { DateTime.now } @@ -140,6 +149,7 @@ expect(test_entity.datetime).to eq(datetime) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.datetime = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -158,6 +168,7 @@ expect(test_entity.time).to eq(time) end end + context 'from an integer' do let(:time) { Time.now } it 'should set the value' do @@ -165,6 +176,7 @@ expect(test_entity.time.to_i).to eq(time.to_i) end end + context 'from a float' do let(:time) { Time.now } it 'should set the value' do @@ -172,6 +184,7 @@ expect(test_entity.time.to_f).to eq(time.to_f) end end + context 'from a string' do context 'that can be parsed' do let(:time) { Time.now } @@ -180,6 +193,7 @@ expect(test_entity.time).to eq(time) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.time = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -207,22 +221,26 @@ expect{ test_entity.bool = true }.not_to raise_error expect(test_entity.bool).to eq(true) end + it 'should set the value to false' do expect{ test_entity.bool = false }.not_to raise_error expect(test_entity.bool).to eq(false) end end + context 'from a string' do context 'that can be parsed' do it 'should parse and set the value to true' do expect{ test_entity.bool = 'true' }.not_to raise_error expect(test_entity.bool).to eq(true) end + it 'should parse and set the value to false' do expect{ test_entity.bool = 'false' }.not_to raise_error expect(test_entity.bool).to eq(false) end end + context 'that can NOT be parsed' do it 'should raise an error' do expect{ test_entity.bool = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -240,12 +258,14 @@ end end end + context 'when allowed to be nil' do it 'should not raise an error when setting to nil' do expect{ test_entity.any_nil = nil }.not_to raise_error expect(test_entity.any_nil).to be nil end end + it 'should allow any value type to be specified' do expect{ test_entity.any = 'hello' }.not_to raise_error expect{ test_entity.any = 5 }.not_to raise_error @@ -260,6 +280,7 @@ expect{ test_entity.hash = { key1: 'value1' } }.not_to raise_error end end + context 'from a String' do it 'should raise an error' do expect{ test_entity.hash = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -275,6 +296,7 @@ expect{ test_entity.array = ['value1', 'value2'] }.not_to raise_error end end + context 'from a String' do it 'should raise an error' do expect{ test_entity.array = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) @@ -283,6 +305,29 @@ end end + context 'one_of attribute specified' do + context 'when setting the attribute value' do + context 'from an Array' do + it 'should set the value' do + expect{ test_entity.one_of = ['Happy Days'] }.not_to raise_error + end + end + + context 'from a Hash' do + it 'should set the value' do + expect{ test_entity.one_of = { 'some' => 'structured data' } }.not_to raise_error + end + end + + context 'from boolean' do + it 'should parse and set the value to false' do + expect{ test_entity.one_of = 'false' }.not_to raise_error + expect(test_entity.one_of).to eq(false) + end + end + end + end + context 'Class Type attribute specified' do context 'when setting the attribute value' do context 'from a TestAddress' do @@ -290,12 +335,14 @@ expect{ test_entity.address = TestAddress.new }.not_to raise_error end end + context 'from a String' do it 'should raise an error' do expect{ test_entity.address = 'ABC' }.to raise_error(ClassKit::Exceptions::InvalidAttributeValueError) end end end + context 'when auto_init is true' do context 'and the attribute has not been set' do it 'should return a new instance of the attribute type' do @@ -305,8 +352,5 @@ end end end - end end - - diff --git a/spec/class_kit/test_objects.rb b/spec/class_kit/test_objects.rb index 58fd5e2..67af4ae 100644 --- a/spec/class_kit/test_objects.rb +++ b/spec/class_kit/test_objects.rb @@ -60,6 +60,7 @@ class TestEntity attr_accessor_type :bool, type: :bool attr_accessor_type :hash, type: Hash attr_accessor_type :array, type: Array + attr_accessor_type :one_of, one_of: [Hash, Array, :bool] attr_accessor_type :address, type: TestAddress, allow_nil: false attr_accessor_type :address_auto, type: TestAddress, allow_nil: false, auto_init: true @@ -71,20 +72,24 @@ class TestEntity class InvalidClass attr_accessor :text end + class TestParent extend ClassKit attr_accessor_type :base1, type: String attr_accessor_type :base2 end + class TestChild < TestParent extend ClassKit attr_accessor_type :child1, type: String attr_accessor_type :child2 end + class TestChild2 < TestParent extend ClassKit attr_accessor_type :text, type: String end + class TestChild3 < TestParent extend ClassKit attr_accessor_type :text1, type: String diff --git a/spec/class_kit/value_helper_spec.rb b/spec/class_kit/value_helper_spec.rb index 82c5048..84f5a2a 100644 --- a/spec/class_kit/value_helper_spec.rb +++ b/spec/class_kit/value_helper_spec.rb @@ -232,6 +232,7 @@ end end end + context 'when type: is BigDecimal' do context 'and value is a valid' do context 'String' do @@ -247,27 +248,31 @@ expect(value).to eq BigDecimal('-0.005') end end + context 'Float' do it 'should parse the value' do value = subject.parse(type: BigDecimal, value: 0.005) expect(value).to be_a(BigDecimal) - expect(value).to eq BigDecimal.new('0.005') + expect(value).to eq BigDecimal('0.005') end end + context 'BigDecimal' do it 'should parse the value' do value = subject.parse(type: BigDecimal, value: 0.005.to_d) expect(value).to be_a(BigDecimal) - expect(value).to eq BigDecimal.new('0.005') + expect(value).to eq BigDecimal('0.005') end end end + context 'and value is NOT valid' do it 'should raise a invalid parse value error' do expect{ subject.parse(type: BigDecimal, value: 'ABC') }.to raise_error(ClassKit::Exceptions::InvalidParseValueError) end end end + context 'when type: is String' do context 'and value is a valid' do context 'String' do @@ -286,6 +291,7 @@ end end end + context 'when type: is Regexp' do context 'and value is a valid' do context 'String' do @@ -295,6 +301,7 @@ expect(value).to eq /[\w\s]+/ end end + context 'Regexp' do it 'should parse the value' do value = subject.parse(type: Regexp, value: /[\w\s]+/) @@ -303,12 +310,14 @@ end end end + context 'and value is NOT valid' do it 'should raise a invalid parse value error' do expect{ subject.parse(type: Regexp, value: TestEntity.new) }.to raise_error(ClassKit::Exceptions::InvalidParseValueError) end end end + context 'when type: is Hash' do context 'and value is a valid' do context 'Hash' do @@ -319,12 +328,14 @@ end end end + context 'and value is NOT valid' do it 'should raise a invalid parse value error' do expect{ subject.parse(type: Hash, value: 'ABC') }.to raise_error(ClassKit::Exceptions::InvalidParseValueError) end end end + context 'when type: is Array' do context 'and value is a valid' do context 'Hash' do @@ -335,12 +346,14 @@ end end end + context 'and value is NOT valid' do it 'should raise a invalid parse value error' do expect{ subject.parse(type: Array, value: 'ABC') }.to raise_error(ClassKit::Exceptions::InvalidParseValueError) end end end + context 'when type: is CustomType' do context 'and value is a valid CustomType' do it 'should parse the value' do diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 2d26408..dd03461 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -1,6 +1,10 @@ require 'simplecov' +require 'simplecov_json_formatter' + +SimpleCov.formatter = SimpleCov::Formatter::JSONFormatter + SimpleCov.start do - add_filter 'spec/' + add_filter 'spec/' end require 'pry'