Retrieve a slice module by name
@param <#> The slice module to check for. @return
# File lib/merb-slices/module.rb, line 10 10: def [](module_name) 11: Object.full_const_get(module_name.to_s) if exists?(module_name) 12: end
Activate a Slice module at runtime
Looks for previously registered slices; then searches :search_path for matches.
@param slice_module<#> Usually a string of version of the slice module name.
# File lib/merb-slices/module.rb, line 89 89: def activate(slice_module) 90: unless slice_file = self.files[slice_module.to_s] 91: module_name_underscored = slice_module.to_s.snake_case.escape_regexp 92: module_name_dasherized = module_name_underscored.tr('_', '-').escape_regexp 93: regexp = Regexp.new(/\/(#{module_name_underscored}|#{module_name_dasherized})\/lib\/(#{module_name_underscored}|#{module_name_dasherized})\.rb$/) 94: slice_file = slice_files_from_search_path.find { |path| path.match(regexp) } # from search path(s) 95: end 96: activate_by_file(slice_file) if slice_file 97: rescue => e 98: Merb.logger.error!("Failed to activate slice #{slice_module} (#{e.message})") 99: end
Register a Slice by its gem/lib init file path and activate it at runtime
Normally slices are loaded using BootLoaders on application startup. This method gives you the possibility to add slices at runtime, all without restarting your app. Together with # it allows you to enable/disable slices at any time. The router is reloaded to incorporate any changes. Disabled slices will be skipped when routes are regenerated.
@param slice_file
@example Merb::Slices.activate_by_file(‘/path/to/gems/slice-name/lib/slice-name.rb’)
# File lib/merb-slices/module.rb, line 113 113: def activate_by_file(slice_file) 114: Merb::Slices::Loader.load_classes(slice_file) 115: slice = register(slice_file, false) # just to get module by slice_file 116: slice.load_slice # load the slice 117: Merb::Slices::Loader.reload_router! 118: slice.init if slice.respond_to?(:init) 119: slice.activate if slice.respond_to?(:activate) && slice.routed? 120: slice 121: rescue 122: Merb::Slices::Loader.reload_router! 123: end
@return
The configuration loaded from Merb.root / "config/slices.yml" or, if the load fails, an empty hash.
# File lib/merb-slices/module.rb, line 192 192: def config 193: @config ||= begin 194: empty_hash = Hash.new { |h,k| h[k] = {} } 195: if File.exists?(Merb.root / "config" / "slices.yml") 196: require "yaml" 197: YAML.load(File.read(Merb.root / "config" / "slices.yml")) || empty_hash 198: else 199: empty_hash 200: end 201: end 202: end
Deactivate a Slice module at runtime
@param slice_module<#> The Slice module to unregister.
# File lib/merb-slices/module.rb, line 129 129: def deactivate(slice_module) 130: if slice = self[slice_module] 131: slice.deactivate if slice.respond_to?(:deactivate) && slice.routed? 132: unregister(slice) 133: end 134: end
Deactivate a Slice module at runtime by specifying its slice file
@param slice_file
# File lib/merb-slices/module.rb, line 139 139: def deactivate_by_file(slice_file) 140: if slice = self.slices.find { |s| s.file == slice_file } 141: deactivate(slice.name) 142: end 143: end
Iterate over all registered slices
By default iterates alphabetically over all registered modules. If Merb::Plugins.config[:merb_slices][:queue] is set, only the defined modules are loaded in the given order. This can be used to selectively load slices, and also maintain load-order for slices that depend on eachother.
@yield Iterate over known slices and pass in the slice module. @yieldparam
module
# File lib/merb-slices/module.rb, line 254 254: def each_slice(&block) 255: loadable_slices = Merb::Plugins.config[:merb_slices].key?(:queue) ? Merb::Plugins.config[:merb_slices][:queue] : slice_names 256: loadable_slices.each do |module_name| 257: if mod = self[module_name] 258: block.call(mod) 259: end 260: end 261: end
Check whether a Slice exists
@param <#> The slice module to check for.
# File lib/merb-slices/module.rb, line 223 223: def exists?(module_name) 224: const_name = module_name.to_s.camel_case 225: slice_names.include?(const_name) && Object.const_defined?(const_name) 226: end
Helper method to transform a slice filename to a module Symbol
# File lib/merb-slices/module.rb, line 15 15: def filename2module(slice_file) 16: File.basename(slice_file, '.rb').gsub('-', '_').camel_case.to_sym 17: end
A lookup for finding a Slice module’s slice file path
@return
# File lib/merb-slices/module.rb, line 240 240: def files 241: @files ||= {} 242: end
@return
A Hash mapping between slice identifiers and non-prefixed named routes.
# File lib/merb-slices/module.rb, line 185 185: def named_routes 186: @named_routes ||= {} 187: end
A lookup for finding a Slice module’s path
@return
# File lib/merb-slices/module.rb, line 232 232: def paths 233: @paths ||= {} 234: end
Register a Slice by its gem/lib path for loading at startup
This is referenced from gems/
@param slice_file
@return
@example Merb::Slices::register(FILE) @example Merb::Slices::register(‘/path/to/my-slice/lib/my-slice.rb’)
# File lib/merb-slices/module.rb, line 32 32: def register(slice_file, force = true) 33: # do what filename2module does, but with intermediate variables 34: identifier = File.basename(slice_file, '.rb') 35: underscored = identifier.gsub('-', '_') 36: module_name = underscored.camel_case 37: slice_path = File.expand_path(File.dirname(slice_file) + '/..') 38: # check if slice_path exists instead of just the module name - more flexible 39: if !self.paths.include?(slice_path) || force 40: Merb.logger.verbose!("Registered slice '#{module_name}' located at #{slice_path}") if force 41: self.files[module_name] = slice_file 42: self.paths[module_name] = slice_path 43: slice_mod = setup_module(module_name) 44: slice_mod.identifier = identifier 45: slice_mod.identifier_sym = underscored.to_sym 46: slice_mod.root = slice_path 47: slice_mod.file = slice_file 48: slice_mod.registered 49: slice_mod 50: else 51: Merb.logger.info!("Already registered slice '#{module_name}' located at #{slice_path}") 52: Object.full_const_get(module_name) 53: end 54: end
Look for any slices in Merb.root / ‘slices’ (the default) or if given, Merb::Plugins.config[:merb_slices][:search_path] (String/Array)
# File lib/merb-slices/module.rb, line 58 58: def register_slices_from_search_path! 59: slice_files_from_search_path.each do |slice_file| 60: absolute_path = File.expand_path(slice_file) 61: Merb.logger.info!("Found slice '#{File.basename(absolute_path, '.rb')}' in search path at #{absolute_path.relative_path_from(Merb.root)}") 62: Merb::Slices::Loader.load_classes(absolute_path) 63: end 64: end
Reload a Slice at runtime
@param slice_module<#> The Slice module to reload.
# File lib/merb-slices/module.rb, line 148 148: def reload(slice_module) 149: if slice = self[slice_module] 150: deactivate slice.name 151: activate_by_file slice.file 152: end 153: end
Reload a Slice at runtime by specifying its slice file
@param slice_file
# File lib/merb-slices/module.rb, line 158 158: def reload_by_file(slice_file) 159: if slice = self.slices.find { |s| s.file == slice_file } 160: reload(slice.name) 161: end 162: end
Slice file locations from all search paths; this default to host-app/slices.
Look for any slices in those default locations or if given, Merb::Plugins.config[:merb_slices][:search_path] (String/Array). Specify files, glob patterns or paths containing slices.
# File lib/merb-slices/module.rb, line 268 268: def slice_files_from_search_path 269: search_paths = Array(Merb::Plugins.config[:merb_slices][:search_path] || [Merb.root / "slices"]) 270: search_paths.inject([]) do |files, path| 271: # handle both Pathname and String 272: path = path.to_s 273: if File.file?(path) && File.extname(path) == ".rb" 274: files << path 275: elsif path.include?("*") 276: files += glob_search_path(path) 277: elsif File.directory?(path) 278: files += glob_search_path(path / "**/lib/*.rb") 279: end 280: files 281: end 282: end
All registered Slice module names
@return
# File lib/merb-slices/module.rb, line 216 216: def slice_names 217: self.paths.keys.sort 218: end
All registered Slice modules
@return
# File lib/merb-slices/module.rb, line 207 207: def slices 208: slice_names.map do |name| 209: Object.full_const_get(name) rescue nil 210: end.compact 211: end
Watch all specified search paths to dynamically load/unload slices at runtime
If a valid slice is found it’s automatically registered and activated; once a slice is removed (or renamed to not match the convention), it will be unregistered and deactivated. Runs in a Thread.
@example Merb::BootLoader.after_app_loads { Merb::Slices.start_dynamic_loader! }
@param interval
The interval in seconds of checking the search path(s) for changes.
# File lib/merb-slices/module.rb, line 174 174: def start_dynamic_loader!(interval = nil) 175: DynamicLoader.start(interval) 176: end
Stop watching search paths to dynamically load/unload slices at runtime
# File lib/merb-slices/module.rb, line 179 179: def stop_dynamic_loader! 180: DynamicLoader.stop 181: end
Unregister a Slice at runtime
This clears the slice module from ObjectSpace and reloads the router. Since the router doesn’t add routes for any disabled slices this will correctly reflect the app’s routing state.
@param slice_module<#> The Slice module to unregister.
# File lib/merb-slices/module.rb, line 73 73: def unregister(slice_module) 74: if (slice = self[slice_module]) && self.paths.delete(module_name = slice.name) 75: slice.loadable_files.each { |file| Merb::Slices::Loader.remove_classes_in_file file } 76: Object.send(:remove_const, module_name) 77: unless Object.const_defined?(module_name) 78: Merb.logger.info!("Unregistered slice #{module_name}") 79: Merb::Slices::Loader.reload_router! 80: end 81: end 82: end
Glob slice files
@param glob_pattern
# File lib/merb-slices/module.rb, line 302 302: def glob_search_path(glob_pattern) 303: # handle both Pathname and String 304: glob_pattern = glob_pattern.to_s 305: Dir[glob_pattern].inject([]) do |files, libfile| 306: basename = File.basename(libfile, '.rb') 307: files << libfile if File.basename(File.dirname(File.dirname(libfile))) == basename 308: files 309: end 310: end
Prepare a module to be a proper Slice module
@param module_name<#> The name of the module to prepare
@return
# File lib/merb-slices/module.rb, line 291 291: def setup_module(module_name) 292: Object.make_module(module_name) 293: slice_mod = Object.full_const_get(module_name) 294: slice_mod.extend(ModuleMixin) 295: slice_mod 296: end
Disabled; run with --debug to generate this.
Generated with the Darkfish Rdoc Generator 1.1.6.