muck-activities 0.1.11 → 0.1.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -30,6 +30,12 @@ Adding an item to the activity feed requires 'acts_as_activity_source' which the
30
30
  Example:
31
31
  add_activity(user.feed_to, user, comment, 'comment')
32
32
 
33
+ Create an activity model that 'acts_as_muck_activity':
34
+
35
+ class Activity < ActiveRecord::Base
36
+ acts_as_muck_activity
37
+ end
38
+
33
39
  === Authorization
34
40
  By default 'has_activities' will add a simple 'can_view?' method:
35
41
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.11
1
+ 0.1.12
@@ -24,7 +24,6 @@ class Muck::ActivitiesController < ApplicationController
24
24
  @activity.source = @parent
25
25
  @activity.content.gsub!(@parent.display_name, '')
26
26
  @parent.save!
27
-
28
27
  @activity_html = get_activity_html(@activity)
29
28
  if @activity.template == 'status_update'
30
29
  @status_html = get_status_html(@parent)
@@ -77,6 +76,11 @@ class Muck::ActivitiesController < ApplicationController
77
76
  page_alert(page, message)
78
77
  end
79
78
  end
79
+ format.json do
80
+ render :json => { :success => false,
81
+ :exception => ex,
82
+ :message => t("muck.activities.create_error", :error => errors) }
83
+ end
80
84
  end
81
85
 
82
86
  end
@@ -96,10 +100,14 @@ class Muck::ActivitiesController < ApplicationController
96
100
  page << "jQuery('##{@activity.dom_id}').fadeOut();"
97
101
  page.replace_html 'current-status', @new_status if @new_status
98
102
  end
103
+ else
104
+ render(:update) do |page|
105
+ page << "jQuery('##{@activity.dom_id}').fadeOut();"
106
+ end
99
107
  end
100
108
  end
101
109
  format.json do
102
- @new_status = get_status_html(@activities_object)
110
+ @new_status = get_status_html(@activities_object) if @activity.is_status_update
103
111
  render :json => { :success => true,
104
112
  :is_status_update => @activity.is_status_update,
105
113
  :html => @new_status,
@@ -123,14 +131,25 @@ class Muck::ActivitiesController < ApplicationController
123
131
  protected
124
132
 
125
133
  def get_status_html(activity)
126
- @template.template_format = :html
127
- render_to_string(:partial => 'activities/current_status', :locals => {:activities_object => activity})
134
+ render_as_html do
135
+ render_to_string(:partial => 'activities/current_status', :locals => {:activities_object => activity})
136
+ end
128
137
  end
129
138
 
130
139
  def get_activity_html(activity)
131
- render_to_string(:partial => "activity_templates/#{activity.template}", :locals => { :activity => activity })
140
+ render_as_html do
141
+ render_to_string(:partial => "activity_templates/#{activity.template}", :locals => { :activity => activity })
142
+ end
132
143
  end
133
144
 
145
+ def render_as_html
146
+ last_template_format = @template.template_format
147
+ @template.template_format = :html
148
+ result = yield
149
+ @template.template_format = last_template_format
150
+ result
151
+ end
152
+
134
153
  def find_parent
135
154
  @klass = params[:parent_type].to_s.capitalize.constantize
136
155
  @parent = @klass.find(params[:parent_id])
@@ -18,19 +18,29 @@ module MuckActivityHelper
18
18
  end
19
19
  end
20
20
 
21
+ # Renders an activity with only activities created by activities_object
22
+ def limited_activity_feed_for(activities_object)
23
+ activities = activities_object.activities.created_by(activities_object).find(:all, :include => ['comments']).paginate(:page => @page, :per_page => @per_page)
24
+ render :partial => 'activities/activity_feed', :locals => { :activities_object => activities_object, :activities => activities }
25
+ end
26
+
27
+ # Renders a full activity feed for activities_object
21
28
  def activity_feed_for(activities_object)
22
29
  activities = get_activities(activities_object)
23
30
  render :partial => 'activities/activity_feed', :locals => { :activities_object => activities_object, :activities => activities }
24
31
  end
25
32
 
33
+ # Renders a status update form for activities_object
26
34
  def status_update(activities_object)
27
35
  render :partial => 'activities/status_update', :locals => { :activities_object => activities_object }
28
36
  end
29
37
 
38
+ # Renders the last status update made by activities_object
30
39
  def current_status(activities_object)
31
40
  render :partial => 'activities/current_status_wrapper', :locals => { :activities_object => activities_object }
32
41
  end
33
42
 
43
+ # Renders a delete button for an activity
34
44
  def delete_activity(activity, button_type = :button, button_text = t("muck.activities.clear"))
35
45
  render :partial => 'activities/delete', :locals => { :delete_object => activity,
36
46
  :button_type => button_type,
@@ -39,6 +49,7 @@ module MuckActivityHelper
39
49
  :delete_path => activity_path(activity, :format => 'js') }
40
50
  end
41
51
 
52
+ # Renders a delete button for a comment inside an activity feed
42
53
  def delete_comment(comment, button_type = :button, button_text = t("muck.activities.delete"))
43
54
  render :partial => 'activities/delete', :locals => { :delete_object => comment,
44
55
  :button_type => button_type,
@@ -47,6 +58,7 @@ module MuckActivityHelper
47
58
  :delete_path => comment_path(comment, :format => 'js') }
48
59
  end
49
60
 
61
+ # Renders an activity feed filter. Filter items come from the name of the templates used to render the activities.
50
62
  def activity_filter(activities_object)
51
63
  activity_types = activities_object.activities.all(:select => "DISTINCT activities.template")
52
64
  render :partial => 'activities/template_filter', :locals => { :activity_types => activity_types }
@@ -0,0 +1,12 @@
1
+ <div class="activity <%= activity_css_class %> delete-container" id="<%= activity.dom_id %>">
2
+ <div class="actor-icon"><%= icon activity.source %></div>
3
+ <div class="activity-content">
4
+ <p><span class="actor"><%= link_to activity.source.display_name, activity.source %></span> <%= activity.content %></p>
5
+ <%= delete_activity(activity, :image) %>
6
+ <span class="activity-time"><%= t("muck.activities.time_ago", :time_in_words => time_ago_in_words(activity.created_at)) %></span>
7
+ <% if !activity.has_comments? -%>
8
+ <span><a id="make_comment_<%=activity.dom_id%>" class="make-comment" href="#"><%=t('muck.activities.make_comment')%></a></span>
9
+ <% end -%>
10
+ </div>
11
+ <%= activity_comments(activity) %>
12
+ </div>
@@ -1,12 +1 @@
1
- <div class="activity activity-status-update delete-container" id="<%= activity.dom_id %>">
2
- <div class="actor-icon"><%= icon activity.source %></div>
3
- <div class="activity-content">
4
- <p><span class="actor"><%= link_to activity.source.display_name, activity.source %></span> <%= activity.content %></p>
5
- <%= delete_activity(activity, :image) %>
6
- <span class="activity-time"><%= t("muck.activities.time_ago", :time_in_words => time_ago_in_words(activity.created_at)) %></span>
7
- <% if !activity.has_comments? -%>
8
- <span><a id="make_comment_<%=activity.dom_id%>" class="make-comment" href="#"><%=t('muck.activities.make_comment')%></a></span>
9
- <% end -%>
10
- </div>
11
- <%= activity_comments(activity) %>
12
- </div>
1
+ <%= render :partial => 'activity_templates/generic', :locals => { :activity => activity, :activity_css_class => 'activity-status-update' } %>
@@ -0,0 +1,76 @@
1
+ module ActiveRecord
2
+ module Acts #:nodoc:
3
+ module MuckActivity #:nodoc:
4
+ def self.included(base)
5
+ base.extend(ClassMethods)
6
+ end
7
+
8
+ module ClassMethods
9
+
10
+ def acts_as_muck_activity(options = {})
11
+
12
+ belongs_to :item, :polymorphic => true
13
+ belongs_to :source, :polymorphic => true
14
+ has_many :activity_feeds
15
+
16
+ acts_as_commentable
17
+
18
+ validates_presence_of :source
19
+
20
+ named_scope :since, lambda { |time| {:conditions => ["activities.created_at > ?", time] } }
21
+ named_scope :before, lambda {|time| {:conditions => ["activities.created_at < ?", time] } }
22
+ named_scope :newest, :order => "activities.created_at DESC"
23
+ named_scope :after, lambda {|id| {:conditions => ["activities.id > ?", id] } }
24
+ named_scope :only_public, :conditions => ["activities.is_public = true"]
25
+ named_scope :filter_by_template, lambda { |template| { :conditions => ["activities.template = ?", template] } unless template.blank? }
26
+ named_scope :created_by, lambda {|activity_object| {:conditions => ["activities.source_id = ? AND activities.source_type = ?", activity_object.id, activity_object.class.to_s] } }
27
+ named_scope :status_updates, :conditions => ["activities.is_status_update = ?", true]
28
+ class_eval <<-EOV
29
+ attr_protected :created_at, :updated_at
30
+ EOV
31
+
32
+ include ActiveRecord::Acts::MuckActivity::InstanceMethods
33
+ extend ActiveRecord::Acts::MuckActivity::SingletonMethods
34
+
35
+ end
36
+ end
37
+
38
+ # class methods
39
+ module SingletonMethods
40
+
41
+ end
42
+
43
+ # All the methods available to a record that has had <tt>acts_as_muck_activity</tt> specified.
44
+ module InstanceMethods
45
+
46
+ def validate
47
+ errors.add_to_base(I18n.t('muck.activities.template_or_item_required')) if template.blank? && item.blank?
48
+ end
49
+
50
+ # Provides a template that can be used to render a view of this activity.
51
+ # If 'template' is not specified when the object created then the item class
52
+ # name will be used to generated a template
53
+ def partial
54
+ template || item.class.name.underscore
55
+ end
56
+
57
+ def has_comments?
58
+ @has_comments ||= !self.comments.blank?
59
+ end
60
+
61
+ # Checks to see if the specified object can edit this activity.
62
+ # Most likely check_object will be a user
63
+ def can_edit?(check_object)
64
+ if check_object.is_a?(User)
65
+ return true if check(check_object, :source_id)
66
+ else
67
+ source == check_object
68
+ end
69
+ false
70
+ end
71
+
72
+ end
73
+
74
+ end
75
+ end
76
+ end
@@ -1,9 +1,10 @@
1
1
  require 'cgi'
2
2
  require 'muck_activities/initialize_routes'
3
- require 'muck_activities/muck_activity'
3
+ require 'muck_activities/muck_activity_sources'
4
4
 
5
+ ActiveRecord::Base.class_eval { include ActiveRecord::Acts::MuckActivity }
5
6
  ActionController::Base.send :helper, MuckActivityHelper
6
- ActiveRecord::Base.send(:include, MuckActivity)
7
- ActionController::Base.send(:include, MuckActivity)
7
+ ActiveRecord::Base.send(:include, MuckActivitySources)
8
+ ActionController::Base.send(:include, MuckActivitySources)
8
9
 
9
10
  I18n.load_path += Dir[ File.join(File.dirname(__FILE__), '..', 'locales', '*.{rb,yml}') ]
@@ -1,4 +1,4 @@
1
- module MuckActivity # :nodoc:
1
+ module MuckActivitySources # :nodoc:
2
2
 
3
3
  def self.included(base) # :nodoc:
4
4
  base.extend ActMethods
@@ -19,6 +19,7 @@ module MuckActivity # :nodoc:
19
19
 
20
20
  # +acts_as_activity_source+ gives the class it is called on a method called
21
21
  # +add_activity+ that can add activities into a feed.
22
+ # This can be applied to models or controllers
22
23
  def acts_as_activity_source
23
24
  unless included_modules.include? InstanceMethods
24
25
  include InstanceMethods
@@ -43,7 +44,11 @@ module MuckActivity # :nodoc:
43
44
  # to false the activity won't be added to the object's activity feed. An example usage would be
44
45
  # letting users configure which items they want to have in their activity feed.
45
46
  def add_activity(feed_to, source, item, template, title = '', content = '', check_method = nil)
46
- feed_to = [feed_to] unless feed_to.is_a?(Array)
47
+ if feed_to.is_a?(Array)
48
+ feed_to = feed_to & feed_to # eliminate duplicates from feed_to array
49
+ else
50
+ feed_to = [feed_to]
51
+ end
47
52
  activity = Activity.create(:item => item, :source => source, :template => template, :title => title, :content => content)
48
53
  feed_to.each do |ft|
49
54
  if check_method
@@ -52,12 +57,13 @@ module MuckActivity # :nodoc:
52
57
  ft.activities << activity
53
58
  end
54
59
  end
60
+ activity
55
61
  end
56
62
 
57
63
  # +status+ returns the first activity item from the user's activity feed that is a status update.
58
64
  # Used for displaying the last status update the user made
59
65
  def status
60
- self.activities.find(:first, :conditions => ['is_status_update = true'], :order => 'created_at DESC')
66
+ self.activities.status_updates.newest.first
61
67
  end
62
68
 
63
69
  def can_view?(check_object)
@@ -1,12 +1,13 @@
1
1
  en:
2
2
  muck:
3
3
  activities:
4
- item_removed: 'Item successfully removed from the recent activities list.'
5
- item_could_not_be_removed: 'Item could not be removed from the recent activities list.'
6
- item_created: 'Added activity'
4
+ item_removed: "Item successfully removed from the recent activities list."
5
+ item_could_not_be_removed: "Item could not be removed from the recent activities list."
6
+ item_created: "Added activity"
7
+ create_error: "There was a problem adding the requested activity: {{error}}"
7
8
  permission_denied: "Sorry, you can't do that."
8
9
  status_update_prompt: "What are you doing right now?"
9
- activity_feed_title: 'Recent Activity'
10
+ activity_feed_title: "Recent Activity"
10
11
  updating_status_message: "Updating your status. Please wait."
11
12
  status_indicator: is
12
13
  invite_friends: Invite Friends
@@ -19,8 +20,8 @@ en:
19
20
  update_status_message: "update your status!"
20
21
  time_ago: "{{time_in_words}} ago"
21
22
  template_or_item_required: "An activity requires a template or an item to display correctly"
22
- paging_newer: '&laquo; Newer'
23
- paging_older: 'Older &raquo;'
23
+ paging_newer: "&laquo; Newer"
24
+ paging_older: "Older &raquo;"
24
25
  all_activities: All Activities
25
26
  make_comment: Comment
26
27
  write_prompt: "Write a comment..."
@@ -2,11 +2,11 @@
2
2
 
3
3
  Gem::Specification.new do |s|
4
4
  s.name = %q{muck-activities}
5
- s.version = "0.1.11"
5
+ s.version = "0.1.12"
6
6
 
7
7
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
8
8
  s.authors = ["Justin Ball"]
9
- s.date = %q{2009-06-19}
9
+ s.date = %q{2009-06-24}
10
10
  s.description = %q{Activity engine for the muck system.}
11
11
  s.email = %q{justinball@gmail.com}
12
12
  s.extra_rdoc_files = [
@@ -21,8 +21,6 @@ Gem::Specification.new do |s|
21
21
  "app/controllers/muck/activities_controller.rb",
22
22
  "app/helpers/muck_activity_helper.rb",
23
23
  "app/helpers/muck_activity_helper.rb",
24
- "app/models/activity.rb",
25
- "app/models/activity.rb",
26
24
  "app/models/activity_feed.rb",
27
25
  "app/models/activity_feed.rb",
28
26
  "app/views/activities/_activity_feed.html.erb",
@@ -43,6 +41,8 @@ Gem::Specification.new do |s|
43
41
  "app/views/activities/_status_update.html.erb",
44
42
  "app/views/activities/_template_filter.html.erb",
45
43
  "app/views/activities/_template_filter.html.erb",
44
+ "app/views/activity_templates/_generic.html.erb",
45
+ "app/views/activity_templates/_generic.html.erb",
46
46
  "app/views/activity_templates/_status_update.html.erb",
47
47
  "app/views/activity_templates/_status_update.html.erb",
48
48
  "config/muck_activities_routes.rb",
@@ -50,14 +50,14 @@ Gem::Specification.new do |s|
50
50
  "db/migrate/20090402033319_add_muck_activities.rb",
51
51
  "db/migrate/20090402033319_add_muck_activities.rb",
52
52
  "install.rb",
53
+ "lib/active_record/acts/muck_activity.rb",
54
+ "lib/active_record/acts/muck_activity.rb",
53
55
  "lib/muck_activities.rb",
54
56
  "lib/muck_activities.rb",
55
- "lib/muck_activities/active_record/acts/muck_activity.rb",
56
- "lib/muck_activities/active_record/acts/muck_activity.rb",
57
57
  "lib/muck_activities/initialize_routes.rb",
58
58
  "lib/muck_activities/initialize_routes.rb",
59
- "lib/muck_activities/muck_activity.rb",
60
- "lib/muck_activities/muck_activity.rb",
59
+ "lib/muck_activities/muck_activity_sources.rb",
60
+ "lib/muck_activities/muck_activity_sources.rb",
61
61
  "lib/muck_activities/tasks.rb",
62
62
  "lib/muck_activities/tasks.rb",
63
63
  "locales/ar.yml",
@@ -126,6 +126,7 @@ Gem::Specification.new do |s|
126
126
  "locales/zh.yml",
127
127
  "muck-activities.gemspec",
128
128
  "pkg/muck-activities-0.1.10.gem",
129
+ "pkg/muck-activities-0.1.11.gem",
129
130
  "public/images/loading.gif",
130
131
  "public/images/loading.gif",
131
132
  "public/javascripts/muck_activities.js",
@@ -161,7 +162,9 @@ Gem::Specification.new do |s|
161
162
  "test/rails_root/app/controllers/default_controller.rb",
162
163
  "test/rails_root/app/helpers/application_helper.rb",
163
164
  "test/rails_root/app/models/.keep",
165
+ "test/rails_root/app/models/activity.rb",
164
166
  "test/rails_root/app/models/comment.rb",
167
+ "test/rails_root/app/models/profile.rb",
165
168
  "test/rails_root/app/models/user.rb",
166
169
  "test/rails_root/app/models/user_session.rb",
167
170
  "test/rails_root/app/views/default/index.html.erb",
@@ -185,6 +188,7 @@ Gem::Specification.new do |s|
185
188
  "test/rails_root/db/migrate/20090402234137_create_languages.rb",
186
189
  "test/rails_root/db/migrate/20090426041056_create_countries.rb",
187
190
  "test/rails_root/db/migrate/20090426041103_create_states.rb",
191
+ "test/rails_root/db/migrate/20090512013727_create_profiles.rb",
188
192
  "test/rails_root/db/migrate/20090602041838_create_users.rb",
189
193
  "test/rails_root/db/migrate/20090613173314_create_comments.rb",
190
194
  "test/rails_root/features/step_definitions/webrat_steps.rb",
@@ -356,6 +360,7 @@ Gem::Specification.new do |s|
356
360
  "test/rails_root/test/unit/.keep",
357
361
  "test/rails_root/test/unit/activity_feed_test.rb",
358
362
  "test/rails_root/test/unit/activity_test.rb",
363
+ "test/rails_root/test/unit/user_test.rb",
359
364
  "uninstall.rb"
360
365
  ]
361
366
  s.has_rdoc = true
@@ -369,7 +374,9 @@ Gem::Specification.new do |s|
369
374
  "test/rails_root/app/controllers/application_controller.rb",
370
375
  "test/rails_root/app/controllers/default_controller.rb",
371
376
  "test/rails_root/app/helpers/application_helper.rb",
377
+ "test/rails_root/app/models/activity.rb",
372
378
  "test/rails_root/app/models/comment.rb",
379
+ "test/rails_root/app/models/profile.rb",
373
380
  "test/rails_root/app/models/user.rb",
374
381
  "test/rails_root/app/models/user_session.rb",
375
382
  "test/rails_root/config/boot.rb",
@@ -387,6 +394,7 @@ Gem::Specification.new do |s|
387
394
  "test/rails_root/db/migrate/20090402234137_create_languages.rb",
388
395
  "test/rails_root/db/migrate/20090426041056_create_countries.rb",
389
396
  "test/rails_root/db/migrate/20090426041103_create_states.rb",
397
+ "test/rails_root/db/migrate/20090512013727_create_profiles.rb",
390
398
  "test/rails_root/db/migrate/20090602041838_create_users.rb",
391
399
  "test/rails_root/db/migrate/20090613173314_create_comments.rb",
392
400
  "test/rails_root/db/schema.rb",
@@ -400,7 +408,8 @@ Gem::Specification.new do |s|
400
408
  "test/rails_root/test/shoulda_macros/controller.rb",
401
409
  "test/rails_root/test/test_helper.rb",
402
410
  "test/rails_root/test/unit/activity_feed_test.rb",
403
- "test/rails_root/test/unit/activity_test.rb"
411
+ "test/rails_root/test/unit/activity_test.rb",
412
+ "test/rails_root/test/unit/user_test.rb"
404
413
  ]
