neo4j-ruby-driver 4.4.0.alpha.4 → 4.4.0.alpha.7

Sign up to get free protection for your applications and to get access to all the features.
Files changed (61) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +1 -0
  3. data/lib/neo4j/driver/exceptions/protocol_exception.rb +2 -2
  4. data/lib/neo4j/driver/internal/bolt_server_address.rb +6 -6
  5. data/lib/neo4j/driver/types/time.rb +4 -2
  6. data/ruby/neo4j/driver/config.rb +1 -1
  7. data/ruby/neo4j/driver/internal/async/inbound/inbound_message_dispatcher.rb +1 -1
  8. data/ruby/neo4j/driver/internal/async/network_connection.rb +15 -22
  9. data/ruby/neo4j/driver/internal/async/network_session.rb +4 -3
  10. data/ruby/neo4j/driver/internal/async/pool/channel.rb +1 -0
  11. data/ruby/neo4j/driver/internal/async/pool/{netty_channel_tracker.rb → channel_tracker.rb} +6 -8
  12. data/ruby/neo4j/driver/internal/async/pool/connection_pool_impl.rb +4 -3
  13. data/ruby/neo4j/driver/internal/cluster/cluster_composition.rb +10 -20
  14. data/ruby/neo4j/driver/internal/cluster/cluster_composition_lookup_result.rb +2 -2
  15. data/ruby/neo4j/driver/internal/cluster/cluster_routing_table.rb +37 -54
  16. data/ruby/neo4j/driver/internal/cluster/identity_resolver.rb +1 -4
  17. data/ruby/neo4j/driver/internal/cluster/loadbalancing/least_connected_load_balancing_strategy.rb +6 -6
  18. data/ruby/neo4j/driver/internal/cluster/loadbalancing/load_balancer.rb +44 -80
  19. data/ruby/neo4j/driver/internal/cluster/multi_databases_routing_procedure_runner.rb +6 -9
  20. data/ruby/neo4j/driver/internal/cluster/rediscovery_impl.rb +65 -155
  21. data/ruby/neo4j/driver/internal/cluster/route_message_routing_procedure_runner.rb +2 -2
  22. data/ruby/neo4j/driver/internal/cluster/routing_procedure_cluster_composition_provider.rb +8 -12
  23. data/ruby/neo4j/driver/internal/cluster/routing_procedure_response.rb +19 -3
  24. data/ruby/neo4j/driver/internal/cluster/routing_table_handler_impl.rb +46 -67
  25. data/ruby/neo4j/driver/internal/cluster/routing_table_registry_impl.rb +42 -61
  26. data/ruby/neo4j/driver/internal/cluster/single_database_routing_procedure_runner.rb +8 -10
  27. data/ruby/neo4j/driver/internal/cursor/async_result_cursor_impl.rb +2 -1
  28. data/ruby/neo4j/driver/internal/cursor/disposable_async_result_cursor.rb +11 -14
  29. data/ruby/neo4j/driver/internal/database_name_util.rb +3 -3
  30. data/ruby/neo4j/driver/internal/default_bookmark_holder.rb +1 -7
  31. data/ruby/neo4j/driver/internal/direct_connection_provider.rb +1 -1
  32. data/ruby/neo4j/driver/internal/driver_factory.rb +4 -4
  33. data/ruby/neo4j/driver/internal/handlers/channel_releasing_reset_response_handler.rb +11 -10
  34. data/ruby/neo4j/driver/internal/handlers/legacy_pull_all_response_handler.rb +35 -25
  35. data/ruby/neo4j/driver/internal/handlers/pulln/auto_pull_response_handler.rb +1 -2
  36. data/ruby/neo4j/driver/internal/handlers/reset_response_handler.rb +1 -1
  37. data/ruby/neo4j/driver/internal/impersonation_util.rb +2 -2
  38. data/ruby/neo4j/driver/internal/internal_bookmark.rb +1 -1
  39. data/ruby/neo4j/driver/internal/internal_database_name.rb +3 -5
  40. data/ruby/neo4j/driver/internal/internal_driver.rb +1 -1
  41. data/ruby/neo4j/driver/internal/messaging/bolt_protocol_version.rb +3 -1
  42. data/ruby/neo4j/driver/internal/messaging/encode/route_message_encoder.rb +8 -2
  43. data/ruby/neo4j/driver/internal/messaging/encode/route_v44_message_encoder.rb +8 -13
  44. data/ruby/neo4j/driver/internal/messaging/request/begin_message.rb +2 -3
  45. data/ruby/neo4j/driver/internal/messaging/request/multi_database_util.rb +2 -2
  46. data/ruby/neo4j/driver/internal/messaging/request/route_message.rb +5 -10
  47. data/ruby/neo4j/driver/internal/messaging/request/run_with_metadata_message.rb +5 -3
  48. data/ruby/neo4j/driver/internal/messaging/request/transaction_metadata_builder.rb +2 -2
  49. data/ruby/neo4j/driver/internal/messaging/v3/bolt_protocol_v3.rb +1 -1
  50. data/ruby/neo4j/driver/internal/messaging/v44/message_writer_v44.rb +1 -1
  51. data/ruby/neo4j/driver/internal/read_only_bookmark_holder.rb +13 -0
  52. data/ruby/neo4j/driver/internal/resolved_bolt_server_address.rb +35 -0
  53. data/ruby/neo4j/driver/internal/security/security_plan_impl.rb +14 -9
  54. data/ruby/neo4j/driver/internal/util/error_util.rb +1 -1
  55. data/ruby/neo4j/driver/net/{server_address1.rb → server_address.rb} +2 -2
  56. data/ruby/neo4j/driver/query.rb +1 -1
  57. data/ruby/neo4j/driver/transaction_config.rb +5 -1
  58. data/ruby/neo4j/driver/values.rb +3 -3
  59. data/ruby/neo4j/driver/version.rb +1 -1
  60. metadata +11 -24
  61. data/ruby/neo4j/driver/internal/database_name.rb +0 -12
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: dceecd30fd6fa4473c3ec6bb640b6126bd7bb06eb5057d58e46064d8c434a929
4
- data.tar.gz: 0e1a77da3ca678a1b4a201fa0d0211a771a009a77bb81b1a0c98e331b22c5471
3
+ metadata.gz: a035a8385e54c70c851003ce4131072610617d515f118d2d4b03f6ada71de3a7
4
+ data.tar.gz: bc8dfddb76165d4aea25d702e1d4bb1be5db3bb375d25f48fab39acb7f247c07
5
5
  SHA512:
6
- metadata.gz: fdd3c4bbdd314fb7036ce6c7fedba8a49e26b194450dea535a7aa05f380d58a6ab04ea7edbba6cf664514c1585084ad0e17c40fb719a9794f127ee3623c169db
7
- data.tar.gz: 673a7aa8a4f3192f7b9b15b91efaca7c05dfcb79779b39ed4f014989db06672f7c293fd3948e16fc515177cae84e428f5885b3f1d3b4c081f05e580afbd66b5d
6
+ metadata.gz: 17a1b5ada9f09120e7dda4316504d59fedf366696d27c26e87c5feeee381a876409a75eaa05cbc177af64415946af7ec8c1de7b4ed5e637ffc464a40c1fd4eea
7
+ data.tar.gz: aa41d20c4794dac6841aa1bf70cb0c3e8573a658e74d8aa4e475f45a2a0a9072056633a83f8744251014ab5a805b6ec368f4a75b036316c2179bc1bcc1f8f8fa
data/README.md CHANGED
@@ -42,6 +42,7 @@ This gem includes 2 different implementations: java driver wrapper and pure ruby
42
42
  ## Testing
43
43
 
44
44
  To run the tests the following tools need to be installed:
45
+
45
46
  $ brew install python
46
47
  $ pip3 install --user git+https://github.com/klobuczek/boltkit@1.3#egg=boltkit
