-
Notifications
You must be signed in to change notification settings - Fork 1.3k
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
Add isPartialResult flag to broker response #11592
Conversation
Codecov Report
@@ Coverage Diff @@
## master #11592 +/- ##
============================================
- Coverage 62.98% 61.39% -1.60%
+ Complexity 1141 207 -934
============================================
Files 2367 2373 +6
Lines 127958 128284 +326
Branches 19744 19804 +60
============================================
- Hits 80593 78755 -1838
- Misses 41630 43850 +2220
+ Partials 5735 5679 -56
Flags with carried forward coverage won't be shown. Click here to find out more.
... and 225 files with indirect coverage changes 📣 We’re building smart automated test selection to slash your CI/CD build times. Learn more |
I thought this was already being returned as part of execution stats. I remember there was a flag hasPartialResults. How is this different ? |
brokerResponse.setPartialResult(true); | ||
brokerResponse.addToExceptions(new QueryProcessingException(QueryException.SERVER_SEGMENT_MISSING_ERROR_CODE, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If some servers are not available we currently used to throw an Exception instead of the results
So likely this won't be required as we have an exception stating which servers are in error
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't see partial result being added when server returns exception. Did I miss it somewhere?
@@ -607,6 +607,7 @@ protected BrokerResponse handleRequest(long requestId, String query, @Nullable S | |||
int numUnavailableSegments = unavailableSegments.size(); | |||
requestContext.setNumUnavailableSegments(numUnavailableSegments); | |||
|
|||
boolean isPartialResult = false; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what is the "partial result" definition? for example if grouplimits reached for order by queries do we consider that as partial results?
i guess the question is when do we set the flag for:
- result is correct (this is no flag)
- result is correct but we didn't look at the entire table (e.g.
select * limit 1000
) - result is not correct but each row is correct (e.g.
select ... group by key order by COUNT(*)
) - result is not correct, some rows might be correct some rows might not due to data size limit (
select ... join ... group by ...
when join hits maxRow limit, grouping result might be partial) - result is incorrect (we shouldn't return in this case)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@walterddr my idea with this flag is to generally cover all cases where we do sent a response back (no failures), but we also know either some segments / servers were not queried (segment unavailability / server down etc) or some rows / groups were ignored.
-
result is correct (this is no flag)
-
result is correct but we didn't look at the entire table (e.g. select * limit 1000) -> I don't think this should be flagged as partial result since the result is correct, we don't have to look the entire table up
-
result is not correct but each row is correct (e.g.
select ... group by key order by COUNT(*)
) -> I'm not sure if there is a way of knowing this in the current server -> broker response? If yes, then I do think we should flag this a partial result. I may not have full context, but is it the trimming of cross segment groups tomax(limit * 5, DEFAULT_MIN_NUM_GROUPS)
that you're referring to? -
result is not correct, some rows might be correct some rows might not due to data size limit (select ... join ... group by ... when join hits maxRow limit, grouping result might be partial) -> Yes this should classify as partialResponse imo
-
result is incorrect (we shouldn't return in this case) -> What do you mean by incorrect here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think general definition (and this is what we did in the current engine IIRC) is that partialResults flag would be set to true in either of the following:
- Result is incomplete (determined by server based on things like GROUP BY heuristics, threshold etc)
- Not all servers queried responded (determine by broker)
Basically when we are able to determine that there was more data to be processed but we couldn't either because of our own algorithms (heuristics / thresholds etc) or failed to hear back from servers.
I think (1) can also be determined by broker during merge.
For SELECT with ORDER BY, I don't think we ever set partialResults
on server and there is no need imo.
For SELECT without ORDER BY, servers do early termination based on LIMIT N, but again partialResults is not set and there is no need.
@Jackie-Jiang @siddharthteotia @walterddr @eaugene
|
brokerResponse.addToExceptions(new QueryProcessingException(QueryException.SERVER_NOT_RESPONDING_ERROR_CODE, | ||
String.format("%d servers %s not responded", numServersNotResponded, serversNotResponded))); | ||
_brokerMetrics.addMeteredTableValue(rawTableName, BrokerMeter.BROKER_RESPONSES_WITH_PARTIAL_SERVERS_RESPONDED, 1); | ||
} | ||
if (totalServersFailedOrNotResponded > 0) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why do we need this? we can simply do
if (totalServersFailedOrNotResponded > 0) { | |
if (numServersQueried - numServersResponded > 0) { |
if there's any exception inside the response, i thought the broker reducer is going to rectify and add proper partial result or failure inside?
for example if it is a SELECT * FROM tbl LIMIT 10
then
- original logic: selection reducer will not tag partial response as long as there's 1 server returns more than 10 rows
- in this PR: it will tag as long as 1 server returns an exception
is that the intention?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
chatted with @Jackie-Jiang offline. i think the idea is to set this as "partial response" even when the results are completely correct. we still want to surface a global "flag" indicating that 'something can be improved underneath'.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Jackie-Jiang @walterddr This was added to make sure any exceptions in the returned dataTable (even if the server has responded with a valid set of rows), are also flagged as potentially partial
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should not be handled here. We can simply check if (brokerResponse.getExceptionsSize() > 0)
in the end in BaseBrokerRequestHandler
and set the flag.
@saurabhd336 We should count the result as partial if there are exceptions in the server response even if the server responded. One example would be when some segments dropped due to schema mismatch on the server side. |
i think there's just one situation when server returns no exception but we still want to set the partial results flag --> that's numGroupsLimitReach flag, which is only a boolean flag in the data table but not part of exception. if we can rectify this we should be good to only look at exceptions? |
We don't want to model it as an exception because it can happen in happy path, and some client might simply count query with exception as failure |
@Jackie-Jiang as per the discussion above, does the PR look ok to you? |
brokerResponse.addToExceptions(new QueryProcessingException(QueryException.SERVER_NOT_RESPONDING_ERROR_CODE, | ||
String.format("%d servers %s not responded", numServersNotResponded, serversNotResponded))); | ||
_brokerMetrics.addMeteredTableValue(rawTableName, BrokerMeter.BROKER_RESPONSES_WITH_PARTIAL_SERVERS_RESPONDED, 1); | ||
} | ||
if (totalServersFailedOrNotResponded > 0) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should not be handled here. We can simply check if (brokerResponse.getExceptionsSize() > 0)
in the end in BaseBrokerRequestHandler
and set the flag.
// If segments are unavailable, the result should be considered partial | ||
isPartialResult = true; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We don't need to update it here. We may set the value in the end by checking if the response contains exceptions
dbff260
to
c9010f5
Compare
c9010f5
to
08654b0
Compare
A new flag to the broker response that explicitly denotes whether or not the result being returned is partial or not. This builds on top of PRs merged to resolve #7264