TWIN Supply Chain Docs
API ReferencePublish Data

Update consignment

POST/supply-chain/data-space/inbox

Authorization

jwtBearerAuthScheme
AuthorizationBearer <token>

In: header

Request Body

application/json

Request to notify the dataspace inbox via the simplified session-auth facade. The caller supplies only the activity; the server injects the generator and the trust credential and ensures the underlying dataspace transfer.

TypeScript Definitions

Use the request body type in TypeScript.

A JSON-LD node object: free-form properties describing a node in the graph.

Response Body

application/json

application/json

application/json

application/json

curl -X POST "https://example.com/supply-chain/data-space/inbox" \  -H "Content-Type: application/json" \  -d '{    "@context": [      "https://www.w3.org/ns/activitystreams"    ],    "type": "Update",    "actor": {      "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",      "type": "TradeParty",      "registeredId": {        "@type": "https://ref.gs1.org/voc/OrganizationID_Type-DID",        "@value": "did:web:your-org.example.com"      }    },    "object": {      "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",      "type": "Consignment",      "identifier": "MYREF-001",      "globalId": "urn:uuid:a1b2c3d4-e5f6-7890-abcd-ef1234567890",      "summaryDescription": "RORO vehicle consignment"    }  }'
{}
{  "name": "GeneralError",  "message": "errorMessage",  "properties": {    "foo": "bar"  }}
{  "name": "UnauthorizedError",  "message": "errorMessage"}
{  "name": "InternalServerError",  "message": "errorMessage"}

Changes a consignment you already published. The payload is the same as Create consignment — the difference is what happens to the fields you leave out.

Every request requires Cookie: access_token=<jwt>. See Authentication.

An update replaces, it does not merge. Always resend the complete consignment, not just the fields that changed.


Every request body is an activity: a JSON wrapper with a type that tells TWIN what to do, and an object that carries the payload. target is not used by this activity. actor is your organisation and is the same on every request — see Actor.

{
  "@context": ["https://www.w3.org/ns/activitystreams"],
  "type": "Update",
  "actor": { ... },
  "object": { ... }
}

Activity schema

The full activity schema including required fields, actor, object, and target:

