Class: Dbd::TimeStamp
- Inherits:
-
Object
- Object
- Dbd::TimeStamp
- Defined in:
- lib/dbd/time_stamp.rb
Overview
TimeStamp
Each Fact has a time_stamp with a granularity of 1 ns. The small granularity is essential to allow enough “density” of Facts in a large fact stream. Since all Facts need to have a strictly monotonically increasing time_stamp, this causes a limitation of max 1_000_000_000 Facts per second in a fact stream.
A second reason for a fine grained granularity of the time_stamp is to reduce the chance (but not to zero) for collisions between Facts when 2 (or more) fact streams with overlapping time ranges need to be merged. But, collisions are always possible and need to be handled (since this can be expensive, we need to avoid them).
A practicaly problem with calculating a “randomized” time_stamp is that the system reports a Wall clock with a granularity of 1 us on MRI Ruby and only 1 ms on JRuby (see JSR 310). To solve this problem, some nifty tricks are needed to create more “randomized” time_stamps, while still guaranteeing, the strictly monotonic increase in an upredictable fact stream.
Performance measurements show a typical 30 - 60 us delay between the consecutive created facts (on MRI and JRuby), so a randomization of e.g. 1 - 999 ns should not cause fundamental problems for the density of the facts (even if computers speed up a factor of 30 or an implementation in a faster language). Still this is an ad-hoc optimization at creation time and can be optimized without breaking the specification of the fact stream.
A time_stamp does not need to represent the exact time of the creation of the fact, it only has to increase strictly monotic in a fact stream.
Constant Summary collapse
- MAX_DRIFT =
Max drift in time_stamp for near?
Rational("1/1_000_000").freeze
Instance Attribute Summary collapse
-
#time ⇒ Object
readonly
Returns the value of attribute time.
Class Method Summary collapse
-
.valid_regexp ⇒ Object
regexp for the nanosecond granularity and in UTC.
Instance Method Summary collapse
- #+(seconds) ⇒ Object
- #-(other) ⇒ Object
- #<(other) ⇒ Object
- #<=(other) ⇒ Object
- #>(other) ⇒ Object
- #>=(other) ⇒ Object
-
#initialize(options = {}) ⇒ TimeStamp
constructor
Builds a new TimeStamp.
-
#near?(other) ⇒ Boolean
determines if 2 time_stamps are “near”.
-
#to_s ⇒ Object
with a nanosecond granularity and in UTC.
Constructor Details
#initialize(options = {}) ⇒ TimeStamp
Builds a new TimeStamp.
47 48 49 50 |
# File 'lib/dbd/time_stamp.rb', line 47 def initialize(={}) @time = [:time] || new_time([:larger_than]) @time = time_from_s(@time) if @time.is_a?(String) end |
Instance Attribute Details
#time ⇒ Object (readonly)
Returns the value of attribute time.
39 40 41 |
# File 'lib/dbd/time_stamp.rb', line 39 def time @time end |
Class Method Details
.valid_regexp ⇒ Object
regexp for the nanosecond granularity and in UTC
Can be used to validate input strings or in tests.
56 57 58 |
# File 'lib/dbd/time_stamp.rb', line 56 def self.valid_regexp /\A\d{4}-\d\d-\d\d \d\d:\d\d:\d\d\.\d{9} UTC\Z/ end |
Instance Method Details
#+(seconds) ⇒ Object
142 143 144 |
# File 'lib/dbd/time_stamp.rb', line 142 def +(seconds) self.class.new(time: (@time + seconds)) end |
#-(other) ⇒ Object
146 147 148 |
# File 'lib/dbd/time_stamp.rb', line 146 def -(other) @time - other.time end |
#<(other) ⇒ Object
130 131 132 |
# File 'lib/dbd/time_stamp.rb', line 130 def <(other) @time < other.time end |
#<=(other) ⇒ Object
138 139 140 |
# File 'lib/dbd/time_stamp.rb', line 138 def <=(other) @time <= other.time end |
#>(other) ⇒ Object
126 127 128 |
# File 'lib/dbd/time_stamp.rb', line 126 def >(other) @time > other.time end |
#>=(other) ⇒ Object
134 135 136 |
# File 'lib/dbd/time_stamp.rb', line 134 def >=(other) @time >= other.time end |
#near?(other) ⇒ Boolean
determines if 2 time_stamps are “near”.
The time_stamp of an equivalent fact may be slightly different (because shifts of a few nanoseconds will be required to resolve collisions on a merge of fact streams with overlapping time_stamp ranges).
122 123 124 |
# File 'lib/dbd/time_stamp.rb', line 122 def near?(other) (self - other).abs <= MAX_DRIFT end |
#to_s ⇒ Object
with a nanosecond granularity and in UTC
108 109 110 |
# File 'lib/dbd/time_stamp.rb', line 108 def to_s @time.strftime(time_format) end |