acts-as-taggable-on 0.0.0 → 1.0.6

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.
Files changed (38) hide show
  1. data/CHANGELOG +2 -9
  2. data/README +196 -0
  3. data/Rakefile +10 -47
  4. data/VERSION +1 -1
  5. data/lib/acts-as-taggable-on.rb +6 -30
  6. data/lib/acts_as_taggable_on/acts_as_taggable_on.rb +313 -28
  7. data/lib/acts_as_taggable_on/acts_as_tagger.rb +45 -40
  8. data/lib/acts_as_taggable_on/tag.rb +6 -48
  9. data/lib/acts_as_taggable_on/tag_list.rb +29 -31
  10. data/lib/acts_as_taggable_on/tagging.rb +1 -18
  11. data/lib/acts_as_taggable_on/tags_helper.rb +2 -8
  12. data/rails/init.rb +6 -1
  13. data/spec/acts_as_taggable_on/acts_as_taggable_on_spec.rb +47 -148
  14. data/spec/acts_as_taggable_on/acts_as_tagger_spec.rb +4 -46
  15. data/spec/acts_as_taggable_on/tag_list_spec.rb +0 -29
  16. data/spec/acts_as_taggable_on/tag_spec.rb +7 -95
  17. data/spec/acts_as_taggable_on/taggable_spec.rb +48 -178
  18. data/spec/acts_as_taggable_on/tagger_spec.rb +5 -57
  19. data/spec/acts_as_taggable_on/tagging_spec.rb +1 -25
  20. data/spec/schema.rb +2 -12
  21. data/spec/spec.opts +6 -1
  22. data/spec/spec_helper.rb +34 -35
  23. metadata +7 -31
  24. data/Gemfile +0 -6
  25. data/README.rdoc +0 -212
  26. data/lib/acts_as_taggable_on/acts_as_taggable_on/cache.rb +0 -56
  27. data/lib/acts_as_taggable_on/acts_as_taggable_on/collection.rb +0 -97
  28. data/lib/acts_as_taggable_on/acts_as_taggable_on/core.rb +0 -220
  29. data/lib/acts_as_taggable_on/acts_as_taggable_on/dirty.rb +0 -29
  30. data/lib/acts_as_taggable_on/acts_as_taggable_on/ownership.rb +0 -101
  31. data/lib/acts_as_taggable_on/acts_as_taggable_on/related.rb +0 -64
  32. data/lib/acts_as_taggable_on/compatibility/Gemfile +0 -6
  33. data/lib/acts_as_taggable_on/compatibility/active_record_backports.rb +0 -17
  34. data/lib/generators/acts_as_taggable_on/migration/migration_generator.rb +0 -31
  35. data/lib/generators/acts_as_taggable_on/migration/templates/active_record/migration.rb +0 -28
  36. data/spec/acts_as_taggable_on/tags_helper_spec.rb +0 -28
  37. data/spec/bm.rb +0 -52
  38. data/spec/models.rb +0 -36
@@ -1,47 +1,52 @@
1
- module ActsAsTaggableOn
2
- module Tagger
3
- def self.included(base)
4
- base.extend ClassMethods
5
- end
6
-
7
- module ClassMethods
8
- def acts_as_tagger(opts={})
9
- has_many :owned_taggings, opts.merge(:as => :tagger, :dependent => :destroy,
10
- :include => :tag, :class_name => "Tagging")
11
- has_many :owned_tags, :through => :owned_taggings, :source => :tag, :uniq => true
12
-
13
- include ActsAsTaggableOn::Tagger::InstanceMethods
14
- extend ActsAsTaggableOn::Tagger::SingletonMethods
1
+ module ActiveRecord
2
+ module Acts
3
+ module Tagger
4
+ def self.included(base)
5
+ base.extend ClassMethods
15
6
  end
16
-
17
- def is_tagger?
18
- false
7
+
8
+ module ClassMethods
9
+ def acts_as_tagger(opts={})
10
+ has_many :owned_taggings, opts.merge(:as => :tagger, :dependent => :destroy,
11
+ :include => :tag, :class_name => "Tagging")
12
+ has_many :owned_tags, :through => :owned_taggings, :source => :tag, :uniq => true
13
+ include ActiveRecord::Acts::Tagger::InstanceMethods
14
+ extend ActiveRecord::Acts::Tagger::SingletonMethods
15
+ end
16
+
17
+ def is_tagger?
18
+ false
19
+ end
19
20
  end
