class AsyncExperiments::ExperimentResult

Attributes

duration[R]
key[R]
name[R]
redis[R]
run_output[R]
statsd[R]
type[R]

Public Class Methods

new(name, id, type, redis, statsd, run_output = nil, duration = nil) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 8
def initialize(name, id, type, redis, statsd, run_output = nil, duration = nil)
  @name = name
  @key = "#{name}:#{id}"
  @redis = redis
  @statsd = statsd
  @type = type
  @run_output = run_output
  @duration = duration

  if Util.blank?(duration)
    redis_data = data_from_redis

    if redis_data
      @run_output ||= redis_data.fetch(:run_output)
      @duration ||= redis_data.fetch(:duration)
    end
  end
end

Public Instance Methods

available?() click to toggle source
# File lib/async_experiments/experiment_result.rb, line 44
def available?
  Util.present?(duration)
end
process_run_output(candidate, expiry) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 38
def process_run_output(candidate, expiry)
  variation = HashDiff.diff(sort(self.run_output), sort(candidate.run_output))
  report_data(variation, candidate, expiry)
  redis.del("experiments:#{key}:candidate")
end
store_run_output(expiry) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 29
def store_run_output(expiry)
  redis_key = "experiments:#{key}:#{type}"
  redis.set(redis_key, {
    run_output: run_output,
    duration: duration,
  }.to_json)
  redis.expire(redis_key, expiry)
end

Private Instance Methods

data_from_redis() click to toggle source
# File lib/async_experiments/experiment_result.rb, line 54
def data_from_redis
  redis_data = redis.get("experiments:#{key}:#{type}")

  if Util.present?(redis_data)
    Util.deep_symbolize_keys(JSON.parse(redis_data))
  end
end
report_data(variation, candidate, expiry) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 62
def report_data(variation, candidate, expiry)
  statsd.timing("experiments.#{name}.control", self.duration)
  statsd.timing("experiments.#{name}.candidate", candidate.duration)

  if variation != []
    statsd.increment("experiments.#{name}.mismatches")
    store_mismatch(variation, expiry)
  end
end
sort(object) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 80
def sort(object)
  case object
  when Array
    object.sort_by(&:object_id)
  when Hash
    object.each_with_object({}) { |(key, value), hash|
      hash[key] = sort(value)
    }
  else
    object
  end
end
store_mismatch(mismatch, expiry) click to toggle source
# File lib/async_experiments/experiment_result.rb, line 72
def store_mismatch(mismatch, expiry)
  json = JSON.dump(mismatch)
  hash = Digest::SHA2.base64digest(json)
  redis_key = "experiments:#{name}:mismatches:#{hash}"
  redis.set(redis_key, json) unless redis.exists(redis_key)
  redis.expire(redis_key, expiry)
end