[tarantool-patches] [PATCH] sql: make SQL_BIND optional in an iproto request

Alexander Turenko alexander.turenko at tarantool.org
Tue Mar 26 02:20:16 MSK 2019


The documentation [1] says this field is optional. I don't know which
commit lead to the regression, only that 2.1.1-7-gd381a45b6 is good.

[1]: https://tarantool.io/en/doc/2.1/dev_guide/internals/sql_protocol/

Fixes #4077.
---

https://github.com/tarantool/tarantool/issues/4077
https://github.com/tarantool/tarantool/tree/Totktonada/gh-4077-iproto-execute-no-bind

 src/box/iproto.cc                             |  7 +-
 .../gh-4077-iproto-execute-no-bind.test.lua   | 69 +++++++++++++++++++
 2 files changed, 73 insertions(+), 3 deletions(-)
 create mode 100755 test/sql-tap/gh-4077-iproto-execute-no-bind.test.lua

diff --git a/src/box/iproto.cc b/src/box/iproto.cc
index 3b0ba6234..3c054338b 100644
--- a/src/box/iproto.cc
+++ b/src/box/iproto.cc
@@ -1622,8 +1622,8 @@ tx_process_sql(struct cmsg *m)
 	struct iproto_msg *msg = tx_accept_msg(m);
 	struct obuf *out;
 	struct sql_response response;
-	struct sql_bind *bind;
-	int bind_count;
+	struct sql_bind *bind = NULL;
+	int bind_count = 0;
 	const char *sql;
 	uint32_t len;
 
@@ -1633,7 +1633,8 @@ tx_process_sql(struct cmsg *m)
 		goto error;
 	assert(msg->header.type == IPROTO_EXECUTE);
 	tx_inject_delay();
-	bind_count = sql_bind_list_decode(msg->sql.bind, &bind);
+	if (msg->sql.bind != NULL)
+		bind_count = sql_bind_list_decode(msg->sql.bind, &bind);
 	if (bind_count < 0)
 		goto error;
 	sql = msg->sql.sql_text;
diff --git a/test/sql-tap/gh-4077-iproto-execute-no-bind.test.lua b/test/sql-tap/gh-4077-iproto-execute-no-bind.test.lua
new file mode 100755
index 000000000..55804768c
--- /dev/null
+++ b/test/sql-tap/gh-4077-iproto-execute-no-bind.test.lua
@@ -0,0 +1,69 @@
+#!/usr/bin/env tarantool
+
+local tap = require('tap')
+local net_box = require('net.box')
+local urilib = require('uri')
+local msgpack = require('msgpack')
+
+local IPROTO_REQUEST_TYPE       = 0x00
+local IPROTO_EXECUTE            = 0x0b
+local IPROTO_SYNC               = 0x01
+local IPROTO_SQL_TEXT           = 0x40
+local IPROTO_SQL_INFO           = 0x42
+local IPROTO_SQL_INFO_ROW_COUNT = 0x00
+local IPROTO_OK                 = 0x00
+local IPROTO_SCHEMA_VERSION     = 0x05
+local IPROTO_STATUS_KEY         = 0x00
+
+box.cfg({
+    listen = os.getenv('LISTEN') or 'localhost:3301',
+})
+
+box.schema.user.grant('guest', 'read,write,execute', 'universe')
+box.sql.execute('create table T(ID int primary key)')
+
+local test = tap.test('gh-4077-iproto-execute-no-bind')
+test:plan(3)
+
+local uri = urilib.parse(box.cfg.listen)
+local sock = net_box.establish_connection(uri.host, uri.service)
+
+-- Send request w/o SQL_BIND field in body.
+local next_request_id = 16
+local header = msgpack.encode({
+    [IPROTO_REQUEST_TYPE] = IPROTO_EXECUTE,
+    [IPROTO_SYNC] = next_request_id,
+})
+local body = msgpack.encode({
+    [IPROTO_SQL_TEXT] = 'insert into T values (1)',
+})
+local size = msgpack.encode(header:len() + body:len())
+sock:write(size .. header .. body)
+
+-- Read response.
+local size = msgpack.decode(sock:read(5))
+local header_body = sock:read(size)
+local header, header_len = msgpack.decode(header_body)
+local body = msgpack.decode(header_body:sub(header_len))
+sock:close()
+
+-- Verify response.
+header[IPROTO_SCHEMA_VERSION] = nil -- expect any
+local exp_header = {
+    [IPROTO_STATUS_KEY] = IPROTO_OK,
+    [IPROTO_SYNC] = next_request_id,
+}
+local exp_body = {
+    [IPROTO_SQL_INFO] = {
+        [IPROTO_SQL_INFO_ROW_COUNT] = 1,
+    }
+}
+test:is_deeply(exp_header, header, 'verify response header')
+test:is_deeply(exp_body, body, 'verify response body')
+
+-- Verify space data.
+local exp_res = {{1}}
+local res = box.space.T:pairs():map(box.tuple.totable):totable()
+test:is_deeply(res, exp_res, 'verify inserted data')
+
+os.exit(test:check() == true and 0 or 1)
-- 
2.20.1





More information about the Tarantool-patches mailing list