class Vanity::Adapters::RedisAdapter

Redis adapter.

@since 1.4.0

Attributes

redis[R]

Public Class Methods

new(options) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 31
def initialize(options)
  @options = options.clone
  @options[:db] ||= @options[:database] || (@options[:path] && @options.delete(:path).split("/")[1].to_i)
  @options[:thread_safe] = true
  connect!
end

Public Instance Methods

ab_add_conversion(experiment, alternative, identity, count = 1, implicit = false) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 198
def ab_add_conversion(experiment, alternative, identity, count = 1, implicit = false)
  call_redis_with_failover(experiment, alternative, identity, count, implicit) do
    if implicit
      @experiments.sadd "#{experiment}:alts:#{alternative}:participants", identity
    else
      participating = @experiments.sismember("#{experiment}:alts:#{alternative}:participants", identity)
    end
    @experiments.sadd "#{experiment}:alts:#{alternative}:converted", identity if implicit || participating
    @experiments.incrby "#{experiment}:alts:#{alternative}:conversions", count
  end
end
ab_add_participant(experiment, alternative, identity) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 168
def ab_add_participant(experiment, alternative, identity)
  call_redis_with_failover(experiment, alternative, identity) do
    @experiments.sadd "#{experiment}:alts:#{alternative}:participants", identity
  end
end
ab_assigned(experiment, identity) click to toggle source

Returns the participant's seen alternative in this experiment, if it exists

# File lib/vanity/adapters/redis_adapter.rb, line 187
def ab_assigned(experiment, identity)
  call_redis_with_failover do
    Vanity.playground.experiments[experiment].alternatives.each do |alternative|
      if @experiments.sismember "#{experiment}:alts:#{alternative.id}:participants", identity
        return alternative.id
      end
    end
    nil
  end
end
ab_counts(experiment, alternative) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 141
def ab_counts(experiment, alternative)
  {
    :participants => @experiments.scard("#{experiment}:alts:#{alternative}:participants").to_i,
          :converted    => @experiments.scard("#{experiment}:alts:#{alternative}:converted").to_i,
    :conversions  => @experiments.get("#{experiment}:alts:#{alternative}:conversions").to_i
  }