{
	"$schema": "https://json-schema.org/draft/2020-12/schema",
	"$id": "https://schema.twindev.org/supply-chain/SupplyChainAppActivity",
	"title": "SupplyChainAppActivity",
	"description": "Supply Chain App Activity.",
	"type": "object",
	"properties": {
		"actor": {
			"$ref": "https://schema.twindev.org/supply-chain/SupplyChainAppActor",
			"description": "The actor responsible for the activity."
		},
		"object": {
			"$ref": "https://schema.twindev.org/supply-chain/SupplyChainAppObject",
			"description": "Activity's object."
		},
		"target": {
			"type": "object",
			"properties": {
				"@context": {
					"const": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld"
				},
				"type": {
					"const": "Consignment"
				},
				"identifier": {
					"type": "string"
				},
				"globalId": {
					"type": "string"
				}
			},
			"required": [
				"@context",
				"type",
				"identifier",
				"globalId"
			],
			"description": "Target information."
		}
	},
	"required": [
		"actor",
		"object"
	],
	"allOf": [
		{
			"description": "A dataspace activity that restricts an activity so that it can be handled by a Dataspace Data Plane",
			"type": "object",
			"properties": {
				"@context": {
					"$ref": "https://schema.twindev.org/w3c-activity-streams/ActivityStreamsContextType",
					"description": "The LD Context.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"type": {
					"anyOf": [
						{
							"$ref": "https://schema.twindev.org/w3c-activity-streams/ActivityStreamsTypes"
						},
						{
							"type": "string"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"$ref": "https://schema.twindev.org/w3c-activity-streams/ActivityStreamsTypes"
									},
									{
										"type": "string"
									}
								]
							}
						}
					],
					"description": "Activity Type.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"id": {
					"type": "string",
					"description": "Global identifier.",
					"format": "uri",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"name": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap"
						}
					],
					"description": "Natural language name.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"nameMap": {
					"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap",
					"description": "Natural language name map.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"summary": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap"
						}
					],
					"description": "Summary of the Activity.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"summaryMap": {
					"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap",
					"description": "Natural language summary map.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"content": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap"
						}
					],
					"description": "Natural language content.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"contentMap": {
					"$ref": "https://schema.twindev.org/json-ld/JsonLdLanguageMap",
					"description": "Natural language content map.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"url": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "A link to the representation of the object.\n\nThe value can be a URI or an embedded node object.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"image": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "A graphical representation of the object.\n\nThe value can be a URI or an embedded `Image`/`Link` object.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"icon": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "An icon for the object.\n\nThe value can be a URI or an embedded `Image`/`Link` object.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"published": {
					"type": "string",
					"description": "Published date-time.",
					"format": "date-time",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"updated": {
					"type": "string",
					"description": "Updated date-time.",
					"format": "date-time",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"startTime": {
					"type": "string",
					"description": "Start time.",
					"format": "date-time",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"endTime": {
					"type": "string",
					"description": "End time.",
					"format": "date-time",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"duration": {
					"type": "string",
					"description": "Duration.",
					"format": "duration",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"generator": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "The generator of the Activity.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"attachment": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Attachments.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"attributedTo": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Objects attributed to.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"audience": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Audience.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"context": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Context.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"location": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Location.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"tag": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Tag.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"inReplyTo": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "In reply to.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"replies": {
					"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject",
					"description": "Replies collection.\n\nTypically an embedded `Collection` of Objects that are replies to this object.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"preview": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Preview.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"to": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "To.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"bto": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "BTo.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"cc": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "CC.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"bcc": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "BCC.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"mediaType": {
					"type": "string",
					"description": "MIME media type of the referenced resource.",
					"$comment": "Inherited from ActivityStreamsObject"
				},
				"result": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Result of the Activity.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"origin": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Activity's origin.",
					"$comment": "Inherited from ActivityStreamsActivity"
				},
				"instrument": {
					"anyOf": [
						{
							"type": "string"
						},
						{
							"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
						},
						{
							"type": "array",
							"items": {
								"anyOf": [
									{
										"type": "string"
									},
									{
										"$ref": "https://schema.twindev.org/json-ld/JsonLdNodeObject"
									}
								]
							}
						}
					],
					"description": "Instrument used in the Activity.",
					"$comment": "Inherited from ActivityStreamsActivity"
				}
			},
			"required": [
				"@context",
				"type"
			],
			"$comment": "Inlined utility base type DataspaceActivity so utility transformations can operate on concrete properties instead of a $ref."
		}
	]
}

What an update replaces

Changes a consignment that already exists. TWIN matches it by globalId or identifier and replaces the consignment with the data you send, so any field you omit is removed.

Attached documents and recorded events stay attached — an update never removes them. Omitting includedConsignment also leaves the existing items untouched, but sending it replaces the whole list, so include every item you want to keep. Fields an event wrote onto the consignment itself (carrierParty and carrierAssignedId, set by a Carrier Booking event) follow the normal rule: omit them and they are removed.

The consignment list is not a reliable check for this. Its summary keeps the last value it knew for any field the update omitted, so ports, transport mode and parties can still be listed for a consignment that no longer carries them. Read the consignment itself to see what actually remains.

DataEffect of an update
Attached documentsKept — an update never removes them
Recorded eventsKept — an update never removes them
includedConsignment (the items)Omit it and the items are untouched; send it and the whole list is replaced
Fields written by an event (carrierParty, carrierAssignedId)Normal rule — omit them and they are removed
atDeparture/atArrivalTransportMovementNormal rule — omit them and they are removed, along with the ports derived from them

The ports of entry and exit are derived from those movements, and data sharing matches on the country behind the port of entry. An update that omits them removes them from the consignment, so resend the movements whenever it should stay shareable.

Changing identifier or globalId does not rename a consignment. TWIN matches on them, so a new value creates a separate consignment instead of updating this one.

Three fields are always required in object: @context, identifier, and globalId. All UNECE D23B fields are optional and validated when present.

FieldTypeRequiredDescription
@contextstringYesMust be "https://vocabulary.uncefact.org/unece-context-D23B.jsonld"
identifierstringYesYour internal reference for this consignment
globalIdstringYesA globally unique ID — use a UUID URN: urn:uuid:<uuid>

Validation schema

Defines what TWIN accepts and validates. Required fields are @context, identifier, and globalId — all other UNECE D23B fields are optional.

{
	"$schema": "https://json-schema.org/draft/2020-12/schema",
	"$id": "https://schema.twindev.org/supply-chain/SupplyChainAppConsignment",
	"title": "SupplyChainAppConsignment",
	"description": "V2 consignment (D23B context).\nAll extended fields are optional for ingestion but validated if present.\nOnly minimal identity fields are required; all other UNECE fields are optional but validated if present.",
	"type": "object",
	"properties": {
		"@context": {
			"$ref": "https://schema.twindev.org/unece/UneceContextType",
			"description": "JSON-LD Context."
		},
		"globalId": {
			"anyOf": [
				{
					"type": "string"
				},
				{
					"$ref": "https://schema.twindev.org/json-ld/JsonLdValueObject"
				}
			],
			"description": "A global identifier of this supply chain consignment."
		},
		"identifier": {
			"anyOf": [
				{
					"type": "string"
				},
				{
					"$ref": "https://schema.twindev.org/json-ld/JsonLdValueObject"
				}
			],
			"description": "A unique identifier for this referenced supply chain consignment."
		},
		"consignmentItemQuantity": {
			"$ref": "https://schema.twindev.org/supply-chain/WrappedQuantity",
			"description": "Wrapped quantity structures."
		},
		"packageQuantity": {
			"$ref": "https://schema.twindev.org/supply-chain/WrappedQuantity",
			"description": "Wrapped package quantity."
		},
		"weightUnitNetWeightMeasure": {
			"type": "array",
			"items": {
				"$ref": "https://schema.twindev.org/supply-chain/WrappedWeightMeasure"
			},
			"description": "Wrapped weight net measurement"
		}
	},
	"required": [
		"@context",
		"globalId",
		"identifier"
	],
	"allOf": [
		{
			"$ref": "https://schema.twindev.org/unece/UneceConsignment"
		}
	]
}

For quantity and weight fields, TWIN uses wrapper objects that pair a numeric value with a unit code:

{
	"$schema": "https://json-schema.org/draft/2020-12/schema",
	"$id": "https://schema.twindev.org/supply-chain/WrappedQuantity",
	"title": "WrappedQuantity",
	"description": "Wrapped UNECE quantity structure (D23B).",
	"type": "object",
	"properties": {
		"unece:QuantityTypeValue": {
			"type": "string",
			"description": "Quantity numeric value."
		},
		"unece:QuantityTypeCode": {
			"$ref": "https://schema.twindev.org/unece/UneceQuantityCode",
			"description": "Unit of measure code."
		}
	},
	"required": [
		"unece:QuantityTypeValue"
	],
	"allOf": [
		{
			"$ref": "https://schema.twindev.org/unece/UneceQuantityType"
		}
	]
}
{
	"$schema": "https://json-schema.org/draft/2020-12/schema",
	"$id": "https://schema.twindev.org/supply-chain/WrappedWeightMeasure",
	"title": "WrappedWeightMeasure",
	"description": "Wrapped UNECE weight measure structure.",
	"type": "object",
	"properties": {
		"unece:WeightUnitMeasureTypeValue": {
			"type": "string",
			"description": "Weight measure numeric value."
		},
		"unece:WeightUnitMeasureTypeCode": {
			"$ref": "https://schema.twindev.org/unece/UneceWeightUnitMeasureCode",
			"description": "Unit of measure code."
		}
	},
	"required": [
		"unece:WeightUnitMeasureTypeValue"
	],
	"allOf": [
		{
			"$ref": "https://schema.twindev.org/unece/UneceWeightUnitMeasureType"
		}
	]
}

Updating an existing consignment (Example)

Include every field you want to keep — TWIN replaces the consignment with the data you send, so anything you omit is removed. Here the carrier booking is added and everything published above is resent unchanged.

