Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
10 changed files
with
186 additions
and
198 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
module Von | ||
module Counters | ||
class Best | ||
|
||
def initialize(field, periods = nil) | ||
@field = field.to_sym | ||
@periods = periods || [] | ||
end | ||
|
||
def hash_key | ||
@hash_key ||= "#{Von.config.namespace}:counters:bests:#{@field}" | ||
end | ||
|
||
def best_total(period) | ||
Von.connection.hget("#{hash_key}:#{period}:best", 'total').to_i | ||
end | ||
|
||
def best_timestamp(period) | ||
Von.connection.hget("#{hash_key}:#{period}:best", 'timestamp') | ||
end | ||
|
||
def current_total(period) | ||
Von.connection.hget("#{hash_key}:#{period}:current", 'total').to_i | ||
end | ||
|
||
def current_timestamp(period) | ||
Von.connection.hget("#{hash_key}:#{period}:current", 'timestamp') | ||
end | ||
|
||
def increment | ||
return if @periods.empty? | ||
|
||
@periods.each do |period| | ||
# TODO: subclass counter (or somethin) and add hincrby/etc helpers | ||
_current_timestamp = current_timestamp(period) | ||
_current_total = current_total(period) | ||
|
||
if period.timestamp != _current_timestamp | ||
# changing current period | ||
Von.connection.hset("#{hash_key}:#{period}:current", 'total', 1) | ||
Von.connection.hset("#{hash_key}:#{period}:current", 'timestamp', period.timestamp) | ||
|
||
if best_total(period) < _current_total | ||
Von.connection.hset("#{hash_key}:#{period}:best", 'total', _current_total) | ||
Von.connection.hset("#{hash_key}:#{period}:best", 'timestamp', _current_timestamp) | ||
end | ||
else | ||
Von.connection.hincrby("#{hash_key}:#{period}:current", 'total', 1) | ||
end | ||
end | ||
end | ||
|
||
def count(period) | ||
if current_timestamp > best_timestamp | ||
{ current_timestamp => current_total } | ||
else | ||
{ best_timestamp => best_total } | ||
end | ||
end | ||
|
||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
module Von | ||
module Counters | ||
class Period | ||
|
||
def initialize(field, periods = nil) | ||
@field = field.to_sym | ||
@periods = periods || [] | ||
end | ||
|
||
# Returns the Redis hash key used for storing counts for this Period | ||
def hash_key(period) | ||
"#{Von.config.namespace}:counters:#{@field}:#{period}" | ||
end | ||
|
||
# Returns the Redis list key used for storing current "active" counters | ||
def list_key(period) | ||
"#{Von.config.namespace}:lists:#{@field}:#{period}" | ||
end | ||
|
||
def increment | ||
return if @periods.empty? | ||
|
||
@periods.each do |period| | ||
_hash_key = hash_key(period) | ||
_list_key = list_key(period) | ||
|
||
Von.connection.hincrby(_hash_key, period.timestamp, 1) | ||
|
||
unless Von.connection.lrange(_list_key, 0, -1).include?(period.timestamp) | ||
Von.connection.rpush(_list_key, period.timestamp) | ||
end | ||
|
||
if Von.connection.llen(_list_key) > period.length | ||
expired_counter = Von.connection.lpop(_list_key) | ||
Von.connection.hdel(_hash_key, expired_counter) | ||
end | ||
end | ||
end | ||
|
||
# Count the fields for the given time period for this Counter. | ||
# | ||
# Returns an Array of Hashes representing the count | ||
def count(period) | ||
return if @periods.empty? | ||
|
||
counts = [] | ||
this_period = nil | ||
_period = @periods.select { |p| p.period == period }.first | ||
|
||
_period.length.times do |i| | ||
this_period = _period.prev(i) | ||
counts.unshift(this_period) | ||
end | ||
|
||
keys = Von.connection.hgetall(hash_key(period)) | ||
counts.map { |date| { date => keys.fetch(date, 0).to_i }} | ||
end | ||
|
||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
module Von | ||
module Counters | ||
class Total | ||
attr_reader :field | ||
|
||
# Initialize a new Counter | ||
# | ||
# field - counter field name | ||
def initialize(field) | ||
@field = field.to_sym | ||
end | ||
|
||
# Returns the Redis hash key used for storing counts for this Counter | ||
def hash_key | ||
"#{Von.config.namespace}:counters:#{@field}" | ||
end | ||
|
||
# Increment the total count for this Counter | ||
# If the key has time periods specified, increment those. | ||
# | ||
# Returns the Integer total for the key | ||
def increment | ||
Von.connection.hincrby(hash_key, 'total', 1).to_i | ||
end | ||
|
||
# Count the "total" field for this Counter. | ||
# | ||
# Returns an Integer count | ||
def count | ||
count = Von.connection.hget(hash_key, 'total') | ||
count.nil? ? 0 : count.to_i | ||
end | ||
|
||
# Lookup the count for this Counter in Redis. | ||
# If a Period argument is given we lookup the count for | ||
# all of the possible units (not expired), zeroing ones that | ||
# aren't set in Redis already. | ||
# | ||
# period - A Period to lookup | ||
# | ||
# Returns an Integer representing the count or an Array of counts. | ||
def self.count(field) | ||
Counter.new(field).count | ||
end | ||
|
||
end | ||
end | ||
end |
Oops, something went wrong.