47
48
  $ neoctrl-install -e 4.4.5 servers
@@ -8,8 +8,8 @@ module Neo4j
8
8
  class ProtocolException < Neo4jException
9
9
  CODE = "Protocol violation: "
10
10
 
11
- def initialize(message, e)
12
- super("#{CODE}message", e)
11
+ def initialize(message, e = nil)
12
+ super(nil, "#{CODE}#{message}", e)
13
13
  end
14
14
  end
15
15
  end
@@ -67,13 +67,15 @@ module Neo4j::Driver
67
67
  LOCAL_DEFAULT = new(host: 'localhost', port: DEFAULT_PORT)
68
68
 
69
69
  def self.from(address)
70
- address.is_a?(BoltServerAddress) ? address : new(address.host, address.port)
70
+ address.is_a?(BoltServerAddress) ? address : new(host: address.host, port: address.port)
71
71
  end
72
72
 
73
- def eql?(other)
74
- attributes.eql?(other&.attributes)
73
+ def ==(other)
74
+ attributes == other&.attributes
75
75
  end
76
76
 
77
+ alias eql? ==
78
+
77
79
  def to_s
78
80
  "#{host}#{"(#{connection_host})" unless host == connection_host}:#{port}"
79
81
  end
@@ -84,11 +86,9 @@ module Neo4j::Driver
84
86
 
85
87
  # @return stream of unicast addresses.
86
88
  def unicast_stream
87
- [self]
89
+ Set[self]
88
90
  end
89
91
 
90
- private
91
-
92
92
  def attributes
93
93
  [@host, @connection_host, @port]
94
94
  end
@@ -30,10 +30,12 @@ module Neo4j
30
30
  end
31
31
  end
32
32
 
33
- def eql?(other)
34
- other.is_a?(self.class) && self.class.significant_fields.all? { |elem| send(elem).eql?(other.send(elem)) }
33
+ def ==(other)
34
+ other.is_a?(self.class) && self.class.significant_fields.all? { |elem| send(elem) == other.send(elem) }
35
35
  end
36
36
 
37
+ alias eql? ==
38
+
37
39
  def +(numeric)
38
40
  self.class.new(@time + numeric)
39
41
  end
@@ -79,7 +79,7 @@ module Neo4j
79
79
 
80
80
  def init_security_and_trust_config
81
81
  relevant = %i[encryption trust_strategy]
82
- customized = slice(*relevant) == DEFAULTS.slice(*relevant)
82
+ customized = slice(*relevant) != DEFAULTS.slice(*relevant)
83
83
  merge!(security_settings: Neo4j::Driver::Internal::SecuritySetting.new(
84
84
  fetch(:encryption), TrustStrategy.new(**fetch(:trust_strategy)), customized),
85
85
  )
@@ -151,7 +151,7 @@ module Neo4j::Driver
151
151
  @auto_read_managing_handler.disable_auto_read_management
152
152
 
153
153
  # restore the default value of auto-read
154
- @channel.config.set_auto_read(true)
154
+ @channel.auto_read = true
155
155
  end
156
156
 
157
157
  @auto_read_managing_handler = new_handler
@@ -33,11 +33,11 @@ module Neo4j::Driver
33
33
  end
34
34
 
35
35
  def enable_auto_read
36
- set_auto_read(true) if open?
36
+ @channel.auto_read = true if open?
37
37
  end
38
38
 
39
39
  def disable_auto_read
40
- set_auto_read(false) if open?
40
+ @channel.auto_read = false if open?
41
41
  end
42
42
 
43
43
  def flush
@@ -69,13 +69,12 @@ module Neo4j::Driver
69
69
 
70
70
  def release
71
71
  if @status.compare_and_set(Status::OPEN, Status::RELEASED)
72
- @channel_pool.release(@channel)
72
+ handler = Handlers::ChannelReleasingResetResponseHandler.new(@channel, @channel_pool, @message_dispatcher, @log, @release)
73
+ write_reset_message_if_needed(handler, false)
74
+ # @metrics_listener.after_connection_released(Connection::ChannelAttributes.pool_id(@channel), @in_use_event)
75
+ # end
76
+ # @release_future
73
77
  end
74
- # handler = Handlers::ChannelReleasingResetResponseHandler.new(@channel, @channel_pool, @message_dispatcher, @clock, @release)
75
- # write_reset_message_if_needed(handler, false)
76
- # @metrics_listener.after_connection_released(Connection::ChannelAttributes.pool_id(@channel), @in_use_event)
77
- # end
78
- # @release_future
79
78
  end
80
79
 
81
80
  def terminate_and_release(reason)
@@ -91,15 +90,13 @@ module Neo4j::Driver
91
90
  private
92
91
 
93
92
  def write_reset_message_if_needed(reset_handler, is_session_reset)
94
- @channel.event_loop.execute do
95
- if is_session_reset && !open?
96
- reset_handler.on_success(java.util.Collections.empty_map)
97
- else
98
- # auto-read could've been disabled, re-enable it to automatically receive response for RESET
99
- set_auto_read(true)
100
- @message_dispatcher.enqueue(reset_handler)
101
- @channel.write_and_flush(Messaging::Request::ResetMessage::RESET).add_listener(-> (_future) { register_connection_read_timeout(@channel) })
102
- end
93
+ if is_session_reset && !open?
94
+ reset_handler.on_success
95
+ else
96
+ # auto-read could've been disabled, re-enable it to automatically receive response for RESET
97
+ @channel.auto_read = true
98
+ @message_dispatcher.enqueue(reset_handler)
99
+ @channel.write_and_flush(Messaging::Request::ResetMessage::RESET)#.add_listener(-> (_future) { register_connection_read_timeout(@channel) })
103
100
  end
104
101
  end
105
102
 
@@ -114,7 +111,7 @@ module Neo4j::Driver
114
111
  @message_dispatcher.enqueue(handler)
115
112
 
116
113
  if flush
117
- @channel.write_and_flush(message)#.add_listener(-> (_future) { register_connection_read_timeout(@channel) })
114
+ @channel.write_and_flush(message) #.add_listener(-> (_future) { register_connection_read_timeout(@channel) })
118
115
  else
119
116
  @channel.write(message)
120
117
  end
@@ -135,10 +132,6 @@ module Neo4j::Driver
135
132
  end
136
133
  end
137
134
 
138
- def set_auto_read(value)
139
- @channel.config.set_auto_read(value)
140
- end
141
-
142
135
  def verify_open(handler1, handler2)
143
136
  connection_status = @status.get
144
137
 
@@ -10,8 +10,8 @@ module Neo4j::Driver
10
10
  @retry_logic = retry_logic
11
11
  @log = Logging::PrefixedLogger.new("[#{hash}]", logger)
12
12
  @bookmark_holder = bookmark_holder
13
- @database_name = database_name.database_name
14
- @connection_context = NetworkSessionConnectionContext.new(@database_name, @bookmark_holder.bookmark, impersonated_user)
13
+ # @database_name = database_name.database_name
14
+ @connection_context = NetworkSessionConnectionContext.new(database_name, @bookmark_holder.bookmark, impersonated_user)
15
15
  @fetch_size = fetch_size
16
16
  @open = Concurrent::AtomicBoolean.new(true)
17
17
  end
@@ -133,7 +133,8 @@ module Neo4j::Driver
133
133
  # This bookmark is only used for rediscovery.
134
134
  # It has to be the initial bookmark given at the creation of the session.
135
135
  # As only that bookmark could carry extra system bookmarks
136
- attr_reader :database_name, :mode, :rediscovery_bookmark, :impersonated_user
136
+ attr_accessor :database_name
137
+ attr :mode, :rediscovery_bookmark, :impersonated_user
137
138
 
138
139
  def initialize(database_name, bookmark, impersonated_user)
139
140
  @database_name = database_name
@@ -6,6 +6,7 @@ module Neo4j::Driver
6
6
  attr :stream
7
7
  attr_accessor :version, :protocol, :message_format, :message_dispatcher
8
8
  attr :attributes # should be attr
9
+ attr_accessor :auto_read
9
10
 
10
11
  def initialize(address, connector, logger)
11
12
  super()
@@ -2,22 +2,20 @@ module Neo4j::Driver
2
2
  module Internal
3
3
  module Async
4
4
  module Pool
5
- class NettyChannelTracker
5
+ class ChannelTracker
6
6
  attr_reader :lock, :read, :write, :address_to_in_use_channel_count, :address_to_idle_channel_count, :log,
7
7
  :metrics_listener, :close_listener, :all_channels
8
8
 
9
- def initialize(metrics_listener, logger, options = {},event_executor = nil, channels = nil)
9
+ def initialize(metrics_listener, logger, **options)
10
10
  @metrics_listener = metrics_listener
11
11
  @log = logger
12
- @all_channels = options[:channels] ? channels : Java::IoNettyChannelGroup::DefaultChannelGroup.new("all-connections", options[:event_executor])
13
- @lock = java.util.concurrent.locks.ReentrantReadWriteLock.new
14
- @read = lock.read_lock
15
- @write = lock.write_lock
16
- @close_listener = -> (future) { channel_closed(future.channel) }
12
+ @all_channels = options[:channels]
13
+ @lock = Concurrent::ReentrantReadWriteLock.new
14
+ @close_listener = method(:channel_closed)
17
15
  end
18
16
 
19
17
  def channel_released(channel)
20
- do_in_write_lock do
18
+ @lock.with_write_lock do
21
19
  decrement_in_use(channel)
22
20
  increment_idle(channel)
23
21
  channel.close_future.add_listener(close_listener)
@@ -20,6 +20,7 @@ module Neo4j::Driver
20
20
 
21
21
  begin
22
22
  channel = pool.acquire
23
+ @log.debug{"Channel #{channel.object_id} acquired"}
23
24
  rescue => error
24
25
  process_acquisition_error(pool, address, error)
25
26
  end
@@ -31,8 +32,7 @@ module Neo4j::Driver
31
32
  @address_to_pool_lock.with_write_lock do
32
33
  @address_to_pool.each do |address, pool|
33
34
  unless addresses_to_retain.include?(address)
34
- active_channels = @netty_channel_tracker.in_use_channel_count(address)
35
- if active_channels.zero?
35
+ unless pool.busy?
36
36
  # address is not present in updated routing table and has no active connections
37
37
  # it's now safe to terminate corresponding connection pool and forget about it
38
38
  @address_to_pool.delete(address)
@@ -47,7 +47,8 @@ module Neo4j::Driver
47
47
  end
48
48
 
49
49
  def in_use_connections(address)
50
- @netty_channel_tracker.in_use_channel_count(address)
50
+ @address_to_pool[address]&.size || 0
51
+ # @netty_channel_tracker.in_use_channel_count(address)
51
52
  end
52
53
 
53
54
  def idle_connections(address)
@@ -2,45 +2,35 @@ module Neo4j::Driver
2
2
  module Internal
3
3
  module Cluster
4
4
  class ClusterComposition < Struct.new(:expiration_timestamp, :readers, :writers, :routers, :database_name)
5
- private
6
-
7
- MAX_LONG = 2 ^ 63 - 1
8
- MAX_TTL = MAX_LONG / 1000
9
-
10
- public
11
-
12
5
  def initialize(expiration_timestamp:, database_name:, readers: [], writers: [], routers: [])
13
6
  super(expiration_timestamp, readers, writers, routers, database_name)
14
7
  end
15
8
 
16
9
  def has_writers?
17
- @writers.present?
10
+ writers.present?
18
11
  end
19
12
 
20
13
  def has_routers_and_readers?
21
- @routers.present? && @readers.present?
14
+ routers.present? && readers.present?
22
15
  end
23
16
 
24
17
  def self.parse(record, now)
25
- return if record.nil?
26
- new(expiration_timestamp: expiration_timestamp(now, record), database_name: record['db'],
27
- **record['servers'].to_h { |value| [servers(value['role']), BoltServerAddress.new(value['addresses'])] })
18
+ return unless record
19
+ new(expiration_timestamp: expiration_timestamp(now, record), database_name: record[:db],
20
+ **record[:servers].to_h do |value|
21
+ [servers(value[:role]),
22
+ value[:addresses].map { |address| BoltServerAddress.new(uri: BoltServerAddress.uri_from(address)) }]
23
+ end)
28
24
  end
29
25
 
30
26
  private
31
27
 
32
28
  def self.expiration_timestamp(now, record)
33
29
  ttl = record['ttl']
34
- expiration_timestamp = now + ttl * 1000
35
-
36
- if ttl < 0 || ttl >= MAX_TTL || expiration_timestamp < 0
37
- expiration_timestamp = MAX_LONG
38
- end
39
-
40
- expiration_timestamp
30
+ now + (ttl.negative? ? 1000.years : ttl.seconds)
41
31
  end
42
32
 
43
- def servers(role)
33
+ def self.servers(role)
44
34
  case role
45
35
  when 'READ'
46
36
  :readers
@@ -2,10 +2,10 @@ module Neo4j::Driver
2
2
  module Internal
3
3
  module Cluster
4
4
  class ClusterCompositionLookupResult
5
- attr_reader :composition, :resolved_initial_routers
5
+ attr_reader :cluster_composition, :resolved_initial_routers
6
6
 
7
7
  def initialize(composition, resolved_initial_routers = nil)
8
- @composition = composition
8
+ @cluster_composition = composition
9
9
  @resolved_initial_routers = resolved_initial_routers
10
10
  end
11
11
  end
@@ -4,39 +4,32 @@ module Neo4j::Driver
4
4
  class ClusterRoutingTable
5
5
  MIN_ROUTERS = 1
6
6
 
7
- attr_reader :database_name
8
-
9
- def initialize(of_database, clock, routing_addresses)
7
+ def initialize(of_database, _clock, *routing_addresses)
10
8
  @database_name = of_database
11
- @clock = clock
12
- @expiration_timestamp = clock.millis - 1
13
- @routers = routing_addresses.freeze
14
- @table_lock = java.util.concurrent.locks.ReentrantReadWriteLock.new
9
+ @expiration_timestamp = Time.now
10
+ @routers = routing_addresses.to_set.freeze
11
+ @table_lock = Concurrent::ReentrantReadWriteLock.new
15
12
  @prefer_initial_router = true
16
- @disused = {}
17
- @readers = []
18
- @writers = []
13
+ @disused = Set.new
14
+ @readers = Set.new
15
+ @writers = Set.new
19
16
  end
20
17
 
21
18
  def stale_for?(mode)
22
- Util::LockUtil.execute_with_lock(@table_lock.read_lock) do
23
- @expiration_timestamp < @clock.millis ||
24
- routers.size < MIN_ROUTERS ||
25
- (mode == AccessMode::READ && @readers.size == 0) ||
26
- (mode == AccessMode::WRITE && @writers.size == 0)
19
+ @table_lock.with_read_lock do
20
+ @expiration_timestamp <= Time.now ||
21
+ routers.size < MIN_ROUTERS ||
22
+ (mode == AccessMode::READ && @readers.size == 0) ||
23
+ (mode == AccessMode::WRITE && @writers.size == 0)
27
24
  end
28
25
  end
29
26
 
30
27
  def has_been_stale_for?(extra_time)
31
- total_time = Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @expiration_timestamp }) + extra_time
32
-
33
- total_time = java.lang.Long::MAX_VALUE if total_time < 0
34
-
35
- total_time < @clock.millis
28
+ Time.now - @table_lock.with_read_lock { @expiration_timestamp } >= extra_time
36
29
  end
