Class: SpeedyAF::Base

Inherits:
Object
  • Object
show all
Defined in:
lib/speedy_af/base.rb

Defined Under Namespace

Classes: NotAvailable

Constant Summary collapse

SOLR_ALL =
10_000_000

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(solr_document, instance_defaults = {}) ⇒ Base

Returns a new instance of Base.



157
158
159
160
161
162
163
164
165
# File 'lib/speedy_af/base.rb', line 157

def initialize(solr_document, instance_defaults = {})
  instance_defaults ||= {}
  @model = Base.model_for(solr_document)
  @attrs = self.class.defaults.merge(instance_defaults)
  solr_document.each_pair do |k, v|
    attr_name, value = parse_solr_field(k, v)
    @attrs[attr_name.to_sym] = value
  end
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(sym, *args) ⇒ Object



197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
# File 'lib/speedy_af/base.rb', line 197

def method_missing(sym, *args)
  return real_object.send(sym, *args) if real?

  if @attrs.key?(sym)
    # Lazy convert the solr document into a speedy_af proxy object
    @attrs[sym] = SpeedyAF::Base.for(@attrs[sym]) if @attrs[sym].is_a?(ActiveFedora::SolrHit)
    @attrs[sym] = @attrs[sym].map { |doc| SpeedyAF::Base.for(doc) } if @attrs[sym].is_a?(Array) && @attrs[sym].all? { |d| d.is_a?(ActiveFedora::SolrHit) }
    return @attrs[sym]
  end

  reflection = reflection_for(sym)
  unless reflection.nil?
    begin
      return load_from_reflection(reflection, sym.to_s =~ /_ids?$/)
    rescue NotAvailable => e
      ActiveFedora::Base.logger.warn(e.message)
    end
  end

  if model.instance_methods.include?(sym)
    ActiveFedora::Base.logger.warn("Reifying #{model} because #{sym} called from #{caller.first}")
    return real_object.send(sym, *args)
  end
  super
end

Instance Attribute Details

#attrsObject (readonly)

Returns the value of attribute attrs.



14
15
16
# File 'lib/speedy_af/base.rb', line 14

def attrs
  @attrs
end

#modelObject (readonly)

Returns the value of attribute model.



14
15
16
# File 'lib/speedy_af/base.rb', line 14

def model
  @model
end

Class Method Details

.config(model, &block) ⇒ Object



39
40
41
42
# File 'lib/speedy_af/base.rb', line 39

def config(model, &block)
  proxy_class = proxy_class_for(model) { Class.new(self) }
  proxy_class.class_eval(&block) if block_given?
end

.defaultsObject



17
18
19
# File 'lib/speedy_af/base.rb', line 17

def defaults
  @defaults ||= {}
end

.defaults=(value) ⇒ Object

Raises:

  • (ArgumentError)


21
22
23
24
# File 'lib/speedy_af/base.rb', line 21

def defaults=(value)
  raise ArgumentError unless value.respond_to?(:merge)
  @defaults = value
end

.find(id, opts = {}) ⇒ Object



44
45
46
# File 'lib/speedy_af/base.rb', line 44

def find(id, opts = {})
  where(%(id:"#{id}"), opts).first
end

.for(doc, opts = {}) ⇒ Object



53
54
55
56
# File 'lib/speedy_af/base.rb', line 53

def for(doc, opts = {})
  proxy = proxy_class_for(model_for(doc))
  proxy.new(doc, opts[:defaults])
end

.from(docs, opts = {}) ⇒ Object



58
59
60
61
62
63
64
65
66
67
68
69
70
# File 'lib/speedy_af/base.rb', line 58

def from(docs, opts = {})
  hash = docs.each_with_object({}) do |doc, h|
    h[doc['id']] = self.for(doc, opts)
  end

  if opts[:load_reflections]
    reflections_hash = gather_reflections(hash, opts)
    reflections_hash.each { |parent_id, reflections| hash[parent_id].attrs.merge!(reflections) }
  end

  return hash.values if opts[:order].nil?
  opts[:order].call.collect { |id| hash[id] }.to_a
end

.model_for(solr_document) ⇒ Object



72
73
74
# File 'lib/speedy_af/base.rb', line 72

def model_for(solr_document)
  solr_document[:has_model_ssim].first.safe_constantize
end

.proxy_class_for(model) ⇒ Object



26
27
28
29
30
31
32
33
34
35
36
37
# File 'lib/speedy_af/base.rb', line 26

def proxy_class_for(model)
  klass = "::SpeedyAF::Proxy::#{model.name}".safe_constantize
  if klass.nil?
    namespace = model.name.deconstantize
    name = model.name.demodulize
    klass_module = namespace.split(/::/).inject(::SpeedyAF::Proxy) do |mod, ns|
      mod.const_defined?(ns, false) ? mod.const_get(ns, false) : mod.const_set(ns, Module.new)
    end
    klass = klass_module.const_set(name, Class.new(self))
  end
  klass
end

.where(query, opts = {}) ⇒ Object



48
49
50
51
# File 'lib/speedy_af/base.rb', line 48

def where(query, opts = {})
  docs = ActiveFedora::SolrService.query(query, rows: SOLR_ALL)
  from(docs, opts)
end

Instance Method Details

#belongs_to_reflectionsObject

rubocop:enable Naming/PredicateName



233
234
235
# File 'lib/speedy_af/base.rb', line 233

def belongs_to_reflections
  SpeedyAF::Base.model_reflections[:belongs_to][model] ||= model.reflections.select { |_name, reflection| reflection.belongs_to? && reflection.respond_to?(:predicate_for_solr) }
end

#has_many_reflectionsObject

rubocop:disable Naming/PredicateName



228
229
230
# File 'lib/speedy_af/base.rb', line 228

def has_many_reflections
  SpeedyAF::Base.model_reflections[:has_many][model] ||= model.reflections.select { |_name, reflection| reflection.has_many? && reflection.respond_to?(:predicate_for_solr) }
end

#real?Boolean

Returns:

  • (Boolean)


175
176
177
# File 'lib/speedy_af/base.rb', line 175

def real?
  !@real_object.nil?
end

#real_objectObject



167
168
169
170
171
172
173
# File 'lib/speedy_af/base.rb', line 167

def real_object
  if @real_object.nil?
    @real_object = model.find(id)
    @attrs.clear
  end
  @real_object
end

#reloadObject



179
180
181
182
183
184
185
# File 'lib/speedy_af/base.rb', line 179

def reload
  dup = Base.find(id)
  @attrs = dup.attrs
  @model = dup.model
  @real_object = nil
  self
end

#respond_to_missing?(sym, _include_private = false) ⇒ Boolean

Returns:

  • (Boolean)


191
192
193
194
195
# File 'lib/speedy_af/base.rb', line 191

def respond_to_missing?(sym, _include_private = false)
  @attrs.key?(sym) ||
    model.respond_to?(:reflections) && model.reflections[sym].present? ||
    model.instance_methods.include?(sym)
end

#subresource_reflectionsObject



223
224
225
# File 'lib/speedy_af/base.rb', line 223

def subresource_reflections
  SpeedyAF::Base.model_reflections[:subresource][model] ||= model.reflections.select { |_name, reflection| reflection.is_a? ActiveFedora::Reflection::HasSubresourceReflection }
end

#to_query(key) ⇒ Object



187
188
189
# File 'lib/speedy_af/base.rb', line 187

def to_query(key)
  "#{key}=#{id}"
end