Just observed that my test cases for broken connections actually act on healthy connections. I mean the following cases:
|
-- Case: the same, but for broken connection. |
|
test:test('loss a broken connection', function(test) |
|
test:plan(2) |
|
|
|
assert(pool.size >= 1, 'test case precondition fails') |
|
|
|
-- Get a connection, make a bad query and loss the |
|
-- connection. |
|
local conn = pool:get() |
|
local ok = pcall(conn.execute, conn, 'bad query') |
|
test:ok(not ok, 'a query actually fails') |
|
conn = nil -- luacheck: no unused |
|
|
|
-- Collect the lost connection. |
|
collectgarbage('collect') |
|
|
|
-- Verify that a pool is aware of collected connections. |
|
test:is(pool.queue:count(), pool.size, 'all connections are put back') |
|
end) |
|
-- Case: get a connection, broke it and put back. |
|
test:test('get, broke and put a connection', function(test) |
|
test:plan(2) |
|
|
|
assert(pool.size >= 1, 'test case precondition fails') |
|
|
|
-- Get a connection and make a bad query. |
|
local conn = pool:get() |
|
local ok = pcall(conn.execute, conn, 'bad query') |
|
test:ok(not ok, 'a query actually fails') |
|
|
|
-- Put the connection back and verify that the pool is full. |
|
pool:put(conn) |
|
test:ok(pool.queue:is_full(), 'a broken connection was given back') |
|
end) |
|
|
|
-- Case: the same, but loss and collect a connection after |
|
-- put. |
|
test:test('get, broke, put and loss a connection', function(test) |
|
test:plan(3) |
|
|
|
assert(pool.size >= 1, 'test case precondition fails') |
|
|
|
-- Get a connection and make a bad query. |
|
local conn = pool:get() |
|
local ok = pcall(conn.execute, conn, 'bad query') |
|
test:ok(not ok, 'a query actually fails') |
|
|
|
-- Put the connection back, loss it and trigger GC. |
|
pool:put(conn) |
|
conn = nil -- luacheck: no unused |
|
collectgarbage('collect') |
|
|
|
-- Verify that the pool is full |
|
test:ok(pool.queue:is_full(), 'a broken connection was given back') |
|
|
|
-- Verify the pool will not be populated by a connection's |
|
-- GC callback. Otherwise :put() will hang. |
|
local item = pool.queue:get() |
|
pool.queue:put(item) |
|
test:ok(true, 'GC callback does not put back a connection that was ' .. |
|
'put manually') |
|
end) |
My initial assumption was that any SQL error (including syntax error) will lead to marking the connection as broken, however it is not so. Only CR_SERVER_LOST or CR_SERVER_GONE_ERROR errors matter here:
|
int err = mysql_errno(raw_conn); |
|
switch (err) { |
|
case CR_SERVER_LOST: |
|
case CR_SERVER_GONE_ERROR: |
|
lua_pushnumber(L, -1); |
|
break; |
|
default: |
|
lua_pushnumber(L, 1); |
|
} |
|
if status ~= 0 then |
|
self.queue:put(status > 0) |
|
return error(datas) |
|
end |
It seems we should find a way to broke a connection from a test. It seems that support of an error injection is needed for Debug build.