Commit 3ca0b15364f3e47e581240061db38484dadf6961
1 parent
9e77f7f1
Exists in
staging
and in
32 other branches
plugin-hotspot: dinamic hotspot for models callbacks
With this, every model that includes Noosfero::Plugin::HotSpot will
provide callbacks hotspots for plugins to answer. The current callbacks
included are {after,before}_{create,destroy,save}.
So if a plugin wants to do something on a comment after_save, it should
define a hotspot somewhat like this:
def comment_after_save_callback(comment)
<code-goes-here>
end
Obviously, the callback provides the object in context as parameter.
This will replace the problematic common practice of creating a
lib/ext/my_model.rb and injecting the callbacks inside the class which
bypass the enabled plugins logic.
Signed-off-by: Rodrigo Souto <rodrigo@colivre.coop.br>
Signed-off-by: Marcos Ronaldo <marcos.rpj2@gmail.com>
Showing
5 changed files
with
46 additions
and
1 deletions
Show diff stats
lib/noosfero/plugin.rb
| @@ -707,6 +707,10 @@ class Noosfero::Plugin | @@ -707,6 +707,10 @@ class Noosfero::Plugin | ||
| 707 | # returns = string with reason of expiration | 707 | # returns = string with reason of expiration |
| 708 | elsif method.to_s =~ /^content_expire_(#{content_actions.join('|')})$/ | 708 | elsif method.to_s =~ /^content_expire_(#{content_actions.join('|')})$/ |
| 709 | nil | 709 | nil |
| 710 | + # -> Generic hotspots for models callbacks | ||
| 711 | + # Example: article_after_create_callback | ||
| 712 | + elsif method.to_s =~ /^(.+)_#{Noosfero::Plugin::HotSpot::CALLBACK_HOTSPOTS.join('|')}_callback$/ | ||
| 713 | + nil | ||
| 710 | elsif context.respond_to?(method) | 714 | elsif context.respond_to?(method) |
| 711 | context.send(method) | 715 | context.send(method) |
| 712 | else | 716 | else |
lib/noosfero/plugin/hot_spot.rb
| @@ -6,6 +6,7 @@ | @@ -6,6 +6,7 @@ | ||
| 6 | # Environment will be used to determine which plugins are enabled and therefore | 6 | # Environment will be used to determine which plugins are enabled and therefore |
| 7 | # which plugins should be instantiated. | 7 | # which plugins should be instantiated. |
| 8 | module Noosfero::Plugin::HotSpot | 8 | module Noosfero::Plugin::HotSpot |
| 9 | + CALLBACK_HOTSPOTS =[:after_save, :after_destroy, :before_save, :before_destroy, :after_create, :before_create] | ||
| 9 | 10 | ||
| 10 | # Returns an instance of Noosfero::Plugin::Manager. | 11 | # Returns an instance of Noosfero::Plugin::Manager. |
| 11 | # | 12 | # |
| @@ -15,4 +16,26 @@ module Noosfero::Plugin::HotSpot | @@ -15,4 +16,26 @@ module Noosfero::Plugin::HotSpot | ||
| 15 | @plugins ||= Noosfero::Plugin::Manager.new(environment, self) | 16 | @plugins ||= Noosfero::Plugin::Manager.new(environment, self) |
| 16 | end | 17 | end |
| 17 | 18 | ||
| 19 | + def self.included(klass) | ||
| 20 | + klass.extend(ClassMethods) | ||
| 21 | + end | ||
| 22 | + | ||
| 23 | + module ClassMethods | ||
| 24 | + def self.extended base | ||
| 25 | + CALLBACK_HOTSPOTS.each do |callback| | ||
| 26 | + if base.respond_to?(callback) | ||
| 27 | + base.class_eval do | ||
| 28 | + self.send callback do |object| | ||
| 29 | + current=self.class | ||
| 30 | + while current.included_modules.include? Noosfero::Plugin::HotSpot do | ||
| 31 | + callback_name = "#{current.name.underscore}_#{callback}_callback" | ||
| 32 | + plugins.dispatch(callback_name, object) | ||
| 33 | + current=current.superclass | ||
| 34 | + end | ||
| 35 | + end | ||
| 36 | + end | ||
| 37 | + end | ||
| 38 | + end | ||
| 39 | + end | ||
| 40 | + end | ||
| 18 | end | 41 | end |
lib/noosfero/plugin/manager.rb
| @@ -75,7 +75,8 @@ class Noosfero::Plugin::Manager | @@ -75,7 +75,8 @@ class Noosfero::Plugin::Manager | ||
| 75 | end | 75 | end |
| 76 | 76 | ||
| 77 | def enabled_plugins | 77 | def enabled_plugins |
| 78 | - @enabled_plugins ||= (Noosfero::Plugin.all & environment.enabled_plugins).map do |plugin| | 78 | + environment_enabled_plugins = environment.present? ? environment.enabled_plugins : [] |
| 79 | + @enabled_plugins ||= (Noosfero::Plugin.all & environment_enabled_plugins).map do |plugin| | ||
| 79 | Noosfero::Plugin.load_plugin_identifier(plugin).new context | 80 | Noosfero::Plugin.load_plugin_identifier(plugin).new context |
| 80 | end | 81 | end |
| 81 | end | 82 | end |
test/unit/plugin_hot_spot_test.rb
| @@ -15,4 +15,19 @@ class PluginHotSpotTest < ActiveSupport::TestCase | @@ -15,4 +15,19 @@ class PluginHotSpotTest < ActiveSupport::TestCase | ||
| 15 | assert_same @client.plugins, @client.plugins | 15 | assert_same @client.plugins, @client.plugins |
| 16 | end | 16 | end |
| 17 | 17 | ||
| 18 | + Noosfero::Plugin::HotSpot::CALLBACK_HOTSPOTS.each do |callback| | ||
| 19 | + should "call #{callback} hotspot" do | ||
| 20 | + class CoolPlugin < Noosfero::Plugin; end | ||
| 21 | + | ||
| 22 | + Noosfero::Plugin.stubs(:all).returns([CoolPlugin.name]) | ||
| 23 | + Environment.default.enable_plugin(CoolPlugin) | ||
| 24 | + CoolPlugin.any_instance.expects("comment_#{callback}_callback".to_sym) | ||
| 25 | + | ||
| 26 | + person = fast_create(Person) | ||
| 27 | + article = fast_create(Article, :profile_id => person.id) | ||
| 28 | + comment = Comment.create!(:author => person, :title => 'test comment', :body => 'body!', :source => article) | ||
| 29 | + comment.destroy | ||
| 30 | + end | ||
| 31 | + end | ||
| 32 | + | ||
| 18 | end | 33 | end |
vendor/plugins/action_tracker/lib/action_tracker_model.rb
| @@ -7,6 +7,8 @@ module ActionTracker | @@ -7,6 +7,8 @@ module ActionTracker | ||
| 7 | belongs_to :user, :polymorphic => true | 7 | belongs_to :user, :polymorphic => true |
| 8 | belongs_to :target, :polymorphic => true | 8 | belongs_to :target, :polymorphic => true |
| 9 | 9 | ||
| 10 | + alias :profile :user | ||
| 11 | + | ||
| 10 | serialize :params, Hash | 12 | serialize :params, Hash |
| 11 | 13 | ||
| 12 | before_validation :stringify_verb | 14 | before_validation :stringify_verb |