end
ab_get_outcome(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 210
def ab_get_outcome(experiment)
  alternative = @experiments.get("#{experiment}:outcome")
  alternative && alternative.to_i
end
ab_not_showing(experiment, identity) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 162
def ab_not_showing(experiment, identity)
  call_redis_with_failover do
    @experiments.del "#{experiment}:participant:#{identity}:show"
  end
end
ab_seen(experiment, identity, alternative_or_id) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 174
def ab_seen(experiment, identity, alternative_or_id)
  with_ab_seen_deprecation(experiment, identity, alternative_or_id) do |expt, ident, alt_id|
    call_redis_with_failover(expt, ident, alt_id) do
      if @experiments.sismember "#{expt}:alts:#{alt_id}:participants", ident
        alt_id
      else
        nil
      end
    end
  end
end
ab_set_outcome(experiment, alternative = 0) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 215
def ab_set_outcome(experiment, alternative = 0)
  @experiments.setnx "#{experiment}:outcome", alternative
end
ab_show(experiment, identity, alternative) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 149
def ab_show(experiment, identity, alternative)
  call_redis_with_failover do
    @experiments.set("#{experiment}:participant:#{identity}:show", alternative)
  end
end
ab_showing(experiment, identity) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 155
def ab_showing(experiment, identity)
  call_redis_with_failover do
    alternative = @experiments.get("#{experiment}:participant:#{identity}:show")
    alternative && alternative.to_i
  end
end
active?() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 38
def active?
  !!@redis
end
connect!() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 54
def connect!
  @redis = @options[:redis] || Redis.new(@options)
  @metrics = Redis::Namespace.new("vanity:metrics", :redis=>redis)
  @experiments = Redis::Namespace.new("vanity:experiments", :redis=>redis)
end
destroy_experiment(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 219
def destroy_experiment(experiment)
  cursor = nil

  while cursor != "0" do
    cursor, keys = @experiments.scan(cursor || "0", match: "#{experiment}:*")

    @experiments.del(*keys) unless keys.empty?
  end
end
destroy_metric(metric) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 89
def destroy_metric(metric)
  @metrics.del(*@metrics.keys("#{metric}:*"))
end
disconnect!() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 42
def disconnect!
  if redis
    redis.disconnect!
  end
  @redis = nil
end
experiment_persisted?(experiment) click to toggle source

– Experiments –

# File lib/vanity/adapters/redis_adapter.rb, line 96
def experiment_persisted?(experiment)
  !!@experiments.get("#{experiment}:created_at")
end
flushdb() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 64
def flushdb
  @redis.flushdb
end
get_experiment_completed_at(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 115
def get_experiment_completed_at(experiment)
  completed_at = @experiments.get("#{experiment}:completed_at")
  completed_at && Time.at(completed_at.to_i)
end
get_experiment_created_at(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 106
def get_experiment_created_at(experiment)
  created_at = @experiments.get("#{experiment}:created_at")
  created_at && Time.at(created_at.to_i)
end
get_metric_last_update_at(metric) click to toggle source

– Metrics –

# File lib/vanity/adapters/redis_adapter.rb, line 70
def get_metric_last_update_at(metric)
  last_update_at = @metrics.get("#{metric}:last_update_at")
  last_update_at && Time.at(last_update_at.to_i)
end
is_experiment_completed?(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 120
def is_experiment_completed?(experiment)
  call_redis_with_failover do
    @experiments.exists("#{experiment}:completed_at")
  end
end
is_experiment_enabled?(experiment) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 132
def is_experiment_enabled?(experiment)
  value = @experiments.get("#{experiment}:enabled")
  if Vanity.configuration.experiments_start_enabled
    value != 'false'
  else
    value == 'true'
  end
end
metric_track(metric, timestamp, identity, values) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 75
def metric_track(metric, timestamp, identity, values)
  call_redis_with_failover(metric, timestamp, identity, values) do
    values.each_with_index do |v,i|
      @metrics.incrby "#{metric}:#{timestamp.to_date}:value:#{i}", v
    end
    @metrics.set("#{metric}:last_update_at", Time.now.to_i)
  end
end
metric_values(metric, from, to) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 84
def metric_values(metric, from, to)
  single = @metrics.mget(*(from.to_date..to.to_date).map { |date| "#{metric}:#{date}:value:0" }) || []
  single.map { |v| [v.to_i] }
end
reconnect!() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 49
def reconnect!
  disconnect!
  connect!
end
set_experiment_completed_at(experiment, time) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 111
def set_experiment_completed_at(experiment, time)
  @experiments.setnx "#{experiment}:completed_at", time.to_i
end
set_experiment_created_at(experiment, time) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 100
def set_experiment_created_at(experiment, time)
  call_redis_with_failover do
    @experiments.setnx "#{experiment}:created_at", time.to_i
  end
end
set_experiment_enabled(experiment, enabled) click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 126
def set_experiment_enabled(experiment, enabled)
  call_redis_with_failover do
    @experiments.set "#{experiment}:enabled", enabled
  end
end
to_s() click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 60
def to_s
  redis.id
end

Protected Instance Methods

call_redis_with_failover(*arguments) { || ... } click to toggle source
# File lib/vanity/adapters/redis_adapter.rb, line 231
def call_redis_with_failover(*arguments)
  calling_method = caller[0][/`.*'/][1..-2]
  begin
    yield
  rescue => e
    if Vanity.configuration.failover_on_datastore_error
      Vanity.configuration.on_datastore_error.call(e, self.class, calling_method, arguments)
    else
      raise e
    end
  end
end