Class: CreatedId::IdRange

Inherits:
ActiveRecord::Base
  • Object
show all
Defined in:
lib/created_id/id_range.rb

Overview

This model stores the id ranges for other models by the hour. It is not meant to be accessed directly.

Class Method Summary collapse

Class Method Details

.id_range(klass, time) ⇒ Array<Integer>

Get the minimum and maximum ids for a model created in a given hour. This method is used in indexing the ranges.

Parameters:

  • klass (Class)

    The class to get the id range for.

  • time (Time)

    The hour to get the id range for.

Returns:

  • (Array<Integer>)

    The minimum and maximum ids for the class created in the given hour.



67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
# File 'lib/created_id/id_range.rb', line 67

def id_range(klass, time)
  klass = klass.base_class
  hour = CreatedId.coerce_hour(time)
  next_hour = hour + 3600

  finder = klass.unscoped.where(created_at: (hour...next_hour))

  prev_id = CreatedId::IdRange.min_id(klass, hour)
  if prev_id
    finder = finder.where(klass.arel_table[:id].gt(prev_id)) if prev_id > 0
  end

  next_id = CreatedId::IdRange.min_id(klass, next_hour + 3600)
  if next_id && (prev_id.nil? || next_id > prev_id)
    finder = finder.where(klass.arel_table[:id].lt(next_id))
  end

  [finder.minimum(:id), finder.maximum(:id)]
end

.max_id(klass, time, allow_nil: false) ⇒ Integer?

Get the maximum id for a class created in a given hour.

Parameters:

  • klass (Class)

    The class to get the maximum id for.

  • time (Time)

    The hour to get the maximum id for.

  • allow_nil (Boolean) (defaults to: false)

    Whether to allow a nil value to be returned. If this is false, then the method will return the maximum possible id for the id column.

Returns:

  • (Integer, nil)

    The maximum id for the class created in the given hour.



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
# File 'lib/created_id/id_range.rb', line 44

def max_id(klass, time, allow_nil: false)
  return nil if time.nil? && allow_nil

  id = for_class(klass).created_after(CreatedId.coerce_hour(time)).order(hour: :asc).first&.max_id

  if id.nil? && !allow_nil
    col_limit = klass.columns.detect { |c| c.name == klass.primary_key }.limit
    id = if col_limit && col_limit > 0
      ((256**col_limit) / 2) - 1
    else
      klass.base_class.unscoped.maximum(:id).to_i
    end
  end

  id
end

.min_id(klass, time, allow_nil: false) ⇒ Integer?

Get the minimum id for a class created in a given hour.

Parameters:

  • klass (Class)

    The class to get the minimum id for.

  • time (Time)

    The hour to get the minimum id for.

  • allow_nil (Boolean) (defaults to: false)

    Whether to allow a nil value to be returned. If this is false, then the method will return 0 if no value is found.

Returns:

  • (Integer, nil)

    The minimum id for the class created in the given hour.



29
30
31
32
33
34
35
# File 'lib/created_id/id_range.rb', line 29

def min_id(klass, time, allow_nil: false)
  return nil if time.nil? && allow_nil

  id = for_class(klass).created_before(time).order(hour: :desc).first&.min_id
  id ||= 0 unless allow_nil
  id
end

.save_created_id(klass, time, min_id, max_id) ⇒ void

This method returns an undefined value.

Save the minimum and maximum ids for a class created in a given hour.

Parameters:

  • klass (Class)

    The class to save the id range for.

  • time (Time)

    The hour to save the id range for.

  • min_id (Integer)

    The minimum id for the class created in the given hour.

  • max_id (Integer)

    The maximum id for the class created in the given hour.



94
95
96
97
98
99
# File 'lib/created_id/id_range.rb', line 94

def save_created_id(klass, time, min_id, max_id)
  record = find_or_initialize_by(class_name: klass.base_class.name, hour: CreatedId.coerce_hour(time))
  record.min_id = min_id
  record.max_id = max_id
  record.save!
end