405
414
 
406
415
  if s.respond_to? :specification_version then
@@ -1 +1 @@
1
- Thu, 18 Jun 2009 11:30:28 -0600
1
+ Fri, 19 Jun 2009 02:12:00 -0600
@@ -13,3 +13,4 @@ require 'muck_engine/tasks'
13
13
  require 'muck_users/tasks'
14
14
  require 'muck_comments/tasks'
15
15
  require 'muck_activities/tasks'
16
+ require 'muck_profiles/tasks'
@@ -0,0 +1,3 @@
1
+ class Activity < ActiveRecord::Base
2
+ acts_as_muck_activity
3
+ end
@@ -0,0 +1,3 @@
1
+ class Profile < ActiveRecord::Base
2
+ acts_as_muck_profile
3
+ end
@@ -2,9 +2,14 @@ class User < ActiveRecord::Base
2
2
  acts_as_authentic do |c|
3
3
  c.crypto_provider = Authlogic::CryptoProviders::BCrypt
4
4
  end
5
-
5
+ acts_as_muck_user
6
+ has_muck_profile
6
7
  has_activities
7
8
 
9
+ def feed_to
10
+ [self]
11
+ end
12
+
8
13
  def admin?
9
14
  false
10
15
  end
@@ -4,3 +4,4 @@
4
4
  <%= current_status(@user) %>