20
- end
21
-
22
- module InstanceMethods
23
- def tag(taggable, opts={})
24
- opts.reverse_merge!(:force => true)
25
-
26
- return false unless taggable.respond_to?(:is_taggable?) && taggable.is_taggable?
27
-
28
- raise "You need to specify a tag context using :on" unless opts.has_key?(:on)
29
- raise "You need to specify some tags using :with" unless opts.has_key?(:with)
30
- raise "No context :#{opts[:on]} defined in #{taggable.class.to_s}" unless (opts[:force] || taggable.tag_types.include?(opts[:on]))
31
-
32
- taggable.set_owner_tag_list_on(self, opts[:on].to_s, opts[:with])
33
- taggable.save
34
- end
35
-
36
- def is_tagger?
37
- self.class.is_tagger?
21
+
22
+ module InstanceMethods
23
+ def self.included(base)
24
+ end
25
+
26
+ def tag(taggable, opts={})
27
+ opts.reverse_merge!(:force => true)
28
+
29
+ return false unless taggable.respond_to?(:is_taggable?) && taggable.is_taggable?
30
+ raise "You need to specify a tag context using :on" unless opts.has_key?(:on)
31
+ raise "You need to specify some tags using :with" unless opts.has_key?(:with)
32
+ raise "No context :#{opts[:on]} defined in #{taggable.class.to_s}" unless
33
+ ( opts[:force] || taggable.tag_types.include?(opts[:on]) )
34
+
35
+ taggable.set_tag_list_on(opts[:on].to_s, opts[:with], self)
36
+ taggable.save
37
+ end
38
+
39
+ def is_tagger?
40
+ self.class.is_tagger?
41
+ end
38
42
  end
39
- end
40
-
41
- module SingletonMethods
42
- def is_tagger?
43
- true
43
+
44
+ module SingletonMethods
45
+ def is_tagger?
46
+ true
47
+ end
44
48
  end
49
+
45
50
  end
46
51
  end
47
52
  end
@@ -1,65 +1,23 @@
1
1
  class Tag < ActiveRecord::Base
2
- include ActsAsTaggableOn::ActiveRecord::Backports if ActiveRecord::VERSION::MAJOR < 3
2
+ has_many :taggings
3
3
 
4
- attr_accessible :name
5
-
6
- ### ASSOCIATIONS:
7
-
8
- has_many :taggings, :dependent => :destroy
9
-
10
- ### VALIDATIONS:
11
-
12
4
  validates_presence_of :name
13
5
  validates_uniqueness_of :name
14
-
15
- ### SCOPES:
16
-
17
- def self.named(name)
18
- where(["name LIKE ?", name])
19
- end
20
-
21
- def self.named_any(list)
22
- where(list.map { |tag| sanitize_sql(["name LIKE ?", tag.to_s]) }.join(" OR "))
23
- end
24
6
 
25
- def self.named_like(name)
26
- where(["name LIKE ?", "%#{name}%"])
27
- end
28
-
29
- def self.named_like_any(list)
30
- where(list.map { |tag| sanitize_sql(["name LIKE ?", "%#{tag.to_s}%"]) }.join(" OR "))
31
- end
32
-
33
- ### CLASS METHODS:
34
-
7
+ # LIKE is used for cross-database case-insensitivity
35
8
  def self.find_or_create_with_like_by_name(name)
36
- named_like(name).first || create(:name => name)
9
+ find(:first, :conditions => ["name LIKE ?", name]) || create(:name => name)
37
10
  end
38
-
39
- def self.find_or_create_all_with_like_by_name(*list)
40
- list = [list].flatten
41
-
42
- return [] if list.empty?
43
-
44
- existing_tags = Tag.named_any(list).all
45
- new_tag_names = list.reject { |name| existing_tags.any? { |tag| tag.name.downcase == name.downcase } }
46
- created_tags = new_tag_names.map { |name| Tag.create(:name => name) }
47
-
48
- existing_tags + created_tags
49
- end
50
-
51
- ### INSTANCE METHODS:
52
-
11
+
53
12
  def ==(object)
54
13
  super || (object.is_a?(Tag) && name == object.name)
55
14
  end
56
-
15
+
57
16
  def to_s
58
17
  name
59
18
  end
60
-
19
+
61
20
  def count
62
21
  read_attribute(:count).to_i
63
22
  end
64
-
65
23
  end
@@ -1,19 +1,17 @@
1
1
  class TagList < Array
2
-
3
2
  cattr_accessor :delimiter
4
-
5
3
  self.delimiter = ','
6
-
4
+
7
5
  def initialize(*args)
8
6
  add(*args)
9
7
  end
10
-
8
+
11
9
  attr_accessor :owner
12
-
10
+
13
11
  # Add tags to the tag_list. Duplicate or blank tags will be ignored.
14
12
  #
15
13
  # tag_list.add("Fun", "Happy")
16
- #
14
+ #
17
15
  # Use the <tt>:parse</tt> option to add an unparsed tag string.
18
16
  #
19
17
  # tag_list.add("Fun, Happy", :parse => true)
@@ -23,34 +21,33 @@ class TagList < Array
23
21
  clean!
24
22
  self
25
23
  end
26
-
24
+
27
25
  # Remove specific tags from the tag_list.
28
- #
26
+ #
29
27
  # tag_list.remove("Sad", "Lonely")
30
28
  #
31
29
  # Like #add, the <tt>:parse</tt> option can be used to remove multiple tags in a string.
32
- #
30
+ #
33
31
  # tag_list.remove("Sad, Lonely", :parse => true)
34
32
  def remove(*names)
35
33
  extract_and_apply_options!(names)
36
34
  delete_if { |name| names.include?(name) }
37
35
  self
38
36
  end
39
-
37
+
40
38
  # Transform the tag_list into a tag string suitable for edting in a form.
41
39
  # The tags are joined with <tt>TagList.delimiter</tt> and quoted if necessary.
42
40
  #
43
41
  # tag_list = TagList.new("Round", "Square,Cube")
44
42
  # tag_list.to_s # 'Round, "Square,Cube"'
45
43
  def to_s
46
- tags = frozen? ? self.dup : self
47
- tags.send(:clean!)
48
-
49
- tags.map do |name|
44
+ clean!
45
+
46
+ map do |name|
50
47
  name.include?(delimiter) ? "\"#{name}\"" : name
51
48
  end.join(delimiter.ends_with?(" ") ? delimiter : "#{delimiter} ")
52
49
  end
53
-
50
+
54
51
  private
55
52
  # Remove whitespace, duplicates, and blanks.
56
53
  def clean!
@@ -58,38 +55,39 @@ class TagList < Array
58
55
  map!(&:strip)
59
56
  uniq!
60
57
  end
61
-
58
+
62
59
  def extract_and_apply_options!(args)
63
60
  options = args.last.is_a?(Hash) ? args.pop : {}
64
61
  options.assert_valid_keys :parse
65
-
62
+
66
63
  if options[:parse]
67
64
  args.map! { |a| self.class.from(a) }
68
65
  end
69
-
66
+
70
67
  args.flatten!
71
68
  end
72
-
69
+
73
70
  class << self
74
-
75
71
  # Returns a new TagList using the given tag string.
76
- #
72
+ #
77
73
  # tag_list = TagList.from("One , Two, Three")
78
74
  # tag_list # ["One", "Two", "Three"]
79
75
  def from(string)
80
- string = string.join(", ") if string.respond_to?(:join)
81
-
82
- new.tap do |tag_list|
76
+ returning new do |tag_list|
83
77
  string = string.to_s.dup
84
-
78
+
85
79
  # Parse the quoted tags
