This is an automated email from the ASF dual-hosted git repository.
liaoxin01 pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/doris.git
The following commit(s) were added to refs/heads/master by this push:
new 38df92bc209 [fix](scan) Avoid misleading "storage reader" wrapper for
data/expression errors (#64755)
38df92bc209 is described below
commit 38df92bc209e4bed9492509791ca3ae1bd7c94c3
Author: Xin Liao <[email protected]>
AuthorDate: Thu Jun 25 16:03:45 2026 +0800
[fix](scan) Avoid misleading "storage reader" wrapper for data/expression
errors (#64755)
## Proposed changes
### Problem
When an `INSERT`/`CTAS` (or any query) hits a data-conversion error
during scan — e.g. a strict `CAST(... AS BIGINT)` on an empty string
produced by `regexp_extract`, which returns `INVALID_ARGUMENT parse
number fail, string: ''` — the user-facing error reads:
```
[INVALID_ARGUMENT]parse number fail, string: ''failed to initialize storage
reader. tablet=421411554, backend=10.228.1.18
```
The `failed to initialize storage reader. tablet=...` suffix makes it
look like the tablet/segment is corrupted or missing, when the real
cause is a data/expression error.
### Root cause
`OlapScanner::_open_impl` appended `failed to initialize storage reader.
tablet=...` to **any** non-OK status returned by `TabletReader::init()`.
But `init()` does not merely set up objects — the merge reader eagerly
reads the first block of each rowset (`BlockReader::_init_collect_iter`
→ `VCollectIterator::build_heap` → `Level0Iterator::refresh_current_row`
→ `RowsetReader::next_batch`) to seed the merge heap. Pushed-down
expressions (`common_expr_ctxs`) are evaluated during that first-block
read, so a strict-cast failure surfaces inside `init()` and gets wrapped
with the storage-reader message.
### Fix
Branch on the error code: only genuine storage-level failures keep the
`failed to initialize storage reader` wording. For `INVALID_ARGUMENT`
(data/expression errors) the message stays neutral and explicitly notes
it is a data/expression error rather than a storage failure, while still
reporting tablet/backend for locating the node.
This is purely a message/diagnostics change; control flow and the
returned error code are unchanged. The underlying strict-cast semantics
issue is tracked separately (see apache/doris#64266).
## Further comments
No behavior change other than the error text; no new tests added.
---
be/src/exec/scan/olap_scanner.cpp | 6 ++++--
.../test_index_compound_directory_fault_injection.groovy | 5 ++++-
2 files changed, 8 insertions(+), 3 deletions(-)
diff --git a/be/src/exec/scan/olap_scanner.cpp
b/be/src/exec/scan/olap_scanner.cpp
index 8da4483ea3a..32097681467 100644
--- a/be/src/exec/scan/olap_scanner.cpp
+++ b/be/src/exec/scan/olap_scanner.cpp
@@ -301,8 +301,10 @@ Status OlapScanner::_open_impl(RuntimeState* state) {
auto res = _tablet_reader->init(_tablet_reader_params);
if (!res.ok()) {
- res.append("failed to initialize storage reader. tablet=" +
- std::to_string(_tablet_reader_params.tablet->tablet_id()) +
+ // init() also runs the eager first-row read that evaluates
pushed-down expressions,
+ // so res may be a data/expression error rather than a storage
failure. Keep its own
+ // message and only append the tablet/backend, without a misleading
storage wording.
+ res.append(". tablet=" +
std::to_string(_tablet_reader_params.tablet->tablet_id()) +
", backend=" + BackendOptions::get_localhost());
return res;
}
diff --git
a/regression-test/suites/fault_injection_p0/test_index_compound_directory_fault_injection.groovy
b/regression-test/suites/fault_injection_p0/test_index_compound_directory_fault_injection.groovy
index ca25f47c88d..a3c90a0a9ae 100644
---
a/regression-test/suites/fault_injection_p0/test_index_compound_directory_fault_injection.groovy
+++
b/regression-test/suites/fault_injection_p0/test_index_compound_directory_fault_injection.groovy
@@ -178,7 +178,10 @@ suite("test_index_compound_directory_fault_injection",
"nonConcurrent") {
res = sql "select COUNT() from
${test_index_compound_directory} where request match 'gif'"
try_sql("DROP TABLE IF EXISTS
${test_index_compound_directory}")
} catch(Exception ex) {
- assertTrue(ex.toString().contains("failed to initialize
storage reader"))
+ // _tablet_reader->init() now returns the underlying error
verbatim and only
+ // appends the tablet/backend context (no longer the misleading
+ // "failed to initialize storage reader" wording).
+ assertTrue(ex.toString().contains("tablet=") &&
ex.toString().contains("backend="))
logger.info("_mock_append_data_error_in_fsindexoutput_flushBuffer, result: " +
ex)
} finally {
GetDebugPoint().disableDebugPointForAllBEs("DorisFSDirectory::FSIndexOutput._mock_append_data_error_in_fsindexoutput_flushBuffer")
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]