Skip to content

Commit 75525d9

Browse files
committed
CMR-11452 - Updated default max window to 720 hours (30 days) and added support for header override to allow any size window
1 parent 7765c53 commit 75525d9

6 files changed

Lines changed: 80 additions & 20 deletions

File tree

bootstrap-app/README.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -255,6 +255,17 @@ Operator can use the `start_index` parameter to index concepts with sequence num
255255
The `/after_date_time` endpoint is retained for compatibility. New callers should use
256256
`/between_date_time`, which bounds the request to an explicit time range.
257257
Compatibility requests to `/after_date_time` are implicitly bounded from `date_time` to the request timestamp and are rejected when that window exceeds the configured maximum.
258+
The maximum is 30 days by default.
259+
260+
To allow an authorized request to exceed the configured maximum time range:
261+
262+
curl -i \
263+
-X POST \
264+
-H "CMR-Bulk-Index-Ignore-Time-Range-Limit: true" \
265+
"http://localhost:3006/bulk_index/after_date_time?date_time=2015-02-02T10:00:00Z"
266+
267+
Only a case-insensitive value of `true` disables the time-range limit. If the header is omitted or
268+
has any other value, the configured maximum remains enforced.
258269

259270
For all providers and all system concepts:
260271

bootstrap-app/src/cmr/bootstrap/api/bulk_index.clj

Lines changed: 27 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
"Defines the bulk index functions for the bootstrap API."
33
(:require
44
[clj-time.core :as time]
5+
[clojure.string :as string]
56
[cmr.bootstrap.config :as bootstrap-config]
67
[cmr.bootstrap.api.messages :as msg]
78
[cmr.bootstrap.api.util :as api-util]
@@ -10,6 +11,9 @@
1011
[cmr.common.services.errors :as errors]
1112
[cmr.common.time-keeper :as time-keeper]))
1213

14+
(def ^:private ignore-after-date-time-limit-header
15+
"cmr-bulk-index-ignore-time-range-limit")
16+
1317
(defn- parse-date-time-param
1418
[_param-name date-time]
1519
(if-let [date-time-value (date-time-parser/try-parse-datetime date-time)]
@@ -77,6 +81,12 @@
7781
:invalid-data
7882
(msg/after-date-time-window-exceeded max-window-hours)))))
7983

84+
(defn- ignore-after-date-time-limit?
85+
[headers]
86+
(= "true"
87+
(some-> (get headers ignore-after-date-time-limit-header)
88+
string/lower-case)))
89+
8090
(defn index-provider
8191
"Index all the collections and granules for a given provider."
8292
[context provider-id-map params]
@@ -112,20 +122,23 @@
112122

113123
(defn data-later-than-date-time
114124
"Index all data with a revision-date later than the given date-time, with the upper bound set to the request time."
115-
[context body params]
116-
(let [dispatcher (api-util/get-dispatcher context params :index-data-between-date-time)
117-
provider-ids (get body "provider_ids")
118-
date-time (:date_time params)
119-
start-date-time (parse-date-time-param :date_time date-time)
120-
end-date-time (time-keeper/now)]
121-
(validate-date-time-range start-date-time end-date-time)
122-
(validate-after-date-time-window start-date-time end-date-time)
123-
{:status 202
124-
:body {:message (msg/data-later-than-date-time
125-
params
126-
(service/index-data-between-date-time
127-
context dispatcher provider-ids start-date-time end-date-time)
128-
date-time)}}))
125+
([context body params]
126+
(data-later-than-date-time context body params {}))
127+
([context body params headers]
128+
(let [dispatcher (api-util/get-dispatcher context params :index-data-between-date-time)
129+
provider-ids (get body "provider_ids")
130+
date-time (:date_time params)
131+
start-date-time (parse-date-time-param :date_time date-time)
132+
end-date-time (time-keeper/now)]
133+
(validate-date-time-range start-date-time end-date-time)
134+
(when-not (ignore-after-date-time-limit? headers)
135+
(validate-after-date-time-window start-date-time end-date-time))
136+
{:status 202
137+
:body {:message (msg/data-later-than-date-time
138+
params
139+
(service/index-data-between-date-time
140+
context dispatcher provider-ids start-date-time end-date-time)
141+
date-time)}})))
129142