37
30
 
38
31
  def update(cluster)
39
- Util::LockUtil.execute_with_lock(@table_lock.write_lock) do
32
+ @table_lock.with_write_lock do
40
33
  @expiration_timestamp = cluster.expiration_timestamp
41
34
  @readers = new_with_reused_addresses(@readers, @disused, cluster.readers)
42
35
  @writers = new_with_reused_addresses(@writers, @disused, cluster.writers)
@@ -47,7 +40,7 @@ module Neo4j::Driver
47
40
  end
48
41
 
49
42
  def forget(address)
50
- Util::LockUtil.execute_with_lock(@table_lock.write_lock) do
43
+ @table_lock.with_write_lock do
51
44
  @routers = new_without_address_if_present(@routers, address)
52
45
  @readers = new_without_address_if_present(@readers, address)
53
46
  @writers = new_without_address_if_present(@writers, address)
@@ -56,27 +49,27 @@ module Neo4j::Driver
56
49
  end
57
50
 
58
51
  def readers
59
- Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @readers })
52
+ @table_lock.with_read_lock { @readers }
60
53
  end
61
54
 
62
55
  def writers
63
- Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @writers })
56
+ @table_lock.with_read_lock { @writers }
64
57
  end
65
58
 
66
59
  def routers
67
- Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @routers })
60
+ @table_lock.with_read_lock { @routers }
68
61
  end
