-
Notifications
You must be signed in to change notification settings - Fork 36.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
refactor: Add util::Result failure values, multiple error and warning messages #25665
base: master
Are you sure you want to change the base?
Conversation
Draft PR since I want to add a commit taking advantages of ability to return chain results and return warnings. |
The following sections might be updated with supplementary metadata relevant to reviewers and maintainers. Code Coverage & BenchmarksFor details see: https://corecheck.dev/bitcoin/bitcoin/pulls/25665. ReviewsSee the guideline for information on the review process.
If your review is incorrectly listed, please react with 👎 to this comment and the bot will ignore it on the next update. ConflictsReviewers, this pull request conflicts with the following ones:
If you consider this pull request important, please also help to review the conflicting pull requests. Ideally, start with the one that should be merged first. |
Use result.Update in CompleteChainstateInit() and ChainstateManager::ActivateSnapshot() so it is possible for them to return warning messages (about flush failures) in upcoming commits. CompleteChainstateInit() was previously changed to use util::Result in bitcoin#25665 and ChainstateManager::ActivateSnapshot() was changed to use it in bitcoin#30267, but previously these functions only returned Result values themselves, and did not call other functions that return Result values. Now, some functions they are calling will also return Result values, so refactor these functions to use result.Update so they can merge results and return complete error and warning messages.
7e2b357
to
58c33f0
Compare
Rebased 7e2b357 -> 58c33f0 ( |
Add util::Result support for returning more error information. For better error handling, adds the ability to return a value on failure, not just a value on success. This is a key missing feature that made the result class not useful for functions like LoadChainstate() which produce different errors that need to be handled differently. This change also makes some more minor improvements: - Smaller type size. util::Result<int> is 16 bytes, and util::Result<void> is 8 bytes. Previously util::Result<int> and util::Result<void> were 72 bytes. - More documentation and tests.
Previous commit causes the warning to be triggered, but the suboptimal return from const statement was added earlier in 517e204. Warning was causing CI failure https://cirrus-ci.com/task/6159914970644480
Add util::Result Update method to make it possible to change the value of an existing Result object. This will be useful for functions that can return multiple error and warning messages, and want to be able to change the result value while keeping existing messages.
Add util::Result support for returning warning messages and multiple errors, not just a single error string. This provides a way for functions to report errors and warnings in a standard way, and simplifies interfaces. The functionality is unit tested here, and put to use in followup PR bitcoin#25722
Suggested by Martin Leitner-Ankerl <martin.ankerl@gmail.com> bitcoin#25722 (comment) Co-authored-by: Martin Leitner-Ankerl <martin.ankerl@gmail.com>
Use result.Update in CompleteChainstateInit() and ChainstateManager::ActivateSnapshot() so it is possible for them to return warning messages (about flush failures) in upcoming commits. CompleteChainstateInit() was previously changed to use util::Result in bitcoin#25665 and ChainstateManager::ActivateSnapshot() was changed to use it in bitcoin#30267, but previously these functions only returned Result values themselves, and did not call other functions that return Result values. Now, some functions they are calling will also return Result values, so refactor these functions to use result.Update so they can merge results and return complete error and warning messages.
Use result.Update in CompleteChainstateInit() and ChainstateManager::ActivateSnapshot() so it is possible for them to return warning messages (about flush failures) in upcoming commits. CompleteChainstateInit() was previously changed to use util::Result in bitcoin#25665 and ChainstateManager::ActivateSnapshot() was changed to use it in bitcoin#30267, but previously these functions only returned Result values themselves, and did not call other functions that return Result values. Now, some functions they are calling will also return Result values, so refactor these functions to use result.Update so they can merge results and return complete error and warning messages.
58c33f0
to
5e14665
Compare
Use result.Update in CompleteChainstateInit() and ChainstateManager::ActivateSnapshot() so it is possible for them to return warning messages (about flush failures) in upcoming commits. CompleteChainstateInit() was previously changed to use util::Result in bitcoin#25665 and ChainstateManager::ActivateSnapshot() was changed to use it in bitcoin#30267, but previously these functions only returned Result values themselves, and did not call other functions that return Result values. Now, some functions they are calling will also return Result values, so refactor these functions to use result.Update so they can merge results and return complete error and warning messages.
Use result.Update in CompleteChainstateInit() and ChainstateManager::ActivateSnapshot() so it is possible for them to return warning messages (about flush failures) in upcoming commits. CompleteChainstateInit() was previously changed to use util::Result in bitcoin#25665 and ChainstateManager::ActivateSnapshot() was changed to use it in bitcoin#30267, but previously these functions only returned Result values themselves, and did not call other functions that return Result values. Now, some functions they are calling will also return Result values, so refactor these functions to use result.Update so they can merge results and return complete error and warning messages.
🐙 This pull request conflicts with the target branch and needs rebase. |
Add
util::Result
support for returning more error information and make use of it in LoadChainstate method as an initial application. Followup PRs #25722 and #29700 use it more broadly to return errors and warnings from wallet and kernel functions as well.This change adds two major features to the result class:
LoadChainstate()
which produce different errors that need to be handled differently 1.For better error reporting, adds the ability to return warning messages and multiple errors, not just a single error string. This provides a way for functions to report errors and warnings in a standard way, and simplifies interfaces:
This change also makes some more minor improvements:
Smaller type size.
util::Result<int>
is 16 bytes, andutil::Result<void>
is 8 bytes. Previously both were 72 bytes.Broader type compatibility. Supports noncopyable and nonmovable success and error types.
Alternatives & design notes
The main goal for the
util::Result
class is to provide a standard way for functions to report error and warnings strings. The interface tries to make it easy to provide detailed error feedback to end users, without cluttering code or making it harder to return other result information. There have been multiple iterations of the design using different internal representations and providing different capabilities:tuple<T,optional<bilingual_str>>
variant<T,bilingual_str>
variant<monostate,T,F>
tuple<variant<T,F>,bilingual_str>
tuple<T,optional<bilingual_str>>
tuple<T,unique_ptr<tuple<F,bilingual_str>>
unique_ptr
to reduce result type size, and avoids heap allocation in the happy path.Prior discussions & history
furszy introduced a
BResult
class providing a standard error reporting mechanism in #25218. It was renamed toutil::Result
in #25721 but kept the same representation and capabilities.MarcoFalke suggested using
BResult
for theLoadChainstate
function in #25308 (comment). Inability to useBResult
there due to lack of support for failure values led to initial work on #25608.w0xlt wrote a
StructuredResult
class in #25308 adding the ability to return failure values but sacrificing standard error reporting, which led to more work on #25608.martinus suggested a space optimization in #25608 (comment) that also made it easier to support distinct failure & success types, leading to #25665 as a replacement for #25608.
Footnotes
Ability to return error values was actually present in the original implementation of #25218, but unfortunately removed in later iterations. ↩