From: Vladimir Davydov <vdavydov.dev@gmail.com>
To: kostja@tarantool.org
Cc: tarantool-patches@freelists.org
Subject: [PATCH v2 7/8] vinyl: factor out vy_check_is_unique_secondary
Date: Sun, 27 May 2018 22:05:55 +0300 [thread overview]
Message-ID: <089a67b8077d0fa67da66c4868e0755f3aa01973.1527446023.git.vdavydov.dev@gmail.com> (raw)
In-Reply-To: <cover.1527446023.git.vdavydov.dev@gmail.com>
In-Reply-To: <cover.1527446023.git.vdavydov.dev@gmail.com>
We need to check unique constraint when building a new index. So let's
factor out this helper function and pass space_name, index_name, and
read view to it explicitly (because index_name_by_id isn't going to work
for an index that is under construction and there's no tx when we are
building a new index). Suggested by @Gerold103.
Needed for #1653
---
src/box/vinyl.c | 81 +++++++++++++++++++++++++++++++++++++++------------------
1 file changed, 56 insertions(+), 25 deletions(-)
diff --git a/src/box/vinyl.c b/src/box/vinyl.c
index 4d670328..41ffa42c 100644
--- a/src/box/vinyl.c
+++ b/src/box/vinyl.c
@@ -1353,7 +1353,9 @@ vy_lsm_get(struct vy_lsm *lsm, struct vy_tx *tx,
* a duplicate key error in the diagnostics area.
* @param env Vinyl environment.
* @param tx Current transaction.
- * @param space Target space.
+ * @param rv Read view.
+ * @param space_name Space name.
+ * @param index_name Index name.
* @param lsm LSM tree in which to search.
* @param key Key statement.
*
@@ -1361,7 +1363,9 @@ vy_lsm_get(struct vy_lsm *lsm, struct vy_tx *tx,
* @retval -1 Memory error or the key is found.
*/
static inline int
-vy_check_is_unique(struct vy_env *env, struct vy_tx *tx, struct space *space,
+vy_check_is_unique(struct vy_env *env, struct vy_tx *tx,
+ const struct vy_read_view **rv,
+ const char *space_name, const char *index_name,
struct vy_lsm *lsm, struct tuple *key)
{
struct tuple *found;
@@ -1371,20 +1375,57 @@ vy_check_is_unique(struct vy_env *env, struct vy_tx *tx, struct space *space,
*/
if (env->status != VINYL_ONLINE)
return 0;
- if (vy_lsm_get(lsm, tx, vy_tx_read_view(tx), key, &found))
+ if (vy_lsm_get(lsm, tx, rv, key, &found))
return -1;
if (found) {
tuple_unref(found);
diag_set(ClientError, ER_TUPLE_FOUND,
- index_name_by_id(space, lsm->index_id),
- space_name(space));
+ index_name, space_name);
return -1;
}
return 0;
}
/**
+ * Check if insertion of a new tuple violates unique constraint
+ * of a secondary index.
+ * @param env Vinyl environment.
+ * @param tx Current transaction.
+ * @param rv Read view.
+ * @param space_name Space name.
+ * @param index_name Index name.
+ * @param lsm LSM tree corresponding to the index.
+ * @param stmt New tuple.
+ *
+ * @retval 0 Success, unique constraint is satisfied.
+ * @retval -1 Duplicate is found or read error occurred.
+ */
+static int
+vy_check_is_unique_secondary(struct vy_env *env, struct vy_tx *tx,
+ const struct vy_read_view **rv,
+ const char *space_name, const char *index_name,
+ struct vy_lsm *lsm, const struct tuple *stmt)
+{
+ assert(lsm->index_id > 0);
+ struct key_def *def = lsm->key_def;
+ if (lsm->check_is_unique &&
+ !key_update_can_be_skipped(def->column_mask,
+ vy_stmt_column_mask(stmt)) &&
+ (!def->is_nullable || !vy_tuple_key_contains_null(stmt, def))) {
+ struct tuple *key = vy_stmt_extract_key(stmt, def,
+ lsm->env->key_format);
+ if (key == NULL)
+ return -1;
+ int rc = vy_check_is_unique(env, tx, rv, space_name,
+ index_name, lsm, key);
+ tuple_unref(key);
+ return rc;
+ }
+ return 0;
+}
+
+/**
* Insert a tuple in a primary index LSM tree.
* @param env Vinyl environment.
* @param tx Current transaction.
@@ -1407,7 +1448,9 @@ vy_insert_primary(struct vy_env *env, struct vy_tx *tx, struct space *space,
* conflict with existing tuples.
*/
if (pk->check_is_unique &&
- vy_check_is_unique(env, tx, space, pk, stmt) != 0)
+ vy_check_is_unique(env, tx, vy_tx_read_view(tx), space_name(space),
+ index_name_by_id(space, pk->index_id),
+ pk, stmt) != 0)
return -1;
return vy_tx_set(tx, pk, stmt);
}
@@ -1431,25 +1474,13 @@ vy_insert_secondary(struct vy_env *env, struct vy_tx *tx, struct space *space,
vy_stmt_type(stmt) == IPROTO_REPLACE);
assert(tx != NULL && tx->state == VINYL_TX_READY);
assert(lsm->index_id > 0);
- /*
- * If the index is unique then the new tuple must not
- * conflict with existing tuples. If the index is not
- * unique a conflict is impossible.
- */
- if (lsm->check_is_unique &&
- !key_update_can_be_skipped(lsm->key_def->column_mask,
- vy_stmt_column_mask(stmt)) &&
- (!lsm->key_def->is_nullable ||
- !vy_tuple_key_contains_null(stmt, lsm->key_def))) {
- struct tuple *key = vy_stmt_extract_key(stmt, lsm->key_def,
- lsm->env->key_format);
- if (key == NULL)
- return -1;
- int rc = vy_check_is_unique(env, tx, space, lsm, key);
- tuple_unref(key);
- if (rc != 0)
- return -1;
- }
+
+ if (vy_check_is_unique_secondary(env, tx, vy_tx_read_view(tx),
+ space_name(space),
+ index_name_by_id(space, lsm->index_id),
+ lsm, stmt) != 0)
+ return -1;
+
/*
* We must always append the statement to transaction write set
* of each LSM tree, even if operation itself does not update
--
2.11.0
next prev parent reply other threads:[~2018-05-27 19:05 UTC|newest]
Thread overview: 14+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-05-27 19:05 [PATCH v2 0/8] Allow to build indexes for vinyl spaces Vladimir Davydov
2018-05-27 19:05 ` [PATCH v2 1/8] vinyl: allocate key parts in vy_recovery_do_create_lsm Vladimir Davydov
2018-05-30 11:51 ` Konstantin Osipov
2018-05-27 19:05 ` [PATCH v2 2/8] vinyl: update recovery context with records written during recovery Vladimir Davydov
2018-05-30 11:51 ` Konstantin Osipov
2018-05-27 19:05 ` [PATCH v2 3/8] vinyl: log new index before WAL write on DDL Vladimir Davydov
2018-06-06 18:01 ` Konstantin Osipov
2018-05-27 19:05 ` [PATCH v2 4/8] vinyl: bump mem version after committing statement Vladimir Davydov
2018-06-07 5:41 ` Konstantin Osipov
2018-05-27 19:05 ` [PATCH v2 5/8] vinyl: allow to commit statements to mem in arbitrary order Vladimir Davydov
2018-06-07 5:41 ` Konstantin Osipov
2018-05-27 19:05 ` [PATCH v2 6/8] vinyl: relax limitation imposed on run min/max lsn Vladimir Davydov
2018-05-27 19:05 ` Vladimir Davydov [this message]
2018-05-27 19:05 ` [PATCH v2 8/8] vinyl: allow to build secondary index for non-empty space Vladimir Davydov
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=089a67b8077d0fa67da66c4868e0755f3aa01973.1527446023.git.vdavydov.dev@gmail.com \
--to=vdavydov.dev@gmail.com \
--cc=kostja@tarantool.org \
--cc=tarantool-patches@freelists.org \
--subject='Re: [PATCH v2 7/8] vinyl: factor out vy_check_is_unique_secondary' \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox