[tarantool-patches] [PATCH v4 13/20] refactoring: remove exceptions from user_has_data
Ilya Kosarev
i.kosarev at tarantool.org
Mon Sep 23 18:57:04 MSK 2019
user_has_data is used in on_replace_dd_user therefore it has to be
cleared from exceptions. Now it doesn't throw any more. It means
we also need to clear from exceptions it's subsidiary function:
space_has_data. Their usages are updated.
Part of #4247
---
src/box/alter.cc | 85 ++++++++++++++++++++++++++++++++++--------------
1 file changed, 60 insertions(+), 25 deletions(-)
diff --git a/src/box/alter.cc b/src/box/alter.cc
index fda5cebd9..7c9a7179c 100644
--- a/src/box/alter.cc
+++ b/src/box/alter.cc
@@ -707,25 +707,41 @@ space_swap_fk_constraints(struct space *new_space, struct space *old_space)
* True if the space has records identified by key 'uid'.
* Uses 'iid' index.
*/
-bool
-space_has_data(uint32_t id, uint32_t iid, uint32_t uid)
+int
+space_has_data(uint32_t id, uint32_t iid, uint32_t uid, bool *out)
{
struct space *space = space_by_id(id);
- if (space == NULL)
- return false;
+ if (space == NULL) {
+ *out = false;
+ return 0;
+ }
- if (space_index(space, iid) == NULL)
- return false;
+ if (space_index(space, iid) == NULL) {
+ *out = false;
+ return 0;
+ }
+
+ if (!space_is_memtx(space)) {
+ diag_set(ClientError, ER_UNSUPPORTED,
+ space->engine->name, "system data");
+ return -1;
+ }
+ struct index *index = index_find(space, iid);
+ if (index == NULL)
+ return -1;
- struct index *index = index_find_system_xc(space, iid);
char key[6];
assert(mp_sizeof_uint(BOX_SYSTEM_ID_MIN) <= sizeof(key));
mp_encode_uint(key, uid);
- struct iterator *it = index_create_iterator_xc(index, ITER_EQ, key, 1);
+ struct iterator *it = index_create_iterator(index, ITER_EQ, key, 1);
+ if (it == NULL)
+ return -1;
IteratorGuard iter_guard(it);
- if (iterator_next_xc(it) != NULL)
- return true;
- return false;
+ struct tuple *tuple;
+ if (iterator_next(it, &tuple) != 0)
+ return -1;
+ *out = (tuple != NULL);
+ return 0;
}
/* }}} */
@@ -2121,7 +2137,9 @@ on_replace_dd_space(struct trigger * /* trigger */, void *event)
"the space has grants");
return -1;
}
- if (space_has_data(BOX_TRUNCATE_ID, 0, old_space->def->id)) {
+ if (space_has_data(BOX_TRUNCATE_ID, 0, old_space->def->id, &out) != 0)
+ return -1;
+ if (out) {
diag_set(ClientError, ER_DROP_SPACE,
space_name(old_space),
"the space has truncate record");
@@ -2641,8 +2659,8 @@ on_replace_dd_truncate(struct trigger * /* trigger */, void *event)
/* {{{ access control */
-bool
-user_has_data(struct user *user)
+int
+user_has_data(struct user *user, bool *has_data)
{
uint32_t uid = user->def->uid;
uint32_t spaces[] = { BOX_SPACE_ID, BOX_FUNC_ID, BOX_SEQUENCE_ID,
@@ -2653,18 +2671,26 @@ user_has_data(struct user *user)
*/
uint32_t indexes[] = { 1, 1, 1, 1, 0 };
uint32_t count = sizeof(spaces)/sizeof(*spaces);
+ bool out;
for (uint32_t i = 0; i < count; i++) {
- if (space_has_data(spaces[i], indexes[i], uid))
- return true;
+ if (space_has_data(spaces[i], indexes[i], uid, &out) != 0)
+ return -1;
+ if (out) {
+ *has_data = true;
+ return 0;
+ }
+ }
+ if (! user_map_is_empty(&user->users)) {
+ *has_data = true;
+ return 0;
}
- if (! user_map_is_empty(&user->users))
- return true;
/*
* If there was a role, the previous check would have
* returned true.
*/
assert(user_map_is_empty(&user->roles));
- return false;
+ *has_data = false;
+ return 0;
}
/**
@@ -2857,7 +2883,11 @@ on_replace_dd_user(struct trigger * /* trigger */, void *event)
* Can only delete user if it has no spaces,
* no functions and no grants.
*/
- if (user_has_data(old_user)) {
+ bool has_data;
+ if (user_has_data(old_user, &has_data) != 0) {
+ return -1;
+ }
+ if (has_data) {
diag_set(ClientError, ER_DROP_USER,
old_user->def->name, "the user has objects");
return -1;
@@ -3219,8 +3249,9 @@ on_replace_dd_func(struct trigger * /* trigger */, void *event)
"function has grants");
return -1;
}
- if (old_func != NULL &&
- space_has_data(BOX_FUNC_INDEX_ID, 1, old_func->def->fid)) {
+ if (space_has_data(BOX_FUNC_INDEX_ID, 1, old_func->def->fid, &out) != 0)
+ return -1;
+ if (old_func != NULL && out) {
diag_set(ClientError, ER_DROP_FUNCTION,
(unsigned) old_func->def->uid,
"function has references");
@@ -4136,17 +4167,21 @@ on_replace_dd_sequence(struct trigger * /* trigger */, void *event)
if (access_check_ddl(seq->def->name, seq->def->id, seq->def->uid,
SC_SEQUENCE, PRIV_D) != 0)
return -1;
- if (space_has_data(BOX_SEQUENCE_DATA_ID, 0, id)) {
+ bool out;
+ if (space_has_data(BOX_SEQUENCE_DATA_ID, 0, id, &out) != 0)
+ return -1;
+ if (out) {
diag_set(ClientError, ER_DROP_SEQUENCE,
seq->def->name, "the sequence has data");
return -1;
}
- if (space_has_data(BOX_SPACE_SEQUENCE_ID, 1, id)) {
+ if (space_has_data(BOX_SPACE_SEQUENCE_ID, 1, id, &out) != 0)
+ return -1;
+ if (out) {
diag_set(ClientError, ER_DROP_SEQUENCE,
seq->def->name, "the sequence is in use");
return -1;
}
- bool out;
if (schema_find_grants("sequence", seq->def->id, &out) != 0) {
return -1;
}
--
2.17.1
More information about the Tarantool-patches
mailing list