Module: Farce::Clock

Extended by:
Clock
Included in:
Clock
Defined in:
lib/farce/clock.rb,
lib/farce/integrations/active_support/clock.rb

Overview

Wrapper module for clock-related functionality. Converts everything to a monotonic clock time in seconds, from when farce/clock was loaded.

See Also:

ActiveSupport Integration collapse

Instance Method Summary collapse

Class Method Details

.parse(value) ⇒ BasicObject

Note:

This methods is only available if ActiveSupport has been loaded.

Treat ActiveSupport durations as relative offsets.



12
13
14
15
# File 'lib/farce/integrations/active_support/clock.rb', line 12

def self.parse(value)
  return offset(value) if ActiveSupport::Duration === value
  super
end

Instance Method Details

#clock(value) ⇒ Float

Converts the given value to a monotonic clock time in seconds, assuming that it already represents a clock time. Returns the current clock time if no value is given.

Same as calling parse(clock: value)

Parameters:

  • value (nil, #to_f) —

    the value to convert to clock time

Returns:

  • (Float) —

    the clock time in seconds

Raises:

  • (ArgumentError) —

    if the resulting clock time is NaN



28
# File 'lib/farce/clock.rb', line 28

def clock(value) = validate_timestamp(value ? value.to_f : current)

#current ⇒ Float

Returns the current monotonic clock time in seconds.

Returns:

  • (Float) —

    the clock time in seconds



32
# File 'lib/farce/clock.rb', line 32

def current = Process.clock_gettime(CLOCK_MONOTONIC) - MONOTONIC

#offset(value) ⇒ Float

Converts the given value to a monotonic clock time in seconds. The value is assumed to be a relative offset from the current time.

Parameters:

  • value (Numeric) —

    the value to convert to clock time

Returns:

  • (Float) —

    the clock time in seconds

Raises:

  • (ArgumentError) —

    if the resulting clock time is NaN



113
114
115
116
# File 'lib/farce/clock.rb', line 113

def offset(value)
  return validate_timestamp(current + value.to_f) if value.is_a?(Numeric)
  raise TypeError, "Cannot convert #{value.class} to clock time"
end

#parse(value = nil) ⇒ Float

Converts the given value to a monotonic clock time in seconds.

Parameters:

  • value (nil, Numeric, Time, ActiveSupport::Duration, Hash) (defaults to: nil) —

    The value to convert to clock time

    If the value is nil, it is treated as the current time.

    ActiveSupport durations are relative offsets when the ActiveSupport integration is loaded.

    Other numeric values use the following cutoffs:

    • Up to 600 (10 minutes): Offsets from the current time.
    • Greater than 600, up to one billion: Clock times (like the value returned by #current).
    • Greater than one billion: UNIX timestamps (like the value returned by Time.now.to_f).

    Hashes may contain up to one key-value pair, with the key being one of the following:

Returns:

  • (Float) —

    the clock time in seconds

Raises:

  • (ArgumentError) —

    if the resulting clock time is NaN



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

def parse(value = nil)
  case value
  when nil, UNDEFINED then return current
  when Float, Integer then return value > CUTOFF_CLOCK ? time(value) : offset(value)
  when Time           then return time(value)
  when Hash
    case value.size
    when 0 then return current
    when 1
      return time(value[:at]) if value.key?(:at)
      method = argument = nil
      value.each_pair { |key, option| method, argument = key, option }
      return public_send(method, argument)
    end
  else
    return at(value.to_time) if value.respond_to?(:to_time)
    return parse(value.to_f) if value.is_a?(Numeric)
  end
  raise TypeError, "Cannot convert #{value.inspect} to clock time"
end

#remaining(deadline) ⇒ Float, ...

Returns the seconds left until a monotonic clock deadline. Expired deadlines return zero. Nil means there is no deadline and returns nil.

Parameters:

  • deadline (Numeric, nil) —

    a deadline from #clock or #timeout

Returns:

  • (Float, Integer, nil) —

    the remaining seconds, zero, or nil

Raises:

  • (ArgumentError) —

    if the deadline is NaN



40
41
42
43
44
# File 'lib/farce/clock.rb', line 40

def remaining(deadline)
  return if deadline.nil?
  remaining = validate_timestamp(deadline - now)
  remaining.positive? ? remaining : 0
end

#time(value) ⇒ Float

Converts the given value to a monotonic clock time in seconds. The value is assumed to be a fixed point in time (independent of the current time).

If the value is numeric and greater than one billion, it is treated as a UNIX timestamp. Meaning that you can't pass a clock time greater than 31 years, or a timestamp before September 9, 2001.

Parameters:

  • value (Numeric, Time) —

    the value to convert to clock time

Returns:

  • (Float) —

    the clock time in seconds

Raises:

  • (ArgumentError) —

    if the resulting clock time is NaN



97
98
99
100
101
102
103
104
105
# File 'lib/farce/clock.rb', line 97

def time(value)
  case value
  when Float, Integer then timestamp = value > CUTOFF_TIME ? value - REAL_TIME : Float(value)
  when Time           then timestamp = value.to_f - REAL_TIME
  when Numeric        then return time(value.to_f)
  else raise TypeError, "Cannot convert #{value.class} to clock time"
  end
  validate_timestamp(timestamp)
end