1#include "duckdb/common/preserved_error.hpp"
2#include "duckdb/common/exception.hpp"
3
4#include "duckdb/common/string_util.hpp"
5#include "duckdb/common/to_string.hpp"
6#include "duckdb/common/types.hpp"
7
8namespace duckdb {
9
10PreservedError::PreservedError() : initialized(false), exception_instance(nullptr) {
11}
12
13PreservedError::PreservedError(const Exception &exception)
14 : initialized(true), type(exception.type), raw_message(SanitizeErrorMessage(error: exception.RawMessage())),
15 exception_instance(exception.Copy()) {
16}
17
18PreservedError::PreservedError(const string &message)
19 : initialized(true), type(ExceptionType::INVALID), raw_message(SanitizeErrorMessage(error: message)),
20 exception_instance(nullptr) {
21}
22
23const string &PreservedError::Message() {
24 if (final_message.empty()) {
25 final_message = Exception::ExceptionTypeToString(type) + " Error: " + raw_message;
26 }
27 return final_message;
28}
29
30string PreservedError::SanitizeErrorMessage(string error) {
31 return StringUtil::Replace(source: std::move(error), from: string("\0", 1), to: "\\0");
32}
33
34void PreservedError::Throw(const string &prepended_message) const {
35 D_ASSERT(initialized);
36 if (!prepended_message.empty()) {
37 string new_message = prepended_message + raw_message;
38 Exception::ThrowAsTypeWithMessage(type, message: new_message, original: exception_instance);
39 }
40 Exception::ThrowAsTypeWithMessage(type, message: raw_message, original: exception_instance);
41}
42
43const ExceptionType &PreservedError::Type() const {
44 D_ASSERT(initialized);
45 return this->type;
46}
47
48PreservedError &PreservedError::AddToMessage(const string &prepended_message) {
49 raw_message = prepended_message + raw_message;
50 return *this;
51}
52
53PreservedError::operator bool() const {
54 return initialized;
55}
56
57bool PreservedError::operator==(const PreservedError &other) const {
58 if (initialized != other.initialized) {
59 return false;
60 }
61 if (type != other.type) {
62 return false;
63 }
64 return raw_message == other.raw_message;
65}
66
67} // namespace duckdb
68