69
62
 
70
63
  def servers
71
- Util::LockUtil.execute_with_lock(@table_lock.write_lock) do
72
- servers = []
73
- servers << (@readers)
74
- servers << (@writers)
75
- servers << (@routers)
76
- servers << (@disused)
64
+ @table_lock.with_write_lock do
65
+ [@readers, @writers, @routers, @disused].reduce(&:+)
77
66
  end
78
67
  end
79
68
 
69
+ def database
70
+ @database_name
71
+ end
72
+
80
73
  def forget_writer(to_remove)
81
74
  Util::LockUtil.execute_with_lock(@table_lock.write_lock) do
82
75
  @writers = new_without_address_if_present(@writers, to_remove)
@@ -85,53 +78,43 @@ module Neo4j::Driver
85
78
  end
86
79
 
87
80
  def replace_router_if_present(old_router, new_router)
88
- Util::LockUtil.execute_with_lock(@table_lock.write_lock, -> () { @routers = new_with_address_replaced_if_present(@routers, old_router, new_router) } )
81
+ @table_lock.with_write_lock { @routers = new_with_address_replaced_if_present(@routers, old_router, new_router) }
89
82
  end
90
83
 
91
84
  def prefer_initial_router
92
- Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @prefer_initial_router })
85
+ @table_lock.with_read_lock { @prefer_initial_router }
93
86
  end
