[ 
https://issues.apache.org/jira/browse/PHOENIX-8045?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Andrew Kyle Purtell updated PHOENIX-8045:
-----------------------------------------
    Description: 
During server-side scan execution Phoenix builds result rows for aggregation 
and state tracking using {{{}ByteUtil.getLargestPossibleRowKeyInRange(){}}}. 
This utility should construct a synthetic key that falls within the active 
scan's boundaries so that downstream client verification logic accepts the 
payload. In the table's end region, the upper limit is an empty byte array 
({{{}HConstants.EMPTY_END_ROW{}}}), conceptually representing positive infinity 
rather than a literal byte sequence.

However, because lexicographical comparison places any non-empty byte array 
after an empty array, the check misinterprets the conceptual indication of 
positive infinity / no end to the range as a zero-length empty start of the 
range. An assertion fails, logs a misleading error, and returns null. Callers 
then fall back to degenerate keys, such as the start key, stop row, or an empty 
key, which fail subsequent client side range checks and this can cause valid 
results to be discarded during background workloads like index builds, dropping 
out rows from the rebuild.

The fix makes {{ByteUtil}} consistent with the client side region boundary 
contract defined in {{{}ScanUtil.verifyKeyInScanRange(){}}}. An empty end key 
is treated as an unbounded range, skipping the upper limit comparison entirely.

  was:
During server-side scan execution Phoenix builds result rows for aggregation 
and state tracking using {{{}ByteUtil.getLargestPossibleRowKeyInRange(){}}}. 
This utility should construct a synthetic key that falls within the active 
scan's boundaries so that downstream client verification logic accepts the 
payload. In the table's end region, the upper limit is an empty byte array 
({{{}HConstants.EMPTY_END_ROW{}}}), conceptually representing positive infinity 
rather than a literal byte sequence.

Because lexicographical comparison places any non-empty byte array after an 
empty array, the check misinterprets the empty bound as a zero-length floor 
rather than an unbounded ceiling. Consequently, the assertion fails, logs an 
unexpected range error, and returns null. Callers then fall back to degenerate 
keys, such as the start key, stop row, or an empty key, which fail subsequent 
client side range checks and causes valid results to be discarded during 
background workloads like index builds.

The fix makes {{ByteUtil}} consistent with the client side region boundary 
contract defined in {{{}ScanUtil.verifyKeyInScanRange(){}}}. An empty end key 
is treated as an unbounded range, skipping the upper limit comparison entirely.


> Treat an empty end key as no upper bound in getLargestPossibleRowKeyInRange
> ---------------------------------------------------------------------------
>
>                 Key: PHOENIX-8045
>                 URL: https://issues.apache.org/jira/browse/PHOENIX-8045
>             Project: Phoenix
>          Issue Type: Bug
>          Components: core
>    Affects Versions: 5.3.2
>            Reporter: Andrew Kyle Purtell
>            Assignee: Andrew Kyle Purtell
>            Priority: Major
>             Fix For: 5.4.0, 5.3.3
>
>
> During server-side scan execution Phoenix builds result rows for aggregation 
> and state tracking using {{{}ByteUtil.getLargestPossibleRowKeyInRange(){}}}. 
> This utility should construct a synthetic key that falls within the active 
> scan's boundaries so that downstream client verification logic accepts the 
> payload. In the table's end region, the upper limit is an empty byte array 
> ({{{}HConstants.EMPTY_END_ROW{}}}), conceptually representing positive 
> infinity rather than a literal byte sequence.
> However, because lexicographical comparison places any non-empty byte array 
> after an empty array, the check misinterprets the conceptual indication of 
> positive infinity / no end to the range as a zero-length empty start of the 
> range. An assertion fails, logs a misleading error, and returns null. Callers 
> then fall back to degenerate keys, such as the start key, stop row, or an 
> empty key, which fail subsequent client side range checks and this can cause 
> valid results to be discarded during background workloads like index builds, 
> dropping out rows from the rebuild.
> The fix makes {{ByteUtil}} consistent with the client side region boundary 
> contract defined in {{{}ScanUtil.verifyKeyInScanRange(){}}}. An empty end key 
> is treated as an unbounded range, skipping the upper limit comparison 
> entirely.



--
This message was sent by Atlassian Jira
(v10.3.26#10030026)

Reply via email to