Skip to content

Commit 262cb95

Browse files
tjwilson90not-napoleon
authored andcommitted
Avoid precision loss in DocValueFormat.RAW#parseLong (#49063)
1 parent 33315a4 commit 262cb95

File tree

2 files changed

+9
-2
lines changed

2 files changed

+9
-2
lines changed

server/src/main/java/org/elasticsearch/search/DocValueFormat.java

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,12 @@ public String format(BytesRef value) {
115115

116116
@Override
117117
public long parseLong(String value, boolean roundUp, LongSupplier now) {
118+
try {
119+
// Prefer parsing as a long to avoid losing precision
120+
return Long.parseLong(value);
121+
} catch (NumberFormatException e) {
122+
// retry as a double
123+
}
118124
double d = Double.parseDouble(value);
119125
if (roundUp) {
120126
d = Math.ceil(d);

server/src/test/java/org/elasticsearch/search/DocValueFormatTests.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -168,6 +168,7 @@ public void testGeoTileFormat() {
168168
public void testRawParse() {
169169
assertEquals(-1L, DocValueFormat.RAW.parseLong("-1", randomBoolean(), null));
170170
assertEquals(1L, DocValueFormat.RAW.parseLong("1", randomBoolean(), null));
171+
assertEquals(Long.MAX_VALUE - 2, DocValueFormat.RAW.parseLong(Long.toString(Long.MAX_VALUE - 2), randomBoolean(), null));
171172
// not checking exception messages as they could depend on the JVM
172173
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseLong("", randomBoolean(), null));
173174
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseLong("abc", randomBoolean(), null));
@@ -176,8 +177,8 @@ public void testRawParse() {
176177
assertEquals(1d, DocValueFormat.RAW.parseDouble("1", randomBoolean(), null), 0d);
177178
assertEquals(.5, DocValueFormat.RAW.parseDouble("0.5", randomBoolean(), null), 0d);
178179
// not checking exception messages as they could depend on the JVM
179-
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseLong("", randomBoolean(), null));
180-
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseLong("abc", randomBoolean(), null));
180+
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseDouble("", randomBoolean(), null));
181+
expectThrows(IllegalArgumentException.class, () -> DocValueFormat.RAW.parseDouble("abc", randomBoolean(), null));
181182

182183
assertEquals(new BytesRef("abc"), DocValueFormat.RAW.parseBytesRef("abc"));
183184
}

0 commit comments

Comments
 (0)