couchbase-jruby-client 0.1.7-java → 0.1.8-java

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: d7e0d408c5e5e7be7aef116504c626b47e3370ca
4
- data.tar.gz: 449cc0459b4cca48176034faebc9b1164a8bb7d5
3
+ metadata.gz: 1c0ea141997ee6f37bc481a1c7eb4d62448440b5
4
+ data.tar.gz: 218d1e6e80321f9a7a6efc229fca2d8e0d2e4e76
5
5
  SHA512:
6
- metadata.gz: 631922413e409bad9ebd705a3e08baed7715a697e8426db07c14c86c270f95c4b81b1350e67d2b963569f8fbbb5feefd3dcc3effd1d4eedae56200dc0a760a46
7
- data.tar.gz: 86070762df8a647c3968192aeea98a9e5b3703f958d250d1b926be15240a62b8823769974ffd69ba51aaf3e5ce464071a72c4136c35dc5aa28137a3a68bb5a77
6
+ metadata.gz: 661cc5eec9882f541ad4441a20e9af2c4d92422a388b9dab2e6d1917d074ab47623a2e84beda34ed5f7bed1f775d0227bbc769d5dc3e910c33f2ecd1882c38e3
7
+ data.tar.gz: 35dadabf6e5238f9926c7b6ff52357253f3d8ccccc68026c89c6a70fabe0c30d6ec9d2ce5ab88183b344d9238164321b4cb60c6cfc93b4e8ce26d1be6ae9196e
data/.gitignore CHANGED
@@ -15,3 +15,6 @@ spec/reports
15
15
  test/tmp
16
16
  test/version_tmp
17
17
  tmp
18
+ test/CouchbaseMock.jar
19
+ Vagrantfile
20
+ .vagrant
data/.ruby-version CHANGED
@@ -1 +1 @@
1
- jruby-1.7.6
1
+ jruby-1.7.9
data/.travis.yml CHANGED
@@ -1,11 +1,3 @@
1
- before_install:
2
- # Couchbase Server
3
- - sudo service memcached stop
4
- - sudo wget http://packages.couchbase.com/releases/2.2.0/couchbase-server-enterprise_2.2.0_x86.deb
5
- - sudo dpkg -i couchbase-server-enterprise_2.2.0_x86.deb
6
- - sudo service couchbase-server start
7
- - /opt/couchbase/bin/couchbase-cli cluster-init -c localhost --cluster-init-username=admin --cluster-init-password=password --cluster-init-ramsize=256
8
- - /opt/couchbase/bin/couchbase-cli bucket-create -c localhost --bucket=default --bucket-type=couchbase --bucket-ramsize=256 -u admin -p password
9
1
  notifications:
10
2
  email:
11
3
  - mike@urlgonomics.com
data/Rakefile CHANGED
@@ -1,10 +1,6 @@
1
1
  require 'bundler/gem_tasks'
2
2
  require 'rake/testtask'
3
3
 
4
- Rake::TestTask.new(:test) do |test|
5
- test.libs << 'test'
6
- test.pattern = 'test/**/test_*.rb'
7
- test.verbose = true
8
- end
4
+ Dir['tasks/*.rake'].sort.each { |f| load f }
9
5
 
10
- task :default => :test
6
+ task :default => :test
@@ -1,14 +1,33 @@
1
+ # Author:: Mike Evans <mike@urlgonomics.com>
2
+ # Copyright:: 2013 Urlgonomics LLC.
3
+ # License:: Apache License, Version 2.0
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+ #
17
+
1
18
  module Couchbase
2
19
  module Async
3
20
  class Callback
4
21
  include Java::NetSpyMemcachedInternal::OperationCompletionListener
22
+ include Java::NetSpyMemcachedInternal::GetCompletionListener
5
23
 
6
- def initialize(operation, &callback)
7
- @operation, @callback = operation, callback
24
+ def initialize(params, &callback)
25
+ @params = params
26
+ @callback = callback
8
27
  end
9
28
 
10
29
  def onComplete(future)
11
- result = Couchbase::Result.new(operation: @operation, future: future)
30
+ result = Couchbase::Result.new(@params.merge(future: future))
12
31
  @callback.call(result)
13
32
  rescue Exception => e
14
33
  result.error = e
@@ -21,137 +21,12 @@ require 'couchbase/async/queue'
21
21
  module Couchbase
22
22
  module Async
23
23
 
24
- def async?
25
- !!async
26
- end
27
-
28
- def async
29
- Thread.current[:bucket_async] ||= @async
30
- end
31
-
32
- def async=(val)
33
- Thread.current[:bucket_async] = val
34
- end
35
-
36
- def running?
37
- !!running
38
- end
39
-
40
- def running
41
- Thread.current[:bucket_running] ||= false
42
- end
43
-
44
- def running=(val)
45
- Thread.current[:bucket_running] = val
46
- end
47
-
48
- def async_queue
49
- Thread.current[:bucket_async_queue] ||= Couchbase::Async::Queue.new(self)
50
- end
51
-
52
- def end_async_queue
53
- Thread.current[:bucket_async_queue] = nil
54
- end
55
-
56
- public
57
-
58
- # Run the event loop.
59
- #
60
- # @since 1.0.0
61
- #
62
- # @param [Hash] options The options for operation for connection
63
- # @option options [Fixnum] :send_threshold (0) if the internal command
64
- # buffer will exceeds this value, then the library will start network
65
- # interaction and block the current thread until all scheduled commands
66
- # will be completed.
67
- #
68
- # @yieldparam [Bucket] bucket the bucket instance
69
- #
70
- # @example Use block to run the loop
71
- # c = Couchbase.new
72
- # c.run do
73
- # c.get("foo") {|ret| puts ret.value}
74
- # end
75
- #
76
- # @example Use lambda to run the loop
77
- # c = Couchbase.new
78
- # operations = lambda do |c|
79
- # c.get("foo") {|ret| puts ret.value}
80
- # end
81
- # c.run(&operations)
82
- #
83
- # @example Use threshold to send out commands automatically
84
- # c = Couchbase.connect
85
- # sent = 0
86
- # c.run(:send_threshold => 8192) do # 8Kb
87
- # c.set("foo1", "x" * 100) {|r| sent += 1}
88
- # # 128 bytes buffered, sent is 0 now
89
- # c.set("foo2", "x" * 10000) {|r| sent += 1}
90
- # # 10028 bytes added, sent is 2 now
91
- # c.set("foo3", "x" * 100) {|r| sent += 1}
92
- # end
93
- # # all commands were executed and sent is 3 now
94
- #
95
- # @example Use {Couchbase::Bucket#run} without block for async connection
96
- # c = Couchbase.new(:async => true)
97
- # c.run # ensure that instance connected
98
- # c.set("foo", "bar"){|r| puts r.cas}
99
- # c.run
100
- #
101
- # @return [nil]
102
- #
103
- # @raise [Couchbase::Error::Connect] if connection closed (see {Bucket#reconnect})
104
- #
105
- def run(options = {})
106
- do_async_setup(block_given?)
107
- yield(self)
108
- async_queue.join
109
-
110
- # TODO: deal with exceptions
111
- nil
112
- ensure
113
- do_async_ensure
114
- end
115
-
116
- def run_async(options = {})
117
- do_async_setup(block_given?)
118
- yield(self)
119
- nil
120
- ensure
121
- do_async_ensure
122
- end
123
-
124
24
  private
125
25
 
126
- def do_async_setup(block_given)
127
- raise LocalJumpError.new('block required for async run') unless block_given
128
- # TODO: check for connection
129
- raise Error::Invalid.new('nested #run') if running?
130
- # TOOD: deal with thresholds
131
-
132
- self.async = true
133
- self.running = true
134
- end
135
-
136
- def do_async_ensure
137
- self.async = false
138
- self.running = false
139
- end_async_queue
140
- end
141
-
142
- def register_future(future, options, &block)
143
- if async_queue
144
- async_queue.add_future(future, options, &block)
145
- else
146
- register_callback(future, &block)
147
- end
148
- future
149
- end
150
-
151
- def register_callback(future, &block)
152
- callback = Couchbase::Callback.new(:set, &block)
26
+ def register_future(future, params, &block)
27
+ callback = Callback.new(params, &block)
153
28
  future.addListener(callback)