5
5
  <%= status_update(@user) %>
6
6
  <%= activity_feed_for(@user) %>
7
+ <%= limited_activity_feed_for(@user) %>
@@ -17,10 +17,13 @@ Rails::Initializer.run do |config|
17
17
  config.time_zone = 'UTC'
18
18
  config.gem 'mislav-will_paginate', :lib => 'will_paginate', :source => 'http://gems.github.com'
19
19
  config.gem "authlogic"
20
+ config.gem "binarylogic-searchlogic", :lib => 'searchlogic', :source => 'http://gems.github.com', :version => '~> 2.0.0'
20
21
  config.gem "bcrypt-ruby", :lib => "bcrypt"
21
22
  config.gem "collectiveidea-awesome_nested_set", :lib => 'awesome_nested_set', :source => "http://gems.github.com"
23
+ config.gem 'thoughtbot-paperclip', :lib => 'paperclip', :source => "http://gems.github.com"
22
24
  config.gem 'muck-engine', :lib => 'muck_engine'
23
25
  config.gem 'muck-users', :lib => 'muck_users'
24
26
  config.gem 'muck-comments', :lib => 'muck_comments'
27
+ config.gem 'muck-profiles', :lib => 'muck_profiles'
25
28
  config.plugin_locators << TestGemLocator
