Skip to main content

Temporal delete-by-query

Delete a slice of temporal history across many entities in one request: pick the entities with a query, pick the attributes, and give a time window. DELETE /temporal/entities?type=Vehicle&drop=speed&timerel=before&timeAt=2024-01-01T00:00:00Z removes every speed reading before 2024 from every vehicle. Off by default.

At a glance​

Turning it on​

[extensions.temporal_delete_by_query]
mode = "enabled"
max_matches = 100000

extensions.temporal_delete_by_query.max_matches (default 100,000) is the most instances one request may delete. Andromeda counts first, and if the count is over the limit, the request gets 403 TooManyResults and nothing is removed.

Using it​

Preview with dryRun=true first. It tells you how many instances would go, and removes nothing:

DELETE /ngsi-ld/v1/temporal/entities?type=Vehicle&timerel=between&timeAt=2024-01-01T00:00:00Z&endTimeAt=2024-06-01T00:00:00Z&drop=speed&dryRun=true
HTTP/1.1 200 OK
Content-Type: application/json

{
"deleted": 4213
}

Then send the same request without dryRun:

DELETE /ngsi-ld/v1/temporal/entities?type=Vehicle&timerel=between&timeAt=2024-01-01T00:00:00Z&endTimeAt=2024-06-01T00:00:00Z&drop=speed
HTTP/1.1 204 No Content

Parameters​

Choosing entities:

  • id, type and idPattern
  • q, the attribute filter
  • georel, geometry, coordinates and geoproperty, the geo filter
  • scopeQ, the Scope filter
  • csf, which is checked but never forwarded, since the delete is local

Choosing the window:

  • timerel, timeAt and endTimeAt
  • timeproperty, the time axis: observedAt (default), createdAt, modifiedAt or deletedAt

Choosing what to delete:

  • drop, the attributes whose instances go, comma-separated
  • keep, the attributes to spare, comma-separated. Every other attribute's instances go. You can't combine it with drop.
  • datasetId, the dataset instances to remove, comma-separated. @none is the default instance.
  • deleteAll, every dataset instance, said explicitly
  • dryRun, to count without deleting

Parameters that only shape a read (format, lastN, pick, omit, join, paging, ordering) get 400 InvalidRequest, so a typo never gets silently ignored.

The window​

The window includes its start and leaves out its end, like a temporal query's window. A delete removes exactly the instances a query over the same window would return.

timerelDeletes instances on the timeproperty axis that are
noneat any time
beforebefore timeAt
afterat or after timeAt
betweenat or after timeAt, and before endTimeAt

between needs endTimeAt.

What goes​

ScopeRemoves, inside the window
drop=a,bevery instance of a and b, in every dataset
keep=a,bevery instance of every attribute except a and b
neitherevery instance of every attribute
plus datasetId=Xonly the instances in dataset X
plus deleteAllevery dataset, the same as leaving out datasetId

Without a window, deleteAll removes the chosen attributes from the history altogether. With a window, only that slice goes and the attributes stay. The Scope history is never touched.

What gets refused​

  • 400 BadRequestData for a request with only a time window

    A window alone doesn't justify wiping every entity's history. Add at least one of type, drop, keep, q or a geoquery.

  • 400 BadRequestData for datasetId together with deleteAll

    deleteAll already means every dataset. Send one or the other.

  • 403 TooManyResults when more than extensions.temporal_delete_by_query.max_matches instances match

    Nothing is removed. Narrow the request, or delete in smaller windows.

Context sources​

The delete is never forwarded. It selects and deletes in this broker's history only.

Why it is an extension​

Every temporal delete in the specification targets one entity by identifier, and none takes a time window:

  • Delete Attribute from Temporal Evolution removes one attribute, or one datasetId instance of it, from one entity.
  • Delete Attribute Instance removes one instance of one attribute of one entity.
  • Delete Temporal Evolution removes the whole history of one entity.

This extension combines an entity query, attribute and dataset scoping as Delete Attribute from Temporal Evolution has it, and a time window in one operation. The too-wide rule and the match limit follow what the specification asks of Purge Entities, and parameters the operation doesn't define are refused.