Skip to content

Commit e694fe0

Browse files
committed
Fix Sorting by _lastUpdated
Closes: #904
1 parent c7e408d commit e694fe0

7 files changed

Lines changed: 55 additions & 48 deletions

File tree

modules/db-protocols/src/blaze/db/impl/protocols.clj

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -128,7 +128,10 @@
128128
(-sorted-index-handles
129129
[search-param batch-db tid direction]
130130
[search-param batch-db tid direction start-id]
131-
"Returns a reducible collection of index handles sorted by the sort clause.")
131+
"Returns a reducible collection of index handles sorted by the sort clause.
132+
133+
The `start-id` is only a performance hint. Search params are allowed to
134+
return all index handles, even if a `start-id` is supplied.")
132135
(-supports-ordered-compartment-index-handles [search-param values]
133136
"Returns true if `search-param` supports fetching ordered compartment index handles with `values`.")
134137
(-ordered-compartment-index-handles

modules/db/src/blaze/db/impl/index.clj

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@
44
[blaze.anomaly :as ba :refer [if-ok when-ok]]
55
[blaze.async.comp :as ac :refer [do-sync]]
66
[blaze.coll.core :as coll]
7-
[blaze.db.impl.codec :as codec]
87
[blaze.db.impl.index.index-handle :as ih]
98
[blaze.db.impl.index.plan :as plan]
109
[blaze.db.impl.protocols :as p]
@@ -261,10 +260,9 @@
261260
(comp (resource-handle-mapper batch-db tid clauses other-clauses)
262261
(distinct))
263262
(index-handles* batch-db tid (first first-clause) start-id))
264-
(let [start-id (codec/id-string start-id)]
265-
(coll/eduction
266-
(drop-while #(not= start-id (:id %)))
267-
(unordered-resource-handles batch-db tid clauses))))))
263+
(coll/eduction
264+
(u/drop-while-not-start-id start-id)
265+
(unordered-resource-handles batch-db tid clauses)))))
268266