26
29
  end
@@ -0,0 +1,21 @@
1
+ class CreateProfiles < ActiveRecord::Migration
2
+
3
+ def self.up
4
+
5
+ create_table :profiles, :force => true do |t|
6
+ t.integer :user_id
7
+ t.string :photo_file_name
8
+ t.string :photo_content_type
9
+ t.integer :photo_file_size
10
+ t.timestamps
11
+ end
12
+
13
+ add_index :profiles, ['user_id']
14
+
15
+ end
16
+
17
+ def self.down
18
+ drop_table :profiles
19
+ end
20
+
21
+ end
@@ -3,7 +3,7 @@ class CreateComments < ActiveRecord::Migration
3
3
  create_table :comments, :force => true do |t|
4
4
  t.integer :commentable_id, :default => 0
5
5
  t.string :commentable_type, :limit => 15, :default => ""
6
- t.text :body, :default => ""
6
+ t.text :body
7
7
  t.integer :user_id, :default => 0, :null => false
8
8
  t.integer :parent_id
9
9
  t.integer :lft
@@ -11,30 +11,56 @@ class Muck::ActivitiesControllerTest < ActionController::TestCase
11
11
  login_as @user
12
12
  end
13
13
 
14
- context 'on GET to index (js)' do
14
+ context "on GET to index" do
15
15
  setup do
16
- @activity = Factory(:activity)
17
- get :index, :parent_type => @user.type, :parent_id => @user, :format => 'js', :latest_activity_id => @activity.to_param
16
+ @activity = Factory(:activity, :template => 'status_update')
17
+ @user.activities << @activity
18
+ end
19
+
20
+ context 'on GET to index (js)' do
21
+ setup do
22
+ get :index, :parent_type => @user.type, :parent_id => @user, :format => 'js', :latest_activity_id => @activity.to_param
23
+ end
24
+ should_respond_with :success
25
+ end
26
+
27
+ context 'on GET to index (js) no latest activity id' do
28
+ setup do
29
+ get :index, :parent_type => @user.type, :parent_id => @user, :format => 'js', :latest_activity_id => nil
30
+ end
31
+ should_respond_with :success
18
32
  end
19
- should_respond_with :success
20
33
  end
21
34
 
22
- context 'on GET to index (js) no latest activity id' do
35
+ context 'fail on POST to create (json)' do
23
36
  setup do
24
- get :index, :parent_type => @user.type, :parent_id => @user, :format => 'js', :latest_activity_id => nil
25
- end
37
+ post :create, :activity => { :content => 'test activity' }, :parent_type => @user.type, :parent_id => @user, :format => 'json'
38
+ end
26
39
  should_respond_with :success
40
+ should_not_set_the_flash
41
+ should "return create json errors" do
42
+ json = ActiveSupport::JSON.decode(@response.body).symbolize_keys!
43
+ assert !json[:success]
44
+ assert_equal json[:message], I18n.t("muck.activities.create_error", :error => assigns(:activity).errors.full_messages.to_sentence)
45
+ end
27
46
  end
28
-
29
- context 'on GET to comment (json)' do
47
+
48
+ context 'on POST to create (json)' do
30
49
  setup do
31
- @activity = Factory(:activity, :source => @user)
32
- @comment = Factory(:comment, :user => @user)
33
- get :comment, :id => @activity.id, :comment_id => @comment.id, :format => 'json'
34
- end
50
+ @activity_content = 'test content for my new activity'
51
+ post :create, :activity => { :content => @activity_content, :template => 'status_update' }, :parent_type => @user.type, :parent_id => @user, :format => 'json'
52
+ end
35
53
  should_respond_with :success
