database: Add error message with mutation info on commit log apply failure

Fixes #9408

While it is rare, some customer issues have shown that we can run into cases
where commit log apply (writing mutations to it) fails badly. In the known
cases, due to oversized mutations. While these should have been caught earlier
in the call chain really, it would probably help both end users and us (trying
to figure out how they got so big and how they got so far) iff we added info
to the errors thrown (and printed), such as ks, cf, and mutation content.
This commit is contained in:
Calle Wilund
2021-09-29 14:47:38 +00:00
parent 63ea666ca0
commit a6202ae079

View File

@@ -1726,12 +1726,25 @@ future<mutation> database::apply_counter_update(schema_ptr s, const frozen_mutat
}));
}
static void throw_commitlog_add_error(schema_ptr s, const frozen_mutation& m) {
// it is tempting to do a full pretty print here, but the mutation is likely
// humungous if we got an error, so just tell us where and pk...
std::throw_with_nested(std::runtime_error(format("Could not write mutation {}:{} ({}) to commitlog"
, s->ks_name(), s->cf_name()
, m.key()
)));
}
future<> database::apply_with_commitlog(column_family& cf, const mutation& m, db::timeout_clock::time_point timeout) {
db::rp_handle h;
if (cf.commitlog() != nullptr && cf.durable_writes()) {
auto fm = freeze(m);
commitlog_entry_writer cew(m.schema(), fm, db::commitlog::force_sync::no);
h = co_await cf.commitlog()->add_entry(m.schema()->id(), cew, timeout);
try {
commitlog_entry_writer cew(m.schema(), fm, db::commitlog::force_sync::no);
h = co_await cf.commitlog()->add_entry(m.schema()->id(), cew, timeout);
} catch (...) {
throw_commitlog_add_error(cf.schema(), fm);
}
}
try {
co_await apply_in_memory(m, cf, std::move(h), timeout);
@@ -1767,8 +1780,12 @@ future<> database::do_apply(schema_ptr s, const frozen_mutation& m, tracing::tra
db::rp_handle h;
auto cl = cf.commitlog();
if (cl != nullptr && cf.durable_writes()) {
commitlog_entry_writer cew(s, m, sync);
h = co_await cf.commitlog()->add_entry(uuid, cew, timeout);
try {
commitlog_entry_writer cew(s, m, sync);
h = co_await cf.commitlog()->add_entry(uuid, cew, timeout);
} catch (...) {
throw_commitlog_add_error(s, m);
}
}
try {
co_await this->apply_in_memory(m, s, std::move(h), timeout);