29
+ future
154
30
  end
155
-
156
31
  end
157
32
  end
@@ -51,7 +51,6 @@ module Couchbase
51
51
  password: '',
52
52
  engine: nil,
53
53
  default_ttl: 0,
54
- async: false,
55
54
  default_arithmetic_init: 0,
56
55
  default_flags: 0,
57
56
  default_format: :document,
@@ -65,7 +64,6 @@ module Couchbase
65
64
  destroying: 0,
66
65
  connected: 0,
67
66
  on_connect_proc: nil,
68
- async_disconnect_hook_set: 0,
69
67
  connected: false
70
68
  }.freeze
71
69
 
@@ -132,11 +130,6 @@ module Couchbase
132
130
  # :libevent :: libevent IO plugin from libcouchbase (optional)
133
131
  # :libev :: libev IO plugin from libcouchbase (optional)
134
132
  # :eventmachine :: EventMachine plugin (builtin, but requires EM gem and ruby 1.9+)
135
- # @option options [true, false] :async (false) If true, the
136
- # connection instance will be considered always asynchronous and
137
- # IO interaction will be occured only when {Couchbase::Bucket#run}
138
- # called. See {Couchbase::Bucket#on_connect} to hook your code
139
- # after the instance will be connected.
140
133
  #
141
134
  # @example Initialize connection using default options
142
135
  # Couchbase.new
@@ -162,16 +155,7 @@ module Couchbase
162
155
  # @return [Bucket]
163
156
  #
164
157
  def initialize(url = nil, options = {})
165
- url_options = if url.is_a? String
166
- fail ArgumentError.new unless url =~ /^http:\/\//
167
- uri = URI.new(url)
168
- { hostname: uri.host, port: uri.port }.
169
- merge(path_to_pool_and_bucket(uri.path))
170
- elsif url.nil?
171
- {}
172
- else
173
- url
174
- end
158
+ url_options = expand_url_options(url)
175
159
 
176
160
  options = Couchbase.normalize_connection_options(options)
177
161
 
@@ -181,13 +165,15 @@ module Couchbase
181
165
  instance_variable_set("@#{key}", value)
182
166
  end
183
167
 
168
+ self.password = '' if self.password.nil?
169
+
184
170
  @transcoders = {
185
171
  document: Transcoder::Document.new,
186
172
  marshal: Transcoder::Marshal.new,
187
173
  plain: Transcoder::Plain.new
188
174
  }
189
175
 
190
- connect unless async?
176
+ connect
191
177
  end
192
178
 
193
179
  def quiet?
@@ -199,11 +185,7 @@ module Couchbase
199
185
  end
200
186
 
201
187
  def connect
202
- uris = if @node_list
203
- Array(@node_list).map { |n| URI.new(n) }
204
- else
205
- Array(URI.new(base_url))
206
- end
188
+ uris = expand_node_list
207
189
 
208
190
  begin
209
191
  builder = CouchbaseConnectionFactoryBuilder.new
@@ -211,10 +193,10 @@ module Couchbase
211
193
  connection_factory = builder.buildCouchbaseConnection(uris, bucket.to_java_string, password.to_java_string)
212
194
  @client = CouchbaseClient.new(connection_factory)
213
195
  @connected = true
214
- rescue Java::ComCouchbaseClientVbucket::ConfigurationException
215
- fail Couchbase::Error::Auth, 'Couchbase configurations are incorrect.'
196
+ rescue Java::ComCouchbaseClientVbucket::ConfigurationException => e
197
+ fail Couchbase::Error::Auth, "Couchbase configurations are incorrect: #{e.to_s}"
216
198
  rescue java.net.ConnectException => e
217
- fail Couchbase::Error::Connect
199
+ fail Couchbase::Error::Connect, e.to_s
218
200
  end
219
201
 
220
202
  self
@@ -238,8 +220,7 @@ module Couchbase
238
220
  end
