Skip to content

Commit

Permalink
feature: add common extractor
Browse files Browse the repository at this point in the history
PC4-17243
  • Loading branch information
vadshalamov committed Jun 1, 2016
1 parent b261c86 commit dd17b6b
Show file tree
Hide file tree
Showing 2 changed files with 88 additions and 0 deletions.
42 changes: 42 additions & 0 deletions lib/treasury/fields/extractor.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
module Treasury
module Fields
# Модуль добавляет классу метод extract_object, подходит для источников и полей денормализации.
#
# Example:
#
# class Field
# extend ::Treasury::Fields::Extractor
# extract_attribute_name :user
# end
#
# Field.extract_object(object: {user_id: 1})
# => 1
module Extractor
def extract_object(params)
object = params.fetch(:object)
object = object[attribute_name.to_sym] || object["#{attribute_name}_id".to_sym] if object.is_a?(Hash)

case object
when ::Numeric
object
when ::String
object.to_i
else
if object && object.respond_to?(:id)
object.id
else
raise ArgumentError,
"#{attribute_name.capitalize} instance or Numeric/String #{attribute_name}_id expected!, "\
"#{params.inspect}"
end
end
end

def extract_attribute_name(name)
class_attribute :attribute_name, instance_writer: false

self.attribute_name = name
end
end
end
end
46 changes: 46 additions & 0 deletions spec/lib/treasury/fields/extractor_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
require 'spec_helper'

RSpec.describe Treasury::Fields::Extractor do
let(:class_with_extractor) do
Class.new do
extend Treasury::Fields::Extractor

extract_attribute_name :user
end
end

describe '.extract_object' do
context 'when object key not present' do
it { expect { class_with_extractor.extract_object({}) }.to raise_error(KeyError) }
end

context 'when object_id not passed' do
it { expect { class_with_extractor.extract_object(object: {}) }.to raise_error(ArgumentError) }
end

context 'when object_id is nil' do
it { expect { class_with_extractor.extract_object(object: {user_id: nil}) }.to raise_error(ArgumentError) }
end

context 'when object is nil' do
it { expect { class_with_extractor.extract_object(object: nil) }.to raise_error(ArgumentError) }
end

context 'when extract another object' do
it { expect { class_with_extractor.extract_object(object: {another_object: 1}) }.to raise_error(ArgumentError) }
end

it 'return object id' do
user = double(:user, id: 1)

expect(class_with_extractor.extract_object(object: user)).to eq 1
end

it 'returns passed object_id' do
expect(class_with_extractor.extract_object(object: {user_id: 1})).to eq 1
expect(class_with_extractor.extract_object(object: {user_id: '1'})).to eq 1
expect(class_with_extractor.extract_object(object: {user: 1})).to eq 1
expect(class_with_extractor.extract_object(object: {user: '1'})).to eq 1
end
end
end

0 comments on commit dd17b6b

Please sign in to comment.