54
+ should_not_set_the_flash
55
+ should "return valid create json" do
56
+ json = ActiveSupport::JSON.decode(@response.body).symbolize_keys!
57
+ assert json[:success]
58
+ assert !json[:is_status_update]
59
+ assert json[:html].include?(@activity_content)
60
+ assert_equal json[:message], I18n.t("muck.activities.created")
61
+ end
36
62
  end
37
-
63
+
38
64
  context 'on POST to create (js)' do
39
65
  setup do
40
66
  post :create, :activity => { :content => 'test activity' }, :parent_type => @user.type, :parent_id => @user, :format => 'js'
@@ -42,7 +68,7 @@ class Muck::ActivitiesControllerTest < ActionController::TestCase
42
68
  should_respond_with :success
43
69
  should_not_set_the_flash
44
70
  end
45
-
71
+
46
72
  context 'on POST to create' do
47
73
  setup do
48
74
  post :create, :activity => { :content => 'test activity' }, :parent_type => @user.type, :parent_id => @user
@@ -61,13 +87,53 @@ class Muck::ActivitiesControllerTest < ActionController::TestCase
61
87
 
62
88
  context 'on DELETE to destroy (js)' do
63
89
  setup do
64
- @activity = Factory(:activity, :source => @user)
90
+ @activity = Factory(:activity, :source => @user, :is_status_update => false)
65
91
  delete :destroy, :id => @activity.id, :format => 'js'
66
92
  end
67
93
  should_respond_with :success
68
94
  should_not_set_the_flash
69
95
  end
70
96
 
97
+ context 'on DELETE to destroy, status update (js)' do
98
+ setup do
99
+ @activity = Factory(:activity, :source => @user, :is_status_update => true)
100
+ delete :destroy, :id => @activity.id, :format => 'js'
101
+ end
102
+ should_respond_with :success
103
+ should_not_set_the_flash
104
+ end
105
+
106
+ context 'on DELETE to destroy (json)' do
107
+ setup do
108
+ @activity = Factory(:activity, :source => @user, :is_status_update => false)
109
+ delete :destroy, :id => @activity.id, :format => 'json'
110
+ end
111
+ should_respond_with :success
112
+ should_not_set_the_flash
113
+ should "return valid delete json" do
114
+ json = ActiveSupport::JSON.decode(@response.body).symbolize_keys!
115
+ assert json[:success]
116
+ assert !json[:is_status_update]
117
+ assert json[:html].blank?
118
+ assert_equal json[:message], I18n.t("muck.activities.item_removed")
119
+ end
120
+ end
121
+
122
+ context 'on DELETE to destroy, status update (json)' do
123
+ setup do
124
+ @activity = Factory(:activity, :source => @user, :is_status_update => true)
125
+ delete :destroy, :id => @activity.id, :format => 'json'
126
+ end
127
+ should_respond_with :success
128
+ should_not_set_the_flash
129
+ should "return valid delete json" do
130
+ json = ActiveSupport::JSON.decode(@response.body).symbolize_keys!
131
+ assert json[:success]
132
+ assert json[:is_status_update]
133
+ assert json[:html].length > 0
134
+ assert_equal json[:message], I18n.t("muck.activities.item_removed")
135
+ end
136
+ end
71
137
  end
72
138
 
73
139
  end
@@ -15,7 +15,7 @@ class DefaultControllerTest < ActionController::TestCase
15
15
  # the default view calls some of the helpers
16
16
  # this is a sanity check to make sure they don't blow up
17
17
  setup do
18
- @user.activities << Factory(:activity)
18
+ @user.activities << Factory(:activity, :template => 'status_update')
19
19
  get :index
20
20
  end
21
21
  should_respond_with :success
@@ -1,5 +1,6 @@
1
1
  require File.dirname(__FILE__) + '/../test_helper'
2
2
 
3
3
  class ActivityFeedTest < ActiveSupport::TestCase
4
-
4
+ should_belong_to :activity
5
+ should_belong_to :ownable
5
6
  end
@@ -9,12 +9,15 @@ class ActivityTest < ActiveSupport::TestCase
9
9
  should_belong_to :item
10
10
  should_belong_to :source
11
11
  should_have_many :activity_feeds
12
+ should_have_many :comments
12
13
 
13
14
  should_have_named_scope :since
14
15
  should_have_named_scope :before
15
- should_have_named_scope :recent
16
+ should_have_named_scope :newest
16
17
  should_have_named_scope :only_public
17
18
  should_have_named_scope :filter_by_template
19
+ should_have_named_scope :status_updates
20
+
18
21
  end
19
22
 
20
23
  should "require template or item" do
@@ -54,4 +57,18 @@ class ActivityTest < ActiveSupport::TestCase
54
57
  assert user.activities.filter_by_template(@template_name).include?(activity)
55
58
  end
56
59
 
60
+ should "only find activities created by the source" do
61
+ user = Factory(:user)
62
+ activity = Factory(:activity, :source => user, :template => @template_name)
63
+ user.activities << activity
64
+
65
+ user2 = Factory(:user)
66
+ activity2 = Factory(:activity, :source => user2, :template => @template_name)
67
+ user2.activities << activity2
68
+
69
+ assert user.activities.created_by(user).include?(activity)
70
+ assert !user.activities.created_by(user).include?(activity2)
71
+
72
+ end
73
+
57
74
  end
