Class: Memcached::Rails

Inherits:
Memcached show all
Defined in:
lib/memcached/rails.rb

Overview

A legacy compatibility wrapper for the Memcached class. It has basic compatibility with the memcache-client API and Rails 3.2. (Note that ActiveSupport::Duration objects are supported, but not recommended, as ttl parameters. Using Fixnum ttls, such as provided by time_constants.gem, is much faster.)

Constant Summary collapse

DEFAULTS =
{
  :logger => nil,
  :string_return_types => false
}

Constants inherited from Memcached

BEHAVIORS, BEHAVIOR_VALUES, CONVERSION_FACTORS, DIRECT_VALUE_BEHAVIORS, DISTRIBUTION_VALUES, ERRNO_HASH, EXCEPTIONS, FLAGS, HASH_VALUES, IGNORED, Lib, VERSION

Instance Attribute Summary collapse

Attributes inherited from Memcached

#options

Instance Method Summary collapse

Methods inherited from Memcached

#clone, #destroy_credentials, #exist, #flush, #get_from_last, load_constants, #prefix_key, #quit, #replace, #reset, #server_by_key, #set_prefix_key, #should_retry, #stats

Constructor Details

#initialize(*args) ⇒ Rails

See Memcached#new for details.



22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
# File 'lib/memcached/rails.rb', line 22

def initialize(*args)
  opts = args.last.is_a?(Hash) ? args.pop : {}
  servers = Array(
    args.any? ? args.unshift : opts.delete(:servers)
  ).flatten.compact

  opts[:prefix_key] = opts.delete(:namespace) if opts[:namespace]
  opts[:prefix_delimiter] = opts.delete(:namespace_separator) if opts[:namespace_separator]

  @logger = opts.delete(:logger)
  @string_return_types = opts.delete(:string_return_types)

  logger.info { "memcached #{VERSION} #{servers.inspect}" } if logger
  super(servers, opts)
end

Instance Attribute Details

#loggerObject

Returns the value of attribute logger.



17
18
19
# File 'lib/memcached/rails.rb', line 17

def logger
  @logger
end

Instance Method Details

#active?Boolean

Check if there are any servers defined?

Returns:

  • (Boolean)


47
48
49
# File 'lib/memcached/rails.rb', line 47

def active?
  servers.any?
end

#add(key, value, ttl = @default_ttl, raw = false) ⇒ Object

Wraps Memcached#add so that it doesn’t raise.



153
154
155
156
157
158
159
160
161
162
163
# File 'lib/memcached/rails.rb', line 153

def add(key, value, ttl=@default_ttl, raw=false)
  super(key, value, ttl, !raw)
  @string_return_types ? "STORED\r\n" : true
rescue TypeError => e
  # Maybe we got an ActiveSupport::Duration
  ttl = ttl.value and retry rescue raise e
rescue NotStored
rescue Error => e
  log_exception e
  @string_return_types? "NOT STORED\r\n" : false
end

#append(*args) ⇒ Object

Wraps Memcached#append so that it doesn’t raise.



192
193
194
195
196
197
# File 'lib/memcached/rails.rb', line 192

def append(*args)
  super
rescue NotStored
rescue Error => e
  log_exception e
end

#cas(key, ttl = @default_ttl, raw = false, &block) ⇒ Object Also known as: compare_and_swap

Wraps Memcached#cas so that it doesn’t raise. Doesn’t set anything if no value is present.



89
90
91
92
93
94
95
96
97
98
99
# File 'lib/memcached/rails.rb', line 89

def cas(key, ttl=@default_ttl, raw=false, &block)
  super(key, ttl, !raw, &block)
  true
rescue TypeError => e
  # Maybe we got an ActiveSupport::Duration
  ttl = ttl.value and retry rescue raise e
rescue NotFound, ConnectionDataExists
  false
rescue Error => e
  log_exception e
end

#decr(*args) ⇒ Object

Wraps Memcached#decr so that it doesn’t raise.



184
185
186
187
188
189
# File 'lib/memcached/rails.rb', line 184

def decr(*args)
  super
rescue NotFound
rescue Error => e
  log_exception e
end

#decrement(name, amount = 1, options = nil) ⇒ Object



243
244
245
246
247
248
# File 'lib/memcached/rails.rb', line 243

def decrement(name, amount = 1, options = nil)
  response = super(name, amount)
  response ? response.to_i : nil
rescue
  nil
end

#delete(key, options = nil) ⇒ Object

Wraps Memcached#delete so that it doesn’t raise.



166
167
168
169
170
171
172
173
# File 'lib/memcached/rails.rb', line 166

def delete(key, options = nil)
  super(key)
  true
rescue NotFound
  false
rescue Error => e
  log_exception e
end

#exist?(key, options = {}) ⇒ Boolean

Returns whether the key exists, even if the value is nil.

Returns:

  • (Boolean)


