Class: Scopify::Scope

Inherits:
Object
  • Object
show all
Defined in:
lib/scopify/scope.rb

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(base, options) ⇒ Scope

Returns a new instance of Scope.



3
4
5
6
# File 'lib/scopify/scope.rb', line 3

def initialize(base, options)
  @base = base
  @options = options
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(method_name, *args, &block) ⇒ Object



65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
# File 'lib/scopify/scope.rb', line 65

def method_missing(method_name, *args, &block)
  if @base.respond_to?(:raw_args_from_scope?) and @base.raw_args_from_scope?(method_name)
    # the method we call is a scope, continue chaining
    result = @base.send(method_name, *args, &block)
    result.is_a?(Scope) ? scoped(result) : result
  else
    # the method we call is a normal method
    # - scope by options from last method call
    # - flatten scope to options hash
    options = (args.last.is_a?(Hash) ? args.pop : {})
    options = scoped(options).to_hash
    args << options
    @base.send(method_name, *args, &block)
  end
end

Class Method Details

.build(base, options) ⇒ Object



12
13
14
15
16
# File 'lib/scopify/scope.rb', line 12

def self.build(base, options)
  # :limit => 1 --> :limit => [1]
  options = options.inject({}){|h,kv| h[kv[0]]||=[]; h[kv[0]] << kv[1]; h}
  new(base, options)
end

Instance Method Details

#scope_optionsObject



8
9
10
# File 'lib/scopify/scope.rb', line 8

def scope_options
  @options
end

#scoped(options) ⇒ Object



18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
# File 'lib/scopify/scope.rb', line 18

def scoped(options)
  merged = @options.dup
  if options.is_a?(Scope)
    # merge in raw options e.g. :limit => [1, 2]
    options.scope_options.each do |k,v|
      merged[k] ||= []
      v.each{|x| merged[k] << x }
    end
  else
    # merge in a normal hash e.g. :limit => 1
    merged = @options.dup
    options.each do |k,v|
      merged[k] ||= []
      merged[k] << v
    end
  end
  self.class.new(@base, merged)
end

#to_hashObject



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
# File 'lib/scopify/scope.rb', line 37

def to_hash
  result = if @base.respond_to?(:scope_to_hash)
    @base.scope_to_hash(@options)
  else
    @options.map do |key, values|
      result = case key
      when :limit, :offset then values.min
      when :conditions
        if values.all?{|x| x.is_a?(Hash)}
          values.inject({}){|hash, x| hash.merge(x)}
        else
          "(#{values * ") AND ("})"
        end
      when :order then values * ', '
      else values
      end
      [key, result]
    end
  end

  if result.is_a?(Hash)
    result
  else
    # convert array to hash
    result.inject({}){|h, kv| h[kv[0]] = kv[1]; h}
  end
end