Bug #5224
ROWID is a variable length binary value (4GL quirk)
0%
History
#2 Updated by Vladimir Tsichevski over 3 years ago
Parsing, formatting and comparing of ROWID
values works differently in FWD:
In OE:
ROWID
is a string of bytes of any length encoded in hexadecimal. For example, the string "0x000000000010000000000000000000000000000000000" is a validROWID
in OE.- All digits matter, including the leading zeroes, so "0x01" and "0x0001" represent two different
ROWID
s. - The interpretation of the contents of these bytes depends on the database backend used.
- In the application code, it is illegal to interpret these bytes as an integer number.
- If OE internal DB is used, the
RECID
s and table partition numbers are used to formROWID
s. - If an external database is used, the
ROWID
contents is provided by this external DB. - Conversion from the string to
ROWID
and back to string always produces the original string value. - When formatting, only the actual bytes in
ROWID
are printed, for example:STRING(TO-ROWID("0x00"))
gives "0x00". - When two
ROWID
s are compared, all actual bytes matter, for example:TO-ROWID("0x00") = TO-ROWID("0x0000")
gives "no".
In FWD:
ROWID
is always a 64-bit integer encoded as hexadecimal.- Leading zeroes in
ROWID
string representation are ignored, so "0x01" and "0x0001" represent the sameROWID
with value 1. - The number of hexadecimal digits (after leading zeroes are trimmed) is no more than 16.
- Conversion from a string to
ROWID
and back to string can produce a different string value. - When formatting, exactly 16 characters are always printed, for example:
STRING(TO-ROWID("0x00"))
gives "0x0000000000000000". - When two
ROWID
s are compared, the results of conversion to integers are compared, for example:TO-ROWID("0x00") = TO-ROWID("0x0000")
gives "yes".
To make FWD fully compatible, the internal representation of ROWID
needs to be changed to byte[]
of any length >= 1.
#3 Updated by Greg Shah over 3 years ago
At this time we have no reason to expect that real applications will depend upon these differences. In FWD code can take a real record in a buffer and that record's rowid can be converted to/from a string in a "round trip" and the result can be used to find that record again. This use case is common. Other cases described above envision arbitrary string construction which cannot be relied upon to match a real rowid even if one can create it, it won't find any record. In addition, any dependence upon the internal representation of a rowid is not stable, since it can change from version to version or even from data server to data server. In other words, it would be very fragile code that would potentially break over time in the 4GL as well. This would be a bad practice which is probably why we have not ever seen application code do such things.
The change to move to a byte[]
from a long
would be very intrusive and potentially costly from a performance perspective. As such, we have no plans to make that change. If some real application code is found and the use case is such that it is important and cannot be easily cleaned up in the 4GL, then we will reconsider the implications at that time.