@@ -17,31 +17,61 @@ def self.included(base)
1717 end
1818 end
1919
20+ attr_accessor :encoded_id_memoized_with_id
21+
22+ def clear_encoded_id_cache!
23+ [ :@encoded_id_hash , :@encoded_id , :@slugged_encoded_id ] . each do |var |
24+ remove_instance_variable ( var ) if instance_variable_defined? ( var )
25+ end
26+ self . encoded_id_memoized_with_id = nil
27+ end
28+
29+ def check_and_clear_memoization
30+ clear_encoded_id_cache! if encoded_id_memoized_with_id && encoded_id_memoized_with_id != id
31+ end
32+
2033 def encoded_id_hash
2134 return unless id
22- return @encoded_id_hash if defined? ( @encoded_id_hash ) && !id_changed?
23- self . class . encode_encoded_id ( id )
35+ check_and_clear_memoization
36+ return @encoded_id_hash if defined? ( @encoded_id_hash )
37+
38+ self . encoded_id_memoized_with_id = id
39+ @encoded_id_hash = self . class . encode_encoded_id ( id )
2440 end
2541
2642 def encoded_id
2743 return unless id
28- return @encoded_id if defined? ( @encoded_id ) && !id_changed?
44+ check_and_clear_memoization
45+ return @encoded_id if defined? ( @encoded_id )
46+
2947 encoded = encoded_id_hash
3048 annotated_by = EncodedId ::Rails . configuration . annotation_method_name
3149 return @encoded_id = encoded unless annotated_by && encoded
50+
3251 separator = EncodedId ::Rails . configuration . annotated_id_separator
52+ self . encoded_id_memoized_with_id = id
3353 @encoded_id = EncodedId ::Rails ::AnnotatedId . new ( id_part : encoded , annotation : send ( annotated_by . to_s ) , separator : separator ) . annotated_id
3454 end
3555
3656 def slugged_encoded_id
3757 return unless id
38- return @slugged_encoded_id if defined? ( @slugged_encoded_id ) && !id_changed?
58+ check_and_clear_memoization
59+ return @slugged_encoded_id if defined? ( @slugged_encoded_id )
60+
3961 with = EncodedId ::Rails . configuration . slug_value_method_name
4062 separator = EncodedId ::Rails . configuration . slugged_id_separator
4163 encoded = encoded_id
4264 return unless encoded
65+
66+ self . encoded_id_memoized_with_id = id
4367 @slugged_encoded_id = EncodedId ::Rails ::SluggedId . new ( id_part : encoded , slug_part : send ( with . to_s ) , separator : separator ) . slugged_id
4468 end
69+
70+ def reload ( options = nil )
71+ result = super
72+ clear_encoded_id_cache!
73+ result
74+ end
4575
4676 # By default the annotation is the model name (it will be parameterized)
4777 def annotation_for_encoded_id
@@ -57,11 +87,10 @@ def name_for_encoded_id_slug
5787 raise StandardError , "You must define a method to generate the slug for the encoded ID of #{ self . class . name } "
5888 end
5989
60- # When duplicating an ActiveRecord object, we want to reset the memoized encoded_id
90+ # When duplicating an ActiveRecord object, we want to reset the memoized encoded IDs
6191 def dup
6292 super . tap do |new_record |
63- new_record . send ( :remove_instance_variable , :@encoded_id ) if new_record . instance_variable_defined? ( :@encoded_id )
64- new_record . send ( :remove_instance_variable , :@slugged_encoded_id ) if new_record . instance_variable_defined? ( :@slugged_encoded_id )
93+ new_record . clear_encoded_id_cache!
6594 end
6695 end
6796 end
0 commit comments