Module: Strelka::PluginLoader
- Included in:
- App, WebSocketServer
- Defined in:
- lib/strelka/plugins.rb
Overview
Module API for the plugin system. This mixin adds the ability to load and install plugins into the extended object.
Instance Attribute Summary collapse
-
#loaded_plugins ⇒ Object
The Hash of loaded plugin modules, keyed by their downcased and symbolified name (e.g., Strelka::App::Templating => :templating).
-
#plugin_path_prefix ⇒ Object
The prefix path for loading plugins.
-
#plugins_installed_from ⇒ Object
If plugins have already been installed, this will be the call frame they were first installed from.
Class Method Summary collapse
-
.extended(mod) ⇒ Object
Extension callback -- initialize some data structures in the extended object.
Instance Method Summary collapse
-
#application_stack ⇒ Object
Return the list of plugin modules that are in effect for the current app.
-
#dump_application_stack ⇒ Object
Output the application stack into the logfile.
-
#inherited(subclass) ⇒ Object
Extension callback -- add instance variables to extending objects.
-
#install_plugins ⇒ Object
Install the mixin part of the plugin, in the order determined by the plugin registry based on the run_outside and run_inside specifications of the plugins themselves.
-
#load_plugin(name) ⇒ Object
Load the plugin with the given
name. -
#new ⇒ Object
Install the mixin part of plugins immediately before the first instance is created.
-
#plugins(*names, &block) ⇒ Object
(also: #plugin)
Load the plugins with the given
namesand install them. -
#plugins_installed? ⇒ Boolean
Returns
trueif the plugins for the extended app class have already been installed. -
#register_plugin(mod, &block) ⇒ Object
Register the plugin
modin the receiving class.
Instance Attribute Details
#loaded_plugins ⇒ Object
The Hash of loaded plugin modules, keyed by their downcased and symbolified name (e.g., Strelka::App::Templating => :templating)
136 137 138 |
# File 'lib/strelka/plugins.rb', line 136 def loaded_plugins @loaded_plugins end |
#plugin_path_prefix ⇒ Object
The prefix path for loading plugins
147 148 149 |
# File 'lib/strelka/plugins.rb', line 147 def plugin_path_prefix @plugin_path_prefix end |
#plugins_installed_from ⇒ Object
If plugins have already been installed, this will be the call frame they were first installed from. This is used to warn about installing plugins twice.
142 143 144 |
# File 'lib/strelka/plugins.rb', line 142 def plugins_installed_from @plugins_installed_from end |
Class Method Details
.extended(mod) ⇒ Object
Extension callback -- initialize some data structures in the extended object.
124 125 126 127 128 129 130 |
# File 'lib/strelka/plugins.rb', line 124 def self::extended( mod ) super mod.extend( Loggability ) mod.log_to( :strelka ) mod.loaded_plugins = Strelka::PluginRegistry.new mod.plugin_path_prefix = mod.name.downcase.gsub( /::/, File::SEPARATOR ) end |
Instance Method Details
#application_stack ⇒ Object
Return the list of plugin modules that are in effect for the current app.
289 290 291 292 |
# File 'lib/strelka/plugins.rb', line 289 def application_stack self.log.debug "Ancestors are: %p" % [ self.class.ancestors ] return self.ancestors.select {|mod| mod.respond_to?(:plugin_name) } end |
#dump_application_stack ⇒ Object
Output the application stack into the logfile.
296 297 298 299 |
# File 'lib/strelka/plugins.rb', line 296 def dump_application_stack stack = self.application_stack.map( &:plugin_name ) self.log.info "Application stack: request -> %s" % [ stack.join(" -> ") ] end |
#inherited(subclass) ⇒ Object
Extension callback -- add instance variables to extending objects.
158 159 160 161 162 163 164 165 166 |
# File 'lib/strelka/plugins.rb', line 158 def inherited( subclass ) super @plugins ||= [] subclass.loaded_plugins = self.loaded_plugins subclass.plugin_path_prefix = self.plugin_path_prefix subclass.plugins_installed_from = nil subclass.instance_variable_set( :@plugins, @plugins.dup ) end |
#install_plugins ⇒ Object
Install the mixin part of the plugin, in the order determined by the plugin registry based on the run_outside and run_inside specifications of the plugins themselves.
259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 |
# File 'lib/strelka/plugins.rb', line 259 def install_plugins if self.plugins_installed? self.log.warn "Plugins were already installed for %p from %p" % [ self, self.plugins_installed_from ] self.log.info "I'll attempt to install any new ones, but plugin ordering" self.log.info "and other functionality might exhibit strange behavior." else self.log.info "Installing plugins for %p." % [ self ] end sorted_plugins = self.loaded_plugins.tsort.reverse sorted_plugins.each do |name| mod = self.loaded_plugins[ name ] unless @plugins.include?( name ) || @plugins.include?( mod ) self.log.debug " skipping %s" % [ name ] next end self.log.info " including %p in %p." % [ mod, self ] include( mod ) end self.plugins_installed_from = caller( 1 ).first end |
#load_plugin(name) ⇒ Object
Load the plugin with the given name
197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 |
# File 'lib/strelka/plugins.rb', line 197 def load_plugin( name ) # Just return Modules as-is return name if name.is_a?( Strelka::Plugin ) mod = self.loaded_plugins[ name.to_sym ] unless mod.is_a?( Module ) pluginpath = File.join( self.plugin_path_prefix, name.to_s ) require( pluginpath ) mod = self.loaded_plugins[ name.to_sym ] or raise "#{name} plugin didn't load correctly." end return mod end |
#new ⇒ Object
Install the mixin part of plugins immediately before the first instance is created.
250 251 252 253 |
# File 'lib/strelka/plugins.rb', line 250 def new( * ) self.install_plugins unless self.plugins_installed? super end |
#plugins(*names, &block) ⇒ Object Also known as: plugin
Load the plugins with the given names and install them.
170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 |
# File 'lib/strelka/plugins.rb', line 170 def plugins( *names, &block ) self.log.info "Adding plugins: %s" % [ names.flatten.map(&:to_s).join(', ') ] # Load the associated Plugin Module objects names.flatten.each {|name| self.load_plugin(name) } # Add the name/s to the list of mixins to apply on startup @plugins |= names # Install the declarative half of the plugin immediately names.each do |name| plugin = nil if name.is_a?( Module ) plugin = name else plugin = self.loaded_plugins[ name ] end self.log.debug " registering %p" % [ name ] self.register_plugin( plugin, &block ) end end |
#plugins_installed? ⇒ Boolean
Returns true if the plugins for the extended app class have already
been installed.
152 153 154 |
# File 'lib/strelka/plugins.rb', line 152 def plugins_installed? return !self.plugins_installed_from.nil? end |
#register_plugin(mod, &block) ⇒ Object
Register the plugin mod in the receiving class. This adds any
declaratives and class-level data necessary for configuring the
plugin.
217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 |
# File 'lib/strelka/plugins.rb', line 217 def register_plugin( mod, &block ) if mod.const_defined?( :ClassMethods ) cm_mod = mod.const_get(:ClassMethods) self.log.debug " adding class methods from %p" % [ cm_mod ] extend( cm_mod ) cm_mod.instance_variables.each do |ivar| next if instance_variable_defined?( ivar ) ival = cm_mod.instance_variable_get( ivar ) copy = Strelka::DataUtilities.deep_copy( ival ) self.log.debug " copying class instance variable %s (%p)" % [ ivar, copy ] instance_variable_set( ivar, copy ) self.log.debug " instance variable %p set to %p in %p" % [ ivar, self.instance_variable_get(ivar), self ] end end if block if mod.respond_to?( :configure_block ) mod.configure_block( self, &block ) else self.log.warn "Blocked passed to %p, which doesn't support block config." % [ mod ] end end end |