{
  "@context": ["https://www.w3.org/ns/activitystreams"],
  "type": "Update",
  "actor": {
    "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",
    "type": "TradeParty",
    "registeredId": {
      "@type": "https://ref.gs1.org/voc/OrganizationID_Type-DID",
      "@value": "did:web:acme-freight.example.com"
    }
  },
  "object": {
    "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",
    "type": "Consignment",
    "identifier": "ACME-2026-001",
    "globalId": "urn:uuid:a1b2c3d4-e5f6-7890-abcd-ef1234567890",
    "summaryDescription": "RORO vehicle consignment",
    "packageQuantity": {
      "type": "QuantityType",
      "unece:QuantityTypeValue": "12"
    },
    "atDepartureTransportMovement": {
      "type": "TransportMovement",
      "transportModeCode": "unece:TransportModeCodeList#1",
      "departureEvent": [
        {
          "type": "TransportEvent",
          "scheduledOccurrenceDateTime": "2026-06-01T08:00:00.000Z",
          "occurrenceLogisticsLocation": {
            "type": "LogisticsLocation",
            "name": "Port of Calais",
            "identifier": {
              "@type": "https://ref.gs1.org/voc/LocationID_Type-UN_LOCODE",
              "@value": "FRCQF"
            }
          }
        }
      ],
      "usedTransportMeans": {
        "type": "LogisticsTransportMeans",
        "transportMeansTypeCode": "unece:TransportMeansTypeCodeList#1512",
        "identifier": { "@value": "Channel Voyager" },
        "attachedLogisticsTransportEquipment": [
          {
            "type": "LogisticsTransportEquipment",
            "identifier": "TRAILER-XY-1",
            "carrierAssignedBookingId": "BOOKING-XY9921"
          }
        ]
      }
    },
    "atArrivalTransportMovement": {
      "type": "TransportMovement",
      "transportModeCode": "unece:TransportModeCodeList#1",
      "arrivalEvent": [
        {
          "type": "TransportEvent",
          "scheduledOccurrenceDateTime": "2026-06-01T14:30:00.000Z",
          "occurrenceLogisticsLocation": {
            "type": "LogisticsLocation",
            "name": "Port of Felixstowe",
            "identifier": {
              "@type": "https://ref.gs1.org/voc/LocationID_Type-UN_LOCODE",
              "@value": "GBFXT"
            }
          }
        }
      ]
    },
    "mainCarriageTransportMovement": [
      {
        "type": "TransportMovement",
        "transportModeCode": "unece:TransportModeCodeList#1",
        "usedTransportMeans": {
          "type": "LogisticsTransportMeans",
          "transportMeansTypeCode": "unece:TransportMeansTypeCodeList#1512"
        }
      }
    ],
    "utilizedTransportEquipment": [
      {
        "type": "LogisticsTransportEquipment",
        "identifier": "TRAILER-XY-1"
      }
    ],
    "includedConsignment": [
      {
        "type": "Consignment",
        "identifier": "ITEM-001",
        "consignorParty": {
          "type": "TradeParty",
          "name": "Acme Exports Ltd",
          "postalAddress": {
            "type": "TradeAddress",
            "tradeAddressCountryId": "unece:CountryId#FR"
          }
        },
        "consigneeParty": {
          "type": "TradeParty",
          "name": "UK Imports Co",
          "postalAddress": {
            "type": "TradeAddress",
            "tradeAddressCountryId": "unece:CountryId#GB"
          }
        },
        "includedConsignmentItem": [
          {
            "type": "ConsignmentItem",
            "goodsTypeCode": "unece:GoodsTypeCodeList#ZZZ",
            "information": "12 pallets of automotive parts",
            "originCountry": {
              "type": "Country",
              "countryId": "unece:CountryId#FR"
            }
          }
        ]
      }
    ]
  }
}
mainCarriageTransportMovement is a list, even for a single movement.

Updating one item in a multi-item consignment (Example)

When an Update includes includedConsignment, TWIN treats it as the complete list of items: matching identifiers are updated, new ones are added, and any item missing from the list is removed. Omit the field to leave items untouched; send an empty array to remove them all.

To change a single item, resend every item you want to keep alongside the one you're updating:

{
  "@context": ["https://www.w3.org/ns/activitystreams"],
  "type": "Update",
  "actor": {
    "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",
    "type": "TradeParty",
    "registeredId": {
      "@type": "https://ref.gs1.org/voc/OrganizationID_Type-DID",
      "@value": "did:web:acme-freight.example.com"
    }
  },
  "object": {
    "@context": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",
    "type": "Consignment",
    "identifier": "ACME-2026-002",
    "globalId": "urn:uuid:b2c3d4e5-f6a7-8901-bcde-f12345678901",
    "includedConsignment": [
      {
        "type": "Consignment",
        "identifier": "ITEM-001",
        "includedConsignmentItem": [
          {
            "type": "ConsignmentItem",
            "information": "500 live chickens"
          }
        ]
      },
      {
        "type": "Consignment",
        "identifier": "ITEM-002",
        "includedConsignmentItem": [
          {
            "type": "ConsignmentItem",
            "information": "60 pallets of consumer electronics"
          }
        ]
      }
    ]
  }
}

Only ITEM-002 changed (40 → 60 pallets); ITEM-001 is resent unchanged so it isn't dropped.

Sending only ITEM-002 here would remove ITEM-001 from the consignment.

Actor

Your organisation as a UNECE TradeParty. Use the same value on every request.

FieldTypeRequiredDescription
@contextstringYesAlways "https://vocabulary.uncefact.org/unece-context-D23B.jsonld"
typestringYesAlways "TradeParty"
registeredIdobjectYesYour organisation's DID — { "@type": "...", "@value": "did:web:your-org.example.com" }

Validation schema

{
	"$schema": "https://json-schema.org/draft/2020-12/schema",
	"$id": "https://schema.twindev.org/supply-chain/SupplyChainAppActor",
	"title": "SupplyChainAppActor",
	"description": "Supply Chain App Actor.",
	"type": "object",
	"properties": {
		"type": {
			"const": "TradeParty",
			"description": "Actor information."
		},
		"registeredId": {
			"type": "object",
			"properties": {
				"@type": {
					"type": "string"
				},
				"@value": {
					"type": "string"
				}
			},
			"required": [
				"@type",
				"@value"
			],
			"description": "Registered identifier for the actor."
		},
		"@context": {
			"const": "https://vocabulary.uncefact.org/unece-context-D23B.jsonld",
			"description": "Context for the actor."
		}
	},
	"required": [
		"type",
		"registeredId",
		"@context"
	],
	"allOf": [
		{
			"$ref": "https://schema.twindev.org/unece/UneceTradeParty"
		}
	]
}

Response

200 OK — the activity was accepted. The response is an activity-log entry describing how it was processed.

{
  "id": "urn:x-activity-log:0199f3b1...",
  "status": "completed",
  "generator": "urn:uuid:...",
  "dateCreated": "2026-06-30T14:00:00.000Z",
  "dateModified": "2026-06-30T14:00:00.001Z",
  "tasks": [
    {
      "taskId": "...",
      "dataspaceAppId": "SupplyChainDataSpaceConnectorApp",
      "result": 0,
      "startDate": "2026-06-30T14:00:00.000Z",
      "endDate": "2026-06-30T14:00:00.001Z",
      "status": "success"
    }
  ]
}

id identifies the activity-log entry, not the consignment. This response carries no consignment id — read the consignment back with the globalId or identifier you published, which Get a Consignment accepts directly.

Accepting the activity is not the same as processing it successfully. A failure inside the supply chain app still comes back as 200, with the reason on the task rather than in the HTTP status — always check the entry's status (completed or error) and each task's status (success or failed):

{
  "id": "urn:x-activity-log:0199f3b1...",
  "status": "error",
  "tasks": [
    {
      "taskId": "...",
      "dataspaceAppId": "SupplyChainDataSpaceConnectorApp",
      "status": "failed",
      "error": {
        "name": "UnprocessableError",
        "source": "DataspaceDataPlaneService",
        "message": "dataspaceDataPlaneService.activitySemanticError",
        "cause": {
          "name": "ValidationError",
          "message": "..."
        }
      }
    }
  ]
}

That is the shape a schema validation failure takes: an UnprocessableError wrapping the ValidationError that describes the offending field.

Errors

Only failures raised before the activity is handed to the supply chain app surface as HTTP errors. Anything the app itself rejects — including schema validation — comes back as 200 with the error on the task.

StatusCause
400Malformed activity — not an object, or no type
401Missing or invalid credentials
500The activity could not be submitted to the data space