94
87
 
95
88
  def expiration_timestamp
96
- Util::LockUtil.execute_with_lock(@table_lock.read_lock, -> () { @expiration_timestamp })
89
+ @table_lock.with_read_lock { @expiration_timestamp }
97
90
  end
98
91
 
99
92
  def to_s
100
- Util::LockUtil.execute_with_lock(@table_lock.read_lock) do
101
- "Ttl #{@expiration_timestamp}, currentTime #{@clock.millis}, routers #{@routers}, writers #{@writers}, readers #{@readers}, database '#{database_name.description}'"
93
+ @table_lock.with_read_lock do
94
+ "Ttl #{@expiration_timestamp}, currentTime #{Time.now}, routers #{@routers}, writers #{@writers}, readers #{@readers}, database '#{@database_name.description}'"
102
95
  end
103
96
  end
104
97
 
105
98
  private
106
99
 
107
100
  def new_without_address_if_present(addresses, address_to_skip)
108
- new_list = []
109
-
110
- addresses.each do |address|
111
- new_list << address unless address.eql?(address_to_skip)
112
- end
113
-
114
- new_list.freeze
101
+ (addresses - [address_to_skip]).freeze
115
102
  end
116
103
 
117
104
  def new_with_address_replaced_if_present(addresses, old_address, new_address)