86
- string.gsub!(/(\A|#{delimiter})\s*"(.*?)"\s*(#{delimiter}\s*|\z)/) { tag_list << $2; $3 }
87
- string.gsub!(/(\A|#{delimiter})\s*'(.*?)'\s*(#{delimiter}\s*|\z)/) { tag_list << $2; $3 }
88
-
80
+ string.gsub!(/"(.*?)"\s*#{delimiter}?\s*/) { tag_list << $1; "" }
81
+ string.gsub!(/'(.*?)'\s*#{delimiter}?\s*/) { tag_list << $1; "" }
82
+
89
83
  tag_list.add(string.split(delimiter))
90
84
  end
91
85
  end
92
-
86
+
87
+ def from_owner(owner, *tags)
88
+ returning from(*tags) do |taglist|
89
+ taglist.owner = owner
90
+ end
91
+ end
93
92
  end
94
-
95
- end
93
+ end
@@ -1,23 +1,6 @@
1
1
  class Tagging < ActiveRecord::Base #:nodoc:
2
- include ActsAsTaggableOn::ActiveRecord::Backports if ActiveRecord::VERSION::MAJOR < 3
3
-
4
- attr_accessible :tag,
5
- :tag_id,
6
- :context,
7
- :taggable,
8
- :taggable_type,
9
- :taggable_id,
10
- :tagger,
11
- :tagger_type,
12
- :tagger_id
13
-
14
2
  belongs_to :tag
15
3
  belongs_to :taggable, :polymorphic => true
16
- belongs_to :tagger, :polymorphic => true
17
-
4
+ belongs_to :tagger, :polymorphic => true
18
5
  validates_presence_of :context
19
- validates_presence_of :tag_id
20
-
21
- validates_uniqueness_of :tag_id, :scope => [ :taggable_type, :taggable_id, :context, :tagger_id, :tagger_type ]
22
-
23
6
  end
@@ -1,17 +1,11 @@
1
1
  module TagsHelper
2
-
3
2
  # See the README for an example using tag_cloud.
4
3
  def tag_cloud(tags, classes)
5
- tags = tags.all if tags.respond_to?(:all)
6
-
7
- return [] if tags.empty?
8
-
9
4
  max_count = tags.sort_by(&:count).last.count.to_f
10
-
5
+
11
6
  tags.each do |tag|
12
7
  index = ((tag.count / max_count) * (classes.size - 1)).round
13
8
  yield tag, classes[index]
14
9
  end
15
10
  end
16
-
17
- end
11
+ end
@@ -1 +1,6 @@
1
- require 'acts-as-taggable-on'
1
+ require 'acts-as-taggable-on'
2
+
3
+ ActiveRecord::Base.send :include, ActiveRecord::Acts::TaggableOn
4
+ ActiveRecord::Base.send :include, ActiveRecord::Acts::Tagger
5
+
6
+ RAILS_DEFAULT_LOGGER.info "** acts_as_taggable_on: initialized properly."
@@ -1,66 +1,59 @@
1
1
  require File.dirname(__FILE__) + '/../spec_helper'
2
2
 
3
3
  describe "Acts As Taggable On" do
4
- before(:each) do
5
- clean_database!
6
- end
7
-
8
4
  it "should provide a class method 'taggable?' that is false for untaggable models" do
9
5
  UntaggableModel.should_not be_taggable
10
6
  end
11
-
7
+
12
8
  describe "Taggable Method Generation" do
13
9
  before(:each) do
14
10
  [TaggableModel, Tag, Tagging, TaggableUser].each(&:delete_all)
15
11
  @taggable = TaggableModel.new(:name => "Bob Jones")
16
12
  end
17
-
13
+
18
14
  it "should respond 'true' to taggable?" do
19
15
  @taggable.class.should be_taggable
20
16
  end
21
-
17
+
22
18
  it "should create a class attribute for tag types" do
23
19
  @taggable.class.should respond_to(:tag_types)
24
20
  end
25
-
26
- it "should create an instance attribute for tag types" do
27
- @taggable.should respond_to(:tag_types)
28
- end
29
-
30
- it "should have all tag types" do
31
- @taggable.tag_types.should == [:tags, :languages, :skills, :needs, :offerings]
32
- end
33
-
21
+
34
22
  it "should generate an association for each tag type" do
35
23
  @taggable.should respond_to(:tags, :skills, :languages)
36
24
  end
37
-
25
+
26
+ it "should generate a cached column checker for each tag type" do
27
+ TaggableModel.should respond_to(:caching_tag_list?, :caching_skill_list?, :caching_language_list?)
28
+ end
29
+
38
30
  it "should add tagged_with and tag_counts to singleton" do
39
- TaggableModel.should respond_to(:tagged_with, :tag_counts)
31
+ TaggableModel.should respond_to(:find_tagged_with, :tag_counts)
40
32
  end
41
-
33
+
34
+ it "should add saving of tag lists and cached tag lists to the instance" do
35
+ @taggable.should respond_to(:save_cached_tag_list)
36
+ @taggable.should respond_to(:save_tags)
37
+ end
38
+
42
39
  it "should generate a tag_list accessor/setter for each tag type" do
43
40
  @taggable.should respond_to(:tag_list, :skill_list, :language_list)
44
41
  @taggable.should respond_to(:tag_list=, :skill_list=, :language_list=)
45
42
  end
46
-
47
- it "should generate a tag_list accessor, that includes owned tags, for each tag type" do
48
- @taggable.should respond_to(:all_tags_list, :all_skills_list, :all_languages_list)
49
- end
50
43
  end
51
-
44
+
52
45
  describe "Single Table Inheritance" do
53
46
  before do
54
47
  @taggable = TaggableModel.new(:name => "taggable")
55
48
  @inherited_same = InheritingTaggableModel.new(:name => "inherited same")
56
49
  @inherited_different = AlteredInheritingTaggableModel.new(:name => "inherited different")
57
50
  end
58
-
51
+
59
52
  it "should pass on tag contexts to STI-inherited models" do
60
53
  @inherited_same.should respond_to(:tag_list, :skill_list, :language_list)
61
54
  @inherited_different.should respond_to(:tag_list, :skill_list, :language_list)
62
55
  end
63
-
56
+
64
57
  it "should have tag contexts added in altered STI models" do
65
58
  @inherited_different.should respond_to(:part_list)
66
59
  end
@@ -73,112 +66,70 @@ describe "Acts As Taggable On" do
73
66
  found_taggable.save
74
67
  end
75
68
  end
76
-
69
+
77
70
  describe "Related Objects" do
78
71
  it "should find related objects based on tag names on context" do
79
72
  taggable1 = TaggableModel.create!(:name => "Taggable 1")
80
73
  taggable2 = TaggableModel.create!(:name => "Taggable 2")
81
74
  taggable3 = TaggableModel.create!(:name => "Taggable 3")
82
-
75
+
83
76
  taggable1.tag_list = "one, two"
84
77
  taggable1.save
85
-
78
+
86
79
  taggable2.tag_list = "three, four"
87
80
  taggable2.save
88
-
81
+
89
82
  taggable3.tag_list = "one, four"
90
83
  taggable3.save
91
-
84
+
92
85
  taggable1.find_related_tags.should include(taggable3)
93
86
  taggable1.find_related_tags.should_not include(taggable2)
94
87
  end
95
-
88
+
96
89
  it "should find other related objects based on tag names on context" do
97
90
  taggable1 = TaggableModel.create!(:name => "Taggable 1")
98
91
  taggable2 = OtherTaggableModel.create!(:name => "Taggable 2")
99
92
  taggable3 = OtherTaggableModel.create!(:name => "Taggable 3")
100
-
93
+
101
94
  taggable1.tag_list = "one, two"
102
95
  taggable1.save
103
-
96
+
104
97
  taggable2.tag_list = "three, four"
105
98
  taggable2.save
106
-
99
+
107
100
  taggable3.tag_list = "one, four"
108
101
  taggable3.save
109
-
102
+
110
103
  taggable1.find_related_tags_for(OtherTaggableModel).should include(taggable3)
111
104
  taggable1.find_related_tags_for(OtherTaggableModel).should_not include(taggable2)
112
105
  end
113
-
106
+
114
107
  it "should not include the object itself in the list of related objects" do
115
108
  taggable1 = TaggableModel.create!(:name => "Taggable 1")
116
109
  taggable2 = TaggableModel.create!(:name => "Taggable 2")
117
-
118
- taggable1.tag_list = "one"
119
- taggable1.save
120
-
121
- taggable2.tag_list = "one, two"
122
- taggable2.save
123
-
124
- taggable1.find_related_tags.should include(taggable2)
125
- taggable1.find_related_tags.should_not include(taggable1)
126
- end
127
- end
128
110
 
129
- describe "Matching Contexts" do
130
- it "should find objects with tags of matching contexts" do
131
- taggable1 = TaggableModel.create!(:name => "Taggable 1")
132
- taggable2 = TaggableModel.create!(:name => "Taggable 2")
133
- taggable3 = TaggableModel.create!(:name => "Taggable 3")
134
-
135
- taggable1.offering_list = "one, two"
136
- taggable1.save!
137
-
138
- taggable2.need_list = "one, two"
139
- taggable2.save!
140
-
141
- taggable3.offering_list = "one, two"
142
- taggable3.save!
143
-
144
- taggable1.find_matching_contexts(:offerings, :needs).should include(taggable2)
145
- taggable1.find_matching_contexts(:offerings, :needs).should_not include(taggable3)
146
- end
147
-
148
- it "should find other related objects with tags of matching contexts" do
149
- taggable1 = TaggableModel.create!(:name => "Taggable 1")
150
- taggable2 = OtherTaggableModel.create!(:name => "Taggable 2")
151
- taggable3 = OtherTaggableModel.create!(:name => "Taggable 3")
152
-
153
- taggable1.offering_list = "one, two"
154
- taggable1.save
155
-
156
- taggable2.need_list = "one, two"
157
- taggable2.save
158
-
159
- taggable3.offering_list = "one, two"
160
- taggable3.save
161
-
162
- taggable1.find_matching_contexts_for(OtherTaggableModel, :offerings, :needs).should include(taggable2)
163
- taggable1.find_matching_contexts_for(OtherTaggableModel, :offerings, :needs).should_not include(taggable3)
164
- end
165
-
166
- it "should not include the object itself in the list of related objects" do
167
- taggable1 = TaggableModel.create!(:name => "Taggable 1")
168
- taggable2 = TaggableModel.create!(:name => "Taggable 2")
169
-
170
111
  taggable1.tag_list = "one"
171
112
  taggable1.save
172
-
113
+
173
114
  taggable2.tag_list = "one, two"
174
115
  taggable2.save
175
-
116
+
176
117
  taggable1.find_related_tags.should include(taggable2)
177
118
  taggable1.find_related_tags.should_not include(taggable1)
178
119
  end
179
120
  end
180
-
121
+
181
122
  describe 'Tagging Contexts' do
123
+ before(:all) do
124
+ class Array
125
+ def freq
126
+ k=Hash.new(0)
127
+ self.each {|e| k[e]+=1}
128
+ k
129
+ end
130
+ end
131
+ end
132
+
182
133
  it 'should eliminate duplicate tagging contexts ' do
183
134
  TaggableModel.acts_as_taggable_on(:skills, :skills)
184
135
  TaggableModel.tag_types.freq[:skills].should_not == 3
@@ -205,62 +156,10 @@ describe "Acts As Taggable On" do
205
156
  TaggableModel.acts_as_taggable_on([nil])
206
157
  }.should_not raise_error
207
158
  end
208
- end
209
-
210
- describe 'Caching' do
211
- before(:each) do
212
- @taggable = CachedModel.new(:name => "Bob Jones")
213
- end
214
-
215
- it "should add saving of tag lists and cached tag lists to the instance" do
216
- @taggable.should respond_to(:save_cached_tag_list)
217
- @taggable.should respond_to(:save_tags)
218
- end
219
159
 
220
- it "should generate a cached column checker for each tag type" do
221
- CachedModel.should respond_to(:caching_tag_list?)
222
- end
223
-
224
- it 'should not have cached tags' do
225
- @taggable.cached_tag_list.should be_blank
226
- end
227
-
228
- it 'should cache tags' do
229
- @taggable.update_attributes(:tag_list => 'awesome, epic')
230
- @taggable.cached_tag_list.should == 'awesome, epic'
231
- end
232
-
233
- it 'should keep the cache' do
234
- @taggable.update_attributes(:tag_list => 'awesome, epic')
235
- @taggable = CachedModel.find(@taggable)
236
- @taggable.save!
237
- @taggable.cached_tag_list.should == 'awesome, epic'
238
- end
239
-
240
- it 'should update the cache' do
241
- @taggable.update_attributes(:tag_list => 'awesome, epic')
242
- @taggable.update_attributes(:tag_list => 'awesome')
243
- @taggable.cached_tag_list.should == 'awesome'
244
- end
245
-
246
- it 'should remove the cache' do
247
- @taggable.update_attributes(:tag_list => 'awesome, epic')
248
- @taggable.update_attributes(:tag_list => '')
249
- @taggable.cached_tag_list.should be_blank
250
- end
251
-
252
- it 'should have a tag list' do
253
- @taggable.update_attributes(:tag_list => 'awesome, epic')
254
- @taggable = CachedModel.find(@taggable.id)
255
- @taggable.tag_list.sort.should == %w(awesome epic).sort
256
- end
257
-
258
- it 'should keep the tag list' do
259
- @taggable.update_attributes(:tag_list => 'awesome, epic')
260
- @taggable = CachedModel.find(@taggable.id)
261
- @taggable.save!
262
- @taggable.tag_list.sort.should == %w(awesome epic).sort
160
+ after(:all) do
161
+ class Array; remove_method :freq; end
263
162
  end
264
163
  end
265
-
266
- end
164
+
165
+ end