diff --git a/lib/mongoid_nested_set/base.rb b/lib/mongoid_nested_set/base.rb index 57e43d9..4ce7eda 100644 --- a/lib/mongoid_nested_set/base.rb +++ b/lib/mongoid_nested_set/base.rb @@ -53,7 +53,11 @@ def acts_as_nested_set(options = {}) attr_accessor :skip_before_destroy - if accessible_attributes.blank? + # Rails 4 no longer uses "attr_protected" and "attr_accessible" for + # mass assignment control by default, but this methods can be restored + # by installing 'protected_attributes' gem. So here we just check + # accessible_attributes method presence + if respond_to?(:accessible_attributes) && accessible_attributes.blank? attr_protected left_field_name.intern, right_field_name.intern end diff --git a/lib/mongoid_nested_set/update.rb b/lib/mongoid_nested_set/update.rb index 12d688a..0b8916f 100755 --- a/lib/mongoid_nested_set/update.rb +++ b/lib/mongoid_nested_set/update.rb @@ -153,7 +153,7 @@ def move_to(target, position) ).update_all("$inc" => { right_field_name => -width }) end - self.set(parent_field_name, new_parent) + self.mongoid_set(parent_field_name, new_parent) self.reload_nested_set self.update_self_and_descendants_depth @@ -188,7 +188,7 @@ def update_depth def update_self_and_descendants_depth if depth? scope_class.each_with_level(self_and_descendants) do |node, level| - node.with(:safe => true).set(:depth, level) unless node.depth == level + node.with(:safe => true).mongoid_set(:depth, level) unless node.depth == level end self.reload end @@ -214,17 +214,37 @@ def destroy_descendants # update lefts and rights for remaining nodes diff = right - left + 1 - scope_class.with(:safe => true).where( + c = scope_class.with(:safe => true).where( nested_set_scope.where(left_field_name.to_sym.gt => right).selector - ).inc(left_field_name, -diff) + ) + mongoid_inc(c, left_field_name, -diff) - scope_class.with(:safe => true).where( + c = scope_class.with(:safe => true).where( nested_set_scope.where(right_field_name.to_sym.gt => right).selector - ).inc(right_field_name, -diff) + ) + mongoid_inc(c, right_field_name, -diff) # Don't allow multiple calls to destroy to corrupt the set self.skip_before_destroy = true end + # Compatibility wrapper for mongoid set method, should works with 3.x.x and + # 4.x.x versions + def mongoid_set(field, value) + if method(:set).arity == 1 + set({field => value}) + else + set(field, value) + end + end + + def mongoid_inc(criteria, field, value) + if criteria.method(:inc).arity == 2 + criteria.inc(field, value) + else + criteria.inc({field => value}) + end + end + end end