269267
(defn type-query
270268
"Returns a reducible collection of resource handles from `batch-db` of type
@@ -273,7 +271,8 @@
273271
([batch-db tid {:keys [sort-clause search-clauses]}]
274272
(if sort-clause
275273
(coll/eduction
276-
(resource-handle-mapper batch-db tid search-clauses search-clauses)
274+
(comp (resource-handle-mapper batch-db tid search-clauses search-clauses)
275+
(distinct))
277276
(sorted-index-handles batch-db tid sort-clause))
278277
(let [[scan-clauses other-clauses] (type-query-plan* batch-db tid search-clauses)]
279278
(if (seq scan-clauses)
@@ -282,7 +281,9 @@
282281
([batch-db tid {:keys [sort-clause search-clauses]} start-id]
283282
(if sort-clause
284283
(coll/eduction
285-
(resource-handle-mapper batch-db tid search-clauses search-clauses)
284+
(comp (resource-handle-mapper batch-db tid search-clauses search-clauses)
285+
(distinct)
286+
(u/drop-while-not-start-id start-id))
286287
(sorted-index-handles batch-db tid sort-clause start-id))
287288
(let [[scan-clauses other-clauses] (type-query-plan* batch-db tid search-clauses)]
288289
(if (seq scan-clauses)

modules/db/src/blaze/db/impl/search_param.clj

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,9 @@
7878
"Returns a reducible collection of index handles sorted by `search-param` in
7979
`direction`, starting with `start-id` (optional).
8080
81+
The `start-id` is only a performance hint. Search params are allowed to return
82+
all index handles, even if a `start-id` is supplied.
83+
8184
The index handles are not distinct and not ordered by id."
8285
([search-param batch-db tid direction]
8386
(p/-sorted-index-handles search-param batch-db tid direction))

modules/db/src/blaze/db/impl/search_param/chained.clj

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -122,13 +122,12 @@
122122
(p/-index-handles search-param batch-db ref-tid modifier compiled-value)))
123123

124124
(-index-handles [this batch-db tid modifier compiled-value start-id]
125-
(let [start-id (codec/id-string start-id)]
126-
(coll/eduction
127-
(comp (u/resource-handle-xf batch-db tid)
128-
(distinct)
129-
(drop-while #(not= start-id (:id %)))
130-
(map ih/from-resource-handle))
131-
(p/-index-handles this batch-db tid modifier compiled-value))))
125+
(coll/eduction
126+
(comp (u/resource-handle-xf batch-db tid)
127+
(distinct)
128+
(u/drop-while-not-start-id start-id)
129+
(map ih/from-resource-handle))
130+
(p/-index-handles this batch-db tid modifier compiled-value)))
132131

133132
(-supports-ordered-compartment-index-handles [_ _]
134133
false)

modules/db/src/blaze/db/impl/search_param/date.clj

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -420,13 +420,9 @@
420420
(all-keys batch-db c-hash tid)
421421
(all-keys-prev batch-db c-hash tid))))
422422

423-
(-sorted-index-handles [_ batch-db tid direction start-id]
424-
(coll/eduction
425-
(comp drop-value
426-
u/by-id-grouper)
427-
(if (= :asc direction)
428-
(all-keys batch-db c-hash tid start-id)
429-
(all-keys-prev batch-db c-hash tid start-id))))
423+
(-sorted-index-handles [search-param batch-db tid direction _start-id]
424+
;; starting with a particilar id isn't possible
425+
(p/-sorted-index-handles search-param batch-db tid direction))
430426

431427
(-supports-ordered-compartment-index-handles [_ _]
432428
false)

modules/db/src/blaze/db/impl/search_param/util.clj

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -153,3 +153,7 @@
153153
(if (known? modifier)
154154
(unsupported-modifier-anom code modifier)
155155
(unknown-modifier-anom code modifier)))
156+
157+
(defn drop-while-not-start-id [start-id]
158+
(let [start-id (codec/id-string start-id)]
159+
(drop-while #(not= start-id (:id %)))))

modules/db/test/blaze/db/api_test.clj

Lines changed: 27 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -2378,22 +2378,25 @@
23782378
[0 :fhir/type] := :fhir/Patient
23792379
[0 :id] := "0")))
23802380

2381-
;; TODO: fix this https://github.com/samply/blaze/issues/904
2382-
#_(testing "sorting by _lastUpdated returns only the newest version of the patient"
2383-
(with-system-data [{:blaze.db/keys [node]} (with-system-clock config)]
2384-
[[[:put {:fhir/type :fhir/Patient :id "0"}]]
2385-
[[:put {:fhir/type :fhir/Patient :id "1"}]]]
2381+
(testing "sorting by _lastUpdated returns every resource only once"
2382+
(with-system-data [{:blaze.db/keys [node]} system-clock-config]
2383+
[[[:put {:fhir/type :fhir/Patient :id "0"}]]
2384+
[[:put {:fhir/type :fhir/Patient :id "1"}]]]
23862385

2387-
;; we have to sleep more than one second here because dates are index only with second resolution
2388-
(Thread/sleep 2000)
2389-
@(d/transact node [[:put {:fhir/type :fhir/Patient :id "0"}]])
2386+
;; we have to sleep more than one second here because dates are index only with second resolution
2387+
(Thread/sleep 1100)
2388+
@(d/transact node [[:put {:fhir/type :fhir/Patient :id "0"}]])
23902389

2391-
(doseq [dir [:asc :desc]]
2392-
(given-type-query node "Patient" [[:sort "_lastUpdated" dir]]
2393-
count := 2
2394-
[0 :fhir/type] := :fhir/Patient
2395-
[0 :id] := "0"
2396-
[0 :active] := #fhir/boolean false))))
2390+
(let [clauses [[:sort "_lastUpdated" :desc]]]
2391+
(given-type-query node "Patient" clauses
2392+
count := 2
2393+
[0 :id] := "0"
2394+
[1 :id] := "1")
2395+
2396+
(testing "it is possible to start with the second patient"
2397+
(given (pull-type-query node "Patient" clauses "1")
2398+
count := 1
2399+
[0 :id] := "1")))))
23972400

23982401
(testing "a node with three patients in one transaction"
23992402
(with-system-data [{:blaze.db/keys [node]} config]
@@ -2402,18 +2405,16 @@
24022405
[:put {:fhir/type :fhir/Patient :id "2" :active #fhir/boolean true}]]]
24032406

24042407
(testing "two active patients will be found"
2405-
(given-type-query node "Patient" [["active" "true"]]
2406-
count := 2
2407-
[0 :fhir/type] := :fhir/Patient
2408-
[0 :id] := "0"
2409-
[1 :fhir/type] := :fhir/Patient
2410-
[1 :id] := "2"))
2408+
(let [clauses [["active" "true"]]]
2409+
(given-type-query node "Patient" clauses
2410+
count := 2
2411+
[0 :id] := "0"
2412+
[1 :id] := "2")
24112413

2412-
(testing "it is possible to start with the second patient"
2413-
(given (pull-type-query node "Patient" [["active" "true"]] "2")
2414-
count := 1
2415-
[0 :fhir/type] := :fhir/Patient
2416-
[0 :id] := "2"))))
2414+
(testing "it is possible to start with the second patient"
2415+
(given (pull-type-query node "Patient" clauses "2")
2416+
count := 1
2417+
[0 :id] := "2"))))))
24172418

24182419
(testing "special case of _lastUpdated date search parameter"
24192420
(testing "inequality searches do return every resource only once"
@@ -2422,7 +2423,7 @@
24222423
[[:put {:fhir/type :fhir/Patient :id "1"}]]]
24232424

24242425
;; we have to sleep more than one second here because dates are index only with second resolution
2425-
(Thread/sleep 2000)
2426+
(Thread/sleep 1100)
24262427
@(d/transact node [[:put {:fhir/type :fhir/Patient :id "0"}]])
24272428

24282429
(given-type-query node "Patient" [["_lastUpdated" "ge2000-01-01"]]

0 commit comments

Comments
 (0)