Add PoC for resource serializers
This commit is contained in:
parent
2023511753
commit
acfe394018
8 changed files with 140 additions and 0 deletions
24
app/serializers/base_serializer.rb
Normal file
24
app/serializers/base_serializer.rb
Normal file
|
@ -0,0 +1,24 @@
|
|||
class BaseSerializer
|
||||
def initialize(request = {})
|
||||
@request = EntityRequest.new(request)
|
||||
@opts = { request: @request }
|
||||
end
|
||||
|
||||
def set(opts)
|
||||
@request.merge!(opts)
|
||||
self
|
||||
end
|
||||
|
||||
def represent(resource, opts = {})
|
||||
self.class.entity_class
|
||||
.represent(resource, @opts.reverse_merge(opts))
|
||||
end
|
||||
|
||||
def self.entity(entity_class)
|
||||
@entity_class ||= entity_class
|
||||
end
|
||||
|
||||
def self.entity_class
|
||||
@entity_class
|
||||
end
|
||||
end
|
16
app/serializers/entity_request.rb
Normal file
16
app/serializers/entity_request.rb
Normal file
|
@ -0,0 +1,16 @@
|
|||
class EntityRequest
|
||||
# We use EntityRequest object to collect parameters and variables
|
||||
# from the controller. Because options that are being passed to the entity
|
||||
# do appear in each entity object in the chain, we need a way to pass data
|
||||
# that is present in the controller (see #20045).
|
||||
#
|
||||
def initialize(parameters)
|
||||
merge!(parameters)
|
||||
end
|
||||
|
||||
def merge!(parameters)
|
||||
parameters.each do |key, value|
|
||||
define_singleton_method(key) { value }
|
||||
end
|
||||
end
|
||||
end
|
17
app/serializers/environment_entity.rb
Normal file
17
app/serializers/environment_entity.rb
Normal file
|
@ -0,0 +1,17 @@
|
|||
class EnvironmentEntity < Grape::Entity
|
||||
include RequestAwareEntity
|
||||
include Gitlab::Routing.url_helpers
|
||||
|
||||
expose :id
|
||||
expose :name
|
||||
expose :project, with: ProjectEntity
|
||||
expose :last_deployment,
|
||||
as: :deployment,
|
||||
using: API::Entities::Deployment
|
||||
|
||||
expose :environment_path
|
||||
|
||||
def environment_path
|
||||
request.path
|
||||
end
|
||||
end
|
3
app/serializers/environment_serializer.rb
Normal file
3
app/serializers/environment_serializer.rb
Normal file
|
@ -0,0 +1,3 @@
|
|||
class EnvironmentSerializer < BaseSerializer
|
||||
entity EnvironmentEntity
|
||||
end
|
8
app/serializers/project_entity.rb
Normal file
8
app/serializers/project_entity.rb
Normal file
|
@ -0,0 +1,8 @@
|
|||
class ProjectEntity < Grape::Entity
|
||||
expose :id
|
||||
expose :name
|
||||
|
||||
expose :test do |project|
|
||||
'something'
|
||||
end
|
||||
end
|
11
app/serializers/request_aware_entity.rb
Normal file
11
app/serializers/request_aware_entity.rb
Normal file
|
@ -0,0 +1,11 @@
|
|||
module RequestAwareEntity
|
||||
# We use SerializableRequest class to collect parameters and variables
|
||||
# from the controller. Because options that are being passed to the entity
|
||||
# are appear in each entity in the chain, we need a way to access data
|
||||
# that is present in the controller (see #20045).
|
||||
#
|
||||
def request
|
||||
options[:request] ||
|
||||
raise(StandardError, 'Request not set!!')
|
||||
end
|
||||
end
|
26
spec/serializers/entity_request_spec.rb
Normal file
26
spec/serializers/entity_request_spec.rb
Normal file
|
@ -0,0 +1,26 @@
|
|||
require 'spec_helper'
|
||||
|
||||
describe EntityRequest do
|
||||
subject do
|
||||
described_class.new(user: 'user', project: 'some project')
|
||||
end
|
||||
|
||||
describe 'methods created' do
|
||||
it 'defines accessible attributes' do
|
||||
expect(subject.user).to eq 'user'
|
||||
expect(subject.project).to eq 'some project'
|
||||
end
|
||||
|
||||
it 'raises error when attribute is not defined' do
|
||||
expect { subject.some_method }.to raise_error NoMethodError
|
||||
end
|
||||
end
|
||||
|
||||
describe '#merge!' do
|
||||
before { subject.merge!(build: 'some build') }
|
||||
|
||||
it 'appends parameters' do
|
||||
expect(subject.build).to eq 'some build'
|
||||
end
|
||||
end
|
||||
end
|
35
spec/serializers/environment_serializer_spec.rb
Normal file
35
spec/serializers/environment_serializer_spec.rb
Normal file
|
@ -0,0 +1,35 @@
|
|||
require 'spec_helper'
|
||||
|
||||
describe EnvironmentSerializer do
|
||||
let(:serializer) do
|
||||
described_class.new(path: 'some path').represent(resource)
|
||||
end
|
||||
|
||||
context 'when there is a single object provided' do
|
||||
let(:resource) { create(:environment) }
|
||||
|
||||
it 'shows json' do
|
||||
puts serializer.to_json
|
||||
end
|
||||
|
||||
it 'it generates payload for single object' do
|
||||
expect(parsed_json).to be_an_instance_of Hash
|
||||
end
|
||||
end
|
||||
|
||||
context 'when there is a collection of objects provided' do
|
||||
let(:resource) { create_list(:environment, 2) }
|
||||
|
||||
it 'shows json' do
|
||||
puts serializer.to_json
|
||||
end
|
||||
|
||||
it 'generates payload for collection' do
|
||||
expect(parsed_json).to be_an_instance_of Array
|
||||
end
|
||||
end
|
||||
|
||||
def parsed_json
|
||||
JSON.parse(serializer.to_json)
|
||||
end
|
||||
end
|
Loading…
Reference in a new issue