1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64
|
# frozen_string_literal: true
require 'gh'
module GH
# Public: Exposes DSL for stacking wrappers.
#
# Examples
#
# api = GH::Stack.build do
# use GH::Cache, cache: Rails.cache
# use GH::Normalizer
# use GH::Remote, username: "admin", password: "admin"
# end
class Stack
attr_reader :options
# Public: Generates a new wrapper stack from the given block.
#
# options - Hash of options that will be passed to all layers upon initialization.
#
# Returns top most Wrapper instance.
def self.build(options = {}, &block)
new(&block).build(options)
end
# Public: Generates a new Stack instance.
#
# options - Hash of options that will be passed to all layers upon initialization.
#
# Can be used for easly stacking layers.
def initialize(_options = {}, &block)
@options = {}
@stack = []
instance_eval(&block) if block
end
# Public: Adds a new layer to the stack.
#
# Layer will be wrapped by layers already on the stack.
def use(klass, options = {})
@stack << [klass, options]
self
end
# Public: Generates wrapper instances for stack configuration.
#
# options - Hash of options that will be passed to all layers upon initialization.
#
# Returns top most Wrapper instance.
def build(options = {})
@stack.reverse.inject(nil) do |backend, (klass, opts)|
klass.new backend, @options.merge(opts).merge(options)
end
end
# Public: ...
def replace(old_class, new_class)
@stack.map! { |klass, options| [old_class == klass ? new_class : klass, options] }
end
alias new build
end
end
|