eliaperantoni commented on code in PR #14439:
URL: https://github.com/apache/datafusion/pull/14439#discussion_r1943778591
##########
datafusion/common/src/error.rs:
##########
@@ -540,6 +570,37 @@ impl DataFusionError {
DiagnosticsIterator { head: self }.next()
}
+
+ /// Sometimes DataFusion is able to collect multiple errors in a SQL query
+ /// before terminating, e.g. across different expressions in a SELECT
+ /// statements or different sides of a UNION. This method returns an
+ /// iterator over all the errors in the collection.
+ ///
+ /// For this to work, the top-level error must be a
+ /// `DataFusionError::Collection`, not something that contains it.
+ pub fn iter(&self) -> impl Iterator<Item = &DataFusionError> {
+ struct ErrorIterator<'a> {
+ queue: VecDeque<&'a DataFusionError>,
+ }
+
+ impl<'a> Iterator for ErrorIterator<'a> {
+ type Item = &'a DataFusionError;
+
+ fn next(&mut self) -> Option<Self::Item> {
+ loop {
+ let popped = self.queue.pop_front()?;
+ match popped {
+ DataFusionError::Collection(errs) =>
self.queue.extend(errs),
+ _ => return Some(popped),
+ }
+ }
+ }
+ }
+
+ let mut queue = VecDeque::new();
+ queue.push_back(self);
+ ErrorIterator { queue }
+ }
Review Comment:
> That doesn't handle recursive Collections but I think that is ok
But then in a query like:
```sql
SELECT
bad,
bad
UNION
SELECT
bad
```
You would get one `DataFusionError::Collection` and one
`DataFusionError::Plan` whereas you could've gotten three
`DataFusionError::Plan`. I think that's worth having this `iter` that's
slightly more complicated.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]