FIWARE / context.Orion-LD

Context Broker and CEF building block for context data management which supports both the NGSI-LD and the NGSI-v2 APIs
https://www.etsi.org/deliver/etsi_gs/CIM/001_099/009/01.06.01_60/gs_CIM009v010601p.pdf
GNU Affero General Public License v3.0
50 stars 43 forks source link

batch operation 'upsert' returns status 400 for existing entities #393

Closed michaeI-s closed 4 years ago

michaeI-s commented 4 years ago

Hi,

I create a new entity with

curl --location --request POST 'http://<SERVER_IP>:<PORT>/ngsi-ld/v1/entityOperations/upsert' \
--header 'Content-Type: application/ld+json' \
--data-raw '[
    {
        "id": "urn:ngsi-ld:testunit:125",
        "type": "AirQualityObserved",
        "dateObserved": {
            "type": "Property",
            "value": {
                "@type": "DateTime",
                "@value": "2018-08-12T12:00:00Z"
            }
        },
        "airQualityLevel": {
            "type": "Property",
            "value": "moderate"
        },
        "CO_Level": {
            "type": "Property",
            "value": "unhealthy"
        },
        "refPointOfInterest": {
            "type": "Relationship",
            "object": "urn:ngsi-ld:PointOfInterest:RZ:HarbourDistrict"
        },
        "@context": [
            "https://schema.lab.fiware.org/ld/context",
            "https://uri.etsi.org/ngsi-ld/v1/ngsi-ld-core-context.jsonld"
        ]
    }
]'

This works and results in a 204 No Content with empty body.
In the second step I change an attribute's value, let' say from

        ...
        "airQualityLevel": {
            "type": "Property",
            "value": "moderate"
        },
        ...

to

        ...
        "airQualityLevel": {
            "type": "Property",
            "value": "unhealthy"
        },
        ...

and repeat the request above with that new value.

My expectation: The entity with the new attribute value will replace the existing entity in the context broker.

Actual result is a nested error message with the following content:

 {
    "@context": "https://uri.etsi.org/ngsi-ld/v1/ngsi-ld-core-context.jsonld",
    "success": [],
    "errors": [
        {
            "entityId": "urn:ngsi-ld:testunit:125",
            "error": {
                "type": "https://uri.etsi.org/ngsi-ld/errors/BadRequestData",
                "title": "non-matching entity type",
                "detail": "AirQualityObserved",
                "status": 400
            }
        }
    ]
}

I'm using the following Orion-LD version:

{
  "Orion-LD version": "post-v0.1.0",
  "based on orion": "1.15.0-next",
  "kbase version": "0.3",
  "kalloc version": "0.3",
  "khash version": "0.3",
  "kjson version": "0.3",
  "boost version": "1_62",
  "microhttpd version": "0.9.48-0",
  "openssl version": "OpenSSL 1.1.0l  10 Sep 2019",
  "mongo version": "1.1.3",
  "rapidjson version": "1.0.2",
  "libcurl version": "7.52.1",
  "libuuid version": "UNKNOWN",
  "branch": "(HEAD",
  "Next File Descriptor": 18
}

Kind regards, Michael

kzangeli commented 4 years ago

It seems like the broker doesn't approve of the entity type. We decided that entity types should not be able to change. Not sure it's in the etsi spec yet. So, show the exact payload data (and context) of the update, and we'll see if we can find something ... Might be a bug, of course.

michaeI-s commented 4 years ago

The entity type has not changed in the update. The request has the same payload like in the initial request, but with changed attribute value:

curl --location --request POST 'http://<SERVER_IP>:<PORT>/ngsi-ld/v1/entityOperations/upsert' \
--header 'Content-Type: application/ld+json' \
--data-raw '[
    {
        "id": "urn:ngsi-ld:testunit:125",
        "type": "AirQualityObserved",
        "dateObserved": {
            "type": "Property",
            "value": {
                "@type": "DateTime",
                "@value": "2018-08-12T12:00:00Z"
            }
        },
        "airQualityLevel": {
            "type": "Property",
            "value": "unhealthy"
        },
        "CO_Level": {
            "type": "Property",
            "value": "unhealthy"
        },
        "refPointOfInterest": {
            "type": "Relationship",
            "object": "urn:ngsi-ld:PointOfInterest:RZ:HarbourDistrict"
        },
        "@context": [
            "https://schema.lab.fiware.org/ld/context",
            "https://uri.etsi.org/ngsi-ld/v1/ngsi-ld-core-context.jsonld"
        ]
    }
]'

You could even change nothing and fire the same request twice and you would get the same result.

But besides that, the current version of the NGSI-LD spec (https://www.etsi.org/deliver/etsi_gs/CIM/001_099/009/01.02.02_60/gs_cim009v010202p.pdf) says nothing about obligatory retention of the original entity type. It just states (page 64, top):

"If there were an existing Entity with the same Entity Id, it shall be completely replaced by the new Entity content provided, if the requested update mode is 'replace'. "

kzangeli commented 4 years ago

So, it's a bug. No probs. Easy fix. About the NGSI-LD spec, it's true, it's not there yet. In version 1.3.1 it will be there.

michaeI-s commented 4 years ago

Fixed as of version

{
  "Orion-LD version": "post-v0.1.0",
  "based on orion": "1.15.0-next",
  "kbase version": "0.3",
  "kalloc version": "0.3",
  "khash version": "0.3",
  "kjson version": "0.3",
  "boost version": "1_62",
  "microhttpd version": "0.9.48-0",
  "openssl version": "OpenSSL 1.1.0l  10 Sep 2019",
  "mongo version": "1.1.3",
  "rapidjson version": "1.0.2",
  "libcurl version": "7.52.1",
  "libuuid version": "UNKNOWN",
  "branch": "(HEAD",
  "Next File Descriptor": 18
}

Thanks again Ken!