* [tarantool-patches] [box.ctl 0/3] Introduce box.ctl.on_ctl_event trigger @ 2018-06-14 15:04 Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event Ilya Markov ` (2 more replies) 0 siblings, 3 replies; 7+ messages in thread From: Ilya Markov @ 2018-06-14 15:04 UTC (permalink / raw) To: georgy; +Cc: tarantool-patches Ilya Markov (3): box.ctl: Introduce stab box.ctl.on_ctl_event box.ctl: Add on_ctl_event trigger calls box.ctl: Add replica error event branch: gh-3159-box-on-ctl-event src/box/CMakeLists.txt | 1 + src/box/alter.cc | 1 + src/box/box.cc | 53 +++++++- src/box/box.h | 1 + src/box/ctl.c | 63 +++++++++ src/box/ctl.h | 82 ++++++++++++ src/box/engine.c | 14 ++ src/box/lua/cfg.cc | 12 ++ src/box/lua/ctl.c | 55 ++++++++ src/box/lua/ctl.h | 2 + src/box/lua/load_cfg.lua | 10 +- src/box/memtx_engine.c | 2 +- src/box/relay.cc | 7 + src/box/replication.cc | 14 ++ src/cfg.c | 37 ++++++ src/cfg.h | 4 + test/replication/master_onctl.lua | 37 ++++++ test/replication/onctl.result | 262 +++++++++++++++++++++++++++++++++++++ test/replication/onctl.test.lua | 108 +++++++++++++++ test/replication/replica_onctl.lua | 34 +++++ test/replication/suite.cfg | 1 + 21 files changed, 796 insertions(+), 4 deletions(-) create mode 100644 src/box/ctl.c create mode 100644 src/box/ctl.h create mode 100644 test/replication/master_onctl.lua create mode 100644 test/replication/onctl.result create mode 100644 test/replication/onctl.test.lua create mode 100644 test/replication/replica_onctl.lua -- 2.7.4 ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event 2018-06-14 15:04 [tarantool-patches] [box.ctl 0/3] Introduce box.ctl.on_ctl_event trigger Ilya Markov @ 2018-06-14 15:04 ` Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event Ilya Markov 2 siblings, 1 reply; 7+ messages in thread From: Ilya Markov @ 2018-06-14 15:04 UTC (permalink / raw) To: georgy; +Cc: tarantool-patches Add required for trigger on_ctl_event structures and lua bindings. Prerequisite #3259 --- src/box/CMakeLists.txt | 1 + src/box/box.cc | 9 ++++++ src/box/box.h | 1 + src/box/ctl.c | 63 +++++++++++++++++++++++++++++++++++++ src/box/ctl.h | 81 ++++++++++++++++++++++++++++++++++++++++++++++++ src/box/lua/cfg.cc | 12 +++++++ src/box/lua/ctl.c | 51 ++++++++++++++++++++++++++++++ src/box/lua/ctl.h | 2 ++ src/box/lua/load_cfg.lua | 10 +++++- src/cfg.c | 37 ++++++++++++++++++++++ src/cfg.h | 4 +++ 11 files changed, 270 insertions(+), 1 deletion(-) create mode 100644 src/box/ctl.c create mode 100644 src/box/ctl.h diff --git a/src/box/CMakeLists.txt b/src/box/CMakeLists.txt index 6b1ae3e..74f6b54 100644 --- a/src/box/CMakeLists.txt +++ b/src/box/CMakeLists.txt @@ -112,6 +112,7 @@ add_library(box STATIC journal.c wal.c call.c + ctl.c ${lua_sources} lua/init.c lua/call.c diff --git a/src/box/box.cc b/src/box/box.cc index 61bfa11..26277e7 100644 --- a/src/box/box.cc +++ b/src/box/box.cc @@ -72,6 +72,7 @@ #include "call.h" #include "func.h" #include "sequence.h" +#include "ctl.h" static char status[64] = "unknown"; @@ -823,6 +824,13 @@ box_set_net_msg_max(void) IPROTO_FIBER_POOL_SIZE_FACTOR); } +void +box_set_on_ctl_event(void) +{ + if (cfg_reset_on_ctl_event() < 0) + diag_raise(); +} + /* }}} configuration bindings */ /** @@ -1808,6 +1816,7 @@ box_cfg_xc(void) box_set_replication_connect_timeout(); box_set_replication_connect_quorum(); box_set_replication_skip_conflict(); + box_set_on_ctl_event(); replication_sync_lag = box_check_replication_sync_lag(); xstream_create(&join_stream, apply_initial_join_row); xstream_create(&subscribe_stream, apply_row); diff --git a/src/box/box.h b/src/box/box.h index d396789..0325527 100644 --- a/src/box/box.h +++ b/src/box/box.h @@ -191,6 +191,7 @@ void box_set_replication_connect_timeout(void); void box_set_replication_connect_quorum(void); void box_set_replication_skip_conflict(void); void box_set_net_msg_max(void); +void box_set_on_ctl_event(void); extern "C" { #endif /* defined(__cplusplus) */ diff --git a/src/box/ctl.c b/src/box/ctl.c new file mode 100644 index 0000000..fc3ae37 --- /dev/null +++ b/src/box/ctl.c @@ -0,0 +1,63 @@ +/* + * Copyright 2010-2018, Tarantool AUTHORS, please see AUTHORS file. + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * 1. Redistributions of source code must retain the above + * copyright notice, this list of conditions and the + * following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY <COPYRIGHT HOLDER> ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL + * <COPYRIGHT HOLDER> OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF + * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ +#include <lib/small/small/rlist.h> +#include <trigger.h> +#include <box/ctl.h> +#include "errcode.h" +#include "error.h" +#include <exception.h> + +RLIST_HEAD(on_ctl_event); + +int +run_on_ctl_event_triggers(const struct on_ctl_event_ctx *result) { + return trigger_run(&on_ctl_event, (void *) result); +} + +int +run_on_ctl_event_trigger_type(enum ctl_event_type type) +{ + struct on_ctl_event_ctx ctx = {}; + ctx.type = type; + return run_on_ctl_event_triggers(&ctx); +} + +int +cfg_reset_on_ctl_event() +{ + if (cfg_reset_trigger("on_ctl_event", &on_ctl_event, + lbox_push_on_ctl_event, NULL) < 0) { + diag_set(ClientError, ER_CFG, "on_ctl_event", + "expected function or table"); + return -1; + } + return 0; +} \ No newline at end of file diff --git a/src/box/ctl.h b/src/box/ctl.h new file mode 100644 index 0000000..1dbb6be --- /dev/null +++ b/src/box/ctl.h @@ -0,0 +1,81 @@ +#ifndef INCLUDES_TARANTOOL_CTL_H +#define INCLUDES_TARANTOOL_CTL_H + +/* + * Copyright 2010-2018, Tarantool AUTHORS, please see AUTHORS file. + * + * Redistribution and use in source and binary forms, with or + * without modification, are permitted provided that the following + * conditions are met: + * + * 1. Redistributions of source code must retain the above + * copyright notice, this list of conditions and the + * following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY <COPYRIGHT HOLDER> ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL + * <COPYRIGHT HOLDER> OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF + * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <cfg.h> +#include <box/lua/ctl.h> +#include "errcode.h" +#include "error.h" +#include <exception.h> + +/** Global on-ctl_event triggers. */ +extern struct rlist on_ctl_event; + +enum ctl_event_type { + CTL_EVENT_SYSTEM_SPACE_RECOVERY, + CTL_EVENT_LOCAL_RECOVERY, + CTL_EVENT_READ_ONLY, + CTL_EVENT_READ_WRITE, + CTL_EVENT_SHUTDOWN, + CTL_EVENT_REPLICASET_ADD, + CTL_EVENT_REPLICASET_REMOVE, +}; + +struct on_ctl_event_ctx { + enum ctl_event_type type; + uint32_t replica_id; +}; + +#if defined(__cplusplus) +extern "C" { +#endif /* defined(__cplusplus) */ + +/** + * Runs on_ctl_event triggers with specified context. + */ +int +run_on_ctl_event_triggers(const struct on_ctl_event_ctx *result); + +/** + * Runs on_ctl_event triggers with specified type. + */ +int +run_on_ctl_event_trigger_type(enum ctl_event_type type); + +int +cfg_reset_on_ctl_event(); +#if defined(__cplusplus) +} /* extern "C" */ +#endif /* defined(__cplusplus) */ + +#endif /* INCLUDES_TARANTOOL_LUA_CTL_H */ diff --git a/src/box/lua/cfg.cc b/src/box/lua/cfg.cc index 5afebc9..c92478f 100644 --- a/src/box/lua/cfg.cc +++ b/src/box/lua/cfg.cc @@ -254,6 +254,17 @@ lbox_cfg_set_net_msg_max(struct lua_State *L) } static int +lbox_cfg_set_on_ctl_event(struct lua_State *L) +{ + try { + box_set_on_ctl_event(); + } catch (Exception *) { + luaT_error(L); + } + return 0; +} + +static int lbox_cfg_set_worker_pool_threads(struct lua_State *L) { (void) L; @@ -331,6 +342,7 @@ box_lua_cfg_init(struct lua_State *L) {"cfg_set_replication_skip_conflict", lbox_cfg_set_replication_skip_conflict}, {"cfg_set_replication_connect_timeout", lbox_cfg_set_replication_connect_timeout}, {"cfg_set_net_msg_max", lbox_cfg_set_net_msg_max}, + {"cfg_set_on_ctl_event", lbox_cfg_set_on_ctl_event}, {NULL, NULL} }; diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c index 9a105ed..52f320a 100644 --- a/src/box/lua/ctl.c +++ b/src/box/lua/ctl.c @@ -35,6 +35,8 @@ #include <lua.h> #include <lauxlib.h> #include <lualib.h> +#include <lua/trigger.h> +#include <box/ctl.h> #include "lua/utils.h" @@ -64,9 +66,37 @@ lbox_ctl_wait_rw(struct lua_State *L) return 0; } + +int +lbox_push_on_ctl_event(struct lua_State *L, void *event) +{ + struct on_ctl_event_ctx *ctx = (struct on_ctl_event_ctx *) event; + lua_newtable(L); + lua_pushstring(L, "type"); + lua_pushinteger(L, ctx->type); + lua_settable(L, -3); + + if (ctx->type == CTL_EVENT_REPLICASET_ADD || + ctx->type == CTL_EVENT_REPLICASET_REMOVE) { + lua_pushstring(L, "replica_id"); + luaL_pushuint64(L, ctx->replica_id); + lua_settable(L, -3); + } + return 1; +} + +static int +lbox_on_ctl_event(struct lua_State *L) +{ + return lbox_trigger_reset(L, 2, &on_ctl_event, + lbox_push_on_ctl_event, NULL); +} + + static const struct luaL_Reg lbox_ctl_lib[] = { {"wait_ro", lbox_ctl_wait_ro}, {"wait_rw", lbox_ctl_wait_rw}, + {"on_ctl_event", lbox_on_ctl_event}, {NULL, NULL} }; @@ -75,4 +105,25 @@ box_lua_ctl_init(struct lua_State *L) { luaL_register_module(L, "box.ctl", lbox_ctl_lib); lua_pop(L, 1); + + luaL_findtable(L, LUA_GLOBALSINDEX, "box.ctl", 1); + lua_newtable(L); + lua_setfield(L, -2, "event"); + lua_getfield(L, -1, "event"); + + lua_pushnumber(L, CTL_EVENT_SYSTEM_SPACE_RECOVERY); + lua_setfield(L, -2, "SYSTEM_SPACE_RECOVERY"); + lua_pushnumber(L, CTL_EVENT_LOCAL_RECOVERY); + lua_setfield(L, -2, "LOCAL_RECOVERY"); + lua_pushnumber(L, CTL_EVENT_READ_ONLY); + lua_setfield(L, -2, "READ_ONLY"); + lua_pushnumber(L, CTL_EVENT_READ_WRITE); + lua_setfield(L, -2, "READ_WRITE"); + lua_pushnumber(L, CTL_EVENT_SHUTDOWN); + lua_setfield(L, -2, "SHUTDOWN"); + lua_pushnumber(L, CTL_EVENT_REPLICASET_ADD); + lua_setfield(L, -2, "CTL_EVENT_REPLICASET_ADD"); + lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); + lua_setfield(L, -2, "CTL_EVENT_REPLICASET_REMOVE"); + lua_pop(L, 2); /* box, ctl */ } diff --git a/src/box/lua/ctl.h b/src/box/lua/ctl.h index e7c2edd..ab63232 100644 --- a/src/box/lua/ctl.h +++ b/src/box/lua/ctl.h @@ -41,6 +41,8 @@ struct lua_State; void box_lua_ctl_init(struct lua_State *L); +int +lbox_push_on_ctl_event(struct lua_State *L, void *event); #if defined(__cplusplus) } /* extern "C" */ #endif /* defined(__cplusplus) */ diff --git a/src/box/lua/load_cfg.lua b/src/box/lua/load_cfg.lua index 0b668cd..c4d1347 100644 --- a/src/box/lua/load_cfg.lua +++ b/src/box/lua/load_cfg.lua @@ -1,7 +1,11 @@ -- load_cfg.lua - internal file local log = require('log') -local json = require('json') +local json = require("json").new() +json.cfg{ + encode_use_tostring = true, +} + local private = require('box.internal') local urilib = require('uri') local math = require('math') @@ -64,6 +68,7 @@ local default_cfg = { feedback_host = "https://feedback.tarantool.io", feedback_interval = 3600, net_msg_max = 768, + on_ctl_event = nil, } -- types of available options @@ -125,6 +130,7 @@ local template_cfg = { feedback_host = 'string', feedback_interval = 'number', net_msg_max = 'number', + on_ctl_event = 'function, table', } local function normalize_uri(port) @@ -216,6 +222,7 @@ local dynamic_cfg = { replicaset_uuid = check_replicaset_uuid, replication_skip_conflict = private.cfg_set_replication_skip_conflict, net_msg_max = private.cfg_set_net_msg_max, + on_ctl_event = private.cfg_set_on_ctl_event, } local dynamic_cfg_skip_at_load = { @@ -232,6 +239,7 @@ local dynamic_cfg_skip_at_load = { force_recovery = true, instance_uuid = true, replicaset_uuid = true, + on_ctl_event = true, } local function convert_gb(size) diff --git a/src/cfg.c b/src/cfg.c index 7c7d6e7..b07c1f3 100644 --- a/src/cfg.c +++ b/src/cfg.c @@ -153,3 +153,40 @@ cfg_getarr_elem(const char *name, int i) lua_pop(tarantool_L, 2); return val; } + +int +cfg_reset_trigger(const char *name, struct rlist *list, + lbox_push_event_f push_event, lbox_pop_event_f pop_event) +{ + cfg_get(name); + struct lua_State *L = tarantool_L; + if (lua_isnil(L, -1)) + return 0; + if (!lua_isfunction(L, -1) && !lua_istable(L, -1)) { + return -1; + } + if (lua_istable(L, -1)) { + lua_pushinteger(L, 1); + lua_gettable(L, -2); + if (!luaL_isnull(L, lua_gettop(L)) && !lua_isfunction(L, -1)) + return -1; + bool is_nil = luaL_isnull(L, lua_gettop(L)); + if (is_nil) { + lua_pop(L, 1); + lua_pushnil(L); + } + lua_pushinteger(L, 2); + lua_gettable(L, -3); + if (!lua_isfunction(L, -1) && !lua_isnil(L, -1)) + return -1; + if (is_nil && lua_isnil(L, -1)) { + return 0; + } + } else { + lua_pushnil(L); + } + int rc = lbox_trigger_reset(L, lua_gettop(L), list, + push_event, pop_event); + lua_pop(L, 1); + return rc; +} \ No newline at end of file diff --git a/src/cfg.h b/src/cfg.h index 8499388..d36465c 100644 --- a/src/cfg.h +++ b/src/cfg.h @@ -32,6 +32,7 @@ */ #include <stdint.h> +#include <lua/trigger.h> #if defined(__cplusplus) extern "C" { @@ -61,6 +62,9 @@ cfg_getarr_size(const char *name); const char * cfg_getarr_elem(const char *name, int i); +int +cfg_reset_trigger(const char *name, struct rlist *list, + lbox_push_event_f push_event, lbox_pop_event_f pop_event); #if defined(__cplusplus) } /* extern "C" */ #endif /* defined(__cplusplus) */ -- 2.7.4 ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] Re: [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event Ilya Markov @ 2018-07-31 11:40 ` Konstantin Belyavskiy 0 siblings, 0 replies; 7+ messages in thread From: Konstantin Belyavskiy @ 2018-07-31 11:40 UTC (permalink / raw) To: georgy, Илья Марков Cc: tarantool-patches [-- Attachment #1: Type: text/plain, Size: 14645 bytes --] Hi, overall patch looks good with minor fixes (short summary, see explanation below): - fix commit message - change function name - remove unused header >Четверг, 14 июня 2018, 18:04 +03:00 от Ilya Markov <imarkov@tarantool.org>: > >Add required for trigger on_ctl_event >structures and lua bindings. > >Prerequisite #3259 #3159 > >--- > src/box/CMakeLists.txt | 1 + > src/box/box.cc | 9 ++++++ > src/box/box.h | 1 + > src/box/ctl.c | 63 +++++++++++++++++++++++++++++++++++++ > src/box/ctl.h | 81 ++++++++++++++++++++++++++++++++++++++++++++++++ > src/box/lua/cfg.cc | 12 +++++++ > src/box/lua/ctl.c | 51 ++++++++++++++++++++++++++++++ > src/box/lua/ctl.h | 2 ++ > src/box/lua/load_cfg.lua | 10 +++++- > src/cfg.c | 37 ++++++++++++++++++++++ > src/cfg.h | 4 +++ > 11 files changed, 270 insertions(+), 1 deletion(-) > create mode 100644 src/box/ctl.c > create mode 100644 src/box/ctl.h > >diff --git a/src/box/CMakeLists.txt b/src/box/CMakeLists.txt >index 6b1ae3e..74f6b54 100644 >--- a/src/box/CMakeLists.txt >+++ b/src/box/CMakeLists.txt >@@ -112,6 +112,7 @@ add_library(box STATIC > journal.c > wal.c > call.c >+ ctl.c > ${lua_sources} > lua/init.c > lua/call.c >diff --git a/src/box/box.cc b/src/box/box.cc >index 61bfa11..26277e7 100644 >--- a/src/box/box.cc >+++ b/src/box/box.cc >@@ -72,6 +72,7 @@ > #include "call.h" > #include "func.h" > #include "sequence.h" >+#include "ctl.h" > > static char status[64] = "unknown"; > >@@ -823,6 +824,13 @@ box_set_net_msg_max(void) > IPROTO_FIBER_POOL_SIZE_FACTOR); > } > >+void >+box_set_on_ctl_event(void) >+{ >+ if (cfg_reset_on_ctl_event() < 0) >+ diag_raise(); >+} Please add _xc suffix, since function raise exception. > >+ > /* }}} configuration bindings */ > > /** >@@ -1808,6 +1816,7 @@ box_cfg_xc(void) > box_set_replication_connect_timeout(); > box_set_replication_connect_quorum(); > box_set_replication_skip_conflict(); >+ box_set_on_ctl_event(); > replication_sync_lag = box_check_replication_sync_lag(); > xstream_create(&join_stream, apply_initial_join_row); > xstream_create(&subscribe_stream, apply_row); >diff --git a/src/box/box.h b/src/box/box.h >index d396789..0325527 100644 >--- a/src/box/box.h >+++ b/src/box/box.h >@@ -191,6 +191,7 @@ void box_set_replication_connect_timeout(void); > void box_set_replication_connect_quorum(void); > void box_set_replication_skip_conflict(void); > void box_set_net_msg_max(void); >+void box_set_on_ctl_event(void); > > extern "C" { > #endif /* defined(__cplusplus) */ >diff --git a/src/box/ctl.c b/src/box/ctl.c >new file mode 100644 >index 0000000..fc3ae37 >--- /dev/null >+++ b/src/box/ctl.c >@@ -0,0 +1,63 @@ >+/* >+ * Copyright 2010-2018, Tarantool AUTHORS, please see AUTHORS file. >+ * >+ * Redistribution and use in source and binary forms, with or >+ * without modification, are permitted provided that the following >+ * conditions are met: >+ * >+ * 1. Redistributions of source code must retain the above >+ * copyright notice, this list of conditions and the >+ * following disclaimer. >+ * >+ * 2. Redistributions in binary form must reproduce the above >+ * copyright notice, this list of conditions and the following >+ * disclaimer in the documentation and/or other materials >+ * provided with the distribution. >+ * >+ * THIS SOFTWARE IS PROVIDED BY <COPYRIGHT HOLDER> ``AS IS'' AND >+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED >+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR >+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL >+ * <COPYRIGHT HOLDER> OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, >+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL >+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF >+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR >+ * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF >+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT >+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF >+ * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF >+ * SUCH DAMAGE. >+ */ >+#include <lib/small/small/rlist.h> >+#include <trigger.h> >+#include <box/ctl.h> >+#include "errcode.h" >+#include "error.h" >+#include <exception.h> >+ >+RLIST_HEAD(on_ctl_event); >+ >+int >+run_on_ctl_event_triggers(const struct on_ctl_event_ctx *result) { >+ return trigger_run(&on_ctl_event, (void *) result); >+} >+ >+int >+run_on_ctl_event_trigger_type(enum ctl_event_type type) >+{ >+ struct on_ctl_event_ctx ctx = {}; >+ ctx.type = type; >+ return run_on_ctl_event_triggers(&ctx); >+} >+ >+int >+cfg_reset_on_ctl_event() >+{ >+ if (cfg_reset_trigger("on_ctl_event", &on_ctl_event, >+ lbox_push_on_ctl_event, NULL) < 0) { >+ diag_set(ClientError, ER_CFG, "on_ctl_event", >+ "expected function or table"); >+ return -1; >+ } >+ return 0; >+} >\ No newline at end of file >diff --git a/src/box/ctl.h b/src/box/ctl.h >new file mode 100644 >index 0000000..1dbb6be >--- /dev/null >+++ b/src/box/ctl.h >@@ -0,0 +1,81 @@ >+#ifndef INCLUDES_TARANTOOL_CTL_H >+#define INCLUDES_TARANTOOL_CTL_H >+ >+/* >+ * Copyright 2010-2018, Tarantool AUTHORS, please see AUTHORS file. >+ * >+ * Redistribution and use in source and binary forms, with or >+ * without modification, are permitted provided that the following >+ * conditions are met: >+ * >+ * 1. Redistributions of source code must retain the above >+ * copyright notice, this list of conditions and the >+ * following disclaimer. >+ * >+ * 2. Redistributions in binary form must reproduce the above >+ * copyright notice, this list of conditions and the following >+ * disclaimer in the documentation and/or other materials >+ * provided with the distribution. >+ * >+ * THIS SOFTWARE IS PROVIDED BY <COPYRIGHT HOLDER> ``AS IS'' AND >+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED >+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR >+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL >+ * <COPYRIGHT HOLDER> OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, >+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL >+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF >+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR >+ * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF >+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT >+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF >+ * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF >+ * SUCH DAMAGE. >+ */ >+ >+#include <cfg.h> >+#include <box/lua/ctl.h> > >+#include "errcode.h" >+#include "error.h" >+#include <exception.h> I think last three headers are useless here. > >+ >+/** Global on-ctl_event triggers. */ >+extern struct rlist on_ctl_event; >+ >+enum ctl_event_type { >+ CTL_EVENT_SYSTEM_SPACE_RECOVERY, >+ CTL_EVENT_LOCAL_RECOVERY, >+ CTL_EVENT_READ_ONLY, >+ CTL_EVENT_READ_WRITE, >+ CTL_EVENT_SHUTDOWN, >+ CTL_EVENT_REPLICASET_ADD, >+ CTL_EVENT_REPLICASET_REMOVE, >+}; >+ >+struct on_ctl_event_ctx { >+ enum ctl_event_type type; >+ uint32_t replica_id; >+}; >+ >+#if defined(__cplusplus) >+extern "C" { >+#endif /* defined(__cplusplus) */ >+ >+/** >+ * Runs on_ctl_event triggers with specified context. >+ */ >+int >+run_on_ctl_event_triggers(const struct on_ctl_event_ctx *result); >+ >+/** >+ * Runs on_ctl_event triggers with specified type. >+ */ >+int >+run_on_ctl_event_trigger_type(enum ctl_event_type type); >+ >+int >+cfg_reset_on_ctl_event(); >+#if defined(__cplusplus) >+} /* extern "C" */ >+#endif /* defined(__cplusplus) */ >+ >+#endif /* INCLUDES_TARANTOOL_LUA_CTL_H */ >diff --git a/src/box/lua/cfg.cc b/src/box/lua/cfg.cc >index 5afebc9..c92478f 100644 >--- a/src/box/lua/cfg.cc >+++ b/src/box/lua/cfg.cc >@@ -254,6 +254,17 @@ lbox_cfg_set_net_msg_max(struct lua_State *L) > } > > static int >+lbox_cfg_set_on_ctl_event(struct lua_State *L) >+{ >+ try { >+ box_set_on_ctl_event(); >+ } catch (Exception *) { >+ luaT_error(L); >+ } >+ return 0; >+} >+ >+static int > lbox_cfg_set_worker_pool_threads(struct lua_State *L) > { > (void) L; >@@ -331,6 +342,7 @@ box_lua_cfg_init(struct lua_State *L) > {"cfg_set_replication_skip_conflict", lbox_cfg_set_replication_skip_conflict}, > {"cfg_set_replication_connect_timeout", lbox_cfg_set_replication_connect_timeout}, > {"cfg_set_net_msg_max", lbox_cfg_set_net_msg_max}, >+ {"cfg_set_on_ctl_event", lbox_cfg_set_on_ctl_event}, > {NULL, NULL} > }; > >diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c >index 9a105ed..52f320a 100644 >--- a/src/box/lua/ctl.c >+++ b/src/box/lua/ctl.c >@@ -35,6 +35,8 @@ > #include <lua.h> > #include <lauxlib.h> > #include <lualib.h> >+#include <lua/trigger.h> >+#include <box/ctl.h> > > #include "lua/utils.h" > >@@ -64,9 +66,37 @@ lbox_ctl_wait_rw(struct lua_State *L) > return 0; > } > >+ >+int >+lbox_push_on_ctl_event(struct lua_State *L, void *event) >+{ >+ struct on_ctl_event_ctx *ctx = (struct on_ctl_event_ctx *) event; >+ lua_newtable(L); >+ lua_pushstring(L, "type"); >+ lua_pushinteger(L, ctx->type); >+ lua_settable(L, -3); >+ >+ if (ctx->type == CTL_EVENT_REPLICASET_ADD || >+ ctx->type == CTL_EVENT_REPLICASET_REMOVE) { >+ lua_pushstring(L, "replica_id"); >+ luaL_pushuint64(L, ctx->replica_id); >+ lua_settable(L, -3); >+ } >+ return 1; >+} >+ >+static int >+lbox_on_ctl_event(struct lua_State *L) >+{ >+ return lbox_trigger_reset(L, 2, &on_ctl_event, >+ lbox_push_on_ctl_event, NULL); >+} >+ >+ > static const struct luaL_Reg lbox_ctl_lib[] = { > {"wait_ro", lbox_ctl_wait_ro}, > {"wait_rw", lbox_ctl_wait_rw}, >+ {"on_ctl_event", lbox_on_ctl_event}, > {NULL, NULL} > }; > >@@ -75,4 +105,25 @@ box_lua_ctl_init(struct lua_State *L) > { > luaL_register_module(L, "box.ctl", lbox_ctl_lib); > lua_pop(L, 1); >+ >+ luaL_findtable(L, LUA_GLOBALSINDEX, "box.ctl", 1); >+ lua_newtable(L); >+ lua_setfield(L, -2, "event"); >+ lua_getfield(L, -1, "event"); >+ >+ lua_pushnumber(L, CTL_EVENT_SYSTEM_SPACE_RECOVERY); >+ lua_setfield(L, -2, "SYSTEM_SPACE_RECOVERY"); >+ lua_pushnumber(L, CTL_EVENT_LOCAL_RECOVERY); >+ lua_setfield(L, -2, "LOCAL_RECOVERY"); >+ lua_pushnumber(L, CTL_EVENT_READ_ONLY); >+ lua_setfield(L, -2, "READ_ONLY"); >+ lua_pushnumber(L, CTL_EVENT_READ_WRITE); >+ lua_setfield(L, -2, "READ_WRITE"); >+ lua_pushnumber(L, CTL_EVENT_SHUTDOWN); >+ lua_setfield(L, -2, "SHUTDOWN"); >+ lua_pushnumber(L, CTL_EVENT_REPLICASET_ADD); >+ lua_setfield(L, -2, "CTL_EVENT_REPLICASET_ADD"); >+ lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); >+ lua_setfield(L, -2, "CTL_EVENT_REPLICASET_REMOVE"); >+ lua_pop(L, 2); /* box, ctl */ > } >diff --git a/src/box/lua/ctl.h b/src/box/lua/ctl.h >index e7c2edd..ab63232 100644 >--- a/src/box/lua/ctl.h >+++ b/src/box/lua/ctl.h >@@ -41,6 +41,8 @@ struct lua_State; > void > box_lua_ctl_init(struct lua_State *L); > >+int >+lbox_push_on_ctl_event(struct lua_State *L, void *event); > #if defined(__cplusplus) > } /* extern "C" */ > #endif /* defined(__cplusplus) */ >diff --git a/src/box/lua/load_cfg.lua b/src/box/lua/load_cfg.lua >index 0b668cd..c4d1347 100644 >--- a/src/box/lua/load_cfg.lua >+++ b/src/box/lua/load_cfg.lua >@@ -1,7 +1,11 @@ > -- load_cfg.lua - internal file > > local log = require('log') >-local json = require('json') >+local json = require("json").new() >+json.cfg{ >+ encode_use_tostring = true, >+} >+ > local private = require('box.internal') > local urilib = require('uri') > local math = require('math') >@@ -64,6 +68,7 @@ local default_cfg = { > feedback_host = " https://feedback.tarantool.io ", > feedback_interval = 3600, > net_msg_max = 768, >+ on_ctl_event = nil, > } > > -- types of available options >@@ -125,6 +130,7 @@ local template_cfg = { > feedback_host = 'string', > feedback_interval = 'number', > net_msg_max = 'number', >+ on_ctl_event = 'function, table', > } > > local function normalize_uri(port) >@@ -216,6 +222,7 @@ local dynamic_cfg = { > replicaset_uuid = check_replicaset_uuid, > replication_skip_conflict = private.cfg_set_replication_skip_conflict, > net_msg_max = private.cfg_set_net_msg_max, >+ on_ctl_event = private.cfg_set_on_ctl_event, > } > > local dynamic_cfg_skip_at_load = { >@@ -232,6 +239,7 @@ local dynamic_cfg_skip_at_load = { > force_recovery = true, > instance_uuid = true, > replicaset_uuid = true, >+ on_ctl_event = true, > } > > local function convert_gb(size) >diff --git a/src/cfg.c b/src/cfg.c >index 7c7d6e7..b07c1f3 100644 >--- a/src/cfg.c >+++ b/src/cfg.c >@@ -153,3 +153,40 @@ cfg_getarr_elem(const char *name, int i) > lua_pop(tarantool_L, 2); > return val; > } >+ >+int >+cfg_reset_trigger(const char *name, struct rlist *list, >+ lbox_push_event_f push_event, lbox_pop_event_f pop_event) >+{ >+ cfg_get(name); >+ struct lua_State *L = tarantool_L; >+ if (lua_isnil(L, -1)) >+ return 0; >+ if (!lua_isfunction(L, -1) && !lua_istable(L, -1)) { >+ return -1; >+ } >+ if (lua_istable(L, -1)) { >+ lua_pushinteger(L, 1); >+ lua_gettable(L, -2); >+ if (!luaL_isnull(L, lua_gettop(L)) && !lua_isfunction(L, -1)) >+ return -1; >+ bool is_nil = luaL_isnull(L, lua_gettop(L)); >+ if (is_nil) { >+ lua_pop(L, 1); >+ lua_pushnil(L); >+ } >+ lua_pushinteger(L, 2); >+ lua_gettable(L, -3); >+ if (!lua_isfunction(L, -1) && !lua_isnil(L, -1)) >+ return -1; >+ if (is_nil && lua_isnil(L, -1)) { >+ return 0; >+ } >+ } else { >+ lua_pushnil(L); >+ } >+ int rc = lbox_trigger_reset(L, lua_gettop(L), list, >+ push_event, pop_event); >+ lua_pop(L, 1); >+ return rc; >+} >\ No newline at end of file >diff --git a/src/cfg.h b/src/cfg.h >index 8499388 ..d36465c 100644 >--- a/src/cfg.h >+++ b/src/cfg.h >@@ -32,6 +32,7 @@ > */ > > #include <stdint.h> >+#include <lua/trigger.h> > > #if defined(__cplusplus) > extern "C" { >@@ -61,6 +62,9 @@ cfg_getarr_size(const char *name); > const char * > cfg_getarr_elem(const char *name, int i); > >+int >+cfg_reset_trigger(const char *name, struct rlist *list, >+ lbox_push_event_f push_event, lbox_pop_event_f pop_event); > #if defined(__cplusplus) > } /* extern "C" */ > #endif /* defined(__cplusplus) */ >-- >2.7.4 > > Best regards, Konstantin Belyavskiy k.belyavskiy@tarantool.org [-- Attachment #2: Type: text/html, Size: 18206 bytes --] ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls 2018-06-14 15:04 [tarantool-patches] [box.ctl 0/3] Introduce box.ctl.on_ctl_event trigger Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event Ilya Markov @ 2018-06-14 15:04 ` Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event Ilya Markov 2 siblings, 1 reply; 7+ messages in thread From: Ilya Markov @ 2018-06-14 15:04 UTC (permalink / raw) To: georgy; +Cc: tarantool-patches Add following cases of triggers: * System space recovery. Called on finish of bootstrap or finish of join or snapshot recovery. * Local recovery. Called on finish of bootstrap or finish of recovery. * Read_only/read_write. Called on changes of read_only state of instance. * Shutdown. Called on controlled shutdown. * Replicaset_add/replicaset_remove. Called on changes in space _cluster. Errors inside triggers are logged and don't influence on instance behaviour. Continue #3159 --- src/box/alter.cc | 1 + src/box/box.cc | 44 ++++++- src/box/engine.c | 14 +++ src/box/lua/ctl.c | 4 +- src/box/memtx_engine.c | 2 +- src/box/replication.cc | 14 +++ test/replication/master_onctl.lua | 34 +++++ test/replication/onctl.result | 250 +++++++++++++++++++++++++++++++++++++ test/replication/onctl.test.lua | 105 ++++++++++++++++ test/replication/replica_onctl.lua | 34 +++++ test/replication/suite.cfg | 1 + 11 files changed, 498 insertions(+), 5 deletions(-) create mode 100644 test/replication/master_onctl.lua create mode 100644 test/replication/onctl.result create mode 100644 test/replication/onctl.test.lua create mode 100644 test/replication/replica_onctl.lua diff --git a/src/box/alter.cc b/src/box/alter.cc index 6f6fcb0..7ec548b 100644 --- a/src/box/alter.cc +++ b/src/box/alter.cc @@ -52,6 +52,7 @@ #include "identifier.h" #include "version.h" #include "sequence.h" +#include "ctl.h" /** * chap-sha1 of empty string, i.e. diff --git a/src/box/box.cc b/src/box/box.cc index 26277e7..1de37d2 100644 --- a/src/box/box.cc +++ b/src/box/box.cc @@ -113,6 +113,11 @@ static fiber_cond ro_cond; */ static bool is_orphan = true; +/** + * Fiber used for on_ctl_event trigger. + */ +static fiber *ro_checker; + /* Use the shared instance of xstream for all appliers */ static struct xstream join_stream; static struct xstream subscribe_stream; @@ -1573,6 +1578,9 @@ box_set_replicaset_uuid(const struct tt_uuid *replicaset_uuid) void box_free(void) { + if (run_on_ctl_event_trigger_type(CTL_EVENT_SHUTDOWN) < 0) + say_error("ctl_trigger error in shutdown: %s", + diag_last_error(diag_get())->errmsg); /* * See gh-584 "box_free() is called even if box is not * initialized @@ -1592,7 +1600,8 @@ box_free(void) engine_shutdown(); wal_thread_stop(); } - + if (!fiber_is_dead(ro_checker)) + fiber_cancel(ro_checker); fiber_cond_destroy(&ro_cond); } @@ -1693,6 +1702,10 @@ bootstrap_from_master(struct replica *master) engine_begin_initial_recovery_xc(NULL); applier_resume_to_state(applier, APPLIER_FINAL_JOIN, TIMEOUT_INFINITY); + if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) + say_error("ctl_trigger error in system space recovery: %s", + diag_last_error(diag_get())->errmsg); + /* * Process final data (WALs). */ @@ -1755,11 +1768,35 @@ tx_prio_cb(struct ev_loop *loop, ev_watcher *watcher, int events) cbus_process(endpoint); } +static int +check_ro_f(MAYBE_UNUSED va_list ap) +{ + double timeout = TIMEOUT_INFINITY; + struct on_ctl_event_ctx ctx; + memset(&ctx, 0, sizeof(ctx)); + while (true) { + if (box_wait_ro(!box_is_ro(), timeout) != 0) { + if (fiber_is_cancelled()) + break; + else + return -1; + } + if (run_on_ctl_event_trigger_type( + box_is_ro() ? CTL_EVENT_READ_ONLY: + CTL_EVENT_READ_WRITE) < 0) + say_error("ctl_trigger error in %s: %s", + box_is_ro() ? "read_only" :"read_write", + diag_last_error(diag_get())->errmsg); + } + return 0; +} + void box_init(void) { fiber_cond_create(&ro_cond); - + ro_checker = fiber_new_xc("check_ro", check_ro_f); + fiber_start(ro_checker, NULL); user_cache_init(); /* * The order is important: to initialize sessions, @@ -1885,6 +1922,9 @@ box_cfg_xc(void) */ memtx_engine_recover_snapshot_xc(memtx, &last_checkpoint_vclock); + if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) + say_error("ctl_trigger error in system space recovery: %s", + diag_last_error(diag_get())->errmsg); engine_begin_final_recovery_xc(); recovery_follow_local(recovery, &wal_stream.base, "hot_standby", diff --git a/src/box/engine.c b/src/box/engine.c index 82293fd..fa78753 100644 --- a/src/box/engine.c +++ b/src/box/engine.c @@ -29,10 +29,12 @@ * SUCH DAMAGE. */ #include "engine.h" +#include "ctl.h" #include <stdint.h> #include <string.h> #include <small/rlist.h> +#include <fiber.h> RLIST_HEAD(engines); @@ -73,6 +75,14 @@ engine_bootstrap(void) if (engine->vtab->bootstrap(engine) != 0) return -1; } + if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) + say_error("ctl_trigger error in system space recovery: %s", + diag_last_error(diag_get())->errmsg); + + if (run_on_ctl_event_trigger_type(CTL_EVENT_LOCAL_RECOVERY) < 0) + say_error("ctl_trigger error in local recovery: %s", + diag_last_error(diag_get())->errmsg); + return 0; } @@ -111,6 +121,10 @@ engine_end_recovery(void) if (engine->vtab->end_recovery(engine) != 0) return -1; } + if (run_on_ctl_event_trigger_type(CTL_EVENT_LOCAL_RECOVERY) < 0) + say_error("ctl_trigger error in local recovery: %s", + diag_last_error(diag_get())->errmsg); + return 0; } diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c index 52f320a..5bd9be3 100644 --- a/src/box/lua/ctl.c +++ b/src/box/lua/ctl.c @@ -122,8 +122,8 @@ box_lua_ctl_init(struct lua_State *L) lua_pushnumber(L, CTL_EVENT_SHUTDOWN); lua_setfield(L, -2, "SHUTDOWN"); lua_pushnumber(L, CTL_EVENT_REPLICASET_ADD); - lua_setfield(L, -2, "CTL_EVENT_REPLICASET_ADD"); + lua_setfield(L, -2, "REPLICASET_ADD"); lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); - lua_setfield(L, -2, "CTL_EVENT_REPLICASET_REMOVE"); + lua_setfield(L, -2, "REPLICASET_REMOVE"); lua_pop(L, 2); /* box, ctl */ } diff --git a/src/box/memtx_engine.c b/src/box/memtx_engine.c index fac84ce..e737ea3 100644 --- a/src/box/memtx_engine.c +++ b/src/box/memtx_engine.c @@ -48,6 +48,7 @@ #include "replication.h" #include "schema.h" #include "gc.h" +#include "ctl.h" static void txn_on_yield_or_stop(struct trigger *trigger, void *event) @@ -197,7 +198,6 @@ memtx_engine_recover_snapshot(struct memtx_engine *memtx, */ if (!xlog_cursor_is_eof(&cursor)) panic("snapshot `%s' has no EOF marker", filename); - return 0; } diff --git a/src/box/replication.cc b/src/box/replication.cc index c1e1769..75aecd0 100644 --- a/src/box/replication.cc +++ b/src/box/replication.cc @@ -41,6 +41,7 @@ #include "error.h" #include "relay.h" #include "vclock.h" /* VCLOCK_MAX */ +#include "ctl.h" uint32_t instance_id = REPLICA_ID_NIL; struct tt_uuid INSTANCE_UUID; @@ -172,6 +173,12 @@ replicaset_add(uint32_t replica_id, const struct tt_uuid *replica_uuid) replica->uuid = *replica_uuid; replica_hash_insert(&replicaset.hash, replica); replica_set_id(replica, replica_id); + struct on_ctl_event_ctx on_ctl_ctx; + on_ctl_ctx.type = CTL_EVENT_REPLICASET_ADD; + on_ctl_ctx.replica_id = replica_id; + if (run_on_ctl_event_triggers(&on_ctl_ctx) < 0) + say_error("ctl_trigger error in replica add: %s", + diag_last_error(diag_get())->errmsg); return replica; } @@ -203,12 +210,19 @@ replica_clear_id(struct replica *replica) * Some records may arrive later on due to asynchronous nature of * replication. */ + struct on_ctl_event_ctx on_ctl_ctx; + on_ctl_ctx.type = CTL_EVENT_REPLICASET_REMOVE; + on_ctl_ctx.replica_id = replica->id; + replicaset.replica_by_id[replica->id] = NULL; replica->id = REPLICA_ID_NIL; if (replica_is_orphan(replica)) { replica_hash_remove(&replicaset.hash, replica); replica_delete(replica); } + if (run_on_ctl_event_triggers(&on_ctl_ctx) < 0) + say_error("ctl_trigger error in replica remove: %s", + diag_last_error(diag_get())->errmsg); } static void diff --git a/test/replication/master_onctl.lua b/test/replication/master_onctl.lua new file mode 100644 index 0000000..e0eb39a --- /dev/null +++ b/test/replication/master_onctl.lua @@ -0,0 +1,34 @@ +#!/usr/bin/env tarantool +os = require('os') + +SYSTEM_SPACE_RECOVERY = 0 +LOCAL_RECOVERY = 0 +READ_ONLY = 0 +READ_WRITE = 0 +REPLICASET_ADD = {} +REPLICASET_REMOVE = {} + +local function onctl(ctx) + if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then + SYSTEM_SPACE_RECOVERY = SYSTEM_SPACE_RECOVERY + 1 + elseif ctx.type == box.ctl.event.LOCAL_RECOVERY then + LOCAL_RECOVERY = LOCAL_RECOVERY + 1 + elseif ctx.type == box.ctl.event.READ_ONLY then + READ_ONLY = READ_ONLY + 1 + elseif ctx.type == box.ctl.event.READ_WRITE then + READ_WRITE = READ_WRITE + 1 + elseif ctx.type == box.ctl.event.REPLICASET_ADD then + table.insert(REPLICASET_ADD, ctx.replica_id) + elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then + table.insert(REPLICASET_REMOVE, ctx.replica_id) + end +end + +box.cfg({ + listen = os.getenv("LISTEN"), + memtx_memory = 107374182, + replication_connect_timeout = 0.5, + on_ctl_event = onctl, +}) + +require('console').listen(os.getenv('ADMIN')) diff --git a/test/replication/onctl.result b/test/replication/onctl.result new file mode 100644 index 0000000..19b3e67 --- /dev/null +++ b/test/replication/onctl.result @@ -0,0 +1,250 @@ +env = require('test_run') +--- +... +test_run = env.new() +--- +... +test_run:cmd("create server master with script='replication/master_onctl.lua'") +--- +- true +... +test_run:cmd("create server replica with rpl_master=master, script='replication/replica_onctl.lua'") +--- +- true +... +test_run:cmd("start server master") +--- +- true +... +test_run:cmd("switch master") +--- +- true +... +box.schema.user.grant('guest', 'replication') +--- +... +SYSTEM_SPACE_RECOVERY +--- +- 1 +... +LOCAL_RECOVERY +--- +- 1 +... +READ_ONLY +--- +- 0 +... +READ_WRITE +--- +- 1 +... +-- must be two entries. First from bootstrap.snap, second for current instance. +REPLICASET_ADD +--- +- - 1 + - 1 +... +-- must be one entry. Deletion of initial tuple in _cluster space. +REPLICASET_REMOVE +--- +- - 1 +... +REPLICASET_ADD = {} +--- +... +REPLICASET_REMOVE = {} +--- +... +new_replica_id = 0 +--- +... +deleted_replica_id = 0 +--- +... +test_run:cmd("setopt delimiter ';'") +--- +- true +... +function on_ctl_new(ctx) + if ctx.type == box.ctl.event.REPLICASET_ADD then + new_replica_id = ctx.replica_id + elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then + deleted_replica_id = ctx.replica_id + end +end; +--- +... +test_run:cmd("setopt delimiter ''"); +--- +- true +... +_ = box.ctl.on_ctl_event(on_ctl_new) +--- +... +test_run:cmd("start server replica") +--- +- true +... +REPLICASET_ADD +--- +- - 2 +... +REPLICASET_REMOVE +--- +- [] +... +new_replica_id +--- +- 2 +... +deleted_replica_id +--- +- 0 +... +test_run:cmd("switch replica") +--- +- true +... +test_run:cmd("setopt delimiter ';'") +--- +- true +... +function on_ctl_shutdown(ctx) + if ctx.type == box.ctl.event.SHUTDOWN then + require("log").info("test replica shutdown") + end +end; +--- +... +function on_ctl_error(ctx) + error("trigger error") +end; +--- +... +test_run:cmd("setopt delimiter ''"); +--- +- true +... +SYSTEM_SPACE_RECOVERY +--- +- 1 +... +LOCAL_RECOVERY +--- +- 1 +... +READ_ONLY +--- +- 0 +... +READ_WRITE +--- +- 1 +... +REPLICASET_ADD +--- +- - 2 +... +REPLICASET_REMOVE +--- +- [] +... +box.cfg{read_only = true} +--- +... +fiber = require("fiber") +--- +... +while READ_ONLY == 0 do fiber.sleep(0.001) end +--- +... +READ_ONLY +--- +- 1 +... +box.cfg{on_ctl_event = on_ctl_error} +--- +... +box.cfg{read_only = false} +--- +... +test_run:grep_log('replica', 'ctl_trigger error') +--- +- ctl_trigger error +... +box.cfg{on_ctl_event = {box.NULL, on_ctl_error}} +--- +... +box.cfg{on_ctl_event = on_ctl_shutdown} +--- +... +test_run:cmd("restart server replica") +-- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. +--test_run:grep_log('replica', 'test replica shutdown') +test_run:cmd("switch master") +--- +- true +... +box.schema.user.revoke('guest', 'replication') +--- +... +_ = box.space._cluster:delete{2} +--- +... +SYSTEM_SPACE_RECOVERY +--- +- 1 +... +LOCAL_RECOVERY +--- +- 1 +... +READ_ONLY +--- +- 0 +... +READ_WRITE +--- +- 1 +... +REPLICASET_ADD +--- +- - 2 +... +REPLICASET_REMOVE +--- +- - 2 +... +new_replica_id +--- +- 2 +... +deleted_replica_id +--- +- 2 +... +box.ctl.on_ctl_event(nil, on_ctl_new) +--- +... +-- cleanup +test_run:cmd("switch default") +--- +- true +... +test_run:cmd("stop server master") +--- +- true +... +test_run:cmd("cleanup server master") +--- +- true +... +test_run:cmd("stop server replica") +--- +- true +... +test_run:cmd("cleanup server replica") +--- +- true +... diff --git a/test/replication/onctl.test.lua b/test/replication/onctl.test.lua new file mode 100644 index 0000000..ff6a898 --- /dev/null +++ b/test/replication/onctl.test.lua @@ -0,0 +1,105 @@ +env = require('test_run') +test_run = env.new() + +test_run:cmd("create server master with script='replication/master_onctl.lua'") +test_run:cmd("create server replica with rpl_master=master, script='replication/replica_onctl.lua'") + +test_run:cmd("start server master") +test_run:cmd("switch master") +box.schema.user.grant('guest', 'replication') + +SYSTEM_SPACE_RECOVERY +LOCAL_RECOVERY +READ_ONLY +READ_WRITE +-- must be two entries. First from bootstrap.snap, second for current instance. +REPLICASET_ADD +-- must be one entry. Deletion of initial tuple in _cluster space. +REPLICASET_REMOVE + +REPLICASET_ADD = {} +REPLICASET_REMOVE = {} + +new_replica_id = 0 +deleted_replica_id = 0 + +test_run:cmd("setopt delimiter ';'") +function on_ctl_new(ctx) + if ctx.type == box.ctl.event.REPLICASET_ADD then + new_replica_id = ctx.replica_id + elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then + deleted_replica_id = ctx.replica_id + end +end; +test_run:cmd("setopt delimiter ''"); + +_ = box.ctl.on_ctl_event(on_ctl_new) + +test_run:cmd("start server replica") + +REPLICASET_ADD +REPLICASET_REMOVE + +new_replica_id +deleted_replica_id + +test_run:cmd("switch replica") + +test_run:cmd("setopt delimiter ';'") +function on_ctl_shutdown(ctx) + if ctx.type == box.ctl.event.SHUTDOWN then + require("log").info("test replica shutdown") + end +end; + +function on_ctl_error(ctx) + error("trigger error") +end; + +test_run:cmd("setopt delimiter ''"); + +SYSTEM_SPACE_RECOVERY +LOCAL_RECOVERY +READ_ONLY +READ_WRITE +REPLICASET_ADD +REPLICASET_REMOVE + +box.cfg{read_only = true} +fiber = require("fiber") +while READ_ONLY == 0 do fiber.sleep(0.001) end +READ_ONLY + +box.cfg{on_ctl_event = on_ctl_error} +box.cfg{read_only = false} +test_run:grep_log('replica', 'ctl_trigger error') +box.cfg{on_ctl_event = {box.NULL, on_ctl_error}} +box.cfg{on_ctl_event = on_ctl_shutdown} + +test_run:cmd("restart server replica") +-- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. +--test_run:grep_log('replica', 'test replica shutdown') + + +test_run:cmd("switch master") +box.schema.user.revoke('guest', 'replication') +_ = box.space._cluster:delete{2} + +SYSTEM_SPACE_RECOVERY +LOCAL_RECOVERY +READ_ONLY +READ_WRITE +REPLICASET_ADD +REPLICASET_REMOVE + +new_replica_id +deleted_replica_id + +box.ctl.on_ctl_event(nil, on_ctl_new) + +-- cleanup +test_run:cmd("switch default") +test_run:cmd("stop server master") +test_run:cmd("cleanup server master") +test_run:cmd("stop server replica") +test_run:cmd("cleanup server replica") diff --git a/test/replication/replica_onctl.lua b/test/replication/replica_onctl.lua new file mode 100644 index 0000000..d6ce73c --- /dev/null +++ b/test/replication/replica_onctl.lua @@ -0,0 +1,34 @@ +#!/usr/bin/env tarantool + +SYSTEM_SPACE_RECOVERY = 0 +LOCAL_RECOVERY = 0 +READ_ONLY = 0 +READ_WRITE = 0 +REPLICASET_ADD = {} +REPLICASET_REMOVE = {} + +local function onctl(ctx) + if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then + SYSTEM_SPACE_RECOVERY = SYSTEM_SPACE_RECOVERY + 1 + elseif ctx.type == box.ctl.event.LOCAL_RECOVERY then + LOCAL_RECOVERY = LOCAL_RECOVERY + 1 + elseif ctx.type == box.ctl.event.READ_ONLY then + READ_ONLY = READ_ONLY + 1 + elseif ctx.type == box.ctl.event.READ_WRITE then + READ_WRITE = READ_WRITE + 1 + elseif ctx.type == box.ctl.event.REPLICASET_ADD then + table.insert(REPLICASET_ADD, ctx.replica_id) + elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then + table.insert(REPLICASET_REMOVE, ctx.replica_id) + end +end + +box.cfg({ + listen = os.getenv("LISTEN"), + replication = os.getenv("MASTER"), + memtx_memory = 107374182, + replication_connect_timeout = 0.5, + on_ctl_event = onctl, +}) + +require('console').listen(os.getenv('ADMIN')) diff --git a/test/replication/suite.cfg b/test/replication/suite.cfg index 95e94e5..365a825 100644 --- a/test/replication/suite.cfg +++ b/test/replication/suite.cfg @@ -6,6 +6,7 @@ "wal_off.test.lua": {}, "hot_standby.test.lua": {}, "rebootstrap.test.lua": {}, + "onctl.test.lua": {}, "*": { "memtx": {"engine": "memtx"}, "vinyl": {"engine": "vinyl"} -- 2.7.4 ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] Re: [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls Ilya Markov @ 2018-07-31 11:40 ` Konstantin Belyavskiy 0 siblings, 0 replies; 7+ messages in thread From: Konstantin Belyavskiy @ 2018-07-31 11:40 UTC (permalink / raw) To: georgy, Илья Марков Cc: tarantool-patches [-- Attachment #1: Type: text/plain, Size: 18761 bytes --] Hi, overall patch looks good with minor conplains (summary) - unused headers - is it worth it to create a separate fiber to check if read-only condition was changed? - test SHUTDOWN should be implemented >Четверг, 14 июня 2018, 18:04 +03:00 от Ilya Markov <imarkov@tarantool.org>: > >Add following cases of triggers: >* System space recovery. Called on finish of bootstrap or finish of join or >snapshot recovery. >* Local recovery. Called on finish of bootstrap or finish of recovery. >* Read_only/read_write. Called on changes of read_only state of >instance. >* Shutdown. Called on controlled shutdown. >* Replicaset_add/replicaset_remove. Called on changes in space _cluster. > >Errors inside triggers are logged and don't influence on instance >behaviour. > >Continue #3159 >--- > src/box/alter.cc | 1 + > src/box/box.cc | 44 ++++++- > src/box/engine.c | 14 +++ > src/box/lua/ctl.c | 4 +- > src/box/memtx_engine.c | 2 +- > src/box/replication.cc | 14 +++ > test/replication/master_onctl.lua | 34 +++++ > test/replication/onctl.result | 250 +++++++++++++++++++++++++++++++++++++ > test/replication/onctl.test.lua | 105 ++++++++++++++++ > test/replication/replica_onctl.lua | 34 +++++ > test/replication/suite.cfg | 1 + > 11 files changed, 498 insertions(+), 5 deletions(-) > create mode 100644 test/replication/master_onctl.lua > create mode 100644 test/replication/onctl.result > create mode 100644 test/replication/onctl.test.lua > create mode 100644 test/replication/replica_onctl.lua > >diff --git a/src/box/alter.cc b/src/box/alter.cc >index 6f6fcb0..7ec548b 100644 >--- a/src/box/alter.cc >+++ b/src/box/alter.cc >@@ -52,6 +52,7 @@ > #include "identifier.h" > #include "version.h" > #include "sequence.h" > >+#include "ctl.h" Not used. > > > /** > * chap-sha1 of empty string, i.e. >diff --git a/src/box/box.cc b/src/box/box.cc >index 26277e7..1de37d2 100644 >--- a/src/box/box.cc >+++ b/src/box/box.cc >@@ -113,6 +113,11 @@ static fiber_cond ro_cond; > */ > static bool is_orphan = true; > >+/** >+ * Fiber used for on_ctl_event trigger. >+ */ >+static fiber *ro_checker; >+ > /* Use the shared instance of xstream for all appliers */ > static struct xstream join_stream; > static struct xstream subscribe_stream; >@@ -1573,6 +1578,9 @@ box_set_replicaset_uuid(const struct tt_uuid *replicaset_uuid) > void > box_free(void) > { >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_SHUTDOWN) < 0) >+ say_error("ctl_trigger error in shutdown: %s", >+ diag_last_error(diag_get())->errmsg); > /* > * See gh-584 "box_free() is called even if box is not > * initialized >@@ -1592,7 +1600,8 @@ box_free(void) > engine_shutdown(); > wal_thread_stop(); > } >- >+ if (!fiber_is_dead(ro_checker)) >+ fiber_cancel(ro_checker); > fiber_cond_destroy(&ro_cond); > } > >@@ -1693,6 +1702,10 @@ bootstrap_from_master(struct replica *master) > engine_begin_initial_recovery_xc(NULL); > applier_resume_to_state(applier, APPLIER_FINAL_JOIN, TIMEOUT_INFINITY); > >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) >+ say_error("ctl_trigger error in system space recovery: %s", >+ diag_last_error(diag_get())->errmsg); >+ > /* > * Process final data (WALs). > */ >@@ -1755,11 +1768,35 @@ tx_prio_cb(struct ev_loop *loop, ev_watcher *watcher, int events) > cbus_process(endpoint); > } > >+static int >+check_ro_f(MAYBE_UNUSED va_list ap) >+{ >+ double timeout = TIMEOUT_INFINITY; >+ struct on_ctl_event_ctx ctx; >+ memset(&ctx, 0, sizeof(ctx)); >+ while (true) { >+ if (box_wait_ro(!box_is_ro(), timeout) != 0) { >+ if (fiber_is_cancelled()) >+ break; >+ else >+ return -1; >+ } >+ if (run_on_ctl_event_trigger_type( >+ box_is_ro() ? CTL_EVENT_READ_ONLY: >+ CTL_EVENT_READ_WRITE) < 0) >+ say_error("ctl_trigger error in %s: %s", >+ box_is_ro() ? "read_only" :"read_write", >+ diag_last_error(diag_get())->errmsg); >+ } >+ return 0; >+} >+ Is it worth it to create a separate fiber? May be check it near or inside fiber_cond_broadcast(&ro_cond)? > > void > box_init(void) > { > fiber_cond_create(&ro_cond); >- >+ ro_checker = fiber_new_xc("check_ro", check_ro_f); >+ fiber_start(ro_checker, NULL); > user_cache_init(); > /* > * The order is important: to initialize sessions, >@@ -1885,6 +1922,9 @@ box_cfg_xc(void) > */ > memtx_engine_recover_snapshot_xc(memtx, > &last_checkpoint_vclock); >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) >+ say_error("ctl_trigger error in system space recovery: %s", >+ diag_last_error(diag_get())->errmsg); > > engine_begin_final_recovery_xc(); > recovery_follow_local(recovery, &wal_stream.base, "hot_standby", >diff --git a/src/box/engine.c b/src/box/engine.c >index 82293fd..fa78753 100644 >--- a/src/box/engine.c >+++ b/src/box/engine.c >@@ -29,10 +29,12 @@ > * SUCH DAMAGE. > */ > #include "engine.h" >+#include "ctl.h" > > #include <stdint.h> > #include <string.h> > #include <small/rlist.h> > >+#include <fiber.h> Not used. > > RLIST_HEAD(engines); > >@@ -73,6 +75,14 @@ engine_bootstrap(void) > if (engine->vtab->bootstrap(engine) != 0) > return -1; > } >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_SYSTEM_SPACE_RECOVERY) < 0) >+ say_error("ctl_trigger error in system space recovery: %s", >+ diag_last_error(diag_get())->errmsg); >+ >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_LOCAL_RECOVERY) < 0) >+ say_error("ctl_trigger error in local recovery: %s", >+ diag_last_error(diag_get())->errmsg); >+ > return 0; > } > >@@ -111,6 +121,10 @@ engine_end_recovery(void) > if (engine->vtab->end_recovery(engine) != 0) > return -1; > } >+ if (run_on_ctl_event_trigger_type(CTL_EVENT_LOCAL_RECOVERY) < 0) >+ say_error("ctl_trigger error in local recovery: %s", >+ diag_last_error(diag_get())->errmsg); >+ > return 0; > } > >diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c >index 52f320a..5bd9be3 100644 >--- a/src/box/lua/ctl.c >+++ b/src/box/lua/ctl.c >@@ -122,8 +122,8 @@ box_lua_ctl_init(struct lua_State *L) > lua_pushnumber(L, CTL_EVENT_SHUTDOWN); > lua_setfield(L, -2, "SHUTDOWN"); > lua_pushnumber(L, CTL_EVENT_REPLICASET_ADD); >- lua_setfield(L, -2, "CTL_EVENT_REPLICASET_ADD"); >+ lua_setfield(L, -2, "REPLICASET_ADD"); > lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); >- lua_setfield(L, -2, "CTL_EVENT_REPLICASET_REMOVE"); >+ lua_setfield(L, -2, "REPLICASET_REMOVE"); > lua_pop(L, 2); /* box, ctl */ > } >diff --git a/src/box/memtx_engine.c b/src/box/memtx_engine.c >index fac84ce..e737ea3 100644 >--- a/src/box/memtx_engine.c >+++ b/src/box/memtx_engine.c >@@ -48,6 +48,7 @@ > #include "replication.h" > #include "schema.h" > #include "gc.h" > >+#include "ctl.h" Also not used. > > static void > txn_on_yield_or_stop(struct trigger *trigger, void *event) >@@ -197,7 +198,6 @@ memtx_engine_recover_snapshot(struct memtx_engine *memtx, > */ > if (!xlog_cursor_is_eof(&cursor)) > panic("snapshot `%s' has no EOF marker", filename); >- > return 0; > } > >diff --git a/src/box/replication.cc b/src/box/replication.cc >index c1e1769..75aecd0 100644 >--- a/src/box/replication.cc >+++ b/src/box/replication.cc >@@ -41,6 +41,7 @@ > #include "error.h" > #include "relay.h" > #include "vclock.h" /* VCLOCK_MAX */ >+#include "ctl.h" > > uint32_t instance_id = REPLICA_ID_NIL; > struct tt_uuid INSTANCE_UUID; >@@ -172,6 +173,12 @@ replicaset_add(uint32_t replica_id, const struct tt_uuid *replica_uuid) > replica->uuid = *replica_uuid; > replica_hash_insert(&replicaset.hash, replica); > replica_set_id(replica, replica_id); >+ struct on_ctl_event_ctx on_ctl_ctx; >+ on_ctl_ctx.type = CTL_EVENT_REPLICASET_ADD; >+ on_ctl_ctx.replica_id = replica_id; >+ if (run_on_ctl_event_triggers(&on_ctl_ctx) < 0) >+ say_error("ctl_trigger error in replica add: %s", >+ diag_last_error(diag_get())->errmsg); > return replica; > } > >@@ -203,12 +210,19 @@ replica_clear_id(struct replica *replica) > * Some records may arrive later on due to asynchronous nature of > * replication. > */ >+ struct on_ctl_event_ctx on_ctl_ctx; >+ on_ctl_ctx.type = CTL_EVENT_REPLICASET_REMOVE; >+ on_ctl_ctx.replica_id = replica->id; >+ > replicaset.replica_by_id[replica->id] = NULL; > replica->id = REPLICA_ID_NIL; > if (replica_is_orphan(replica)) { > replica_hash_remove(&replicaset.hash, replica); > replica_delete(replica); > } >+ if (run_on_ctl_event_triggers(&on_ctl_ctx) < 0) >+ say_error("ctl_trigger error in replica remove: %s", >+ diag_last_error(diag_get())->errmsg); > } > > static void >diff --git a/test/replication/master_onctl.lua b/test/replication/master_onctl.lua >new file mode 100644 >index 0000000..e0eb39a >--- /dev/null >+++ b/test/replication/master_onctl.lua >@@ -0,0 +1,34 @@ >+#!/usr/bin/env tarantool >+os = require('os') >+ >+SYSTEM_SPACE_RECOVERY = 0 >+LOCAL_RECOVERY = 0 >+READ_ONLY = 0 >+READ_WRITE = 0 >+REPLICASET_ADD = {} >+REPLICASET_REMOVE = {} >+ >+local function onctl(ctx) >+ if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then >+ SYSTEM_SPACE_RECOVERY = SYSTEM_SPACE_RECOVERY + 1 >+ elseif ctx.type == box.ctl.event.LOCAL_RECOVERY then >+ LOCAL_RECOVERY = LOCAL_RECOVERY + 1 >+ elseif ctx.type == box.ctl.event.READ_ONLY then >+ READ_ONLY = READ_ONLY + 1 >+ elseif ctx.type == box.ctl.event.READ_WRITE then >+ READ_WRITE = READ_WRITE + 1 >+ elseif ctx.type == box.ctl.event.REPLICASET_ADD then >+ table.insert(REPLICASET_ADD, ctx.replica_id) >+ elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then >+ table.insert(REPLICASET_REMOVE, ctx.replica_id) >+ end >+end >+ >+box.cfg({ >+ listen = os.getenv("LISTEN"), >+ memtx_memory = 107374182, >+ replication_connect_timeout = 0.5, >+ on_ctl_event = onctl, >+}) >+ >+require('console').listen(os.getenv('ADMIN')) >diff --git a/test/replication/onctl.result b/test/replication/onctl.result >new file mode 100644 >index 0000000..19b3e67 >--- /dev/null >+++ b/test/replication/onctl.result >@@ -0,0 +1,250 @@ >+env = require('test_run') >+--- >+... >+test_run = env.new() >+--- >+... >+test_run:cmd("create server master with script='replication/master_onctl.lua'") >+--- >+- true >+... >+test_run:cmd("create server replica with rpl_master=master, script='replication/replica_onctl.lua'") >+--- >+- true >+... >+test_run:cmd("start server master") >+--- >+- true >+... >+test_run:cmd("switch master") >+--- >+- true >+... >+box.schema.user.grant('guest', 'replication') >+--- >+... >+SYSTEM_SPACE_RECOVERY >+--- >+- 1 >+... >+LOCAL_RECOVERY >+--- >+- 1 >+... >+READ_ONLY >+--- >+- 0 >+... >+READ_WRITE >+--- >+- 1 >+... >+-- must be two entries. First from bootstrap.snap, second for current instance. >+REPLICASET_ADD >+--- >+- - 1 >+ - 1 >+... >+-- must be one entry. Deletion of initial tuple in _cluster space. >+REPLICASET_REMOVE >+--- >+- - 1 >+... >+REPLICASET_ADD = {} >+--- >+... >+REPLICASET_REMOVE = {} >+--- >+... >+new_replica_id = 0 >+--- >+... >+deleted_replica_id = 0 >+--- >+... >+test_run:cmd("setopt delimiter ';'") >+--- >+- true >+... >+function on_ctl_new(ctx) >+ if ctx.type == box.ctl.event.REPLICASET_ADD then >+ new_replica_id = ctx.replica_id >+ elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then >+ deleted_replica_id = ctx.replica_id >+ end >+end; >+--- >+... >+test_run:cmd("setopt delimiter ''"); >+--- >+- true >+... >+_ = box.ctl.on_ctl_event(on_ctl_new) >+--- >+... >+test_run:cmd("start server replica") >+--- >+- true >+... >+REPLICASET_ADD >+--- >+- - 2 >+... >+REPLICASET_REMOVE >+--- >+- [] >+... >+new_replica_id >+--- >+- 2 >+... >+deleted_replica_id >+--- >+- 0 >+... >+test_run:cmd("switch replica") >+--- >+- true >+... >+test_run:cmd("setopt delimiter ';'") >+--- >+- true >+... >+function on_ctl_shutdown(ctx) >+ if ctx.type == box.ctl.event.SHUTDOWN then >+ require("log").info("test replica shutdown") >+ end >+end; >+--- >+... >+function on_ctl_error(ctx) >+ error("trigger error") >+end; >+--- >+... >+test_run:cmd("setopt delimiter ''"); >+--- >+- true >+... >+SYSTEM_SPACE_RECOVERY >+--- >+- 1 >+... >+LOCAL_RECOVERY >+--- >+- 1 >+... >+READ_ONLY >+--- >+- 0 >+... >+READ_WRITE >+--- >+- 1 >+... >+REPLICASET_ADD >+--- >+- - 2 >+... >+REPLICASET_REMOVE >+--- >+- [] >+... >+box.cfg{read_only = true} >+--- >+... >+fiber = require("fiber") >+--- >+... >+while READ_ONLY == 0 do fiber.sleep(0.001) end >+--- >+... >+READ_ONLY >+--- >+- 1 >+... >+box.cfg{on_ctl_event = on_ctl_error} >+--- >+... >+box.cfg{read_only = false} >+--- >+... >+test_run:grep_log('replica', 'ctl_trigger error') >+--- >+- ctl_trigger error >+... >+box.cfg{on_ctl_event = {box.NULL, on_ctl_error}} >+--- >+... >+box.cfg{on_ctl_event = on_ctl_shutdown} >+--- >+... >+test_run:cmd("restart server replica") >+-- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. >+--test_run:grep_log('replica', 'test replica shutdown') >+test_run:cmd("switch master") >+--- >+- true >+... >+box.schema.user.revoke('guest', 'replication') >+--- >+... >+_ = box.space._cluster:delete{2} >+--- >+... >+SYSTEM_SPACE_RECOVERY >+--- >+- 1 >+... >+LOCAL_RECOVERY >+--- >+- 1 >+... >+READ_ONLY >+--- >+- 0 >+... >+READ_WRITE >+--- >+- 1 >+... >+REPLICASET_ADD >+--- >+- - 2 >+... >+REPLICASET_REMOVE >+--- >+- - 2 >+... >+new_replica_id >+--- >+- 2 >+... >+deleted_replica_id >+--- >+- 2 >+... >+box.ctl.on_ctl_event(nil, on_ctl_new) >+--- >+... >+-- cleanup >+test_run:cmd("switch default") >+--- >+- true >+... >+test_run:cmd("stop server master") >+--- >+- true >+... >+test_run:cmd("cleanup server master") >+--- >+- true >+... >+test_run:cmd("stop server replica") >+--- >+- true >+... >+test_run:cmd("cleanup server replica") >+--- >+- true >+... >diff --git a/test/replication/onctl.test.lua b/test/replication/onctl.test.lua >new file mode 100644 >index 0000000..ff6a898 >--- /dev/null >+++ b/test/replication/onctl.test.lua >@@ -0,0 +1,105 @@ >+env = require('test_run') >+test_run = env.new() >+ >+test_run:cmd("create server master with script='replication/master_onctl.lua'") >+test_run:cmd("create server replica with rpl_master=master, script='replication/replica_onctl.lua'") >+ >+test_run:cmd("start server master") >+test_run:cmd("switch master") >+box.schema.user.grant('guest', 'replication') >+ >+SYSTEM_SPACE_RECOVERY >+LOCAL_RECOVERY >+READ_ONLY >+READ_WRITE >+-- must be two entries. First from bootstrap.snap, second for current instance. >+REPLICASET_ADD >+-- must be one entry. Deletion of initial tuple in _cluster space. >+REPLICASET_REMOVE >+ >+REPLICASET_ADD = {} >+REPLICASET_REMOVE = {} >+ >+new_replica_id = 0 >+deleted_replica_id = 0 >+ >+test_run:cmd("setopt delimiter ';'") >+function on_ctl_new(ctx) >+ if ctx.type == box.ctl.event.REPLICASET_ADD then >+ new_replica_id = ctx.replica_id >+ elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then >+ deleted_replica_id = ctx.replica_id >+ end >+end; >+test_run:cmd("setopt delimiter ''"); >+ >+_ = box.ctl.on_ctl_event(on_ctl_new) >+ >+test_run:cmd("start server replica") >+ >+REPLICASET_ADD >+REPLICASET_REMOVE >+ >+new_replica_id >+deleted_replica_id >+ >+test_run:cmd("switch replica") >+ >+test_run:cmd("setopt delimiter ';'") >+function on_ctl_shutdown(ctx) >+ if ctx.type == box.ctl.event.SHUTDOWN then >+ require("log").info("test replica shutdown") >+ end >+end; >+ >+function on_ctl_error(ctx) >+ error("trigger error") >+end; >+ >+test_run:cmd("setopt delimiter ''"); >+ >+SYSTEM_SPACE_RECOVERY >+LOCAL_RECOVERY >+READ_ONLY >+READ_WRITE >+REPLICASET_ADD >+REPLICASET_REMOVE >+ >+box.cfg{read_only = true} >+fiber = require("fiber") >+while READ_ONLY == 0 do fiber.sleep(0.001) end >+READ_ONLY >+ >+box.cfg{on_ctl_event = on_ctl_error} >+box.cfg{read_only = false} >+test_run:grep_log('replica', 'ctl_trigger error') >+box.cfg{on_ctl_event = {box.NULL, on_ctl_error}} >+box.cfg{on_ctl_event = on_ctl_shutdown} >+ >+test_run:cmd("restart server replica") >+-- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. >+--test_run:grep_log('replica', 'test replica shutdown') It should be done > >+ >+ >+test_run:cmd("switch master") >+box.schema.user.revoke('guest', 'replication') >+_ = box.space._cluster:delete{2} >+ >+SYSTEM_SPACE_RECOVERY >+LOCAL_RECOVERY >+READ_ONLY >+READ_WRITE >+REPLICASET_ADD >+REPLICASET_REMOVE >+ >+new_replica_id >+deleted_replica_id >+ >+box.ctl.on_ctl_event(nil, on_ctl_new) >+ >+-- cleanup >+test_run:cmd("switch default") >+test_run:cmd("stop server master") >+test_run:cmd("cleanup server master") >+test_run:cmd("stop server replica") >+test_run:cmd("cleanup server replica") >diff --git a/test/replication/replica_onctl.lua b/test/replication/replica_onctl.lua >new file mode 100644 >index 0000000..d6ce73c >--- /dev/null >+++ b/test/replication/replica_onctl.lua >@@ -0,0 +1,34 @@ >+#!/usr/bin/env tarantool >+ >+SYSTEM_SPACE_RECOVERY = 0 >+LOCAL_RECOVERY = 0 >+READ_ONLY = 0 >+READ_WRITE = 0 >+REPLICASET_ADD = {} >+REPLICASET_REMOVE = {} >+ >+local function onctl(ctx) >+ if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then >+ SYSTEM_SPACE_RECOVERY = SYSTEM_SPACE_RECOVERY + 1 >+ elseif ctx.type == box.ctl.event.LOCAL_RECOVERY then >+ LOCAL_RECOVERY = LOCAL_RECOVERY + 1 >+ elseif ctx.type == box.ctl.event.READ_ONLY then >+ READ_ONLY = READ_ONLY + 1 >+ elseif ctx.type == box.ctl.event.READ_WRITE then >+ READ_WRITE = READ_WRITE + 1 >+ elseif ctx.type == box.ctl.event.REPLICASET_ADD then >+ table.insert(REPLICASET_ADD, ctx.replica_id) >+ elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then >+ table.insert(REPLICASET_REMOVE, ctx.replica_id) >+ end >+end >+ >+box.cfg({ >+ listen = os.getenv("LISTEN"), >+ replication = os.getenv("MASTER"), >+ memtx_memory = 107374182, >+ replication_connect_timeout = 0.5, >+ on_ctl_event = onctl, >+}) >+ >+require('console').listen(os.getenv('ADMIN')) >diff --git a/test/replication/suite.cfg b/test/replication/suite.cfg >index 95e94e5..365a825 100644 >--- a/test/replication/suite.cfg >+++ b/test/replication/suite.cfg >@@ -6,6 +6,7 @@ > "wal_off.test.lua": {}, > "hot_standby.test.lua": {}, > "rebootstrap.test.lua": {}, >+ "onctl.test.lua": {}, > "*": { > "memtx": {"engine": "memtx"}, > "vinyl": {"engine": "vinyl"} >-- >2.7.4 > > Best regards, Konstantin Belyavskiy k.belyavskiy@tarantool.org [-- Attachment #2: Type: text/html, Size: 23719 bytes --] ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event 2018-06-14 15:04 [tarantool-patches] [box.ctl 0/3] Introduce box.ctl.on_ctl_event trigger Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls Ilya Markov @ 2018-06-14 15:04 ` Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy 2 siblings, 1 reply; 7+ messages in thread From: Ilya Markov @ 2018-06-14 15:04 UTC (permalink / raw) To: georgy; +Cc: tarantool-patches Add event: replica fails with some error. In scope of #3159 --- src/box/ctl.h | 1 + src/box/lua/ctl.c | 6 +++++- src/box/relay.cc | 7 +++++++ test/replication/master_onctl.lua | 3 +++ test/replication/onctl.result | 12 ++++++++++++ test/replication/onctl.test.lua | 5 ++++- 6 files changed, 32 insertions(+), 2 deletions(-) diff --git a/src/box/ctl.h b/src/box/ctl.h index 1dbb6be..db6f08a 100644 --- a/src/box/ctl.h +++ b/src/box/ctl.h @@ -49,6 +49,7 @@ enum ctl_event_type { CTL_EVENT_SHUTDOWN, CTL_EVENT_REPLICASET_ADD, CTL_EVENT_REPLICASET_REMOVE, + CTL_EVENT_REPLICA_CONNECTION_ERROR, }; struct on_ctl_event_ctx { diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c index 5bd9be3..8a0dfc2 100644 --- a/src/box/lua/ctl.c +++ b/src/box/lua/ctl.c @@ -37,6 +37,7 @@ #include <lualib.h> #include <lua/trigger.h> #include <box/ctl.h> +#include <tt_uuid.h> #include "lua/utils.h" @@ -77,7 +78,8 @@ lbox_push_on_ctl_event(struct lua_State *L, void *event) lua_settable(L, -3); if (ctx->type == CTL_EVENT_REPLICASET_ADD || - ctx->type == CTL_EVENT_REPLICASET_REMOVE) { + ctx->type == CTL_EVENT_REPLICASET_REMOVE || + ctx->type == CTL_EVENT_REPLICA_CONNECTION_ERROR) { lua_pushstring(L, "replica_id"); luaL_pushuint64(L, ctx->replica_id); lua_settable(L, -3); @@ -125,5 +127,7 @@ box_lua_ctl_init(struct lua_State *L) lua_setfield(L, -2, "REPLICASET_ADD"); lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); lua_setfield(L, -2, "REPLICASET_REMOVE"); + lua_pushnumber(L, CTL_EVENT_REPLICA_CONNECTION_ERROR); + lua_setfield(L, -2, "REPLICA_CONNECTION_ERROR"); lua_pop(L, 2); /* box, ctl */ } diff --git a/src/box/relay.cc b/src/box/relay.cc index a25cc54..d535f83 100644 --- a/src/box/relay.cc +++ b/src/box/relay.cc @@ -52,6 +52,7 @@ #include "xrow_io.h" #include "xstream.h" #include "wal.h" +#include "ctl.h" /** * Cbus message to send status updates from relay to tx thread. @@ -548,6 +549,12 @@ relay_subscribe_f(va_list ap) if (!diag_is_empty(&relay->diag)) { /* An error has occurred while reading ACKs of xlog. */ diag_move(&relay->diag, diag_get()); + struct on_ctl_event_ctx ctx; + ctx.type = CTL_EVENT_REPLICA_CONNECTION_ERROR; + ctx.replica_id = relay->replica->id; + if (run_on_ctl_event_triggers(&ctx) < 0) + say_error("ctl_trigger error in replica error: %s", + diag_last_error(diag_get())->errmsg); /* Reference the diag in the status. */ diag_add_error(&relay->diag, diag_last_error(diag_get())); } diff --git a/test/replication/master_onctl.lua b/test/replication/master_onctl.lua index e0eb39a..355e791 100644 --- a/test/replication/master_onctl.lua +++ b/test/replication/master_onctl.lua @@ -7,6 +7,7 @@ READ_ONLY = 0 READ_WRITE = 0 REPLICASET_ADD = {} REPLICASET_REMOVE = {} +REPLICA_CONNECTION_ERROR = {} local function onctl(ctx) if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then @@ -21,6 +22,8 @@ local function onctl(ctx) table.insert(REPLICASET_ADD, ctx.replica_id) elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then table.insert(REPLICASET_REMOVE, ctx.replica_id) + elseif ctx.type == box.ctl.event.REPLICA_CONNECTION_ERROR then + table.insert(REPLICA_CONNECTION_ERROR, ctx.replica_id) end end diff --git a/test/replication/onctl.result b/test/replication/onctl.result index 19b3e67..24a6683 100644 --- a/test/replication/onctl.result +++ b/test/replication/onctl.result @@ -50,6 +50,10 @@ REPLICASET_REMOVE --- - - 1 ... +REPLICA_CONNECTION_ERROR +--- +- [] +... REPLICASET_ADD = {} --- ... @@ -94,6 +98,10 @@ REPLICASET_REMOVE --- - [] ... +REPLICA_CONNECTION_ERROR +--- +- [] +... new_replica_id --- - 2 @@ -186,6 +194,10 @@ test_run:cmd("switch master") --- - true ... +REPLICA_CONNECTION_ERROR +--- +- - 2 +... box.schema.user.revoke('guest', 'replication') --- ... diff --git a/test/replication/onctl.test.lua b/test/replication/onctl.test.lua index ff6a898..352b118 100644 --- a/test/replication/onctl.test.lua +++ b/test/replication/onctl.test.lua @@ -16,6 +16,7 @@ READ_WRITE REPLICASET_ADD -- must be one entry. Deletion of initial tuple in _cluster space. REPLICASET_REMOVE +REPLICA_CONNECTION_ERROR REPLICASET_ADD = {} REPLICASET_REMOVE = {} @@ -39,6 +40,7 @@ test_run:cmd("start server replica") REPLICASET_ADD REPLICASET_REMOVE +REPLICA_CONNECTION_ERROR new_replica_id deleted_replica_id @@ -80,8 +82,9 @@ test_run:cmd("restart server replica") -- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. --test_run:grep_log('replica', 'test replica shutdown') - test_run:cmd("switch master") +REPLICA_CONNECTION_ERROR + box.schema.user.revoke('guest', 'replication') _ = box.space._cluster:delete{2} -- 2.7.4 ^ permalink raw reply [flat|nested] 7+ messages in thread
* [tarantool-patches] Re: [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event Ilya Markov @ 2018-07-31 11:40 ` Konstantin Belyavskiy 0 siblings, 0 replies; 7+ messages in thread From: Konstantin Belyavskiy @ 2018-07-31 11:40 UTC (permalink / raw) To: georgy, Илья Марков Cc: tarantool-patches [-- Attachment #1: Type: text/plain, Size: 5355 bytes --] Hi, Overall patch looks good with minor complains: - unused header. >Четверг, 14 июня 2018, 18:04 +03:00 от Ilya Markov <imarkov@tarantool.org>: > >Add event: replica fails with some error. > >In scope of #3159 >--- > src/box/ctl.h | 1 + > src/box/lua/ctl.c | 6 +++++- > src/box/relay.cc | 7 +++++++ > test/replication/master_onctl.lua | 3 +++ > test/replication/onctl.result | 12 ++++++++++++ > test/replication/onctl.test.lua | 5 ++++- > 6 files changed, 32 insertions(+), 2 deletions(-) > >diff --git a/src/box/ctl.h b/src/box/ctl.h >index 1dbb6be..db6f08a 100644 >--- a/src/box/ctl.h >+++ b/src/box/ctl.h >@@ -49,6 +49,7 @@ enum ctl_event_type { > CTL_EVENT_SHUTDOWN, > CTL_EVENT_REPLICASET_ADD, > CTL_EVENT_REPLICASET_REMOVE, >+ CTL_EVENT_REPLICA_CONNECTION_ERROR, > }; > > struct on_ctl_event_ctx { >diff --git a/src/box/lua/ctl.c b/src/box/lua/ctl.c >index 5bd9be3..8a0dfc2 100644 >--- a/src/box/lua/ctl.c >+++ b/src/box/lua/ctl.c >@@ -37,6 +37,7 @@ > #include <lualib.h> > #include <lua/trigger.h> > #include <box/ctl.h> > >+#include <tt_uuid.h> Please remove it, since it's unused. > > > #include "lua/utils.h" > >@@ -77,7 +78,8 @@ lbox_push_on_ctl_event(struct lua_State *L, void *event) > lua_settable(L, -3); > > if (ctx->type == CTL_EVENT_REPLICASET_ADD || >- ctx->type == CTL_EVENT_REPLICASET_REMOVE) { >+ ctx->type == CTL_EVENT_REPLICASET_REMOVE || >+ ctx->type == CTL_EVENT_REPLICA_CONNECTION_ERROR) { > lua_pushstring(L, "replica_id"); > luaL_pushuint64(L, ctx->replica_id); > lua_settable(L, -3); >@@ -125,5 +127,7 @@ box_lua_ctl_init(struct lua_State *L) > lua_setfield(L, -2, "REPLICASET_ADD"); > lua_pushnumber(L, CTL_EVENT_REPLICASET_REMOVE); > lua_setfield(L, -2, "REPLICASET_REMOVE"); >+ lua_pushnumber(L, CTL_EVENT_REPLICA_CONNECTION_ERROR); >+ lua_setfield(L, -2, "REPLICA_CONNECTION_ERROR"); > lua_pop(L, 2); /* box, ctl */ > } >diff --git a/src/box/relay.cc b/src/box/relay.cc >index a25cc54..d535f83 100644 >--- a/src/box/relay.cc >+++ b/src/box/relay.cc >@@ -52,6 +52,7 @@ > #include "xrow_io.h" > #include "xstream.h" > #include "wal.h" >+#include "ctl.h" > > /** > * Cbus message to send status updates from relay to tx thread. >@@ -548,6 +549,12 @@ relay_subscribe_f(va_list ap) > if (!diag_is_empty(&relay->diag)) { > /* An error has occurred while reading ACKs of xlog. */ > diag_move(&relay->diag, diag_get()); >+ struct on_ctl_event_ctx ctx; >+ ctx.type = CTL_EVENT_REPLICA_CONNECTION_ERROR; >+ ctx.replica_id = relay->replica->id; >+ if (run_on_ctl_event_triggers(&ctx) < 0) >+ say_error("ctl_trigger error in replica error: %s", >+ diag_last_error(diag_get())->errmsg); > /* Reference the diag in the status. */ > diag_add_error(&relay->diag, diag_last_error(diag_get())); > } >diff --git a/test/replication/master_onctl.lua b/test/replication/master_onctl.lua >index e0eb39a..355e791 100644 >--- a/test/replication/master_onctl.lua >+++ b/test/replication/master_onctl.lua >@@ -7,6 +7,7 @@ READ_ONLY = 0 > READ_WRITE = 0 > REPLICASET_ADD = {} > REPLICASET_REMOVE = {} >+REPLICA_CONNECTION_ERROR = {} > > local function onctl(ctx) > if ctx.type == box.ctl.event.SYSTEM_SPACE_RECOVERY then >@@ -21,6 +22,8 @@ local function onctl(ctx) > table.insert(REPLICASET_ADD, ctx.replica_id) > elseif ctx.type == box.ctl.event.REPLICASET_REMOVE then > table.insert(REPLICASET_REMOVE, ctx.replica_id) >+ elseif ctx.type == box.ctl.event.REPLICA_CONNECTION_ERROR then >+ table.insert(REPLICA_CONNECTION_ERROR, ctx.replica_id) > end > end > >diff --git a/test/replication/onctl.result b/test/replication/onctl.result >index 19b3e67..24a6683 100644 >--- a/test/replication/onctl.result >+++ b/test/replication/onctl.result >@@ -50,6 +50,10 @@ REPLICASET_REMOVE > --- > - - 1 > ... >+REPLICA_CONNECTION_ERROR >+--- >+- [] >+... > REPLICASET_ADD = {} > --- > ... >@@ -94,6 +98,10 @@ REPLICASET_REMOVE > --- > - [] > ... >+REPLICA_CONNECTION_ERROR >+--- >+- [] >+... > new_replica_id > --- > - 2 >@@ -186,6 +194,10 @@ test_run:cmd("switch master") > --- > - true > ... >+REPLICA_CONNECTION_ERROR >+--- >+- - 2 >+... > box.schema.user.revoke('guest', 'replication') > --- > ... >diff --git a/test/replication/onctl.test.lua b/test/replication/onctl.test.lua >index ff6a898..352b118 100644 >--- a/test/replication/onctl.test.lua >+++ b/test/replication/onctl.test.lua >@@ -16,6 +16,7 @@ READ_WRITE > REPLICASET_ADD > -- must be one entry. Deletion of initial tuple in _cluster space. > REPLICASET_REMOVE >+REPLICA_CONNECTION_ERROR > > REPLICASET_ADD = {} > REPLICASET_REMOVE = {} >@@ -39,6 +40,7 @@ test_run:cmd("start server replica") > > REPLICASET_ADD > REPLICASET_REMOVE >+REPLICA_CONNECTION_ERROR > > new_replica_id > deleted_replica_id >@@ -80,8 +82,9 @@ test_run:cmd("restart server replica") > -- TODO: test SHUTDOWN, when it is possible to grep logs of killed replica. > --test_run:grep_log('replica', 'test replica shutdown') > >- > test_run:cmd("switch master") >+REPLICA_CONNECTION_ERROR >+ > box.schema.user.revoke('guest', 'replication') > _ = box.space._cluster:delete{2} > >-- >2.7.4 > > Best regards, Konstantin Belyavskiy k.belyavskiy@tarantool.org [-- Attachment #2: Type: text/html, Size: 7087 bytes --] ^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2018-07-31 11:40 UTC | newest] Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2018-06-14 15:04 [tarantool-patches] [box.ctl 0/3] Introduce box.ctl.on_ctl_event trigger Ilya Markov 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 1/3] box.ctl: Introduce stab box.ctl.on_ctl_event Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 2/3] box.ctl: Add on_ctl_event trigger calls Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy 2018-06-14 15:04 ` [tarantool-patches] [box.ctl 3/3] box.ctl: Add replica error event Ilya Markov 2018-07-31 11:40 ` [tarantool-patches] " Konstantin Belyavskiy
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox