Skip to content

Issue with ChangeRequest when adding link to other LogisticsObject

It seems adding statements to the RDF repository does not consider links / IRIs.

Optional<XSD.Datatype> literalDatatype = XSD.Datatype.from(Values.iri(operation.o().datatype()));
Value object;
if (literalDatatype.isPresent()) {
    // a literal is added
    object = Values.literal(operation.o().value(), literalDatatype.get().getCoreDatatype());
} else {
    // an "embedded" object is to be added
    IRI objectIri = bnodeToIri.computeIfAbsent(
        operation.o().value(), s -> Values.iri(operation.o().value())
    );
    //  - add type statement using operations datatype value
    loRepository.add(objectIri, RDF.TYPE, Values.iri(operation.o().datatype()), connection);

    //  - set the object to be the IRI of the "embedded object"
    object = objectIri;
}

(https://git.openlogisticsfoundation.org/wg-digitalaircargo/ne-one/-/blob/9bc97f2a16535332c4c03787d5060137a170ee4d/src/main/java/org/openlogisticsfoundation/neone/service/LogisticsObjectService.java#L412)

Example from https://iata-cargo.github.io/ONE-Record/logistics-objects/#example-c5

Steps to reproduce:

1. Create LogisticsObject

POST /logistics-objects HTTP/1.1
Host: localhost:8080
Content-Type: application/ld+json

{    
    "@type": [
        "LogisticsObject",
        "Piece"
    ],
    "@id": "http://localhost:8080/logistics-objects/piece-1",
    "customsInformation": {
        "@id": "http://localhost:8080/logistics-objecs/customs-information-1"
    },    
    "@context": {
        "@vocab": "https://onerecord.iata.org/ns/cargo#"
    }
}

2. Patch LogisticsObject

PATCH /logistics-objects/piece-1 HTTP/1.1
Host: localhost:8080
Content-Type: application/ld+json

{
    "@context": {
        "cargo": "https://onerecord.iata.org/ns/cargo#",
        "api": "https://onerecord.iata.org/ns/api#"
    },
    "@type": "api:Change",
    "api:hasLogisticsObject": {
        "@id": "http://localhost:8080/logistics-objects/piece-1"
    },
    "api:hasDescription": "add CustomsInformation",
    "api:hasOperation": [
        {
            "@type": "api:Operation",
            "api:op": {
                "@id": "api:ADD"
            },
            "api:s": "http://localhost:8080/logistics-objects/piece-1",
            "api:p": "https://onerecord.iata.org/ns/cargo#customsInformation",
            "api:o": [{
                "@type": "api:OperationObject",
                "api:hasDatatype": "https://onerecord.iata.org/ns/cargo#CustomsInformation",
                "api:hasValue": "http://localhost:8080/logistics-objecs/customs-information-2"
            }]
        }
    ],
    "api:hasRevision": {
        "@type": "http://www.w3.org/2001/XMLSchema#positiveInteger",
        "@value": "1"
    }
}

3. Get LogisticsObject

GET /logistics-objects/piece-1 HTTP/1.1
Host: localhost:8080

Expected result:

{
    "@graph": [
        {
            "@id": "http://localhost:8080/logistics-objects/piece-1",
            "@type": [
                "LogisticsObject",
                "Piece"
            ],
            "customsInformation": [
                {
                    "@id": "http://localhost:8080/logistics-objecs/customs-information-1"
                },
                {
                    "@id": "http://localhost:8080/logistics-objecs/customs-information-2"
                }
            ]
        }
    ],
    "@context": {
        "@vocab": "https://onerecord.iata.org/ns/cargo#"
    }
}

Actual result:

{
    "@graph": [
        {
            "@id": "http://localhost:8080/logistics-objects/piece-1",
            "@type": [
                "LogisticsObject",
                "Piece"
            ],
            "customsInformation": [
                {
                    "@id": "http://localhost:8080/logistics-objecs/customs-information-1"
                },
                {
                    "@id": "neone:8046a599-6ed4-40df-b32e-a779280db788"
                }
            ]
        },
        {
            "@id": "neone:8046a599-6ed4-40df-b32e-a779280db788",
            "@type": "CustomsInformation"
        }
    ],
    "@context": {
        "@vocab": "https://onerecord.iata.org/ns/cargo#"
    }
}
Edited by Daniel A. Doeppner