Skip to content

Commit cd8155b

Browse files
[Inference API] Handle empty date strings when parsing endpoint metadata (elastic#143584)
This adds handling of blank date strings when parsing endpoint metadata heuristics by treating it as `null`. This could not occur in practice as EIS won't be serving empty strings. However, there are tests that pass in an empty string (e.g. callers of `createAuthorizedEndpoint` in `ElasticInferenceServiceAuthorizationResponseEntityTests` may lead to this case). Rather than change the tests, it makes more sense to make date parsing more robust.
1 parent 9f27b96 commit cd8155b

File tree

3 files changed

+34
-16
lines changed

3 files changed

+34
-16
lines changed

x-pack/plugin/inference/src/main/java/org/elasticsearch/xpack/inference/common/parser/DateParser.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ public static LocalDate parseLocalDate(Map<String, Object> sourceMap, String key
2424

2525
public static LocalDate parseLocalDate(String dateString, String key, String root) {
2626
try {
27-
if (dateString == null) {
27+
if (Strings.isNullOrBlank(dateString)) {
2828
return null;
2929
}
3030
return LocalDate.parse(dateString);

x-pack/plugin/inference/src/test/java/org/elasticsearch/xpack/inference/common/parser/DateParserTests.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,11 @@ public void testParseLocalDate_FromString_ReturnsNull_WhenNull() {
7171
assertThat(DateParser.parseLocalDate((String) null, KEY, ROOT), nullValue());
7272
}
7373

74+
public void testParseLocalDate_FromString_ReturnsNull_WhenEmptyString() {
75+
assertThat(DateParser.parseLocalDate("", KEY, ROOT), nullValue());
76+
assertThat(DateParser.parseLocalDate(" ", KEY, ROOT), nullValue());
77+
}
78+
7479
public void testParseLocalDate_FromString_Throws_WhenInvalidFormat() {
7580
var e = expectThrows(IllegalArgumentException.class, () -> DateParser.parseLocalDate(INVALID_DATE_FORMAT, KEY, ROOT));
7681
assertThat(e.getMessage(), containsString(pathToKey(ROOT, KEY)));

x-pack/plugin/inference/src/test/java/org/elasticsearch/xpack/inference/services/elastic/authorization/ElasticInferenceServiceAuthorizationModelTests.java

Lines changed: 28 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1026,15 +1026,15 @@ public void testHandlesNullDatesInHeuristics() {
10261026
}
10271027

10281028
public void testFiltersEndpointsWithInvalidReleaseDate() {
1029-
var id1 = "id1";
1030-
var invalidId = "invalid_id";
1031-
var invalidId2 = "invalid_id2";
1029+
var validDateId = "valid_date_id";
1030+
var blankDateId = "blank_date_id";
1031+
var invalidDateId = "invalid_date_id";
10321032
var status = STATUS_GA;
10331033

10341034
var response = new ElasticInferenceServiceAuthorizationResponseEntity(
10351035
List.of(
10361036
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1037-
id1,
1037+
validDateId,
10381038
"name1",
10391039
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
10401040
status,
@@ -1046,7 +1046,7 @@ public void testFiltersEndpointsWithInvalidReleaseDate() {
10461046
null
10471047
),
10481048
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1049-
invalidId,
1049+
invalidDateId,
10501050
"name2",
10511051
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
10521052
status,
@@ -1058,13 +1058,13 @@ public void testFiltersEndpointsWithInvalidReleaseDate() {
10581058
null
10591059
),
10601060
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1061-
invalidId2,
1061+
blankDateId,
10621062
"name3",
10631063
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
10641064
status,
10651065
null,
1066-
TEST_RELEASE_DATE,
1067-
"",
1066+
" ",
1067+
null,
10681068
null,
10691069
null,
10701070
null
@@ -1073,19 +1073,20 @@ public void testFiltersEndpointsWithInvalidReleaseDate() {
10731073
);
10741074

10751075
var auth = ElasticInferenceServiceAuthorizationModel.of(response, "url");
1076-
assertThat(auth.getEndpointIds(), is(Set.of(id1)));
1076+
assertThat(auth.getEndpointIds(), is(Set.of(validDateId, blankDateId)));
10771077
assertTrue(auth.isAuthorized());
10781078
}
10791079

10801080
public void testFiltersEndpointsWithInvalidEndOfLifeDate() {
1081-
var id1 = "id1";
1082-
var invalidId = "invalid_id";
1081+
var validDateId = "valid_date_id";
1082+
var invalidDateId = "invalid_date_id";
1083+
var blankDateId = "blank_date_id";
10831084
var status = STATUS_GA;
10841085

10851086
var response = new ElasticInferenceServiceAuthorizationResponseEntity(
10861087
List.of(
10871088
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1088-
id1,
1089+
validDateId,
10891090
"name1",
10901091
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
10911092
status,
@@ -1097,22 +1098,34 @@ public void testFiltersEndpointsWithInvalidEndOfLifeDate() {
10971098
null
10981099
),
10991100
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1100-
invalidId,
1101+
invalidDateId,
11011102
"name2",
11021103
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
11031104
status,
11041105
null,
1105-
"",
1106+
TEST_RELEASE_DATE,
11061107
"invalid-date-format",
11071108
null,
11081109
null,
11091110
null
1111+
),
1112+
new ElasticInferenceServiceAuthorizationResponseEntity.AuthorizedEndpoint(
1113+
blankDateId,
1114+
"name2",
1115+
createTaskTypeObject(EIS_CHAT_PATH, TaskType.CHAT_COMPLETION.toString()),
1116+
status,
1117+
null,
1118+
TEST_RELEASE_DATE,
1119+
" ",
1120+
null,
1121+
null,
1122+
null
11101123
)
11111124
)
11121125
);
11131126

11141127
var auth = ElasticInferenceServiceAuthorizationModel.of(response, "url");
1115-
assertThat(auth.getEndpointIds(), is(Set.of(id1)));
1128+
assertThat(auth.getEndpointIds(), is(Set.of(validDateId, blankDateId)));
11161129
assertTrue(auth.isAuthorized());
11171130
}
11181131

0 commit comments

Comments
 (0)