riak-client 1.0.0.beta → 1.0.0
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/.gitignore +7 -4
- data/Gemfile +12 -17
- data/Guardfile +1 -1
- data/LICENSE +16 -0
- data/README.markdown +178 -0
- data/RELEASE_NOTES.md +99 -0
- data/Rakefile +25 -1
- data/erl_src/riak_kv_test014_backend.beam +0 -0
- data/erl_src/riak_kv_test014_backend.erl +189 -0
- data/erl_src/riak_kv_test_backend.beam +0 -0
- data/erl_src/riak_kv_test_backend.erl +37 -19
- data/lib/riak/client.rb +322 -272
- data/lib/riak/client/beefcake_protobuffs_backend.rb +6 -10
- data/lib/riak/client/decaying.rb +28 -0
- data/lib/riak/client/excon_backend.rb +27 -11
- data/lib/riak/client/http_backend.rb +71 -2
- data/lib/riak/client/http_backend/configuration.rb +17 -3
- data/lib/riak/client/http_backend/transport_methods.rb +3 -3
- data/lib/riak/client/net_http_backend.rb +18 -14
- data/lib/riak/client/node.rb +111 -0
- data/lib/riak/client/pool.rb +180 -0
- data/lib/riak/client/protobuffs_backend.rb +15 -5
- data/lib/riak/client/search.rb +9 -3
- data/lib/riak/link.rb +5 -7
- data/lib/riak/locale/en.yml +1 -0
- data/lib/riak/node/configuration.rb +1 -0
- data/lib/riak/node/defaults.rb +19 -6
- data/lib/riak/node/generation.rb +9 -2
- data/lib/riak/node/log.rb +2 -2
- data/lib/riak/node/version.rb +22 -16
- data/lib/riak/robject.rb +19 -3
- data/lib/riak/serializers.rb +1 -1
- data/lib/riak/test_server.rb +10 -2
- data/lib/riak/version.rb +1 -1
- data/riak-client.gemspec +3 -3
- data/spec/failover/failover.rb +59 -0
- data/spec/integration/riak/http_backends_spec.rb +2 -2
- data/spec/integration/riak/node_spec.rb +16 -24
- data/spec/integration/riak/protobuffs_backends_spec.rb +1 -1
- data/spec/integration/riak/test_server_spec.rb +4 -3
- data/spec/integration/riak/threading_spec.rb +193 -0
- data/spec/riak/beefcake_protobuffs_backend/object_methods_spec.rb +23 -0
- data/spec/riak/beefcake_protobuffs_backend_spec.rb +4 -2
- data/spec/riak/bucket_spec.rb +2 -1
- data/spec/riak/client_spec.rb +80 -181
- data/spec/riak/excon_backend_spec.rb +3 -2
- data/spec/riak/http_backend/configuration_spec.rb +37 -5
- data/spec/riak/http_backend/object_methods_spec.rb +1 -1
- data/spec/riak/http_backend/transport_methods_spec.rb +2 -2
- data/spec/riak/http_backend_spec.rb +53 -3
- data/spec/riak/map_reduce_spec.rb +1 -1
- data/spec/riak/net_http_backend_spec.rb +1 -2
- data/spec/riak/node_spec.rb +173 -0
- data/spec/riak/pool_spec.rb +306 -0
- data/spec/riak/robject_spec.rb +8 -4
- data/spec/riak/search_spec.rb +66 -15
- data/spec/riak/serializers_spec.rb +12 -1
- data/spec/spec_helper.rb +9 -1
- data/spec/support/http_backend_implementation_examples.rb +6 -2
- data/spec/support/sometimes.rb +46 -0
- data/spec/support/test_server.rb +50 -19
- data/spec/support/unified_backend_examples.rb +11 -10
- data/spec/support/version_filter.rb +14 -0
- metadata +40 -29
- data/lib/active_support/cache/riak_store.rb +0 -2
- data/lib/riak/cache_store.rb +0 -84
- data/lib/riak/client/pump.rb +0 -30
- data/lib/riak/util/fiber1.8.rb +0 -48
- data/spec/integration/riak/cache_store_spec.rb +0 -129
@@ -3,7 +3,6 @@ require 'riak/json'
|
|
3
3
|
require 'riak/client'
|
4
4
|
require 'riak/failed_request'
|
5
5
|
require 'riak/client/protobuffs_backend'
|
6
|
-
require 'riak/client/pump'
|
7
6
|
|
8
7
|
module Riak
|
9
8
|
class Client
|
@@ -91,11 +90,10 @@ module Riak
|
|
91
90
|
req = RpbListKeysReq.new(:bucket => maybe_encode(bucket))
|
92
91
|
write_protobuff(:ListKeysReq, req)
|
93
92
|
keys = []
|
94
|
-
pump = Pump.new(block) if block_given?
|
95
93
|
while msg = decode_response
|
96
94
|
break if msg.done
|
97
|
-
if
|
98
|
-
|
95
|
+
if block_given?
|
96
|
+
yield msg.keys
|
99
97
|
else
|
100
98
|
keys += msg.keys
|
101
99
|
end
|
@@ -107,13 +105,10 @@ module Riak
|
|
107
105
|
req = RpbMapRedReq.new(:request => mr.to_json, :content_type => "application/json")
|
108
106
|
write_protobuff(:MapRedReq, req)
|
109
107
|
results = []
|
110
|
-
pump = Pump.new(lambda do |msg|
|
111
|
-
block.call msg.phase, JSON.parse(msg.response)
|
112
|
-
end) if block_given?
|
113
108
|
while msg = decode_response
|
114
109
|
break if msg.done
|
115
|
-
if
|
116
|
-
|
110
|
+
if block_given?
|
111
|
+
yield msg.phase, JSON.parse(msg.response)
|
117
112
|
else
|
118
113
|
results[msg.phase] ||= []
|
119
114
|
results[msg.phase] += JSON.parse(msg.response)
|
@@ -176,7 +171,8 @@ module Riak
|
|
176
171
|
end
|
177
172
|
rescue SystemCallError, SocketError => e
|
178
173
|
reset_socket
|
179
|
-
raise
|
174
|
+
raise
|
175
|
+
#raise Riak::ProtobuffsFailedRequest.new(:server_error, e.message)
|
180
176
|
end
|
181
177
|
end
|
182
178
|
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
class Riak::Client::Decaying
|
2
|
+
# A float which decays exponentially with time.
|
3
|
+
|
4
|
+
attr_accessor :e
|
5
|
+
attr_accessor :p
|
6
|
+
# @param[:p] The initial value
|
7
|
+
# @param[:e] Exponent base
|
8
|
+
# @param[:r] Timescale
|
9
|
+
def initialize(opts = {})
|
10
|
+
@p = opts[:p] || 0
|
11
|
+
@e = opts[:e] || Math::E
|
12
|
+
@r = opts[:r] || Math.log(0.5) / 10
|
13
|
+
@t0 = Time.now
|
14
|
+
end
|
15
|
+
|
16
|
+
# Add d to current value.
|
17
|
+
def <<(d)
|
18
|
+
@p = value + d
|
19
|
+
end
|
20
|
+
|
21
|
+
# Return current value
|
22
|
+
def value
|
23
|
+
now = Time.now
|
24
|
+
dt = now - @t0
|
25
|
+
@t0 = now
|
26
|
+
@p = @p * (@e ** (@r * dt))
|
27
|
+
end
|
28
|
+
end
|
@@ -1,8 +1,6 @@
|
|
1
|
-
|
2
1
|
require 'riak/failed_request'
|
3
2
|
require 'riak/client/http_backend'
|
4
3
|
require 'riak/client/http_backend/request_headers'
|
5
|
-
require 'riak/client/pump'
|
6
4
|
|
7
5
|
module Riak
|
8
6
|
class Client
|
@@ -13,15 +11,36 @@ module Riak
|
|
13
11
|
def self.configured?
|
14
12
|
begin
|
15
13
|
require 'excon'
|
16
|
-
|
14
|
+
Client::NETWORK_ERRORS << Excon::Errors::SocketError
|
15
|
+
Client::NETWORK_ERRORS.uniq!
|
16
|
+
Excon::VERSION >= "0.5.7" && patch_excon
|
17
17
|
rescue LoadError
|
18
18
|
false
|
19
19
|
end
|
20
20
|
end
|
21
21
|
|
22
|
+
# Adjusts Excon's connection collection to allow multiple
|
23
|
+
# connections to the same host from the same Thread. Instead we
|
24
|
+
# use the Riak::Client::Pool to segregate connections.
|
25
|
+
# @note This can be changed when Excon has a proper pool of its own.
|
26
|
+
def self.patch_excon
|
27
|
+
unless defined? @@patched
|
28
|
+
::Excon::Connection.class_eval do
|
29
|
+
def sockets
|
30
|
+
@sockets ||= {}
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
@@patched = true
|
35
|
+
end
|
36
|
+
|
37
|
+
def teardown
|
38
|
+
connection.reset
|
39
|
+
end
|
40
|
+
|
22
41
|
private
|
23
42
|
def perform(method, uri, headers, expect, data=nil, &block)
|
24
|
-
configure_ssl if @
|
43
|
+
configure_ssl if @node.ssl_enabled?
|
25
44
|
|
26
45
|
params = {
|
27
46
|
:method => method.to_s.upcase,
|
@@ -32,11 +51,8 @@ module Riak
|
|
32
51
|
params[:body] = data if [:put,:post].include?(method)
|
33
52
|
params[:idempotent] = (method != :post)
|
34
53
|
|
35
|
-
|
36
|
-
|
37
|
-
# Later versions of Excon pass multiple arguments to the block
|
38
|
-
block = lambda {|*args| pump.pump(args.first) }
|
39
|
-
end
|
54
|
+
# Later versions of Excon pass multiple arguments to the block
|
55
|
+
block = lambda {|*args| yield args.first } if block_given?
|
40
56
|
|
41
57
|
response = connection.request(params, &block)
|
42
58
|
response_headers.initialize_http_header(response.headers)
|
@@ -57,8 +73,8 @@ module Riak
|
|
57
73
|
end
|
58
74
|
|
59
75
|
def configure_ssl
|
60
|
-
Excon.ssl_verify_peer = @
|
61
|
-
Excon.ssl_ca_path = @
|
76
|
+
Excon.ssl_verify_peer = @node.ssl_options[:verify_mode].to_s === "peer"
|
77
|
+
Excon.ssl_ca_path = @node.ssl_options[:ca_path] if @node.ssl_options[:ca_path]
|
62
78
|
end
|
63
79
|
end
|
64
80
|
end
|
@@ -29,11 +29,17 @@ module Riak
|
|
29
29
|
# The Riak::Client that uses this backend
|
30
30
|
attr_reader :client
|
31
31
|
|
32
|
+
# The Riak::Client::Node that uses this backend
|
33
|
+
attr_reader :node
|
34
|
+
|
32
35
|
# Create an HTTPBackend for the Riak::Client.
|
33
|
-
# @param [Client]
|
34
|
-
|
36
|
+
# @param [Client] The client
|
37
|
+
# @param [Node] The node we're connecting to.
|
38
|
+
def initialize(client, node)
|
35
39
|
raise ArgumentError, t("client_type", :client => client) unless Client === client
|
40
|
+
raise ArgumentError, t("node_type", :node => node) unless Node === node
|
36
41
|
@client = client
|
42
|
+
@node = node
|
37
43
|
end
|
38
44
|
|
39
45
|
# Pings the server
|
@@ -246,6 +252,69 @@ module Riak
|
|
246
252
|
def update_search_index(index, updates)
|
247
253
|
post(200, solr_update_path(index), updates, {'Content-Type' => 'text/xml'})
|
248
254
|
end
|
255
|
+
|
256
|
+
# (Luwak) Fetches a file from the Luwak large-file interface.
|
257
|
+
# @param [String] filename the name of the file
|
258
|
+
# @yield [chunk] A block which will receive individual chunks of
|
259
|
+
# the file as they are streamed
|
260
|
+
# @yieldparam [String] chunk a block of the file
|
261
|
+
# @return [IO, nil] the file (also having content_type and
|
262
|
+
# original_filename accessors). The file will need to be
|
263
|
+
# reopened to be read
|
264
|
+
def get_file(filename, &block)
|
265
|
+
if block_given?
|
266
|
+
get(200, luwak_path(filename), &block)
|
267
|
+
nil
|
268
|
+
else
|
269
|
+
tmpfile = LuwakFile.new(escape(filename))
|
270
|
+
begin
|
271
|
+
response = get(200, luwak_path(filename)) do |chunk|
|
272
|
+
tmpfile.write chunk
|
273
|
+
end
|
274
|
+
tmpfile.content_type = response[:headers]['content-type'].first
|
275
|
+
tmpfile
|
276
|
+
ensure
|
277
|
+
tmpfile.close
|
278
|
+
end
|
279
|
+
end
|
280
|
+
end
|
281
|
+
|
282
|
+
# (Luwak) Detects whether a file exists in the Luwak large-file
|
283
|
+
# interface.
|
284
|
+
# @param [String] filename the name of the file
|
285
|
+
# @return [true,false] whether the file exists
|
286
|
+
def file_exists?(filename)
|
287
|
+
result = head([200,404], luwak_path(filename))
|
288
|
+
result[:code] == 200
|
289
|
+
end
|
290
|
+
|
291
|
+
# (Luwak) Deletes a file from the Luwak large-file interface.
|
292
|
+
# @param [String] filename the name of the file
|
293
|
+
def delete_file(filename)
|
294
|
+
delete([204,404], luwak_path(filename))
|
295
|
+
end
|
296
|
+
|
297
|
+
# (Luwak) Uploads a file to the Luwak large-file interface.
|
298
|
+
# @overload store_file(filename, content_type, data)
|
299
|
+
# Stores the file at the given key/filename
|
300
|
+
# @param [String] filename the key/filename for the object
|
301
|
+
# @param [String] content_type the MIME Content-Type for the data
|
302
|
+
# @param [IO, String] data the contents of the file
|
303
|
+
# @overload store_file(content_type, data)
|
304
|
+
# Stores the file with a server-determined key/filename
|
305
|
+
# @param [String] content_type the MIME Content-Type for the data
|
306
|
+
# @param [String, #read] data the contents of the file
|
307
|
+
# @return [String] the key/filename where the object was stored
|
308
|
+
def store_file(*args)
|
309
|
+
data, content_type, filename = args.reverse
|
310
|
+
if filename
|
311
|
+
put(204, luwak_path(filename), data, {"Content-Type" => content_type})
|
312
|
+
filename
|
313
|
+
else
|
314
|
+
response = post(201, luwak_path(nil), data, {"Content-Type" => content_type})
|
315
|
+
response[:headers]["location"].first.split("/").last
|
316
|
+
end
|
317
|
+
end
|
249
318
|
end
|
250
319
|
end
|
251
320
|
end
|
@@ -132,6 +132,16 @@ module Riak
|
|
132
132
|
end
|
133
133
|
end
|
134
134
|
|
135
|
+
# @return [URI] a URL path for the Luwak interface
|
136
|
+
def luwak_path(key)
|
137
|
+
raise t('luwak_unsupported') unless luwak_wm_file
|
138
|
+
if key
|
139
|
+
path(luwak_wm_file, escape(key))
|
140
|
+
else
|
141
|
+
path(luwak_wm_file)
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
135
145
|
private
|
136
146
|
def server_config
|
137
147
|
@server_config ||= {}.tap do |hash|
|
@@ -152,15 +162,15 @@ module Riak
|
|
152
162
|
end
|
153
163
|
|
154
164
|
def riak_kv_wm_raw
|
155
|
-
server_config[:riak_kv_wm_raw] ||
|
165
|
+
server_config[:riak_kv_wm_raw] || node.http_paths[:prefix]
|
156
166
|
end
|
157
167
|
|
158
168
|
def riak_kv_wm_link_walker
|
159
|
-
server_config[:riak_kv_wm_link_walker] ||
|
169
|
+
server_config[:riak_kv_wm_link_walker] || node.http_paths[:prefix]
|
160
170
|
end
|
161
171
|
|
162
172
|
def riak_kv_wm_mapred
|
163
|
-
server_config[:riak_kv_wm_mapred] ||
|
173
|
+
server_config[:riak_kv_wm_mapred] || node.http_paths[:mapred]
|
164
174
|
end
|
165
175
|
|
166
176
|
def riak_kv_wm_ping
|
@@ -178,6 +188,10 @@ module Riak
|
|
178
188
|
def riak_solr_indexer_wm
|
179
189
|
server_config[:riak_solr_indexer_wm]
|
180
190
|
end
|
191
|
+
|
192
|
+
def luwak_wm_file
|
193
|
+
server_config[:luwak_wm_file]
|
194
|
+
end
|
181
195
|
end
|
182
196
|
end
|
183
197
|
end
|
@@ -140,13 +140,13 @@ module Riak
|
|
140
140
|
end
|
141
141
|
|
142
142
|
def basic_auth_header
|
143
|
-
@
|
143
|
+
@node.basic_auth ? {"Authorization" => "Basic #{Base64::encode64(@node.basic_auth)}"} : {}
|
144
144
|
end
|
145
145
|
|
146
146
|
# @return [URI] The calculated root URI for the Riak HTTP endpoint
|
147
147
|
def root_uri
|
148
|
-
protocol =
|
149
|
-
URI.parse("#{protocol}://#{
|
148
|
+
protocol = node.ssl_enabled? ? "https" : "http"
|
149
|
+
URI.parse("#{protocol}://#{node.host}:#{node.http_port}")
|
150
150
|
end
|
151
151
|
|
152
152
|
# Calculates an absolute URI from a relative path specification
|
@@ -27,11 +27,15 @@ module Riak
|
|
27
27
|
@read_timeout ||= 4096
|
28
28
|
end
|
29
29
|
|
30
|
+
# Net::HTTP doesn't use persistent connections, so there's no
|
31
|
+
# work to do here.
|
32
|
+
def teardown; end
|
33
|
+
|
30
34
|
private
|
31
35
|
def perform(method, uri, headers, expect, data=nil) #:nodoc:
|
32
36
|
http = Net::HTTP.new(uri.host, uri.port)
|
33
37
|
http.read_timeout = self.class.read_timeout
|
34
|
-
configure_ssl(http) if @
|
38
|
+
configure_ssl(http) if @node.ssl_enabled?
|
35
39
|
|
36
40
|
request = Net::HTTP.const_get(method.to_s.capitalize).new(uri.request_uri, headers)
|
37
41
|
case data
|
@@ -51,28 +55,28 @@ module Riak
|
|
51
55
|
|
52
56
|
{}.tap do |result|
|
53
57
|
http.request(request) do |response|
|
54
|
-
|
55
|
-
result.merge!({:headers => response.to_hash, :code => response.code.to_i})
|
56
|
-
response.read_body {|chunk| yield chunk } if block_given?
|
57
|
-
if return_body?(method, response.code, block_given?)
|
58
|
-
result[:body] = response.body
|
59
|
-
end
|
60
|
-
else
|
58
|
+
unless valid_response?(expect, response.code)
|
61
59
|
raise Riak::HTTPFailedRequest.new(method, expect, response.code.to_i, response.to_hash, response.body)
|
62
60
|
end
|
61
|
+
|
62
|
+
result.merge!({:headers => response.to_hash, :code => response.code.to_i})
|
63
|
+
response.read_body {|chunk| yield chunk } if block_given?
|
64
|
+
if return_body?(method, response.code, block_given?)
|
65
|
+
result[:body] = response.body
|
66
|
+
end
|
63
67
|
end
|
64
68
|
end
|
65
69
|
end
|
66
70
|
|
67
71
|
def configure_ssl(http)
|
68
72
|
http.use_ssl = true
|
69
|
-
http.verify_mode = OpenSSL::SSL.const_get("VERIFY_#{@
|
70
|
-
if @
|
71
|
-
http.cert = OpenSSL::X509::Certificate.new(@
|
72
|
-
http.key = OpenSSL::PKey::RSA.new(@
|
73
|
+
http.verify_mode = OpenSSL::SSL.const_get("VERIFY_#{@node.ssl_options[:verify_mode].upcase}")
|
74
|
+
if @node.ssl_options[:pem]
|
75
|
+
http.cert = OpenSSL::X509::Certificate.new(@node.ssl_options[:pem])
|
76
|
+
http.key = OpenSSL::PKey::RSA.new(@node.ssl_options[:pem], @node.ssl_options[:pem_password])
|
73
77
|
end
|
74
|
-
http.ca_file = @
|
75
|
-
http.ca_path = @
|
78
|
+
http.ca_file = @node.ssl_options[:ca_file] if @node.ssl_options[:ca_file]
|
79
|
+
http.ca_path = @node.ssl_options[:ca_path] if @node.ssl_options[:ca_path]
|
76
80
|
end
|
77
81
|
end
|
78
82
|
end
|
@@ -0,0 +1,111 @@
|
|
1
|
+
module Riak
|
2
|
+
class Client
|
3
|
+
class Node
|
4
|
+
# Represents a single riak node in a cluster.
|
5
|
+
|
6
|
+
include Util::Translation
|
7
|
+
include Util::Escape
|
8
|
+
|
9
|
+
VALID_OPTIONS = [:host, :http_port, :pb_port, :http_paths, :prefix,
|
10
|
+
:mapred, :luwak, :solr, :port, :basic_auth, :ssl_options, :ssl]
|
11
|
+
|
12
|
+
# For a score which halves in 10 seconds, choose
|
13
|
+
# ln(1/2)/10
|
14
|
+
ERRORS_DECAY_RATE = Math.log(0.5)/10
|
15
|
+
|
16
|
+
# What IP address or hostname does this node listen on?
|
17
|
+
attr_accessor :host
|
18
|
+
# Which port does the HTTP interface listen on?
|
19
|
+
attr_accessor :http_port
|
20
|
+
# Which port does the protocol buffers interface listen on?
|
21
|
+
attr_accessor :pb_port
|
22
|
+
# A hash of HTTP paths used on this node.
|
23
|
+
attr_accessor :http_paths
|
24
|
+
# A "user:password" string.
|
25
|
+
attr_reader :basic_auth
|
26
|
+
attr_accessor :ssl_options
|
27
|
+
# A Decaying rate of errors.
|
28
|
+
attr_reader :error_rate
|
29
|
+
|
30
|
+
def initialize(client, opts = {})
|
31
|
+
@client = client
|
32
|
+
@ssl = opts[:ssl]
|
33
|
+
@ssl_options = opts[:ssl_options]
|
34
|
+
@host = opts[:host] || "127.0.0.1"
|
35
|
+
@http_port = opts[:http_port] || opts[:port] || 8098
|
36
|
+
@pb_port = opts[:pb_port] || 8087
|
37
|
+
@http_paths = {
|
38
|
+
:prefix => opts[:prefix] || "/riak/",
|
39
|
+
:mapred => opts[:mapred] || "/mapred",
|
40
|
+
:luwak => opts[:luwak] || "/luwak",
|
41
|
+
:solr => opts[:solr] || "/solr" # Unused?
|
42
|
+
}.merge(opts[:http_paths] || {})
|
43
|
+
self.basic_auth = opts[:basic_auth]
|
44
|
+
|
45
|
+
@error_rate = Decaying.new
|
46
|
+
end
|
47
|
+
|
48
|
+
def ==(o)
|
49
|
+
o.kind_of? Node and
|
50
|
+
@host == o.host and
|
51
|
+
@http_port == o.http_port and
|
52
|
+
@pb_port == o.pb_port
|
53
|
+
end
|
54
|
+
|
55
|
+
# Sets the HTTP Basic Authentication credentials.
|
56
|
+
# @param [String] value an auth string in the form "user:password"
|
57
|
+
def basic_auth=(value)
|
58
|
+
case value
|
59
|
+
when nil
|
60
|
+
@basic_auth = nil
|
61
|
+
when String
|
62
|
+
raise ArgumentError, t("invalid_basic_auth") unless value.to_s.split(':').length === 2
|
63
|
+
@basic_auth = value
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
# Can this node be used for HTTP requests?
|
68
|
+
def http?
|
69
|
+
# TODO: Need to sort out capabilities
|
70
|
+
true
|
71
|
+
end
|
72
|
+
|
73
|
+
# Can this node be used for protocol buffers requests?
|
74
|
+
def protobuffs?
|
75
|
+
# TODO: Need to sort out capabilities
|
76
|
+
true
|
77
|
+
end
|
78
|
+
|
79
|
+
# Enables or disables SSL on this node to be utilized by the HTTP
|
80
|
+
# Backends
|
81
|
+
def ssl=(value)
|
82
|
+
@ssl_options = Hash === value ? value : {}
|
83
|
+
value ? ssl_enable : ssl_disable
|
84
|
+
end
|
85
|
+
|
86
|
+
# Checks if SSL is enabled for HTTP
|
87
|
+
def ssl_enabled?
|
88
|
+
@client.protocol == 'https' || @ssl_options.present?
|
89
|
+
end
|
90
|
+
|
91
|
+
def ssl_enable
|
92
|
+
@client.protocol = 'https'
|
93
|
+
@ssl_options[:pem] = File.read(@ssl_options[:pem_file]) if @ssl_options[:pem_file]
|
94
|
+
@ssl_options[:verify_mode] ||= "peer" if @ssl_options.stringify_keys.any? {|k,v| %w[pem ca_file ca_path].include?(k)}
|
95
|
+
@ssl_options[:verify_mode] ||= "none"
|
96
|
+
raise ArgumentError.new(t('invalid_ssl_verify_mode', :invalid => @ssl_options[:verify_mode])) unless %w[none peer].include?(@ssl_options[:verify_mode])
|
97
|
+
|
98
|
+
@ssl_options
|
99
|
+
end
|
100
|
+
|
101
|
+
def ssl_disable
|
102
|
+
@client.protocol = 'http'
|
103
|
+
@ssl_options = nil
|
104
|
+
end
|
105
|
+
|
106
|
+
def inspect
|
107
|
+
"<#Node #{@host}:#{@http_port}:#{@pb_port}>"
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|