tarantool16 0.0.5 → 0.0.6
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 +4 -4
- data/README.md +4 -0
- data/lib/tarantool16/connection/common.rb +10 -4
- data/lib/tarantool16/connection/dumb.rb +120 -7
- data/lib/tarantool16/db.rb +7 -1
- data/lib/tarantool16/dumb_db.rb +23 -28
- data/lib/tarantool16/schema.rb +27 -8
- data/lib/tarantool16/version.rb +1 -1
- data/test/bench_timeout.rb +36 -0
- data/test/config.lua +2 -2
- data/test/helper.rb +32 -3
- data/test/test_dumb.rb +71 -8
- metadata +5 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 34d90ff491fcf45653aa4038a3c2730f67071cf3
|
4
|
+
data.tar.gz: 3352d2894b63e5db9407fd1c621752babfc08ff9
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 34046053a18655464b966e9ad50182c3f947de8c29d63fdca3d291ec364c53538697a97845f8d048a546a5bfc543416456d60b8721e24f287af08b73182de1d0
|
7
|
+
data.tar.gz: a6ce2048a5ed0c7d48040015f2485ea295c57b07ba9bd8ca887fe0ac18c8e17dec2f4184e687fb9e196b58f92f0315eb2b9703430757adf353117c19f2569ea6
|
data/README.md
CHANGED
@@ -10,6 +10,7 @@ module Tarantool16
|
|
10
10
|
class ConnectionError < Error; end
|
11
11
|
class CouldNotConnect < ConnectionError; end
|
12
12
|
class Disconnected < ConnectionError; end
|
13
|
+
class Timeout < ConnectionError; end
|
13
14
|
class Retry < ConnectionError; end
|
14
15
|
class UnexpectedResponse < Error; end
|
15
16
|
|
@@ -31,6 +32,7 @@ module Tarantool16
|
|
31
32
|
else
|
32
33
|
@reconnect = false
|
33
34
|
end
|
35
|
+
@timeout = opts[:timeout]
|
34
36
|
@p = MessagePack::Packer.new
|
35
37
|
@u = MessagePack::Unpacker.new
|
36
38
|
@s = 0
|
@@ -127,10 +129,10 @@ module Tarantool16
|
|
127
129
|
elsif code == nil
|
128
130
|
return Option.error(nil, UnexpectedResponse, "Mailformed response: no code for sync=#{sync}")
|
129
131
|
end
|
130
|
-
|
132
|
+
begin
|
131
133
|
bmap = @u.read
|
132
134
|
body = bmap[IPROTO_DATA] || bmap[IPROTO_ERROR]
|
133
|
-
|
135
|
+
rescue EOFError
|
134
136
|
body = nil
|
135
137
|
end
|
136
138
|
Option.ok(sync, code, body)
|
@@ -139,8 +141,12 @@ module Tarantool16
|
|
139
141
|
end
|
140
142
|
|
141
143
|
def host_port
|
142
|
-
|
143
|
-
[
|
144
|
+
@host =~ /^(.*):([^:]+)$/
|
145
|
+
[$1, $2.to_i]
|
146
|
+
end
|
147
|
+
|
148
|
+
def _ipv6?
|
149
|
+
@host.count(':') > 1
|
144
150
|
end
|
145
151
|
|
146
152
|
def _insert(space_no, tuple, cb)
|
@@ -1,4 +1,10 @@
|
|
1
1
|
require 'socket'
|
2
|
+
require 'io/wait'
|
3
|
+
begin
|
4
|
+
#require 'kgio'
|
5
|
+
rescue LoadError
|
6
|
+
end
|
7
|
+
|
2
8
|
require_relative 'common'
|
3
9
|
module Tarantool16
|
4
10
|
module Connection
|
@@ -61,17 +67,25 @@ module Tarantool16
|
|
61
67
|
unless could_be_connected?
|
62
68
|
raise Disconnected, "connection is closed"
|
63
69
|
end
|
64
|
-
@socket =
|
70
|
+
@socket = Socket.new((_ipv6? ? Socket::AF_INET6 : Socket::AF_INET), Socket::SOCK_STREAM)
|
65
71
|
@socket.setsockopt(::Socket::IPPROTO_TCP, ::Socket::TCP_NODELAY, 1)
|
72
|
+
@socket.sync = true
|
73
|
+
sockaddr = Socket.pack_sockaddr_in(*host_port.reverse)
|
66
74
|
@retry = @reconnect
|
67
|
-
|
75
|
+
if @timeout
|
76
|
+
_connect_nonblock(sockaddr)
|
77
|
+
else
|
78
|
+
@socket.connect(sockaddr)
|
79
|
+
end
|
80
|
+
greeting = _read(IPROTO_GREETING_SIZE)
|
68
81
|
unless greeting && greeting.bytesize == IPROTO_GREETING_SIZE
|
69
82
|
raise Disconnected, "mailformed greeting #{greeting.inspect}"
|
70
83
|
end
|
71
84
|
@nbuf = "\x00\x00\x00\x00\x00".force_encoding('BINARY')
|
72
85
|
parse_greeting greeting
|
73
86
|
authenticate if @user
|
74
|
-
rescue ::Errno::ECONNREFUSED, ::Errno::EPIPE, Disconnected => e
|
87
|
+
rescue ::Errno::ECONNREFUSED, ::Errno::EPIPE, Disconnected, Timeout => e
|
88
|
+
@socket.close rescue nil
|
75
89
|
@socket = nil
|
76
90
|
if !@reconnect
|
77
91
|
@socket = false
|
@@ -82,9 +96,37 @@ module Tarantool16
|
|
82
96
|
raise CouldNotConnect, e.message
|
83
97
|
end
|
84
98
|
|
99
|
+
def _connect_nonblock(sockaddr)
|
100
|
+
expire = now_f + @timeout
|
101
|
+
begin
|
102
|
+
@socket.connect_nonblock(sockaddr)
|
103
|
+
rescue IO::WaitWritable
|
104
|
+
t = [@socket]
|
105
|
+
IO.select(t, t, nil, expire - now_f)
|
106
|
+
begin
|
107
|
+
@socket.connect_nonblock(sockaddr)
|
108
|
+
rescue Errno::EISCONN
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|
112
|
+
|
85
113
|
def syswrite(req)
|
86
|
-
|
87
|
-
|
114
|
+
unless @timeout
|
115
|
+
if @socket.syswrite(req) != req.bytesize
|
116
|
+
raise Retry, "Could not write message"
|
117
|
+
end
|
118
|
+
else
|
119
|
+
expire = now_f
|
120
|
+
begin
|
121
|
+
until req.empty?
|
122
|
+
n = @socket.write_nonblock(req)
|
123
|
+
req = req[n..-1]
|
124
|
+
end
|
125
|
+
rescue IO::WaitWritable
|
126
|
+
_wait_writable(expire - now_f)
|
127
|
+
rescue Errno::EINTR
|
128
|
+
retry
|
129
|
+
end
|
88
130
|
end
|
89
131
|
end
|
90
132
|
|
@@ -94,7 +136,7 @@ module Tarantool16
|
|
94
136
|
end
|
95
137
|
|
96
138
|
def _read_response
|
97
|
-
str =
|
139
|
+
str = _read(5, @nbuf)
|
98
140
|
unless str && str.bytesize == 5
|
99
141
|
# check if we sent request or not
|
100
142
|
begin
|
@@ -109,7 +151,7 @@ module Tarantool16
|
|
109
151
|
end
|
110
152
|
n = parse_size(str)
|
111
153
|
raise n unless ::Integer === n
|
112
|
-
resp =
|
154
|
+
resp = _read(n)
|
113
155
|
raise Disconnected, "disconnected while read response" unless resp && resp.bytesize == n
|
114
156
|
r = parse_response(resp)
|
115
157
|
if r.ok? && r.sync != @s
|
@@ -117,6 +159,77 @@ module Tarantool16
|
|
117
159
|
end
|
118
160
|
r
|
119
161
|
end
|
162
|
+
|
163
|
+
def _read(n, buf=nil)
|
164
|
+
unless @timeout
|
165
|
+
buf ? @socket.read(n, buf) : @socket.read(n)
|
166
|
+
else
|
167
|
+
expire = now_f + @timeout
|
168
|
+
rbuf = nil
|
169
|
+
while n > 0
|
170
|
+
case tbuf = _read_nonblock(n, buf)
|
171
|
+
when String
|
172
|
+
if rbuf
|
173
|
+
rbuf << tbuf
|
174
|
+
else
|
175
|
+
rbuf = tbuf
|
176
|
+
end
|
177
|
+
buf = nil
|
178
|
+
n -= tbuf.size
|
179
|
+
when :wait_readable
|
180
|
+
nf = now_f
|
181
|
+
if expire <= nf
|
182
|
+
raise Timeout, "response timeouted"
|
183
|
+
else
|
184
|
+
_wait_readable(expire - nf)
|
185
|
+
end
|
186
|
+
when nil
|
187
|
+
raise EOFError
|
188
|
+
end
|
189
|
+
end
|
190
|
+
return rbuf
|
191
|
+
end
|
192
|
+
end
|
193
|
+
|
194
|
+
if defined?(Kgio)
|
195
|
+
def _read_nonblock(n, buf)
|
196
|
+
return buf ? Kgio.tryread(@socket, n, buf) : Kgio.tryread(@socket, n)
|
197
|
+
end
|
198
|
+
else
|
199
|
+
def _read_nonblock(n, buf)
|
200
|
+
begin
|
201
|
+
if buf
|
202
|
+
@socket.read_nonblock(n, buf)
|
203
|
+
else
|
204
|
+
@socket.read_nonblock(n)
|
205
|
+
end
|
206
|
+
rescue IO::WaitReadable
|
207
|
+
return :wait_readable
|
208
|
+
rescue Errno::EINTR
|
209
|
+
retry
|
210
|
+
end
|
211
|
+
end
|
212
|
+
end
|
213
|
+
|
214
|
+
if RUBY_ENGINE == 'jruby'
|
215
|
+
def _wait_readable(timeout)
|
216
|
+
IO.select([@socket], nil, nil, timeout)
|
217
|
+
end
|
218
|
+
else
|
219
|
+
def _wait_readable(timeout)
|
220
|
+
@socket.wait(timeout)
|
221
|
+
end
|
222
|
+
end
|
223
|
+
if IO.instance_methods.include?(:wait_writable)
|
224
|
+
def _wait_writable(timeout)
|
225
|
+
@socket.wait_writable(timeout)
|
226
|
+
end
|
227
|
+
else
|
228
|
+
def _wait_writable(timeout)
|
229
|
+
t = [@socket]
|
230
|
+
IO.select(t, t, nil, expire - now_f)
|
231
|
+
end
|
232
|
+
end
|
120
233
|
end
|
121
234
|
end
|
122
235
|
end
|
data/lib/tarantool16/db.rb
CHANGED
@@ -160,7 +160,13 @@ module Tarantool16
|
|
160
160
|
def _select(sno, ino, key, offset, limit, iterator, need_hash, cb)
|
161
161
|
key = [] if key.nil?
|
162
162
|
ino = 0 if ino.nil? && key.is_a?(Array)
|
163
|
-
|
163
|
+
unless iterator.is_a?(Integer)
|
164
|
+
if key.empty? && (Array === key || Hash === key)
|
165
|
+
iterator = ITERATOR_ALL
|
166
|
+
else
|
167
|
+
iterator = ::Tarantool16.iter(iterator)
|
168
|
+
end
|
169
|
+
end
|
164
170
|
if sno.is_a?(Integer) && ino.is_a?(Integer) && (key.is_a?(Array) || key.nil?)
|
165
171
|
return conn._select(sno, ino, key, offset, limit, iterator, cb)
|
166
172
|
end
|
data/lib/tarantool16/dumb_db.rb
CHANGED
@@ -20,36 +20,16 @@ module Tarantool16
|
|
20
20
|
offset = opts[:offset] || 0
|
21
21
|
limit = opts[:limit] || 2**30
|
22
22
|
iterator = opts[:iterator]
|
23
|
-
need_hash = opts
|
24
|
-
key =
|
25
|
-
when nil
|
26
|
-
[]
|
27
|
-
when Array
|
28
|
-
key
|
29
|
-
when Hash
|
30
|
-
need_hash = true
|
31
|
-
key
|
32
|
-
else
|
33
|
-
[key]
|
34
|
-
end
|
23
|
+
need_hash = opts.fetch(:hash, Hash === key)
|
24
|
+
key = _norm_key(key)
|
35
25
|
_select(sno, ino, key, offset, limit, iterator, need_hash, RETURN_OR_RAISE)
|
36
26
|
end
|
37
27
|
|
38
28
|
def get(sno, key, opts={})
|
39
29
|
ino = opts[:index]
|
40
30
|
iterator = opts[:iterator]
|
41
|
-
need_hash = opts
|
42
|
-
key =
|
43
|
-
when nil
|
44
|
-
[]
|
45
|
-
when Array
|
46
|
-
key
|
47
|
-
when Hash
|
48
|
-
need_hash = true
|
49
|
-
key
|
50
|
-
else
|
51
|
-
[key]
|
52
|
-
end
|
31
|
+
need_hash = opts.fetch(:hash, Hash === key)
|
32
|
+
key = _norm_key(key)
|
53
33
|
_select(sno, ino, key, 0, 1, iterator, need_hash, RETURN_ONE_OR_RAISE)
|
54
34
|
end
|
55
35
|
|
@@ -64,14 +44,18 @@ module Tarantool16
|
|
64
44
|
end
|
65
45
|
|
66
46
|
def delete(sno, key, opts = {})
|
67
|
-
|
68
|
-
|
47
|
+
key_hash = Hash === key
|
48
|
+
ino = opts[:index] || (key_hash ? nil : 0)
|
49
|
+
need_hash = opts.fetch(:hash, key_hash)
|
50
|
+
key = _norm_key(key)
|
69
51
|
_delete(sno, ino, key, need_hash, RETURN_OR_RAISE)
|
70
52
|
end
|
71
53
|
|
72
54
|
def update(sno, key, ops, opts = {})
|
73
|
-
|
74
|
-
|
55
|
+
key_hash = Hash === key
|
56
|
+
ino = opts[:index] || (key_hash ? nil : 0)
|
57
|
+
need_hash = opts.fetch(:hash, key_hash)
|
58
|
+
key = _norm_key(key)
|
75
59
|
_update(sno, ino, key, ops, need_hash, RETURN_OR_RAISE)
|
76
60
|
end
|
77
61
|
|
@@ -83,6 +67,17 @@ module Tarantool16
|
|
83
67
|
yield
|
84
68
|
end
|
85
69
|
|
70
|
+
def _norm_key(key)
|
71
|
+
case key
|
72
|
+
when Array
|
73
|
+
key
|
74
|
+
when Hash
|
75
|
+
key
|
76
|
+
else
|
77
|
+
[key]
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
86
81
|
class SchemaFuture
|
87
82
|
UNDEF = Object.new.freeze
|
88
83
|
def initialize
|
data/lib/tarantool16/schema.rb
CHANGED
@@ -70,17 +70,15 @@ module Tarantool16
|
|
70
70
|
@indices && !@indices.empty?
|
71
71
|
end
|
72
72
|
|
73
|
-
def get_ino(ino, key,
|
73
|
+
def get_ino(ino, key, _iter, cb)
|
74
74
|
if ino.nil?
|
75
75
|
unless key.is_a?(Hash)
|
76
76
|
opt = Option.error(SchemaError, "Could not detect index without field names and iterator: #{key.inspect} in #{name_sid}")
|
77
77
|
return cb.call(opt)
|
78
78
|
end
|
79
|
-
unless iter.is_a?(Integer)
|
80
|
-
iter = ::Tarantool16.iter(iter)
|
81
|
-
end
|
82
79
|
# key should be Hash here
|
83
80
|
keys = key.keys
|
81
|
+
keys << _iter
|
84
82
|
_ino = @_fields_2_ino[keys]
|
85
83
|
if _ino
|
86
84
|
ind = @indices[_ino]
|
@@ -89,6 +87,8 @@ module Tarantool16
|
|
89
87
|
opt = Option.error(SchemaError, "Could not detect index for fields #{key.keys} in #{name_sid}")
|
90
88
|
return cb.call(opt)
|
91
89
|
end
|
90
|
+
keys.pop
|
91
|
+
iter = _iter.is_a?(Integer) ? _iter : ::Tarantool16.iter(iter)
|
92
92
|
|
93
93
|
fields = keys.map{|fld|
|
94
94
|
case fld
|
@@ -105,7 +105,7 @@ module Tarantool16
|
|
105
105
|
for ind in @indices
|
106
106
|
next unless ind
|
107
107
|
first_fields = ind.parts[0,fields.size]
|
108
|
-
if ind.can_iterator?(iter)
|
108
|
+
if ind.can_iterator?(iter, fields.size)
|
109
109
|
if fields == first_fields
|
110
110
|
index = ind
|
111
111
|
break
|
@@ -114,6 +114,7 @@ module Tarantool16
|
|
114
114
|
end
|
115
115
|
end
|
116
116
|
end
|
117
|
+
keys << _iter
|
117
118
|
if index
|
118
119
|
@_fields_2_ino[keys.freeze] = index.pos
|
119
120
|
yield index.pos, index.map_key(key)
|
@@ -189,7 +190,15 @@ module Tarantool16
|
|
189
190
|
_op[1] = @field_names[_1].pos
|
190
191
|
_op
|
191
192
|
when Array
|
192
|
-
|
193
|
+
fld_pos = case op[0]
|
194
|
+
when Integer
|
195
|
+
op[0]
|
196
|
+
when Symbol, String
|
197
|
+
@field_names[op[0]].pos
|
198
|
+
else
|
199
|
+
raise "No field #{op[0].inspect} in #{name_sid}"
|
200
|
+
end
|
201
|
+
_1.dup.insert(1, fld_pos)
|
193
202
|
end
|
194
203
|
end
|
195
204
|
end
|
@@ -236,8 +245,18 @@ module Tarantool16
|
|
236
245
|
}
|
237
246
|
end
|
238
247
|
|
239
|
-
def can_iterator?(iter)
|
240
|
-
@iters.include?(iter)
|
248
|
+
def can_iterator?(iter, flds_cnt)
|
249
|
+
@iters.include?(iter) && begin
|
250
|
+
if iter == ITERATOR_ALL
|
251
|
+
true
|
252
|
+
elsif @type == :hash && flds_cnt == @parts.count
|
253
|
+
true
|
254
|
+
elsif flds_cnt == 1
|
255
|
+
true
|
256
|
+
else
|
257
|
+
false
|
258
|
+
end
|
259
|
+
end
|
241
260
|
end
|
242
261
|
|
243
262
|
def map_key(key)
|
data/lib/tarantool16/version.rb
CHANGED
@@ -0,0 +1,36 @@
|
|
1
|
+
require 'tarantool16'
|
2
|
+
require 'timeout'
|
3
|
+
|
4
|
+
def bench_1000_get(kind, timeout=nil)
|
5
|
+
case kind
|
6
|
+
when :no, :external
|
7
|
+
db = Tarantool16.new host: '127.0.0.1:33013'
|
8
|
+
when :native
|
9
|
+
db = Tarantool16.new host: '127.0.0.1:33013', timeout: timeout
|
10
|
+
end
|
11
|
+
now = Time.now.to_f
|
12
|
+
if kind == :external
|
13
|
+
10000.times do
|
14
|
+
Timeout.timeout(1) do
|
15
|
+
db.get(:test, 1)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
else
|
19
|
+
10000.times do
|
20
|
+
db.get(:test, 1)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
r = Time.now.to_f - now
|
24
|
+
db.conn.disconnect
|
25
|
+
r
|
26
|
+
end
|
27
|
+
|
28
|
+
puts "Without timeout: %f" % bench_1000_get(:no, nil)
|
29
|
+
puts "With timeout: %f" % bench_1000_get(:native, 1)
|
30
|
+
puts "With Timeout: %f" % bench_1000_get(:external, 1)
|
31
|
+
puts "Without timeout: %f" % bench_1000_get(:no, nil)
|
32
|
+
puts "With timeout: %f" % bench_1000_get(:native, 1)
|
33
|
+
puts "With Timeout: %f" % bench_1000_get(:external, 1)
|
34
|
+
puts "Without timeout: %f" % bench_1000_get(:no, nil)
|
35
|
+
puts "With timeout: %f" % bench_1000_get(:native, 1)
|
36
|
+
puts "With Timeout: %f" % bench_1000_get(:external, 1)
|
data/test/config.lua
CHANGED
data/test/helper.rb
CHANGED
@@ -62,15 +62,40 @@ class Spawn
|
|
62
62
|
Dir.chdir(@dir) do
|
63
63
|
@pid = spawn(@binary, 'config.lua', {out: log, err: log})
|
64
64
|
end
|
65
|
-
|
65
|
+
100.times do
|
66
|
+
begin
|
67
|
+
TCPSocket.new('127.0.0.1', @admin_port).close
|
68
|
+
return
|
69
|
+
rescue Errno::ECONNREFUSED
|
70
|
+
sleep(0.02)
|
71
|
+
end
|
72
|
+
end
|
73
|
+
raise "NOT CONNECTED"
|
74
|
+
end
|
75
|
+
|
76
|
+
def with_pause
|
77
|
+
Process.kill('STOP', @pid)
|
78
|
+
yield
|
79
|
+
ensure
|
80
|
+
Process.kill('CONT', @pid)
|
66
81
|
end
|
67
82
|
|
68
83
|
def reseed
|
69
84
|
run
|
70
85
|
s = TCPSocket.new '127.0.0.1', @admin_port
|
86
|
+
begin
|
87
|
+
sleep(0.0005)
|
88
|
+
s.read_nonblock(1000)
|
89
|
+
rescue Errno::EWOULDBLOCK
|
90
|
+
retry
|
91
|
+
end
|
71
92
|
s.send("reseed()\n", 0)
|
72
|
-
|
73
|
-
|
93
|
+
begin
|
94
|
+
sleep(0.0005)
|
95
|
+
s.read_nonblock(1000)
|
96
|
+
rescue Errno::EWOULDBLOCK
|
97
|
+
retry
|
98
|
+
end
|
74
99
|
s.close
|
75
100
|
end
|
76
101
|
|
@@ -92,6 +117,10 @@ class Spawn
|
|
92
117
|
inst(what).reseed
|
93
118
|
end
|
94
119
|
|
120
|
+
def self.with_pause(what=:main)
|
121
|
+
inst(what).with_pause{ yield }
|
122
|
+
end
|
123
|
+
|
95
124
|
def self.stop(what=:main)
|
96
125
|
if inst = CONF[what][:inst]
|
97
126
|
inst.stop
|
data/test/test_dumb.rb
CHANGED
@@ -2,9 +2,16 @@ require_relative 'helper'
|
|
2
2
|
|
3
3
|
describe 'DumbConnection' do
|
4
4
|
before { Spawn.reseed }
|
5
|
-
let(:db) { Tarantool16.new host: 'localhost:16788' }
|
6
|
-
let(:r1) { [1, 'hello', [1,2]].deep_freeze }
|
7
|
-
let(:r2) { [2, 'world', [3,4]].deep_freeze }
|
5
|
+
let(:db) { Tarantool16.new host: 'localhost:16788', timeout: 0.1 }
|
6
|
+
let(:r1) { [1, 'hello', [1,2], 100].deep_freeze }
|
7
|
+
let(:r2) { [2, 'world', [3,4], 200].deep_freeze }
|
8
|
+
let(:r3) { [3, 'wicky', [7,10], 300].deep_freeze }
|
9
|
+
|
10
|
+
def rwith(r, fld, val)
|
11
|
+
r=r.dup
|
12
|
+
r[fld]=val
|
13
|
+
r
|
14
|
+
end
|
8
15
|
|
9
16
|
it "should select by pk" do
|
10
17
|
db.select(:test, 1).must_equal [r1]
|
@@ -35,17 +42,41 @@ describe 'DumbConnection' do
|
|
35
42
|
db.select(:test, [[4,4]], index: 2, iterator: "<->").must_equal [r2, r1]
|
36
43
|
end
|
37
44
|
|
45
|
+
it "should iterate with offset and limit" do
|
46
|
+
db.insert(:test, r3)
|
47
|
+
db.select(:test, 1, iterator: :>=, index: 3, limit: 1).must_equal [r1]
|
48
|
+
db.select(:test, 1, iterator: :>=, index: 3, offset: 1).must_equal [r2, r3]
|
49
|
+
db.select(:test, 1, iterator: :>=, index: 3, limit: 1, offset: 1).must_equal [r2]
|
50
|
+
end
|
51
|
+
|
38
52
|
it "should insert" do
|
39
|
-
db.insert(:test,
|
40
|
-
db.select(513,
|
53
|
+
db.insert(:test, r3)
|
54
|
+
db.select(513, 3).must_equal [r3]
|
55
|
+
end
|
56
|
+
|
57
|
+
it "should update" do
|
58
|
+
db.update(:test, 1, [[:+, 3, 1]]).must_equal [rwith(r1,3,101)]
|
59
|
+
db.update(:test, "world", {1 => [':', 6, 0, '!']}, index: 1).must_equal [rwith(r2,1,"world!")]
|
60
|
+
end
|
61
|
+
|
62
|
+
it "should delete" do
|
63
|
+
db.delete(:test, 1).must_equal [r1]
|
64
|
+
db.delete(:test, "world", index: 1).must_equal [r2]
|
41
65
|
end
|
42
66
|
|
43
67
|
describe "with field names" do
|
44
68
|
before {
|
45
|
-
db.define_fields(:test, [[:id, :int], [:name, :str], [:point, :array]])
|
69
|
+
db.define_fields(:test, [[:id, :int], [:name, :str], [:point, :array], [:count, :int]])
|
46
70
|
}
|
47
|
-
let(:h1){ {id:1, name:'hello', point:[1,2]}.deep_freeze }
|
48
|
-
let(:h2){ {id:2, name:'world', point:[3,4]}.deep_freeze }
|
71
|
+
let(:h1){ {id:1, name:'hello', point:[1,2], count:100}.deep_freeze }
|
72
|
+
let(:h2){ {id:2, name:'world', point:[3,4], count:200}.deep_freeze }
|
73
|
+
let(:h3) { {id:3, name:'wicky', point:[7,10], count:300}.deep_freeze }
|
74
|
+
|
75
|
+
def hwith(h, fld, val)
|
76
|
+
h=h.dup
|
77
|
+
h[fld] = val
|
78
|
+
h
|
79
|
+
end
|
49
80
|
|
50
81
|
it "should select by hash" do
|
51
82
|
db.select(:test, {id: 1}).must_equal [h1]
|
@@ -55,6 +86,38 @@ describe 'DumbConnection' do
|
|
55
86
|
it "should iterate" do
|
56
87
|
db.select(:test, {id: 0}, iterator: :>).must_equal [h1, h2]
|
57
88
|
db.select(:test, {id: 4}, iterator: :<).must_equal [h2, h1]
|
89
|
+
db.select(:test, {name: 'hello'}, iterator: :>).must_equal [h2]
|
90
|
+
db.select(:test, {point: [0,0]}, iterator: "<->").must_equal [h1, h2]
|
91
|
+
db.select(:test, {point: [4,4]}, iterator: "<->").must_equal [h2, h1]
|
92
|
+
end
|
93
|
+
|
94
|
+
it "should insert" do
|
95
|
+
db.insert(:test, h3)
|
96
|
+
db.select(513, {id:3}).must_equal [h3]
|
97
|
+
end
|
98
|
+
|
99
|
+
it "should update" do
|
100
|
+
db.update(:test, {id: 1}, [[:+, :count, 1]]).must_equal [hwith(h1, :count, 101)]
|
101
|
+
db.update(:test, {name: "world"}, {count: [:+, 1]}).must_equal [hwith(h2, :count, 201)]
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
describe "timeouts" do
|
106
|
+
it "should timeout on connect" do
|
107
|
+
Spawn.with_pause do
|
108
|
+
proc {
|
109
|
+
db.get(:test, 1)
|
110
|
+
}.must_raise Tarantool16::Connection::CouldNotConnect
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
it "should timeout on request" do
|
115
|
+
db.get(:test, 1)
|
116
|
+
Spawn.with_pause do
|
117
|
+
proc {
|
118
|
+
db.get(:test, 1)
|
119
|
+
}.must_raise Tarantool16::Connection::Timeout
|
120
|
+
end
|
58
121
|
end
|
59
122
|
end
|
60
123
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: tarantool16
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.6
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Sokolov Yura aka funny_falcon
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-08-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -77,6 +77,7 @@ files:
|
|
77
77
|
- lib/tarantool16/schema.rb
|
78
78
|
- lib/tarantool16/version.rb
|
79
79
|
- tarantool16.gemspec
|
80
|
+
- test/bench_timeout.rb
|
80
81
|
- test/config.lua
|
81
82
|
- test/helper.rb
|
82
83
|
- test/test_dumb.rb
|
@@ -100,11 +101,12 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
100
101
|
version: '0'
|
101
102
|
requirements: []
|
102
103
|
rubyforge_project:
|
103
|
-
rubygems_version: 2.4.
|
104
|
+
rubygems_version: 2.4.3
|
104
105
|
signing_key:
|
105
106
|
specification_version: 4
|
106
107
|
summary: adapter for Tarantool 1.6
|
107
108
|
test_files:
|
109
|
+
- test/bench_timeout.rb
|
108
110
|
- test/config.lua
|
109
111
|
- test/helper.rb
|
110
112
|
- test/test_dumb.rb
|