239
221
 
240
222
  def disconnect
241
- if connected?
242
- @client.shutdown(3, TimeUnit::SECONDS)
223
+ if connected? && @client.shutdown(3, TimeUnit::SECONDS)
243
224
  @client = nil
244
225
  @connection_factory = nil
245
226
  @connected = false
@@ -329,17 +310,9 @@ module Couchbase
329
310
  #
330
311
  # @return [Fixnum] the CAS of new value
331
312
  def cas(key, options = {})
332
- if async?
333
- block = Proc.new
334
- get(key) do |ret|
335
- val = block.call(ret) # get new value from caller
336
- set(ret.key, val, options.merge(:cas => ret.cas, &block))
337
- end
338
- else
339
- val, flags, ver = get(key, :extended => true)
340
- val = yield(val) # get new value from caller
341
- set(key, val, options.merge(:cas => ver))
342
- end
313
+ val, flags, ver = get(key, :extended => true)
314
+ val = yield(val) # get new value from caller
315
+ set(key, val, options.merge(:cas => ver))
343
316
  end
344
317
  alias :compare_and_swap :cas
345
318
 
@@ -369,89 +342,7 @@ module Couchbase
369
342
  # end
370
343
  # end
371
344
  def flush
372
- if !async? && block_given?
373
- sync_block_error
374
- end
375
- req = make_http_request("/pools/default/buckets/#{bucket}/controller/doFlush",
376
- :type => :management, :method => :post, :extended => true)
377
- res = nil
378
- req.on_body do |r|
379
- res = r
380
- res.instance_variable_set("@operation", :flush)
381
- yield(res) if block_given?
382
- end
383
- req.continue
384
- true
385
- end
386
-
387
- # Create and register one-shot timer
388
- #
389
- # @return [Couchbase::Timer]
390
- def create_timer(interval, &block)
391
- Timer.new(self, interval, &block)
392
- end
393
-
394
- # Create and register periodic timer
395
- #
396
- # @return [Couchbase::Timer]
397
- def create_periodic_timer(interval, &block)
398
- Timer.new(self, interval, :periodic => true, &block)
399
- end
400
-
401
- # Wait for persistence condition
402
- #
403
- # @since 1.2.0.dp6
404
- #
405
- # This operation is useful when some confidence needed regarding the
406
- # state of the keys. With two parameters +:replicated+ and +:persisted+
407
- # it allows to set up the waiting rule.
408
- #
409
- # @param [String, Symbol, Array, Hash] keys The list of the keys to
410
- # observe. Full form is hash with key-cas value pairs, but there are
411
- # also shortcuts like just Array of keys or single key. CAS value
412
- # needed to when you need to ensure that the storage persisted exactly
413
- # the same version of the key you are asking to observe.
414
- # @param [Hash] options The options for operation
415
- # @option options [Fixnum] :timeout The timeout in microseconds
416
- # @option options [Fixnum] :replicated How many replicas should receive
417
- # the copy of the key.
418
- # @option options [Fixnum] :persisted How many nodes should store the
419
- # key on the disk.
420
- #
421
- # @raise [Couchbase::Error::Timeout] if the given time is up
422
- #
423
- # @return [Fixnum, Hash<String, Fixnum>] will return CAS value just like
424
- # mutators or pairs key-cas in case of multiple keys.
425
- def observe_and_wait(*keys, &block)
426
- options = {:timeout => default_observe_timeout}
427
- options.update(keys.pop) if keys.size > 1 && keys.last.is_a?(Hash)
428
- verify_observe_options(options)
429
- if block && !async?
430
- raise ArgumentError, "synchronous mode doesn't support callbacks"
431
- end
432
- if keys.size == 0
433
- raise ArgumentError, "at least one key is required"
434
- end
435
- if keys.size == 1 && keys[0].is_a?(Hash)
436
- key_cas = keys[0]
437
- else
438
- key_cas = keys.flatten.reduce({}) do |h, kk|
439
- h[kk] = nil # set CAS to nil
440
- h
441
- end
442
- end
443
- if async?
444
- do_observe_and_wait(key_cas, options, &block)
445
- else
446
- res = do_observe_and_wait(key_cas, options, &block) while res.nil?
447
- unless async?
448
- if keys.size == 1 && (keys[0].is_a?(String) || keys[0].is_a?(Symbol))
449
- return res.values.first
450
- else
451
- return res
452
- end
453
- end
454
- end
345
+ @client.flush.get
455
346
  end
