Class: Longleaf::ServiceClassCache

Inherits:
Object
  • Object
show all
Defined in:
lib/longleaf/services/service_class_cache.rb

Overview

Cache for loading and retrieving preservation service classes

Constant Summary collapse

STD_PRESERVATION_SERVICE_PATH =
'longleaf/preservation_services/'

Instance Method Summary collapse

Constructor Details

#initialize(app_manager) ⇒ ServiceClassCache

Returns a new instance of ServiceClassCache.



8
9
10
11
12
13
14
# File 'lib/longleaf/services/service_class_cache.rb', line 8

def initialize(app_manager)
  @app_manager = app_manager
  # Cache storing per service definition instances of service classes
  @service_instance_cache = Hash.new
  # Cache storing per script path class of service
  @class_cache = Hash.new
end

Instance Method Details

#service_class(service_def) ⇒ Class

Load and return the PreservationService class assigned to the provided service definition, based on the work_script and work_class properties provided.

Parameters:

Returns:

  • (Class)

    class of work_script



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
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
# File 'lib/longleaf/services/service_class_cache.rb', line 38

def service_class(service_def)
  service_name = service_def.name
  work_script = service_def.work_script

  if work_script.include?('/')
    expanded_path = Pathname.new(work_script).expand_path.to_s
    if !from_permitted_path?(expanded_path)
      raise ConfigurationError.new("Unable to load work_script for service #{service_name}, #{work_script} is not in a known library path.")
    end

    last_slash_index = work_script.rindex('/')
    script_path = work_script[0..last_slash_index]
    script_name = work_script[(last_slash_index + 1)..-1]
  else
    script_path = STD_PRESERVATION_SERVICE_PATH
    script_name = work_script
  end

  # Strip off the extension
  script_name.sub!('.rb', '')

  require_path = File.join(script_path, script_name)
  # Return the cached Class if this path has been encountered before
  if @class_cache.key?(require_path)
    return @class_cache[require_path]
  end

  # Load the script
  begin
    require require_path
  rescue LoadError
    raise ConfigurationError.new("Failed to load work_script '#{script_name}' for service #{service_name}")
  end

  # Generate the class name, either configured or from file naming convention if possible
  if service_def.work_class
    class_name = service_def.work_class
  else
    class_name = script_name.split('_').map(&:capitalize).join
    # Assume the longleaf module for classes in the standard path
    class_name = 'Longleaf::' + class_name if script_path == STD_PRESERVATION_SERVICE_PATH
  end

  begin
    class_constant = constantize(class_name)
    # cache the class for this work_script and return it
    @class_cache[require_path] = class_constant
  rescue NameError
    raise ConfigurationError.new("Failed to load work_script '#{script_name}' for service #{service_name}, class name #{class_name} was not found.")
  end
end

#service_instance(service_def) ⇒ PreservationService

Returns an instance of the preversation service defined for the provided service definition, based on the work_script and work_class properties provided.

Parameters:

Returns:

  • (PreservationService)

    Instance of the preservation service class for the definition.



21
22
23
24
25
26
27
28
29
30
31
# File 'lib/longleaf/services/service_class_cache.rb', line 21

def service_instance(service_def)
  service_name = service_def.name
  # Return the cached instance of the service
  if @service_instance_cache.key?(service_name)
    return @service_instance_cache[service_name]
  end

  clazz = service_class(service_def)
  # Cache and return the class instance
  @service_instance_cache[service_name] = clazz.new(service_def, @app_manager)
end