130143
(defn data-between-date-time
131144
"Index data with revision-date in the requested date-time range.

bootstrap-app/src/cmr/bootstrap/api/routes.clj

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -61,9 +61,9 @@
6161
(POST "/collections" {:keys [request-context body params]}
6262
(acl/verify-ingest-management-permission request-context :update)
6363
(bulk-index/index-collection request-context body params))
64-
(POST "/after_date_time" {:keys [request-context body params]}
64+
(POST "/after_date_time" {:keys [request-context body params headers]}
6565
(acl/verify-ingest-management-permission request-context :update)
66-
(bulk-index/data-later-than-date-time request-context body params))
66+
(bulk-index/data-later-than-date-time request-context body params headers))
6767
(POST "/between_date_time" {:keys [request-context body params]}
6868
(acl/verify-ingest-management-permission request-context :update)
6969
(bulk-index/data-between-date-time request-context body params))

bootstrap-app/src/cmr/bootstrap/config.clj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@
4949
(defconfig bulk-index-after-date-time-max-window-hours
5050
"Maximum number of hours allowed for /bulk_index/after_date_time. Larger windows should use
5151
/bulk_index/between_date_time explicitly."
52-
{:default 168
52+
{:default 720
5353
:type Long})
5454

5555
(declare initialize-kms-on-boot)

bootstrap-app/test/cmr/bootstrap/test/api/bulk_index_test.clj

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,42 @@
204204
{}
205205
{:date_time "2026-05-13T01:00:00Z"})))))))
206206

207+
(deftest data-later-than-date-time-supports-time-range-limit-override
208+
(let [context {:system :system}
209+
service-call (atom nil)]
210+
(with-redefs [api-util/get-dispatcher (constantly :dispatcher)
211+
time-keeper/now (constantly (time/date-time 2026 5 13 5 0))
212+
bootstrap-config/bulk-index-after-date-time-max-window-hours (constantly 3)
213+
service/index-data-between-date-time
214+
(fn [& args]
215+
(reset! service-call args)
216+
{:message "indexed"})]
217+
(testing "When the override header is true, then a range over the configured limit is accepted"
218+
(is (= 202
219+
(:status
220+
(bulk-index/data-later-than-date-time
221+
context
222+
{"provider_ids" ["PROV1"]}
223+
{:date_time "2026-05-13T01:00:00Z"}
224+
{"cmr-bulk-index-ignore-time-range-limit" "TRUE"}))))
225+
(is (= [context
226+
:dispatcher
227+
["PROV1"]
228+
(time/date-time 2026 5 13 1 0)
229+
(time/date-time 2026 5 13 5 0)]
230+
@service-call)))
231+
232+
(testing "When the override header is not true, then the configured range limit is enforced"
233+
(doseq [header-value ["false" "invalid"]]
234+
(is (= :invalid-data
235+
(:type
236+
(service-error
237+
#(bulk-index/data-later-than-date-time
238+
context
239+
{}
240+
{:date_time "2026-05-13T01:00:00Z"}
241+
{"cmr-bulk-index-ignore-time-range-limit" header-value}))))))))))
242+
207243
(deftest data-later-than-date-time-validates-range
208244
(let [context {:system :system}]
209245
(with-redefs [api-util/get-dispatcher (constantly :dispatcher)

system-int-test/test/cmr/system_int_test/bootstrap/bulk_index/concepts_test.clj

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -318,13 +318,13 @@
318318
(deftest ^:oracle bulk-index-after-date-time-rejects-large-window
319319
(s/only-with-real-database
320320
(try
321-
(dev-sys-util/freeze-time! "3016-01-10T00:00:00Z")
321+
(dev-sys-util/freeze-time! "3016-02-01T00:00:00Z")
322322
(let [{:keys [status errors]} (bootstrap/bulk-index-after-date-time
323-
"3016-01-02T00:00:00Z"
323+
"3016-01-01T00:00:00Z"
324324
{tc/token-header (tc/echo-system-token)}
325325
["PROV1"])]
326326
(is (= 422 status))
327-
(is (re-find #"The requested time window exceeds the /bulk_index/after_date_time limit of 168 hours"
327+
(is (re-find #"The requested time window exceeds the /bulk_index/after_date_time limit of 720 hours"
328328
(first errors))))
329329
(finally
330330
(dev-sys-util/clear-current-time!)))))

0 commit comments

Comments
 (0)