456
347
 
457
348
  private
@@ -460,114 +351,26 @@ module Couchbase
460
351
  {}
461
352
  end
462
353
 
463
- def verify_observe_options(options)
464
- unless num_replicas
465
- raise Couchbase::Error::Libcouchbase, "cannot detect number of the replicas"
466
- end
467
- unless options[:persisted] || options[:replicated]
468
- raise ArgumentError, "either :persisted or :replicated option must be set"
469
- end
470
- if options[:persisted] && !(1..num_replicas + 1).include?(options[:persisted])
471
- raise ArgumentError, "persisted number should be in range (1..#{num_replicas + 1})"
472
- end
473
- if options[:replicated] && !(1..num_replicas).include?(options[:replicated])
474
- raise ArgumentError, "replicated number should be in range (1..#{num_replicas})"
354
+ def expand_url_options(url)
355
+ if url.is_a? String
356
+ fail ArgumentError.new unless url =~ /^http:\/\//
357
+ uri = URI.new(url)
358
+ { hostname: uri.host, port: uri.port }.merge(path_to_pool_and_bucket(uri.path))
359
+ elsif url.nil?
360
+ {}
361
+ else
362
+ url
475
363
  end
476
364
  end
477
365
 
478
- def do_observe_and_wait(keys, options, &block)
479
- acc = Hash.new do |h, k|
480
- h[k] = Hash.new(0)
481
- h[k][:cas] = [keys[k]] # first position is for master node
482
- h[k]
483
- end
484
- check_condition = lambda do
485
- ok = catch :break do
486
- acc.each do |key, stats|
487
- master = stats[:cas][0]
488
- if master.nil?
489
- # master node doesn't have the key
490
- throw :break
491
- end
492
- if options[:persisted] && (stats[:persisted] < options[:persisted] ||
493
- stats[:cas].count(master) != options[:persisted])
494
- throw :break
495
- end
496
- if options[:replicated] && (stats[:replicated] < options[:replicated] ||
497
- stats[:cas].count(master) != options[:replicated] + 1)
498
- throw :break
499
- end
500
- end
501
- true
502
- end
503
- if ok
504
- if async?
505
- options[:timer].cancel if options[:timer]
506
- keys.each do |k, _|
507
- block.call(Result.new(:key => k,
508
- :cas => acc[k][:cas][0],
509
- :operation => :observe_and_wait))
510
- end
511
- return :async
512
- else
513
- return keys.inject({}){|res, (k, _)| res[k] = acc[k][:cas][0]; res}
514
- end
515
- else
516
- options[:timeout] /= 2
517
- if options[:timeout] > 0
518
- if async?
519
- options[:timer] = create_timer(options[:timeout]) do
520
- do_observe_and_wait(keys, options, &block)
521
- end
522
- return :async
523
- else
524
- # do wait for timeout
525
- run { create_timer(options[:timeout]){} }
526
- # return nil to avoid recursive call
527
- return nil
528
- end
529
- else
530
- err = Couchbase::Error::Timeout.new("the observe request was timed out")
531
- err.instance_variable_set("@operation", :observe_and_wait)
532
- if async?
533
- keys.each do |k, _|
534
- block.call(Result.new(:key => k,
535
- :cas => acc[k][:cas][0],
536
- :operation => :observe_and_wait,
537
- :error => err))
538
- end
539
- return :async
540
- else
541
- err.instance_variable_set("@key", keys.keys)
542
- raise err
543
- end
544
- end
545
- end
546
- end
547
- collect = lambda do |results|
548
- results.each do |res|
549
- if res.completed?
550
- check_condition.call if async?
551
- else
552
- if res.from_master?
553
- acc[res.key][:cas][0] = res.cas
554
- else
555
- acc[res.key][:cas] << res.cas
556
- end
557
- acc[res.key][res.status] += 1
558
- if res.status == :persisted
559
- acc[res.key][:replicated] += 1
560
- end
561
- end
562
- end
563
- end
564
- if async?
565
- observe(keys.keys, options, &collect)
366
+ def expand_node_list
367
+ if @node_list
368
+ Array(@node_list).map { |n| URI.new(n) }
566
369
  else
