Module: EvenBetterNestedSet::NestedSet

Defined in:
lib/eb_nested_set.rb

Defined Under Namespace

Modules: ClassMethods

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.included(base) ⇒ Object



58
59
60
61
# File 'lib/eb_nested_set.rb', line 58

def self.included(base)
  super
  base.extend ClassMethods
end

Instance Method Details

#ancestors(force_reload = false) ⇒ Array[ActiveRecord::Base]

Returns a list of ancestors this node belongs to

Parameters:

  • force_reload (Boolean) (defaults to: false)

    forces the list to be reloaded

Returns:

  • (Array[ActiveRecord::Base])

    a list of nodes that this node descends from



218
219
220
221
222
223
224
# File 'lib/eb_nested_set.rb', line 218

def ancestors(force_reload=false)
  @ancestors = nil if force_reload
  @ancestors ||= base_class.find(
    :all,:conditions => ["#{nested_set_column(:left)} < ? AND #{nested_set_column(:right)} > ?", left, right],
    :order => "#{nested_set_column(:left)} DESC"
  )
end

#boundsRange

Returns the left to the right boundary of this node.

Returns:

  • (Range)

    the left to the right boundary of this node



323
324
325
# File 'lib/eb_nested_set.rb', line 323

def bounds
  left..right
end

#cache_children(*nodes) ⇒ Object

Caches the nodes as this node’s children.



351
352
353
354
# File 'lib/eb_nested_set.rb', line 351

def cache_children(*nodes) #:nodoc:
  @cached_children ||= []
  children.target = @cached_children.push(*nodes)
end

#cache_nested_setObject

Caches the children of this node



257
258
259
# File 'lib/eb_nested_set.rb', line 257

def cache_nested_set
  @cached_children || base_class.sort_nodes_to_nested_set(family)
end

#cache_parent(parent) ⇒ Object

Caches the node as this node’s parent.



344
345
346
# File 'lib/eb_nested_set.rb', line 344

def cache_parent(parent) #:nodoc:
  self.parent = parent
end

#descendant_of?(node) ⇒ Boolean

Checks if this node is a descendant of node

Parameters:

  • node (ActiveRecord::Base)

    the node to check agains

Returns:

  • (Boolean)

    whether this node is a descendant



192
193
194
# File 'lib/eb_nested_set.rb', line 192

def descendant_of?(node)
  node.left < self.left && self.right < node.right
end

#descendantsArray[ActiveRecord::Base]

Returns all nodes that descend from this node

Returns:

  • (Array[ActiveRecord::Base])


250
251
252
# File 'lib/eb_nested_set.rb', line 250

def descendants
  base_class.descendants(self)
end

#familyArray[ActiveRecord::Base]

Returns the node and all nodes that descend from it.

Returns:

  • (Array[ActiveRecord::Base])


266
267
268
# File 'lib/eb_nested_set.rb', line 266

def family
  [self, *descendants]
end

#family_ids(force_reload = false) ⇒ Array[Integer]

Returns the ids of the node and all nodes that descend from it.

Returns:

  • (Array[Integer])


275
276
277
278
279
280
281
282
283
284
285
# File 'lib/eb_nested_set.rb', line 275

def family_ids(force_reload=false)
  return @family_ids unless @family_ids.nil? or force_reload
  
  transaction do
    reload_boundaries
    query = "SELECT id FROM #{self.class.quote_db_property(base_class.table_name)} " + 
            "WHERE #{nested_set_column(:left)} >= #{left} AND #{nested_set_column(:right)} <= #{right} " +
            "ORDER BY #{nested_set_column(:left)}"
    @family_ids = base_class.connection.select_values(query).map(&:to_i)
  end
end

#generationArray[ActiveRecord::Base]

Returns all nodes that share the same parent as this node.

Returns:

  • (Array[ActiveRecord::Base])


292
293
294
# File 'lib/eb_nested_set.rb', line 292

def generation
  root? ? base_class.roots : parent.children
end

#kinArray[ActiveRecord::Base]

Returns all nodes that descend from the same root node as this node

Returns:

  • (Array[ActiveRecord::Base])


241
242
243
# File 'lib/eb_nested_set.rb', line 241

def kin
  patriarch.family
end

#leftInteger

Returns the left boundary of this node.

Returns:

  • (Integer)

    the left boundary of this node



330
331
332
# File 'lib/eb_nested_set.rb', line 330

def left
  read_attribute(self.class.nested_set_options[:left])
end

#levelInteger

Returns how deeply this node is nested, that is how many ancestors it has.

Returns:

  • (Integer)

    the number of ancestors of this node.



310
311
312
313
314
315
316
317
318
# File 'lib/eb_nested_set.rb', line 310

def level
  if root?
    0
  elsif @ancestors
    @ancestors.size
  else
    base_class.count :conditions => ["#{nested_set_column(:left)} < ? AND #{nested_set_column(:right)} > ?", left, right]
  end
end

#lineage(force_reload = false) ⇒ Array[ActiveRecord::Base]

Returns a list of the node itself and all of its ancestors

Parameters:

  • force_reload (Boolean) (defaults to: false)

    forces the list to be reloaded

Returns:

  • (Array[ActiveRecord::Base])

    a list of nodes that this node descends from



232
233
234
# File 'lib/eb_nested_set.rb', line 232

def lineage(force_reload=false)
  [self, *ancestors(force_reload)]
end

#recalculate_nested_set(left) ⇒ Object

Rebuild this node’s childrens boundaries



359
360
361
362
363
364
365
366
367
368
# File 'lib/eb_nested_set.rb', line 359

def recalculate_nested_set(left) #:nodoc:
  child_left = left + 1
  children.each do |child|
    child_left = child.recalculate_nested_set(child_left)
  end
  set_boundaries(left, child_left)
  save_without_validation!
  
  right + 1
end

#rightInteger

Returns the right boundary of this node.

Returns:

  • (Integer)

    the right boundary of this node



337
338
339
# File 'lib/eb_nested_set.rb', line 337

def right
  read_attribute(self.class.nested_set_options[:right])
end

#root(force_reload = nil) ⇒ ActiveRecord::Base Also known as: patriarch

Finds the root node that this node descends from

Parameters:

  • force_reload (Boolean) (defaults to: nil)

    forces the root node to be reloaded

Returns:

  • (ActiveRecord::Base)

    node the root node this descends from



202
203
204
205
206
207
208
# File 'lib/eb_nested_set.rb', line 202

def root(force_reload=nil)
  @root = nil if force_reload
  @root ||= transaction do
    reload_boundaries
    base_class.roots.find(:first, :conditions => ["#{nested_set_column(:left)} <= ? AND #{nested_set_column(:right)} >= ?", left, right])
  end
end

#root?Boolean

Checks if this root is a root node

Returns:

  • (Boolean)

    whether this node is a root node or not



182
183
184
# File 'lib/eb_nested_set.rb', line 182

def root?
  not parent_id?
end

#siblingsArray[ActiveRecord::Base]

Returns all nodes that are siblings of this node

Returns:

  • (Array[ActiveRecord::Base])


301
302
303
# File 'lib/eb_nested_set.rb', line 301

def siblings
  generation - [self]
end