@@ -0,0 +1,22 @@
1
+ require File.dirname(__FILE__) + '/../test_helper'
2
+
3
+ class UserTest < ActiveSupport::TestCase
4
+ context "activities" do
5
+ setup do
6
+ @user = Factory(:user)
7
+ end
8
+ should_have_many :activity_feeds
9
+ should_have_many :activities
10
+ should "create an activity" do
11
+ assert_difference "Activity.count", 1 do
12
+ @user.add_activity(@user.feed_to, @user, @user, 'status_update', 'status', 'a status update')
13
+ end
14
+ end
15
+ should "set the user's current status" do
16
+ activity = @user.add_activity(@user.feed_to, @user, @user, 'status_update', 'status', 'a status update')
17
+ activity.is_status_update = true
18
+ activity.save!
19
+ assert_equal @user.status, activity
20
+ end
21
+ end
22
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: muck-activities
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.11
4
+ version: 0.1.12
5
5
  platform: ruby
6
6
  authors:
7
7
  - Justin Ball
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-06-19 00:00:00 -06:00
12
+ date: 2009-06-24 00:00:00 -06:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -57,7 +57,6 @@ files:
57
57
  - VERSION
58
58
  - app/controllers/muck/activities_controller.rb
59
59
  - app/helpers/muck_activity_helper.rb
60
- - app/models/activity.rb
61
60
  - app/models/activity_feed.rb
62
61
  - app/views/activities/_activity_feed.html.erb
63
62
  - app/views/activities/_cached_activities.html.erb
@@ -68,14 +67,15 @@ files:
68
67
  - app/views/activities/_delete.html.erb
69
68
  - app/views/activities/_status_update.html.erb
70
69
  - app/views/activities/_template_filter.html.erb
70
+ - app/views/activity_templates/_generic.html.erb
71
71
  - app/views/activity_templates/_status_update.html.erb
72
72
  - config/muck_activities_routes.rb
73
73
  - db/migrate/20090402033319_add_muck_activities.rb
74
74
  - install.rb
75
+ - lib/active_record/acts/muck_activity.rb
75
76
  - lib/muck_activities.rb
76
- - lib/muck_activities/active_record/acts/muck_activity.rb
77
77
  - lib/muck_activities/initialize_routes.rb
78
- - lib/muck_activities/muck_activity.rb
78
+ - lib/muck_activities/muck_activity_sources.rb
79
79
  - lib/muck_activities/tasks.rb
80
80
  - locales/ar.yml
81
81
  - locales/bg.yml
@@ -111,6 +111,7 @@ files:
111
111
  - locales/zh.yml
112
112
  - muck-activities.gemspec
113
113
  - pkg/muck-activities-0.1.10.gem
114
+ - pkg/muck-activities-0.1.11.gem
114
115
  - public/images/loading.gif
115
116
  - public/javascripts/muck_activities.js
116
117
  - rails/init.rb
@@ -142,7 +143,9 @@ files:
142
143
  - test/rails_root/app/controllers/default_controller.rb
143
144
  - test/rails_root/app/helpers/application_helper.rb
144
145
  - test/rails_root/app/models/.keep
146
+ - test/rails_root/app/models/activity.rb
145
147
  - test/rails_root/app/models/comment.rb
148
+ - test/rails_root/app/models/profile.rb
146
149
  - test/rails_root/app/models/user.rb
147
150
  - test/rails_root/app/models/user_session.rb
148
151
  - test/rails_root/app/views/default/index.html.erb
@@ -166,6 +169,7 @@ files:
166
169
  - test/rails_root/db/migrate/20090402234137_create_languages.rb
167
170
  - test/rails_root/db/migrate/20090426041056_create_countries.rb
168
171
  - test/rails_root/db/migrate/20090426041103_create_states.rb
172
+ - test/rails_root/db/migrate/20090512013727_create_profiles.rb
169
173
  - test/rails_root/db/migrate/20090602041838_create_users.rb
170
174
  - test/rails_root/db/migrate/20090613173314_create_comments.rb
171
175
  - test/rails_root/features/step_definitions/webrat_steps.rb
@@ -337,6 +341,7 @@ files:
337
341
  - test/rails_root/test/unit/.keep
338
342
  - test/rails_root/test/unit/activity_feed_test.rb
339
343
  - test/rails_root/test/unit/activity_test.rb
344
+ - test/rails_root/test/unit/user_test.rb
340
345
  - uninstall.rb
341
346
  has_rdoc: true
342
347
  homepage: http://github.com/jbasdf/muck_activities
@@ -368,7 +373,9 @@ test_files:
368
373
  - test/rails_root/app/controllers/application_controller.rb
369
374
  - test/rails_root/app/controllers/default_controller.rb
370
375
  - test/rails_root/app/helpers/application_helper.rb
376
+ - test/rails_root/app/models/activity.rb
371
377
  - test/rails_root/app/models/comment.rb
378
+ - test/rails_root/app/models/profile.rb
372
379
  - test/rails_root/app/models/user.rb
373
380
  - test/rails_root/app/models/user_session.rb
374
381
  - test/rails_root/config/boot.rb
@@ -386,6 +393,7 @@ test_files:
386
393
  - test/rails_root/db/migrate/20090402234137_create_languages.rb
387
394
  - test/rails_root/db/migrate/20090426041056_create_countries.rb
388
395
  - test/rails_root/db/migrate/20090426041103_create_states.rb