567
- observe(keys.keys, options).each{|_, v| collect.call(v)}
568
- check_condition.call
370
+ Array(URI.new(base_url))
569
371
  end
570
372
  end
373
+
571
374
  end
572
375
 
573
376
  end
@@ -100,7 +100,6 @@ module Couchbase::Operations
100
100
  # end
101
101
  #
102
102
  def incr(*args)
103
- sync_block_error if !async? && block_given?
104
103
  do_arithmetic(:incr, *args)
105
104
  end
106
105
  alias_method :increment, :incr
@@ -189,7 +188,6 @@ module Couchbase::Operations
189
188
  # end
190
189
  #
191
190
  def decr(*args)
192
- sync_block_error if !async? && block_given?
193
191
  do_arithmetic(:decr, *args)
194
192
  end
195
193
  alias_method :decrement, :decr
@@ -228,31 +226,31 @@ module Couchbase::Operations
228
226
  end
229
227
 
230
228
  def single_arithmetic(op, key, delta, options = {})
231
- if async?
232
- java_async_arithmetic(op, key, delta)
233
- else
234
- result = java_arithmetic(op, key, delta)
235
- set_default_arithmetic_or_raise(key, result, options)
236
- end
229
+ result = case op
230
+ when :incr
231
+ client.incr(key, delta)
232
+ when :decr
233
+ client.decr(key, delta)
234
+ end
235
+
236
+ set_default_arithmetic_or_raise(key, result, options)
237
237
  end
238
238
 
239
239
  def set_default_arithmetic_or_raise(key, result, options)
240
- if result < 0
241
- if options[:initial] || options[:create] || set_default_arithmetic_init?
242
- value = if options[:initial]
243
- options[:initial]
244
- elsif options[:create]
245
- 0
246
- else
247
- default_arithmetic_init_int
248
- end
240
+ return result if result > 0
249
241
 
250
- set(key, value, options) && value
251
- else
252
- not_found_error(true)
253
- end
242
+ if options[:initial] || options[:create] || set_default_arithmetic_init?
243
+ value = if options[:initial]
244
+ options[:initial]
245
+ elsif options[:create]
246
+ 0
247
+ else
248
+ default_arithmetic_init_int
249
+ end
250
+
251
+ set(key, value, options) && value
254
252
  else
255
- result
253
+ not_found_error(true)
256
254
  end
257
255
  end
258
256
 
@@ -280,39 +278,13 @@ module Couchbase::Operations
280
278
  end
281
279
  end
282
280
 
283
- def java_arithmetic(op, key, delta)
284
- case op
285
- when :incr
286
- java_incr(key, delta)
287
- when :decr
288
- java_decr(key, delta)
289
- end
290
- end
291
-
292
- def java_async_arithmetic(op, key, delta)
293
- case op
294
- when :incr
295
- java_async_incr(key, delta)
296
- when :decr
297
- java_async_decr(key, delta)
298
- end
299
- end
300
-
301
- def java_incr(key, delta)
302
- client.incr(key, delta)
303
- end
304
-
305
- def java_async_incr(key, delta)
306
- client.asyncIncr(key, delta)
307
- end
281
+ # def java_async_incr(key, delta)
282
+ # client.asyncIncr(key, delta)
283
+ # end
308
284
 
309
- def java_decr(key, delta)
310
- client.decr(key, delta)
311
- end
312
-
313
- def java_async_decr(key, delta)
314
- client.asyncDecr(key, delta)
315
- end
285
+ # def java_async_decr(key, delta)
286
+ # client.asyncDecr(key, delta)
287
+ # end
316
288
 
317
289
  end
318
290
  end