couchbase 1.2.3-x86-mingw32 → 1.3.0-x86-mingw32
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.yardopts +1 -1
- data/README.markdown +12 -8
- data/RELEASE_NOTES.markdown +19 -0
- data/couchbase.gemspec +1 -0
- data/examples/chat-goliath-grape/Gemfile +5 -0
- data/examples/chat-goliath-grape/README.markdown +50 -0
- data/examples/chat-goliath-grape/app.rb +67 -0
- data/examples/chat-goliath-grape/config/app.rb +20 -0
- data/examples/transcoders/Gemfile +3 -0
- data/examples/transcoders/README.markdown +59 -0
- data/examples/transcoders/cb-zcat +40 -0
- data/examples/transcoders/cb-zcp +45 -0
- data/examples/transcoders/gzip_transcoder.rb +49 -0
- data/examples/transcoders/options.rb +54 -0
- data/ext/couchbase_ext/arguments.c +67 -22
- data/ext/couchbase_ext/bucket.c +64 -20
- data/ext/couchbase_ext/context.c +2 -1
- data/ext/couchbase_ext/couchbase_ext.c +59 -9
- data/ext/couchbase_ext/couchbase_ext.h +18 -9
- data/ext/couchbase_ext/get.c +19 -23
- data/ext/couchbase_ext/store.c +1 -1
- data/ext/couchbase_ext/utils.c +38 -81
- data/lib/active_support/cache/couchbase_store.rb +60 -23
- data/lib/couchbase.rb +4 -2
- data/lib/couchbase/connection_pool.rb +55 -0
- data/lib/couchbase/transcoder.rb +120 -0
- data/lib/couchbase/version.rb +1 -1
- data/tasks/compile.rake +1 -1
- data/test/test_bucket.rb +1 -1
- data/test/test_couchbase_connection_pool.rb +73 -0
- data/test/test_couchbase_rails_cache_store.rb +36 -12
- data/test/test_format.rb +51 -1
- metadata +33 -4
@@ -97,7 +97,7 @@ struct cb_bucket_st
|
|
97
97
|
uint8_t connected; /* non-zero if instance has been connected. it is possible to defer connection with :async option */
|
98
98
|
uint8_t running; /* non-zero if event loop is running */
|
99
99
|
uint8_t trigger_connect_cb_on_set; /* if non-zero, the on_connect callback will be triggered immediately after set */
|
100
|
-
VALUE
|
100
|
+
VALUE transcoder;
|
101
101
|
uint32_t default_flags;
|
102
102
|
time_t default_ttl;
|
103
103
|
time_t default_observe_timeout;
|
@@ -127,7 +127,8 @@ struct cb_context_st
|
|
127
127
|
VALUE rv;
|
128
128
|
VALUE exception;
|
129
129
|
VALUE observe_options;
|
130
|
-
VALUE
|
130
|
+
VALUE transcoder;
|
131
|
+
VALUE transcoder_opts;
|
131
132
|
VALUE operation;
|
132
133
|
VALUE headers_val;
|
133
134
|
int headers_built;
|
@@ -169,8 +170,10 @@ extern VALUE cb_cTimer;
|
|
169
170
|
/* Modules */
|
170
171
|
extern VALUE cb_mCouchbase;
|
171
172
|
extern VALUE cb_mError;
|
173
|
+
extern VALUE cb_mTranscoder;
|
174
|
+
extern VALUE cb_mDocument;
|
175
|
+
extern VALUE cb_mPlain;
|
172
176
|
extern VALUE cb_mMarshal;
|
173
|
-
extern VALUE cb_mMultiJson;
|
174
177
|
extern VALUE cb_mURI;
|
175
178
|
extern VALUE em_m;
|
176
179
|
|
@@ -203,6 +206,7 @@ extern ID cb_sym_environment;
|
|
203
206
|
extern ID cb_sym_eventmachine;
|
204
207
|
extern ID cb_sym_extended;
|
205
208
|
extern ID cb_sym_flags;
|
209
|
+
extern ID cb_sym_forced;
|
206
210
|
extern ID cb_sym_format;
|
207
211
|
extern ID cb_sym_found;
|
208
212
|
extern ID cb_sym_get;
|
@@ -239,6 +243,7 @@ extern ID cb_sym_set;
|
|
239
243
|
extern ID cb_sym_stats;
|
240
244
|
extern ID cb_sym_timeout;
|
241
245
|
extern ID cb_sym_touch;
|
246
|
+
extern ID cb_sym_transcoder;
|
242
247
|
extern ID cb_sym_ttl;
|
243
248
|
extern ID cb_sym_type;
|
244
249
|
extern ID cb_sym_unlock;
|
@@ -336,10 +341,8 @@ int cb_first_value_i(VALUE key, VALUE value, VALUE arg);
|
|
336
341
|
void cb_build_headers(struct cb_context_st *ctx, const char * const *headers);
|
337
342
|
void cb_maybe_do_loop(struct cb_bucket_st *bucket);
|
338
343
|
VALUE cb_unify_key(struct cb_bucket_st *bucket, VALUE key, int apply_prefix);
|
339
|
-
VALUE cb_encode_value(VALUE val, uint32_t flags);
|
340
|
-
VALUE cb_decode_value(VALUE blob, uint32_t flags, VALUE
|
341
|
-
uint32_t cb_flags_set_format(uint32_t flags, ID format);
|
342
|
-
ID cb_flags_get_format(uint32_t flags);
|
344
|
+
VALUE cb_encode_value(VALUE transcoder, VALUE val, uint32_t *flags, VALUE options);
|
345
|
+
VALUE cb_decode_value(VALUE transcoder, VALUE blob, uint32_t flags, VALUE options);
|
343
346
|
void cb_async_error_notify(struct cb_bucket_st *bucket, VALUE exc);
|
344
347
|
|
345
348
|
|
@@ -388,6 +391,8 @@ VALUE cb_bucket_connected_p(VALUE self);
|
|
388
391
|
VALUE cb_bucket_async_p(VALUE self);
|
389
392
|
VALUE cb_bucket_quiet_get(VALUE self);
|
390
393
|
VALUE cb_bucket_quiet_set(VALUE self, VALUE val);
|
394
|
+
VALUE cb_bucket_transcoder_get(VALUE self);
|
395
|
+
VALUE cb_bucket_transcoder_set(VALUE self, VALUE val);
|
391
396
|
VALUE cb_bucket_default_flags_get(VALUE self);
|
392
397
|
VALUE cb_bucket_default_flags_set(VALUE self, VALUE val);
|
393
398
|
VALUE cb_bucket_default_format_get(VALUE self);
|
@@ -488,6 +493,8 @@ struct cb_params_st
|
|
488
493
|
lcb_cas_t cas;
|
489
494
|
lcb_datatype_t datatype;
|
490
495
|
VALUE observe;
|
496
|
+
VALUE transcoder;
|
497
|
+
VALUE transcoder_opts;
|
491
498
|
} store;
|
492
499
|
struct {
|
493
500
|
/* number of items */
|
@@ -509,7 +516,8 @@ struct cb_params_st
|
|
509
516
|
/* arguments given in form of hash key-ttl to "get and touch" */
|
510
517
|
unsigned int gat : 1;
|
511
518
|
lcb_time_t ttl;
|
512
|
-
VALUE
|
519
|
+
VALUE transcoder;
|
520
|
+
VALUE transcoder_opts;
|
513
521
|
VALUE keys_ary;
|
514
522
|
} get;
|
515
523
|
struct {
|
@@ -526,7 +534,8 @@ struct cb_params_st
|
|
526
534
|
lcb_uint64_t initial;
|
527
535
|
lcb_uint64_t delta;
|
528
536
|
int sign;
|
529
|
-
VALUE
|
537
|
+
VALUE transcoder;
|
538
|
+
VALUE transcoder_opts;
|
530
539
|
lcb_datatype_t datatype;
|
531
540
|
} arith;
|
532
541
|
struct {
|
data/ext/couchbase_ext/get.c
CHANGED
@@ -22,7 +22,7 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
22
22
|
{
|
23
23
|
struct cb_context_st *ctx = (struct cb_context_st *)cookie;
|
24
24
|
struct cb_bucket_st *bucket = ctx->bucket;
|
25
|
-
VALUE key, val, flags, cas, exc = Qnil, res;
|
25
|
+
VALUE key, val, flags, cas, exc = Qnil, res, raw;
|
26
26
|
|
27
27
|
ctx->nqueries--;
|
28
28
|
key = STR_NEW((const char*)resp->v.v0.key, resp->v.v0.nkey);
|
@@ -38,22 +38,17 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
38
38
|
|
39
39
|
flags = ULONG2NUM(resp->v.v0.flags);
|
40
40
|
cas = ULL2NUM(resp->v.v0.cas);
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
rb_ivar_set(ctx->exception, cb_id_iv_inner_exception, val);
|
53
|
-
val = raw;
|
54
|
-
}
|
55
|
-
} else if (cb_flags_get_format(resp->v.v0.flags) == cb_sym_plain) {
|
56
|
-
val = cb_vStrEmpty;
|
41
|
+
raw = STR_NEW((const char*)resp->v.v0.bytes, resp->v.v0.nbytes);
|
42
|
+
val = cb_decode_value(ctx->transcoder, raw, resp->v.v0.flags, ctx->transcoder_opts);
|
43
|
+
if (rb_obj_is_kind_of(val, rb_eStandardError)) {
|
44
|
+
VALUE exc_str = rb_funcall(val, cb_id_to_s, 0);
|
45
|
+
VALUE msg = rb_funcall(rb_mKernel, cb_id_sprintf, 3,
|
46
|
+
rb_str_new2("unable to convert value for key \"%s\": %s"), key, exc_str);
|
47
|
+
ctx->exception = rb_exc_new3(cb_eValueFormatError, msg);
|
48
|
+
rb_ivar_set(ctx->exception, cb_id_iv_operation, cb_sym_get);
|
49
|
+
rb_ivar_set(ctx->exception, cb_id_iv_key, key);
|
50
|
+
rb_ivar_set(ctx->exception, cb_id_iv_inner_exception, val);
|
51
|
+
val = Qnil;
|
57
52
|
}
|
58
53
|
if (bucket->async) { /* asynchronous */
|
59
54
|
if (ctx->proc != Qnil) {
|
@@ -96,8 +91,8 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
96
91
|
* @param keys [String, Symbol, Array] One or several keys to fetch
|
97
92
|
* @param options [Hash] Options for operation.
|
98
93
|
* @option options [true, false] :extended (false) If set to +true+, the
|
99
|
-
* operation will return tuple +[value, flags, cas]+, otherwise (by
|
100
|
-
* default) it returns just value.
|
94
|
+
* operation will return a tuple +[value, flags, cas]+, otherwise (by
|
95
|
+
* default) it returns just the value.
|
101
96
|
* @option options [Fixnum] :ttl (self.default_ttl) Expiry time for key.
|
102
97
|
* Values larger than 30*24*60*60 seconds (30 days) are interpreted as
|
103
98
|
* absolute times (from the epoch).
|
@@ -128,7 +123,7 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
128
123
|
* +cas+).
|
129
124
|
*
|
130
125
|
* @return [Object, Array, Hash] the value(s) (or tuples in extended mode)
|
131
|
-
*
|
126
|
+
* associated with the key.
|
132
127
|
*
|
133
128
|
* @raise [Couchbase::Error::NotFound] if the key is missing in the
|
134
129
|
* bucket.
|
@@ -137,7 +132,7 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
137
132
|
*
|
138
133
|
* @raise [ArgumentError] when passing the block in synchronous mode
|
139
134
|
*
|
140
|
-
* @example Get single value in
|
135
|
+
* @example Get single value in quiet mode (the default)
|
141
136
|
* c.get("foo") #=> the associated value or nil
|
142
137
|
*
|
143
138
|
* @example Use alternative hash-like syntax
|
@@ -199,7 +194,7 @@ cb_get_callback(lcb_t handle, const void *cookie, lcb_error_t error, const lcb_g
|
|
199
194
|
* @param options [Hash] Options for operation. (see options definition
|
200
195
|
* above)
|
201
196
|
*
|
202
|
-
* @return [Hash] the values (or tuples in extended mode)
|
197
|
+
* @return [Hash] the values (or tuples in extended mode) associated with
|
203
198
|
* the keys.
|
204
199
|
*
|
205
200
|
* @example Get and touch multiple keys
|
@@ -239,7 +234,8 @@ cb_bucket_get(int argc, VALUE *argv, VALUE self)
|
|
239
234
|
ctx = cb_context_alloc_common(bucket, proc, params.cmd.get.num);
|
240
235
|
ctx->extended = params.cmd.get.extended;
|
241
236
|
ctx->quiet = params.cmd.get.quiet;
|
242
|
-
ctx->
|
237
|
+
ctx->transcoder = params.cmd.get.transcoder;
|
238
|
+
ctx->transcoder_opts = params.cmd.get.transcoder_opts;
|
243
239
|
if (params.cmd.get.replica) {
|
244
240
|
err = lcb_get_replica(bucket->handle, (const void *)ctx,
|
245
241
|
params.cmd.get.num, params.cmd.get.ptr_gr);
|
data/ext/couchbase_ext/store.c
CHANGED
@@ -201,7 +201,7 @@ cb_bucket_store(lcb_storage_t cmd, int argc, VALUE *argv, VALUE self)
|
|
201
201
|
* @option options [Symbol] :format (self.default_format) The
|
202
202
|
* representation for storing the value in the bucket. For more info see
|
203
203
|
* {Bucket#default_format}.
|
204
|
-
* @option options [Fixnum] :cas The CAS value for an object. This value
|
204
|
+
* @option options [Fixnum] :cas The CAS value for an object. This value is
|
205
205
|
* created on the server and is guaranteed to be unique for each value of
|
206
206
|
* a given key. This value is used to provide simple optimistic
|
207
207
|
* concurrency control when multiple clients or threads try to update an
|
data/ext/couchbase_ext/utils.c
CHANGED
@@ -360,89 +360,33 @@ cb_check_error(lcb_error_t rc, const char *msg, VALUE key)
|
|
360
360
|
return cb_check_error_with_status(rc, msg, key, 0);
|
361
361
|
}
|
362
362
|
|
363
|
-
|
364
|
-
uint32_t
|
365
|
-
cb_flags_set_format(uint32_t flags, ID format)
|
366
|
-
{
|
367
|
-
flags &= ~((uint32_t)CB_FMT_MASK); /* clear format bits */
|
368
|
-
|
369
|
-
if (format == cb_sym_document) {
|
370
|
-
return flags | CB_FMT_DOCUMENT;
|
371
|
-
} else if (format == cb_sym_marshal) {
|
372
|
-
return flags | CB_FMT_MARSHAL;
|
373
|
-
} else if (format == cb_sym_plain) {
|
374
|
-
return flags | CB_FMT_PLAIN;
|
375
|
-
}
|
376
|
-
return flags; /* document is the default */
|
377
|
-
}
|
378
|
-
|
379
|
-
ID
|
380
|
-
cb_flags_get_format(uint32_t flags)
|
381
|
-
{
|
382
|
-
flags &= CB_FMT_MASK; /* select format bits */
|
383
|
-
|
384
|
-
switch (flags) {
|
385
|
-
case CB_FMT_DOCUMENT:
|
386
|
-
return cb_sym_document;
|
387
|
-
case CB_FMT_MARSHAL:
|
388
|
-
return cb_sym_marshal;
|
389
|
-
case CB_FMT_PLAIN:
|
390
|
-
/* fall through */
|
391
|
-
default:
|
392
|
-
/* all other formats treated as plain */
|
393
|
-
return cb_sym_plain;
|
394
|
-
}
|
395
|
-
}
|
396
|
-
|
397
|
-
|
398
363
|
static VALUE
|
399
364
|
do_encode(VALUE *args)
|
400
365
|
{
|
401
366
|
VALUE val = args[0];
|
402
|
-
uint32_t flags = (
|
403
|
-
|
404
|
-
|
405
|
-
|
406
|
-
|
407
|
-
|
408
|
-
|
409
|
-
|
410
|
-
|
411
|
-
default:
|
412
|
-
/* all other formats treated as plain */
|
413
|
-
return val;
|
367
|
+
uint32_t *flags = (uint32_t *)args[1];
|
368
|
+
VALUE transcoder = args[2];
|
369
|
+
VALUE options = args[3];
|
370
|
+
VALUE ret;
|
371
|
+
|
372
|
+
ret = rb_funcall(transcoder, cb_id_dump, 3, val, ULONG2NUM(*flags), options);
|
373
|
+
Check_Type(ret, T_ARRAY);
|
374
|
+
if (RARRAY_LEN(ret) != 2) {
|
375
|
+
rb_raise(rb_eArgError, "#dump method of transcoder should return two items");
|
414
376
|
}
|
377
|
+
*flags = NUM2ULONG(RARRAY_PTR(ret)[1]);
|
378
|
+
return RARRAY_PTR(ret)[0];
|
415
379
|
}
|
416
380
|
|
417
381
|
static VALUE
|
418
382
|
do_decode(VALUE *args)
|
419
383
|
{
|
420
384
|
VALUE blob = args[0];
|
421
|
-
VALUE
|
422
|
-
|
423
|
-
|
424
|
-
|
425
|
-
|
426
|
-
} else if (force_format == cb_sym_marshal) {
|
427
|
-
return rb_funcall(cb_mMarshal, cb_id_load, 1, blob);
|
428
|
-
} else { /* cb_sym_plain and any other cb_symbol */
|
429
|
-
return blob;
|
430
|
-
}
|
431
|
-
} else {
|
432
|
-
uint32_t flags = ((uint32_t)args[1] & CB_FMT_MASK);
|
433
|
-
|
434
|
-
switch (flags) {
|
435
|
-
case CB_FMT_DOCUMENT:
|
436
|
-
return rb_funcall(cb_mMultiJson, cb_id_load, 1, blob);
|
437
|
-
case CB_FMT_MARSHAL:
|
438
|
-
return rb_funcall(cb_mMarshal, cb_id_load, 1, blob);
|
439
|
-
case CB_FMT_PLAIN:
|
440
|
-
/* fall through */
|
441
|
-
default:
|
442
|
-
/* all other formats treated as plain */
|
443
|
-
return blob;
|
444
|
-
}
|
445
|
-
}
|
385
|
+
VALUE transcoder = args[2];
|
386
|
+
VALUE flags = args[1];
|
387
|
+
VALUE options = args[3];
|
388
|
+
|
389
|
+
return rb_funcall(transcoder, cb_id_load, 3, blob, ULONG2NUM(flags), options);
|
446
390
|
}
|
447
391
|
|
448
392
|
static VALUE
|
@@ -453,20 +397,27 @@ coding_failed(VALUE unused, VALUE exc)
|
|
453
397
|
}
|
454
398
|
|
455
399
|
VALUE
|
456
|
-
cb_encode_value(VALUE val, uint32_t flags)
|
400
|
+
cb_encode_value(VALUE transcoder, VALUE val, uint32_t *flags, VALUE options)
|
457
401
|
{
|
458
|
-
VALUE
|
402
|
+
VALUE args[4];
|
459
403
|
|
460
404
|
args[0] = val;
|
461
405
|
args[1] = (VALUE)flags;
|
462
|
-
|
463
|
-
|
406
|
+
args[2] = transcoder;
|
407
|
+
args[3] = options;
|
408
|
+
|
409
|
+
/* if nil, just pass value through */
|
410
|
+
if (NIL_P(args[2])) {
|
411
|
+
return val;
|
412
|
+
}
|
413
|
+
/* bytestring or exception object */
|
414
|
+
return rb_rescue(do_encode, (VALUE)args, coding_failed, 0);
|
464
415
|
}
|
465
416
|
|
466
417
|
VALUE
|
467
|
-
cb_decode_value(VALUE blob, uint32_t flags, VALUE
|
418
|
+
cb_decode_value(VALUE transcoder, VALUE blob, uint32_t flags, VALUE options)
|
468
419
|
{
|
469
|
-
VALUE
|
420
|
+
VALUE args[4];
|
470
421
|
|
471
422
|
/* first it must be bytestring */
|
472
423
|
if (TYPE(blob) != T_STRING) {
|
@@ -474,9 +425,15 @@ cb_decode_value(VALUE blob, uint32_t flags, VALUE force_format)
|
|
474
425
|
}
|
475
426
|
args[0] = blob;
|
476
427
|
args[1] = (VALUE)flags;
|
477
|
-
args[2] =
|
478
|
-
|
479
|
-
|
428
|
+
args[2] = transcoder;
|
429
|
+
args[3] = options;
|
430
|
+
|
431
|
+
/* if nil, just pass blob through */
|
432
|
+
if (NIL_P(args[2])) {
|
433
|
+
return blob;
|
434
|
+
}
|
435
|
+
/* the value or exception object */
|
436
|
+
return rb_rescue(do_decode, (VALUE)args, coding_failed, 0);
|
480
437
|
}
|
481
438
|
|
482
439
|
void
|
@@ -55,9 +55,15 @@ module ActiveSupport
|
|
55
55
|
options[:default_ttl] ||= options.delete(:expires_in)
|
56
56
|
options[:default_format] ||= :marshal
|
57
57
|
options[:key_prefix] ||= options.delete(:namespace)
|
58
|
+
options[:connection_pool] ||= options.delete(:connection_pool)
|
58
59
|
args.push(options)
|
59
|
-
|
60
|
-
|
60
|
+
|
61
|
+
if options[:connection_pool]
|
62
|
+
@data = ::Couchbase::ConnectionPool.new(options[:connection_pool], *args)
|
63
|
+
else
|
64
|
+
@data = ::Couchbase::Bucket.new(*args)
|
65
|
+
@data.extend(Threadsafe)
|
66
|
+
end
|
61
67
|
end
|
62
68
|
|
63
69
|
# Fetches data from the cache, using the given key.
|
@@ -184,9 +190,7 @@ module ActiveSupport
|
|
184
190
|
options[:format] = :plain
|
185
191
|
end
|
186
192
|
instrument(:read_multi, names, options) do
|
187
|
-
@
|
188
|
-
@data.get(names, options)
|
189
|
-
end
|
193
|
+
@data.get(names, options)
|
190
194
|
end
|
191
195
|
rescue ::Couchbase::Error::Base => e
|
192
196
|
logger.error("#{e.class}: #{e.message}") if logger
|
@@ -247,9 +251,7 @@ module ActiveSupport
|
|
247
251
|
options[:create] = true
|
248
252
|
instrument(:increment, name, options) do |payload|
|
249
253
|
payload[:amount] = amount if payload
|
250
|
-
@
|
251
|
-
@data.incr(name, amount, options)
|
252
|
-
end
|
254
|
+
@data.incr(name, amount, options)
|
253
255
|
end
|
254
256
|
rescue ::Couchbase::Error::Base => e
|
255
257
|
logger.error("#{e.class}: #{e.message}") if logger
|
@@ -281,9 +283,7 @@ module ActiveSupport
|
|
281
283
|
options[:create] = true
|
282
284
|
instrument(:decrement, name, options) do |payload|
|
283
285
|
payload[:amount] = amount if payload
|
284
|
-
@
|
285
|
-
@data.decr(name, amount, options)
|
286
|
-
end
|
286
|
+
@data.decr(name, amount, options)
|
287
287
|
end
|
288
288
|
rescue ::Couchbase::Error::Base => e
|
289
289
|
logger.error("#{e.class}: #{e.message}") if logger
|
@@ -297,18 +297,14 @@ module ActiveSupport
|
|
297
297
|
#
|
298
298
|
# @return [Hash]
|
299
299
|
def stats(*arg)
|
300
|
-
@
|
301
|
-
@data.stats(*arg)
|
302
|
-
end
|
300
|
+
@data.stats(*arg)
|
303
301
|
end
|
304
302
|
|
305
303
|
protected
|
306
304
|
|
307
305
|
# Read an entry from the cache.
|
308
306
|
def read_entry(key, options) # :nodoc:
|
309
|
-
@
|
310
|
-
@data.get(key, options)
|
311
|
-
end
|
307
|
+
@data.get(key, options)
|
312
308
|
rescue ::Couchbase::Error::Base => e
|
313
309
|
logger.error("#{e.class}: #{e.message}") if logger
|
314
310
|
raise if @raise_errors
|
@@ -325,9 +321,7 @@ module ActiveSupport
|
|
325
321
|
if ttl = options.delete(:expires_in)
|
326
322
|
options[:ttl] ||= ttl
|
327
323
|
end
|
328
|
-
@
|
329
|
-
@data.send(method, key, value, options)
|
330
|
-
end
|
324
|
+
@data.send(method, key, value, options)
|
331
325
|
rescue ::Couchbase::Error::Base => e
|
332
326
|
logger.error("#{e.class}: #{e.message}") if logger
|
333
327
|
raise if @raise_errors
|
@@ -336,9 +330,7 @@ module ActiveSupport
|
|
336
330
|
|
337
331
|
# Delete an entry from the cache.
|
338
332
|
def delete_entry(key, options) # :nodoc:
|
339
|
-
@
|
340
|
-
@data.delete(key, options)
|
341
|
-
end
|
333
|
+
@data.delete(key, options)
|
342
334
|
rescue ::Couchbase::Error::Base => e
|
343
335
|
logger.error("#{e.class}: #{e.message}") if logger
|
344
336
|
raise if @raise_errors
|
@@ -367,6 +359,51 @@ module ActiveSupport
|
|
367
359
|
key.respond_to?(:to_param) ? key.to_param : key
|
368
360
|
end
|
369
361
|
|
362
|
+
module Threadsafe
|
363
|
+
def self.extended(obj)
|
364
|
+
obj.init_threadsafe
|
365
|
+
end
|
366
|
+
|
367
|
+
def get(*)
|
368
|
+
@lock.synchronize do
|
369
|
+
super
|
370
|
+
end
|
371
|
+
end
|
372
|
+
|
373
|
+
def send(*)
|
374
|
+
@lock.synchronize do
|
375
|
+
super
|
376
|
+
end
|
377
|
+
end
|
378
|
+
|
379
|
+
def delete(*)
|
380
|
+
@lock.synchronize do
|
381
|
+
super
|
382
|
+
end
|
383
|
+
end
|
384
|
+
|
385
|
+
def incr(*)
|
386
|
+
@lock.synchronize do
|
387
|
+
super
|
388
|
+
end
|
389
|
+
end
|
390
|
+
|
391
|
+
def decr(*)
|
392
|
+
@lock.synchronize do
|
393
|
+
super
|
394
|
+
end
|
395
|
+
end
|
396
|
+
|
397
|
+
def stats(*)
|
398
|
+
@lock.synchronize do
|
399
|
+
super
|
400
|
+
end
|
401
|
+
end
|
402
|
+
|
403
|
+
def init_threadsafe
|
404
|
+
@lock = Monitor.new
|
405
|
+
end
|
406
|
+
end
|
370
407
|
end
|
371
408
|
end
|
372
409
|
end
|