79
80
81
82
83
84
85
86
# File 'lib/memcached/rails.rb', line 79

def exist?(key, options = {})
  exist(key)
  true
rescue NotFound
  false
rescue Error => e
  log_exception e
end

#fetch(key, options = nil) ⇒ Object



137
138
139
140
141
142
143
144
145
146
147
148
149
150
# File 'lib/memcached/rails.rb', line 137

def fetch(key, options = nil)
  result = read(key, options)
  if result.nil?
    if block_given?
      result = yield
      write(key, result, options)
      result
    else
      result
    end
  else
    result
  end
end

#get(key, raw = false) ⇒ Object Also known as: []

Wraps Memcached#get so that it doesn’t raise. This has the side-effect of preventing you from storing nil values.



58
59
60
61
62
63
# File 'lib/memcached/rails.rb', line 58

def get(key, raw=false)
  super(key, !raw)
rescue NotFound
rescue Error => e
  log_exception e
end

#get_multi(keys, raw = false) ⇒ Object

Wraps Memcached#get.



104
105
106
107
108
109
# File 'lib/memcached/rails.rb', line 104

def get_multi(keys, raw=false)
  get_orig(keys, !raw)
rescue NotFound
rescue Error => e
  log_exception e
end

#incr(*args) ⇒ Object

Wraps Memcached#incr so that it doesn’t raise.



176
177
178
179
180
181
# File 'lib/memcached/rails.rb', line 176

def incr(*args)
  super
rescue NotFound
rescue Error => e
  log_exception e
end

#increment(name, amount = 1, options = nil) ⇒ Object



236
237
238
239
240
241
# File 'lib/memcached/rails.rb', line 236

def increment(name, amount = 1, options = nil)
  response = super(name, amount)
  response ? response.to_i : nil
rescue
  nil
end

#log_exception(e) ⇒ Object



51
52
53
54
# File 'lib/memcached/rails.rb', line 51

def log_exception(e)
  logger.warn("memcached error: #{e.class}: #{e.message}") if logger
  false
end

#namespaceObject



42
43
44
# File 'lib/memcached/rails.rb', line 42

def namespace
   @options[:prefix_key]
end

#prepend(*args) ⇒ Object

Wraps Memcached#prepend so that it doesn’t raise.



200
201
202
203
204
205
# File 'lib/memcached/rails.rb', line 200

def prepend(*args)
  super
rescue NotStored
rescue Error => e
  log_exception e
end

#read(key, options = nil) ⇒ Object

Alternative to #get. Accepts a key and an optional options hash supporting the single option :raw.



67
68
69
70
71
72
73
74
75
76
# File 'lib/memcached/rails.rb', line 67

def read(key, options = nil)
  if options
    get(key, options[:raw])
  else
    get(key)
  end
rescue NotFound
rescue Error => e
  log_exception e
end

#read_multi(*keys) ⇒ Object



213
214
215
216
# File 'lib/memcached/rails.rb', line 213

def read_multi(*keys)
  return {} if keys.empty?
  get_multi(keys)
end

#serversObject

Return an array of server objects.



219
220
221
222
223
224
225
# File 'lib/memcached/rails.rb', line 219

def servers
  server_structs.each do |server|
    def server.alive?
      next_retry <= Time.now
    end
  end
end

#servers=Object



19
# File 'lib/memcached/rails.rb', line 19

alias :servers= :set_servers

#set(key, value, ttl = @default_ttl, raw = false) ⇒ Object Also known as: []=

Wraps Memcached#set.



112
113
114
115
116
117
118
119
120
121
122
# File 'lib/memcached/rails.rb', line 112

def set(key, value, ttl=@default_ttl, raw=false)
  super(key, value, ttl, !raw)
  true
rescue TypeError => e
  # Maybe we got an ActiveSupport::Duration
  ttl = ttl.value and retry rescue raise e
rescue NotStored
  false
rescue Error => e
  log_exception e
end

#set_servers(servers) ⇒ Object

Wraps Memcached#set_servers to convert server objects to strings.



228
229
230
231
232
233
234
# File 'lib/memcached/rails.rb', line 228

def set_servers(servers)
  servers = Array(servers)
  servers.map! do |server|
    server.is_a?(String) ? server : inspect_server(server)
  end
  super
end

#write(key, value, options = nil) ⇒ Object

Alternative to #set. Accepts a key, value, and an optional options hash supporting the options :raw and :ttl.



126
127
128
129
130
131
132
133
134
135
# File 'lib/memcached/rails.rb', line 126

def write(key, value, options = nil)
  value = value.to_s if options && options[:raw]
  ttl = options ? (options[:ttl] || options[:expires_in] || @default_ttl) : @default_ttl
  raw = options ? options[:raw] : nil
  if options && options[:unless_exist]
    add(key, value, ttl, raw)
  else
    set(key, value, ttl, raw)
  end
end