Skip to content

Commit

Permalink
MSET change it to batch write instead of batch per key (apache#1634)
Browse files Browse the repository at this point in the history
The previous implementation which wrote the batch per key,
we should change it to a single batch. Also use the multi-key
lock before the write operations instead of inside the loop.

This is mention in apache#1631, found by hulk.

Co-authored-by: mwish <1506118561@qq.com>
  • Loading branch information
enjoy-binbin and mapleFU authored Aug 7, 2023
1 parent 20b49b4 commit 0e73fec
Showing 1 changed file with 16 additions and 11 deletions.
27 changes: 16 additions & 11 deletions src/types/redis_string.cc
Original file line number Diff line number Diff line change
Expand Up @@ -371,28 +371,33 @@ rocksdb::Status String::MSet(const std::vector<StringPair> &pairs, uint64_t ttl,
expire = now + ttl;
}

// Data race, key string maybe overwrite by other key while didn't lock the key here,
// Data race, key string maybe overwrite by other key while didn't lock the keys here,
// to improve the set performance
std::string ns_key;
std::optional<MultiLockGuard> guard;
if (lock) {
std::vector<std::string> lock_keys;
lock_keys.reserve(pairs.size());
for (const StringPair &pair : pairs) {
AppendNamespacePrefix(pair.key, &ns_key);
lock_keys.emplace_back(ns_key);
}
guard.emplace(storage_->GetLockManager(), lock_keys);
}

auto batch = storage_->GetWriteBatchBase();
WriteBatchLogData log_data(kRedisString);
batch->PutLogData(log_data.Encode());
for (const auto &pair : pairs) {
std::string bytes;
Metadata metadata(kRedisString, false);
metadata.expire = expire;
metadata.Encode(&bytes);
bytes.append(pair.value.data(), pair.value.size());
auto batch = storage_->GetWriteBatchBase();
WriteBatchLogData log_data(kRedisString);
batch->PutLogData(log_data.Encode());
AppendNamespacePrefix(pair.key, &ns_key);
batch->Put(metadata_cf_handle_, ns_key, bytes);
std::optional<LockGuard> guard;
if (lock) {
guard.emplace(storage_->GetLockManager(), ns_key);
}
auto s = storage_->Write(storage_->DefaultWriteOptions(), batch->GetWriteBatch());
if (!s.ok()) return s;
}
return rocksdb::Status::OK();
return storage_->Write(storage_->DefaultWriteOptions(), batch->GetWriteBatch());
}

rocksdb::Status String::MSetNX(const std::vector<StringPair> &pairs, uint64_t ttl, bool *flag) {
Expand Down

0 comments on commit 0e73fec

Please sign in to comment.