118
- new_list = []
119
-
120
- addresses.each { |address| new_list << address.eql?(old_address) ? new_address : address }
121
-
122
- new_list.freeze
105
+ addresses.map { |address| address == old_address ? new_address : address }.freeze
123
106
  end
124
107
 
125
108
  def new_with_reused_addresses(current_addresses, disused_addresses, new_addresses)
126
- new_list = java.util.stream.Stream.concat(current_addresses.stream, disused_addresses.stream)
127
- .filter(-> (address) { new_addresses.remove(to_bolt_server_address(address)) })
128
- .collect(java.util.stream.Collectors.to_collection(-> () { Array.new(new_addresses.size) }))
129
- new_list << new_addresses
130
- new_list.freeze
109
+ (current_addresses + disused_addresses + new_addresses).freeze
131
110
  end
132
111
 
133
112
  def to_bolt_server_address(address)
134
- BoltServerAddress.class.eql?(address.class) ? address : BoltServerAddress.new(address.host, address.port)
113
+ if BoltServerAddress.class == address.class
114
+ address
115
+ else
116
+ BoltServerAddress.new(host: address.host, port: address.port)
117
+ end
135
118
  end
136
119
  end
137
120
  end
@@ -3,10 +3,7 @@ module Neo4j::Driver
3
3
  module Cluster
4
4
  class IdentityResolver
5
5
  IDENTITY_RESOLVER = new
6
-
7
- def resolve(initial_router)
8
- java.util.Collections.singleton(initial_router)
9
- end
6
+ alias resolve Array
10
7
  end
11
8
  end
12
9
  end
@@ -28,10 +28,9 @@ module Neo4j::Driver
28
28
 
29
29
  def select(addresses, addresses_index, address_type)
30
30
  size = addresses.size
31
-
32
31
  if size == 0
33
32
  @log.debug("Unable to select #{address_type}, no known addresses given")
34
- return nil
33
+ return
35
34
  end
36
35
 
37
36
  # choose start index for iteration in round-robin fashion
@@ -39,22 +38,23 @@ module Neo4j::Driver
39
38
  index = start_index
40
39
 
41
40
  least_connected_address = nil
42
- least_active_connections = java.lang.Integer::MAX_VALUE
41
+ least_active_connections = nil
43
42
 
44
43
  # iterate over the array to find the least connected address
44
+ addresses = addresses.to_a
45
45
  loop do
46
46
  address = addresses[index]
47
47
  active_connections = @connection_pool.in_use_connections(address)
48
48
 
49
- if active_connections < least_active_connections
49
+ if least_active_connections.nil? || active_connections < least_active_connections
50
50
  least_connected_address = address
51
51
  least_active_connections = active_connections
52
52
  end
53
53
 
54
54
  # loop over to the start of the array when end is reached
55
- index = (index == size - 1) ? 0 : index += 1
55
+ index = (index + 1) % size
56
56
 
57
- break if index != start_index
57
+ break if index == start_index
58
58
  end
59
59
 
60
60
  @log.debug("Selected #{address_type} with address: '#{least_connected_address}' and active connections: #{least_active_connections}")