396
+ - test/rails_root/db/migrate/20090512013727_create_profiles.rb
389
397
  - test/rails_root/db/migrate/20090602041838_create_users.rb
390
398
  - test/rails_root/db/migrate/20090613173314_create_comments.rb
391
399
  - test/rails_root/db/schema.rb
@@ -400,3 +408,4 @@ test_files:
400
408
  - test/rails_root/test/test_helper.rb
401
409
  - test/rails_root/test/unit/activity_feed_test.rb
402
410
  - test/rails_root/test/unit/activity_test.rb
411
+ - test/rails_root/test/unit/user_test.rb
@@ -1,62 +0,0 @@
1
- # == Schema Information
2
- #
3
- # Table name: activities
4
- #
5
- # id :integer(4) not null, primary key
6
- # item_id :integer(4)
7
- # item_type :string(255)
8
- # template :string(255)
9
- # source_id :integer(4)
10
- # source_type :string(255)
11
- # content :text
12
- # title :string(255)
13
- # status_update :boolean(1)
14
- # created_at :datetime
15
- # updated_at :datetime
16
- #
17
-
18
- class Activity < ActiveRecord::Base
19
- unloadable
20
-
21
- belongs_to :item, :polymorphic => true
22
- belongs_to :source, :polymorphic => true
23
- has_many :activity_feeds
24
-
25
- acts_as_commentable
26
-
27
- validates_presence_of :source
28
-
29
- named_scope :since, lambda { |time| {:conditions => ["activities.created_at > ?", time] } }
30
- named_scope :before, lambda {|time| {:conditions => ["activities.created_at < ?", time] } }
31
- named_scope :recent, :order => "activities.created_at DESC"
32
- named_scope :after, lambda {|id| {:conditions => ["activities.id > ?", id] } }
33
- named_scope :only_public, :conditions => ["activities.is_public = true"]
34
- named_scope :filter_by_template, lambda { |template| { :conditions => ["activities.template = ?", template] } unless template.blank? }
35
-
36
- def validate
37
- errors.add_to_base(I18n.t('muck.activities.template_or_item_required')) if template.blank? && item.blank?
38
- end
39
-
40
- # Provides a template that can be used to render a view of this activity.
41
- # If 'template' is not specified when the object created then the item class
42
- # name will be used to generated a template
43
- def partial
44
- template || item.class.name.underscore
45
- end
46
-
47
- def has_comments?
48
- @has_comments ||= !self.comments.blank?
49
- end
50
-
51
- # Checks to see if the specified object can edit this activity.
52
- # Most likely check_object will be a user
53
- def can_edit?(check_object)
54
- if check_object.is_a?(User)
55
- return true if check(check_object, :source_id)
56
- else
57
- source == check_object
58
- end
59
- false
60
- end
61
-
62
- end
@@ -1,68 +0,0 @@
1
- module MuckActivity # :nodoc:
2
-
3
- def self.included(base) # :nodoc:
4
- base.extend ActMethods
5
- end
6
-
7
- module ActMethods
8
-
9
- # +has_activities+ gives the class it is called on an activity feed and a method called
10
- # +add_activity+ that can add activities into a feed. Retrieve activity feed items
11
- # via object.activities. ie @user.activities.
12
- def has_activities
13
- unless included_modules.include? InstanceMethods
14
- has_many :activity_feeds, :as => :ownable
15
- has_many :activities, :through => :activity_feeds, :order => 'created_at desc'
16
- include InstanceMethods
17
- end
18
- end
19
-
20
- # +acts_as_activity_source+ gives the class it is called on a method called
21
- # +add_activity+ that can add activities into a feed.
22
- def acts_as_activity_source
23
- unless included_modules.include? InstanceMethods
24
- include InstanceMethods
25
- end
26
- end
27
-
28
- end
29
-
30
- module InstanceMethods
31
-
32
- # +add_activity+ adds an activity to all activites feeds that belong to the objects found in feed_to.
33
- # * +feed_to+: an array of objects that have +has_activities+ declared on them. The generated activity
34
- # will be pushed into the feed of each of these objects.
35
- # * +source+: the object that peformed the activity ie a user or group
36
- # * +item+: an object that will be used to generated the entry in an activity feed
37
- # * +template+: name of an partial that will be used to generated the entry in the activity feed. Place
38
- # templates in /app/views/activity_templates
39
- # * +title+: optional title that can be used in the template
40
- # * +content+: option content that can be used in the template. Useful for activities that might not have
41
- # an item but instead might have a message or other text.
42
- # * +check_method+: method that will be called on each item in the feed_to array. If the method evaluates
43
- # to false the activity won't be added to the object's activity feed. An example usage would be
44
- # letting users configure which items they want to have in their activity feed.
45
- def add_activity(feed_to, source, item, template, title = '', content = '', check_method = nil)
46
- feed_to = [feed_to] unless feed_to.is_a?(Array)
47
- activity = Activity.create(:item => item, :source => source, :template => template, :title => title, :content => content)
48
- feed_to.each do |ft|
49
- if check_method
50
- ft.activities << activity if ft.send(check_method)
51
- else
52
- ft.activities << activity
53
- end
54
- end
55
- end
56
-
57
- # +status+ returns the first activity item from the user's activity feed that is a status update.
58
- # Used for displaying the last status update the user made
59
- def status
60
- self.activities.find(:first, :conditions => ['is_status_update = true'], :order => 'created_at DESC')
61
- end
62
-
63
- def can_view?(check_object)
64
- self == check_object
65
- end
66
- end
67
-
68
- end